Priority: P1: Critical
Affects Version/s: 5.11.0, 5.11.1, 5.11.2, 5.12.5
Component/s: Widgets: Main Window
Commits:a9246c7132a2c8864d3ae6cebd260bb9ee711fcb (qt/qtbase/5.12) 009abcd7b66738bece6cf354776dfb2ef401636b (qt/qtbase/5.15) e2f35fa6842508f6bd9d2343f08a17a2a292fd71 (qt/qtbase/5.12.7)
Sprint:Bug Fixing Week Q2/2020
Starting with Qt 5.11, winId() seems to return a freed pointer when the QMainWindow is hidden and then showed which led to a crash when used. This issue could not be reproduced on Qt 5.9 and Qt 5.10 and has been introduced in Qt 5.11.
See attached screencast: screencast.mov
Steps to reproduce:
- Download the attached application QtBlackTitlebar QtBlackTitlebar_src.zip
- Compile the application on macOS 10.13.5 and run it
- Close the window
- Using the QSystemTray, display the window
Result: The application crashes.
The application tries to determine if the new Key NSWindow is the main window in:
In order to do so, it gets the singleton instance of the MainWindow (which is a QMainWindow) and gets the winId() pointer. It casts the winId() pointer to an NSView and compares the NSWindow to the NSWindow passed in the NSNotification.
Using winId() like this is probably not ideal but the value returned by winId() should never be a freed pointer. If the underlaying object has been released, winId() should probably return a NULL pointer.
Also I could not find any proper API to detect if the NSWindow received in windowDidBecomeKey: is the main QMainWindow. A possible workaround could be to check the class type of the NSWindow like the following, although it is again not clean: