Commit 8fb8adfc90fa5ffb059d9b38cec061f7bbcbfc49

Alex Szpakowski 2019-07-13T17:04:02

macOS: Fix SDL_GL_CreateContext/MakeCurrent on non-main threads causing a Main Thread Checker warning when built with Xcode 11 / the macOS 10.15 SDK. Fixes bug #4714.

diff --git a/src/video/cocoa/SDL_cocoaopengl.m b/src/video/cocoa/SDL_cocoaopengl.m
index ea59f99..987fa99 100644
--- a/src/video/cocoa/SDL_cocoaopengl.m
+++ b/src/video/cocoa/SDL_cocoaopengl.m
@@ -95,6 +95,18 @@
 
     if (newWindow) {
         SDL_WindowData *windowdata = (SDL_WindowData *)newWindow->driverdata;
+        NSView *contentview = windowdata->sdlContentView;
+
+        /* This should never be nil since sdlContentView is only nil if the
+           window was created via SDL_CreateWindowFrom, and SDL doesn't allow
+           OpenGL contexts to be created in that case. However, it doesn't hurt
+           to check. */
+        if (contentview == nil) {
+            /* Prefer to access the cached content view above instead of this,
+               since as of Xcode 11 + SDK 10.15, [window contentView] causes
+               Apple's Main Thread Checker to output a warning. */
+            contentview = [windowdata->nswindow contentView];
+        }
 
         /* Now sign up for scheduled updates for the new window. */
         NSMutableArray *contexts = windowdata->nscontexts;
@@ -102,8 +114,8 @@
             [contexts addObject:self];
         }
 
-        if ([self view] != [windowdata->nswindow contentView]) {
-            [self setView:[windowdata->nswindow contentView]];
+        if ([self view] != contentview) {
+            [self setView:contentview];
             if (self == [NSOpenGLContext currentContext]) {
                 [self update];
             } else {
diff --git a/src/video/cocoa/SDL_cocoawindow.h b/src/video/cocoa/SDL_cocoawindow.h
index 3c4ff63..9704e18 100644
--- a/src/video/cocoa/SDL_cocoawindow.h
+++ b/src/video/cocoa/SDL_cocoawindow.h
@@ -113,6 +113,7 @@ struct SDL_WindowData
 {
     SDL_Window *window;
     NSWindow *nswindow;
+    NSView *sdlContentView; /* nil if window is created via CreateWindowFrom */
     NSMutableArray *nscontexts;
     SDL_bool created;
     SDL_bool inWindowMove;
diff --git a/src/video/cocoa/SDL_cocoawindow.m b/src/video/cocoa/SDL_cocoawindow.m
index 5972568..faee02c 100644
--- a/src/video/cocoa/SDL_cocoawindow.m
+++ b/src/video/cocoa/SDL_cocoawindow.m
@@ -1307,6 +1307,11 @@ SetupWindowData(_THIS, SDL_Window * window, NSWindow *nswindow, SDL_bool created
     data->videodata = videodata;
     data->nscontexts = [[NSMutableArray alloc] init];
 
+    /* Only store this for windows created by us since the content view might
+     * get replaced from under us otherwise, and we only need it when the
+     * window is guaranteed to be created by us (OpenGL contexts). */
+    data->sdlContentView = created ? [nswindow contentView] : nil;
+
     /* Create an event listener for the window */
     data->listener = [[Cocoa_WindowListener alloc] init];