bug-gnu-emacs
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

bug#63495: 28.2; menu crashes on macos


From: Alan Third
Subject: bug#63495: 28.2; menu crashes on macos
Date: Thu, 13 Jul 2023 20:41:23 +0100

On Thu, Jul 13, 2023 at 10:47:35AM +0200, Daniel Martín wrote:
> One fundamental problem I see with the current logic (or maybe I'm
> misunderstanding something) is that, menuNeedsUpdate: is called for both
> the menubar and for context menus.  However, the ns_update_menubar
> routine does not even use the NSMenu that AppKit passed to
> menuNeedsUpdate:, it always does this:
> 
> id menu = [NSApp mainMenu];
>
> This means that the menu variable will always be the menubar.  The code
> in ns_update_menubar is only prepared to handle menubar updates, but as
> this function updates menu_items, a data structure that is used later by
> the context menu in find_and_return_menu_selection, Emacs crashes
> because of inconsistencies.

Indeed, it looks like context menus don't go anywhere near
ns_update_menubar and use similar, but not identical, code in
ns_menu_show to construct the menu contents.

> Is there any reason we need to do something for context menus in
> menuNeedsUpdate:?  Alan said that context menus are completely built in
> advance (as opposed to the menubar, which is partially built), so I
> propose the following patch (which does seem to fix the crash for me and
> doesn't cause regressions with the menubar):
> 
> diff --git a/src/nsmenu.m b/src/nsmenu.m
> index 2c1f575bdf2..ca367d1abd1 100644
> --- a/src/nsmenu.m
> +++ b/src/nsmenu.m
> @@ -477,6 +477,16 @@ - (instancetype)initWithTitle: (NSString *)title
>     call to ns_update_menubar.  */
>  - (void)menuNeedsUpdate: (NSMenu *)menu
>  {
> +
> +  /* The context menu is built and then displayed, as opposed to the
> +     top-menu, which is partially built and then updated and filled in
> +     when it's time to display it.  Therefore, we don't call
> +     ns_update_menubar if a context menu is active. */
> +  if (context_menu_value != 0)
> +    {
> +      return;
> +    }
> +
>  #ifdef NS_IMPL_GNUSTEP
>    static int inside = 0;
>  #endif

This was going to be my next suggestion, after checking that
context_menu_value is always non-zero when using the context menu and
zero when using the main menu. Which I haven't done.

The next best thing I can think of is to add a flag that marks it
specifically as a context menu, or create a specific context menu
class that over-rides menuNeedsUpdate, but I dislike the former as we
can probably work out it's a context menu in other ways, and the
latter is a bit ridiculous.
-- 
Alan Third





reply via email to

[Prev in Thread] Current Thread [Next in Thread]