Просмотр исходного кода

gpu: make NULL object releases no-ops

These functions already return immediately for NULL objects in normal builds, but it was done through CHECK_PARAM. When building with SDL_DISABLE_INVALID_PARAMS, these checks were compiled out, and NULL resources could reach backend release functions and cause segfault.

Always return on NULL so API behaves consistently regardless of SDL_DISABLE_INVALID_PARAMS.
Andrei Sabalenka 18 часов назад
Родитель
Сommit
7ee8160922
2 измененных файлов с 48 добавлено и 24 удалено
  1. 24 0
      include/SDL3/SDL_gpu.h
  2. 24 24
      src/gpu/SDL_gpu.c

+ 24 - 0
include/SDL3/SDL_gpu.h

@@ -3060,6 +3060,9 @@ extern SDL_DECLSPEC void SDLCALL SDL_PopGPUDebugGroup(
  *
  *
  * You must not reference the texture after calling this function.
  * You must not reference the texture after calling this function.
  *
  *
+ * It is safe to pass NULL for `texture`, in that case this function
+ * is a no-op.
+ *
  * \param device a GPU context.
  * \param device a GPU context.
  * \param texture a texture to be destroyed.
  * \param texture a texture to be destroyed.
  *
  *
@@ -3074,6 +3077,9 @@ extern SDL_DECLSPEC void SDLCALL SDL_ReleaseGPUTexture(
  *
  *
  * You must not reference the sampler after calling this function.
  * You must not reference the sampler after calling this function.
  *
  *
+ * It is safe to pass NULL for `sampler`, in that case this function
+ * is a no-op.
+ *
  * \param device a GPU context.
  * \param device a GPU context.
  * \param sampler a sampler to be destroyed.
  * \param sampler a sampler to be destroyed.
  *
  *
@@ -3088,6 +3094,9 @@ extern SDL_DECLSPEC void SDLCALL SDL_ReleaseGPUSampler(
  *
  *
  * You must not reference the buffer after calling this function.
  * You must not reference the buffer after calling this function.
  *
  *
+ * It is safe to pass NULL for `buffer`, in that case this function
+ * is a no-op.
+ *
  * \param device a GPU context.
  * \param device a GPU context.
  * \param buffer a buffer to be destroyed.
  * \param buffer a buffer to be destroyed.
  *
  *
@@ -3102,6 +3111,9 @@ extern SDL_DECLSPEC void SDLCALL SDL_ReleaseGPUBuffer(
  *
  *
  * You must not reference the transfer buffer after calling this function.
  * You must not reference the transfer buffer after calling this function.
  *
  *
+ * It is safe to pass NULL for `transfer_buffer`, in that case this
+ * function is a no-op.
+ *
  * \param device a GPU context.
  * \param device a GPU context.
  * \param transfer_buffer a transfer buffer to be destroyed.
  * \param transfer_buffer a transfer buffer to be destroyed.
  *
  *
@@ -3116,6 +3128,9 @@ extern SDL_DECLSPEC void SDLCALL SDL_ReleaseGPUTransferBuffer(
  *
  *
  * You must not reference the compute pipeline after calling this function.
  * You must not reference the compute pipeline after calling this function.
  *
  *
+ * It is safe to pass NULL for `compute_pipeline`, in that case this
+ * function is a no-op.
+ *
  * \param device a GPU context.
  * \param device a GPU context.
  * \param compute_pipeline a compute pipeline to be destroyed.
  * \param compute_pipeline a compute pipeline to be destroyed.
  *
  *
@@ -3130,6 +3145,9 @@ extern SDL_DECLSPEC void SDLCALL SDL_ReleaseGPUComputePipeline(
  *
  *
  * You must not reference the shader after calling this function.
  * You must not reference the shader after calling this function.
  *
  *
+ * It is safe to pass NULL for `shader`, in that case this function
+ * is a no-op.
+ *
  * \param device a GPU context.
  * \param device a GPU context.
  * \param shader a shader to be destroyed.
  * \param shader a shader to be destroyed.
  *
  *
@@ -3144,6 +3162,9 @@ extern SDL_DECLSPEC void SDLCALL SDL_ReleaseGPUShader(
  *
  *
  * You must not reference the graphics pipeline after calling this function.
  * You must not reference the graphics pipeline after calling this function.
  *
  *
+ * It is safe to pass NULL for `graphics_pipeline`, in that case this
+ * function is a no-op.
+ *
  * \param device a GPU context.
  * \param device a GPU context.
  * \param graphics_pipeline a graphics pipeline to be destroyed.
  * \param graphics_pipeline a graphics pipeline to be destroyed.
  *
  *
@@ -4487,6 +4508,9 @@ extern SDL_DECLSPEC bool SDLCALL SDL_QueryGPUFence(
  *
  *
  * You must not reference the fence after calling this function.
  * You must not reference the fence after calling this function.
  *
  *
+ * It is safe to pass NULL for `fence`, in that case this function
+ * is a no-op.
+ *
  * \param device a GPU context.
  * \param device a GPU context.
  * \param fence a fence.
  * \param fence a fence.
  *
  *

+ 24 - 24
src/gpu/SDL_gpu.c

@@ -1549,12 +1549,12 @@ void SDL_ReleaseGPUTexture(
     SDL_GPUDevice *device,
     SDL_GPUDevice *device,
     SDL_GPUTexture *texture)
     SDL_GPUTexture *texture)
 {
 {
-    CHECK_DEVICE_MAGIC(device, );
-
-    CHECK_PARAM(texture == NULL) {
+    if(texture == NULL) {
         return;
         return;
     }
     }
 
 
+    CHECK_DEVICE_MAGIC(device, );
+
     device->ReleaseTexture(
     device->ReleaseTexture(
         device->driverData,
         device->driverData,
         texture);
         texture);
@@ -1564,12 +1564,12 @@ void SDL_ReleaseGPUSampler(
     SDL_GPUDevice *device,
     SDL_GPUDevice *device,
     SDL_GPUSampler *sampler)
     SDL_GPUSampler *sampler)
 {
 {
-    CHECK_DEVICE_MAGIC(device, );
-
-    CHECK_PARAM(sampler == NULL) {
+    if(sampler == NULL) {
         return;
         return;
     }
     }
 
 
+    CHECK_DEVICE_MAGIC(device, );
+
     device->ReleaseSampler(
     device->ReleaseSampler(
         device->driverData,
         device->driverData,
         sampler);
         sampler);
@@ -1579,12 +1579,12 @@ void SDL_ReleaseGPUBuffer(
     SDL_GPUDevice *device,
     SDL_GPUDevice *device,
     SDL_GPUBuffer *buffer)
     SDL_GPUBuffer *buffer)
 {
 {
-    CHECK_DEVICE_MAGIC(device, );
-
-    CHECK_PARAM(buffer == NULL) {
+    if(buffer == NULL) {
         return;
         return;
     }
     }
 
 
+    CHECK_DEVICE_MAGIC(device, );
+
     device->ReleaseBuffer(
     device->ReleaseBuffer(
         device->driverData,
         device->driverData,
         buffer);
         buffer);
@@ -1594,12 +1594,12 @@ void SDL_ReleaseGPUTransferBuffer(
     SDL_GPUDevice *device,
     SDL_GPUDevice *device,
     SDL_GPUTransferBuffer *transfer_buffer)
     SDL_GPUTransferBuffer *transfer_buffer)
 {
 {
-    CHECK_DEVICE_MAGIC(device, );
-
-    CHECK_PARAM(transfer_buffer == NULL) {
+    if(transfer_buffer == NULL) {
         return;
         return;
     }
     }
 
 
+    CHECK_DEVICE_MAGIC(device, );
+
     device->ReleaseTransferBuffer(
     device->ReleaseTransferBuffer(
         device->driverData,
         device->driverData,
         transfer_buffer);
         transfer_buffer);
@@ -1609,12 +1609,12 @@ void SDL_ReleaseGPUShader(
     SDL_GPUDevice *device,
     SDL_GPUDevice *device,
     SDL_GPUShader *shader)
     SDL_GPUShader *shader)
 {
 {
-    CHECK_DEVICE_MAGIC(device, );
-
-    CHECK_PARAM(shader == NULL) {
+    if(shader == NULL) {
         return;
         return;
     }
     }
 
 
+    CHECK_DEVICE_MAGIC(device, );
+
     device->ReleaseShader(
     device->ReleaseShader(
         device->driverData,
         device->driverData,
         shader);
         shader);
@@ -1624,12 +1624,12 @@ void SDL_ReleaseGPUComputePipeline(
     SDL_GPUDevice *device,
     SDL_GPUDevice *device,
     SDL_GPUComputePipeline *compute_pipeline)
     SDL_GPUComputePipeline *compute_pipeline)
 {
 {
-    CHECK_DEVICE_MAGIC(device, );
-
-    CHECK_PARAM(compute_pipeline == NULL) {
+    if(compute_pipeline == NULL) {
         return;
         return;
     }
     }
 
 
+    CHECK_DEVICE_MAGIC(device, );
+
     device->ReleaseComputePipeline(
     device->ReleaseComputePipeline(
         device->driverData,
         device->driverData,
         compute_pipeline);
         compute_pipeline);
@@ -1639,12 +1639,12 @@ void SDL_ReleaseGPUGraphicsPipeline(
     SDL_GPUDevice *device,
     SDL_GPUDevice *device,
     SDL_GPUGraphicsPipeline *graphics_pipeline)
     SDL_GPUGraphicsPipeline *graphics_pipeline)
 {
 {
-    CHECK_DEVICE_MAGIC(device, );
-
-    CHECK_PARAM(graphics_pipeline == NULL) {
+    if(graphics_pipeline == NULL) {
         return;
         return;
     }
     }
 
 
+    CHECK_DEVICE_MAGIC(device, );
+
     device->ReleaseGraphicsPipeline(
     device->ReleaseGraphicsPipeline(
         device->driverData,
         device->driverData,
         graphics_pipeline);
         graphics_pipeline);
@@ -3504,12 +3504,12 @@ void SDL_ReleaseGPUFence(
     SDL_GPUDevice *device,
     SDL_GPUDevice *device,
     SDL_GPUFence *fence)
     SDL_GPUFence *fence)
 {
 {
-    CHECK_DEVICE_MAGIC(device, );
-
-    CHECK_PARAM(fence == NULL) {
+    if(fence == NULL) {
         return;
         return;
     }
     }
 
 
+    CHECK_DEVICE_MAGIC(device, );
+
     device->ReleaseFence(
     device->ReleaseFence(
         device->driverData,
         device->driverData,
         fence);
         fence);