? alsa-fix.diff
Index: Makefile.am
===================================================================
RCS file: /cvs/gnome/gnome-control-center/gnome-settings-daemon/Makefile.am,v
retrieving revision 1.41
diff -u -r1.41 Makefile.am
--- Makefile.am	16 Jan 2004 12:00:37 -0000	1.41
+++ Makefile.am	17 Mar 2004 11:41:19 -0000
@@ -58,13 +58,14 @@
 #	$(AccessX_files)		
 
 gnome_settings_daemon_LDADD = \
-	$(LIBXKLAVIER_LIBS)					\
+	$(LIBXKLAVIER_LIBS)						\
 	$(GNOME_SETTINGS_DAEMON_LIBS)					\
 	$(top_builddir)/libbackground/libbackground.la			\
 	$(top_builddir)/libsounds/libsounds.a				\
 	$(top_builddir)/libgswitchit/libgswitchit.a			\
 	$(top_builddir)/libwindow-settings/libgnome-window-settings.la 	\
-	$(top_builddir)/gnome-settings-daemon/actions/libacme.la\
+	$(top_builddir)/gnome-settings-daemon/actions/libacme.la	\
+	$(ALSA_LIBS) $(GST_LIBS)					\
 	$(XF86MISC_LIBS)
 
 #AccessX_files = \
Index: gnome-settings-multimedia-keys.c
===================================================================
RCS file: /cvs/gnome/gnome-control-center/gnome-settings-daemon/gnome-settings-multimedia-keys.c,v
retrieving revision 1.5
diff -u -r1.5 gnome-settings-multimedia-keys.c
--- gnome-settings-multimedia-keys.c	15 Jan 2004 19:38:42 -0000	1.5
+++ gnome-settings-multimedia-keys.c	17 Mar 2004 11:41:20 -0000
@@ -227,27 +227,82 @@
 }
 
 static void
-unhookup_keysym (int keycode)
+unhookup_keysym (int keycode, int index)
 {
 	char *command;
 
 	if (keycode <= 0)
 		return;
 
-	command = g_strdup_printf ("xmodmap -e \"keycode %d = \"", keycode);
+	if (keys[index].saved_binding != NULL) {
+		command = g_strdup_printf ("xmodmap -e \"%s\"",
+				keys[index].saved_binding);
+	} else {
+		command = g_strdup_printf ("xmodmap -e \"keycode %d = \"",
+				keycode);
+	}
+
+	g_free (keys[index].saved_binding);
+	keys[index].saved_binding = NULL;
 
 	g_spawn_command_line_sync (command, NULL, NULL, NULL, NULL);
 	g_free (command);
 }
 
+static char *
+save_original_modmap_cmd (int keycode)
+{
+	char *argv[3];
+	char *output, **lines, *res;
+	int i;
+	GError *error = NULL;
+	
+	argv[0] = "xmodmap";
+	argv[1] = "-pke";
+	argv[2] = NULL;
+	
+	res = NULL;
+
+	if (g_spawn_sync (NULL, argv, NULL,
+				G_SPAWN_SEARCH_PATH, 0, 0,
+				&output, NULL, NULL, &error) == FALSE)
+	{
+		/* FIXME we need to print out the error, or show
+		 * a dialog window with it*/
+		g_error_free (error);
+		return NULL;
+	}
+
+	lines = g_strsplit (output, "\n", 0);
+	for (i = 0; lines[i] != NULL; i++)
+	{
+		int tmp;
+
+		if (sscanf (lines[i], "keycode %d = ", &tmp) != 1)
+			continue;
+
+		if (keycode == tmp)
+		{
+			res = g_strdup (lines[i]);
+			break;
+		}
+	}
+
+	g_strfreev (lines);
+
+	return res;
+}
+
 static gboolean
-hookup_keysym (int keycode, const char *keysym)
+hookup_keysym (int keycode, const char *keysym, int index)
 {
 	char *command;
 
 	if (keycode <= 0)
 		return TRUE;
 
+	keys[index].saved_binding = save_original_modmap_cmd (keycode);
+
 	command = g_strdup_printf ("xmodmap -e \"keycode %d = %s\"",
 			keycode, keysym);
 
@@ -324,7 +379,7 @@
 			Key *key;
 
 			if (keys[i].key != NULL)
-				unhookup_keysym (keys[i].key->keycode);
+				unhookup_keysym (keys[i].key->keycode, i);
 
 			g_free (keys[i].key);
 			keys[i].key = NULL;
@@ -344,19 +399,19 @@
 
 			switch (keys[i].key_type) {
 			case PLAY_KEY:
-				hookup_keysym (key->keycode, "XF86AudioPlay");
+				hookup_keysym (key->keycode, "XF86AudioPlay", i);
 				break;
 			case PAUSE_KEY:
-				hookup_keysym (key->keycode, "XF86AudioPause");
+				hookup_keysym (key->keycode, "XF86AudioPause", i);
 				break;
 			case STOP_KEY:
-				hookup_keysym (key->keycode, "XF86AudioStop");
+				hookup_keysym (key->keycode, "XF86AudioStop", i);
 				break;
 			case PREVIOUS_KEY:
-				hookup_keysym (key->keycode, "XF86AudioPrev");
+				hookup_keysym (key->keycode, "XF86AudioPrev", i);
 				break;
 			case NEXT_KEY:
-				hookup_keysym (key->keycode, "XF86AudioNext");
+				hookup_keysym (key->keycode, "XF86AudioNext", i);
 				break;
 			}
 
@@ -448,23 +503,23 @@
 		switch (keys[i].key_type) {
 		case PLAY_KEY:
 			hookup_keysym (keys[i].key->keycode,
-					"XF86AudioPlay");
+					"XF86AudioPlay", i);
 			break;
 		case PAUSE_KEY:
 			hookup_keysym (keys[i].key->keycode,
-					"XF86AudioPause");
+					"XF86AudioPause", i);
 			break;
 		case STOP_KEY:
 			hookup_keysym (keys[i].key->keycode,
-					"XF86AudioStop");
+					"XF86AudioStop", i);
 			break;
 		case PREVIOUS_KEY:
 			hookup_keysym (keys[i].key->keycode,
-					"XF86AudioPrev");
+					"XF86AudioPrev", i);
 			break;
 		case NEXT_KEY:
 			hookup_keysym (keys[i].key->keycode,
-					"XF86AudioNext");
+					"XF86AudioNext", i);
 			break;
 		}
 	}
Index: actions/acme.h
===================================================================
RCS file: /cvs/gnome/gnome-control-center/gnome-settings-daemon/actions/acme.h,v
retrieving revision 1.2
diff -u -r1.2 acme.h
--- actions/acme.h	14 Jan 2004 00:22:55 -0000	1.2
+++ actions/acme.h	17 Mar 2004 11:41:20 -0000
@@ -60,8 +60,9 @@
 	int key_type;
 	const char *gconf_key;
 	Key *key;
+	char *saved_binding;
 } keys[HANDLED_KEYS] = {
-	{ MUTE_KEY, GCONF_BINDING_DIR "/volume_mute",NULL },
+	{ MUTE_KEY, GCONF_BINDING_DIR "/volume_mute",NULL, NULL },
 	{ VOLUME_DOWN_KEY, GCONF_BINDING_DIR "/volume_down", NULL },
 	{ VOLUME_UP_KEY, GCONF_BINDING_DIR "/volume_up", NULL },
 	{ POWER_KEY, GCONF_BINDING_DIR "/power", NULL },
