Index: gtk/gtkmenu.c
===================================================================
--- gtk/gtkmenu.c	(revision 19563)
+++ gtk/gtkmenu.c	(working copy)
@@ -2883,7 +2883,18 @@ gtk_menu_key_press (GtkWidget	*widget,
 	    }
 	}
     }
-  
+  else if (!can_change_accels)
+    {
+      GtkWidget *toplevel = gtk_menu_get_toplevel (widget);
+
+      if (GTK_IS_WINDOW (toplevel) &&
+          _gtk_window_has_accel (GTK_WINDOW (toplevel), event))
+        {
+          gtk_menu_shell_cancel (GTK_MENU_SHELL (widget));
+          _gtk_window_activate_accel (GTK_WINDOW (toplevel), event);
+        }
+    }
+
   return TRUE;
 }
 
Index: gtk/gtkwindow.c
===================================================================
--- gtk/gtkwindow.c	(revision 19563)
+++ gtk/gtkwindow.c	(working copy)
@@ -7934,27 +7934,14 @@ gtk_window_free_key_hash (GtkWindow *win
     }
 }
 
-/**
- * gtk_window_activate_key:
- * @window:  a #GtkWindow
- * @event:   a #GdkEventKey
- *
- * Activates mnemonics and accelerators for this #GtkWindow. This is normally
- * called by the default ::key_press_event handler for toplevel windows,
- * however in some cases it may be useful to call this directly when
- * overriding the standard key handling for a toplevel window.
- *
- * Return value: %TRUE if a mnemonic or accelerator was found and activated.
- **/
-gboolean
-gtk_window_activate_key (GtkWindow   *window,
-			 GdkEventKey *event)
+static GtkWindowKeyEntry *
+gtk_window_get_key_entry (GtkWindow   *window,
+                          GdkEventKey *event,
+                          gboolean     include_mnemonics)
 {
   GtkKeyHash *key_hash;
-  GtkWindowKeyEntry *found_entry = NULL;
-
-  g_return_val_if_fail (GTK_IS_WINDOW (window), FALSE);
-  g_return_val_if_fail (event != NULL, FALSE);
+  GtkWindowKeyEntry *first_mnemonic = NULL;
+  GtkWindowKeyEntry *first_accel = NULL;
 
   key_hash = gtk_window_get_key_hash (window);
 
@@ -7970,20 +7957,56 @@ gtk_window_activate_key (GtkWindow   *wi
       for (tmp_list = entries; tmp_list; tmp_list = tmp_list->next)
 	{
 	  GtkWindowKeyEntry *entry = tmp_list->data;
+
 	  if (entry->is_mnemonic)
 	    {
-	      found_entry = entry;
-	      break;
+	      first_mnemonic = entry;
+
+              if (include_mnemonics)
+                break;
 	    }
-	}
-      
-      if (!found_entry && entries)
-	found_entry = entries->data;
+          else
+            {
+              first_accel = entry;
+
+              if (!include_mnemonics)
+                break;
+            }
 
-      g_slist_free (entries);
+          g_slist_free (entries);
+        }
     }
 
-  if (found_entry)
+  if (include_mnemonics && first_mnemonic)
+    return first_mnemonic;
+
+  return first_accel;
+}
+
+/**
+ * gtk_window_activate_key:
+ * @window:  a #GtkWindow
+ * @event:   a #GdkEventKey
+ *
+ * Activates mnemonics and accelerators for this #GtkWindow. This is normally
+ * called by the default ::key_press_event handler for toplevel windows,
+ * however in some cases it may be useful to call this directly when
+ * overriding the standard key handling for a toplevel window.
+ *
+ * Return value: %TRUE if a mnemonic or accelerator was found and activated.
+ **/
+gboolean
+gtk_window_activate_key (GtkWindow   *window,
+			 GdkEventKey *event)
+{
+  GtkWindowKeyEntry *entry;
+
+  g_return_val_if_fail (GTK_IS_WINDOW (window), FALSE);
+  g_return_val_if_fail (event != NULL, FALSE);
+
+  entry = gtk_window_get_key_entry (window, event, TRUE);
+
+  if (entry)
     {
       gboolean enable_mnemonics;
       gboolean enable_accels;
@@ -7993,23 +8016,71 @@ gtk_window_activate_key (GtkWindow   *wi
                     "gtk-enable-accels", &enable_accels,
                     NULL);
 
-      if (found_entry->is_mnemonic)
+      if (entry->is_mnemonic)
         {
           if (enable_mnemonics)
-            return gtk_window_mnemonic_activate (window, found_entry->keyval,
-                                                 found_entry->modifiers);
+            return gtk_window_mnemonic_activate (window, entry->keyval,
+                                                 entry->modifiers);
         }
       else
         {
           if (enable_accels)
-            return gtk_accel_groups_activate (G_OBJECT (window), found_entry->keyval,
-                                              found_entry->modifiers);
+            return gtk_accel_groups_activate (G_OBJECT (window), entry->keyval,
+                                              entry->modifiers);
         }
     }
 
   return FALSE;
 }
 
+gboolean
+_gtk_window_has_accel (GtkWindow   *window,
+                       GdkEventKey *event)
+{
+  GtkWindowKeyEntry *entry ;
+  gboolean enable_accels;
+
+  g_return_val_if_fail (GTK_IS_WINDOW (window), FALSE);
+  g_return_val_if_fail (event != NULL, FALSE);
+
+  g_object_get (gtk_widget_get_settings (GTK_WIDGET (window)),
+                "gtk-enable-accels", &enable_accels,
+                NULL);
+
+  if (!enable_accels)
+    return FALSE;
+
+  entry = gtk_window_get_key_entry (window, event, FALSE);
+
+  return entry != NULL;
+}
+
+gboolean
+_gtk_window_activate_accel (GtkWindow   *window,
+                            GdkEventKey *event)
+{
+  GtkWindowKeyEntry *entry;
+  gboolean enable_accels;
+
+  g_return_val_if_fail (GTK_IS_WINDOW (window), FALSE);
+  g_return_val_if_fail (event != NULL, FALSE);
+
+  g_object_get (gtk_widget_get_settings (GTK_WIDGET (window)),
+                "gtk-enable-accels", &enable_accels,
+                NULL);
+
+  if (!enable_accels)
+    return FALSE;
+
+  entry = gtk_window_get_key_entry (window, event, FALSE);
+
+  if (entry)
+    return gtk_accel_groups_activate (G_OBJECT (window), entry->keyval,
+                                      entry->modifiers);
+
+  return FALSE;
+}
+
 static void
 window_update_has_focus (GtkWindow *window)
 {
Index: gtk/gtkwindow.h
===================================================================
--- gtk/gtkwindow.h	(revision 19563)
+++ gtk/gtkwindow.h	(working copy)
@@ -425,6 +425,11 @@ void _gtk_window_keys_foreach (GtkWindow
 			       GtkWindowKeysForeachFunc func,
 			       gpointer                 func_data);
 
+gboolean        _gtk_window_has_accel           (GtkWindow      *window,
+                                                 GdkEventKey    *event);
+gboolean        _gtk_window_activate_accel      (GtkWindow      *window,
+                                                 GdkEventKey    *event);
+
 /* --- internal (GtkAcceleratable) --- */
 gboolean	_gtk_window_query_nonaccels	(GtkWindow	*window,
 						 guint		 accel_key,
