Browse Source

Fixed memory leak cleaning up mouse and keyboard instances

Fixes https://github.com/libsdl-org/SDL/issues/9487
Sam Lantinga 11 months ago
parent
commit
537c62f4c1

+ 2 - 2
src/core/linux/SDL_evdev.c

@@ -619,7 +619,7 @@ static int SDL_EVDEV_init_keyboard(SDL_evdevlist_item *item, int udev_class)
 
 static void SDL_EVDEV_destroy_keyboard(SDL_evdevlist_item *item)
 {
-    SDL_RemoveKeyboard((SDL_KeyboardID)item->fd);
+    SDL_RemoveKeyboard((SDL_KeyboardID)item->fd, SDL_TRUE);
 }
 
 static int SDL_EVDEV_init_mouse(SDL_evdevlist_item *item, int udev_class)
@@ -656,7 +656,7 @@ static int SDL_EVDEV_init_mouse(SDL_evdevlist_item *item, int udev_class)
 
 static void SDL_EVDEV_destroy_mouse(SDL_evdevlist_item *item)
 {
-    SDL_RemoveMouse((SDL_MouseID)item->fd);
+    SDL_RemoveMouse((SDL_MouseID)item->fd, SDL_TRUE);
 }
 
 static int SDL_EVDEV_init_touchscreen(SDL_evdevlist_item *item, int udev_class)

+ 11 - 7
src/events/SDL_keyboard.c

@@ -734,7 +734,7 @@ void SDL_AddKeyboard(SDL_KeyboardID keyboardID, const char *name, SDL_bool send_
     }
 }
 
-void SDL_RemoveKeyboard(SDL_KeyboardID keyboardID)
+void SDL_RemoveKeyboard(SDL_KeyboardID keyboardID, SDL_bool send_event)
 {
     int keyboard_index = SDL_GetKeyboardIndex(keyboardID);
     if (keyboard_index < 0) {
@@ -749,11 +749,13 @@ void SDL_RemoveKeyboard(SDL_KeyboardID keyboardID)
     }
     --SDL_keyboard_count;
 
-    SDL_Event event;
-    SDL_zero(event);
-    event.type = SDL_EVENT_KEYBOARD_REMOVED;
-    event.kdevice.which = keyboardID;
-    SDL_PushEvent(&event);
+    if (send_event) {
+        SDL_Event event;
+        SDL_zero(event);
+        event.type = SDL_EVENT_KEYBOARD_REMOVED;
+        event.kdevice.which = keyboardID;
+        SDL_PushEvent(&event);
+    }
 }
 
 SDL_bool SDL_HasKeyboard(void)
@@ -1254,7 +1256,9 @@ int SDL_SendEditingText(const char *text, int start, int length)
 
 void SDL_QuitKeyboard(void)
 {
-    SDL_keyboard_count = 0;
+    for (int i = SDL_keyboard_count; i--;) {
+        SDL_RemoveKeyboard(SDL_keyboards[i].instance_id, SDL_FALSE);
+    }
     SDL_free(SDL_keyboards);
     SDL_keyboards = NULL;
 }

+ 1 - 1
src/events/SDL_keyboard_c.h

@@ -39,7 +39,7 @@ extern SDL_bool SDL_IsKeyboard(Uint16 vendor, Uint16 product, int num_keys);
 extern void SDL_AddKeyboard(SDL_KeyboardID keyboardID, const char *name, SDL_bool send_event);
 
 /* A keyboard has been removed from the system */
-extern void SDL_RemoveKeyboard(SDL_KeyboardID keyboardID);
+extern void SDL_RemoveKeyboard(SDL_KeyboardID keyboardID, SDL_bool send_event);
 
 /* Get the default keymap */
 extern void SDL_GetDefaultKeymap(SDL_Keycode *keymap);

+ 11 - 7
src/events/SDL_mouse.c

@@ -280,7 +280,7 @@ void SDL_AddMouse(SDL_MouseID mouseID, const char *name, SDL_bool send_event)
     }
 }
 
-void SDL_RemoveMouse(SDL_MouseID mouseID)
+void SDL_RemoveMouse(SDL_MouseID mouseID, SDL_bool send_event)
 {
     int mouse_index = SDL_GetMouseIndex(mouseID);
     if (mouse_index < 0) {
@@ -308,11 +308,13 @@ void SDL_RemoveMouse(SDL_MouseID mouseID)
         }
     }
 
-    SDL_Event event;
-    SDL_zero(event);
-    event.type = SDL_EVENT_MOUSE_REMOVED;
-    event.mdevice.which = mouseID;
-    SDL_PushEvent(&event);
+    if (send_event) {
+        SDL_Event event;
+        SDL_zero(event);
+        event.type = SDL_EVENT_MOUSE_REMOVED;
+        event.mdevice.which = mouseID;
+        SDL_PushEvent(&event);
+    }
 }
 
 SDL_bool SDL_HasMouse(void)
@@ -1118,7 +1120,9 @@ void SDL_QuitMouse(void)
     SDL_DelHintCallback(SDL_HINT_MOUSE_RELATIVE_WARP_MOTION,
                         SDL_MouseRelativeWarpMotionChanged, mouse);
 
-    SDL_mouse_count = 0;
+    for (int i = SDL_mouse_count; i--; ) {
+        SDL_RemoveMouse(SDL_mice[i].instance_id, SDL_FALSE);
+    }
     SDL_free(SDL_mice);
     SDL_mice = NULL;
 }

+ 1 - 1
src/events/SDL_mouse_c.h

@@ -140,7 +140,7 @@ extern SDL_bool SDL_IsMouse(Uint16 vendor, Uint16 product);
 extern void SDL_AddMouse(SDL_MouseID mouseID, const char *name, SDL_bool send_event);
 
 /* A mouse has been removed from the system */
-extern void SDL_RemoveMouse(SDL_MouseID mouseID);
+extern void SDL_RemoveMouse(SDL_MouseID mouseID, SDL_bool send_event);
 
 /* Get the mouse state structure */
 extern SDL_Mouse *SDL_GetMouse(void);

+ 2 - 2
src/video/uikit/SDL_uikitevents.m

@@ -193,7 +193,7 @@ static void OnGCKeyboardDisconnected(GCKeyboard *keyboard) API_AVAILABLE(macos(1
 {
     SDL_KeyboardID keyboardID = (SDL_KeyboardID)(uintptr_t)keyboard;
 
-    SDL_RemoveKeyboard(keyboardID);
+    SDL_RemoveKeyboard(keyboardID, SDL_TRUE);
 
     keyboard.keyboardInput.keyChangedHandler = nil;
 }
@@ -385,7 +385,7 @@ static void OnGCMouseDisconnected(GCMouse *mouse) API_AVAILABLE(macos(11.0), ios
 
     UpdatePointerLock();
 
-    SDL_RemoveMouse(mouseID);
+    SDL_RemoveMouse(mouseID, SDL_TRUE);
 }
 
 void SDL_InitGCMouse(void)

+ 2 - 2
src/video/wayland/SDL_waylandevents.c

@@ -1732,7 +1732,7 @@ static void seat_handle_capabilities(void *data, struct wl_seat *seat,
         input->pointer = NULL;
         input->display->pointer = NULL;
 
-        SDL_RemoveMouse(input->pointer_id);
+        SDL_RemoveMouse(input->pointer_id, SDL_TRUE);
         input->pointer_id = 0;
     }
 
@@ -1760,7 +1760,7 @@ static void seat_handle_capabilities(void *data, struct wl_seat *seat,
         wl_keyboard_destroy(input->keyboard);
         input->keyboard = NULL;
 
-        SDL_RemoveKeyboard(input->keyboard_id);
+        SDL_RemoveKeyboard(input->keyboard_id, SDL_TRUE);
         input->keyboard_id = 0;
     }
 

+ 2 - 2
src/video/windows/SDL_windowsevents.c

@@ -926,13 +926,13 @@ void WIN_CheckKeyboardAndMouseHotplug(SDL_VideoDevice *_this, SDL_bool initial_c
 
     for (int i = old_keyboard_count; i--;) {
         if (!HasDeviceID(old_keyboards[i], new_keyboards, new_keyboard_count)) {
-            SDL_RemoveKeyboard(old_keyboards[i]);
+            SDL_RemoveKeyboard(old_keyboards[i], send_event);
         }
     }
 
     for (int i = old_mouse_count; i--;) {
         if (!HasDeviceID(old_mice[i], new_mice, new_mouse_count)) {
-            SDL_RemoveMouse(old_mice[i]);
+            SDL_RemoveMouse(old_mice[i], send_event);
         }
     }
 

+ 2 - 2
src/video/x11/SDL_x11xinput2.c

@@ -823,13 +823,13 @@ void X11_Xinput2UpdateDevices(SDL_VideoDevice *_this, SDL_bool initial_check)
 
     for (int i = old_keyboard_count; i--;) {
         if (!HasDeviceID(old_keyboards[i], new_keyboards, new_keyboard_count)) {
-            SDL_RemoveKeyboard(old_keyboards[i]);
+            SDL_RemoveKeyboard(old_keyboards[i], send_event);
         }
     }
 
     for (int i = old_mouse_count; i--;) {
         if (!HasDeviceID(old_mice[i], new_mice, new_mouse_count)) {
-            SDL_RemoveMouse(old_mice[i]);
+            SDL_RemoveMouse(old_mice[i], send_event);
         }
     }