kvm tools: Don't dynamically allocate threadpool jobs

To allow efficient use of shorter-term threadpool jobs, don't
allocate them dynamically upon creation. Instead, store them
within 'job' structures.

This will prevent some overhead creating/destroying jobs which live
for a short time.

Signed-off-by: Sasha Levin <levinsasha928@gmail.com>
Signed-off-by: Pekka Enberg <penberg@kernel.org>
This commit is contained in:
Sasha Levin
2011-07-02 19:52:03 -04:00
committed by Will Deacon
parent 97b408af3d
commit df0c7f571e
7 changed files with 50 additions and 53 deletions
+26 -3
View File
@@ -1,14 +1,37 @@
#ifndef KVM__THREADPOOL_H
#define KVM__THREADPOOL_H
#include "kvm/mutex.h"
#include <linux/list.h>
struct kvm;
typedef void (*kvm_thread_callback_fn_t)(struct kvm *kvm, void *data);
struct thread_pool__job {
kvm_thread_callback_fn_t callback;
struct kvm *kvm;
void *data;
int signalcount;
pthread_mutex_t mutex;
struct list_head queue;
};
static inline void thread_pool__init_job(struct thread_pool__job *job, struct kvm *kvm, kvm_thread_callback_fn_t callback, void *data)
{
*job = (struct thread_pool__job) {
.kvm = kvm,
.callback = callback,
.data = data,
.mutex = PTHREAD_MUTEX_INITIALIZER,
};
}
int thread_pool__init(unsigned long thread_count);
void *thread_pool__add_job(struct kvm *kvm, kvm_thread_callback_fn_t callback, void *data);
void thread_pool__do_job(void *job);
void thread_pool__do_job(struct thread_pool__job *job);
#endif
+2 -1
View File
@@ -2,6 +2,7 @@
#define KVM__VIRTIO_9P_H
#include "kvm/virtio.h"
#include "kvm/pci.h"
#include "kvm/threadpool.h"
#include <sys/types.h>
#include <dirent.h>
@@ -34,7 +35,7 @@ struct p9_fid {
struct p9_dev_job {
struct virt_queue *vq;
struct p9_dev *p9dev;
void *job_id;
struct thread_pool__job job_id;
};
struct p9_dev {
+2 -28
View File
@@ -6,17 +6,6 @@
#include <pthread.h>
#include <stdbool.h>
struct thread_pool__job {
kvm_thread_callback_fn_t callback;
struct kvm *kvm;
void *data;
int signalcount;
pthread_mutex_t mutex;
struct list_head queue;
};
static pthread_mutex_t job_mutex = PTHREAD_MUTEX_INITIALIZER;
static pthread_mutex_t thread_mutex = PTHREAD_MUTEX_INITIALIZER;
static pthread_cond_t job_cond = PTHREAD_COND_INITIALIZER;
@@ -139,26 +128,11 @@ int thread_pool__init(unsigned long thread_count)
return i;
}
void *thread_pool__add_job(struct kvm *kvm,
kvm_thread_callback_fn_t callback, void *data)
{
struct thread_pool__job *job = calloc(1, sizeof(*job));
*job = (struct thread_pool__job) {
.kvm = kvm,
.data = data,
.callback = callback,
.mutex = PTHREAD_MUTEX_INITIALIZER
};
return job;
}
void thread_pool__do_job(void *job)
void thread_pool__do_job(struct thread_pool__job *job)
{
struct thread_pool__job *jobinfo = job;
if (jobinfo == NULL)
if (jobinfo == NULL || jobinfo->callback == NULL)
return;
mutex_lock(&jobinfo->mutex);
+3 -4
View File
@@ -18,7 +18,6 @@
#include <linux/virtio_9p.h>
#include <net/9p/9p.h>
/* Warning: Immediately use value returned from this function */
static const char *rel_to_abs(struct p9_dev *p9dev,
const char *path, char *abs_path)
@@ -659,7 +658,7 @@ static void ioevent_callback(struct kvm *kvm, void *param)
{
struct p9_dev_job *job = param;
thread_pool__do_job(job->job_id);
thread_pool__do_job(&job->job_id);
}
static bool virtio_p9_pci_io_out(struct ioport *ioport, struct kvm *kvm,
@@ -694,7 +693,7 @@ static bool virtio_p9_pci_io_out(struct ioport *ioport, struct kvm *kvm,
.vq = queue,
.p9dev = p9dev,
};
job->job_id = thread_pool__add_job(kvm, virtio_p9_do_io, job);
thread_pool__init_job(&job->job_id, kvm, virtio_p9_do_io, job);
ioevent = (struct ioevent) {
.io_addr = p9dev->base_addr + VIRTIO_PCI_QUEUE_NOTIFY,
@@ -717,7 +716,7 @@ static bool virtio_p9_pci_io_out(struct ioport *ioport, struct kvm *kvm,
u16 queue_index;
queue_index = ioport__read16(data);
thread_pool__do_job(p9dev->jobs[queue_index].job_id);
thread_pool__do_job(&p9dev->jobs[queue_index].job_id);
break;
}
case VIRTIO_PCI_STATUS:
+4 -4
View File
@@ -31,7 +31,7 @@
struct blk_dev_job {
struct virt_queue *vq;
struct blk_dev *bdev;
void *job_id;
struct thread_pool__job job_id;
};
struct blk_dev {
@@ -206,7 +206,7 @@ static bool virtio_blk_pci_io_out(struct ioport *ioport, struct kvm *kvm, u16 po
.bdev = bdev,
};
job->job_id = thread_pool__add_job(kvm, virtio_blk_do_io, job);
thread_pool__init_job(&job->job_id, kvm, virtio_blk_do_io, job);
break;
}
@@ -217,7 +217,7 @@ static bool virtio_blk_pci_io_out(struct ioport *ioport, struct kvm *kvm, u16 po
u16 queue_index;
queue_index = ioport__read16(data);
thread_pool__do_job(bdev->jobs[queue_index].job_id);
thread_pool__do_job(&bdev->jobs[queue_index].job_id);
break;
}
@@ -248,7 +248,7 @@ static void ioevent_callback(struct kvm *kvm, void *param)
{
struct blk_dev_job *job = param;
thread_pool__do_job(job->job_id);
thread_pool__do_job(&job->job_id);
}
void virtio_blk__init(struct kvm *kvm, struct disk_image *disk)
+5 -5
View File
@@ -51,7 +51,7 @@ struct con_dev {
u16 queue_selector;
u16 base_addr;
void *jobs[VIRTIO_CONSOLE_NUM_QUEUES];
struct thread_pool__job jobs[VIRTIO_CONSOLE_NUM_QUEUES];
};
static struct con_dev cdev = {
@@ -93,7 +93,7 @@ static void virtio_console__inject_interrupt_callback(struct kvm *kvm, void *par
void virtio_console__inject_interrupt(struct kvm *kvm)
{
thread_pool__do_job(cdev.jobs[VIRTIO_CONSOLE_RX_QUEUE]);
thread_pool__do_job(&cdev.jobs[VIRTIO_CONSOLE_RX_QUEUE]);
}
static bool virtio_console_pci_io_device_specific_in(void *data, unsigned long offset, int size, u32 count)
@@ -203,9 +203,9 @@ static bool virtio_console_pci_io_out(struct ioport *ioport, struct kvm *kvm, u1
vring_init(&queue->vring, VIRTIO_CONSOLE_QUEUE_SIZE, p, VIRTIO_PCI_VRING_ALIGN);
if (cdev.queue_selector == VIRTIO_CONSOLE_TX_QUEUE)
cdev.jobs[cdev.queue_selector] = thread_pool__add_job(kvm, virtio_console_handle_callback, queue);
thread_pool__init_job(&cdev.jobs[cdev.queue_selector], kvm, virtio_console_handle_callback, queue);
else if (cdev.queue_selector == VIRTIO_CONSOLE_RX_QUEUE)
cdev.jobs[cdev.queue_selector] = thread_pool__add_job(kvm, virtio_console__inject_interrupt_callback, queue);
thread_pool__init_job(&cdev.jobs[cdev.queue_selector], kvm, virtio_console__inject_interrupt_callback, queue);
break;
}
@@ -214,7 +214,7 @@ static bool virtio_console_pci_io_out(struct ioport *ioport, struct kvm *kvm, u1
break;
case VIRTIO_PCI_QUEUE_NOTIFY: {
u16 queue_index = ioport__read16(data);
thread_pool__do_job(cdev.jobs[queue_index]);
thread_pool__do_job(&cdev.jobs[queue_index]);
break;
}
case VIRTIO_PCI_STATUS:
+8 -8
View File
@@ -21,13 +21,13 @@
#include <sys/stat.h>
#include <pthread.h>
#define NUM_VIRT_QUEUES 1
#define VIRTIO_RNG_QUEUE_SIZE 128
#define NUM_VIRT_QUEUES 1
#define VIRTIO_RNG_QUEUE_SIZE 128
struct rng_dev_job {
struct virt_queue *vq;
struct rng_dev *rdev;
void *job_id;
struct virt_queue *vq;
struct rng_dev *rdev;
struct thread_pool__job job_id;
};
struct rng_dev {
@@ -146,7 +146,7 @@ static bool virtio_rng_pci_io_out(struct ioport *ioport, struct kvm *kvm, u16 po
.rdev = rdev,
};
job->job_id = thread_pool__add_job(kvm, virtio_rng_do_io, job);
thread_pool__init_job(&job->job_id, kvm, virtio_rng_do_io, job);
break;
}
@@ -156,7 +156,7 @@ static bool virtio_rng_pci_io_out(struct ioport *ioport, struct kvm *kvm, u16 po
case VIRTIO_PCI_QUEUE_NOTIFY: {
u16 queue_index;
queue_index = ioport__read16(data);
thread_pool__do_job(rdev->jobs[queue_index].job_id);
thread_pool__do_job(&rdev->jobs[queue_index].job_id);
break;
}
case VIRTIO_PCI_STATUS:
@@ -182,7 +182,7 @@ static void ioevent_callback(struct kvm *kvm, void *param)
{
struct rng_dev_job *job = param;
thread_pool__do_job(job->job_id);
thread_pool__do_job(&job->job_id);
}
void virtio_rng__init(struct kvm *kvm)