Browse Source

render: Manage memory for SDL_Renderer* at higher level.

Previously, each backend would allocate and free the renderer struct. Now
the higher level does it, so the backends only manage their private resources.

This removes some boilerplate and avoids some potential accidents.

(Manually cherry-picked from 39c8434f5fd099397df7c6269d30b6f807b2456a)

Reference Issue #10174.
Ryan C. Gordon 9 months ago
parent
commit
944dc4701c

+ 39 - 11
src/render/SDL_render.c

@@ -954,6 +954,7 @@ SDL_Renderer *SDL_CreateRenderer(SDL_Window *window, int index, Uint32 flags)
     int n = SDL_GetNumRenderDrivers();
     SDL_bool batching = SDL_TRUE;
     const char *hint;
+    int rc = -1;
 
 #if defined(__ANDROID__)
     Android_ActivityMutex_Lock_Running();
@@ -974,6 +975,14 @@ SDL_Renderer *SDL_CreateRenderer(SDL_Window *window, int index, Uint32 flags)
         goto error;
     }
 
+    renderer = (SDL_Renderer *)SDL_calloc(1, sizeof(*renderer));
+    if (!renderer) {
+        SDL_OutOfMemory();
+        goto error;
+    }
+
+    renderer->magic = &renderer_magic;
+
     hint = SDL_GetHint(SDL_HINT_RENDER_VSYNC);
     if (hint && *hint) {
         if (SDL_GetHintBoolean(SDL_HINT_RENDER_VSYNC, SDL_TRUE)) {
@@ -991,30 +1000,36 @@ SDL_Renderer *SDL_CreateRenderer(SDL_Window *window, int index, Uint32 flags)
 
                 if (SDL_strcasecmp(hint, driver->info.name) == 0) {
                     /* Create a new renderer instance */
-                    renderer = driver->CreateRenderer(window, flags);
-                    if (renderer) {
+                    rc = driver->CreateRenderer(renderer, window, flags);
+                    if (rc == 0) {
                         batching = SDL_FALSE;
+                    } else {
+                        SDL_zerop(renderer);  /* make sure we don't leave function pointers from a previous CreateRenderer() in this struct. */
+                        renderer->magic = &renderer_magic;
                     }
                     break;
                 }
             }
         }
 
-        if (!renderer) {
+        if (rc == -1) {
             for (index = 0; index < n; ++index) {
                 const SDL_RenderDriver *driver = render_drivers[index];
 
                 if ((driver->info.flags & flags) == flags) {
                     /* Create a new renderer instance */
-                    renderer = driver->CreateRenderer(window, flags);
-                    if (renderer) {
+                    rc = driver->CreateRenderer(renderer, window, flags);
+                    if (rc == 0) {
                         /* Yay, we got one! */
                         break;
+                    } else {
+                        SDL_zerop(renderer);  /* make sure we don't leave function pointers from a previous CreateRenderer() in this struct. */
+                        renderer->magic = &renderer_magic;
                     }
                 }
             }
         }
-        if (!renderer) {
+        if (rc == -1) {
             SDL_SetError("Couldn't find matching render driver");
             goto error;
         }
@@ -1025,9 +1040,9 @@ SDL_Renderer *SDL_CreateRenderer(SDL_Window *window, int index, Uint32 flags)
             goto error;
         }
         /* Create a new renderer instance */
-        renderer = render_drivers[index]->CreateRenderer(window, flags);
+        rc = render_drivers[index]->CreateRenderer(renderer, window, flags);
         batching = SDL_FALSE;
-        if (!renderer) {
+        if (rc == -1) {
             goto error;
         }
     }
@@ -1108,6 +1123,7 @@ SDL_Renderer *SDL_CreateRenderer(SDL_Window *window, int index, Uint32 flags)
     return renderer;
 
 error:
+    SDL_free(renderer);
 
 #if defined(__ANDROID__)
     Android_ActivityMutex_Unlock();
@@ -1124,12 +1140,23 @@ SDL_Renderer *SDL_CreateSoftwareRenderer(SDL_Surface *surface)
 {
 #if SDL_VIDEO_RENDER_SW
     SDL_Renderer *renderer;
+    int rc;
 
-    renderer = SW_CreateRendererForSurface(surface);
+    renderer = (SDL_Renderer *)SDL_calloc(1, sizeof(*renderer));
+    if (!renderer) {
+        SDL_OutOfMemory();
+        return NULL;
+    }
 
-    if (renderer) {
+    renderer->magic = &renderer_magic;
+
+    rc = SW_CreateRendererForSurface(renderer, surface);
+
+    if (rc == -1) {
+        SDL_free(renderer);
+        renderer = NULL;
+    } else {
         VerifyDrawQueueFunctions(renderer);
-        renderer->magic = &renderer_magic;
         renderer->target_mutex = SDL_CreateMutex();
         renderer->scale.x = 1.0f;
         renderer->scale.y = 1.0f;
@@ -4366,6 +4393,7 @@ void SDL_DestroyRenderer(SDL_Renderer *renderer)
 
     /* Free the renderer instance */
     renderer->DestroyRenderer(renderer);
+    SDL_free(renderer);
 }
 
 int SDL_GL_BindTexture(SDL_Texture *texture, float *texw, float *texh)

+ 1 - 1
src/render/SDL_sysrender.h

@@ -288,7 +288,7 @@ struct SDL_Renderer
 /* Define the SDL render driver structure */
 struct SDL_RenderDriver
 {
-    SDL_Renderer *(*CreateRenderer)(SDL_Window *window, Uint32 flags);
+    int (*CreateRenderer)(SDL_Renderer *renderer, SDL_Window *window, Uint32 flags);
 
     /* Info about the renderer capabilities */
     SDL_RendererInfo info;

+ 7 - 22
src/render/direct3d/SDL_render_d3d.c

@@ -1447,7 +1447,6 @@ static void D3D_DestroyRenderer(SDL_Renderer *renderer)
         }
         SDL_free(data);
     }
-    SDL_free(renderer);
 }
 
 static int D3D_Reset(SDL_Renderer *renderer)
@@ -1547,9 +1546,8 @@ static int D3D_SetVSync(SDL_Renderer *renderer, const int vsync)
     return 0;
 }
 
-SDL_Renderer *D3D_CreateRenderer(SDL_Window *window, Uint32 flags)
+int D3D_CreateRenderer(SDL_Renderer *renderer, SDL_Window *window, Uint32 flags)
 {
-    SDL_Renderer *renderer;
     D3D_RenderData *data;
     SDL_SysWMinfo windowinfo;
     HRESULT result;
@@ -1562,24 +1560,14 @@ SDL_Renderer *D3D_CreateRenderer(SDL_Window *window, Uint32 flags)
     SDL_DisplayMode fullscreen_mode;
     int displayIndex;
 
-    renderer = (SDL_Renderer *) SDL_calloc(1, sizeof(*renderer));
-    if (!renderer) {
-        SDL_OutOfMemory();
-        return NULL;
-    }
-
     data = (D3D_RenderData *)SDL_calloc(1, sizeof(*data));
     if (!data) {
-        SDL_free(renderer);
-        SDL_OutOfMemory();
-        return NULL;
+        return SDL_OutOfMemory();
     }
 
     if (!D3D_LoadDLL(&data->d3dDLL, &data->d3d)) {
-        SDL_free(renderer);
         SDL_free(data);
-        SDL_SetError("Unable to create Direct3D interface");
-        return NULL;
+        return SDL_SetError("Unable to create Direct3D interface");
     }
 
     renderer->WindowEvent = D3D_WindowEvent;
@@ -1662,23 +1650,20 @@ SDL_Renderer *D3D_CreateRenderer(SDL_Window *window, Uint32 flags)
                                      &pparams, &data->device);
     if (FAILED(result)) {
         D3D_DestroyRenderer(renderer);
-        D3D_SetError("CreateDevice()", result);
-        return NULL;
+        return D3D_SetError("CreateDevice()", result);
     }
 
     /* Get presentation parameters to fill info */
     result = IDirect3DDevice9_GetSwapChain(data->device, 0, &chain);
     if (FAILED(result)) {
         D3D_DestroyRenderer(renderer);
-        D3D_SetError("GetSwapChain()", result);
-        return NULL;
+        return D3D_SetError("GetSwapChain()", result);
     }
     result = IDirect3DSwapChain9_GetPresentParameters(chain, &pparams);
     if (FAILED(result)) {
         IDirect3DSwapChain9_Release(chain);
         D3D_DestroyRenderer(renderer);
-        D3D_SetError("GetPresentParameters()", result);
-        return NULL;
+        return D3D_SetError("GetPresentParameters()", result);
     }
     IDirect3DSwapChain9_Release(chain);
     if (pparams.PresentationInterval == D3DPRESENT_INTERVAL_ONE) {
@@ -1720,7 +1705,7 @@ SDL_Renderer *D3D_CreateRenderer(SDL_Window *window, Uint32 flags)
     data->drawstate.cliprect_enabled_dirty = SDL_TRUE;
     data->drawstate.blend = SDL_BLENDMODE_INVALID;
 
-    return renderer;
+    return 0;
 }
 
 SDL_RenderDriver D3D_RenderDriver = {

+ 5 - 15
src/render/direct3d11/SDL_render_d3d11.c

@@ -304,7 +304,6 @@ static void D3D11_DestroyRenderer(SDL_Renderer *renderer)
     if (data) {
         SDL_free(data);
     }
-    SDL_free(renderer);
 }
 
 static D3D11_BLEND GetBlendFunc(SDL_BlendFactor factor)
@@ -2308,22 +2307,13 @@ static int D3D11_SetVSync(SDL_Renderer *renderer, const int vsync)
 }
 #endif
 
-SDL_Renderer *D3D11_CreateRenderer(SDL_Window *window, Uint32 flags)
+int D3D11_CreateRenderer(SDL_Renderer *renderer, SDL_Window *window, Uint32 flags)
 {
-    SDL_Renderer *renderer;
     D3D11_RenderData *data;
 
-    renderer = (SDL_Renderer *)SDL_calloc(1, sizeof(*renderer));
-    if (!renderer) {
-        SDL_OutOfMemory();
-        return NULL;
-    }
-
     data = (D3D11_RenderData *)SDL_calloc(1, sizeof(*data));
     if (!data) {
-        SDL_free(renderer);
-        SDL_OutOfMemory();
-        return NULL;
+        return SDL_OutOfMemory();
     }
 
     data->identity = MatrixIdentity();
@@ -2385,14 +2375,14 @@ SDL_Renderer *D3D11_CreateRenderer(SDL_Window *window, Uint32 flags)
     /* Initialize Direct3D resources */
     if (FAILED(D3D11_CreateDeviceResources(renderer))) {
         D3D11_DestroyRenderer(renderer);
-        return NULL;
+        return -1;
     }
     if (FAILED(D3D11_CreateWindowSizeDependentResources(renderer))) {
         D3D11_DestroyRenderer(renderer);
-        return NULL;
+        return -1;
     }
 
-    return renderer;
+    return 0;
 }
 
 SDL_RenderDriver D3D11_RenderDriver = {

+ 5 - 15
src/render/direct3d12/SDL_render_d3d12.c

@@ -556,7 +556,6 @@ static void D3D12_DestroyRenderer(SDL_Renderer *renderer)
     if (data) {
         SDL_free(data);
     }
-    SDL_free(renderer);
 }
 
 static int D3D12_GetOutputSize(SDL_Renderer *renderer, int *w, int *h)
@@ -3014,22 +3013,13 @@ static int D3D12_SetVSync(SDL_Renderer *renderer, const int vsync)
     return 0;
 }
 
-SDL_Renderer *D3D12_CreateRenderer(SDL_Window *window, Uint32 flags)
+int D3D12_CreateRenderer(SDL_Renderer *renderer, SDL_Window *window, Uint32 flags)
 {
-    SDL_Renderer *renderer;
     D3D12_RenderData *data;
 
-    renderer = (SDL_Renderer *)SDL_calloc(1, sizeof(*renderer));
-    if (!renderer) {
-        SDL_OutOfMemory();
-        return NULL;
-    }
-
     data = (D3D12_RenderData *)SDL_calloc(1, sizeof(*data));
     if (!data) {
-        SDL_free(renderer);
-        SDL_OutOfMemory();
-        return NULL;
+        return SDL_OutOfMemory();
     }
 
     data->identity = MatrixIdentity();
@@ -3074,14 +3064,14 @@ SDL_Renderer *D3D12_CreateRenderer(SDL_Window *window, Uint32 flags)
     /* Initialize Direct3D resources */
     if (FAILED(D3D12_CreateDeviceResources(renderer))) {
         D3D12_DestroyRenderer(renderer);
-        return NULL;
+        return -1;
     }
     if (FAILED(D3D12_CreateWindowSizeDependentResources(renderer))) {
         D3D12_DestroyRenderer(renderer);
-        return NULL;
+        return -1;
     }
 
-    return renderer;
+    return 0;
 }
 
 SDL_RenderDriver D3D12_RenderDriver = {

+ 7 - 20
src/render/metal/SDL_render_metal.m

@@ -1513,8 +1513,6 @@ static void METAL_DestroyRenderer(SDL_Renderer * renderer)
         /* SDL_Metal_DestroyView(data.mtlview); */
         CFBridgingRelease(data.mtlview);
     }
-
-    SDL_free(renderer);
 }}
 
 static void *METAL_GetMetalLayer(SDL_Renderer * renderer)
@@ -1580,9 +1578,8 @@ static SDL_MetalView GetWindowView(SDL_Window *window)
     return nil;
 }
 
-static SDL_Renderer *METAL_CreateRenderer(SDL_Window * window, Uint32 flags)
+static int METAL_CreateRenderer(SDL_Renderer *renderer, SDL_Window * window, Uint32 flags)
 { @autoreleasepool {
-    SDL_Renderer *renderer = NULL;
     METAL_RenderData *data = NULL;
     id<MTLDevice> mtldevice = nil;
     SDL_MetalView view = NULL;
@@ -1641,17 +1638,11 @@ static SDL_Renderer *METAL_CreateRenderer(SDL_Window * window, Uint32 flags)
 
     SDL_VERSION(&syswm.version);
     if (!SDL_GetWindowWMInfo(window, &syswm)) {
-        return NULL;
+        return -1;
     }
 
     if (IsMetalAvailable(&syswm) == -1) {
-        return NULL;
-    }
-
-    renderer = (SDL_Renderer *) SDL_calloc(1, sizeof(*renderer));
-    if (!renderer) {
-        SDL_OutOfMemory();
-        return NULL;
+        return -1;
     }
 
 #ifdef __MACOSX__
@@ -1672,9 +1663,7 @@ static SDL_Renderer *METAL_CreateRenderer(SDL_Window * window, Uint32 flags)
     }
 
     if (mtldevice == nil) {
-        SDL_free(renderer);
-        SDL_SetError("Failed to obtain Metal device");
-        return NULL;
+        return SDL_SetError("Failed to obtain Metal device");
     }
 
     view = GetWindowView(window);
@@ -1683,8 +1672,7 @@ static SDL_Renderer *METAL_CreateRenderer(SDL_Window * window, Uint32 flags)
     }
 
     if (view == NULL) {
-        SDL_free(renderer);
-        return NULL;
+        return -1;
     }
 
     // !!! FIXME: error checking on all of this.
@@ -1696,8 +1684,7 @@ static SDL_Renderer *METAL_CreateRenderer(SDL_Window * window, Uint32 flags)
          */
         /* SDL_Metal_DestroyView(view); */
         CFBridgingRelease(view);
-        SDL_free(renderer);
-        return NULL;
+        return -1;
     }
 
     renderer->driverdata = (void*)CFBridgingRetain(data);
@@ -1875,7 +1862,7 @@ static SDL_Renderer *METAL_CreateRenderer(SDL_Window * window, Uint32 flags)
     renderer->info.max_texture_width = maxtexsize;
     renderer->info.max_texture_height = maxtexsize;
 
-    return renderer;
+    return 0;
 }}
 
 SDL_RenderDriver METAL_RenderDriver = {

+ 3 - 15
src/render/opengl/SDL_render_gl.c

@@ -1555,7 +1555,6 @@ static void GL_DestroyRenderer(SDL_Renderer *renderer)
         }
         SDL_free(data);
     }
-    SDL_free(renderer);
 }
 
 static int GL_BindTexture(SDL_Renderer *renderer, SDL_Texture *texture, float *texw, float *texh)
@@ -1700,9 +1699,8 @@ static SDL_bool GL_IsProbablyAccelerated(const GL_RenderData *data)
     return SDL_TRUE;
 }
 
-static SDL_Renderer *GL_CreateRenderer(SDL_Window *window, Uint32 flags)
+static int GL_CreateRenderer(SDL_Renderer *renderer, SDL_Window *window, Uint32 flags)
 {
-    SDL_Renderer *renderer;
     GL_RenderData *data;
     GLint value;
     Uint32 window_flags;
@@ -1731,15 +1729,8 @@ static SDL_Renderer *GL_CreateRenderer(SDL_Window *window, Uint32 flags)
     }
 #endif
 
-    renderer = (SDL_Renderer *)SDL_calloc(1, sizeof(*renderer));
-    if (!renderer) {
-        SDL_OutOfMemory();
-        goto error;
-    }
-
     data = (GL_RenderData *)SDL_calloc(1, sizeof(*data));
     if (!data) {
-        SDL_free(renderer);
         SDL_OutOfMemory();
         goto error;
     }
@@ -1777,20 +1768,17 @@ static SDL_Renderer *GL_CreateRenderer(SDL_Window *window, Uint32 flags)
 
     data->context = SDL_GL_CreateContext(window);
     if (!data->context) {
-        SDL_free(renderer);
         SDL_free(data);
         goto error;
     }
     if (SDL_GL_MakeCurrent(window, data->context) < 0) {
         SDL_GL_DeleteContext(data->context);
-        SDL_free(renderer);
         SDL_free(data);
         goto error;
     }
 
     if (GL_LoadFunctions(data) < 0) {
         SDL_GL_DeleteContext(data->context);
-        SDL_free(renderer);
         SDL_free(data);
         goto error;
     }
@@ -1944,7 +1932,7 @@ static SDL_Renderer *GL_CreateRenderer(SDL_Window *window, Uint32 flags)
     data->drawstate.color = 0xFFFFFFFF;
     data->drawstate.clear_color = 0xFFFFFFFF;
 
-    return renderer;
+    return 0;
 
 error:
     if (changed_window) {
@@ -1954,7 +1942,7 @@ error:
         SDL_GL_SetAttribute(SDL_GL_CONTEXT_MINOR_VERSION, minor);
         SDL_RecreateWindow(window, window_flags);
     }
-    return NULL;
+    return -1;
 }
 
 SDL_RenderDriver GL_RenderDriver = {

+ 4 - 12
src/render/opengles/SDL_render_gles.c

@@ -997,7 +997,6 @@ static void GLES_DestroyRenderer(SDL_Renderer *renderer)
         }
         SDL_free(data);
     }
-    SDL_free(renderer);
 }
 
 static int GLES_BindTexture(SDL_Renderer *renderer, SDL_Texture *texture, float *texw, float *texh)
@@ -1054,10 +1053,9 @@ static int GLES_SetVSync(SDL_Renderer *renderer, const int vsync)
     return retval;
 }
 
-static SDL_Renderer *GLES_CreateRenderer(SDL_Window *window, Uint32 flags)
+static int GLES_CreateRenderer(SDL_Renderer *renderer, SDL_Window *window, Uint32 flags)
 {
-    SDL_Renderer *renderer;
-    GLES_RenderData *data;
+    GLES_RenderData *data = NULL;
     GLint value;
     Uint32 window_flags;
     int profile_mask = 0, major = 0, minor = 0;
@@ -1081,12 +1079,6 @@ static SDL_Renderer *GLES_CreateRenderer(SDL_Window *window, Uint32 flags)
         }
     }
 
-    renderer = (SDL_Renderer *)SDL_calloc(1, sizeof(*renderer));
-    if (!renderer) {
-        SDL_OutOfMemory();
-        goto error;
-    }
-
     data = (GLES_RenderData *)SDL_calloc(1, sizeof(*data));
     if (!data) {
         GLES_DestroyRenderer(renderer);
@@ -1192,7 +1184,7 @@ static SDL_Renderer *GLES_CreateRenderer(SDL_Window *window, Uint32 flags)
     data->drawstate.color = 0xFFFFFFFF;
     data->drawstate.clear_color = 0xFFFFFFFF;
 
-    return renderer;
+    return 0;
 
 error:
     if (changed_window) {
@@ -1202,7 +1194,7 @@ error:
         SDL_GL_SetAttribute(SDL_GL_CONTEXT_MINOR_VERSION, minor);
         SDL_RecreateWindow(window, window_flags);
     }
-    return NULL;
+    return -1;
 }
 
 SDL_RenderDriver GLES_RenderDriver = {

+ 5 - 22
src/render/opengles2/SDL_render_gles2.c

@@ -1406,7 +1406,6 @@ static void GLES2_DestroyRenderer(SDL_Renderer *renderer)
 
         SDL_free(data);
     }
-    SDL_free(renderer);
 }
 
 static int GLES2_CreateTexture(SDL_Renderer *renderer, SDL_Texture *texture)
@@ -2030,10 +2029,9 @@ static int GLES2_UnbindTexture(SDL_Renderer *renderer, SDL_Texture *texture)
  * Renderer instantiation                                                                        *
  *************************************************************************************************/
 
-static SDL_Renderer *GLES2_CreateRenderer(SDL_Window *window, Uint32 flags)
+static int GLES2_CreateRenderer(SDL_Renderer *renderer, SDL_Window *window, Uint32 flags)
 {
-    SDL_Renderer *renderer;
-    GLES2_RenderData *data;
+    GLES2_RenderData *data = NULL;
     Uint32 window_flags = 0; /* -Wconditional-uninitialized */
     GLint window_framebuffer;
     GLint value;
@@ -2066,16 +2064,8 @@ static SDL_Renderer *GLES2_CreateRenderer(SDL_Window *window, Uint32 flags)
         }
     }
 
-    /* Create the renderer struct */
-    renderer = (SDL_Renderer *)SDL_calloc(1, sizeof(SDL_Renderer));
-    if (!renderer) {
-        SDL_OutOfMemory();
-        goto error;
-    }
-
     data = (GLES2_RenderData *)SDL_calloc(1, sizeof(GLES2_RenderData));
     if (!data) {
-        SDL_free(renderer);
         SDL_OutOfMemory();
         goto error;
     }
@@ -2087,28 +2077,20 @@ static SDL_Renderer *GLES2_CreateRenderer(SDL_Window *window, Uint32 flags)
     /* Create an OpenGL ES 2.0 context */
     data->context = SDL_GL_CreateContext(window);
     if (!data->context) {
-        SDL_free(renderer);
-        SDL_free(data);
         goto error;
     }
     if (SDL_GL_MakeCurrent(window, data->context) < 0) {
         SDL_GL_DeleteContext(data->context);
-        SDL_free(renderer);
-        SDL_free(data);
         goto error;
     }
 
     if (GLES2_LoadFunctions(data) < 0) {
         SDL_GL_DeleteContext(data->context);
-        SDL_free(renderer);
-        SDL_free(data);
         goto error;
     }
 
     if (GLES2_CacheShaders(data) < 0) {
         SDL_GL_DeleteContext(data->context);
-        SDL_free(renderer);
-        SDL_free(data);
         goto error;
     }
 
@@ -2219,9 +2201,10 @@ static SDL_Renderer *GLES2_CreateRenderer(SDL_Window *window, Uint32 flags)
 
     GL_CheckError("", renderer);
 
-    return renderer;
+    return 0;
 
 error:
+    SDL_free(data);
     if (changed_window) {
         /* Uh oh, better try to put it back... */
         SDL_GL_SetAttribute(SDL_GL_CONTEXT_PROFILE_MASK, profile_mask);
@@ -2229,7 +2212,7 @@ error:
         SDL_GL_SetAttribute(SDL_GL_CONTEXT_MINOR_VERSION, minor);
         SDL_RecreateWindow(window, window_flags);
     }
-    return NULL;
+    return -1;
 }
 
 SDL_RenderDriver GLES2_RenderDriver = {

+ 3 - 13
src/render/ps2/SDL_render_ps2.c

@@ -593,8 +593,6 @@ static void PS2_DestroyRenderer(SDL_Renderer *renderer)
     if (vsync_sema_id >= 0) {
         DeleteSema(vsync_sema_id);
     }
-
-    SDL_free(renderer);
 }
 
 static int PS2_SetVSync(SDL_Renderer *renderer, const int vsync)
@@ -605,25 +603,17 @@ static int PS2_SetVSync(SDL_Renderer *renderer, const int vsync)
     return 0;
 }
 
-static SDL_Renderer *PS2_CreateRenderer(SDL_Window *window, Uint32 flags)
+static int PS2_CreateRenderer(SDL_Renderer *renderer, SDL_Window *window, Uint32 flags)
 {
-    SDL_Renderer *renderer;
     PS2_RenderData *data;
     GSGLOBAL *gsGlobal;
     ee_sema_t sema;
     SDL_bool dynamicVsync;
 
-    renderer = (SDL_Renderer *)SDL_calloc(1, sizeof(*renderer));
-    if (!renderer) {
-        SDL_OutOfMemory();
-        return NULL;
-    }
-
     data = (PS2_RenderData *)SDL_calloc(1, sizeof(*data));
     if (!data) {
         PS2_DestroyRenderer(renderer);
-        SDL_OutOfMemory();
-        return NULL;
+        return SDL_OutOfMemory();
     }
 
     /* Specific gsKit init */
@@ -689,7 +679,7 @@ static SDL_Renderer *PS2_CreateRenderer(SDL_Window *window, Uint32 flags)
     renderer->driverdata = data;
     renderer->window = window;
 
-    return renderer;
+    return 0;
 }
 
 SDL_RenderDriver PS2_RenderDriver = {

+ 3 - 13
src/render/psp/SDL_render_psp.c

@@ -1299,7 +1299,6 @@ static void PSP_DestroyRenderer(SDL_Renderer *renderer)
         data->displayListAvail = SDL_FALSE;
         SDL_free(data);
     }
-    SDL_free(renderer);
 }
 
 static int PSP_SetVSync(SDL_Renderer *renderer, const int vsync)
@@ -1309,25 +1308,16 @@ static int PSP_SetVSync(SDL_Renderer *renderer, const int vsync)
     return 0;
 }
 
-SDL_Renderer *PSP_CreateRenderer(SDL_Window *window, Uint32 flags)
+int PSP_CreateRenderer(SDL_Renderer *renderer, SDL_Window *window, Uint32 flags)
 {
-
-    SDL_Renderer *renderer;
     PSP_RenderData *data;
     int pixelformat;
     void *doublebuffer = NULL;
 
-    renderer = (SDL_Renderer *)SDL_calloc(1, sizeof(*renderer));
-    if (!renderer) {
-        SDL_OutOfMemory();
-        return NULL;
-    }
-
     data = (PSP_RenderData *)SDL_calloc(1, sizeof(*data));
     if (!data) {
         PSP_DestroyRenderer(renderer);
-        SDL_OutOfMemory();
-        return NULL;
+        return SDL_OutOfMemory();
     }
 
     renderer->WindowEvent = PSP_WindowEvent;
@@ -1419,7 +1409,7 @@ SDL_Renderer *PSP_CreateRenderer(SDL_Window *window, Uint32 flags)
     sceKernelRegisterSubIntrHandler(PSP_VBLANK_INT, 0, psp_on_vblank, data);
     sceKernelEnableSubIntr(PSP_VBLANK_INT, 0);
 
-    return renderer;
+    return 0;
 }
 
 SDL_RenderDriver PSP_RenderDriver = {

+ 7 - 17
src/render/software/SDL_render_sw.c

@@ -987,30 +987,20 @@ static void SW_DestroyRenderer(SDL_Renderer *renderer)
         SDL_DestroyWindowSurface(window);
     }
     SDL_free(data);
-    SDL_free(renderer);
 }
 
-SDL_Renderer *SW_CreateRendererForSurface(SDL_Surface *surface)
+int SW_CreateRendererForSurface(SDL_Renderer *renderer, SDL_Surface *surface)
 {
-    SDL_Renderer *renderer;
     SW_RenderData *data;
 
     if (!surface) {
-        SDL_InvalidParamError("surface");
-        return NULL;
-    }
-
-    renderer = (SDL_Renderer *)SDL_calloc(1, sizeof(*renderer));
-    if (!renderer) {
-        SDL_OutOfMemory();
-        return NULL;
+        return SDL_InvalidParamError("surface");
     }
 
     data = (SW_RenderData *)SDL_calloc(1, sizeof(*data));
     if (!data) {
         SW_DestroyRenderer(renderer);
-        SDL_OutOfMemory();
-        return NULL;
+        return SDL_OutOfMemory();
     }
     data->surface = surface;
     data->window = surface;
@@ -1039,10 +1029,10 @@ SDL_Renderer *SW_CreateRendererForSurface(SDL_Surface *surface)
     renderer->info = SW_RenderDriver.info;
     renderer->driverdata = data;
 
-    return renderer;
+    return 0;
 }
 
-static SDL_Renderer *SW_CreateRenderer(SDL_Window *window, Uint32 flags)
+static int SW_CreateRenderer(SDL_Renderer *renderer, SDL_Window *window, Uint32 flags)
 {
     const char *hint;
     SDL_Surface *surface;
@@ -1068,9 +1058,9 @@ static SDL_Renderer *SW_CreateRenderer(SDL_Window *window, Uint32 flags)
     }
 
     if (!surface) {
-        return NULL;
+        return -1;
     }
-    return SW_CreateRendererForSurface(surface);
+    return SW_CreateRendererForSurface(renderer, surface);
 }
 
 SDL_RenderDriver SW_RenderDriver = {

+ 1 - 1
src/render/software/SDL_render_sw_c.h

@@ -22,7 +22,7 @@
 #ifndef SDL_render_sw_c_h_
 #define SDL_render_sw_c_h_
 
-extern SDL_Renderer *SW_CreateRendererForSurface(SDL_Surface *surface);
+extern int SW_CreateRendererForSurface(SDL_Renderer *renderer, SDL_Surface *surface);
 
 #endif /* SDL_render_sw_c_h_ */
 

+ 3 - 13
src/render/vitagxm/SDL_render_vita_gxm.c

@@ -211,22 +211,13 @@ static int VITA_GXM_SetVSync(SDL_Renderer *renderer, const int vsync)
     return 0;
 }
 
-SDL_Renderer *VITA_GXM_CreateRenderer(SDL_Window *window, Uint32 flags)
+int VITA_GXM_CreateRenderer(SDL_Renderer *renderer, SDL_Window *window, Uint32 flags)
 {
-    SDL_Renderer *renderer;
     VITA_GXM_RenderData *data;
 
-    renderer = (SDL_Renderer *)SDL_calloc(1, sizeof(*renderer));
-    if (!renderer) {
-        SDL_OutOfMemory();
-        return NULL;
-    }
-
     data = (VITA_GXM_RenderData *)SDL_calloc(1, sizeof(VITA_GXM_RenderData));
     if (!data) {
-        SDL_free(renderer);
-        SDL_OutOfMemory();
-        return NULL;
+        return SDL_OutOfMemory();
     }
 
     renderer->WindowEvent = VITA_GXM_WindowEvent;
@@ -277,7 +268,7 @@ SDL_Renderer *VITA_GXM_CreateRenderer(SDL_Window *window, Uint32 flags)
         return NULL;
     }
 
-    return renderer;
+    return 0;
 }
 
 static void VITA_GXM_WindowEvent(SDL_Renderer *renderer, const SDL_WindowEvent *event)
@@ -1222,7 +1213,6 @@ static void VITA_GXM_DestroyRenderer(SDL_Renderer *renderer)
         data->drawing = SDL_FALSE;
         SDL_free(data);
     }
-    SDL_free(renderer);
 }
 
 #endif /* SDL_VIDEO_RENDER_VITA_GXM */