Tk Source Code

View Ticket
Login
Ticket UUID: 6328ce0301a65a482dcf96f5c1013533549bd2ac
Title: macOS: crash with menu
Type: Bug Version: trunk
Submitter: nab Created on: 2025-03-09 09:04:35
Subsystem: 11. Aqua Menus Assigned To: marc_culler
Priority: 5 Medium Severity: Important
Status: Closed Last Modified: 2025-03-12 14:07:13
Resolution: Fixed Closed By: marc_culler
    Closed on: 2025-03-12 14:07:13
Description:
Hi Marc,
while (trying) using trunk with my app, I've triggered a crash which I can reproduce with widgets Demo:
-run the widget demo 
-click on 1. Menus and cascades (sub-menus) 
-click on Dismiss
-open pendulum simulation
-in the Apple bar menu click on Wish

Boom


here's the log:

Process:               Wish [87798]
Path:                  /Users/USER/*/Tk.framework/Versions/9.0/Resources/Wish.app/Contents/MacOS/Wish
Identifier:            com.tcltk.wish
Version:               9.0.2 (9.0.2)
Code Type:             ARM-64 (Native)
Parent Process:        launchd [1]
User ID:               501

Date/Time:             2025-03-09 09:53:40.4595 +0100
OS Version:            macOS 15.3.1 (24D70)
Report Version:        12
Anonymous UUID:        FD7EAADE-1F5C-AA2D-68E3-E204BE5F937D

Sleep/Wake UUID:       3E7FD2BB-7D01-48B5-92CE-00025F78F063

Time Awake Since Boot: 640000 seconds
Time Since Wake:       2391 seconds

System Integrity Protection: enabled

Crashed Thread:        0  Dispatch queue: com.apple.main-thread

Exception Type:        EXC_BAD_ACCESS (SIGSEGV)
Exception Codes:       KERN_INVALID_ADDRESS at 0x0000000000000036
Exception Codes:       0x0000000000000001, 0x0000000000000036

Termination Reason:    Namespace SIGNAL, Code 11 Segmentation fault: 11
Terminating Process:   exc handler [87798]

VM Region Info: 0x36 is not in any region.  Bytes before following region: 4373970890
      REGION TYPE                    START - END         [ VSIZE] PRT/MAX SHRMOD  REGION DETAIL
      UNUSED SPACE AT START
--->  
      __TEXT                      104b58000-104b60000    [   32K] r-x/r-x SM=COW  /Users/USER/*/Tk.framework/Versions/9.0/Resources/Wish.app/Contents/MacOS/Wish

Thread 0 Crashed::  Dispatch queue: com.apple.main-thread
0   Tk                            	       0x104f526b4 TkActivateMenuEntry + 36 (tkMenu.c:2706)
1   AppKit                        	       0x191102e4c -[NSMenu _informDelegateOfHighlightedItem:] + 544
2   AppKit                        	       0x1917f3158 -[NSCocoaMenuImpl _addHighlightForView:] + 720
3   AppKit                        	       0x1917f2c18 __60-[NSCocoaMenuImpl _highlightMenuItemView:shouldOpenSubmenu:]_block_invoke + 164
4   AppKit                        	       0x1917f28dc -[NSCocoaMenuImpl _highlightMenuItemView:shouldOpenSubmenu:] + 380
5   AppKit                        	       0x1917ece78 -[NSCocoaMenuImpl _performBlock:resigningFirstResponder:] + 72
6   AppKit                        	       0x1917f1c20 -[NSCocoaMenuImpl _routeEventIfNeeded:toSubview:] + 824
7   AppKit                        	       0x1917f16ec -[NSCocoaMenuImpl handleMouseEvent:] + 144
8   AppKit                        	       0x191beaf28 -[NSMenuBarImpl mouseDown:] + 128
9   AppKit                        	       0x1915f4aa8 -[NSMenuTrackingSession _mouseDownEventHandler:] + 184
10  AppKit                        	       0x1916af7a8 -[NSMenuBarTrackingSession _mouseDownEventHandler:] + 304
11  AppKit                        	       0x1916af638 -[NSMenuBarTrackingSession _handleMonitorEvent:] + 408
12  AppKit                        	       0x1916af328 __57-[NSMenuBarTrackingSession _addLocalEventMonitorIfNeeded]_block_invoke + 104
13  AppKit                        	       0x1910581e0 _NSSendEventToDequeuingObservers + 252
14  AppKit                        	       0x1917c91f0 -[NSApplication(NSEventRouting) _nextEventMatchingEventMask:untilDate:inMode:dequeue:] + 2172
15  Tk                            	       0x104ff8850 TkMacOSXEventsCheckProc + 276 (tkMacOSXNotify.c:447)
16  Tcl                           	       0x1053ea460 Tcl_DoOneEvent + 376
17  Tk                            	       0x104f31448 Tk_MainEx + 1476 (tkMain.c:377)
18  Wish                          	       0x104b5ee78 main + 80 (tkAppInit.c:115)
19  dyld                          	       0x18ce84274 start + 2840
User Comments: marc_culler (claiming to be Marc Culler) added on 2025-03-12 14:07:13:
Thanks.  I removed the unused variables.

nab added on 2025-03-12 08:25:50:
Hi Marc,

there's two warnings after the merge:
/Users/nico/daylight/lib/build/tk/unix/../macosx/tkMacOSXMenu.c:1163:24: warning: variable 'currentInterp' set but not used [-Wunused-but-set-variable]
 1163 |     static Tcl_Interp *currentInterp = NULL;
      |                        ^
1 warning generated.


/Users/nico/daylight/lib/build/tk/unix/../macosx/tkMacOSXWm.c:1297:17: warning: unused variable 'menubar' [-Wunused-variable]
 1297 |                     Tk_Window menubar = frontPtr->wmInfoPtr->menuPtr->mainMenuPtr->tkwin;
      |                               ^~~~~~~

++
Nicolas

marc_culler (claiming to be Marc Culler) added on 2025-03-12 03:54:15:
I am closing this ticket now.  I don't think it is related to the issue with
the "About" window.

marc_culler (claiming to be Marc Culler) added on 2025-03-11 19:11:18:
Thank you Nicolas.

I will look at why closing the about window does not return focus to any
window of the app.

nab added on 2025-03-11 17:52:48:
Hi Marc,
thanks !!
the bug fix branch works as expected.
it was easy in my app to configure -menu for each new toplevels as I have one proc for each new one.

but in my app I use (a little modified) wigdet::dialog which is part of Tk lib which create his own toplevel, and it was quite a work to add configure -menu for each of them.

but I did it and it's ok

++
Nicolas

marc_culler (claiming to be Marc Culler) added on 2025-03-11 17:39:19:
I have opened a new bugfix branch for this ticket bug-6328ce0301-again
which fixes the issue with destroying windows other than the focus window.

Nicolas, would you please test that branch?

marc_culler (claiming to be Marc Culler) added on 2025-03-11 13:49:22:
I didn't report the problem accurately.  It is not that a window is
being activated without having its menubar posted.  The problem seems
to be that whenever a non-focus window is destroyed it menubar is
removed but the menubar for the new key window is not posted.

A separate issue is which menubar should be used if an app is active but
has no Key Window.

marc_culler (claiming to be Marc Culler) added on 2025-03-11 13:37:07:
Hi Nicolas,

I see what you are talking about.  When a window is destroyed and another
window receives focus, the menubar for the new focus window does not get
posted.  If a window receives focus by clicking the mouse inside the window
then its manubar does get posted.  It also seems to be possible for no
menubar to be posted, which is the bug that I was running into and which
I thought was caused by the previous strange setup.  I saw that happen but
I don't know what I did to make it happen.

I have reopened the ticket.

I think this should not be hard to fix.  As I recall, there is a notification which a TKWindow receives when the window becomes the "Key
Window", i.e. when it receives focus.  I think that the callback for that
notification just needs to post the menubar assigned to the window.  I
will look at that.

nab added on 2025-03-11 12:17:57:
also (but maybe that's another story...)
run mbtest.tcl
Click on Wish/about Tcl/TK
Close the about toplevel
focus does not come back to Third

++

nab added on 2025-03-11 12:13:58:
well it does the same thing...
run mbtest.tcl
Third is on top
Close First (without activating it)
Third is top but menu display root's one

++

marc_culler (claiming to be Marc Culler) added on 2025-03-11 12:00:46:
Hi Nicolas,
Thqt sounds bad.  But I can't produce that behavior when I try it.  Do
you have a simple script that shows what you are seeing?

I uploaded a test script mbtest.tcl which does not seem to show that
behavior.

nab added on 2025-03-11 07:27:52:
Hi Marc,
the menuBar for all toplevels does not work very well...
I did call $win configure -menu .menuBar for every toplevels I initiate.

if I destroy a toplevel, Wish menu is back for previous toplevel

++

marc_culler (claiming to be Marc Culler) added on 2025-03-10 22:28:35:
Thanks, Kevin.  And thanks Nicolas for the report.

I think I can close this now.

kevin_walzer added on 2025-03-10 21:14:26:
I agree the menubar should be explicitly configured or the default one that is displayed when Wish is first launched. That is simple and easy to understand.

marc_culler (claiming to be Marc Culler) added on 2025-03-10 15:14:33:
I am uploading a simple demo script that attaches different menus to
different toplevels.

marc_culler (claiming to be Marc Culler) added on 2025-03-10 14:05:15:
Let's get an opinion from Kevin.

nab added on 2025-03-10 13:52:01:
okayyyy...
in that case I will configure menubar for each new toplevel

++

marc_culler (claiming to be Marc Culler) added on 2025-03-10 13:46:20:
Hi Nicolas,

I disagree. I implemented the "inherit from parent" scheme so I could try
it out.  I think it is a bad idea.  It introduces lots of confusing
unpredictable behavior.  Also, I realized that the previous version of it
was responsible for a very unpleasant bug in one of my own applications.

The issue is that the menubar is set when a window is moved to the front.
So, for example, suppose you have two toplevels .a and .a.b and you change
the menubar for .a.  With the "inherit from parent" scheme If .b is in front
when you do that, the menubar will stay the same, for now, but next time .b
moves to the front it will have a different menubar.  If .a is in front
then the menubar will change immediately.  So which menubar is being
displayed does not depend on the program.  I depends on what the user
happens to be doing at a certain time. That is bad.

Consider the alternative: either you explicitly assign a menubar to a
toplevel or it gets the default menu.  There is nothing the least bit
confusing about that.  It is compeletely predictable.

What is the cost of having the menubar behavior be completely predictable?
One line of code when a toplevel is created.  For me, predictable behavior
is well worth that cost.  And introducing confusion in order to avoid
one line of code per toplevel seems like a really bad idea.

nab added on 2025-03-10 07:04:52:
Hi Marc,
the  bug-6328ce0301-inherit branch works fine for me, the main menubar of my app is propagated to each new toplevel which IMHO is the desired behavior.

thanks.

++

marc_culler (claiming to be Marc Culler) added on 2025-03-09 22:24:47:
Well, I thought that was how you were supposed to do it.  But apparently
there used to be some other behavior, like maybe a window defaults to using
the same menu as the root window, or its parent.  I am not sure.

It seems reasonable to me that you should have to specify for each window
which menu it should use.

I wish I knew when this behavior changed.

nab added on 2025-03-09 21:37:32:
no as I was never obliged to do that...
I only install private bindings for new toplevels and the WM_DELETE_WINDOW handler.

I never had to use $new_toplevel configure -menu $app_menu

should I?
(indeed it will fix my issue...)

++

marc_culler (claiming to be Marc Culler) added on 2025-03-09 21:25:11:
Nicolas,

When you create a new toplevel, and you want the new toplevel to use your
custom app menu instead of the default menu, you are supposed to call

$new_toplevel configure -menu $app_menu

Are you doing that?

nab added on 2025-03-09 20:39:45:
I've understood what is going on, it seems that with this bug fix branch, every fresh toplevel have Wish menuBar by default... not the app one.

I do create a .menubar menu for .
if I open another toplevel, my .menubar menu disappear wand Wish one is displayed.
if I focus back to . then my .menubar is displayed.

hope it helps.

++

marc_culler (claiming to be Marc Culler) added on 2025-03-09 19:11:48:
That means that Tk_SetMainMenubar is being called with a NULL menu name.
When that happens it (now) uses the default menu (instead of crashing).

For example, with the "Menus and cascades demo" you can open a different
demo at the same time, and when you switch back and forth between the
two demos the menubars switch as well. When you activate the window for
the menu demo, the call to Tk_SetMainMenubar is passing the menu name
".menu.menu" which is the name given to the menubar menu in that demo.
When you switch to the other demo that function is called with a NULL
menu name.

Does your app create a named menu for the main window, or are you just
(temporarily) adding cascades to the default menu?  Perhaps comparing
your code with the demo code would provide some hints.  Maybe tbe menu
name is not being saved correctly in the toplevel structure.

nab added on 2025-03-09 18:41:26:
Hi Marc,
it's fixed for the reported crash.

BUT... it leads to another undesirable behavior...
when I start my app, there's my menu stuff in the Apple bar.
fine.

if I load a file the apple menu bar disappear (as usual) but then it's not redisplayed as my app menu... it's displayed as Wish menu !!

I'll attached a pict.

++

marc_culler (claiming to be Marc Culler) added on 2025-03-09 18:18:12:
Hi Nicolas,

I think this is fixed in the bugfix branch bug-6328ce0301.

The logic of the code that I removed did not make sense to me.  But maybe
it was there for some reason that I don't understand.  So this should be
tested carefully.  I couldn't find any issues, though.  Can you please test?
Thanks.

marc_culler (claiming to be Marc Culler) added on 2025-03-09 16:54:35:
I just verified that this crash also occurs in the core-9-0-1 release.

marc_culler (claiming to be Marc Culler) added on 2025-03-09 16:49:40:
I take it back.  This bug has nothing to do with my fix for [7e28ef577a].
It was there several commits before I committed my fix.  I haven't bisected
yet, but it has been there for a while.  I would guess it goes back to
the first 9.0 release at least.  It also has nothing to do with the
pendulum.  You can get the same crash by starting any other demo and
opening the Wish menu.

There is something broken about the menubar, which you can also see
in the widget demo without making it crash.

When you start the widget demo you have five menus:
    Wish File Edit Window Help

When you run the "Menus and Cascades" demo you get 7 menus:
   Wish File Basic Cascades Icons More Colors

When you dismiss the menu demo you do not get the original 5 item menu back.
You get a menu with only one cascade, "Wish".  And that menu is apparently
corrupted.

So the only connection with [7e28ef577a] is that the fix for it made
you play around with your app and discover this bug.  Thanks for doing
that!

At least I know where to look now.

marc_culler (claiming to be Marc Culler) added on 2025-03-09 15:22:15:
Thanks, Nicolas.

That is definitely caused by my fix for [7e28ef577a].  I think I know what
the cause is.

Attachments: