Просмотр исходного кода

deferred timer system so that timers may be deferred during synchronization.

git-svn-id: http://svn.fedorahosted.org/svn/corosync/trunk@1067 fd59a12c-fef9-0310-b244-a6a79926bd2f
Steven Dake 19 лет назад
Родитель
Сommit
ad2fa27191
11 измененных файлов с 404 добавлено и 396 удалено
  1. 6 9
      exec/Makefile
  2. 11 8
      exec/aispoll.c
  3. 3 1
      exec/aispoll.h
  4. 22 26
      exec/amf.c
  5. 19 17
      exec/ckpt.c
  6. 9 19
      exec/evt.c
  7. 51 11
      exec/ipc.c
  8. 17 3
      exec/ipc.h
  9. 28 4
      exec/main.c
  10. 0 287
      exec/tlist.c
  11. 238 11
      exec/tlist.h

+ 6 - 9
exec/Makefile

@@ -44,8 +44,8 @@ ifeq (${OPENAIS_COMPAT}, LINUX)
 endif
 endif
 
 
 # Totem objects
 # Totem objects
-TOTEM_SRC = aispoll.c totemip.c totemnet.c totemrrp.c totemsrp.c totemmrp.c totempg.c tlist.c crypto.c wthread.c
-TOTEM_OBJS = aispoll.o totemip.o totemnet.o totemrrp.o totemsrp.o totemmrp.o totempg.o tlist.o crypto.o wthread.o
+TOTEM_SRC = aispoll.c totemip.c totemnet.c totemrrp.c totemsrp.c totemmrp.c totempg.c crypto.c wthread.c
+TOTEM_OBJS = aispoll.o totemip.o totemnet.o totemrrp.o totemsrp.o totemmrp.o totempg.o crypto.o wthread.o
 EXEC_LIBS = libtotem_pg.a
 EXEC_LIBS = libtotem_pg.a
 
 
 # LCR objects
 # LCR objects
@@ -53,10 +53,10 @@ LCR_SRC = evs.c clm.c amf.c ckpt.c evt.c lck.c msg.c cfg.c cpg.c amfconfig.c ais
 LCR_OBJS = evs.o clm.o amf.o ckpt.o evt.o lck.o msg.o cfg.o cpg.o amfconfig.o aisparser.o vsf_ykd.o
 LCR_OBJS = evs.o clm.o amf.o ckpt.o evt.o lck.o msg.o cfg.o cpg.o amfconfig.o aisparser.o vsf_ykd.o
 
 
 # main executive objects
 # main executive objects
-MAIN_SRC = main.c print.c mempool.c \
-		util.c sync.c ykd.c service.c ipc.c totemconfig.c mainconfig.c
-MAIN_OBJS = main.o print.o mempool.o \
-		util.o sync.o service.o ipc.o totemconfig.o mainconfig.o ../lcr/lcr_ifact.o
+MAIN_SRC = main.c print.c mempool.c util.c sync.c service.c ipc.c timer.c \
+	totemconfig.c mainconfig.c
+MAIN_OBJS = main.o print.o mempool.o util.o sync.o service.o ipc.o timer.o \
+	totemconfig.o mainconfig.o ../lcr/lcr_ifact.o
 OTHER_OBJS = objdb.o
 OTHER_OBJS = objdb.o
 
 
 ifeq (${BUILD_DYNAMIC}, 1) 
 ifeq (${BUILD_DYNAMIC}, 1) 
@@ -246,9 +246,6 @@ totemnet.o: totemnet.c
 wthread.o: wthread.c
 wthread.o: wthread.c
 	$(CC) $(CFLAGS) $(CPPFLAGS) -fPIC -c -o $@ $(*F).c
 	$(CC) $(CFLAGS) $(CPPFLAGS) -fPIC -c -o $@ $(*F).c
 
 
-tlist.o: tlist.c
-	$(CC) $(CFLAGS) $(CPPFLAGS) -fPIC -c -o $@ $(*F).c
-
 crypto.o: crypto.c
 crypto.o: crypto.c
 	$(CC) $(CFLAGS) $(CPPFLAGS) -fPIC -c -o $@ $(*F).c
 	$(CC) $(CFLAGS) $(CPPFLAGS) -fPIC -c -o $@ $(*F).c
 
 

+ 11 - 8
exec/aispoll.c

@@ -56,7 +56,8 @@ struct poll_instance {
 	struct pollfd *ufds;
 	struct pollfd *ufds;
 	int poll_entry_count;
 	int poll_entry_count;
 	struct timerlist timerlist;
 	struct timerlist timerlist;
-	pthread_mutex_t *serialize;
+	void (*serialize_lock_fn) (void);
+	void (*serialize_unlock_fn) (void);
 };
 };
 
 
 /*
 /*
@@ -68,7 +69,9 @@ static struct hdb_handle_database poll_instance_database = {
 	.iterator	= 0
 	.iterator	= 0
 };
 };
 
 
-poll_handle poll_create (pthread_mutex_t *serialize)
+poll_handle poll_create (
+	void (*serialize_lock_fn) (void),
+	void (*serialize_unlock_fn) (void))
 {
 {
 	poll_handle handle;
 	poll_handle handle;
 	struct poll_instance *poll_instance;
 	struct poll_instance *poll_instance;
@@ -88,7 +91,8 @@ poll_handle poll_create (pthread_mutex_t *serialize)
 	poll_instance->poll_entries = 0;
 	poll_instance->poll_entries = 0;
 	poll_instance->ufds = 0;
 	poll_instance->ufds = 0;
 	poll_instance->poll_entry_count = 0;
 	poll_instance->poll_entry_count = 0;
-	poll_instance->serialize = serialize;
+	poll_instance->serialize_lock_fn = serialize_unlock_fn;
+	poll_instance->serialize_unlock_fn = serialize_unlock_fn;
 	timerlist_init (&poll_instance->timerlist);
 	timerlist_init (&poll_instance->timerlist);
 
 
 	return (handle);
 	return (handle);
@@ -118,7 +122,6 @@ int poll_destroy (poll_handle handle)
 	if (poll_instance->ufds) {
 	if (poll_instance->ufds) {
 		free (poll_instance->ufds);
 		free (poll_instance->ufds);
 	}
 	}
-	timerlist_free (&poll_instance->timerlist);
 
 
 	hdb_handle_destroy (&poll_instance_database, handle);
 	hdb_handle_destroy (&poll_instance_database, handle);
 
 
@@ -395,13 +398,13 @@ retry_poll:
 			if (poll_instance->ufds[i].fd != -1 &&
 			if (poll_instance->ufds[i].fd != -1 &&
 				poll_instance->ufds[i].revents) {
 				poll_instance->ufds[i].revents) {
 
 
-				pthread_mutex_lock (poll_instance->serialize);
+				poll_instance->serialize_lock_fn();
 				res = poll_instance->poll_entries[i].dispatch_fn (handle,
 				res = poll_instance->poll_entries[i].dispatch_fn (handle,
 					poll_instance->ufds[i].fd, 
 					poll_instance->ufds[i].fd, 
 					poll_instance->ufds[i].revents,
 					poll_instance->ufds[i].revents,
 					poll_instance->poll_entries[i].data);
 					poll_instance->poll_entries[i].data);
 
 
-				pthread_mutex_unlock (poll_instance->serialize);
+				poll_instance->serialize_unlock_fn();
 				/*
 				/*
 				 * Remove dispatch functions that return -1
 				 * Remove dispatch functions that return -1
 				 */
 				 */
@@ -410,9 +413,9 @@ retry_poll:
 				}
 				}
 			}
 			}
 		}
 		}
-		pthread_mutex_lock (poll_instance->serialize);
+		poll_instance->serialize_lock_fn();
 		timerlist_expire (&poll_instance->timerlist);
 		timerlist_expire (&poll_instance->timerlist);
-		pthread_mutex_unlock (poll_instance->serialize);
+		poll_instance->serialize_unlock_fn();
 	} /* for (;;) */
 	} /* for (;;) */
 
 
 	hdb_handle_put (&poll_instance_database, handle);
 	hdb_handle_put (&poll_instance_database, handle);

+ 3 - 1
exec/aispoll.h

@@ -39,7 +39,9 @@
 typedef void * poll_timer_handle;
 typedef void * poll_timer_handle;
 typedef unsigned int poll_handle;
 typedef unsigned int poll_handle;
 
 
-poll_handle poll_create (pthread_mutex_t *mutex);
+poll_handle poll_create (
+	void (*serialize_lock) (void),
+	void (*serialize_unlock) (void));
 
 
 int poll_destroy (poll_handle poll_handle);
 int poll_destroy (poll_handle poll_handle);
 
 

+ 22 - 26
exec/amf.c

@@ -62,11 +62,11 @@
 #include "../include/list.h"
 #include "../include/list.h"
 #include "../lcr/lcr_comp.h"
 #include "../lcr/lcr_comp.h"
 #include "totempg.h"
 #include "totempg.h"
-#include "aispoll.h"
 #include "mempool.h"
 #include "mempool.h"
 #include "util.h"
 #include "util.h"
 #include "amfconfig.h"
 #include "amfconfig.h"
 #include "main.h"
 #include "main.h"
+#include "timer.h"
 #include "service.h"
 #include "service.h"
 #include "objdb.h"
 #include "objdb.h"
 #include "print.h"
 #include "print.h"
@@ -1115,11 +1115,11 @@ static int amf_exec_init_fn (struct objdb_iface_ver0 *objdb)
 		this_amf_node->saAmfNodeOperState = SA_AMF_OPERATIONAL_ENABLED;
 		this_amf_node->saAmfNodeOperState = SA_AMF_OPERATIONAL_ENABLED;
 
 
 		/* wait a while before starting applications as the AMF spec. says. */
 		/* wait a while before starting applications as the AMF spec. says. */
-		poll_timer_add(aisexec_poll_handle,
-					   amf_cluster.saAmfClusterStartupTimeout,
-					   NULL,
-					   cluster_start_applications,
-					   &amf_cluster.timeout_handle);
+		openais_timer_add(
+			amf_cluster.saAmfClusterStartupTimeout,
+			NULL,
+			cluster_start_applications,
+			&amf_cluster.timeout_handle);
 	} else {
 	} else {
 		log_printf (LOG_LEVEL_INFO, "This CLM node (%s) is not configured as an AMF node, disabling...", hostname);
 		log_printf (LOG_LEVEL_INFO, "This CLM node (%s) is not configured as an AMF node, disabling...", hostname);
 	}
 	}
@@ -1732,11 +1732,11 @@ static void cluster_start_applications (void *data)
 	}
 	}
 
 
 	/* wait a while before assigning SIs as the AMF spec. says. */
 	/* wait a while before assigning SIs as the AMF spec. says. */
-	poll_timer_add(aisexec_poll_handle,
-				   amf_cluster.saAmfClusterStartupTimeout,
-				   NULL,
-				   cluster_assign_workload,
-				   &amf_cluster.timeout_handle);
+	openais_timer_add(
+		amf_cluster.saAmfClusterStartupTimeout,
+		NULL,
+		cluster_assign_workload,
+		&amf_cluster.timeout_handle);
 }
 }
 
 
 #if 0
 #if 0
@@ -2307,10 +2307,9 @@ static void healthcheck_activate (struct amf_healthcheck *healthcheck_active)
 		&res_lib_amf_healthcheckcallback,
 		&res_lib_amf_healthcheckcallback,
 		sizeof (struct res_lib_amf_healthcheckcallback));
 		sizeof (struct res_lib_amf_healthcheckcallback));
 
 
-	poll_timer_delete (aisexec_poll_handle,
-		healthcheck_active->timer_handle_duration);
+	openais_timer_delete (healthcheck_active->timer_handle_duration);
 
 
-	poll_timer_add (aisexec_poll_handle,
+	openais_timer_add (
 		healthcheck_active->saAmfHealthcheckMaxDuration,
 		healthcheck_active->saAmfHealthcheckMaxDuration,
 		(void *)healthcheck_active,
 		(void *)healthcheck_active,
 		timer_function_healthcheck_timeout,
 		timer_function_healthcheck_timeout,
@@ -2322,11 +2321,9 @@ static void healthcheck_deactivate (struct amf_healthcheck *healthcheck_active)
 	dprintf ("deactivating healthcheck for component %s\n",
 	dprintf ("deactivating healthcheck for component %s\n",
              getSaNameT (&healthcheck_active->comp->name));
              getSaNameT (&healthcheck_active->comp->name));
 
 
-    poll_timer_delete (aisexec_poll_handle,
-		healthcheck_active->timer_handle_period);
+	openais_timer_delete (healthcheck_active->timer_handle_period);
 
 
-	poll_timer_delete (aisexec_poll_handle,
-		healthcheck_active->timer_handle_duration);
+	openais_timer_delete (healthcheck_active->timer_handle_duration);
 
 
 	invocation_destroy_by_data ((void *)healthcheck_active);
 	invocation_destroy_by_data ((void *)healthcheck_active);
 	healthcheck_active->active = 0;
 	healthcheck_active->active = 0;
@@ -2364,7 +2361,7 @@ static  void su_operational_state_set (
 			TRACE1 ("All SUs in SG '%s' in service, assigning SIs\n", unit->sg->name.value);
 			TRACE1 ("All SUs in SG '%s' in service, assigning SIs\n", unit->sg->name.value);
 			sg_assign_si (unit->sg);
 			sg_assign_si (unit->sg);
 			if (amf_cluster.timeout_handle) {
 			if (amf_cluster.timeout_handle) {
-				poll_timer_delete (aisexec_poll_handle, amf_cluster.timeout_handle);
+				openais_timer_delete (amf_cluster.timeout_handle);
 			}
 			}
 		}
 		}
 	} else if (oper_state == SA_AMF_OPERATIONAL_DISABLED) {
 	} else if (oper_state == SA_AMF_OPERATIONAL_DISABLED) {
@@ -2956,15 +2953,14 @@ static void message_handler_req_lib_amf_response (void *conn, void *msg)
 			TRACE3 ("Lib healthcheck response from '%s'",
 			TRACE3 ("Lib healthcheck response from '%s'",
 					comp_dn_make (healthcheck->comp, &name));
 					comp_dn_make (healthcheck->comp, &name));
 
 
-			poll_timer_delete (aisexec_poll_handle,
-							   healthcheck->timer_handle_duration);
+			openais_timer_delete (healthcheck->timer_handle_duration);
 			healthcheck->timer_handle_duration = 0;
 			healthcheck->timer_handle_duration = 0;
 
 
-			poll_timer_add (aisexec_poll_handle,
-							healthcheck->saAmfHealthcheckPeriod,
-							(void *)healthcheck,
-							timer_function_healthcheck_next_fn,
-							&healthcheck->timer_handle_period);
+			openais_timer_add (
+				healthcheck->saAmfHealthcheckPeriod,
+				(void *)healthcheck,
+				timer_function_healthcheck_next_fn,
+				&healthcheck->timer_handle_period);
 			break;
 			break;
 		}
 		}
 		case AMF_RESPONSE_CSISETCALLBACK: {
 		case AMF_RESPONSE_CSISETCALLBACK: {

+ 19 - 17
exec/ckpt.c

@@ -56,6 +56,8 @@
 #include "aispoll.h"
 #include "aispoll.h"
 #include "service.h"
 #include "service.h"
 #include "mempool.h"
 #include "mempool.h"
+#include "tlist.h"
+#include "timer.h"
 #include "util.h"
 #include "util.h"
 #include "main.h"
 #include "main.h"
 #include "totempg.h"
 #include "totempg.h"
@@ -83,7 +85,7 @@ struct saCkptCheckpointSection {
 	struct list_head list;
 	struct list_head list;
 	SaCkptSectionDescriptorT sectionDescriptor;
 	SaCkptSectionDescriptorT sectionDescriptor;
 	void *sectionData;
 	void *sectionData;
-	poll_timer_handle expiration_timer;
+	timer_handle expiration_timer;
 };
 };
 
 
 struct ckpt_refcnt {
 struct ckpt_refcnt {
@@ -98,7 +100,7 @@ struct saCkptCheckpoint {
 	struct list_head sections_list_head;
 	struct list_head sections_list_head;
 	int referenceCount;
 	int referenceCount;
 	int unlinked;
 	int unlinked;
-	poll_timer_handle retention_timer;
+	timer_handle retention_timer;
 	int expired;
 	int expired;
 	int active_replica_set;
 	int active_replica_set;
 	int sectionCount;
 	int sectionCount;
@@ -837,7 +839,7 @@ static void ckpt_recovery_initialize (void)
 			savedSection = 
 			savedSection = 
 				(struct saCkptCheckpointSection *) malloc (sizeof(struct saCkptCheckpointSection));
 				(struct saCkptCheckpointSection *) malloc (sizeof(struct saCkptCheckpointSection));
 			assert(savedSection);
 			assert(savedSection);
-			poll_timer_delete_data (aisexec_poll_handle, section->expiration_timer);
+			openais_timer_delete_data (section->expiration_timer);
 			memcpy(savedSection, section, sizeof(struct saCkptCheckpointSection));
 			memcpy(savedSection, section, sizeof(struct saCkptCheckpointSection));
 			list_init(&savedSection->list);		
 			list_init(&savedSection->list);		
 			list_add_tail(&savedSection->list,&savedCheckpoint->sections_list_head);
 			list_add_tail(&savedSection->list,&savedCheckpoint->sections_list_head);
@@ -1131,7 +1133,7 @@ static void ckpt_recovery_finalize (void)
 				memcpy(&ckpt_id->ckpt_name,&checkpoint->name,sizeof(SaNameT));
 				memcpy(&ckpt_id->ckpt_name,&checkpoint->name,sizeof(SaNameT));
 				memcpy(&ckpt_id->ckpt_section_id, &section->sectionDescriptor.sectionId,sizeof(SaCkptSectionIdT));
 				memcpy(&ckpt_id->ckpt_section_id, &section->sectionDescriptor.sectionId,sizeof(SaCkptSectionIdT));
 
 
-				poll_timer_add (aisexec_poll_handle,
+				openais_timer_add (
 					abstime_to_msec (section->sectionDescriptor.expirationTime),
 					abstime_to_msec (section->sectionDescriptor.expirationTime),
 					ckpt_id,
 					ckpt_id,
 					timer_function_section_expire,
 					timer_function_section_expire,
@@ -1289,8 +1291,8 @@ void clean_checkpoint_list(struct list_head *head)
 		else if ((checkpoint->expired == 0) && (checkpoint->referenceCount == 1)) { /*defect 1192*/
 		else if ((checkpoint->expired == 0) && (checkpoint->referenceCount == 1)) { /*defect 1192*/
 			log_printf (LOG_LEVEL_NOTICE, "clean_checkpoint_list: Starting timer to release checkpoint %s.\n",
 			log_printf (LOG_LEVEL_NOTICE, "clean_checkpoint_list: Starting timer to release checkpoint %s.\n",
 				&checkpoint->name.value);
 				&checkpoint->name.value);
-			poll_timer_delete (aisexec_poll_handle, checkpoint->retention_timer);
-			poll_timer_add (aisexec_poll_handle,
+			openais_timer_delete (checkpoint->retention_timer);
+			openais_timer_add (
 				checkpoint->checkpointCreationAttributes.retentionDuration / 1000000,
 				checkpoint->checkpointCreationAttributes.retentionDuration / 1000000,
 				checkpoint,
 				checkpoint,
 				timer_function_retention,
 				timer_function_retention,
@@ -1439,7 +1441,7 @@ void checkpoint_section_and_associate_timer_cleanup (struct saCkptCheckpointSect
 	 * defect 1112 on a section release we need to delete the timer AND its data or memory leaks
 	 * defect 1112 on a section release we need to delete the timer AND its data or memory leaks
 	 */
 	 */
 	if (deleteTimer) {	
 	if (deleteTimer) {	
-		poll_timer_delete_data (aisexec_poll_handle, section->expiration_timer);
+		openais_timer_delete_data (section->expiration_timer);
 	}
 	}
 	free (section);
 	free (section);
 }
 }
@@ -1456,7 +1458,7 @@ void checkpoint_release (struct saCkptCheckpoint *checkpoint)
 	struct list_head *list;
 	struct list_head *list;
 	struct saCkptCheckpointSection *section;
 	struct saCkptCheckpointSection *section;
 
 
-	poll_timer_delete (aisexec_poll_handle, checkpoint->retention_timer);
+	openais_timer_delete (checkpoint->retention_timer);
 
 
 	/*
 	/*
 	 * Release all checkpoint sections for this checkpoint
 	 * Release all checkpoint sections for this checkpoint
@@ -1666,7 +1668,7 @@ static void message_handler_req_exec_ckpt_checkpointopen (
 	/*
 	/*
 	 * Reset retention duration since this checkpoint was just opened
 	 * Reset retention duration since this checkpoint was just opened
 	 */
 	 */
-	poll_timer_delete (aisexec_poll_handle, ckptCheckpoint->retention_timer);
+	openais_timer_delete (ckptCheckpoint->retention_timer);
 	ckptCheckpoint->retention_timer = 0;
 	ckptCheckpoint->retention_timer = 0;
 
 
 	/*
 	/*
@@ -1851,7 +1853,7 @@ static int recovery_checkpoint_open(
 	/*
 	/*
 	 * Reset retention duration since this checkpoint was just opened
 	 * Reset retention duration since this checkpoint was just opened
 	 */
 	 */
-	poll_timer_delete (aisexec_poll_handle, ckptCheckpoint->retention_timer);
+	openais_timer_delete (ckptCheckpoint->retention_timer);
 	ckptCheckpoint->retention_timer = 0;
 	ckptCheckpoint->retention_timer = 0;
 
 
 	/*
 	/*
@@ -2063,7 +2065,7 @@ static void message_handler_req_exec_ckpt_checkpointclose (
 		release_checkpoint = 1;		
 		release_checkpoint = 1;		
 	} else
 	} else
 	if (checkpoint->referenceCount == 1 ) { /*defect 1192*/		
 	if (checkpoint->referenceCount == 1 ) { /*defect 1192*/		
-		poll_timer_add (aisexec_poll_handle,
+		openais_timer_add (
 			checkpoint->checkpointCreationAttributes.retentionDuration / 1000000,
 			checkpoint->checkpointCreationAttributes.retentionDuration / 1000000,
 			checkpoint,
 			checkpoint,
 			timer_function_retention,
 			timer_function_retention,
@@ -2155,9 +2157,9 @@ static void message_handler_req_exec_ckpt_checkpointretentiondurationset (
 				req_exec_ckpt_checkpointretentiondurationset->retentionDuration;
 				req_exec_ckpt_checkpointretentiondurationset->retentionDuration;
 	
 	
 			if (checkpoint->expired == 0 && checkpoint->referenceCount == 1) { /*defect 1192*/
 			if (checkpoint->expired == 0 && checkpoint->referenceCount == 1) { /*defect 1192*/
-				poll_timer_delete (aisexec_poll_handle, checkpoint->retention_timer);
+				openais_timer_delete (checkpoint->retention_timer);
 	
 	
-				poll_timer_add (aisexec_poll_handle,
+				openais_timer_add (
 					checkpoint->checkpointCreationAttributes.retentionDuration / 1000000,
 					checkpoint->checkpointCreationAttributes.retentionDuration / 1000000,
 					checkpoint,
 					checkpoint,
 					timer_function_retention,
 					timer_function_retention,
@@ -2340,7 +2342,7 @@ static int recovery_section_create (SaCkptSectionDescriptorT *sectionDescriptor,
 		log_printf (LOG_LEVEL_DEBUG, "CKPT: recovery_section_create Enqueuing Timer to Expire section %s in ckpt %s\n",
 		log_printf (LOG_LEVEL_DEBUG, "CKPT: recovery_section_create Enqueuing Timer to Expire section %s in ckpt %s\n",
 			ckpt_id->ckpt_section_id.id,
 			ckpt_id->ckpt_section_id.id,
 			(char *)&ckpt_id->ckpt_name.value);
 			(char *)&ckpt_id->ckpt_name.value);
-		poll_timer_add (aisexec_poll_handle,
+		openais_timer_add (
 			abstime_to_msec (ckptCheckpointSection->sectionDescriptor.expirationTime),
 			abstime_to_msec (ckptCheckpointSection->sectionDescriptor.expirationTime),
 			ckpt_id,
 			ckpt_id,
 			timer_function_section_expire,
 			timer_function_section_expire,
@@ -2473,7 +2475,7 @@ static void message_handler_req_exec_ckpt_sectioncreate (
 		log_printf (LOG_LEVEL_DEBUG, "CKPT: req_exec_ckpt_sectioncreate Enqueuing Timer to Expire section %s in ckpt %s\n",
 		log_printf (LOG_LEVEL_DEBUG, "CKPT: req_exec_ckpt_sectioncreate Enqueuing Timer to Expire section %s in ckpt %s\n",
 			ckpt_id->ckpt_section_id.id,
 			ckpt_id->ckpt_section_id.id,
 			(char *)&ckpt_id->ckpt_name.value);
 			(char *)&ckpt_id->ckpt_name.value);
-		poll_timer_add (aisexec_poll_handle,
+		openais_timer_add (
 			abstime_to_msec (ckptCheckpointSection->sectionDescriptor.expirationTime),
 			abstime_to_msec (ckptCheckpointSection->sectionDescriptor.expirationTime),
 			ckpt_id,
 			ckpt_id,
 			timer_function_section_expire,
 			timer_function_section_expire,
@@ -2617,7 +2619,7 @@ static void message_handler_req_exec_ckpt_sectionexpirationtimeset (
 
 
 	ckptCheckpointSection->sectionDescriptor.expirationTime = req_lib_ckpt_sectionexpirationtimeset->expirationTime;
 	ckptCheckpointSection->sectionDescriptor.expirationTime = req_lib_ckpt_sectionexpirationtimeset->expirationTime;
 
 
-	poll_timer_delete (aisexec_poll_handle, ckptCheckpointSection->expiration_timer);
+	openais_timer_delete (ckptCheckpointSection->expiration_timer);
 	ckptCheckpointSection->expiration_timer = 0;
 	ckptCheckpointSection->expiration_timer = 0;
 
 
 	if (req_lib_ckpt_sectionexpirationtimeset->expirationTime != SA_TIME_END) {
 	if (req_lib_ckpt_sectionexpirationtimeset->expirationTime != SA_TIME_END) {
@@ -2629,7 +2631,7 @@ static void message_handler_req_exec_ckpt_sectionexpirationtimeset (
 			ckpt_id->ckpt_section_id.id,
 			ckpt_id->ckpt_section_id.id,
 			(char *)&ckpt_id->ckpt_name.value,
 			(char *)&ckpt_id->ckpt_name.value,
 			ckpt_id);
 			ckpt_id);
-		poll_timer_add (aisexec_poll_handle,
+		openais_timer_add (
 			abstime_to_msec (ckptCheckpointSection->sectionDescriptor.expirationTime),
 			abstime_to_msec (ckptCheckpointSection->sectionDescriptor.expirationTime),
 			ckpt_id,
 			ckpt_id,
 			timer_function_section_expire,
 			timer_function_section_expire,

+ 9 - 19
exec/evt.c

@@ -61,6 +61,8 @@
 #include "totempg.h"
 #include "totempg.h"
 #include "swab.h"
 #include "swab.h"
 #include "print.h"
 #include "print.h"
+#include "tlist.h"
+#include "timer.h"
 
 
 /*
 /*
  * event instance structure. Contains information about the
  * event instance structure. Contains information about the
@@ -379,7 +381,7 @@ struct open_chan_pending {
 	SaNameT				ocp_chan_name;
 	SaNameT				ocp_chan_name;
 	void 				*ocp_conn;
 	void 				*ocp_conn;
 	SaEvtChannelOpenFlagsT	ocp_open_flag;
 	SaEvtChannelOpenFlagsT	ocp_open_flag;
-	poll_timer_handle	ocp_timer_handle;
+	timer_handle		ocp_timer_handle;
 	uint64_t			ocp_c_handle;
 	uint64_t			ocp_c_handle;
 	uint64_t			ocp_serial_no;
 	uint64_t			ocp_serial_no;
 	struct list_head	ocp_entry;
 	struct list_head	ocp_entry;
@@ -547,7 +549,7 @@ struct event_svr_channel_instance {
 struct event_data {
 struct event_data {
 	uint32_t			    			ed_ref_count;
 	uint32_t			    			ed_ref_count;
 	struct list_head		    		ed_retained;
 	struct list_head		    		ed_retained;
-	poll_timer_handle 					ed_timer_handle;
+	timer_handle 						ed_timer_handle;
 	struct event_svr_channel_open 	    **ed_delivered;
 	struct event_svr_channel_open 	    **ed_delivered;
 	uint32_t			    			ed_delivered_count;
 	uint32_t			    			ed_delivered_count;
 	uint32_t			    			ed_delivered_next;
 	uint32_t			    			ed_delivered_next;
@@ -1078,7 +1080,7 @@ static void unlink_channel(struct event_svr_channel_instance *eci,
 		edp = list_entry(l, struct event_data, ed_retained);
 		edp = list_entry(l, struct event_data, ed_retained);
 		if ((edp->ed_my_chan == eci) && 
 		if ((edp->ed_my_chan == eci) && 
 				(edp->ed_event.led_chan_unlink_id == EVT_CHAN_ACTIVE)) {
 				(edp->ed_event.led_chan_unlink_id == EVT_CHAN_ACTIVE)) {
-			poll_timer_delete(aisexec_poll_handle, edp->ed_timer_handle);
+			openais_timer_delete(edp->ed_timer_handle);
 			edp->ed_event.led_retention_time = 0;
 			edp->ed_event.led_retention_time = 0;
 			list_del(&edp->ed_retained);
 			list_del(&edp->ed_retained);
 			list_init(&edp->ed_retained);
 			list_init(&edp->ed_retained);
@@ -1486,7 +1488,6 @@ clear_retention_time(SaEvtEventIdT event_id)
 {
 {
 	struct event_data *edp;
 	struct event_data *edp;
 	struct list_head *l, *nxt;
 	struct list_head *l, *nxt;
-	int ret;
 
 
 	log_printf(RETENTION_TIME_DEBUG, "Search for Event ID %llx\n", event_id);
 	log_printf(RETENTION_TIME_DEBUG, "Search for Event ID %llx\n", event_id);
 	for (l = retained_list.next; l != &retained_list; l = nxt) {
 	for (l = retained_list.next; l != &retained_list; l = nxt) {
@@ -1499,12 +1500,7 @@ clear_retention_time(SaEvtEventIdT event_id)
 		log_printf(RETENTION_TIME_DEBUG, 
 		log_printf(RETENTION_TIME_DEBUG, 
 							"Clear retention time for Event ID %llx\n", 
 							"Clear retention time for Event ID %llx\n", 
 				edp->ed_event.led_event_id);
 				edp->ed_event.led_event_id);
-		ret = poll_timer_delete(aisexec_poll_handle, edp->ed_timer_handle);
-		if (ret != 0 ) {
-			log_printf(LOG_LEVEL_ERROR, "Error expiring event ID %llx\n",
-							edp->ed_event.led_event_id);
-			return SA_AIS_ERR_NOT_EXIST;
-		}
+		openais_timer_delete(edp->ed_timer_handle);
 		edp->ed_event.led_retention_time = 0;
 		edp->ed_event.led_retention_time = 0;
 		list_del(&edp->ed_retained);
 		list_del(&edp->ed_retained);
 		list_init(&edp->ed_retained);
 		list_init(&edp->ed_retained);
@@ -2037,7 +2033,7 @@ static void retain_event(struct event_data *evt)
 	 * Time in nanoseconds - convert to miliseconds
 	 * Time in nanoseconds - convert to miliseconds
 	 */
 	 */
 	msec_in_future = (uint32_t)((evt->ed_event.led_retention_time) / 1000000ULL);
 	msec_in_future = (uint32_t)((evt->ed_event.led_retention_time) / 1000000ULL);
-	ret = poll_timer_add(aisexec_poll_handle,
+	ret = openais_timer_add(
 					msec_in_future,
 					msec_in_future,
 					evt,
 					evt,
 					event_retention_timeout,
 					event_retention_timeout,
@@ -2185,7 +2181,7 @@ static void lib_evt_open_channel(void *conn, void *message)
 	 * Time in nanoseconds - convert to miliseconds
 	 * Time in nanoseconds - convert to miliseconds
 	 */
 	 */
 	msec_in_future = (uint32_t)(req->ico_timeout / 1000000ULL);
 	msec_in_future = (uint32_t)(req->ico_timeout / 1000000ULL);
-	ret = poll_timer_add(aisexec_poll_handle,
+	ret = openais_timer_add(
 			msec_in_future,
 			msec_in_future,
 			ocp,
 			ocp,
 			chan_open_timeout,
 			chan_open_timeout,
@@ -3385,13 +3381,7 @@ static void evt_chan_open_finish(struct open_chan_pending *ocp,
 	log_printf(CHAN_OPEN_DEBUG, "Open channel finish %s\n",
 	log_printf(CHAN_OPEN_DEBUG, "Open channel finish %s\n",
 											getSaNameT(&ocp->ocp_chan_name));
 											getSaNameT(&ocp->ocp_chan_name));
 	if (ocp->ocp_timer_handle) {
 	if (ocp->ocp_timer_handle) {
-		timer_del_status = poll_timer_delete(aisexec_poll_handle,
-				ocp->ocp_timer_handle);
-		if (timer_del_status != 0) {
-			log_printf(LOG_LEVEL_WARNING,
-				"Error clearing timeout for open channel of %s\n",
-				   getSaNameT(&ocp->ocp_chan_name));
-		}
+		openais_timer_delete (ocp->ocp_timer_handle);
 	}
 	}
 
 
 	/*
 	/*

+ 51 - 11
exec/ipc.c

@@ -1,6 +1,6 @@
 /*
 /*
  * Copyright (c) 2002-2006 MontaVista Software, Inc.
  * Copyright (c) 2002-2006 MontaVista Software, Inc.
- * Copyright (c) 2006 Red Hat, Inc..
+ * Copyright (c) 2006 Red Hat, Inc.
  *
  *
  * All rights reserved.
  * All rights reserved.
  *
  *
@@ -71,6 +71,7 @@
 #include "swab.h"
 #include "swab.h"
 #include "objdb.h"
 #include "objdb.h"
 #include "config.h"
 #include "config.h"
+#include "tlist.h"
 #define LOG_SERVICE LOG_SERVICE_IPC
 #define LOG_SERVICE LOG_SERVICE_IPC
 #include "print.h"
 #include "print.h"
 
 
@@ -78,12 +79,14 @@
 
 
 #define SERVER_BACKLOG 5
 #define SERVER_BACKLOG 5
 
 
-static pthread_mutex_t serialize_input = PTHREAD_MUTEX_INITIALIZER;
-
 static unsigned int g_gid_valid = 0;
 static unsigned int g_gid_valid = 0;
 
 
 static struct totem_ip_address *my_ip;
 static struct totem_ip_address *my_ip;
 
 
+static void (*ipc_serialize_lock_fn) (void);
+
+static void (*ipc_serialize_unlock_fn) (void);
+
 struct outq_item {
 struct outq_item {
 	void *msg;
 	void *msg;
 	size_t mlen;
 	size_t mlen;
@@ -118,6 +121,7 @@ struct conn_info {
 	void *private_data;	/* library connection private data */
 	void *private_data;	/* library connection private data */
 	struct conn_info *conn_info_partner;	/* partner connection dispatch<->response */
 	struct conn_info *conn_info_partner;	/* partner connection dispatch<->response */
 	enum disc_state disc;	/* disconnect state */
 	enum disc_state disc;	/* disconnect state */
+	struct timerlist timerlist;
 	pthread_mutex_t mutex;
 	pthread_mutex_t mutex;
 };
 };
 
 
@@ -369,13 +373,13 @@ retry_poll:
 			goto retry_poll;
 			goto retry_poll;
 		}
 		}
 		timeout = -1;
 		timeout = -1;
-		pthread_mutex_lock (&serialize_input);
+		ipc_serialize_lock_fn ();
 		if (fds == 1 && ufd.revents) {
 		if (fds == 1 && ufd.revents) {
 			if ((ufd.revents & (POLLERR|POLLHUP)) ||
 			if ((ufd.revents & (POLLERR|POLLHUP)) ||
 				conn_info->state == CONN_STATE_DISCONNECTING_DELAYED) {
 				conn_info->state == CONN_STATE_DISCONNECTING_DELAYED) {
 				res = libais_disconnect (conn_info);
 				res = libais_disconnect (conn_info);
 				if (res != 0) {
 				if (res != 0) {
-					pthread_mutex_unlock (&serialize_input);
+					ipc_serialize_unlock_fn ();
 					continue;
 					continue;
 				} else {
 				} else {
 					break;
 					break;
@@ -387,17 +391,17 @@ retry_poll:
 
 
 			if (conn_info->state == CONN_STATE_CONNECTED && conn_info->conn_info_partner == 0) {
 			if (conn_info->state == CONN_STATE_CONNECTED && conn_info->conn_info_partner == 0) {
 				timeout = 10;
 				timeout = 10;
-				pthread_mutex_unlock (&serialize_input);
+				ipc_serialize_unlock_fn ();
 				continue;
 				continue;
 			}
 			}
 			if ((ufd.revents & POLLIN) == POLLIN) {
 			if ((ufd.revents & POLLIN) == POLLIN) {
 				libais_deliver (conn_info);
 				libais_deliver (conn_info);
 			}
 			}
 		}
 		}
-		pthread_mutex_unlock (&serialize_input);
+		ipc_serialize_unlock_fn ();
 	}
 	}
 
 
-	pthread_mutex_unlock (&serialize_input);
+	ipc_serialize_unlock_fn ();
 	pthread_exit (0);
 	pthread_exit (0);
 	return (0);
 	return (0);
 }
 }
@@ -745,7 +749,8 @@ void message_source_set (
 }
 }
 
 
 void openais_ipc_init (
 void openais_ipc_init (
-	poll_handle ais_poll_handle,
+	void (*serialize_lock_fn) (void),
+	void (*serialize_unlock_fn) (void),
 	unsigned int gid_valid,
 	unsigned int gid_valid,
 	struct totem_ip_address *my_ip_in)
 	struct totem_ip_address *my_ip_in)
 {
 {
@@ -755,6 +760,10 @@ void openais_ipc_init (
 
 
 	log_init ("IPC");
 	log_init ("IPC");
 
 
+	ipc_serialize_lock_fn = serialize_lock_fn;
+
+	ipc_serialize_unlock_fn = serialize_unlock_fn;
+
 	/*
 	/*
 	 * Create socket for libais clients, name socket, listen for connections
 	 * Create socket for libais clients, name socket, listen for connections
 	 */
 	 */
@@ -972,9 +981,40 @@ retry_sendmsg_two:
 	return (0);
 	return (0);
 }
 }
 
 
-pthread_mutex_t *openais_ipc_mutex_get (void)
+int openais_ipc_timer_add (
+	void *conn,
+	void (*timer_fn) (void *data),
+	void *data,
+	unsigned int msec_in_future,
+	timer_handle *handle)
 {
 {
-	return (&serialize_input);
+	struct conn_info *conn_info = (struct conn_info *)conn;
+	int res;
+
+	res = timerlist_add_future (
+		&conn_info->timerlist,
+		timer_fn,
+		data,
+		msec_in_future,
+		handle);
+
+	return (res);
 }
 }
 
 
+void openais_ipc_timer_del (
+	void *conn,
+	timer_handle timer_handle)
+{
+	struct conn_info *conn_info = (struct conn_info *)conn;
+
+	timerlist_del (&conn_info->timerlist, timer_handle);
+}
 
 
+void openais_ipc_timer_del_data (
+	void *conn,
+	timer_handle timer_handle)
+{
+	struct conn_info *conn_info = (struct conn_info *)conn;
+
+	timerlist_del (&conn_info->timerlist, timer_handle);
+}

+ 17 - 3
exec/ipc.h

@@ -35,7 +35,7 @@
 #ifndef IPC_H_DEFINED
 #ifndef IPC_H_DEFINED
 #define IPC_H_DEFINED
 #define IPC_H_DEFINED
 
 
-#include "aispoll.h"
+#include "tlist.h"
 
 
 extern void message_source_set (struct message_source *source, void *conn);
 extern void message_source_set (struct message_source *source, void *conn);
 
 
@@ -48,10 +48,24 @@ extern void *openais_conn_private_data_get (void *conn);
 extern int openais_conn_send_response (void *conn, void *msg, int mlen);
 extern int openais_conn_send_response (void *conn, void *msg, int mlen);
 
 
 extern void openais_ipc_init (
 extern void openais_ipc_init (
-	poll_handle handle,
+        void (*serialize_lock_fn) (void),
+        void (*serialize_unlock_fn) (void),
 	unsigned int gid_valid,
 	unsigned int gid_valid,
 	struct totem_ip_address *non_loopback_ip);
 	struct totem_ip_address *non_loopback_ip);
 
 
-extern pthread_mutex_t *openais_ipc_mutex_get (void);
+extern int openais_ipc_timer_add (
+	void *conn,
+	void (*timer_fn) (void *data),
+	void *data,
+	unsigned int msec_in_future,
+	timer_handle *handle);
+
+extern void openais_ipc_timer_del (
+	void *conn,
+	timer_handle timer_handle);
+
+extern void openais_ipc_timer_del_data (
+	void *conn,
+	timer_handle timer_handle);
 
 
 #endif /* IPC_H_DEFINED */
 #endif /* IPC_H_DEFINED */

+ 28 - 4
exec/main.c

@@ -72,12 +72,13 @@
 #include "objdb.h"
 #include "objdb.h"
 #include "config.h"
 #include "config.h"
 #include "ipc.h"
 #include "ipc.h"
+#include "timer.h"
 #include "print.h"
 #include "print.h"
 #include "util.h"
 #include "util.h"
 
 
 #define SERVER_BACKLOG 5
 #define SERVER_BACKLOG 5
 
 
-static char *release_name = "Wilson version 0.74";
+static char *release_name = "Wilson version 0.77";
 
 
 static int ais_uid = 0;
 static int ais_uid = 0;
 
 
@@ -85,6 +86,8 @@ static int gid_valid = 0;
 
 
 static unsigned int service_count = 32;
 static unsigned int service_count = 32;
 
 
+static pthread_mutex_t serialize_mutex = PTHREAD_MUTEX_INITIALIZER;
+
 static struct totem_logging_configuration totem_logging_configuration;
 static struct totem_logging_configuration totem_logging_configuration;
 
 
 static char delivery_data[MESSAGE_SIZE_MAX];
 static char delivery_data[MESSAGE_SIZE_MAX];
@@ -139,6 +142,17 @@ static int pool_sizes[] = { 0, 0, 0, 0, 0, 4096, 0, 1, 0, /* 256 */
 					1024, 0, 1, 4096, 0, 0, 0, 0, /* 65536 */
 					1024, 0, 1, 4096, 0, 0, 0, 0, /* 65536 */
 					1, 1, 1, 1, 1, 1, 1, 1, 1 };
 					1, 1, 1, 1, 1, 1, 1, 1, 1 };
 
 
+void serialize_mutex_lock (void)
+{
+	pthread_mutex_lock (&serialize_mutex);
+}
+
+void serialize_mutex_unlock (void)
+{
+	pthread_mutex_unlock (&serialize_mutex);
+}
+
+
 static void openais_sync_completed (void)
 static void openais_sync_completed (void)
 {
 {
 }
 }
@@ -370,7 +384,13 @@ int main (int argc, char **argv)
 
 
 	totemip_localhost(AF_INET, &this_non_loopback_ip);
 	totemip_localhost(AF_INET, &this_non_loopback_ip);
 
 
-	aisexec_poll_handle = poll_create (openais_ipc_mutex_get());
+	openais_timer_init (
+		serialize_mutex_lock,
+		serialize_mutex_unlock);
+
+	aisexec_poll_handle = poll_create (
+		serialize_mutex_lock,
+		serialize_mutex_unlock);
 
 
 	/*
 	/*
 	 * Load the object database interface
 	 * Load the object database interface
@@ -528,9 +548,13 @@ int main (int argc, char **argv)
 	signal (SIGINT, sigintr_handler);
 	signal (SIGINT, sigintr_handler);
 	signal (SIGUSR2, sigusr2_handler);
 	signal (SIGUSR2, sigusr2_handler);
 
 
-	openais_ipc_init (aisexec_poll_handle, gid_valid, &this_non_loopback_ip);
+	openais_ipc_init (
+		serialize_mutex_lock,
+		serialize_mutex_unlock,
+		gid_valid,
+		&this_non_loopback_ip);
 
 
-	aisexec_tty_detach ();
+//	aisexec_tty_detach ();
 
 
 	log_printf (LOG_LEVEL_NOTICE, "AIS Executive Service: started and ready to provide service.\n");
 	log_printf (LOG_LEVEL_NOTICE, "AIS Executive Service: started and ready to provide service.\n");
 
 

+ 0 - 287
exec/tlist.c

@@ -1,287 +0,0 @@
-/*
- * Copyright (c) 2003-2004 MontaVista Software, Inc.
- *
- * All rights reserved.
- *
- * Author: Steven Dake (sdake@mvista.com)
- *
- * This software licensed under BSD license, the text of which follows:
- * 
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are met:
- *
- * - Redistributions of source code must retain the above copyright notice,
- *   this list of conditions and the following disclaimer.
- * - Redistributions in binary form must reproduce the above copyright notice,
- *   this list of conditions and the following disclaimer in the documentation
- *   and/or other materials provided with the distribution.
- * - Neither the name of the MontaVista Software, Inc. nor the names of its
- *   contributors may be used to endorse or promote products derived from this
- *   software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
- * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
- * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
- * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
- * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
- * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
- * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
- * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
- * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
- * THE POSSIBILITY OF SUCH DAMAGE.
- */
-#include <sys/time.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <errno.h>
-#include <string.h>
-
-#include "../include/list.h"
-#include "tlist.h"
-
-struct timer {
-	struct list_head list;
-	struct timeval tv;
-	void (*timer_fn)(void *data);
-	void *data;
-	timer_handle handle_addr;
-};
-
-void timerlist_init (struct timerlist *timerlist)
-{
-	list_init (&timerlist->timer_head);
-}
-
-void timerlist_free (struct timerlist *timerlist)
-{
-}
-
-int timers_inuse = 0;
-
-static inline void timeval_adjust_to_msec (struct timeval *tv) {
-        tv->tv_usec = (tv->tv_usec / 1000) * 1000;
-}
-
-
-void timerlist_add (struct timerlist *timerlist, struct timer *timer)
-{
-	struct list_head *timer_list = 0;
-	struct timer *timer_from_list;
-	int found;
-
-	timeval_adjust_to_msec (&timer->tv);
-//printf ("Adding timer %d %d\n", timer->tv.tv_sec, timer->tv.tv_usec);
-	for (found = 0, timer_list = timerlist->timer_head.next;
-		timer_list != &timerlist->timer_head;
-		timer_list = timer_list->next) {
-
-		timer_from_list = list_entry (timer_list,
-			struct timer, list);
-
-		if ((timer_from_list->tv.tv_sec > timer->tv.tv_sec) ||
-			((timer_from_list->tv.tv_sec == timer->tv.tv_sec) &&
-			(timer_from_list->tv.tv_usec > timer->tv.tv_usec))) {
-			list_add (&timer->list, timer_list->prev);
-			found = 1;
-			break; /* for timer iteration */
-		}
-	}
-	if (found == 0) {
-		list_add (&timer->list, timerlist->timer_head.prev);
-		timers_inuse++;
-	}
-}
-
-timer_handle timerlist_add_future (struct timerlist *timerlist,
-	void (*timer_fn) (void *data),
-	void *data,
-	unsigned int msec_in_future,
-	timer_handle *handle)
-{
-	struct timer *timer;
-	struct timeval current_time;
-	unsigned int seconds;
-	unsigned int mseconds;
-
-	timer = (struct timer *)malloc (sizeof (struct timer));
-	if (timer == 0) {
-		errno = ENOMEM;
-		return (0);
-	}
-	
-	seconds = msec_in_future / 1000;
-	mseconds = msec_in_future % 1000;
-
-	gettimeofday (&current_time, 0);
-	timeval_adjust_to_msec (&current_time);
-	timer->tv.tv_sec = current_time.tv_sec + seconds;
-	timer->tv.tv_usec = current_time.tv_usec + mseconds * 1000;
-	if (timer->tv.tv_usec >= 1000000) {
-		timer->tv.tv_sec++;
-		timer->tv.tv_usec -= 1000000;
-	}
-	timer->data = data;
-	timer->timer_fn = timer_fn;
-	timer->handle_addr = handle;
-	timerlist_add (timerlist, timer);
-
-	*handle = timer;
-	return (0);
-}
-
-void timerlist_del (struct timerlist *timerlist, timer_handle timer_handle)
-{
-	struct timer *timer = (struct timer *)timer_handle;
-
-	memset (timer->handle_addr, 0, sizeof (struct timer *));
-	/*
-	 * If the next timer after the currently expiring timer because
-	 * timerlist_del is called from a timer handler, get to the enxt
-	 * timer
-	 */
-	if (timerlist->timer_iter == &timer->list) {
-		timerlist->timer_iter = timerlist->timer_iter->next;
-	}
-	list_del (&timer->list);
-	list_init (&timer->list);
-	timers_inuse--;
-	free (timer);
-}
-
-void timerlist_del_data (struct timerlist *timerlist, timer_handle timer_handle)
-{
-	struct timer *timer = (struct timer *)timer_handle;
-
-	if (timer->data) {
-		free (timer->data);
-	}
-	timerlist_del(timerlist,timer_handle);
-}
-
-static void timerlist_pre_dispatch (struct timerlist *timerlist, timer_handle timer_handle)
-{
-	struct timer *timer = (struct timer *)timer_handle;
-
-	memset (timer->handle_addr, 0, sizeof (struct timer *));
-	list_del (&timer->list);
-	list_init (&timer->list);
-	timers_inuse--;
-}
-
-static void timerlist_post_dispatch (struct timerlist *timerlist, timer_handle timer_handle)
-{
-	struct timer *timer = (struct timer *)timer_handle;
-
-	free (timer);
-}
-
-#ifdef CODE_COVERAGE_COMPILE_OUT
-int timer_expire_get_tv (struct timerlist *timerlist, struct timeval *tv)
-{
-	struct timeval current_time;
-	struct timer *timer_from_list;
-
-	/*
-	 * empty list, no expire
-	 */
-	if (timerlist->timer_head.next == &timerlist->timer_head) {
-		return (-1);
-	}
-	
-	timer_from_list = list_entry (timerlist->timer_head.next,
-		struct timer, list);
-
-	gettimeofday (&current_time, 0);
-	timeval_adjust_to_msec (&current_time);
-
-	/*
-	 * timer at head of list is expired, zero msecs required
-	 */
-	if ((timer_from_list->tv.tv_sec < current_time.tv_sec) ||
-		((timer_from_list->tv.tv_sec == current_time.tv_sec) &&
-		(timer_from_list->tv.tv_usec <= current_time.tv_usec))) {
-		
-		tv->tv_sec = 0;
-		tv->tv_usec = 0;
-	}
-
-	tv->tv_sec = timer_from_list->tv.tv_sec - current_time.tv_sec;
-	tv->tv_usec = timer_from_list->tv.tv_usec - current_time.tv_usec;
-	if (tv->tv_usec < 0) {
-		tv->tv_sec -= 1;
-		tv->tv_usec += 1000000;
-	}
-	if (tv->tv_sec < 0) {
-		tv->tv_sec = 0;
-		tv->tv_usec = 0;
-	}
-
-	timeval_adjust_to_msec (tv);
-	return (0);
-}
-#endif /* CODE_COVERAGE_COMPILE_OUT */
-
-unsigned int timerlist_timeout_msec (struct timerlist *timerlist)
-{
-	struct timeval current_time;
-	struct timer *timer_from_list;
-	unsigned int time_in_msec;
-
-	/*
-	 * empty list, no expire
-	 */
-	if (timerlist->timer_head.next == &timerlist->timer_head) {
-		return (-1);
-	}
-	
-	timer_from_list = list_entry (timerlist->timer_head.next,
-		struct timer, list);
-
-	gettimeofday (&current_time, 0);
-	timeval_adjust_to_msec (&current_time);
-
-	/*
-	 * timer at head of list is expired, zero msecs required
-	 */
-	if ((timer_from_list->tv.tv_sec < current_time.tv_sec) ||
-		((timer_from_list->tv.tv_sec == current_time.tv_sec) &&
-		(timer_from_list->tv.tv_usec <= current_time.tv_usec))) {
-		return (0);
-	}
-	time_in_msec = ((timer_from_list->tv.tv_sec - current_time.tv_sec) * 1000) + ((timer_from_list->tv.tv_usec - current_time.tv_usec) / 1000);
-
-	return time_in_msec;
-}
-
-void timerlist_expire (struct timerlist *timerlist)
-{
-	struct timer *timer_from_list;
-	struct timeval current_time;
-
-	gettimeofday (&current_time, 0);
-	timeval_adjust_to_msec (&current_time);
-
-	for (timerlist->timer_iter = timerlist->timer_head.next;
-		timerlist->timer_iter != &timerlist->timer_head;) {
-
-		timer_from_list = list_entry (timerlist->timer_iter,
-			struct timer, list);
-
-		if ((timer_from_list->tv.tv_sec < current_time.tv_sec) ||
-			((timer_from_list->tv.tv_sec == current_time.tv_sec) &&
-			(timer_from_list->tv.tv_usec <= current_time.tv_usec))) {
-//printf ("Executing timer %d %d\n", timer_from_list->tv.tv_sec, timer_from_list->tv.tv_usec);
-			timerlist->timer_iter = timerlist->timer_iter->next;
-
-			timerlist_pre_dispatch (timerlist, timer_from_list);
-
-			timer_from_list->timer_fn (timer_from_list->data);
-
-			timerlist_post_dispatch (timerlist, timer_from_list);
-		} else {
-			break; /* for timer iteration */
-		}
-	}
-	timerlist->timer_iter = 0;
-}

+ 238 - 11
exec/tlist.h

@@ -1,5 +1,6 @@
 /*
 /*
  * Copyright (c) 2003-2004 MontaVista Software, Inc.
  * Copyright (c) 2003-2004 MontaVista Software, Inc.
+ * Copyright (c) 2006 Red Hat, Inc.
  *
  *
  * All rights reserved.
  * All rights reserved.
  *
  *
@@ -32,12 +33,17 @@
  * THE POSSIBILITY OF SUCH DAMAGE.
  * THE POSSIBILITY OF SUCH DAMAGE.
  */
  */
 
 
-#include <sys/time.h>
-#include "../include/list.h"
-
 #ifndef TLIST_H_DEFINED
 #ifndef TLIST_H_DEFINED
 #define TLIST_H_DEFINED
 #define TLIST_H_DEFINED
 
 
+#include <sys/time.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <errno.h>
+#include <string.h>
+
+#include "../include/list.h"
+
 typedef void * timer_handle;
 typedef void * timer_handle;
 
 
 struct timerlist {
 struct timerlist {
@@ -45,22 +51,243 @@ struct timerlist {
 	struct list_head *timer_iter;
 	struct list_head *timer_iter;
 };
 };
 
 
-void timerlist_init (struct timerlist *timerlist);
+struct timerlist_timer {
+	struct list_head list;
+	struct timeval tv;
+	void (*timer_fn)(void *data);
+	void *data;
+	timer_handle handle_addr;
+};
+
+static inline void timerlist_init (struct timerlist *timerlist)
+{
+	list_init (&timerlist->timer_head);
+}
+
+static inline void timeval_adjust_to_msec (struct timeval *tv) {
+        tv->tv_usec = (tv->tv_usec / 1000) * 1000;
+}
 
 
-void timerlist_free (struct timerlist *timerlist);
 
 
-timer_handle timerlist_add_future (struct timerlist *timerlist,
+static inline void timerlist_add (struct timerlist *timerlist, struct timerlist_timer *timer)
+{
+	struct list_head *timer_list = 0;
+	struct timerlist_timer *timer_from_list;
+	int found;
+
+	timeval_adjust_to_msec (&timer->tv);
+//printf ("Adding timer %d %d\n", timer->tv.tv_sec, timer->tv.tv_usec);
+	for (found = 0, timer_list = timerlist->timer_head.next;
+		timer_list != &timerlist->timer_head;
+		timer_list = timer_list->next) {
+
+		timer_from_list = list_entry (timer_list,
+			struct timerlist_timer, list);
+
+		if ((timer_from_list->tv.tv_sec > timer->tv.tv_sec) ||
+			((timer_from_list->tv.tv_sec == timer->tv.tv_sec) &&
+			(timer_from_list->tv.tv_usec > timer->tv.tv_usec))) {
+			list_add (&timer->list, timer_list->prev);
+			found = 1;
+			break; /* for timer iteration */
+		}
+	}
+	if (found == 0) {
+		list_add (&timer->list, timerlist->timer_head.prev);
+	}
+}
+
+static inline int timerlist_add_future (struct timerlist *timerlist,
 	void (*timer_fn) (void *data),
 	void (*timer_fn) (void *data),
 	void *data,
 	void *data,
 	unsigned int msec_in_future,
 	unsigned int msec_in_future,
-    timer_handle *handle);
+	timer_handle *handle)
+{
+	struct timerlist_timer *timer;
+	struct timeval current_time;
+	unsigned int seconds;
+	unsigned int mseconds;
+
+	timer = (struct timerlist_timer *)malloc (sizeof (struct timerlist_timer));
+	if (timer == 0) {
+		errno = ENOMEM;
+		return (-1);
+	}
+	
+	seconds = msec_in_future / 1000;
+	mseconds = msec_in_future % 1000;
+
+	gettimeofday (&current_time, 0);
+	timeval_adjust_to_msec (&current_time);
+	timer->tv.tv_sec = current_time.tv_sec + seconds;
+	timer->tv.tv_usec = current_time.tv_usec + mseconds * 1000;
+	if (timer->tv.tv_usec >= 1000000) {
+		timer->tv.tv_sec++;
+		timer->tv.tv_usec -= 1000000;
+	}
+	timer->data = data;
+	timer->timer_fn = timer_fn;
+	timer->handle_addr = handle;
+	timerlist_add (timerlist, timer);
+
+	*handle = timer;
+	return (0);
+}
+
+static inline void timerlist_del (struct timerlist *timerlist, timer_handle timer_handle)
+{
+	struct timerlist_timer *timer = (struct timerlist_timer *)timer_handle;
+
+	memset (timer->handle_addr, 0, sizeof (struct timerlist_timer *));
+	/*
+	 * If the next timer after the currently expiring timer because
+	 * timerlist_del is called from a timer handler, get to the enxt
+	 * timer
+	 */
+	if (timerlist->timer_iter == &timer->list) {
+		timerlist->timer_iter = timerlist->timer_iter->next;
+	}
+	list_del (&timer->list);
+	list_init (&timer->list);
+	free (timer);
+}
+
+static inline void timerlist_del_data (struct timerlist *timerlist, timer_handle timer_handle)
+{
+	struct timerlist_timer *timer = (struct timerlist_timer *)timer_handle;
+
+	if (timer->data) {
+		free (timer->data);
+	}
+	timerlist_del(timerlist,timer_handle);
+}
+
+static inline void timerlist_pre_dispatch (struct timerlist *timerlist, timer_handle timer_handle)
+{
+	struct timerlist_timer *timer = (struct timerlist_timer *)timer_handle;
+
+	memset (timer->handle_addr, 0, sizeof (struct timerlist_timer *));
+	list_del (&timer->list);
+	list_init (&timer->list);
+}
+
+static inline void timerlist_post_dispatch (struct timerlist *timerlist, timer_handle timer_handle)
+{
+	struct timerlist_timer *timer = (struct timerlist_timer *)timer_handle;
+
+	free (timer);
+}
+
+#ifdef CODE_COVERAGE_COMPILE_OUT
+static inline int timer_expire_get_tv (struct timerlist *timerlist, struct timeval *tv)
+{
+	struct timeval current_time;
+	struct timerlist_timer *timer_from_list;
+
+	/*
+	 * empty list, no expire
+	 */
+	if (timerlist->timer_head.next == &timerlist->timer_head) {
+		return (-1);
+	}
+	
+	timer_from_list = list_entry (timerlist->timer_head.next,
+		struct timerlist_timer, list);
+
+	gettimeofday (&current_time, 0);
+	timeval_adjust_to_msec (&current_time);
+
+	/*
+	 * timer at head of list is expired, zero msecs required
+	 */
+	if ((timer_from_list->tv.tv_sec < current_time.tv_sec) ||
+		((timer_from_list->tv.tv_sec == current_time.tv_sec) &&
+		(timer_from_list->tv.tv_usec <= current_time.tv_usec))) {
+		
+		tv->tv_sec = 0;
+		tv->tv_usec = 0;
+	}
+
+	tv->tv_sec = timer_from_list->tv.tv_sec - current_time.tv_sec;
+	tv->tv_usec = timer_from_list->tv.tv_usec - current_time.tv_usec;
+	if (tv->tv_usec < 0) {
+		tv->tv_sec -= 1;
+		tv->tv_usec += 1000000;
+	}
+	if (tv->tv_sec < 0) {
+		tv->tv_sec = 0;
+		tv->tv_usec = 0;
+	}
+
+	timeval_adjust_to_msec (tv);
+	return (0);
+}
+#endif /* CODE_COVERAGE_COMPILE_OUT */
+
+static inline unsigned int timerlist_timeout_msec (struct timerlist *timerlist)
+{
+	struct timeval current_time;
+	struct timerlist_timer *timer_from_list;
+	int time_in_msec;
+
+	/*
+	 * empty list, no expire
+	 */
+	if (timerlist->timer_head.next == &timerlist->timer_head) {
+		return (-1);
+	}
+	
+	timer_from_list = list_entry (timerlist->timer_head.next,
+		struct timerlist_timer, list);
+
+	gettimeofday (&current_time, 0);
+	timeval_adjust_to_msec (&current_time);
+
+	/*
+	 * timer at head of list is expired, zero msecs required
+	 */
+	if ((timer_from_list->tv.tv_sec < current_time.tv_sec) ||
+		((timer_from_list->tv.tv_sec == current_time.tv_sec) &&
+		(timer_from_list->tv.tv_usec <= current_time.tv_usec))) {
+		return (0);
+	}
+	time_in_msec = ((timer_from_list->tv.tv_sec - current_time.tv_sec) * 1000) + ((timer_from_list->tv.tv_usec - current_time.tv_usec) / 1000);
+
+	if (time_in_msec < 0) {
+		return (0);
+	}
+	return time_in_msec;
+}
+
+static inline void timerlist_expire (struct timerlist *timerlist)
+{
+	struct timerlist_timer *timer_from_list;
+	struct timeval current_time;
+
+	gettimeofday (&current_time, 0);
+	timeval_adjust_to_msec (&current_time);
+
+	for (timerlist->timer_iter = timerlist->timer_head.next;
+		timerlist->timer_iter != &timerlist->timer_head;) {
 
 
-void timerlist_del (struct timerlist *timerlist, timer_handle timer_handle);
+		timer_from_list = list_entry (timerlist->timer_iter,
+			struct timerlist_timer, list);
 
 
-void timerlist_del_data (struct timerlist *timerlist, timer_handle timer_handle);
+		if ((timer_from_list->tv.tv_sec < current_time.tv_sec) ||
+			((timer_from_list->tv.tv_sec == current_time.tv_sec) &&
+			(timer_from_list->tv.tv_usec <= current_time.tv_usec))) {
+//printf ("Executing timer %d %d\n", timer_from_list->tv.tv_sec, timer_from_list->tv.tv_usec);
+			timerlist->timer_iter = timerlist->timer_iter->next;
 
 
-void timerlist_expire (struct timerlist *timerlist);
+			timerlist_pre_dispatch (timerlist, timer_from_list);
 
 
-unsigned int timerlist_timeout_msec (struct timerlist *timerlist);
+			timer_from_list->timer_fn (timer_from_list->data);
 
 
+			timerlist_post_dispatch (timerlist, timer_from_list);
+		} else {
+			break; /* for timer iteration */
+		}
+	}
+	timerlist->timer_iter = 0;
+}
 #endif /* TLIST_H_DEFINED */
 #endif /* TLIST_H_DEFINED */