* src/util/timer.c src/util/timer.h: timer implementation * src/libvirt.c: Initialize timer * src/Makefile.am: build timer * src/libvirt_private.syms: Export public functions Signed-off-by: Wen Congyang <wency@xxxxxxxxxxxxxx> --- cfg.mk | 1 + src/Makefile.am | 3 +- src/libvirt.c | 2 + src/libvirt_private.syms | 6 ++ src/util/timer.c | 159 ++++++++++++++++++++++++++++++++++++++++++++++ src/util/timer.h | 34 ++++++++++ 6 files changed, 204 insertions(+), 1 deletions(-) create mode 100644 src/util/timer.c create mode 100644 src/util/timer.h diff --git a/cfg.mk b/cfg.mk index 03186b3..6909876 100644 --- a/cfg.mk +++ b/cfg.mk @@ -129,6 +129,7 @@ useless_free_options = \ --name=virStoragePoolSourceFree \ --name=virStorageVolDefFree \ --name=virThreadPoolFree \ + --name=virTimerFree \ --name=xmlFree \ --name=xmlXPathFreeContext \ --name=xmlXPathFreeObject diff --git a/src/Makefile.am b/src/Makefile.am index 1eefd39..d2a7c30 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -80,7 +80,8 @@ UTIL_SOURCES = \ util/xml.c util/xml.h \ util/virtaudit.c util/virtaudit.h \ util/virterror.c util/virterror_internal.h \ - util/event_impl.c util/event_impl.h + util/event_impl.c util/event_impl.h \ + util/timer.c util/timer.h EXTRA_DIST += util/threads-pthread.c util/threads-win32.c diff --git a/src/libvirt.c b/src/libvirt.c index ee2495a..b938a60 100644 --- a/src/libvirt.c +++ b/src/libvirt.c @@ -40,6 +40,7 @@ #include "util.h" #include "memory.h" #include "configmake.h" +#include "timer.h" #ifndef WITH_DRIVER_MODULES # ifdef WITH_TEST @@ -332,6 +333,7 @@ virInitialize(void) if (virThreadInitialize() < 0 || virErrorInitialize() < 0 || + virTimerInitialize() < 0 || virRandomInitialize(time(NULL) ^ getpid())) return -1; diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms index 21829fa..c9ee742 100644 --- a/src/libvirt_private.syms +++ b/src/libvirt_private.syms @@ -802,6 +802,12 @@ virThreadSelf; virThreadSelfID; +# timer.h +virTimerNew; +virSetTimeout; +virTimerFree; + + # usb.h usbDeviceFileIterate; usbDeviceGetBus; diff --git a/src/util/timer.c b/src/util/timer.c new file mode 100644 index 0000000..20b8b77 --- /dev/null +++ b/src/util/timer.c @@ -0,0 +1,159 @@ +/* + * timer.c: timer functions + * + * Copyright (C) 2010 Fujitsu Limited + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + * + * Author: Wen Congyang <wency@xxxxxxxxxxxxxx> + */ + +#include <config.h> + +#include "event.h" +#include "event_impl.h" +#include "memory.h" +#include "threads.h" +#include "timer.h" +#include "virterror_internal.h" + +#define VIR_FROM_THIS VIR_FROM_NONE + +struct _virTimer { + int timer_id; + + virTimerCallback function; + void *opaque; +}; + +/* use timerFunc to prevent the user know timer id. */ +static void timerFunc(int timer_id ATTRIBUTE_UNUSED, void *opaque) +{ + virTimerPtr timer = opaque; + timer->function(timer->opaque); +} + +/** + * virTimerNew: + * @callback: the callback to call when timeout has expired + * @opaque: user data to pass to the callback + * + * Create a new timer object. + * + * Returns the poitner to new timer object, or NULL upon error + */ +virTimerPtr virTimerNew(virTimerCallback callback, void *opaque) +{ + virTimerPtr timer = NULL; + + if (VIR_ALLOC(timer) < 0) { + virReportOOMError(); + return NULL; + } + + timer->timer_id = -1; + timer->function = callback; + timer->opaque = opaque; + + return timer; +} + +/** + * virSetTimeout: + * @timer: pointer to timer object + * @expire_time: the new timeout value(must be 0 or above) + * + * Alarm or disalarm the timer. When expire_time is more than 0, alarm the + * timer with the new timeout value. When expire_time is 0, disalarm the timer. + * + * Returns 0 in case of success or -1 in case of error. + */ +int virSetTimeout(virTimerPtr timer, int expire_time) +{ + if (expire_time < 0) { + /* expire_time is invalid */ + return -1; + } + + if (expire_time == 0) { + /* delete the timer */ + if (timer->timer_id == -1) + return 0; + + if (virEventRemoveTimeout(timer->timer_id) < 0) + return -1; + + timer->timer_id = -1; + return 0; + } + + if (timer->timer_id == -1) { + /* add new timer */ + int ret; + + if ((ret = virEventAddTimeout(expire_time, timerFunc, + timer, NULL)) < 0) { + return -1; + } + timer->timer_id = ret; + return 0; + } + + /* update the timer */ + virEventUpdateTimeout(timer->timer_id, expire_time); + return 0; +} + +/** + * virTimerFree: + * @timer: pointer to timer object + * + * Free the associated timer object. + */ +void virTimerFree(virTimerPtr timer) +{ + if (!timer) + return; + + VIR_FREE(timer); +} + +static int timer_initialized = 0; +static virThread timer_thread; +static bool timer_quit = false; + +static void timerThreadFunc(void *opaque ATTRIBUTE_UNUSED) +{ + while(!timer_quit) { + virEventRunOnce(); + } +} + +/* This init function requires: + * 1. single-thread environment. + * 2. it must be called after virThreadInitialize(). + */ +int virTimerInitialize(void) +{ + if (timer_initialized) + return 0; + + if (virThreadCreate(&timer_thread, true, timerThreadFunc, NULL) < 0) + return -1; + + timer_initialized = 1; + timer_quit = false; + return 0; +} diff --git a/src/util/timer.h b/src/util/timer.h new file mode 100644 index 0000000..2d010b1 --- /dev/null +++ b/src/util/timer.h @@ -0,0 +1,34 @@ +/* + * timer.h: structure and entry points for timer support + * + * Copyright (C) 2010 Fujitsu Limited + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + * + * Author: Wen Congyang <wency@xxxxxxxxxxxxxx> + */ + +#ifndef __VIR_TIMER_H__ +# define __VIR_TIMER_H__ + +typedef struct _virTimer virTimer; +typedef virTimer *virTimerPtr; +typedef void (*virTimerCallback)(void *); + +extern virTimerPtr virTimerNew(virTimerCallback, void *); +extern int virSetTimeout(virTimerPtr, int) ATTRIBUTE_NONNULL(1); +extern void virTimerFree(virTimerPtr); +extern int virTimerInitialize(void) ATTRIBUTE_RETURN_CHECK; +#endif /* __VIR_TIMER_H__ */ -- 1.7.1 -- libvir-list mailing list libvir-list@xxxxxxxxxx https://www.redhat.com/mailman/listinfo/libvir-list