Browse Source

Make sure we always copy the data returned using SDL_GetStringRule

This prevents race conditions where calling an API from one thread returns the data and it's freed by updates on another thread
Sam Lantinga 9 months ago
parent
commit
bb96320cc4

+ 2 - 0
src/SDL_internal.h

@@ -296,6 +296,8 @@ extern int SDLCALL SDL_WaitSemaphoreTimeoutNS(SDL_Semaphore *sem, Sint64 timeout
 extern int SDLCALL SDL_WaitConditionTimeoutNS(SDL_Condition *cond, SDL_Mutex *mutex, Sint64 timeoutNS);
 extern SDL_bool SDLCALL SDL_WaitEventTimeoutNS(SDL_Event *event, Sint64 timeoutNS);
 
+extern const char *SDL_CreateTemporaryString(const char *string);
+
 /* Queue `memory` to be passed to SDL_free once the event queue is emptied.
    this manages the list of pointers to SDL_AllocateEventMemory, but you
    can use it to queue pointers from other subsystems that can die at any

+ 1 - 1
src/SDL_properties.c

@@ -65,7 +65,7 @@ static void SDL_FreePropertyWithCleanup(const void *key, const void *value, void
             }
             break;
         case SDL_PROPERTY_TYPE_STRING:
-            SDL_FreeLater(property->value.string_value);  // this pointer might be given to the app by SDL_GetStringProperty.
+            SDL_FreeLater(property->value.string_value);  // SDL_GetStringProperty() returns this pointer
             break;
         default:
             break;

+ 5 - 5
src/audio/SDL_audio.c

@@ -170,7 +170,7 @@ static int GetDefaultSampleFramesFromFreq(const int freq)
 int *SDL_ChannelMapDup(const int *origchmap, int channels)
 {
     const size_t chmaplen = sizeof (*origchmap) * channels;
-    int *chmap = (int *) SDL_malloc(chmaplen);
+    int *chmap = (int *)SDL_malloc(chmaplen);
     if (chmap) {
         SDL_memcpy(chmap, origchmap, chmaplen);
     }
@@ -544,8 +544,8 @@ static void DestroyPhysicalAudioDevice(SDL_AudioDevice *device)
     SDL_DestroyMutex(device->lock);
     SDL_DestroyCondition(device->close_cond);
     SDL_free(device->work_buffer);
-    SDL_FreeLater(device->chmap);  // this pointer is handed to the app during SDL_GetAudioDeviceChannelMap
-    SDL_FreeLater(device->name);  // this pointer is handed to the app during SDL_GetAudioDeviceName
+    SDL_free(device->chmap);
+    SDL_free(device->name);
     SDL_free(device);
 }
 
@@ -1432,7 +1432,7 @@ const char *SDL_GetAudioDeviceName(SDL_AudioDeviceID devid)
     const char *retval = NULL;
     SDL_AudioDevice *device = ObtainPhysicalAudioDevice(devid);
     if (device) {
-        retval = device->name;
+        retval = SDL_CreateTemporaryString(device->name);
     }
     ReleaseAudioDevice(device);
 
@@ -1465,8 +1465,8 @@ const int *SDL_GetAudioDeviceChannelMap(SDL_AudioDeviceID devid, int *count)
     int channels = 0;
     SDL_AudioDevice *device = ObtainPhysicalAudioDeviceDefaultAllowed(devid);
     if (device) {
-        retval = device->chmap;
         channels = device->spec.channels;
+        retval = SDL_FreeLater(SDL_ChannelMapDup(device->chmap, channels));
     }
     ReleaseAudioDevice(device);
 

+ 6 - 6
src/audio/SDL_audiocvt.c

@@ -565,7 +565,7 @@ int SDL_SetAudioStreamFormat(SDL_AudioStream *stream, const SDL_AudioSpec *src_s
 
     if (src_spec) {
         if (src_spec->channels != stream->src_spec.channels) {
-            SDL_FreeLater(stream->src_chmap);  // this pointer is handed to the app during SDL_GetAudioStreamInputChannelMap
+            SDL_free(stream->src_chmap);
             stream->src_chmap = NULL;
         }
         SDL_copyp(&stream->src_spec, src_spec);
@@ -573,7 +573,7 @@ int SDL_SetAudioStreamFormat(SDL_AudioStream *stream, const SDL_AudioSpec *src_s
 
     if (dst_spec) {
         if (dst_spec->channels != stream->dst_spec.channels) {
-            SDL_FreeLater(stream->dst_chmap);  // this pointer is handed to the app during SDL_GetAudioStreamInputChannelMap
+            SDL_free(stream->dst_chmap);
             stream->dst_chmap = NULL;
         }
         SDL_copyp(&stream->dst_spec, dst_spec);
@@ -613,11 +613,11 @@ static int SetAudioStreamChannelMap(SDL_AudioStream *stream, const SDL_AudioSpec
             if (!dupmap) {
                 retval = SDL_SetError("Invalid channel mapping");
             } else {
-                SDL_FreeLater(*stream_chmap);  // this pointer is handed to the app during SDL_GetAudioStreamInputChannelMap
+                SDL_free(*stream_chmap);
                 *stream_chmap = dupmap;
             }
         } else {
-            SDL_FreeLater(*stream_chmap);  // this pointer is handed to the app during SDL_GetAudioStreamInputChannelMap
+            SDL_free(*stream_chmap);
             *stream_chmap = NULL;
         }
     }
@@ -642,8 +642,8 @@ const int *SDL_GetAudioStreamInputChannelMap(SDL_AudioStream *stream, int *count
     int channels = 0;
     if (stream) {
         SDL_LockMutex(stream->lock);
-        retval = stream->src_chmap;
         channels = stream->src_spec.channels;
+        retval = SDL_FreeLater(SDL_ChannelMapDup(stream->src_chmap, channels));
         SDL_UnlockMutex(stream->lock);
     }
 
@@ -660,8 +660,8 @@ const int *SDL_GetAudioStreamOutputChannelMap(SDL_AudioStream *stream, int *coun
     int channels = 0;
     if (stream) {
         SDL_LockMutex(stream->lock);
-        retval = stream->dst_chmap;
         channels = stream->dst_spec.channels;
+        retval = SDL_FreeLater(SDL_ChannelMapDup(stream->dst_chmap, channels));
         SDL_UnlockMutex(stream->lock);
     }
 

+ 3 - 3
src/camera/SDL_camera.c

@@ -286,7 +286,7 @@ static void DestroyPhysicalCamera(SDL_Camera *device)
         camera_driver.impl.FreeDeviceHandle(device);
         SDL_DestroyMutex(device->lock);
         SDL_free(device->all_specs);
-        SDL_FreeLater(device->name);  // this is returned in SDL_GetCameraName.
+        SDL_free(device->name);
         SDL_free(device);
     }
 }
@@ -674,10 +674,10 @@ int SDL_GetCameraFormat(SDL_Camera *camera, SDL_CameraSpec *spec)
 
 const char *SDL_GetCameraName(SDL_CameraID instance_id)
 {
-    char *retval = NULL;
+    const char *retval = NULL;
     SDL_Camera *device = ObtainPhysicalCamera(instance_id);
     if (device) {
-        retval = device->name;
+        retval = SDL_CreateTemporaryString(device->name);
         ReleaseCamera(device);
     }
     return retval;

+ 2 - 2
src/events/SDL_dropevents.c

@@ -59,13 +59,13 @@ static int SDL_SendDrop(SDL_Window *window, const SDL_EventType evtype, const ch
         event.type = evtype;
         event.common.timestamp = 0;
         if (source) {
-            event.drop.source = SDL_AllocateEventString(source);
+            event.drop.source = SDL_CreateTemporaryString(source);
             if (!event.drop.source) {
                 return 0;
             }
         }
         if (data) {
-            event.drop.data = SDL_AllocateEventString(data);
+            event.drop.data = SDL_CreateTemporaryString(data);
             if (!event.drop.data) {
                 return 0;
             }

+ 1 - 1
src/events/SDL_events.c

@@ -290,7 +290,7 @@ void *SDL_AllocateEventMemory(size_t size)
     return SDL_FreeLater(SDL_malloc(size));
 }
 
-const char *SDL_AllocateEventString(const char *string)
+const char *SDL_CreateTemporaryString(const char *string)
 {
     if (string) {
         return SDL_FreeLater(SDL_strdup(string));

+ 0 - 2
src/events/SDL_events_c.h

@@ -40,8 +40,6 @@ extern int SDL_StartEventLoop(void);
 extern void SDL_StopEventLoop(void);
 extern void SDL_QuitInterrupt(void);
 
-extern const char *SDL_AllocateEventString(const char *string);
-
 extern int SDL_SendAppEvent(SDL_EventType eventType);
 extern int SDL_SendKeymapChangedEvent(void);
 extern int SDL_SendLocaleChangedEvent(void);

+ 5 - 5
src/events/SDL_keyboard.c

@@ -156,7 +156,7 @@ void SDL_RemoveKeyboard(SDL_KeyboardID keyboardID, SDL_bool send_event)
         return;
     }
 
-    SDL_FreeLater(SDL_keyboards[keyboard_index].name);
+    SDL_free(SDL_keyboards[keyboard_index].name);
 
     if (keyboard_index != SDL_keyboard_count - 1) {
         SDL_memcpy(&SDL_keyboards[keyboard_index], &SDL_keyboards[keyboard_index + 1], (SDL_keyboard_count - keyboard_index - 1) * sizeof(SDL_keyboards[keyboard_index]));
@@ -207,7 +207,7 @@ const char *SDL_GetKeyboardNameForID(SDL_KeyboardID instance_id)
     if (keyboard_index < 0) {
         return NULL;
     }
-    return SDL_keyboards[keyboard_index].name;
+    return SDL_CreateTemporaryString(SDL_keyboards[keyboard_index].name);
 }
 
 void SDL_ResetKeyboard(void)
@@ -719,7 +719,7 @@ int SDL_SendKeyboardText(const char *text)
         event.type = SDL_EVENT_TEXT_INPUT;
         event.common.timestamp = 0;
         event.text.windowID = keyboard->focus ? keyboard->focus->id : 0;
-        event.text.text = SDL_AllocateEventString(text);
+        event.text.text = SDL_CreateTemporaryString(text);
         if (!event.text.text) {
             return 0;
         }
@@ -751,7 +751,7 @@ int SDL_SendEditingText(const char *text, int start, int length)
         event.edit.windowID = keyboard->focus ? keyboard->focus->id : 0;
         event.edit.start = start;
         event.edit.length = length;
-        event.edit.text = SDL_AllocateEventString(text);
+        event.edit.text = SDL_CreateTemporaryString(text);
         if (!event.edit.text) {
             return 0;
         }
@@ -783,7 +783,7 @@ int SDL_SendEditingTextCandidates(char **candidates, int num_candidates, int sel
                 return 0;
             }
             for (int i = 0; i < num_candidates; ++i) {
-                event_candidates[i] = SDL_AllocateEventString(candidates[i]);
+                event_candidates[i] = SDL_CreateTemporaryString(candidates[i]);
             }
             event_candidates[num_candidates] = NULL;
             event.edit_candidates.candidates = event_candidates;

+ 1 - 1
src/events/SDL_keymap.c

@@ -1017,7 +1017,7 @@ const char *SDL_GetKeyName(SDL_Keycode key)
 
         end = SDL_UCS4ToUTF8(key, name);
         *end = '\0';
-        return SDL_FreeLater(SDL_strdup(name));
+        return SDL_CreateTemporaryString(name);
     }
 }
 

+ 2 - 2
src/events/SDL_mouse.c

@@ -312,7 +312,7 @@ void SDL_RemoveMouse(SDL_MouseID mouseID, SDL_bool send_event)
         return;
     }
 
-    SDL_FreeLater(SDL_mice[mouse_index].name);  // SDL_GetMouseNameForID returns this pointer.
+    SDL_free(SDL_mice[mouse_index].name);
 
     if (mouse_index != SDL_mouse_count - 1) {
         SDL_memcpy(&SDL_mice[mouse_index], &SDL_mice[mouse_index + 1], (SDL_mouse_count - mouse_index - 1) * sizeof(SDL_mice[mouse_index]));
@@ -376,7 +376,7 @@ const char *SDL_GetMouseNameForID(SDL_MouseID instance_id)
     if (mouse_index < 0) {
         return NULL;
     }
-    return SDL_mice[mouse_index].name;
+    return SDL_CreateTemporaryString(SDL_mice[mouse_index].name);
 }
 
 void SDL_SetDefaultCursor(SDL_Cursor *cursor)

+ 6 - 3
src/events/SDL_touch.c

@@ -102,7 +102,10 @@ SDL_Touch *SDL_GetTouch(SDL_TouchID id)
 const char *SDL_GetTouchDeviceName(SDL_TouchID id)
 {
     SDL_Touch *touch = SDL_GetTouch(id);
-    return touch ? touch->name : NULL;
+    if (!touch) {
+        return NULL;
+    }
+    return SDL_CreateTemporaryString(touch->name);
 }
 
 SDL_TouchDeviceType SDL_GetTouchDeviceType(SDL_TouchID id)
@@ -245,7 +248,7 @@ static int SDL_DelFinger(SDL_Touch *touch, SDL_FingerID fingerid)
         // Move the deleted finger to just past the end of the active fingers array and shift the active fingers by one.
         // This ensures that the descriptor for the now-deleted finger is located at `touch->fingers[touch->num_fingers]`
         // and is ready for use in SDL_AddFinger.
-        SDL_Finger *deleted_finger = touch->fingers[index]; 
+        SDL_Finger *deleted_finger = touch->fingers[index];
         SDL_memmove(&touch->fingers[index], &touch->fingers[index + 1], (touch->num_fingers - index) * sizeof(touch->fingers[index]));
         touch->fingers[touch->num_fingers] = deleted_finger;
     }
@@ -493,7 +496,7 @@ void SDL_DelTouch(SDL_TouchID id)
         SDL_free(touch->fingers[i]);
     }
     SDL_free(touch->fingers);
-    SDL_FreeLater(touch->name);  // this pointer might be given to the app by SDL_GetTouchDeviceName.
+    SDL_free(touch->name);
     SDL_free(touch);
 
     SDL_num_touch--;

+ 2 - 6
src/filesystem/SDL_filesystem.c

@@ -383,8 +383,7 @@ const char * const *SDL_InternalGlobDirectory(const char *path, const char *patt
     SDL_free(folded);
     SDL_free(pathcpy);
 
-    SDL_FreeLater(retval);
-    return (const char * const *) retval;
+    return SDL_FreeLater(retval);
 }
 
 static int GlobDirectoryGetPathInfo(const char *path, SDL_PathInfo *info, void *userdata)
@@ -435,10 +434,7 @@ const char *SDL_GetUserFolder(SDL_Folder folder)
 const char *SDL_GetPrefPath(const char *org, const char *app)
 {
     char *path = SDL_SYS_GetPrefPath(org, app);
-    if (path) {
-        SDL_FreeLater(path);
-    }
-    return path;
+    return SDL_FreeLater(path);
 }
 
 

+ 4 - 4
src/haptic/SDL_haptic.c

@@ -100,7 +100,7 @@ const char *SDL_GetHapticNameForID(SDL_HapticID instance_id)
     if (SDL_GetHapticIndex(instance_id, &device_index)) {
         name = SDL_SYS_HapticName(device_index);
     }
-    return name ? SDL_FreeLater(SDL_strdup(name)) : NULL;
+    return SDL_CreateTemporaryString(name);
 }
 
 SDL_Haptic *SDL_OpenHaptic(SDL_HapticID instance_id)
@@ -187,9 +187,9 @@ SDL_HapticID SDL_GetHapticID(SDL_Haptic *haptic)
 
 const char *SDL_GetHapticName(SDL_Haptic *haptic)
 {
-    CHECK_HAPTIC_MAGIC(haptic, 0);
+    CHECK_HAPTIC_MAGIC(haptic, NULL);
 
-    return haptic->name;
+    return SDL_CreateTemporaryString(haptic->name);
 }
 
 SDL_bool SDL_IsMouseHaptic(void)
@@ -336,7 +336,7 @@ void SDL_CloseHaptic(SDL_Haptic *haptic)
     }
 
     /* Free the data associated with this device */
-    SDL_FreeLater(haptic->name);  // this pointer is handed to the app in SDL_GetHapticName()
+    SDL_free(haptic->name);
     SDL_free(haptic);
 }
 

+ 8 - 12
src/joystick/SDL_gamepad.c

@@ -1600,7 +1600,7 @@ static GamepadMapping_t *SDL_PrivateAddMappingForGUID(SDL_JoystickGUID jGUID, co
         /* Only overwrite the mapping if the priority is the same or higher. */
         if (pGamepadMapping->priority <= priority) {
             /* Update existing mapping */
-            SDL_FreeLater(pGamepadMapping->name);  // this is returned in SDL_GetGamepadName.
+            SDL_free(pGamepadMapping->name);
             pGamepadMapping->name = pchName;
             SDL_free(pGamepadMapping->mapping);
             pGamepadMapping->mapping = pchMapping;
@@ -2198,8 +2198,7 @@ const char * const *SDL_GetGamepadMappings(int *count)
         SDL_free(mappings);
     }
 
-    SDL_FreeLater(retval);
-    return (const char * const *) retval;
+    return SDL_FreeLater(retval);
 }
 
 /*
@@ -2221,8 +2220,7 @@ const char *SDL_GetGamepadMappingForGUID(SDL_JoystickGUID guid)
     }
     SDL_UnlockJoysticks();
 
-    SDL_FreeLater(retval);
-    return retval;
+    return SDL_FreeLater(retval);
 }
 
 /*
@@ -2240,8 +2238,7 @@ const char *SDL_GetGamepadMapping(SDL_Gamepad *gamepad)
     }
     SDL_UnlockJoysticks();
 
-    SDL_FreeLater(retval);
-    return retval;
+    return SDL_FreeLater(retval);
 }
 
 /*
@@ -2434,7 +2431,7 @@ const char *SDL_GetGamepadNameForID(SDL_JoystickID instance_id)
             if (SDL_strcmp(mapping->name, "*") == 0) {
                 retval = SDL_GetJoystickNameForID(instance_id);
             } else {
-                retval = mapping->name;
+                retval = SDL_CreateTemporaryString(mapping->name);
             }
         }
     }
@@ -2538,8 +2535,7 @@ const char *SDL_GetGamepadMappingForID(SDL_JoystickID instance_id)
     }
     SDL_UnlockJoysticks();
 
-    SDL_FreeLater(retval);
-    return retval;
+    return SDL_FreeLater(retval);
 }
 
 /*
@@ -3314,7 +3310,7 @@ const char *SDL_GetGamepadName(SDL_Gamepad *gamepad)
             gamepad->joystick->steam_handle != 0) {
             retval = SDL_GetJoystickName(gamepad->joystick);
         } else {
-            retval = gamepad->name;
+            retval = SDL_CreateTemporaryString(gamepad->name);
         }
     }
     SDL_UnlockJoysticks();
@@ -3707,7 +3703,7 @@ void SDL_QuitGamepadMappings(void)
     while (s_pSupportedGamepads) {
         pGamepadMap = s_pSupportedGamepads;
         s_pSupportedGamepads = s_pSupportedGamepads->next;
-        SDL_FreeLater(pGamepadMap->name);  // this is returned in SDL_GetGamepadName.
+        SDL_free(pGamepadMap->name);
         SDL_free(pGamepadMap->mapping);
         SDL_free(pGamepadMap);
     }

+ 12 - 12
src/joystick/SDL_joystick.c

@@ -780,13 +780,13 @@ const char *SDL_GetJoystickNameForID(SDL_JoystickID instance_id)
     SDL_LockJoysticks();
     info = SDL_GetJoystickVirtualGamepadInfoForID(instance_id);
     if (info) {
-        name = info->name;
+        name = SDL_CreateTemporaryString(info->name);
     } else if (SDL_GetDriverAndJoystickIndex(instance_id, &driver, &device_index)) {
-        name = driver->GetDeviceName(device_index);
+        name = SDL_CreateTemporaryString(driver->GetDeviceName(device_index));
     }
     SDL_UnlockJoysticks();
 
-    return name ? SDL_FreeLater(SDL_strdup(name)) : NULL;
+    return name;
 }
 
 /*
@@ -800,14 +800,14 @@ const char *SDL_GetJoystickPathForID(SDL_JoystickID instance_id)
 
     SDL_LockJoysticks();
     if (SDL_GetDriverAndJoystickIndex(instance_id, &driver, &device_index)) {
-        path = driver->GetDevicePath(device_index);
+        path = SDL_CreateTemporaryString(driver->GetDevicePath(device_index));
     }
     SDL_UnlockJoysticks();
 
     if (!path) {
         SDL_Unsupported();
     }
-    return path ? SDL_FreeLater(SDL_strdup(path)) : NULL;
+    return path;
 }
 
 /*
@@ -1653,9 +1653,9 @@ const char *SDL_GetJoystickName(SDL_Joystick *joystick)
 
         info = SDL_GetJoystickVirtualGamepadInfoForID(joystick->instance_id);
         if (info) {
-            retval = info->name;
+            retval = SDL_CreateTemporaryString(info->name);
         } else {
-            retval = joystick->name;
+            retval = SDL_CreateTemporaryString(joystick->name);
         }
     }
     SDL_UnlockJoysticks();
@@ -1675,7 +1675,7 @@ const char *SDL_GetJoystickPath(SDL_Joystick *joystick)
         CHECK_JOYSTICK_MAGIC(joystick, NULL);
 
         if (joystick->path) {
-            retval = joystick->path;
+            retval = SDL_CreateTemporaryString(joystick->path);
         } else {
             SDL_Unsupported();
             retval = NULL;
@@ -1884,9 +1884,9 @@ void SDL_CloseJoystick(SDL_Joystick *joystick)
         }
 
         /* Free the data associated with this joystick */
-        SDL_FreeLater(joystick->name);  // SDL_GetJoystickName returns this pointer.
-        SDL_FreeLater(joystick->path);  // SDL_GetJoystickPath returns this pointer.
-        SDL_FreeLater(joystick->serial);  // SDL_GetJoystickSerial returns this pointer.
+        SDL_free(joystick->name);
+        SDL_free(joystick->path);
+        SDL_free(joystick->serial);
         SDL_free(joystick->axes);
         SDL_free(joystick->balls);
         SDL_free(joystick->hats);
@@ -3431,7 +3431,7 @@ const char *SDL_GetJoystickSerial(SDL_Joystick *joystick)
     {
         CHECK_JOYSTICK_MAGIC(joystick, NULL);
 
-        retval = joystick->serial;
+        retval = SDL_CreateTemporaryString(joystick->serial);
     }
     SDL_UnlockJoysticks();
 

+ 4 - 4
src/sensor/SDL_sensor.c

@@ -246,11 +246,11 @@ const char *SDL_GetSensorNameForID(SDL_SensorID instance_id)
 
     SDL_LockSensors();
     if (SDL_GetDriverAndSensorIndex(instance_id, &driver, &device_index)) {
-        name = driver->GetDeviceName(device_index);
+        name = SDL_CreateTemporaryString(driver->GetDeviceName(device_index));
     }
     SDL_UnlockSensors();
 
-    return name ? SDL_FreeLater(SDL_strdup(name)) : NULL;
+    return name;
 }
 
 SDL_SensorType SDL_GetSensorTypeForID(SDL_SensorID instance_id)
@@ -407,7 +407,7 @@ const char *SDL_GetSensorName(SDL_Sensor *sensor)
     {
         CHECK_SENSOR_MAGIC(sensor, NULL);
 
-        retval = sensor->name;
+        retval = SDL_CreateTemporaryString(sensor->name);
     }
     SDL_UnlockSensors();
 
@@ -526,7 +526,7 @@ void SDL_CloseSensor(SDL_Sensor *sensor)
         }
 
         /* Free the data associated with this sensor */
-        SDL_FreeLater(sensor->name);  // this pointer gets handed to the app by SDL_GetSensorName().
+        SDL_free(sensor->name);
         SDL_free(sensor);
     }
     SDL_UnlockSensors();

+ 1 - 1
src/thread/SDL_thread.c

@@ -329,7 +329,7 @@ void SDL_RunThread(SDL_Thread *thread)
     if (!SDL_AtomicCompareAndSwap(&thread->state, SDL_THREAD_STATE_ALIVE, SDL_THREAD_STATE_ZOMBIE)) {
         /* Clean up if something already detached us. */
         if (SDL_AtomicCompareAndSwap(&thread->state, SDL_THREAD_STATE_DETACHED, SDL_THREAD_STATE_CLEANED)) {
-            SDL_FreeLater(thread->name);
+            SDL_free(thread->name); /* Can't free later, we've already cleaned up TLS */
             SDL_free(thread);
         }
     }

+ 1 - 1
src/video/SDL_clipboard.c

@@ -349,7 +349,7 @@ int SDL_SetPrimarySelectionText(const char *text)
             return -1;
         }
     } else {
-        SDL_FreeLater(_this->primary_selection_text);  // this pointer might be given to the app by SDL_GetPrimarySelectionText.
+        SDL_FreeLater(_this->primary_selection_text);  // SDL_GetPrimarySelectionText() returns this pointer.
         _this->primary_selection_text = SDL_strdup(text);
     }