hal/hald callout.c, 1.15, 1.16 device_info.c, 1.17, 1.18 hald_dbus.c, 1.17, 1.18

David Zeuthen david at freedesktop.org
Tue Jan 18 11:48:15 PST 2005


Update of /cvs/hal/hal/hald
In directory gabe:/tmp/cvs-serv19239/hald

Modified Files:
	callout.c device_info.c hald_dbus.c 
Log Message:
2005-01-18  David Zeuthen  <david at fubar.dk>

	* tools/linux/Makefile.am: Remove hal.dev build rules

	* tools/linux/hal_dev.c: Remove

	* configure.in: Set linux2 as the default backend

	* hald/linux: Remove all files here as they will get reimplemented
	in hald/linux2

	* hald/linux2: Add a bunch of new files

	* hald/linux2/probing: Add some new files

2005-01-18  David Zeuthen  <davidz at redhat.com>

	Merge some more changes from the stable branch (except those
	in hald/linux and doc/spec)

	2005-01-12  David Zeuthen  <davidz at redhat.com>

	* hald/callout.c (callout_timeout_handler): Be tough and kill
	the misbehaving child the hard way - suggestion from Joe Shaw.

	2005-01-12  David Zeuthen  <davidz at redhat.com>

	* hald/linux/osspec.c (HOTPLUG_TIMEOUT): Increase to 25 seconds
	to better cope with callouts timeout of 10 seconds

	* hald/callout.c (iochn_data): Cope with callouts terminating
	and free timeout handler
	(callout_timeout_handler): New function; kill callouts if they
	time out
	(process_next_callout): Setup timeout for callouts - set to
	ten seconds

	2005-01-11  David Zeuthen  <davidz at redhat.com>

	* hald/callout.c: Simplify a lot more by demanding that callouts
	are run sequentially - which they are anyway since everything is
	serialized. Make a mental note to review and stress test this in
	the morning.

	2005-01-11  David Zeuthen  <davidz at redhat.com>

	* hald/callout.c: Fix some craziness adding an idle handler for
	detecting when callouts complete - fixes bug on my new AMD64
	system with device add/remove prior to completion of callouts -
	one visible effect was that fstab-sync was crashing since it
	couldn't retrieve the block.device device as the device was
	removed prior to the completion of the callout

	2005-01-07  David Zeuthen  <davidz at redhat.com>

	* fdi/20freedesktop/ide-drives.fdi: Also check IDE floppies for whether
	they are Zip drives

	2005-01-07  Joe Shaw  <joeshaw at novell.com>

	* configure.in: Check for popt when building fstab-sync and error
	out if it's not found.

	* tools/Makefile.am: Build fstab-sync conditionally based on
	whether --enable-fstab-sync is passed in.

	2005-01-06  David Zeuthen  <davidz at redhat.com>

	* libhal/libhal.c (hal_device_query_capability): Patch from Tim
	Müller <t.i.m at zen.co.uk>. The attached patch fixes a small memory
	leak in libhal's hal_device_query_capability().

	2005-01-03  David Zeuthen  <davidz at redhat.com>

	* configure.in: Added it to ALL_LINGUAS

	* po/it.po: Italien translation from Pier Luigi Fiorini
	<pierluigi.fiorini at mockup.org>

	2004-12-15  David Zeuthen  <davidz at redhat.com>

	* fdi/20freedesktop/usb-zip-drives.fdi: Only match on actual
	harddisks to avoid wrong detection of e.g. "Iomega ZipCD 650 USB CDRW"
	drives (Red Hat bug #143834)

	* fdi/20freedesktop/ide-drives.fdi: ditto



Index: callout.c
===================================================================
RCS file: /cvs/hal/hal/hald/callout.c,v
retrieving revision 1.15
retrieving revision 1.16
diff -u -d -r1.15 -r1.16
--- callout.c	31 Aug 2004 23:40:22 -0000	1.15
+++ callout.c	18 Jan 2005 19:48:12 -0000	1.16
@@ -54,76 +54,36 @@
 	HalDevice *device;
 	char **envp;
 	int envp_index;
-	int pid;
+	pid_t pid;
 	gboolean last_of_device;
+	guint timeout_id;
 } Callout;
 
-static void process_callouts (void);
+static void process_next_callout (void);
 
 /* Callouts that still needing to be processed
  *
  * Key: HalDevice  Value: pointer to GSList of Callouts */
-static GHashTable *pending_callouts = NULL;
-
-/* List of Callouts currently being processed */
-static GSList *active_callouts = NULL;
+static GSList *pending_callouts = NULL;
 
-static gboolean processing_callouts = FALSE;
+static Callout *active_callout = NULL;
 
 static void
 add_pending_callout (HalDevice *device, Callout *callout)
 {
-	GSList **clist = NULL;
-
-	if (pending_callouts == NULL)
-		pending_callouts = g_hash_table_new (NULL, NULL);
-	else
-		clist = g_hash_table_lookup (pending_callouts, device);
-
-	if (clist == NULL) {
-		clist = g_new0 (GSList *, 1);
-		g_hash_table_insert (pending_callouts, device, clist);
-	}
-
-	*clist = g_slist_append (*clist, callout);
-}
-
-static void
-get_device (gpointer key, gpointer value, gpointer user_data)
-{
-	HalDevice **device = user_data;
-
-	if (*device == NULL)
-		*device = (HalDevice *) key;
+	pending_callouts = g_slist_append (pending_callouts, callout);
 }
 
 static Callout *
-pop_pending_callout (gboolean *last_of_device)
+pop_pending_callout (void)
 {
-	GSList **clist;
-	HalDevice *device = NULL;
 	Callout *callout;
 
 	if (pending_callouts == NULL)
 		return NULL;
 
-	/* Hmm, not sure of a better way to do this... */
-	g_hash_table_foreach (pending_callouts, get_device, &device);
-
-	clist = g_hash_table_lookup (pending_callouts, device);
-
-	if (clist == NULL)
-		return NULL;
-
-	callout = (Callout *) (*clist)->data;
-	*clist = g_slist_remove (*clist, callout);
-
-	if (*clist == NULL) {
-		g_hash_table_remove (pending_callouts, device);
-		g_free (clist);
-		*last_of_device = TRUE;
-	} else
-		*last_of_device = FALSE;
+	callout = (Callout *) pending_callouts->data;
+	pending_callouts = g_slist_remove (pending_callouts, callout);
 
 	return callout;
 }
@@ -185,9 +145,7 @@
 	gchar data[1];
 	GError *err = NULL;
 	pid_t child_pid;
-	Callout *callout;
-	GSList *it;
-
+	Callout *previous_callout;
 
 	/* Empty the pipe; one character per dead child */
 	if (G_IO_STATUS_NORMAL != 
@@ -211,51 +169,79 @@
 			/* this can happen indeed since we loop */
 			goto out;
 		}
-	
-		/* Now find the corresponding Callout object */
-		callout = NULL;
-		for (it=g_slist_nth(active_callouts, 0); 
-		     it != NULL; 
-		     it = g_slist_next(it)) {
-			Callout *callout_it = (Callout *) it->data;
-			if (callout_it->pid == child_pid) {
-				callout = callout_it;
-				break;
-			}
+
+		HAL_INFO (("Child pid %d terminated", child_pid));
+
+		if (active_callout == NULL) {
+			HAL_ERROR (("No active callout for child with pid %d - did it timeout?", child_pid));
+			goto out;
 		}
 
-		if (callout == NULL) {
+		if (active_callout->pid != child_pid) {
 			/* this should never happen */
-			HAL_ERROR (("Cannot find callout for terminated "
-				    "child with pid %d", child_pid));
+			HAL_ERROR (("Cannot find callout for terminated child with pid %d", child_pid));
 			goto out;
 		}
 
+		previous_callout = active_callout;
+		active_callout = NULL;
 
-		/* remove element from active_callouts list */
-		active_callouts = g_slist_delete_link (active_callouts,
-							       it);
+		g_source_remove (previous_callout->timeout_id);
 
-		if (callout->last_of_device)
-			hal_device_callouts_finished (callout->device);
+		if (previous_callout->last_of_device) {
+			hal_device_callouts_finished (previous_callout->device);
+			HAL_INFO (("Callouts done for %s", previous_callout->device->udi));
+		}
 		
-		g_free (callout->filename);
-		g_strfreev (callout->envp);
-		g_object_unref (callout->device);
-		g_free (callout);
+
+		g_free (previous_callout->filename);
+		g_strfreev (previous_callout->envp);
+		g_object_unref (previous_callout->device);
+		g_free (previous_callout);
 		
-		process_callouts ();
+		process_next_callout ();
 	}
 	
 out:
 	return TRUE;
 }
 
+#define CALLOUT_TIMEOUT 10000
+
+static gboolean
+callout_timeout_handler (gpointer data)
+{
+	Callout *callout;
+
+	callout = (Callout *) data;
+	
+	HAL_WARNING (("Timeout (%d ms) for callout %s", CALLOUT_TIMEOUT, callout->filename));
+
+	/* kill the child.. kill it the hard way */
+	kill (callout->pid, SIGKILL);
+
+	active_callout = NULL;
+
+	if (callout->last_of_device) {
+		hal_device_callouts_finished (callout->device);
+		HAL_INFO (("Callouts done for %s", callout->device->udi));
+	}
+	
+	
+	g_free (callout->filename);
+	g_strfreev (callout->envp);
+	g_object_unref (callout->device);
+	g_free (callout);
+
+	process_next_callout ();
+
+	return FALSE;
+}
+
 static void
-process_callouts (void)
+process_next_callout (void)
 {
 	Callout *callout;
-	gboolean last_of_device;
 	char *argv[3];
 	GError *err = NULL;
 	int num_props;
@@ -282,16 +268,15 @@
 		have_installed_sigchild_handler = TRUE;
 	}
 
-	if (pending_callouts == NULL ||
-	    g_hash_table_size (pending_callouts) == 0) {
-		processing_callouts = FALSE;
+next_callout:
+	if (active_callout != NULL)
 		return;
-	}
 
-	processing_callouts = TRUE;
+	callout = pop_pending_callout ();
+	if (callout == NULL)
+		return;
 
-	callout = pop_pending_callout (&last_of_device);
-	callout->last_of_device = last_of_device;
+	active_callout = callout;
 
 	argv[0] = callout->filename;
 
@@ -327,7 +312,8 @@
 	 */
 	callout->envp[callout->envp_index] = NULL;
 
-	active_callouts = g_slist_append (active_callouts, callout);
+	/* Setup timer for timeouts - ten seconds */
+	callout->timeout_id = g_timeout_add (CALLOUT_TIMEOUT, callout_timeout_handler, (gpointer) callout);
 
 	HAL_INFO (("Invoking %s/%s", callout->working_dir, argv[0]));
 
@@ -337,14 +323,13 @@
 		HAL_WARNING (("Couldn't invoke %s: %s", argv[0],
 			      err->message));
 		g_error_free (err);
+		g_source_remove (callout->timeout_id);
+		active_callout = NULL;
+		goto next_callout;
+	} else {
+		HAL_INFO (("Child pid %d for %s", callout->pid, argv[0]));
 	}
-}
 
-static gboolean
-process_callouts_idle (gpointer user_data)
-{
-	process_callouts ();
-	return FALSE;
 }
 
 void
@@ -354,6 +339,7 @@
 	GError *err = NULL;
 	const char *filename;
 	gboolean any_callouts = FALSE;
+	Callout *callout;
 
 	/* Directory doesn't exist.  This isn't an error, just exit
 	 * quietly. */
@@ -369,9 +355,9 @@
 		goto finish;
 	}
 
+	callout = NULL;
 	while ((filename = g_dir_read_name (dir)) != NULL) {
 		char *full_filename;
-		Callout *callout;
 		int num_props;
 		int i;
 
@@ -420,10 +406,13 @@
 		any_callouts = TRUE;
 	}
 
+	if (callout != NULL)
+		callout->last_of_device = TRUE;
+
 	g_dir_close (dir);
 
-	if (!processing_callouts)
-		g_idle_add (process_callouts_idle, NULL);
+	if (any_callouts)
+		process_next_callout ();
 
 finish:
 	/*
@@ -440,6 +429,7 @@
 {
 	GDir *dir;
 	GError *err = NULL;
+	Callout *callout;
 	const char *filename;
 
 	/* Directory doesn't exist.  This isn't an error, just exit
@@ -456,9 +446,9 @@
 		return;
 	}
 
+	callout = NULL;
 	while ((filename = g_dir_read_name (dir)) != NULL) {
 		char *full_filename;
-		Callout *callout;
 		int num_props;
 		int i;
 
@@ -506,10 +496,12 @@
 		add_pending_callout (callout->device, callout);
 	}
 
+	if (callout != NULL)
+		callout->last_of_device = TRUE;
+
 	g_dir_close (dir);
 
-	if (!processing_callouts)
-		g_idle_add (process_callouts_idle, NULL);
+	process_next_callout ();
 }
 
 void
@@ -517,6 +509,7 @@
 {
 	GDir *dir;
 	GError *err = NULL;
+	Callout *callout;
 	const char *filename;
 
 	/* Directory doesn't exist.  This isn't an error, just exit
@@ -533,9 +526,9 @@
 		return;
 	}
 
+	callout = NULL;
 	while ((filename = g_dir_read_name (dir)) != NULL) {
 		char *full_filename, *value;
-		Callout *callout;
 		int num_props;
 		int i;
 
@@ -559,6 +552,8 @@
 		callout->action = CALLOUT_MODIFY;
 		callout->device = g_object_ref (device);
 
+		callout->last_of_device = FALSE;
+
 		num_props = hal_device_num_properties (device);
 
 		value = hal_device_property_to_string (device, key);
@@ -587,8 +582,11 @@
 		g_free (value);
 	}
 
+	if (callout != NULL)
+		callout->last_of_device = TRUE;
+
+
 	g_dir_close (dir);
 
-	if (!processing_callouts)
-		g_idle_add (process_callouts_idle, NULL);
+	process_next_callout ();
 }

Index: device_info.c
===================================================================
RCS file: /cvs/hal/hal/hald/device_info.c,v
retrieving revision 1.17
retrieving revision 1.18
diff -u -d -r1.17 -r1.18
--- device_info.c	14 Dec 2004 02:57:48 -0000	1.17
+++ device_info.c	18 Jan 2005 19:48:12 -0000	1.18
@@ -1157,7 +1157,7 @@
 			    filename[len - 3] == 'f' &&
 			    filename[len - 2] == 'd' &&
 			    filename[len - 1] == 'i') {
-				HAL_INFO (("scan_fdi_files: Processing file '%s'", filename));
+				/*HAL_INFO (("scan_fdi_files: Processing file '%s'", filename));*/
 				found_fdi_file = process_fdi_file (dir, filename, d);
 				if (found_fdi_file) {
 					HAL_INFO (("*** Matched file %s/%s", dir, filename));

Index: hald_dbus.c
===================================================================
RCS file: /cvs/hal/hal/hald/hald_dbus.c,v
retrieving revision 1.17
retrieving revision 1.18
diff -u -d -r1.17 -r1.18
--- hald_dbus.c	14 Dec 2004 02:57:48 -0000	1.17
+++ hald_dbus.c	18 Jan 2005 19:48:12 -0000	1.18
@@ -94,7 +94,7 @@
 
 	snprintf (buf, 511, "No property %s on device with id %s", key,
 		  device_id);
-	HAL_WARNING ((buf));
+	/*HAL_WARNING ((buf));*/
 	reply = dbus_message_new_error (in_reply_to,
 					"org.freedesktop.Hal.NoSuchProperty",
 					buf);




More information about the hal-commit mailing list