/*
  Simple DirectMedia Layer
  Copyright (C) 1997-2025 Sam Lantinga <slouken@libsdl.org>

  This software is provided 'as-is', without any express or implied
  warranty.  In no event will the authors be held liable for any damages
  arising from the use of this software.

  Permission is granted to anyone to use this software for any purpose,
  including commercial applications, and to alter it and redistribute it
  freely, subject to the following restrictions:

  1. The origin of this software must not be misrepresented; you must not
     claim that you wrote the original software. If you use this software
     in a product, an acknowledgment in the product documentation would be
     appreciated but is not required.
  2. Altered source versions must be plainly marked as such, and must not be
     misrepresented as being the original software.
  3. This notice may not be removed or altered from any source distribution.
*/
#include "SDL_internal.h"

// This is the joystick API for Simple DirectMedia Layer

#include "SDL_sysjoystick.h"
#include "../SDL_hints_c.h"
#include "SDL_gamepad_c.h"
#include "SDL_joystick_c.h"
#include "SDL_steam_virtual_gamepad.h"

#include "../events/SDL_events_c.h"
#include "../video/SDL_sysvideo.h"
#include "../sensor/SDL_sensor_c.h"
#include "hidapi/SDL_hidapijoystick_c.h"

// This is included in only one place because it has a large static list of controllers
#include "controller_type.h"

#if defined(SDL_PLATFORM_WIN32) || defined(SDL_PLATFORM_WINGDK)
// Needed for checking for input remapping programs
#include "../core/windows/SDL_windows.h"

#undef UNICODE // We want ASCII functions
#include <tlhelp32.h>
#endif

#ifdef SDL_JOYSTICK_VIRTUAL
#include "./virtual/SDL_virtualjoystick_c.h"
#endif

static SDL_JoystickDriver *SDL_joystick_drivers[] = {
#ifdef SDL_JOYSTICK_HIDAPI // Highest priority driver for supported devices
    &SDL_HIDAPI_JoystickDriver,
#endif
#ifdef SDL_JOYSTICK_PRIVATE
    &SDL_PRIVATE_JoystickDriver,
#endif
#ifdef SDL_JOYSTICK_GAMEINPUT // Higher priority than other Windows drivers
    &SDL_GAMEINPUT_JoystickDriver,
#endif
#ifdef SDL_JOYSTICK_RAWINPUT // Before WINDOWS driver, as WINDOWS wants to check if this driver is handling things
    &SDL_RAWINPUT_JoystickDriver,
#endif
#if defined(SDL_JOYSTICK_DINPUT) || defined(SDL_JOYSTICK_XINPUT) // Before WGI driver, as WGI wants to check if this driver is handling things
    &SDL_WINDOWS_JoystickDriver,
#endif
#ifdef SDL_JOYSTICK_WGI
    &SDL_WGI_JoystickDriver,
#endif
#ifdef SDL_JOYSTICK_WINMM
    &SDL_WINMM_JoystickDriver,
#endif
#ifdef SDL_JOYSTICK_LINUX
    &SDL_LINUX_JoystickDriver,
#endif
#ifdef SDL_JOYSTICK_IOKIT
    &SDL_DARWIN_JoystickDriver,
#endif
#if (defined(SDL_PLATFORM_MACOS) || defined(SDL_PLATFORM_IOS) || defined(SDL_PLATFORM_TVOS)) && !defined(SDL_JOYSTICK_DISABLED)
    &SDL_IOS_JoystickDriver,
#endif
#ifdef SDL_JOYSTICK_ANDROID
    &SDL_ANDROID_JoystickDriver,
#endif
#ifdef SDL_JOYSTICK_EMSCRIPTEN
    &SDL_EMSCRIPTEN_JoystickDriver,
#endif
#ifdef SDL_JOYSTICK_HAIKU
    &SDL_HAIKU_JoystickDriver,
#endif
#ifdef SDL_JOYSTICK_USBHID /* !!! FIXME: "USBHID" is a generic name, and doubly-confusing with HIDAPI next to it. This is the *BSD interface, rename this. */
    &SDL_BSD_JoystickDriver,
#endif
#ifdef SDL_JOYSTICK_PS2
    &SDL_PS2_JoystickDriver,
#endif
#ifdef SDL_JOYSTICK_PSP
    &SDL_PSP_JoystickDriver,
#endif
#ifdef SDL_JOYSTICK_VIRTUAL
    &SDL_VIRTUAL_JoystickDriver,
#endif
#ifdef SDL_JOYSTICK_VITA
    &SDL_VITA_JoystickDriver,
#endif
#ifdef SDL_JOYSTICK_N3DS
    &SDL_N3DS_JoystickDriver,
#endif
#if defined(SDL_JOYSTICK_DUMMY) || defined(SDL_JOYSTICK_DISABLED)
    &SDL_DUMMY_JoystickDriver
#endif
};

#ifndef SDL_THREAD_SAFETY_ANALYSIS
static
#endif
SDL_Mutex *SDL_joystick_lock = NULL; // This needs to support recursive locks
static SDL_AtomicInt SDL_joystick_lock_pending;
static int SDL_joysticks_locked;
static bool SDL_joysticks_initialized;
static bool SDL_joysticks_quitting;
static bool SDL_joystick_being_added;
static SDL_Joystick *SDL_joysticks SDL_GUARDED_BY(SDL_joystick_lock) = NULL;
static int SDL_joystick_player_count SDL_GUARDED_BY(SDL_joystick_lock) = 0;
static SDL_JoystickID *SDL_joystick_players SDL_GUARDED_BY(SDL_joystick_lock) = NULL;
static bool SDL_joystick_allows_background_events = false;

static Uint32 initial_old_xboxone_controllers[] = {
    MAKE_VIDPID(0x0000, 0x6686),
    MAKE_VIDPID(0x0079, 0x18a1),
    MAKE_VIDPID(0x0079, 0x18c2),
    MAKE_VIDPID(0x0079, 0x18c8),
    MAKE_VIDPID(0x0079, 0x18cf),
    MAKE_VIDPID(0x03f0, 0x0495),
    MAKE_VIDPID(0x045e, 0x02d1),
    MAKE_VIDPID(0x045e, 0x02dd),
    MAKE_VIDPID(0x045e, 0x02e0),
    MAKE_VIDPID(0x045e, 0x02e3),
    MAKE_VIDPID(0x045e, 0x02ea),
    MAKE_VIDPID(0x045e, 0x02fd),
    MAKE_VIDPID(0x045e, 0x02ff),
    MAKE_VIDPID(0x045e, 0x0867),
    MAKE_VIDPID(0x045e, 0x0b00),
    MAKE_VIDPID(0x045e, 0x0b05),
    MAKE_VIDPID(0x045e, 0x0b0a),
    MAKE_VIDPID(0x045e, 0x0b0c),
    MAKE_VIDPID(0x045e, 0x0b20),
    MAKE_VIDPID(0x045e, 0x0b21),
    MAKE_VIDPID(0x045e, 0x0b22),
    MAKE_VIDPID(0x046d, 0x0000),
    MAKE_VIDPID(0x046d, 0x1004),
    MAKE_VIDPID(0x046d, 0x1007),
    MAKE_VIDPID(0x046d, 0x1008),
    MAKE_VIDPID(0x046d, 0xf301),
    MAKE_VIDPID(0x0738, 0x02a0),
    MAKE_VIDPID(0x0738, 0x4a01),
    MAKE_VIDPID(0x0738, 0x7263),
    MAKE_VIDPID(0x0738, 0xb738),
    MAKE_VIDPID(0x0738, 0xcb29),
    MAKE_VIDPID(0x0738, 0xf401),
    MAKE_VIDPID(0x0c12, 0x0e17),
    MAKE_VIDPID(0x0c12, 0x0e1c),
    MAKE_VIDPID(0x0c12, 0x0e22),
    MAKE_VIDPID(0x0c12, 0x0e30),
    MAKE_VIDPID(0x0d62, 0x9a1a),
    MAKE_VIDPID(0x0d62, 0x9a1b),
    MAKE_VIDPID(0x0e00, 0x0e00),
    MAKE_VIDPID(0x0e6f, 0x012a),
    MAKE_VIDPID(0x0e6f, 0x0139),
    MAKE_VIDPID(0x0e6f, 0x013B),
    MAKE_VIDPID(0x0e6f, 0x013a),
    MAKE_VIDPID(0x0e6f, 0x0145),
    MAKE_VIDPID(0x0e6f, 0x0146),
    MAKE_VIDPID(0x0e6f, 0x0152),
    MAKE_VIDPID(0x0e6f, 0x015b),
    MAKE_VIDPID(0x0e6f, 0x015c),
    MAKE_VIDPID(0x0e6f, 0x015d),
    MAKE_VIDPID(0x0e6f, 0x015f),
    MAKE_VIDPID(0x0e6f, 0x0160),
    MAKE_VIDPID(0x0e6f, 0x0161),
    MAKE_VIDPID(0x0e6f, 0x0162),
    MAKE_VIDPID(0x0e6f, 0x0163),
    MAKE_VIDPID(0x0e6f, 0x0164),
    MAKE_VIDPID(0x0e6f, 0x0165),
    MAKE_VIDPID(0x0e6f, 0x0166),
    MAKE_VIDPID(0x0e6f, 0x0167),
    MAKE_VIDPID(0x0e6f, 0x0205),
    MAKE_VIDPID(0x0e6f, 0x0206),
    MAKE_VIDPID(0x0e6f, 0x0246),
    MAKE_VIDPID(0x0e6f, 0x0261),
    MAKE_VIDPID(0x0e6f, 0x0262),
    MAKE_VIDPID(0x0e6f, 0x02a0),
    MAKE_VIDPID(0x0e6f, 0x02a1),
    MAKE_VIDPID(0x0e6f, 0x02a2),
    MAKE_VIDPID(0x0e6f, 0x02a3),
    MAKE_VIDPID(0x0e6f, 0x02a4),
    MAKE_VIDPID(0x0e6f, 0x02a5),
    MAKE_VIDPID(0x0e6f, 0x02a6),
    MAKE_VIDPID(0x0e6f, 0x02a7),
    MAKE_VIDPID(0x0e6f, 0x02a8),
    MAKE_VIDPID(0x0e6f, 0x02a9),
    MAKE_VIDPID(0x0e6f, 0x02aa),
    MAKE_VIDPID(0x0e6f, 0x02ab),
    MAKE_VIDPID(0x0e6f, 0x02ac),
    MAKE_VIDPID(0x0e6f, 0x02ad),
    MAKE_VIDPID(0x0e6f, 0x02ae),
    MAKE_VIDPID(0x0e6f, 0x02af),
    MAKE_VIDPID(0x0e6f, 0x02b0),
    MAKE_VIDPID(0x0e6f, 0x02b1),
    MAKE_VIDPID(0x0e6f, 0x02b2),
    MAKE_VIDPID(0x0e6f, 0x02b3),
    MAKE_VIDPID(0x0e6f, 0x02b5),
    MAKE_VIDPID(0x0e6f, 0x02b6),
    MAKE_VIDPID(0x0e6f, 0x02b8),
    MAKE_VIDPID(0x0e6f, 0x02bd),
    MAKE_VIDPID(0x0e6f, 0x02be),
    MAKE_VIDPID(0x0e6f, 0x02bf),
    MAKE_VIDPID(0x0e6f, 0x02c0),
    MAKE_VIDPID(0x0e6f, 0x02c1),
    MAKE_VIDPID(0x0e6f, 0x02c2),
    MAKE_VIDPID(0x0e6f, 0x02c3),
    MAKE_VIDPID(0x0e6f, 0x02c4),
    MAKE_VIDPID(0x0e6f, 0x02c5),
    MAKE_VIDPID(0x0e6f, 0x02c6),
    MAKE_VIDPID(0x0e6f, 0x02c7),
    MAKE_VIDPID(0x0e6f, 0x02c8),
    MAKE_VIDPID(0x0e6f, 0x02c9),
    MAKE_VIDPID(0x0e6f, 0x02ca),
    MAKE_VIDPID(0x0e6f, 0x02cb),
    MAKE_VIDPID(0x0e6f, 0x02cd),
    MAKE_VIDPID(0x0e6f, 0x02ce),
    MAKE_VIDPID(0x0e6f, 0x02cf),
    MAKE_VIDPID(0x0e6f, 0x02d5),
    MAKE_VIDPID(0x0e6f, 0x0346),
    MAKE_VIDPID(0x0e6f, 0x0446),
    MAKE_VIDPID(0x0e6f, 0xf501),
    MAKE_VIDPID(0x0f0d, 0x0063),
    MAKE_VIDPID(0x0f0d, 0x0067),
    MAKE_VIDPID(0x0f0d, 0x0078),
    MAKE_VIDPID(0x0f0d, 0x0097),
    MAKE_VIDPID(0x0f0d, 0x00ba),
    MAKE_VIDPID(0x0f0d, 0x00c0),
    MAKE_VIDPID(0x0f0d, 0x00c5),
    MAKE_VIDPID(0x0f0d, 0x00d8),
    MAKE_VIDPID(0x0f0d, 0x00ed),
    MAKE_VIDPID(0x0fff, 0x02a1),
    MAKE_VIDPID(0x12ab, 0x0304),
    MAKE_VIDPID(0x1430, 0x0291),
    MAKE_VIDPID(0x1430, 0x02a9),
    MAKE_VIDPID(0x1430, 0x070b),
    MAKE_VIDPID(0x1430, 0x0719),
    MAKE_VIDPID(0x146b, 0x0611),
    MAKE_VIDPID(0x1532, 0x0a00),
    MAKE_VIDPID(0x1532, 0x0a03),
    MAKE_VIDPID(0x1532, 0x0a14),
    MAKE_VIDPID(0x1532, 0x0a15),
    MAKE_VIDPID(0x16d0, 0x0f3f),
    MAKE_VIDPID(0x1bad, 0x028e),
    MAKE_VIDPID(0x1bad, 0x02a0),
    MAKE_VIDPID(0x1bad, 0x5500),
    MAKE_VIDPID(0x20ab, 0x55ef),
    MAKE_VIDPID(0x24c6, 0x541a),
    MAKE_VIDPID(0x24c6, 0x542a),
    MAKE_VIDPID(0x24c6, 0x543a),
    MAKE_VIDPID(0x24c6, 0x5509),
    MAKE_VIDPID(0x24c6, 0x551a),
    MAKE_VIDPID(0x24c6, 0x561a),
    MAKE_VIDPID(0x24c6, 0x581a),
    MAKE_VIDPID(0x24c6, 0x591a),
    MAKE_VIDPID(0x24c6, 0x592a),
    MAKE_VIDPID(0x24c6, 0x791a),
    MAKE_VIDPID(0x2516, 0x0069),
    MAKE_VIDPID(0x25b1, 0x0360),
    MAKE_VIDPID(0x2c22, 0x2203),
    MAKE_VIDPID(0x2e24, 0x0652),
    MAKE_VIDPID(0x2e24, 0x1618),
    MAKE_VIDPID(0x2e24, 0x1688),
    MAKE_VIDPID(0x2f24, 0x0011),
    MAKE_VIDPID(0x2f24, 0x002e),
    MAKE_VIDPID(0x2f24, 0x0050),
    MAKE_VIDPID(0x2f24, 0x0053),
    MAKE_VIDPID(0x2f24, 0x008f),
    MAKE_VIDPID(0x2f24, 0x0091),
    MAKE_VIDPID(0x2f24, 0x00b7),
    MAKE_VIDPID(0xd2d2, 0xd2d2),
};
static SDL_vidpid_list old_xboxone_controllers = {
    "SDL_JOYSTICK_OLD_XBOXONE_CONTROLLERS", 0, 0, NULL,
    "SDL_JOYSTICK_OLD_XBOXONE_CONTROLLERS_EXCLUDED", 0, 0, NULL,
    SDL_arraysize(initial_old_xboxone_controllers), initial_old_xboxone_controllers,
    false
};

static Uint32 initial_arcadestick_devices[] = {
    MAKE_VIDPID(0x0079, 0x181a), // Venom Arcade Stick
    MAKE_VIDPID(0x0079, 0x181b), // Venom Arcade Stick
    MAKE_VIDPID(0x0c12, 0x0ef6), // Hitbox Arcade Stick
    MAKE_VIDPID(0x0e6f, 0x0109), // PDP Versus Fighting Pad
    MAKE_VIDPID(0x0f0d, 0x0016), // Hori Real Arcade Pro.EX
    MAKE_VIDPID(0x0f0d, 0x001b), // Hori Real Arcade Pro VX
    MAKE_VIDPID(0x0f0d, 0x0063), // Hori Real Arcade Pro Hayabusa (USA) Xbox One
    MAKE_VIDPID(0x0f0d, 0x006a), // Real Arcade Pro 4
    MAKE_VIDPID(0x0f0d, 0x0078), // Hori Real Arcade Pro V Kai Xbox One
    MAKE_VIDPID(0x0f0d, 0x008a), // HORI Real Arcade Pro 4
    MAKE_VIDPID(0x0f0d, 0x008c), // Hori Real Arcade Pro 4
    MAKE_VIDPID(0x0f0d, 0x00aa), // HORI Real Arcade Pro V Hayabusa in Switch Mode
    MAKE_VIDPID(0x0f0d, 0x00ed), // Hori Fighting Stick mini 4 kai
    MAKE_VIDPID(0x0f0d, 0x011c), // Hori Fighting Stick Alpha in PS4 Mode
    MAKE_VIDPID(0x0f0d, 0x011e), // Hori Fighting Stick Alpha in PC Mode
    MAKE_VIDPID(0x0f0d, 0x0184), // Hori Fighting Stick Alpha in PS5 Mode
    MAKE_VIDPID(0x146b, 0x0604), // NACON Daija Arcade Stick
    MAKE_VIDPID(0x1532, 0x0a00), // Razer Atrox Arcade Stick
    MAKE_VIDPID(0x1bad, 0xf03d), // Street Fighter IV Arcade Stick TE - Chun Li
    MAKE_VIDPID(0x1bad, 0xf502), // Hori Real Arcade Pro.VX SA
    MAKE_VIDPID(0x1bad, 0xf504), // Hori Real Arcade Pro. EX
    MAKE_VIDPID(0x1bad, 0xf506), // Hori Real Arcade Pro.EX Premium VLX
    MAKE_VIDPID(0x20d6, 0xa715), // PowerA Nintendo Switch Fusion Arcade Stick
    MAKE_VIDPID(0x24c6, 0x5000), // Razer Atrox Arcade Stick
    MAKE_VIDPID(0x24c6, 0x5501), // Hori Real Arcade Pro VX-SA
    MAKE_VIDPID(0x24c6, 0x550e), // Hori Real Arcade Pro V Kai 360
    MAKE_VIDPID(0x2c22, 0x2300), // Qanba Obsidian Arcade Joystick in PS4 Mode
    MAKE_VIDPID(0x2c22, 0x2302), // Qanba Obsidian Arcade Joystick in PS3 Mode
    MAKE_VIDPID(0x2c22, 0x2303), // Qanba Obsidian Arcade Joystick in PC Mode
    MAKE_VIDPID(0x2c22, 0x2500), // Qanba Dragon Arcade Joystick in PS4 Mode
    MAKE_VIDPID(0x2c22, 0x2502), // Qanba Dragon Arcade Joystick in PS3 Mode
    MAKE_VIDPID(0x2c22, 0x2503), // Qanba Dragon Arcade Joystick in PC Mode
};
static SDL_vidpid_list arcadestick_devices = {
    SDL_HINT_JOYSTICK_ARCADESTICK_DEVICES, 0, 0, NULL,
    SDL_HINT_JOYSTICK_ARCADESTICK_DEVICES_EXCLUDED, 0, 0, NULL,
    SDL_arraysize(initial_arcadestick_devices), initial_arcadestick_devices,
    false
};

/* This list is taken from:
   https://raw.githubusercontent.com/denilsonsa/udev-joystick-blacklist/master/generate_rules.py
 */
static Uint32 initial_blacklist_devices[] = {
    // Microsoft Microsoft Wireless Optical Desktop 2.10
    // Microsoft Wireless Desktop - Comfort Edition
    MAKE_VIDPID(0x045e, 0x009d),

    // Microsoft Microsoft Digital Media Pro Keyboard
    // Microsoft Corp. Digital Media Pro Keyboard
    MAKE_VIDPID(0x045e, 0x00b0),

    // Microsoft Microsoft Digital Media Keyboard
    // Microsoft Corp. Digital Media Keyboard 1.0A
    MAKE_VIDPID(0x045e, 0x00b4),

    // Microsoft Microsoft Digital Media Keyboard 3000
    MAKE_VIDPID(0x045e, 0x0730),

    // Microsoft Microsoft 2.4GHz Transceiver v6.0
    // Microsoft Microsoft 2.4GHz Transceiver v8.0
    // Microsoft Corp. Nano Transceiver v1.0 for Bluetooth
    // Microsoft Wireless Mobile Mouse 1000
    // Microsoft Wireless Desktop 3000
    MAKE_VIDPID(0x045e, 0x0745),

    // Microsoft SideWinder(TM) 2.4GHz Transceiver
    MAKE_VIDPID(0x045e, 0x0748),

    // Microsoft Corp. Wired Keyboard 600
    MAKE_VIDPID(0x045e, 0x0750),

    // Microsoft Corp. Sidewinder X4 keyboard
    MAKE_VIDPID(0x045e, 0x0768),

    // Microsoft Corp. Arc Touch Mouse Transceiver
    MAKE_VIDPID(0x045e, 0x0773),

    // Microsoft 2.4GHz Transceiver v9.0
    // Microsoft Nano Transceiver v2.1
    // Microsoft Sculpt Ergonomic Keyboard (5KV-00001)
    MAKE_VIDPID(0x045e, 0x07a5),

    // Microsoft Nano Transceiver v1.0
    // Microsoft Wireless Keyboard 800
    MAKE_VIDPID(0x045e, 0x07b2),

    // Microsoft Nano Transceiver v2.0
    MAKE_VIDPID(0x045e, 0x0800),

    MAKE_VIDPID(0x046d, 0xc30a), // Logitech, Inc. iTouch Composite keyboard

    MAKE_VIDPID(0x04d9, 0xa0df), // Tek Syndicate Mouse (E-Signal USB Gaming Mouse)

    // List of Wacom devices at: http://linuxwacom.sourceforge.net/wiki/index.php/Device_IDs
    MAKE_VIDPID(0x056a, 0x0010), // Wacom ET-0405 Graphire
    MAKE_VIDPID(0x056a, 0x0011), // Wacom ET-0405A Graphire2 (4x5)
    MAKE_VIDPID(0x056a, 0x0012), // Wacom ET-0507A Graphire2 (5x7)
    MAKE_VIDPID(0x056a, 0x0013), // Wacom CTE-430 Graphire3 (4x5)
    MAKE_VIDPID(0x056a, 0x0014), // Wacom CTE-630 Graphire3 (6x8)
    MAKE_VIDPID(0x056a, 0x0015), // Wacom CTE-440 Graphire4 (4x5)
    MAKE_VIDPID(0x056a, 0x0016), // Wacom CTE-640 Graphire4 (6x8)
    MAKE_VIDPID(0x056a, 0x0017), // Wacom CTE-450 Bamboo Fun (4x5)
    MAKE_VIDPID(0x056a, 0x0018), // Wacom CTE-650 Bamboo Fun 6x8
    MAKE_VIDPID(0x056a, 0x0019), // Wacom CTE-631 Bamboo One
    MAKE_VIDPID(0x056a, 0x00d1), // Wacom Bamboo Pen and Touch CTH-460
    MAKE_VIDPID(0x056a, 0x030e), // Wacom Intuos Pen (S) CTL-480

    MAKE_VIDPID(0x09da, 0x054f), // A4 Tech Co., G7 750 mouse
    MAKE_VIDPID(0x09da, 0x1410), // A4 Tech Co., Ltd Bloody AL9 mouse
    MAKE_VIDPID(0x09da, 0x3043), // A4 Tech Co., Ltd Bloody R8A Gaming Mouse
    MAKE_VIDPID(0x09da, 0x31b5), // A4 Tech Co., Ltd Bloody TL80 Terminator Laser Gaming Mouse
    MAKE_VIDPID(0x09da, 0x3997), // A4 Tech Co., Ltd Bloody RT7 Terminator Wireless
    MAKE_VIDPID(0x09da, 0x3f8b), // A4 Tech Co., Ltd Bloody V8 mouse
    MAKE_VIDPID(0x09da, 0x51f4), // Modecom MC-5006 Keyboard
    MAKE_VIDPID(0x09da, 0x5589), // A4 Tech Co., Ltd Terminator TL9 Laser Gaming Mouse
    MAKE_VIDPID(0x09da, 0x7b22), // A4 Tech Co., Ltd Bloody V5
    MAKE_VIDPID(0x09da, 0x7f2d), // A4 Tech Co., Ltd Bloody R3 mouse
    MAKE_VIDPID(0x09da, 0x8090), // A4 Tech Co., Ltd X-718BK Oscar Optical Gaming Mouse
    MAKE_VIDPID(0x09da, 0x9033), // A4 Tech Co., X7 X-705K
    MAKE_VIDPID(0x09da, 0x9066), // A4 Tech Co., Sharkoon Fireglider Optical
    MAKE_VIDPID(0x09da, 0x9090), // A4 Tech Co., Ltd XL-730K / XL-750BK / XL-755BK Laser Mouse
    MAKE_VIDPID(0x09da, 0x90c0), // A4 Tech Co., Ltd X7 G800V keyboard
    MAKE_VIDPID(0x09da, 0xf012), // A4 Tech Co., Ltd Bloody V7 mouse
    MAKE_VIDPID(0x09da, 0xf32a), // A4 Tech Co., Ltd Bloody B540 keyboard
    MAKE_VIDPID(0x09da, 0xf613), // A4 Tech Co., Ltd Bloody V2 mouse
    MAKE_VIDPID(0x09da, 0xf624), // A4 Tech Co., Ltd Bloody B120 Keyboard

    MAKE_VIDPID(0x1b1c, 0x1b3c), // Corsair Harpoon RGB gaming mouse

    MAKE_VIDPID(0x1d57, 0xad03), // [T3] 2.4GHz and IR Air Mouse Remote Control

    MAKE_VIDPID(0x1e7d, 0x2e4a), // Roccat Tyon Mouse

    MAKE_VIDPID(0x20a0, 0x422d), // Winkeyless.kr Keyboards

    MAKE_VIDPID(0x2516, 0x001f), // Cooler Master Storm Mizar Mouse
    MAKE_VIDPID(0x2516, 0x0028), // Cooler Master Storm Alcor Mouse

    /*****************************************************************/
    // Additional entries
    /*****************************************************************/

    MAKE_VIDPID(0x04d9, 0x8008), // OBINLB USB-HID Keyboard (Anne Pro II)
    MAKE_VIDPID(0x04d9, 0x8009), // OBINLB USB-HID Keyboard (Anne Pro II)
    MAKE_VIDPID(0x04d9, 0xa292), // OBINLB USB-HID Keyboard (Anne Pro II)
    MAKE_VIDPID(0x04d9, 0xa293), // OBINLB USB-HID Keyboard (Anne Pro II)
    MAKE_VIDPID(0x04f2, 0xa13c), // HP Deluxe Webcam KQ246AA
    MAKE_VIDPID(0x0e6f, 0x018a), // PDP REALMz Wireless Controller for Switch, USB charging
    MAKE_VIDPID(0x1532, 0x0266), // Razer Huntsman V2 Analog, non-functional DInput device
    MAKE_VIDPID(0x1532, 0x0282), // Razer Huntsman Mini Analog, non-functional DInput device
    MAKE_VIDPID(0x26ce, 0x01a2), // ASRock LED Controller
    MAKE_VIDPID(0x20d6, 0x0002), // PowerA Enhanced Wireless Controller for Nintendo Switch (charging port only)
    MAKE_VIDPID(0x3434, 0x0211), // Keychron K1 Pro System Control
};
static SDL_vidpid_list blacklist_devices = {
    SDL_HINT_JOYSTICK_BLACKLIST_DEVICES, 0, 0, NULL,
    SDL_HINT_JOYSTICK_BLACKLIST_DEVICES_EXCLUDED, 0, 0, NULL,
    SDL_arraysize(initial_blacklist_devices), initial_blacklist_devices,
    false
};

static Uint32 initial_flightstick_devices[] = {
    MAKE_VIDPID(0x044f, 0x0402), // HOTAS Warthog Joystick
    MAKE_VIDPID(0x044f, 0xb10a), // ThrustMaster, Inc. T.16000M Joystick
    MAKE_VIDPID(0x046d, 0xc215), // Logitech Extreme 3D
    MAKE_VIDPID(0x0583, 0x6258), // Padix USB joystick with viewfinder
    MAKE_VIDPID(0x0583, 0x688f), // Padix QF-688uv Windstorm Pro
    MAKE_VIDPID(0x0583, 0x7070), // Padix QF-707u Bazooka
    MAKE_VIDPID(0x0583, 0xa019), // Padix USB vibration joystick with viewfinder
    MAKE_VIDPID(0x0583, 0xa131), // Padix USB Wireless 2.4GHz
    MAKE_VIDPID(0x0583, 0xa209), // Padix MetalStrike ForceFeedback
    MAKE_VIDPID(0x0583, 0xb010), // Padix MetalStrike Pro
    MAKE_VIDPID(0x0583, 0xb012), // Padix Wireless MetalStrike
    MAKE_VIDPID(0x0583, 0xb013), // Padix USB Wireless 2.4GHZ
    MAKE_VIDPID(0x0738, 0x2221), // Saitek Pro Flight X-56 Rhino Stick
    MAKE_VIDPID(0x10f5, 0x7084), // Turtle Beach VelocityOne
    MAKE_VIDPID(0x231d, 0x0126), // Gunfighter Mk.III 'Space Combat Edition' (right)
    MAKE_VIDPID(0x231d, 0x0127), // Gunfighter Mk.III 'Space Combat Edition' (left)
    MAKE_VIDPID(0x362c, 0x0001), // Yawman Arrow
};
static SDL_vidpid_list flightstick_devices = {
    SDL_HINT_JOYSTICK_FLIGHTSTICK_DEVICES, 0, 0, NULL,
    SDL_HINT_JOYSTICK_FLIGHTSTICK_DEVICES_EXCLUDED, 0, 0, NULL,
    SDL_arraysize(initial_flightstick_devices), initial_flightstick_devices,
    false
};

static Uint32 initial_gamecube_devices[] = {
    MAKE_VIDPID(0x0079, 0x1843), // DragonRise GameCube Controller Adapter
    MAKE_VIDPID(0x0079, 0x1844), // DragonRise GameCube Controller Adapter
    MAKE_VIDPID(0x0079, 0x1846), // DragonRise GameCube Controller Adapter
    MAKE_VIDPID(0x057e, 0x0337), // Nintendo Wii U GameCube Controller Adapter
    MAKE_VIDPID(0x057e, 0x2073), // Nintendo Switch 2 NSO GameCube Controller
    MAKE_VIDPID(0x0926, 0x8888), // Cyber Gadget GameCube Controller
    MAKE_VIDPID(0x0e6f, 0x0185), // PDP Wired Fight Pad Pro for Nintendo Switch
    MAKE_VIDPID(0x1a34, 0xf705), // GameCube {HuiJia USB box}
    MAKE_VIDPID(0x20d6, 0xa711), // PowerA Wired Controller Nintendo GameCube Style
};
static SDL_vidpid_list gamecube_devices = {
    SDL_HINT_JOYSTICK_GAMECUBE_DEVICES, 0, 0, NULL,
    SDL_HINT_JOYSTICK_GAMECUBE_DEVICES_EXCLUDED, 0, 0, NULL,
    SDL_arraysize(initial_gamecube_devices), initial_gamecube_devices,
    false
};

static Uint32 initial_rog_gamepad_mice[] = {
    MAKE_VIDPID(0x0b05, 0x18e3), // ROG Chakram (wired) Mouse
    MAKE_VIDPID(0x0b05, 0x18e5), // ROG Chakram (wireless) Mouse
    MAKE_VIDPID(0x0b05, 0x1906), // ROG Pugio II
    MAKE_VIDPID(0x0b05, 0x1958), // ROG Chakram Core Mouse
    MAKE_VIDPID(0x0b05, 0x1a18), // ROG Chakram X (wired) Mouse
    MAKE_VIDPID(0x0b05, 0x1a1a), // ROG Chakram X (wireless) Mouse
    MAKE_VIDPID(0x0b05, 0x1a1c), // ROG Chakram X (Bluetooth) Mouse
};
static SDL_vidpid_list rog_gamepad_mice = {
    SDL_HINT_ROG_GAMEPAD_MICE, 0, 0, NULL,
    SDL_HINT_ROG_GAMEPAD_MICE_EXCLUDED, 0, 0, NULL,
    SDL_arraysize(initial_rog_gamepad_mice), initial_rog_gamepad_mice,
    false
};

static Uint32 initial_throttle_devices[] = {
    MAKE_VIDPID(0x044f, 0x0404), // HOTAS Warthog Throttle
    MAKE_VIDPID(0x0738, 0xa221), // Saitek Pro Flight X-56 Rhino Throttle
    MAKE_VIDPID(0x10f5, 0x7085), // Turtle Beach VelocityOne Throttle
};
static SDL_vidpid_list throttle_devices = {
    SDL_HINT_JOYSTICK_THROTTLE_DEVICES, 0, 0, NULL,
    SDL_HINT_JOYSTICK_THROTTLE_DEVICES_EXCLUDED, 0, 0, NULL,
    SDL_arraysize(initial_throttle_devices), initial_throttle_devices,
    false
};

static Uint32 initial_wheel_devices[] = {
    MAKE_VIDPID(0x0079, 0x1864), // DragonRise Inc. Wired Wheel (active mode) (also known as PXN V900 (PS3), Superdrive SV-750, or a Genesis Seaborg 400)
    MAKE_VIDPID(0x044f, 0xb65d), // Thrustmaster Wheel FFB
    MAKE_VIDPID(0x044f, 0xb65e), // Thrustmaster T500RS
    MAKE_VIDPID(0x044f, 0xb664), // Thrustmaster TX (initial mode)
    MAKE_VIDPID(0x044f, 0xb669), // Thrustmaster TX (active mode)
    MAKE_VIDPID(0x044f, 0xb66d), // Thrustmaster T300RS (PS4 mode)
    MAKE_VIDPID(0x044f, 0xb66d), // Thrustmaster Wheel FFB
    MAKE_VIDPID(0x044f, 0xb66e), // Thrustmaster T300RS (normal mode)
    MAKE_VIDPID(0x044f, 0xb66f), // Thrustmaster T300RS (advanced mode)
    MAKE_VIDPID(0x044f, 0xb677), // Thrustmaster T150
    MAKE_VIDPID(0x044f, 0xb67f), // Thrustmaster TMX
    MAKE_VIDPID(0x044f, 0xb691), // Thrustmaster TS-XW (initial mode)
    MAKE_VIDPID(0x044f, 0xb692), // Thrustmaster TS-XW (active mode)
    MAKE_VIDPID(0x044f, 0xb696), // Thrustmaster T248
    MAKE_VIDPID(0x046d, 0xc24f), // Logitech G29 (PS3)
    MAKE_VIDPID(0x046d, 0xc260), // Logitech G29 (PS4)
    MAKE_VIDPID(0x046d, 0xc261), // Logitech G920 (initial mode)
    MAKE_VIDPID(0x046d, 0xc262), // Logitech G920 (active mode)
    MAKE_VIDPID(0x046d, 0xc266), // Logitech G923 for Playstation 4 and PC (PC mode)
    MAKE_VIDPID(0x046d, 0xc267), // Logitech G923 for Playstation 4 and PC (PS4 mode)
    MAKE_VIDPID(0x046d, 0xc268), // Logitech PRO Racing Wheel (PC mode)
    MAKE_VIDPID(0x046d, 0xc269), // Logitech PRO Racing Wheel (PS4/PS5 mode)
    MAKE_VIDPID(0x046d, 0xc26d), // Logitech G923 (Xbox)
    MAKE_VIDPID(0x046d, 0xc26e), // Logitech G923
    MAKE_VIDPID(0x046d, 0xc272), // Logitech PRO Racing Wheel for Xbox (PC mode)
    MAKE_VIDPID(0x046d, 0xc294), // Logitech generic wheel
    MAKE_VIDPID(0x046d, 0xc295), // Logitech Momo Force
    MAKE_VIDPID(0x046d, 0xc298), // Logitech Driving Force Pro
    MAKE_VIDPID(0x046d, 0xc299), // Logitech G25
    MAKE_VIDPID(0x046d, 0xc29a), // Logitech Driving Force GT
    MAKE_VIDPID(0x046d, 0xc29b), // Logitech G27
    MAKE_VIDPID(0x046d, 0xca03), // Logitech Momo Racing
    MAKE_VIDPID(0x0483, 0x0522), // Simagic Wheelbase (including M10, Alpha Mini, Alpha, Alpha U)
    MAKE_VIDPID(0x0483, 0xa355), // VRS DirectForce Pro Wheel Base
    MAKE_VIDPID(0x0583, 0xa132), // Padix USB Wireless 2.4GHz Wheelpad
    MAKE_VIDPID(0x0583, 0xa133), // Padix USB Wireless 2.4GHz Wheel
    MAKE_VIDPID(0x0583, 0xa202), // Padix Force Feedback Wheel
    MAKE_VIDPID(0x0583, 0xb002), // Padix Vibration USB Wheel
    MAKE_VIDPID(0x0583, 0xb005), // Padix USB Wheel
    MAKE_VIDPID(0x0583, 0xb008), // Padix USB Wireless 2.4GHz Wheel
    MAKE_VIDPID(0x0583, 0xb009), // Padix USB Wheel
    MAKE_VIDPID(0x0583, 0xb018), // Padix TW6 Wheel
    MAKE_VIDPID(0x0eb7, 0x0001), // Fanatec ClubSport Wheel Base V2
    MAKE_VIDPID(0x0eb7, 0x0004), // Fanatec ClubSport Wheel Base V2.5
    MAKE_VIDPID(0x0eb7, 0x0005), // Fanatec CSL Elite Wheel Base+ (PS4)
    MAKE_VIDPID(0x0eb7, 0x0006), // Fanatec Podium Wheel Base DD1
    MAKE_VIDPID(0x0eb7, 0x0007), // Fanatec Podium Wheel Base DD2
    MAKE_VIDPID(0x0eb7, 0x0011), // Fanatec Forza Motorsport (CSR Wheel / CSR Elite Wheel)
    MAKE_VIDPID(0x0eb7, 0x0020), // Fanatec generic wheel / CSL DD / GT DD Pro
    MAKE_VIDPID(0x0eb7, 0x0197), // Fanatec Porsche Wheel (Turbo / GT3 RS / Turbo S / GT3 V2 / GT2)
    MAKE_VIDPID(0x0eb7, 0x038e), // Fanatec ClubSport Wheel Base V1
    MAKE_VIDPID(0x0eb7, 0x0e03), // Fanatec CSL Elite Wheel Base
    MAKE_VIDPID(0x11ff, 0x0511), // DragonRise Inc. Wired Wheel (initial mode) (also known as PXN V900 (PS3), Superdrive SV-750, or a Genesis Seaborg 400)
    MAKE_VIDPID(0x1209, 0xffb0), // Generic FFBoard OpenFFBoard universal forcefeedback wheel
    MAKE_VIDPID(0x16d0, 0x0d5a), // Simucube 1 Wheelbase
    MAKE_VIDPID(0x16d0, 0x0d5f), // Simucube 2 Ultimate Wheelbase
    MAKE_VIDPID(0x16d0, 0x0d60), // Simucube 2 Pro Wheelbase
    MAKE_VIDPID(0x16d0, 0x0d61), // Simucube 2 Sport Wheelbase
    MAKE_VIDPID(0x2433, 0xf300), // Asetek SimSports Invicta Wheelbase
    MAKE_VIDPID(0x2433, 0xf301), // Asetek SimSports Forte Wheelbase
    MAKE_VIDPID(0x2433, 0xf303), // Asetek SimSports La Prima Wheelbase
    MAKE_VIDPID(0x2433, 0xf306), // Asetek SimSports Tony Kannan Wheelbase
    MAKE_VIDPID(0x3416, 0x0301), // Cammus C5 Wheelbase
    MAKE_VIDPID(0x3416, 0x0302), // Cammus C12 Wheelbase
    MAKE_VIDPID(0x346e, 0x0000), // Moza R16/R21 Wheelbase
    MAKE_VIDPID(0x346e, 0x0002), // Moza R9 Wheelbase
    MAKE_VIDPID(0x346e, 0x0004), // Moza R5 Wheelbase
    MAKE_VIDPID(0x346e, 0x0005), // Moza R3 Wheelbase
    MAKE_VIDPID(0x346e, 0x0006), // Moza R12 Wheelbase
};
static SDL_vidpid_list wheel_devices = {
    SDL_HINT_JOYSTICK_WHEEL_DEVICES, 0, 0, NULL,
    SDL_HINT_JOYSTICK_WHEEL_DEVICES_EXCLUDED, 0, 0, NULL,
    SDL_arraysize(initial_wheel_devices), initial_wheel_devices,
    false
};

static Uint32 initial_zero_centered_devices[] = {
    MAKE_VIDPID(0x05a0, 0x3232), // 8Bitdo Zero Gamepad
    MAKE_VIDPID(0x0e8f, 0x3013), // HuiJia SNES USB adapter
};
static SDL_vidpid_list zero_centered_devices = {
    SDL_HINT_JOYSTICK_ZERO_CENTERED_DEVICES, 0, 0, NULL,
    NULL, 0, 0, NULL,
    SDL_arraysize(initial_zero_centered_devices), initial_zero_centered_devices,
    false
};

#define CHECK_JOYSTICK_MAGIC(joystick, result)                  \
    if (!SDL_ObjectValid(joystick, SDL_OBJECT_TYPE_JOYSTICK)) { \
        SDL_InvalidParamError("joystick");                      \
        SDL_UnlockJoysticks();                                  \
        return result;                                          \
    }

#define CHECK_JOYSTICK_VIRTUAL(joystick, result)                \
    if (!joystick->is_virtual) {                                \
        SDL_SetError("joystick isn't virtual");                 \
        SDL_UnlockJoysticks();                                  \
        return result;                                          \
    }

bool SDL_JoysticksInitialized(void)
{
    return SDL_joysticks_initialized;
}

bool SDL_JoysticksQuitting(void)
{
    return SDL_joysticks_quitting;
}

void SDL_LockJoysticks(void)
{
    (void)SDL_AtomicIncRef(&SDL_joystick_lock_pending);
    SDL_LockMutex(SDL_joystick_lock);
    (void)SDL_AtomicDecRef(&SDL_joystick_lock_pending);

    ++SDL_joysticks_locked;
}

void SDL_UnlockJoysticks(void)
{
    bool last_unlock = false;

    --SDL_joysticks_locked;

    if (!SDL_joysticks_initialized) {
        // NOTE: There's a small window here where another thread could lock the mutex after we've checked for pending locks
        if (!SDL_joysticks_locked && SDL_GetAtomicInt(&SDL_joystick_lock_pending) == 0) {
            last_unlock = true;
        }
    }

    /* The last unlock after joysticks are uninitialized will cleanup the mutex,
     * allowing applications to lock joysticks while reinitializing the system.
     */
    if (last_unlock) {
        SDL_Mutex *joystick_lock = SDL_joystick_lock;

        SDL_LockMutex(joystick_lock);
        {
            SDL_UnlockMutex(SDL_joystick_lock);

            SDL_joystick_lock = NULL;
        }
        SDL_UnlockMutex(joystick_lock);
        SDL_DestroyMutex(joystick_lock);
    } else {
        SDL_UnlockMutex(SDL_joystick_lock);
    }
}

bool SDL_JoysticksLocked(void)
{
    return (SDL_joysticks_locked > 0);
}

void SDL_AssertJoysticksLocked(void)
{
    SDL_assert(SDL_JoysticksLocked());
}

/*
 * Get the driver and device index for a joystick instance ID
 * This should be called while the joystick lock is held, to prevent another thread from updating the list
 */
static bool SDL_GetDriverAndJoystickIndex(SDL_JoystickID instance_id, SDL_JoystickDriver **driver, int *driver_index)
{
    int i, num_joysticks, device_index;

    SDL_AssertJoysticksLocked();

    if (instance_id > 0) {
        for (i = 0; i < SDL_arraysize(SDL_joystick_drivers); ++i) {
            num_joysticks = SDL_joystick_drivers[i]->GetCount();
            for (device_index = 0; device_index < num_joysticks; ++device_index) {
                SDL_JoystickID joystick_id = SDL_joystick_drivers[i]->GetDeviceInstanceID(device_index);
                if (joystick_id == instance_id) {
                    *driver = SDL_joystick_drivers[i];
                    *driver_index = device_index;
                    return true;
                }
            }
        }
    }

    SDL_SetError("Joystick %" SDL_PRIu32 " not found", instance_id);
    return false;
}

static int SDL_FindFreePlayerIndex(void)
{
    int player_index;

    SDL_AssertJoysticksLocked();

    for (player_index = 0; player_index < SDL_joystick_player_count; ++player_index) {
        if (SDL_joystick_players[player_index] == 0) {
            break;
        }
    }
    return player_index;
}

static int SDL_GetPlayerIndexForJoystickID(SDL_JoystickID instance_id)
{
    int player_index;

    SDL_AssertJoysticksLocked();

    for (player_index = 0; player_index < SDL_joystick_player_count; ++player_index) {
        if (instance_id == SDL_joystick_players[player_index]) {
            break;
        }
    }
    if (player_index == SDL_joystick_player_count) {
        player_index = -1;
    }
    return player_index;
}

static SDL_JoystickID SDL_GetJoystickIDForPlayerIndex(int player_index)
{
    SDL_AssertJoysticksLocked();

    if (player_index < 0 || player_index >= SDL_joystick_player_count) {
        return 0;
    }
    return SDL_joystick_players[player_index];
}

static bool SDL_SetJoystickIDForPlayerIndex(int player_index, SDL_JoystickID instance_id)
{
    SDL_JoystickID existing_instance = SDL_GetJoystickIDForPlayerIndex(player_index);
    SDL_JoystickDriver *driver;
    int device_index;
    int existing_player_index;

    SDL_AssertJoysticksLocked();

    if (player_index >= SDL_joystick_player_count) {
        SDL_JoystickID *new_players = (SDL_JoystickID *)SDL_realloc(SDL_joystick_players, (player_index + 1) * sizeof(*SDL_joystick_players));
        if (!new_players) {
            return false;
        }

        SDL_joystick_players = new_players;
        SDL_memset(&SDL_joystick_players[SDL_joystick_player_count], 0, (player_index - SDL_joystick_player_count + 1) * sizeof(SDL_joystick_players[0]));
        SDL_joystick_player_count = player_index + 1;
    } else if (player_index >= 0 && SDL_joystick_players[player_index] == instance_id) {
        // Joystick is already assigned the requested player index
        return true;
    }

    // Clear the old player index
    existing_player_index = SDL_GetPlayerIndexForJoystickID(instance_id);
    if (existing_player_index >= 0) {
        SDL_joystick_players[existing_player_index] = 0;
    }

    if (player_index >= 0) {
        SDL_joystick_players[player_index] = instance_id;
    }

    // Update the driver with the new index
    if (SDL_GetDriverAndJoystickIndex(instance_id, &driver, &device_index)) {
        driver->SetDevicePlayerIndex(device_index, player_index);
    }

    // Move any existing joystick to another slot
    if (existing_instance > 0) {
        SDL_SetJoystickIDForPlayerIndex(SDL_FindFreePlayerIndex(), existing_instance);
    }
    return true;
}

static void SDLCALL SDL_JoystickAllowBackgroundEventsChanged(void *userdata, const char *name, const char *oldValue, const char *hint)
{
    if (SDL_GetStringBoolean(hint, false)) {
        SDL_joystick_allows_background_events = true;
    } else {
        SDL_joystick_allows_background_events = false;
    }
}

bool SDL_InitJoysticks(void)
{
    int i;
    bool result = false;

    // Create the joystick list lock
    if (SDL_joystick_lock == NULL) {
        SDL_joystick_lock = SDL_CreateMutex();
    }

    if (!SDL_InitSubSystem(SDL_INIT_EVENTS)) {
        return false;
    }

    SDL_LockJoysticks();

    SDL_joysticks_initialized = true;

    SDL_LoadVIDPIDList(&old_xboxone_controllers);
    SDL_LoadVIDPIDList(&arcadestick_devices);
    SDL_LoadVIDPIDList(&blacklist_devices);
    SDL_LoadVIDPIDList(&flightstick_devices);
    SDL_LoadVIDPIDList(&gamecube_devices);
    SDL_LoadVIDPIDList(&rog_gamepad_mice);
    SDL_LoadVIDPIDList(&throttle_devices);
    SDL_LoadVIDPIDList(&wheel_devices);
    SDL_LoadVIDPIDList(&zero_centered_devices);

    SDL_InitGamepadMappings();

    // See if we should allow joystick events while in the background
    SDL_AddHintCallback(SDL_HINT_JOYSTICK_ALLOW_BACKGROUND_EVENTS,
                        SDL_JoystickAllowBackgroundEventsChanged, NULL);

    SDL_InitSteamVirtualGamepadInfo();

    for (i = 0; i < SDL_arraysize(SDL_joystick_drivers); ++i) {
        if (SDL_joystick_drivers[i]->Init()) {
            result = true;
        }
    }
    SDL_UnlockJoysticks();

    if (!result) {
        SDL_QuitJoysticks();
    }

    return result;
}

bool SDL_JoysticksOpened(void)
{
    bool opened;

    SDL_LockJoysticks();
    {
        if (SDL_joysticks != NULL) {
            opened = true;
        } else {
            opened = false;
        }
    }
    SDL_UnlockJoysticks();

    return opened;
}

bool SDL_JoystickHandledByAnotherDriver(struct SDL_JoystickDriver *driver, Uint16 vendor_id, Uint16 product_id, Uint16 version, const char *name)
{
    int i;
    bool result = false;

    SDL_LockJoysticks();
    {
        for (i = 0; i < SDL_arraysize(SDL_joystick_drivers); ++i) {
            if (driver == SDL_joystick_drivers[i]) {
                // Higher priority drivers do not have this device
                break;
            }
            if (SDL_joystick_drivers[i]->IsDevicePresent(vendor_id, product_id, version, name)) {
                result = true;
                break;
            }
        }
    }
    SDL_UnlockJoysticks();

    return result;
}

bool SDL_HasJoystick(void)
{
    int i;
    int total_joysticks = 0;

    SDL_LockJoysticks();
    {
        for (i = 0; i < SDL_arraysize(SDL_joystick_drivers); ++i) {
            total_joysticks += SDL_joystick_drivers[i]->GetCount();
        }
    }
    SDL_UnlockJoysticks();

    if (total_joysticks > 0) {
        return true;
    }
    return false;
}

SDL_JoystickID *SDL_GetJoysticks(int *count)
{
    int i, num_joysticks, device_index;
    int joystick_index = 0, total_joysticks = 0;
    SDL_JoystickID *joysticks;

    SDL_LockJoysticks();
    {
        for (i = 0; i < SDL_arraysize(SDL_joystick_drivers); ++i) {
            total_joysticks += SDL_joystick_drivers[i]->GetCount();
        }

        joysticks = (SDL_JoystickID *)SDL_malloc((total_joysticks + 1) * sizeof(*joysticks));
        if (joysticks) {
            if (count) {
                *count = total_joysticks;
            }

            for (i = 0; i < SDL_arraysize(SDL_joystick_drivers); ++i) {
                num_joysticks = SDL_joystick_drivers[i]->GetCount();
                for (device_index = 0; device_index < num_joysticks; ++device_index) {
                    SDL_assert(joystick_index < total_joysticks);
                    joysticks[joystick_index] = SDL_joystick_drivers[i]->GetDeviceInstanceID(device_index);
                    SDL_assert(joysticks[joystick_index] > 0);
                    ++joystick_index;
                }
            }
            SDL_assert(joystick_index == total_joysticks);
            joysticks[joystick_index] = 0;
        } else {
            if (count) {
                *count = 0;
            }
        }
    }
    SDL_UnlockJoysticks();

    return joysticks;
}

const SDL_SteamVirtualGamepadInfo *SDL_GetJoystickVirtualGamepadInfoForID(SDL_JoystickID instance_id)
{
    SDL_JoystickDriver *driver;
    int device_index;
    const SDL_SteamVirtualGamepadInfo *info = NULL;

    if (SDL_SteamVirtualGamepadEnabled() &&
        SDL_GetDriverAndJoystickIndex(instance_id, &driver, &device_index)) {
        info = SDL_GetSteamVirtualGamepadInfo(driver->GetDeviceSteamVirtualGamepadSlot(device_index));
    }
    return info;
}

/*
 * Get the implementation dependent name of a joystick
 */
const char *SDL_GetJoystickNameForID(SDL_JoystickID instance_id)
{
    SDL_JoystickDriver *driver;
    int device_index;
    const char *name = NULL;
    const SDL_SteamVirtualGamepadInfo *info;

    SDL_LockJoysticks();
    info = SDL_GetJoystickVirtualGamepadInfoForID(instance_id);
    if (info) {
        name = SDL_GetPersistentString(info->name);
    } else if (SDL_GetDriverAndJoystickIndex(instance_id, &driver, &device_index)) {
        name = SDL_GetPersistentString(driver->GetDeviceName(device_index));
    }
    SDL_UnlockJoysticks();

    return name;
}

/*
 * Get the implementation dependent path of a joystick
 */
const char *SDL_GetJoystickPathForID(SDL_JoystickID instance_id)
{
    SDL_JoystickDriver *driver;
    int device_index;
    const char *path = NULL;

    SDL_LockJoysticks();
    if (SDL_GetDriverAndJoystickIndex(instance_id, &driver, &device_index)) {
        path = SDL_GetPersistentString(driver->GetDevicePath(device_index));
    }
    SDL_UnlockJoysticks();

    if (!path) {
        SDL_Unsupported();
    }
    return path;
}

/*
 *  Get the player index of a joystick, or -1 if it's not available
 */
int SDL_GetJoystickPlayerIndexForID(SDL_JoystickID instance_id)
{
    int player_index;

    SDL_LockJoysticks();
    player_index = SDL_GetPlayerIndexForJoystickID(instance_id);
    SDL_UnlockJoysticks();

    return player_index;
}

/*
 * Return true if this joystick is known to have all axes centered at zero
 * This isn't generally needed unless the joystick never generates an initial axis value near zero,
 * e.g. it's emulating axes with digital buttons
 */
static bool SDL_JoystickAxesCenteredAtZero(SDL_Joystick *joystick)
{
    // printf("JOYSTICK '%s' VID/PID 0x%.4x/0x%.4x AXES: %d\n", joystick->name, vendor, product, joystick->naxes);

    if (joystick->naxes == 2) {
        // Assume D-pad or thumbstick style axes are centered at 0
        return true;
    }

    return SDL_VIDPIDInList(SDL_GetJoystickVendor(joystick), SDL_GetJoystickProduct(joystick), &zero_centered_devices);
}

static bool IsROGAlly(SDL_Joystick *joystick)
{
    Uint16 vendor, product;
    SDL_GUID guid = SDL_GetJoystickGUID(joystick);

    // The ROG Ally controller spoofs an Xbox 360 controller
    SDL_GetJoystickGUIDInfo(guid, &vendor, &product, NULL, NULL);
    if (vendor == USB_VENDOR_MICROSOFT && product == USB_PRODUCT_XBOX360_WIRED_CONTROLLER) {
        // Check to see if this system has the expected sensors
        bool has_ally_accel = false;
        bool has_ally_gyro = false;

        if (SDL_InitSubSystem(SDL_INIT_SENSOR)) {
            SDL_SensorID *sensors = SDL_GetSensors(NULL);
            if (sensors) {
                int i;
                for (i = 0; sensors[i]; ++i) {
                    SDL_SensorID sensor = sensors[i];

                    if (!has_ally_accel && SDL_GetSensorTypeForID(sensor) == SDL_SENSOR_ACCEL) {
                        const char *sensor_name = SDL_GetSensorNameForID(sensor);
                        if (sensor_name && SDL_strcmp(sensor_name, "Sensor BMI320 Acc") == 0) {
                            has_ally_accel = true;
                        }
                    }
                    if (!has_ally_gyro && SDL_GetSensorTypeForID(sensor) == SDL_SENSOR_GYRO) {
                        const char *sensor_name = SDL_GetSensorNameForID(sensor);
                        if (sensor_name && SDL_strcmp(sensor_name, "Sensor BMI320 Gyr") == 0) {
                            has_ally_gyro = true;
                        }
                    }
                }
                SDL_free(sensors);
            }
            SDL_QuitSubSystem(SDL_INIT_SENSOR);
        }
        if (has_ally_accel && has_ally_gyro) {
            return true;
        }
    }
    return false;
}

static bool ShouldAttemptSensorFusion(SDL_Joystick *joystick, bool *invert_sensors)
{
    SDL_AssertJoysticksLocked();

    *invert_sensors = false;

    // The SDL controller sensor API is only available for gamepads (at the moment)
    if (!SDL_IsGamepad(joystick->instance_id)) {
        return false;
    }

    // If the controller already has sensors, use those
    if (joystick->nsensors > 0) {
        return false;
    }

    const char *hint = SDL_GetHint(SDL_HINT_GAMECONTROLLER_SENSOR_FUSION);
    if (hint && *hint) {
        if (*hint == '@' || SDL_strncmp(hint, "0x", 2) == 0) {
            SDL_vidpid_list gamepads;
            SDL_GUID guid;
            Uint16 vendor, product;
            bool enabled;
            SDL_zero(gamepads);

            // See if the gamepad is in our list of devices to enable
            guid = SDL_GetJoystickGUID(joystick);
            SDL_GetJoystickGUIDInfo(guid, &vendor, &product, NULL, NULL);
            SDL_LoadVIDPIDListFromHints(&gamepads, hint, NULL);
            enabled = SDL_VIDPIDInList(vendor, product, &gamepads);
            SDL_FreeVIDPIDList(&gamepads);
            if (enabled) {
                return true;
            }
        } else {
            return SDL_GetStringBoolean(hint, false);
        }
    }

    // See if this is another known wraparound gamepad
    if (joystick->name &&
        (SDL_strstr(joystick->name, "Backbone One") ||
         SDL_strstr(joystick->name, "Kishi"))) {
        return true;
    }
    if (IsROGAlly(joystick)) {
        /* I'm not sure if this is a Windows thing, or a quirk for ROG Ally,
         * but we need to invert the sensor data on all axes.
         */
        *invert_sensors = true;
        return true;
    }
    return false;
}

static void AttemptSensorFusion(SDL_Joystick *joystick, bool invert_sensors)
{
    SDL_SensorID *sensors;
    unsigned int i, j;

    SDL_AssertJoysticksLocked();

    if (!SDL_InitSubSystem(SDL_INIT_SENSOR)) {
        return;
    }

    sensors = SDL_GetSensors(NULL);
    if (sensors) {
        for (i = 0; sensors[i]; ++i) {
            SDL_SensorID sensor = sensors[i];

            if (!joystick->accel_sensor && SDL_GetSensorTypeForID(sensor) == SDL_SENSOR_ACCEL) {
                // Increment the sensor subsystem reference count
                SDL_InitSubSystem(SDL_INIT_SENSOR);

                joystick->accel_sensor = sensor;
                SDL_PrivateJoystickAddSensor(joystick, SDL_SENSOR_ACCEL, 0.0f);
            }
            if (!joystick->gyro_sensor && SDL_GetSensorTypeForID(sensor) == SDL_SENSOR_GYRO) {
                // Increment the sensor subsystem reference count
                SDL_InitSubSystem(SDL_INIT_SENSOR);

                joystick->gyro_sensor = sensor;
                SDL_PrivateJoystickAddSensor(joystick, SDL_SENSOR_GYRO, 0.0f);
            }
        }
        SDL_free(sensors);
    }
    SDL_QuitSubSystem(SDL_INIT_SENSOR);

    /* SDL defines sensor orientation for phones relative to the natural
       orientation, and for gamepads relative to being held in front of you.
       When a phone is being used as a gamepad, its orientation changes,
       so adjust sensor axes to match.
     */
    if (SDL_GetNaturalDisplayOrientation(SDL_GetPrimaryDisplay()) == SDL_ORIENTATION_LANDSCAPE) {
        /* When a device in landscape orientation is laid flat, the axes change
           orientation as follows:
            -X to +X becomes -X to +X
            -Y to +Y becomes +Z to -Z
            -Z to +Z becomes -Y to +Y
        */
        joystick->sensor_transform[0][0] = 1.0f;
        joystick->sensor_transform[1][2] = 1.0f;
        joystick->sensor_transform[2][1] = -1.0f;
    } else {
        /* When a device in portrait orientation is rotated left and laid flat,
           the axes change orientation as follows:
            -X to +X becomes +Z to -Z
            -Y to +Y becomes +X to -X
            -Z to +Z becomes -Y to +Y
        */
        joystick->sensor_transform[0][1] = -1.0f;
        joystick->sensor_transform[1][2] = 1.0f;
        joystick->sensor_transform[2][0] = -1.0f;
    }

    if (invert_sensors) {
        for (i = 0; i < SDL_arraysize(joystick->sensor_transform); ++i) {
            for (j = 0; j < SDL_arraysize(joystick->sensor_transform[i]); ++j) {
                joystick->sensor_transform[i][j] *= -1.0f;
            }
        }
    }
}

static void CleanupSensorFusion(SDL_Joystick *joystick)
{
    SDL_AssertJoysticksLocked();

    if (joystick->accel_sensor || joystick->gyro_sensor) {
        if (joystick->accel_sensor) {
            if (joystick->accel) {
                SDL_CloseSensor(joystick->accel);
                joystick->accel = NULL;
            }
            joystick->accel_sensor = 0;

            // Decrement the sensor subsystem reference count
            SDL_QuitSubSystem(SDL_INIT_SENSOR);
        }
        if (joystick->gyro_sensor) {
            if (joystick->gyro) {
                SDL_CloseSensor(joystick->gyro);
                joystick->gyro = NULL;
            }
            joystick->gyro_sensor = 0;

            // Decrement the sensor subsystem reference count
            SDL_QuitSubSystem(SDL_INIT_SENSOR);
        }
    }
}

static bool ShouldSwapFaceButtons(const SDL_SteamVirtualGamepadInfo *info)
{
    // When "Use Nintendo Button Layout" is enabled under Steam (the default)
    // it will send button 0 for the A (east) button and button 1 for the
    // B (south) button. This is done so that games that interpret the
    // buttons as Xbox input will get button 0 for "A" as they expect.
    //
    // However, SDL reports positional buttons, so we need to swap
    // the buttons so they show up in the correct position. This provides
    // consistent behavior regardless of whether we're running under Steam,
    // under the default settings.
    if (info &&
        (info->type == SDL_GAMEPAD_TYPE_NINTENDO_SWITCH_PRO ||
         info->type == SDL_GAMEPAD_TYPE_NINTENDO_SWITCH_JOYCON_LEFT ||
         info->type == SDL_GAMEPAD_TYPE_NINTENDO_SWITCH_JOYCON_RIGHT ||
         info->type == SDL_GAMEPAD_TYPE_NINTENDO_SWITCH_JOYCON_PAIR)) {
        return true;
    }
    return false;
}

/*
 * Open a joystick for use - the index passed as an argument refers to
 * the N'th joystick on the system.  This index is the value which will
 * identify this joystick in future joystick events.
 *
 * This function returns a joystick identifier, or NULL if an error occurred.
 */
SDL_Joystick *SDL_OpenJoystick(SDL_JoystickID instance_id)
{
    SDL_JoystickDriver *driver;
    int device_index;
    SDL_Joystick *joystick;
    SDL_Joystick *joysticklist;
    const char *joystickname = NULL;
    const char *joystickpath = NULL;
    bool invert_sensors = false;
    const SDL_SteamVirtualGamepadInfo *info;

    SDL_LockJoysticks();

    if (!SDL_GetDriverAndJoystickIndex(instance_id, &driver, &device_index)) {
        SDL_UnlockJoysticks();
        return NULL;
    }

    joysticklist = SDL_joysticks;
    /* If the joystick is already open, return it
     * it is important that we have a single joystick for each instance id
     */
    while (joysticklist) {
        if (instance_id == joysticklist->instance_id) {
            joystick = joysticklist;
            ++joystick->ref_count;
            SDL_UnlockJoysticks();
            return joystick;
        }
        joysticklist = joysticklist->next;
    }

    // Create and initialize the joystick
    joystick = (SDL_Joystick *)SDL_calloc(1, sizeof(*joystick));
    if (!joystick) {
        SDL_UnlockJoysticks();
        return NULL;
    }
    SDL_SetObjectValid(joystick, SDL_OBJECT_TYPE_JOYSTICK, true);
    joystick->driver = driver;
    joystick->instance_id = instance_id;
    joystick->attached = true;
    joystick->led_expiration = SDL_GetTicks();
    joystick->battery_percent = -1;
#ifdef SDL_JOYSTICK_VIRTUAL
    joystick->is_virtual = (driver == &SDL_VIRTUAL_JoystickDriver);
#endif

    if (!driver->Open(joystick, device_index)) {
        SDL_SetObjectValid(joystick, SDL_OBJECT_TYPE_JOYSTICK, false);
        SDL_free(joystick);
        SDL_UnlockJoysticks();
        return NULL;
    }

    joystickname = driver->GetDeviceName(device_index);
    if (joystickname) {
        joystick->name = SDL_strdup(joystickname);
    }

    joystickpath = driver->GetDevicePath(device_index);
    if (joystickpath) {
        joystick->path = SDL_strdup(joystickpath);
    }

    joystick->guid = driver->GetDeviceGUID(device_index);

    if (joystick->naxes > 0) {
        joystick->axes = (SDL_JoystickAxisInfo *)SDL_calloc(joystick->naxes, sizeof(*joystick->axes));
    }
    if (joystick->nballs > 0) {
        joystick->balls = (SDL_JoystickBallData *)SDL_calloc(joystick->nballs, sizeof(*joystick->balls));
    }
    if (joystick->nhats > 0) {
        joystick->hats = (Uint8 *)SDL_calloc(joystick->nhats, sizeof(*joystick->hats));
    }
    if (joystick->nbuttons > 0) {
        joystick->buttons = (bool *)SDL_calloc(joystick->nbuttons, sizeof(*joystick->buttons));
    }
    if (((joystick->naxes > 0) && !joystick->axes) ||
        ((joystick->nballs > 0) && !joystick->balls) ||
        ((joystick->nhats > 0) && !joystick->hats) ||
        ((joystick->nbuttons > 0) && !joystick->buttons)) {
        SDL_CloseJoystick(joystick);
        SDL_UnlockJoysticks();
        return NULL;
    }

    // If this joystick is known to have all zero centered axes, skip the auto-centering code
    if (SDL_JoystickAxesCenteredAtZero(joystick)) {
        for (int i = 0; i < joystick->naxes; ++i) {
            joystick->axes[i].has_initial_value = true;
        }
    }

    // We know the initial values for HIDAPI and XInput joysticks
    if ((SDL_IsJoystickHIDAPI(joystick->guid) ||
         SDL_IsJoystickXInput(joystick->guid) ||
         SDL_IsJoystickRAWINPUT(joystick->guid) ||
         SDL_IsJoystickWGI(joystick->guid)) &&
        joystick->naxes >= SDL_GAMEPAD_AXIS_COUNT) {
        int left_trigger, right_trigger;
        if (SDL_IsJoystickXInput(joystick->guid)) {
            left_trigger = 2;
            right_trigger = 5;
        } else {
            left_trigger = SDL_GAMEPAD_AXIS_LEFT_TRIGGER;
            right_trigger = SDL_GAMEPAD_AXIS_RIGHT_TRIGGER;
        }
        for (int i = 0; i < SDL_GAMEPAD_AXIS_COUNT; ++i) {
            int initial_value;
            if (i == left_trigger || i == right_trigger) {
                initial_value = SDL_MIN_SINT16;
            } else {
                initial_value = 0;
            }
            joystick->axes[i].value = initial_value;
            joystick->axes[i].zero = initial_value;
            joystick->axes[i].initial_value = initial_value;
            joystick->axes[i].has_initial_value = true;
        }
    }

    // Get the Steam Input API handle
    info = SDL_GetJoystickVirtualGamepadInfoForID(instance_id);
    if (info) {
        joystick->steam_handle = info->handle;
        joystick->swap_face_buttons = ShouldSwapFaceButtons(info);
    }

    // Use system gyro and accelerometer if the gamepad doesn't have built-in sensors
    if (ShouldAttemptSensorFusion(joystick, &invert_sensors)) {
        AttemptSensorFusion(joystick, invert_sensors);
    }

    // Add joystick to list
    ++joystick->ref_count;
    // Link the joystick in the list
    joystick->next = SDL_joysticks;
    SDL_joysticks = joystick;

    driver->Update(joystick);

    SDL_UnlockJoysticks();

    return joystick;
}

SDL_JoystickID SDL_AttachVirtualJoystick(const SDL_VirtualJoystickDesc *desc)
{
#ifdef SDL_JOYSTICK_VIRTUAL
    SDL_JoystickID result;

    SDL_LockJoysticks();
    result = SDL_JoystickAttachVirtualInner(desc);
    SDL_UnlockJoysticks();
    return result;
#else
    SDL_SetError("SDL not built with virtual-joystick support");
    return 0;
#endif
}

bool SDL_DetachVirtualJoystick(SDL_JoystickID instance_id)
{
#ifdef SDL_JOYSTICK_VIRTUAL
    bool result;

    SDL_LockJoysticks();
    result = SDL_JoystickDetachVirtualInner(instance_id);
    SDL_UnlockJoysticks();
    return result;
#else
    return SDL_SetError("SDL not built with virtual-joystick support");
#endif
}

bool SDL_IsJoystickVirtual(SDL_JoystickID instance_id)
{
#ifdef SDL_JOYSTICK_VIRTUAL
    SDL_JoystickDriver *driver;
    int device_index;
    bool is_virtual = false;

    SDL_LockJoysticks();
    if (SDL_GetDriverAndJoystickIndex(instance_id, &driver, &device_index)) {
        if (driver == &SDL_VIRTUAL_JoystickDriver) {
            is_virtual = true;
        }
    }
    SDL_UnlockJoysticks();

    return is_virtual;
#else
    return false;
#endif
}

bool SDL_SetJoystickVirtualAxis(SDL_Joystick *joystick, int axis, Sint16 value)
{
    bool result;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, false);
        CHECK_JOYSTICK_VIRTUAL(joystick, false);

#ifdef SDL_JOYSTICK_VIRTUAL
        result = SDL_SetJoystickVirtualAxisInner(joystick, axis, value);
#else
        result = SDL_SetError("SDL not built with virtual-joystick support");
#endif
    }
    SDL_UnlockJoysticks();

    return result;
}

bool SDL_SetJoystickVirtualBall(SDL_Joystick *joystick, int ball, Sint16 xrel, Sint16 yrel)
{
    bool result;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, false);
        CHECK_JOYSTICK_VIRTUAL(joystick, false);

#ifdef SDL_JOYSTICK_VIRTUAL
        result = SDL_SetJoystickVirtualBallInner(joystick, ball, xrel, yrel);
#else
        result = SDL_SetError("SDL not built with virtual-joystick support");
#endif
    }
    SDL_UnlockJoysticks();

    return result;
}

bool SDL_SetJoystickVirtualButton(SDL_Joystick *joystick, int button, bool down)
{
    bool result;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, false);
        CHECK_JOYSTICK_VIRTUAL(joystick, false);

#ifdef SDL_JOYSTICK_VIRTUAL
        result = SDL_SetJoystickVirtualButtonInner(joystick, button, down);
#else
        result = SDL_SetError("SDL not built with virtual-joystick support");
#endif
    }
    SDL_UnlockJoysticks();

    return result;
}

bool SDL_SetJoystickVirtualHat(SDL_Joystick *joystick, int hat, Uint8 value)
{
    bool result;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, false);
        CHECK_JOYSTICK_VIRTUAL(joystick, false);

#ifdef SDL_JOYSTICK_VIRTUAL
        result = SDL_SetJoystickVirtualHatInner(joystick, hat, value);
#else
        result = SDL_SetError("SDL not built with virtual-joystick support");
#endif
    }
    SDL_UnlockJoysticks();

    return result;
}

bool SDL_SetJoystickVirtualTouchpad(SDL_Joystick *joystick, int touchpad, int finger, bool down, float x, float y, float pressure)
{
    bool result;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, false);
        CHECK_JOYSTICK_VIRTUAL(joystick, false);

#ifdef SDL_JOYSTICK_VIRTUAL
        result = SDL_SetJoystickVirtualTouchpadInner(joystick, touchpad, finger, down, x, y, pressure);
#else
        result = SDL_SetError("SDL not built with virtual-joystick support");
#endif
    }
    SDL_UnlockJoysticks();

    return result;
}

bool SDL_SendJoystickVirtualSensorData(SDL_Joystick *joystick, SDL_SensorType type, Uint64 sensor_timestamp, const float *data, int num_values)
{
    bool result;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, false);
        CHECK_JOYSTICK_VIRTUAL(joystick, false);

#ifdef SDL_JOYSTICK_VIRTUAL
        result = SDL_SendJoystickVirtualSensorDataInner(joystick, type, sensor_timestamp, data, num_values);
#else
        result = SDL_SetError("SDL not built with virtual-joystick support");
#endif
    }
    SDL_UnlockJoysticks();

    return result;
}

/*
 * Checks to make sure the joystick is valid.
 */
bool SDL_IsJoystickValid(SDL_Joystick *joystick)
{
    SDL_AssertJoysticksLocked();
    return SDL_ObjectValid(joystick, SDL_OBJECT_TYPE_JOYSTICK);
}

bool SDL_PrivateJoystickGetAutoGamepadMapping(SDL_JoystickID instance_id, SDL_GamepadMapping *out)
{
    SDL_JoystickDriver *driver;
    int device_index;
    bool is_ok = false;

    SDL_LockJoysticks();
    if (SDL_GetDriverAndJoystickIndex(instance_id, &driver, &device_index)) {
        is_ok = driver->GetGamepadMapping(device_index, out);
    }
    SDL_UnlockJoysticks();

    return is_ok;
}

/*
 * Get the number of multi-dimensional axis controls on a joystick
 */
int SDL_GetNumJoystickAxes(SDL_Joystick *joystick)
{
    int result;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, -1);

        result = joystick->naxes;
    }
    SDL_UnlockJoysticks();

    return result;
}

/*
 * Get the number of hats on a joystick
 */
int SDL_GetNumJoystickHats(SDL_Joystick *joystick)
{
    int result;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, -1);

        result = joystick->nhats;
    }
    SDL_UnlockJoysticks();

    return result;
}

/*
 * Get the number of trackballs on a joystick
 */
int SDL_GetNumJoystickBalls(SDL_Joystick *joystick)
{
    CHECK_JOYSTICK_MAGIC(joystick, -1);

    return joystick->nballs;
}

/*
 * Get the number of buttons on a joystick
 */
int SDL_GetNumJoystickButtons(SDL_Joystick *joystick)
{
    int result;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, -1);

        result = joystick->nbuttons;
    }
    SDL_UnlockJoysticks();

    return result;
}

/*
 * Get the current state of an axis control on a joystick
 */
Sint16 SDL_GetJoystickAxis(SDL_Joystick *joystick, int axis)
{
    Sint16 state;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, 0);

        if (axis < joystick->naxes) {
            state = joystick->axes[axis].value;
        } else {
            SDL_SetError("Joystick only has %d axes", joystick->naxes);
            state = 0;
        }
    }
    SDL_UnlockJoysticks();

    return state;
}

/*
 * Get the initial state of an axis control on a joystick
 */
bool SDL_GetJoystickAxisInitialState(SDL_Joystick *joystick, int axis, Sint16 *state)
{
    bool result;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, false);

        if (axis >= joystick->naxes) {
            SDL_SetError("Joystick only has %d axes", joystick->naxes);
            result = false;
        } else {
            if (state) {
                *state = joystick->axes[axis].initial_value;
            }
            result = joystick->axes[axis].has_initial_value;
        }
    }
    SDL_UnlockJoysticks();

    return result;
}

/*
 * Get the current state of a hat on a joystick
 */
Uint8 SDL_GetJoystickHat(SDL_Joystick *joystick, int hat)
{
    Uint8 state;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, 0);

        if (hat < joystick->nhats) {
            state = joystick->hats[hat];
        } else {
            SDL_SetError("Joystick only has %d hats", joystick->nhats);
            state = 0;
        }
    }
    SDL_UnlockJoysticks();

    return state;
}

/*
 * Get the ball axis change since the last poll
 */
bool SDL_GetJoystickBall(SDL_Joystick *joystick, int ball, int *dx, int *dy)
{
    bool result;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, false);

        if (ball < joystick->nballs) {
            if (dx) {
                *dx = joystick->balls[ball].dx;
            }
            if (dy) {
                *dy = joystick->balls[ball].dy;
            }
            joystick->balls[ball].dx = 0;
            joystick->balls[ball].dy = 0;
            result = true;
        } else {
            result = SDL_SetError("Joystick only has %d balls", joystick->nballs);
        }
    }
    SDL_UnlockJoysticks();

    return result;
}

/*
 * Get the current state of a button on a joystick
 */
bool SDL_GetJoystickButton(SDL_Joystick *joystick, int button)
{
    bool down = false;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, false);

        if (button < joystick->nbuttons) {
            down = joystick->buttons[button];
        } else {
            SDL_SetError("Joystick only has %d buttons", joystick->nbuttons);
        }
    }
    SDL_UnlockJoysticks();

    return down;
}

/*
 * Return if the joystick in question is currently attached to the system,
 *  \return false if not plugged in, true if still present.
 */
bool SDL_JoystickConnected(SDL_Joystick *joystick)
{
    bool result;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, false);

        result = joystick->attached;
    }
    SDL_UnlockJoysticks();

    return result;
}

/*
 * Get the instance id for this opened joystick
 */
SDL_JoystickID SDL_GetJoystickID(SDL_Joystick *joystick)
{
    SDL_JoystickID result;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, 0);

        result = joystick->instance_id;
    }
    SDL_UnlockJoysticks();

    return result;
}

/*
 * Return the SDL_Joystick associated with an instance id.
 */
SDL_Joystick *SDL_GetJoystickFromID(SDL_JoystickID instance_id)
{
    SDL_Joystick *joystick;

    SDL_LockJoysticks();
    for (joystick = SDL_joysticks; joystick; joystick = joystick->next) {
        if (joystick->instance_id == instance_id) {
            break;
        }
    }
    SDL_UnlockJoysticks();
    return joystick;
}

/**
 * Return the SDL_Joystick associated with a player index.
 */
SDL_Joystick *SDL_GetJoystickFromPlayerIndex(int player_index)
{
    SDL_JoystickID instance_id;
    SDL_Joystick *joystick;

    SDL_LockJoysticks();
    instance_id = SDL_GetJoystickIDForPlayerIndex(player_index);
    for (joystick = SDL_joysticks; joystick; joystick = joystick->next) {
        if (joystick->instance_id == instance_id) {
            break;
        }
    }
    SDL_UnlockJoysticks();
    return joystick;
}

/*
 * Get the properties associated with a joystick
 */
SDL_PropertiesID SDL_GetJoystickProperties(SDL_Joystick *joystick)
{
    SDL_PropertiesID result;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, 0);

        if (joystick->props == 0) {
            joystick->props = SDL_CreateProperties();
        }
        result = joystick->props;
    }
    SDL_UnlockJoysticks();

    return result;
}

/*
 * Get the friendly name of this joystick
 */
const char *SDL_GetJoystickName(SDL_Joystick *joystick)
{
    const char *result;
    const SDL_SteamVirtualGamepadInfo *info;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, NULL);

        info = SDL_GetJoystickVirtualGamepadInfoForID(joystick->instance_id);
        if (info) {
            result = SDL_GetPersistentString(info->name);
        } else {
            result = SDL_GetPersistentString(joystick->name);
        }
    }
    SDL_UnlockJoysticks();

    return result;
}

/*
 * Get the implementation dependent path of this joystick
 */
const char *SDL_GetJoystickPath(SDL_Joystick *joystick)
{
    const char *result;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, NULL);

        if (joystick->path) {
            result = SDL_GetPersistentString(joystick->path);
        } else {
            SDL_Unsupported();
            result = NULL;
        }
    }
    SDL_UnlockJoysticks();

    return result;
}

/**
 *  Get the player index of an opened joystick, or -1 if it's not available
 */
int SDL_GetJoystickPlayerIndex(SDL_Joystick *joystick)
{
    int result;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, -1);

        result = SDL_GetPlayerIndexForJoystickID(joystick->instance_id);
    }
    SDL_UnlockJoysticks();

    return result;
}

/**
 *  Set the player index of an opened joystick
 */
bool SDL_SetJoystickPlayerIndex(SDL_Joystick *joystick, int player_index)
{
    bool result;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, false);

        result = SDL_SetJoystickIDForPlayerIndex(player_index, joystick->instance_id);
    }
    SDL_UnlockJoysticks();

    return result;
}

bool SDL_RumbleJoystick(SDL_Joystick *joystick, Uint16 low_frequency_rumble, Uint16 high_frequency_rumble, Uint32 duration_ms)
{
    bool result;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, false);

        if (low_frequency_rumble == joystick->low_frequency_rumble &&
            high_frequency_rumble == joystick->high_frequency_rumble) {
            // Just update the expiration
            result = true;
        } else {
            result = joystick->driver->Rumble(joystick, low_frequency_rumble, high_frequency_rumble);
            if (result) {
                joystick->rumble_resend = SDL_GetTicks() + SDL_RUMBLE_RESEND_MS;
                if (joystick->rumble_resend == 0) {
                    joystick->rumble_resend = 1;
                }
            } else {
                joystick->rumble_resend = 0;
            }
        }

        if (result) {
            joystick->low_frequency_rumble = low_frequency_rumble;
            joystick->high_frequency_rumble = high_frequency_rumble;

            if ((low_frequency_rumble || high_frequency_rumble) && duration_ms) {
                joystick->rumble_expiration = SDL_GetTicks() + SDL_min(duration_ms, SDL_MAX_RUMBLE_DURATION_MS);
                if (!joystick->rumble_expiration) {
                    joystick->rumble_expiration = 1;
                }
            } else {
                joystick->rumble_expiration = 0;
                joystick->rumble_resend = 0;
            }
        }
    }
    SDL_UnlockJoysticks();

    return result;
}

bool SDL_RumbleJoystickTriggers(SDL_Joystick *joystick, Uint16 left_rumble, Uint16 right_rumble, Uint32 duration_ms)
{
    bool result;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, false);

        if (left_rumble == joystick->left_trigger_rumble && right_rumble == joystick->right_trigger_rumble) {
            // Just update the expiration
            result = true;
        } else {
            result = joystick->driver->RumbleTriggers(joystick, left_rumble, right_rumble);
            if (result) {
                joystick->trigger_rumble_resend = SDL_GetTicks() + SDL_RUMBLE_RESEND_MS;
                if (joystick->trigger_rumble_resend == 0) {
                    joystick->trigger_rumble_resend = 1;
                }
            } else {
                joystick->trigger_rumble_resend = 0;
            }
        }

        if (result) {
            joystick->left_trigger_rumble = left_rumble;
            joystick->right_trigger_rumble = right_rumble;

            if ((left_rumble || right_rumble) && duration_ms) {
                joystick->trigger_rumble_expiration = SDL_GetTicks() + SDL_min(duration_ms, SDL_MAX_RUMBLE_DURATION_MS);
            } else {
                joystick->trigger_rumble_expiration = 0;
                joystick->trigger_rumble_resend = 0;
            }
        }
    }
    SDL_UnlockJoysticks();

    return result;
}

bool SDL_SetJoystickLED(SDL_Joystick *joystick, Uint8 red, Uint8 green, Uint8 blue)
{
    bool result;
    bool isfreshvalue;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, false);

        isfreshvalue = red != joystick->led_red ||
                       green != joystick->led_green ||
                       blue != joystick->led_blue;

        if (isfreshvalue || SDL_GetTicks() >= joystick->led_expiration) {
            result = joystick->driver->SetLED(joystick, red, green, blue);
            joystick->led_expiration = SDL_GetTicks() + SDL_LED_MIN_REPEAT_MS;
        } else {
            // Avoid spamming the driver
            result = true;
        }

        // Save the LED value regardless of success, so we don't spam the driver
        joystick->led_red = red;
        joystick->led_green = green;
        joystick->led_blue = blue;
    }
    SDL_UnlockJoysticks();

    return result;
}

bool SDL_SendJoystickEffect(SDL_Joystick *joystick, const void *data, int size)
{
    bool result;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, false);

        result = joystick->driver->SendEffect(joystick, data, size);
    }
    SDL_UnlockJoysticks();

    return result;
}

/*
 * Close a joystick previously opened with SDL_OpenJoystick()
 */
void SDL_CloseJoystick(SDL_Joystick *joystick)
{
    SDL_Joystick *joysticklist;
    SDL_Joystick *joysticklistprev;
    int i;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick,);

        // First decrement ref count
        if (--joystick->ref_count > 0) {
            SDL_UnlockJoysticks();
            return;
        }

        SDL_DestroyProperties(joystick->props);

        if (joystick->rumble_expiration) {
            SDL_RumbleJoystick(joystick, 0, 0, 0);
        }
        if (joystick->trigger_rumble_expiration) {
            SDL_RumbleJoystickTriggers(joystick, 0, 0, 0);
        }

        CleanupSensorFusion(joystick);

        joystick->driver->Close(joystick);
        joystick->hwdata = NULL;
        SDL_SetObjectValid(joystick, SDL_OBJECT_TYPE_JOYSTICK, false);

        joysticklist = SDL_joysticks;
        joysticklistprev = NULL;
        while (joysticklist) {
            if (joystick == joysticklist) {
                if (joysticklistprev) {
                    // unlink this entry
                    joysticklistprev->next = joysticklist->next;
                } else {
                    SDL_joysticks = joystick->next;
                }
                break;
            }
            joysticklistprev = joysticklist;
            joysticklist = joysticklist->next;
        }

        // Free the data associated with this joystick
        SDL_free(joystick->name);
        SDL_free(joystick->path);
        SDL_free(joystick->serial);
        SDL_free(joystick->axes);
        SDL_free(joystick->balls);
        SDL_free(joystick->hats);
        SDL_free(joystick->buttons);
        for (i = 0; i < joystick->ntouchpads; i++) {
            SDL_JoystickTouchpadInfo *touchpad = &joystick->touchpads[i];
            SDL_free(touchpad->fingers);
        }
        SDL_free(joystick->touchpads);
        SDL_free(joystick->sensors);
        SDL_free(joystick);
    }
    SDL_UnlockJoysticks();
}

void SDL_QuitJoysticks(void)
{
    int i;
    SDL_JoystickID *joysticks;

    SDL_LockJoysticks();

    SDL_joysticks_quitting = true;

    joysticks = SDL_GetJoysticks(NULL);
    if (joysticks) {
        for (i = 0; joysticks[i]; ++i) {
            SDL_PrivateJoystickRemoved(joysticks[i]);
        }
        SDL_free(joysticks);
    }

    while (SDL_joysticks) {
        SDL_joysticks->ref_count = 1;
        SDL_CloseJoystick(SDL_joysticks);
    }

    // Quit drivers in reverse order to avoid breaking dependencies between drivers
    for (i = SDL_arraysize(SDL_joystick_drivers) - 1; i >= 0; --i) {
        SDL_joystick_drivers[i]->Quit();
    }

    if (SDL_joystick_players) {
        SDL_free(SDL_joystick_players);
        SDL_joystick_players = NULL;
        SDL_joystick_player_count = 0;
    }

    SDL_QuitSubSystem(SDL_INIT_EVENTS);

    SDL_QuitSteamVirtualGamepadInfo();

    SDL_RemoveHintCallback(SDL_HINT_JOYSTICK_ALLOW_BACKGROUND_EVENTS,
                        SDL_JoystickAllowBackgroundEventsChanged, NULL);

    SDL_FreeVIDPIDList(&old_xboxone_controllers);
    SDL_FreeVIDPIDList(&arcadestick_devices);
    SDL_FreeVIDPIDList(&blacklist_devices);
    SDL_FreeVIDPIDList(&flightstick_devices);
    SDL_FreeVIDPIDList(&gamecube_devices);
    SDL_FreeVIDPIDList(&rog_gamepad_mice);
    SDL_FreeVIDPIDList(&throttle_devices);
    SDL_FreeVIDPIDList(&wheel_devices);
    SDL_FreeVIDPIDList(&zero_centered_devices);

    SDL_QuitGamepadMappings();

    SDL_joysticks_quitting = false;
    SDL_joysticks_initialized = false;

    SDL_UnlockJoysticks();
}

static bool SDL_PrivateJoystickShouldIgnoreEvent(void)
{
    if (SDL_joystick_allows_background_events) {
        return false;
    }

    if (SDL_HasWindows() && SDL_GetKeyboardFocus() == NULL) {
        // We have windows but we don't have focus, ignore the event.
        return true;
    }
    return false;
}

// These are global for SDL_sysjoystick.c and SDL_events.c

void SDL_PrivateJoystickAddTouchpad(SDL_Joystick *joystick, int nfingers)
{
    int ntouchpads;
    SDL_JoystickTouchpadInfo *touchpads;

    SDL_AssertJoysticksLocked();

    ntouchpads = joystick->ntouchpads + 1;
    touchpads = (SDL_JoystickTouchpadInfo *)SDL_realloc(joystick->touchpads, (ntouchpads * sizeof(SDL_JoystickTouchpadInfo)));
    if (touchpads) {
        SDL_JoystickTouchpadInfo *touchpad = &touchpads[ntouchpads - 1];
        SDL_JoystickTouchpadFingerInfo *fingers = (SDL_JoystickTouchpadFingerInfo *)SDL_calloc(nfingers, sizeof(SDL_JoystickTouchpadFingerInfo));

        if (fingers) {
            touchpad->nfingers = nfingers;
            touchpad->fingers = fingers;
        } else {
            // Out of memory, this touchpad won't be active
            touchpad->nfingers = 0;
            touchpad->fingers = NULL;
        }

        joystick->ntouchpads = ntouchpads;
        joystick->touchpads = touchpads;
    }
}

void SDL_PrivateJoystickAddSensor(SDL_Joystick *joystick, SDL_SensorType type, float rate)
{
    int nsensors;
    SDL_JoystickSensorInfo *sensors;

    SDL_AssertJoysticksLocked();

    nsensors = joystick->nsensors + 1;
    sensors = (SDL_JoystickSensorInfo *)SDL_realloc(joystick->sensors, (nsensors * sizeof(SDL_JoystickSensorInfo)));
    if (sensors) {
        SDL_JoystickSensorInfo *sensor = &sensors[nsensors - 1];

        SDL_zerop(sensor);
        sensor->type = type;
        sensor->rate = rate;

        joystick->nsensors = nsensors;
        joystick->sensors = sensors;
    }
}

void SDL_PrivateJoystickSensorRate(SDL_Joystick *joystick, SDL_SensorType type, float rate)
{
    int i;
    SDL_AssertJoysticksLocked();

    for (i = 0; i < joystick->nsensors; ++i) {
        if (joystick->sensors[i].type == type) {
            joystick->sensors[i].rate = rate;
        }
    }
}

void SDL_PrivateJoystickAdded(SDL_JoystickID instance_id)
{
    SDL_JoystickDriver *driver;
    int device_index;
    int player_index = -1;
    bool is_gamepad;

    SDL_AssertJoysticksLocked();

    if (SDL_JoysticksQuitting()) {
        return;
    }

    SDL_joystick_being_added = true;

    if (SDL_GetDriverAndJoystickIndex(instance_id, &driver, &device_index)) {
        player_index = driver->GetDeviceSteamVirtualGamepadSlot(device_index);
        if (player_index < 0) {
            player_index = driver->GetDevicePlayerIndex(device_index);
        }
    }
    if (player_index < 0 && SDL_IsGamepad(instance_id)) {
        player_index = SDL_FindFreePlayerIndex();
    }
    if (player_index >= 0) {
        SDL_SetJoystickIDForPlayerIndex(player_index, instance_id);
    }

    {
        SDL_Event event;

        event.type = SDL_EVENT_JOYSTICK_ADDED;
        event.common.timestamp = 0;

        if (SDL_EventEnabled(event.type)) {
            event.jdevice.which = instance_id;
            SDL_PushEvent(&event);
        }
    }

    // This might create an automatic gamepad mapping, so wait to send the event
    is_gamepad = SDL_IsGamepad(instance_id);

    SDL_joystick_being_added = false;

    if (is_gamepad) {
        SDL_PrivateGamepadAdded(instance_id);
    }
}

bool SDL_IsJoystickBeingAdded(void)
{
    return SDL_joystick_being_added;
}

void SDL_PrivateJoystickForceRecentering(SDL_Joystick *joystick)
{
    Uint8 i, j;
    Uint64 timestamp = SDL_GetTicksNS();

    SDL_AssertJoysticksLocked();

    // Tell the app that everything is centered/unpressed...
    for (i = 0; i < joystick->naxes; i++) {
        if (joystick->axes[i].has_initial_value) {
            SDL_SendJoystickAxis(timestamp, joystick, i, joystick->axes[i].zero);
        }
    }

    for (i = 0; i < joystick->nbuttons; i++) {
        SDL_SendJoystickButton(timestamp, joystick, i, false);
    }

    for (i = 0; i < joystick->nhats; i++) {
        SDL_SendJoystickHat(timestamp, joystick, i, SDL_HAT_CENTERED);
    }

    for (i = 0; i < joystick->ntouchpads; i++) {
        SDL_JoystickTouchpadInfo *touchpad = &joystick->touchpads[i];

        for (j = 0; j < touchpad->nfingers; ++j) {
            SDL_SendJoystickTouchpad(timestamp, joystick, i, j, false, 0.0f, 0.0f, 0.0f);
        }
    }
}

void SDL_PrivateJoystickRemoved(SDL_JoystickID instance_id)
{
    SDL_Joystick *joystick = NULL;
    int player_index;
    SDL_Event event;

    SDL_AssertJoysticksLocked();

    // Find this joystick...
    for (joystick = SDL_joysticks; joystick; joystick = joystick->next) {
        if (joystick->instance_id == instance_id) {
            SDL_PrivateJoystickForceRecentering(joystick);
            joystick->attached = false;
            break;
        }
    }

    if (SDL_IsGamepad(instance_id)) {
        SDL_PrivateGamepadRemoved(instance_id);
    }

    event.type = SDL_EVENT_JOYSTICK_REMOVED;
    event.common.timestamp = 0;

    if (SDL_EventEnabled(event.type)) {
        event.jdevice.which = instance_id;
        SDL_PushEvent(&event);
    }

    player_index = SDL_GetPlayerIndexForJoystickID(instance_id);
    if (player_index >= 0) {
        SDL_joystick_players[player_index] = 0;
    }
}

void SDL_SendJoystickAxis(Uint64 timestamp, SDL_Joystick *joystick, Uint8 axis, Sint16 value)
{
    SDL_JoystickAxisInfo *info;

    SDL_AssertJoysticksLocked();

    // Make sure we're not getting garbage or duplicate events
    if (axis >= joystick->naxes) {
        return;
    }

    info = &joystick->axes[axis];
    if (!info->has_initial_value ||
        (!info->has_second_value && (info->initial_value <= -32767 || info->initial_value == 32767) && SDL_abs(value) < (SDL_JOYSTICK_AXIS_MAX / 4))) {
        info->initial_value = value;
        info->value = value;
        info->zero = value;
        info->has_initial_value = true;
    } else if (value == info->value && !info->sending_initial_value) {
        return;
    } else {
        info->has_second_value = true;
    }
    if (!info->sent_initial_value) {
        // Make sure we don't send motion until there's real activity on this axis
        const int MAX_ALLOWED_JITTER = SDL_JOYSTICK_AXIS_MAX / 80; // ShanWan PS3 controller needed 96
        if (SDL_abs(value - info->value) <= MAX_ALLOWED_JITTER &&
            !SDL_IsJoystickVIRTUAL(joystick->guid)) {
            return;
        }
        info->sent_initial_value = true;
        info->sending_initial_value = true;
        SDL_SendJoystickAxis(timestamp, joystick, axis, info->initial_value);
        info->sending_initial_value = false;
    }

    /* We ignore events if we don't have keyboard focus, except for centering
     * events.
     */
    if (SDL_PrivateJoystickShouldIgnoreEvent()) {
        if (info->sending_initial_value ||
            (value > info->zero && value >= info->value) ||
            (value < info->zero && value <= info->value)) {
            return;
        }
    }

    // Update internal joystick state
    SDL_assert(timestamp != 0);
    info->value = value;
    joystick->update_complete = timestamp;

    // Post the event, if desired
    if (SDL_EventEnabled(SDL_EVENT_JOYSTICK_AXIS_MOTION)) {
        SDL_Event event;
        event.type = SDL_EVENT_JOYSTICK_AXIS_MOTION;
        event.common.timestamp = timestamp;
        event.jaxis.which = joystick->instance_id;
        event.jaxis.axis = axis;
        event.jaxis.value = value;
        SDL_PushEvent(&event);
    }
}

void SDL_SendJoystickBall(Uint64 timestamp, SDL_Joystick *joystick, Uint8 ball, Sint16 xrel, Sint16 yrel)
{
    SDL_AssertJoysticksLocked();

    // Make sure we're not getting garbage events
    if (ball >= joystick->nballs) {
        return;
    }

    // We ignore events if we don't have keyboard focus.
    if (SDL_PrivateJoystickShouldIgnoreEvent()) {
        return;
    }

    // Update internal mouse state
    joystick->balls[ball].dx += xrel;
    joystick->balls[ball].dy += yrel;

    // Post the event, if desired
    if (SDL_EventEnabled(SDL_EVENT_JOYSTICK_BALL_MOTION)) {
        SDL_Event event;
        event.type = SDL_EVENT_JOYSTICK_BALL_MOTION;
        event.common.timestamp = timestamp;
        event.jball.which = joystick->instance_id;
        event.jball.ball = ball;
        event.jball.xrel = xrel;
        event.jball.yrel = yrel;
        SDL_PushEvent(&event);
    }
}

void SDL_SendJoystickHat(Uint64 timestamp, SDL_Joystick *joystick, Uint8 hat, Uint8 value)
{
    SDL_AssertJoysticksLocked();

    // Make sure we're not getting garbage or duplicate events
    if (hat >= joystick->nhats) {
        return;
    }
    if (value == joystick->hats[hat]) {
        return;
    }

    /* We ignore events if we don't have keyboard focus, except for centering
     * events.
     */
    if (SDL_PrivateJoystickShouldIgnoreEvent()) {
        if (value != SDL_HAT_CENTERED) {
            return;
        }
    }

    // Update internal joystick state
    SDL_assert(timestamp != 0);
    joystick->hats[hat] = value;
    joystick->update_complete = timestamp;

    // Post the event, if desired
    if (SDL_EventEnabled(SDL_EVENT_JOYSTICK_HAT_MOTION)) {
        SDL_Event event;
        event.type = SDL_EVENT_JOYSTICK_HAT_MOTION;
        event.common.timestamp = timestamp;
        event.jhat.which = joystick->instance_id;
        event.jhat.hat = hat;
        event.jhat.value = value;
        SDL_PushEvent(&event);
    }
}

void SDL_SendJoystickButton(Uint64 timestamp, SDL_Joystick *joystick, Uint8 button, bool down)
{
    SDL_Event event;

    SDL_AssertJoysticksLocked();

    if (down) {
        event.type = SDL_EVENT_JOYSTICK_BUTTON_DOWN;
    } else {
        event.type = SDL_EVENT_JOYSTICK_BUTTON_UP;
    }

    if (joystick->swap_face_buttons) {
        switch (button) {
        case 0:
            button = 1;
            break;
        case 1:
            button = 0;
            break;
        case 2:
            button = 3;
            break;
        case 3:
            button = 2;
            break;
        default:
            break;
        }
    }

    // Make sure we're not getting garbage or duplicate events
    if (button >= joystick->nbuttons) {
        return;
    }
    if (down == joystick->buttons[button]) {
        return;
    }

    /* We ignore events if we don't have keyboard focus, except for button
     * release. */
    if (SDL_PrivateJoystickShouldIgnoreEvent()) {
        if (down) {
            return;
        }
    }

    // Update internal joystick state
    SDL_assert(timestamp != 0);
    joystick->buttons[button] = down;
    joystick->update_complete = timestamp;

    // Post the event, if desired
    if (SDL_EventEnabled(event.type)) {
        event.common.timestamp = timestamp;
        event.jbutton.which = joystick->instance_id;
        event.jbutton.button = button;
        event.jbutton.down = down;
        SDL_PushEvent(&event);
    }
}

static void SendSteamHandleUpdateEvents(void)
{
    SDL_Joystick *joystick;
    const SDL_SteamVirtualGamepadInfo *info;

    // Check to see if any Steam handles changed
    for (joystick = SDL_joysticks; joystick; joystick = joystick->next) {
        bool changed = false;

        if (!SDL_IsGamepad(joystick->instance_id)) {
            continue;
        }

        info = SDL_GetJoystickVirtualGamepadInfoForID(joystick->instance_id);
        if (info) {
            if (joystick->steam_handle != info->handle) {
                joystick->steam_handle = info->handle;
                joystick->swap_face_buttons = ShouldSwapFaceButtons(info);
                changed = true;
            }
        } else {
            if (joystick->steam_handle != 0) {
                joystick->steam_handle = 0;
                joystick->swap_face_buttons = false;
                changed = true;
            }
        }
        if (changed) {
            SDL_Event event;

            SDL_zero(event);
            event.type = SDL_EVENT_GAMEPAD_STEAM_HANDLE_UPDATED;
            event.common.timestamp = 0;
            event.gdevice.which = joystick->instance_id;
            SDL_PushEvent(&event);
        }
    }
}

void SDL_UpdateJoysticks(void)
{
    int i;
    Uint64 now;
    SDL_Joystick *joystick;

    if (!SDL_WasInit(SDL_INIT_JOYSTICK)) {
        return;
    }

    SDL_LockJoysticks();

    if (SDL_UpdateSteamVirtualGamepadInfo()) {
        SendSteamHandleUpdateEvents();
    }

#ifdef SDL_JOYSTICK_HIDAPI
    // Special function for HIDAPI devices, as a single device can provide multiple SDL_Joysticks
    HIDAPI_UpdateDevices();
#endif // SDL_JOYSTICK_HIDAPI

    for (joystick = SDL_joysticks; joystick; joystick = joystick->next) {
        if (!joystick->attached) {
            continue;
        }

        joystick->driver->Update(joystick);

        if (joystick->delayed_guide_button) {
            SDL_GamepadHandleDelayedGuideButton(joystick);
        }

        now = SDL_GetTicks();
        if (joystick->rumble_expiration && now >= joystick->rumble_expiration) {
            SDL_RumbleJoystick(joystick, 0, 0, 0);
            joystick->rumble_resend = 0;
        }

        if (joystick->rumble_resend && now >= joystick->rumble_resend) {
            joystick->driver->Rumble(joystick, joystick->low_frequency_rumble, joystick->high_frequency_rumble);
            joystick->rumble_resend = now + SDL_RUMBLE_RESEND_MS;
            if (joystick->rumble_resend == 0) {
                joystick->rumble_resend = 1;
            }
        }

        if (joystick->trigger_rumble_expiration && now >= joystick->trigger_rumble_expiration) {
            SDL_RumbleJoystickTriggers(joystick, 0, 0, 0);
            joystick->trigger_rumble_resend = 0;
        }

        if (joystick->trigger_rumble_resend && now >= joystick->trigger_rumble_resend) {
            joystick->driver->RumbleTriggers(joystick, joystick->left_trigger_rumble, joystick->right_trigger_rumble);
            joystick->trigger_rumble_resend = now + SDL_RUMBLE_RESEND_MS;
            if (joystick->trigger_rumble_resend == 0) {
                joystick->trigger_rumble_resend = 1;
            }
        }
    }

    if (SDL_EventEnabled(SDL_EVENT_JOYSTICK_UPDATE_COMPLETE)) {
        for (joystick = SDL_joysticks; joystick; joystick = joystick->next) {
            if (joystick->update_complete) {
                SDL_Event event;

                event.type = SDL_EVENT_JOYSTICK_UPDATE_COMPLETE;
                event.common.timestamp = joystick->update_complete;
                event.jdevice.which = joystick->instance_id;
                SDL_PushEvent(&event);

                joystick->update_complete = 0;
            }
        }
    }

    /* this needs to happen AFTER walking the joystick list above, so that any
       dangling hardware data from removed devices can be free'd
     */
    for (i = 0; i < SDL_arraysize(SDL_joystick_drivers); ++i) {
        SDL_joystick_drivers[i]->Detect();
    }

    SDL_UnlockJoysticks();
}

static const Uint32 SDL_joystick_event_list[] = {
    SDL_EVENT_JOYSTICK_AXIS_MOTION,
    SDL_EVENT_JOYSTICK_BALL_MOTION,
    SDL_EVENT_JOYSTICK_HAT_MOTION,
    SDL_EVENT_JOYSTICK_BUTTON_DOWN,
    SDL_EVENT_JOYSTICK_BUTTON_UP,
    SDL_EVENT_JOYSTICK_ADDED,
    SDL_EVENT_JOYSTICK_REMOVED,
    SDL_EVENT_JOYSTICK_BATTERY_UPDATED
};

void SDL_SetJoystickEventsEnabled(bool enabled)
{
    unsigned int i;

    for (i = 0; i < SDL_arraysize(SDL_joystick_event_list); ++i) {
        SDL_SetEventEnabled(SDL_joystick_event_list[i], enabled);
    }
}

bool SDL_JoystickEventsEnabled(void)
{
    bool enabled = false;
    unsigned int i;

    for (i = 0; i < SDL_arraysize(SDL_joystick_event_list); ++i) {
        enabled = SDL_EventEnabled(SDL_joystick_event_list[i]);
        if (enabled) {
            break;
        }
    }
    return enabled;
}

void SDL_GetJoystickGUIDInfo(SDL_GUID guid, Uint16 *vendor, Uint16 *product, Uint16 *version, Uint16 *crc16)
{
    Uint16 *guid16 = (Uint16 *)guid.data;
    Uint16 bus = SDL_Swap16LE(guid16[0]);

    if ((bus < ' ' || bus == SDL_HARDWARE_BUS_VIRTUAL) && guid16[3] == 0x0000 && guid16[5] == 0x0000) {
        /* This GUID fits the standard form:
         * 16-bit bus
         * 16-bit CRC16 of the joystick name (can be zero)
         * 16-bit vendor ID
         * 16-bit zero
         * 16-bit product ID
         * 16-bit zero
         * 16-bit version
         * 8-bit driver identifier ('h' for HIDAPI, 'x' for XInput, etc.)
         * 8-bit driver-dependent type info
         */
        if (vendor) {
            *vendor = SDL_Swap16LE(guid16[2]);
        }
        if (product) {
            *product = SDL_Swap16LE(guid16[4]);
        }
        if (version) {
            *version = SDL_Swap16LE(guid16[6]);
        }
        if (crc16) {
            *crc16 = SDL_Swap16LE(guid16[1]);
        }
    } else if (bus < ' ' || bus == SDL_HARDWARE_BUS_VIRTUAL) {
        /* This GUID fits the unknown VID/PID form:
         * 16-bit bus
         * 16-bit CRC16 of the joystick name (can be zero)
         * 11 characters of the joystick name, null terminated
         */
        if (vendor) {
            *vendor = 0;
        }
        if (product) {
            *product = 0;
        }
        if (version) {
            *version = 0;
        }
        if (crc16) {
            *crc16 = SDL_Swap16LE(guid16[1]);
        }
    } else {
        if (vendor) {
            *vendor = 0;
        }
        if (product) {
            *product = 0;
        }
        if (version) {
            *version = 0;
        }
        if (crc16) {
            *crc16 = 0;
        }
    }
}

char *SDL_CreateJoystickName(Uint16 vendor, Uint16 product, const char *vendor_name, const char *product_name)
{
    const char *custom_name = GuessControllerName(vendor, product);
    if (custom_name) {
        return SDL_strdup(custom_name);
    }

    return SDL_CreateDeviceName(vendor, product, vendor_name, product_name, "Controller");
}

SDL_GUID SDL_CreateJoystickGUID(Uint16 bus, Uint16 vendor, Uint16 product, Uint16 version, const char *vendor_name, const char *product_name, Uint8 driver_signature, Uint8 driver_data)
{
    SDL_GUID guid;
    Uint16 *guid16 = (Uint16 *)guid.data;
    Uint16 crc = 0;

    SDL_zero(guid);

    if (vendor_name && *vendor_name && product_name && *product_name) {
        crc = SDL_crc16(crc, vendor_name, SDL_strlen(vendor_name));
        crc = SDL_crc16(crc, " ", 1);
        crc = SDL_crc16(crc, product_name, SDL_strlen(product_name));
    } else if (product_name) {
        crc = SDL_crc16(crc, product_name, SDL_strlen(product_name));
    }

    // We only need 16 bits for each of these; space them out to fill 128.
    // Byteswap so devices get same GUID on little/big endian platforms.
    *guid16++ = SDL_Swap16LE(bus);
    *guid16++ = SDL_Swap16LE(crc);

    if (vendor) {
        *guid16++ = SDL_Swap16LE(vendor);
        *guid16++ = 0;
        *guid16++ = SDL_Swap16LE(product);
        *guid16++ = 0;
        *guid16++ = SDL_Swap16LE(version);
        guid.data[14] = driver_signature;
        guid.data[15] = driver_data;
    } else {
        size_t available_space = sizeof(guid.data) - 4;

        if (driver_signature) {
            available_space -= 2;
            guid.data[14] = driver_signature;
            guid.data[15] = driver_data;
        }
        if (product_name) {
            SDL_strlcpy((char *)guid16, product_name, available_space);
        }
    }
    return guid;
}

SDL_GUID SDL_CreateJoystickGUIDForName(const char *name)
{
    return SDL_CreateJoystickGUID(SDL_HARDWARE_BUS_UNKNOWN, 0, 0, 0, NULL, name, 0, 0);
}

void SDL_SetJoystickGUIDVendor(SDL_GUID *guid, Uint16 vendor)
{
    Uint16 *guid16 = (Uint16 *)guid->data;

    guid16[2] = SDL_Swap16LE(vendor);
}

void SDL_SetJoystickGUIDProduct(SDL_GUID *guid, Uint16 product)
{
    Uint16 *guid16 = (Uint16 *)guid->data;

    guid16[4] = SDL_Swap16LE(product);
}

void SDL_SetJoystickGUIDVersion(SDL_GUID *guid, Uint16 version)
{
    Uint16 *guid16 = (Uint16 *)guid->data;

    guid16[6] = SDL_Swap16LE(version);
}

void SDL_SetJoystickGUIDCRC(SDL_GUID *guid, Uint16 crc)
{
    Uint16 *guid16 = (Uint16 *)guid->data;

    guid16[1] = SDL_Swap16LE(crc);
}

SDL_GamepadType SDL_GetGamepadTypeFromVIDPID(Uint16 vendor, Uint16 product, const char *name, bool forUI)
{
    SDL_GamepadType type = SDL_GAMEPAD_TYPE_STANDARD;

    if (vendor == 0x0000 && product == 0x0000) {
        // Some devices are only identifiable by their name
        if (name &&
            (SDL_strcmp(name, "Lic Pro Controller") == 0 ||
             SDL_strcmp(name, "Nintendo Wireless Gamepad") == 0 ||
             SDL_strcmp(name, "Wireless Gamepad") == 0)) {
            // HORI or PowerA Switch Pro Controller clone
            type = SDL_GAMEPAD_TYPE_NINTENDO_SWITCH_PRO;
        }

    } else if (vendor == 0x0001 && product == 0x0001) {
        type = SDL_GAMEPAD_TYPE_STANDARD;

    } else if (vendor == USB_VENDOR_NINTENDO &&
               (product == USB_PRODUCT_NINTENDO_SWITCH_JOYCON_LEFT ||
                product == USB_PRODUCT_NINTENDO_SWITCH2_JOYCON_LEFT)) {
        type = SDL_GAMEPAD_TYPE_NINTENDO_SWITCH_JOYCON_LEFT;

    } else if (vendor == USB_VENDOR_NINTENDO &&
               (product == USB_PRODUCT_NINTENDO_SWITCH_JOYCON_RIGHT ||
                product == USB_PRODUCT_NINTENDO_SWITCH2_JOYCON_RIGHT)) {
        if (name && SDL_strstr(name, "NES Controller") != NULL) {
            // We don't have a type for the Nintendo Online NES Controller
            type = SDL_GAMEPAD_TYPE_STANDARD;
        } else {
            type = SDL_GAMEPAD_TYPE_NINTENDO_SWITCH_JOYCON_RIGHT;
        }

    } else if (vendor == USB_VENDOR_NINTENDO && product == USB_PRODUCT_NINTENDO_SWITCH_JOYCON_GRIP) {
        if (name && SDL_strstr(name, "(L)") != NULL) {
            type = SDL_GAMEPAD_TYPE_NINTENDO_SWITCH_JOYCON_LEFT;
        } else {
            type = SDL_GAMEPAD_TYPE_NINTENDO_SWITCH_JOYCON_RIGHT;
        }

    } else if (vendor == USB_VENDOR_NINTENDO &&
               (product == USB_PRODUCT_NINTENDO_SWITCH_JOYCON_PAIR ||
                product == USB_PRODUCT_NINTENDO_SWITCH2_JOYCON_PAIR)) {
        type = SDL_GAMEPAD_TYPE_NINTENDO_SWITCH_JOYCON_PAIR;

    } else if (forUI && SDL_IsJoystickGameCube(vendor, product)) {
        type = SDL_GAMEPAD_TYPE_GAMECUBE;

    } else {
        switch (GuessControllerType(vendor, product)) {
        case k_eControllerType_XBox360Controller:
            type = SDL_GAMEPAD_TYPE_XBOX360;
            break;
        case k_eControllerType_XBoxOneController:
            type = SDL_GAMEPAD_TYPE_XBOXONE;
            break;
        case k_eControllerType_PS3Controller:
            type = SDL_GAMEPAD_TYPE_PS3;
            break;
        case k_eControllerType_PS4Controller:
            type = SDL_GAMEPAD_TYPE_PS4;
            break;
        case k_eControllerType_PS5Controller:
            type = SDL_GAMEPAD_TYPE_PS5;
            break;
        case k_eControllerType_XInputPS4Controller:
            if (forUI) {
                type = SDL_GAMEPAD_TYPE_PS4;
            } else {
                type = SDL_GAMEPAD_TYPE_STANDARD;
            }
            break;
        case k_eControllerType_SwitchProController:
        case k_eControllerType_SwitchInputOnlyController:
            type = SDL_GAMEPAD_TYPE_NINTENDO_SWITCH_PRO;
            break;
        case k_eControllerType_XInputSwitchController:
            if (forUI) {
                type = SDL_GAMEPAD_TYPE_NINTENDO_SWITCH_PRO;
            } else {
                type = SDL_GAMEPAD_TYPE_STANDARD;
            }
            break;
        default:
            break;
        }
    }
    return type;
}

SDL_GamepadType SDL_GetGamepadTypeFromGUID(SDL_GUID guid, const char *name)
{
    SDL_GamepadType type;
    Uint16 vendor, product;

    SDL_GetJoystickGUIDInfo(guid, &vendor, &product, NULL, NULL);
    type = SDL_GetGamepadTypeFromVIDPID(vendor, product, name, true);
    if (type == SDL_GAMEPAD_TYPE_STANDARD) {
        if (SDL_IsJoystickXInput(guid)) {
            // This is probably an Xbox One controller
            return SDL_GAMEPAD_TYPE_XBOXONE;
        }
#ifdef SDL_JOYSTICK_HIDAPI
        if (SDL_IsJoystickHIDAPI(guid)) {
            return HIDAPI_GetGamepadTypeFromGUID(guid);
        }
#endif // SDL_JOYSTICK_HIDAPI
    }
    return type;
}

bool SDL_JoystickGUIDUsesVersion(SDL_GUID guid)
{
    Uint16 vendor, product;

    if (SDL_IsJoystickMFI(guid)) {
        // The version bits are used as button capability mask
        return false;
    }

    SDL_GetJoystickGUIDInfo(guid, &vendor, &product, NULL, NULL);
    if (vendor && product) {
        return true;
    }
    return false;
}

bool SDL_IsJoystickXboxOne(Uint16 vendor_id, Uint16 product_id)
{
    EControllerType eType = GuessControllerType(vendor_id, product_id);
    return eType == k_eControllerType_XBoxOneController;
}

bool SDL_IsJoystickXboxOneElite(Uint16 vendor_id, Uint16 product_id)
{
    if (vendor_id == USB_VENDOR_MICROSOFT) {
        if (product_id == USB_PRODUCT_XBOX_ONE_ELITE_SERIES_1 ||
            product_id == USB_PRODUCT_XBOX_ONE_ELITE_SERIES_2 ||
            product_id == USB_PRODUCT_XBOX_ONE_ELITE_SERIES_2_BLUETOOTH ||
            product_id == USB_PRODUCT_XBOX_ONE_ELITE_SERIES_2_BLE) {
            return true;
        }
    }
    return false;
}

bool SDL_IsJoystickXboxSeriesX(Uint16 vendor_id, Uint16 product_id)
{
    // Most new controllers have the share button, so we'll default to true and
    // have a list of older XBox One controllers that are known not to have it.
    if (SDL_VIDPIDInList(vendor_id, product_id, &old_xboxone_controllers)) {
        return false;
    }
    return true;
}

bool SDL_IsJoystickBluetoothXboxOne(Uint16 vendor_id, Uint16 product_id)
{
    if (vendor_id == USB_VENDOR_MICROSOFT) {
        if (product_id == USB_PRODUCT_XBOX_ONE_ADAPTIVE_BLUETOOTH ||
            product_id == USB_PRODUCT_XBOX_ONE_ADAPTIVE_BLE ||
            product_id == USB_PRODUCT_XBOX_ONE_S_REV1_BLUETOOTH ||
            product_id == USB_PRODUCT_XBOX_ONE_S_REV2_BLUETOOTH ||
            product_id == USB_PRODUCT_XBOX_ONE_S_REV2_BLE ||
            product_id == USB_PRODUCT_XBOX_ONE_ELITE_SERIES_2_BLUETOOTH ||
            product_id == USB_PRODUCT_XBOX_ONE_ELITE_SERIES_2_BLE ||
            product_id == USB_PRODUCT_XBOX_SERIES_X_BLE) {
            return true;
        }
    }
    return false;
}

bool SDL_IsJoystickPS4(Uint16 vendor_id, Uint16 product_id)
{
    EControllerType eType = GuessControllerType(vendor_id, product_id);
    return eType == k_eControllerType_PS4Controller;
}

bool SDL_IsJoystickPS5(Uint16 vendor_id, Uint16 product_id)
{
    EControllerType eType = GuessControllerType(vendor_id, product_id);
    return eType == k_eControllerType_PS5Controller;
}

bool SDL_IsJoystickDualSenseEdge(Uint16 vendor_id, Uint16 product_id)
{
    if (vendor_id == USB_VENDOR_SONY) {
        if (product_id == USB_PRODUCT_SONY_DS5_EDGE) {
            return true;
        }
    }
    return false;
}

bool SDL_IsJoystickNintendoSwitchPro(Uint16 vendor_id, Uint16 product_id)
{
    EControllerType eType = GuessControllerType(vendor_id, product_id);
    return eType == k_eControllerType_SwitchProController || eType == k_eControllerType_SwitchInputOnlyController;
}

bool SDL_IsJoystickNintendoSwitchProInputOnly(Uint16 vendor_id, Uint16 product_id)
{
    EControllerType eType = GuessControllerType(vendor_id, product_id);
    return eType == k_eControllerType_SwitchInputOnlyController;
}

bool SDL_IsJoystickNintendoSwitchJoyCon(Uint16 vendor_id, Uint16 product_id)
{
    EControllerType eType = GuessControllerType(vendor_id, product_id);
    return eType == k_eControllerType_SwitchJoyConLeft || eType == k_eControllerType_SwitchJoyConRight;
}

bool SDL_IsJoystickNintendoSwitchJoyConLeft(Uint16 vendor_id, Uint16 product_id)
{
    EControllerType eType = GuessControllerType(vendor_id, product_id);
    return eType == k_eControllerType_SwitchJoyConLeft;
}

bool SDL_IsJoystickNintendoSwitchJoyConRight(Uint16 vendor_id, Uint16 product_id)
{
    EControllerType eType = GuessControllerType(vendor_id, product_id);
    return eType == k_eControllerType_SwitchJoyConRight;
}

bool SDL_IsJoystickNintendoSwitchJoyConGrip(Uint16 vendor_id, Uint16 product_id)
{
    return vendor_id == USB_VENDOR_NINTENDO && product_id == USB_PRODUCT_NINTENDO_SWITCH_JOYCON_GRIP;
}

bool SDL_IsJoystickNintendoSwitchJoyConPair(Uint16 vendor_id, Uint16 product_id)
{
    return vendor_id == USB_VENDOR_NINTENDO &&
           (product_id == USB_PRODUCT_NINTENDO_SWITCH_JOYCON_PAIR ||
            product_id == USB_PRODUCT_NINTENDO_SWITCH2_JOYCON_PAIR);
}

bool SDL_IsJoystickGameCube(Uint16 vendor_id, Uint16 product_id)
{
    return SDL_VIDPIDInList(vendor_id, product_id, &gamecube_devices);
}

bool SDL_IsJoystickAmazonLunaController(Uint16 vendor_id, Uint16 product_id)
{
    return ((vendor_id == USB_VENDOR_AMAZON && product_id == USB_PRODUCT_AMAZON_LUNA_CONTROLLER) ||
            (vendor_id == BLUETOOTH_VENDOR_AMAZON && product_id == BLUETOOTH_PRODUCT_LUNA_CONTROLLER));
}

bool SDL_IsJoystickGoogleStadiaController(Uint16 vendor_id, Uint16 product_id)
{
    return vendor_id == USB_VENDOR_GOOGLE && product_id == USB_PRODUCT_GOOGLE_STADIA_CONTROLLER;
}

bool SDL_IsJoystickNVIDIASHIELDController(Uint16 vendor_id, Uint16 product_id)
{
    return (vendor_id == USB_VENDOR_NVIDIA &&
            (product_id == USB_PRODUCT_NVIDIA_SHIELD_CONTROLLER_V103 ||
             product_id == USB_PRODUCT_NVIDIA_SHIELD_CONTROLLER_V104));
}

bool SDL_IsJoystickSteamVirtualGamepad(Uint16 vendor_id, Uint16 product_id, Uint16 version)
{
#ifdef SDL_PLATFORM_MACOS
    return (vendor_id == USB_VENDOR_MICROSOFT && product_id == USB_PRODUCT_XBOX360_WIRED_CONTROLLER && version == 0);
#else
    return (vendor_id == USB_VENDOR_VALVE && product_id == USB_PRODUCT_STEAM_VIRTUAL_GAMEPAD);
#endif
}

bool SDL_IsJoystickSteamController(Uint16 vendor_id, Uint16 product_id)
{
    EControllerType eType = GuessControllerType(vendor_id, product_id);
    return eType == k_eControllerType_SteamController || eType == k_eControllerType_SteamControllerV2;
}

bool SDL_IsJoystickHoriSteamController(Uint16 vendor_id, Uint16 product_id)
{
    return vendor_id == USB_VENDOR_HORI && (product_id == USB_PRODUCT_HORI_STEAM_CONTROLLER || product_id == USB_PRODUCT_HORI_STEAM_CONTROLLER_BT);
}

bool SDL_IsJoystickSInputController(Uint16 vendor_id, Uint16 product_id)
{
    if (vendor_id == USB_VENDOR_RASPBERRYPI) {
        if (product_id == USB_PRODUCT_HANDHELDLEGEND_SINPUT_GENERIC ||
            product_id == USB_PRODUCT_HANDHELDLEGEND_PROGCC ||
            product_id == USB_PRODUCT_HANDHELDLEGEND_GCULTIMATE ||
            product_id == USB_PRODUCT_BONZIRICHANNEL_FIREBIRD ||
            product_id == USB_PRODUCT_VOIDGAMING_PS4FIREBIRD) {
            return true;
        }
    }
    return false;
}

bool SDL_IsJoystickFlydigiController(Uint16 vendor_id, Uint16 product_id)
{
    return vendor_id == USB_VENDOR_FLYDIGI && product_id == USB_PRODUCT_FLYDIGI_GAMEPAD;
}

bool SDL_IsJoystickSteamDeck(Uint16 vendor_id, Uint16 product_id)
{
    EControllerType eType = GuessControllerType(vendor_id, product_id);
    return eType == k_eControllerType_SteamControllerNeptune;
}

bool SDL_IsJoystickXInput(SDL_GUID guid)
{
    return (guid.data[14] == 'x') ? true : false;
}

bool SDL_IsJoystickWGI(SDL_GUID guid)
{
    return (guid.data[14] == 'w') ? true : false;
}

bool SDL_IsJoystickHIDAPI(SDL_GUID guid)
{
    return (guid.data[14] == 'h') ? true : false;
}

bool SDL_IsJoystickMFI(SDL_GUID guid)
{
    return (guid.data[14] == 'm') ? true : false;
}

bool SDL_IsJoystickRAWINPUT(SDL_GUID guid)
{
    return (guid.data[14] == 'r') ? true : false;
}

bool SDL_IsJoystickVIRTUAL(SDL_GUID guid)
{
    return (guid.data[14] == 'v') ? true : false;
}

bool SDL_IsJoystickWheel(Uint16 vendor_id, Uint16 product_id)
{
    return SDL_VIDPIDInList(vendor_id, product_id, &wheel_devices);
}

static bool SDL_IsJoystickArcadeStick(Uint16 vendor_id, Uint16 product_id)
{
    return SDL_VIDPIDInList(vendor_id, product_id, &arcadestick_devices);
}

static bool SDL_IsJoystickFlightStick(Uint16 vendor_id, Uint16 product_id)
{
    return SDL_VIDPIDInList(vendor_id, product_id, &flightstick_devices);
}

static bool SDL_IsJoystickThrottle(Uint16 vendor_id, Uint16 product_id)
{
    return SDL_VIDPIDInList(vendor_id, product_id, &throttle_devices);
}

static SDL_JoystickType SDL_GetJoystickGUIDType(SDL_GUID guid)
{
    Uint16 vendor;
    Uint16 product;

    SDL_GetJoystickGUIDInfo(guid, &vendor, &product, NULL, NULL);

    if (SDL_IsJoystickWheel(vendor, product)) {
        return SDL_JOYSTICK_TYPE_WHEEL;
    }

    if (SDL_IsJoystickArcadeStick(vendor, product)) {
        return SDL_JOYSTICK_TYPE_ARCADE_STICK;
    }

    if (SDL_IsJoystickFlightStick(vendor, product)) {
        return SDL_JOYSTICK_TYPE_FLIGHT_STICK;
    }

    if (SDL_IsJoystickThrottle(vendor, product)) {
        return SDL_JOYSTICK_TYPE_THROTTLE;
    }

    if (SDL_IsJoystickXInput(guid)) {
        // XInput GUID, get the type based on the XInput device subtype
        switch (guid.data[15]) {
        case 0x01: // XINPUT_DEVSUBTYPE_GAMEPAD
            return SDL_JOYSTICK_TYPE_GAMEPAD;
        case 0x02: // XINPUT_DEVSUBTYPE_WHEEL
            return SDL_JOYSTICK_TYPE_WHEEL;
        case 0x03: // XINPUT_DEVSUBTYPE_ARCADE_STICK
            return SDL_JOYSTICK_TYPE_ARCADE_STICK;
        case 0x04: // XINPUT_DEVSUBTYPE_FLIGHT_STICK
            return SDL_JOYSTICK_TYPE_FLIGHT_STICK;
        case 0x05: // XINPUT_DEVSUBTYPE_DANCE_PAD
            return SDL_JOYSTICK_TYPE_DANCE_PAD;
        case 0x06: // XINPUT_DEVSUBTYPE_GUITAR
        case 0x07: // XINPUT_DEVSUBTYPE_GUITAR_ALTERNATE
        case 0x0B: // XINPUT_DEVSUBTYPE_GUITAR_BASS
            return SDL_JOYSTICK_TYPE_GUITAR;
        case 0x08: // XINPUT_DEVSUBTYPE_DRUM_KIT
            return SDL_JOYSTICK_TYPE_DRUM_KIT;
        case 0x13: // XINPUT_DEVSUBTYPE_ARCADE_PAD
            return SDL_JOYSTICK_TYPE_ARCADE_PAD;
        default:
            return SDL_JOYSTICK_TYPE_UNKNOWN;
        }
    }

    if (SDL_IsJoystickWGI(guid)) {
        return (SDL_JoystickType)guid.data[15];
    }

    if (SDL_IsJoystickVIRTUAL(guid)) {
        return (SDL_JoystickType)guid.data[15];
    }

#ifdef SDL_JOYSTICK_HIDAPI
    if (SDL_IsJoystickHIDAPI(guid)) {
        return HIDAPI_GetJoystickTypeFromGUID(guid);
    }
#endif // SDL_JOYSTICK_HIDAPI

    if (GuessControllerType(vendor, product) != k_eControllerType_UnknownNonSteamController) {
        return SDL_JOYSTICK_TYPE_GAMEPAD;
    }

    return SDL_JOYSTICK_TYPE_UNKNOWN;
}

bool SDL_ShouldIgnoreJoystick(Uint16 vendor_id, Uint16 product_id, Uint16 version, const char *name)
{
    // Check the joystick blacklist
    if (SDL_VIDPIDInList(vendor_id, product_id, &blacklist_devices)) {
        return true;
    }
    if (!SDL_GetHintBoolean(SDL_HINT_JOYSTICK_ROG_CHAKRAM, false)) {
        if (SDL_VIDPIDInList(vendor_id, product_id, &rog_gamepad_mice)) {
            return true;
        }
    }

    if (SDL_ShouldIgnoreGamepad(vendor_id, product_id, version, name)) {
        return true;
    }

    return false;
}

// return the guid for this index
SDL_GUID SDL_GetJoystickGUIDForID(SDL_JoystickID instance_id)
{
    SDL_JoystickDriver *driver;
    int device_index;
    SDL_GUID guid;

    SDL_LockJoysticks();
    if (SDL_GetDriverAndJoystickIndex(instance_id, &driver, &device_index)) {
        guid = driver->GetDeviceGUID(device_index);
    } else {
        SDL_zero(guid);
    }
    SDL_UnlockJoysticks();

    return guid;
}

Uint16 SDL_GetJoystickVendorForID(SDL_JoystickID instance_id)
{
    Uint16 vendor;
    const SDL_SteamVirtualGamepadInfo *info;

    SDL_LockJoysticks();
    info = SDL_GetJoystickVirtualGamepadInfoForID(instance_id);
    if (info) {
        vendor = info->vendor_id;
    } else {
        SDL_GUID guid = SDL_GetJoystickGUIDForID(instance_id);

        SDL_GetJoystickGUIDInfo(guid, &vendor, NULL, NULL, NULL);
    }
    SDL_UnlockJoysticks();

    return vendor;
}

Uint16 SDL_GetJoystickProductForID(SDL_JoystickID instance_id)
{
    Uint16 product;
    const SDL_SteamVirtualGamepadInfo *info;

    SDL_LockJoysticks();
    info = SDL_GetJoystickVirtualGamepadInfoForID(instance_id);
    if (info) {
        product = info->product_id;
    } else {
        SDL_GUID guid = SDL_GetJoystickGUIDForID(instance_id);

        SDL_GetJoystickGUIDInfo(guid, NULL, &product, NULL, NULL);
    }
    SDL_UnlockJoysticks();

    return product;
}

Uint16 SDL_GetJoystickProductVersionForID(SDL_JoystickID instance_id)
{
    Uint16 version;
    SDL_GUID guid = SDL_GetJoystickGUIDForID(instance_id);

    SDL_GetJoystickGUIDInfo(guid, NULL, NULL, &version, NULL);
    return version;
}

SDL_JoystickType SDL_GetJoystickTypeForID(SDL_JoystickID instance_id)
{
    SDL_JoystickType type;
    SDL_GUID guid = SDL_GetJoystickGUIDForID(instance_id);

    type = SDL_GetJoystickGUIDType(guid);
    if (type == SDL_JOYSTICK_TYPE_UNKNOWN) {
        if (SDL_IsGamepad(instance_id)) {
            type = SDL_JOYSTICK_TYPE_GAMEPAD;
        }
    }
    return type;
}

SDL_GUID SDL_GetJoystickGUID(SDL_Joystick *joystick)
{
    SDL_GUID result;

    SDL_LockJoysticks();
    {
        static SDL_GUID emptyGUID;

        CHECK_JOYSTICK_MAGIC(joystick, emptyGUID);

        result = joystick->guid;
    }
    SDL_UnlockJoysticks();

    return result;
}

Uint16 SDL_GetJoystickVendor(SDL_Joystick *joystick)
{
    Uint16 vendor;
    const SDL_SteamVirtualGamepadInfo *info;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, 0);

        info = SDL_GetJoystickVirtualGamepadInfoForID(joystick->instance_id);
        if (info) {
            vendor = info->vendor_id;
        } else {
            SDL_GUID guid = SDL_GetJoystickGUID(joystick);

            SDL_GetJoystickGUIDInfo(guid, &vendor, NULL, NULL, NULL);
        }
    }
    SDL_UnlockJoysticks();

    return vendor;
}

Uint16 SDL_GetJoystickProduct(SDL_Joystick *joystick)
{
    Uint16 product;
    const SDL_SteamVirtualGamepadInfo *info;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, 0);

        info = SDL_GetJoystickVirtualGamepadInfoForID(joystick->instance_id);
        if (info) {
            product = info->product_id;
        } else {
            SDL_GUID guid = SDL_GetJoystickGUID(joystick);

            SDL_GetJoystickGUIDInfo(guid, NULL, &product, NULL, NULL);
        }
    }
    SDL_UnlockJoysticks();

    return product;
}

Uint16 SDL_GetJoystickProductVersion(SDL_Joystick *joystick)
{
    Uint16 version;
    SDL_GUID guid = SDL_GetJoystickGUID(joystick);

    SDL_GetJoystickGUIDInfo(guid, NULL, NULL, &version, NULL);
    return version;
}

Uint16 SDL_GetJoystickFirmwareVersion(SDL_Joystick *joystick)
{
    Uint16 result;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, 0);

        result = joystick->firmware_version;
    }
    SDL_UnlockJoysticks();

    return result;
}

const char *SDL_GetJoystickSerial(SDL_Joystick *joystick)
{
    const char *result;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, NULL);

        result = SDL_GetPersistentString(joystick->serial);
    }
    SDL_UnlockJoysticks();

    return result;
}

SDL_JoystickType SDL_GetJoystickType(SDL_Joystick *joystick)
{
    SDL_JoystickType type;
    SDL_GUID guid = SDL_GetJoystickGUID(joystick);

    type = SDL_GetJoystickGUIDType(guid);
    if (type == SDL_JOYSTICK_TYPE_UNKNOWN) {
        SDL_LockJoysticks();
        {
            CHECK_JOYSTICK_MAGIC(joystick, SDL_JOYSTICK_TYPE_UNKNOWN);

            if (SDL_IsGamepad(joystick->instance_id)) {
                type = SDL_JOYSTICK_TYPE_GAMEPAD;
            }
        }
        SDL_UnlockJoysticks();
    }
    return type;
}

void SDL_SendJoystickPowerInfo(SDL_Joystick *joystick, SDL_PowerState state, int percent)
{
    SDL_AssertJoysticksLocked();

    if (state != joystick->battery_state || percent != joystick->battery_percent) {
        joystick->battery_state = state;
        joystick->battery_percent = percent;

        if (SDL_EventEnabled(SDL_EVENT_JOYSTICK_BATTERY_UPDATED)) {
            SDL_Event event;
            event.type = SDL_EVENT_JOYSTICK_BATTERY_UPDATED;
            event.common.timestamp = 0;
            event.jbattery.which = joystick->instance_id;
            event.jbattery.state = state;
            event.jbattery.percent = percent;
            SDL_PushEvent(&event);
        }
    }
}

SDL_JoystickConnectionState SDL_GetJoystickConnectionState(SDL_Joystick *joystick)
{
    SDL_JoystickConnectionState result;

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, SDL_JOYSTICK_CONNECTION_INVALID);

        result = joystick->connection_state;
    }
    SDL_UnlockJoysticks();

    return result;
}

SDL_PowerState SDL_GetJoystickPowerInfo(SDL_Joystick *joystick, int *percent)
{
    SDL_PowerState result;

    if (percent) {
        *percent = -1;
    }

    SDL_LockJoysticks();
    {
        CHECK_JOYSTICK_MAGIC(joystick, SDL_POWERSTATE_ERROR);

        result = joystick->battery_state;

        if (percent) {
            *percent = joystick->battery_percent;
        }
    }
    SDL_UnlockJoysticks();

    return result;
}

void SDL_SendJoystickTouchpad(Uint64 timestamp, SDL_Joystick *joystick, int touchpad, int finger, bool down, float x, float y, float pressure)
{
    SDL_JoystickTouchpadInfo *touchpad_info;
    SDL_JoystickTouchpadFingerInfo *finger_info;
    Uint32 event_type;

    SDL_AssertJoysticksLocked();

    if (touchpad < 0 || touchpad >= joystick->ntouchpads) {
        return;
    }

    touchpad_info = &joystick->touchpads[touchpad];
    if (finger < 0 || finger >= touchpad_info->nfingers) {
        return;
    }

    finger_info = &touchpad_info->fingers[finger];

    if (!down) {
        if (x == 0.0f && y == 0.0f) {
            x = finger_info->x;
            y = finger_info->y;
        }
        pressure = 0.0f;
    }

    if (x < 0.0f) {
        x = 0.0f;
    } else if (x > 1.0f) {
        x = 1.0f;
    }
    if (y < 0.0f) {
        y = 0.0f;
    } else if (y > 1.0f) {
        y = 1.0f;
    }
    if (pressure < 0.0f) {
        pressure = 0.0f;
    } else if (pressure > 1.0f) {
        pressure = 1.0f;
    }

    if (down == finger_info->down) {
        if (!down ||
            (x == finger_info->x && y == finger_info->y && pressure == finger_info->pressure)) {
            return;
        }
    }

    if (down == finger_info->down) {
        event_type = SDL_EVENT_GAMEPAD_TOUCHPAD_MOTION;
    } else if (down) {
        event_type = SDL_EVENT_GAMEPAD_TOUCHPAD_DOWN;
    } else {
        event_type = SDL_EVENT_GAMEPAD_TOUCHPAD_UP;
    }

    // We ignore events if we don't have keyboard focus, except for touch release
    if (SDL_PrivateJoystickShouldIgnoreEvent()) {
        if (event_type != SDL_EVENT_GAMEPAD_TOUCHPAD_UP) {
            return;
        }
    }

    // Update internal joystick state
    SDL_assert(timestamp != 0);
    finger_info->down = down;
    finger_info->x = x;
    finger_info->y = y;
    finger_info->pressure = pressure;
    joystick->update_complete = timestamp;

    // Post the event, if desired
    if (SDL_EventEnabled(event_type)) {
        SDL_Event event;
        event.type = event_type;
        event.common.timestamp = timestamp;
        event.gtouchpad.which = joystick->instance_id;
        event.gtouchpad.touchpad = touchpad;
        event.gtouchpad.finger = finger;
        event.gtouchpad.x = x;
        event.gtouchpad.y = y;
        event.gtouchpad.pressure = pressure;
        SDL_PushEvent(&event);
    }
}

void SDL_SendJoystickSensor(Uint64 timestamp, SDL_Joystick *joystick, SDL_SensorType type, Uint64 sensor_timestamp, const float *data, int num_values)
{
    SDL_AssertJoysticksLocked();

    // We ignore events if we don't have keyboard focus
    if (SDL_PrivateJoystickShouldIgnoreEvent()) {
        return;
    }

    for (int i = 0; i < joystick->nsensors; ++i) {
        SDL_JoystickSensorInfo *sensor = &joystick->sensors[i];

        if (sensor->type == type) {
            if (sensor->enabled) {
                num_values = SDL_min(num_values, SDL_arraysize(sensor->data));

                // Update internal sensor state
                SDL_memcpy(sensor->data, data, num_values * sizeof(*data));
                joystick->update_complete = timestamp;

                // Post the event, if desired
                if (SDL_EventEnabled(SDL_EVENT_GAMEPAD_SENSOR_UPDATE)) {
                    SDL_Event event;
                    event.type = SDL_EVENT_GAMEPAD_SENSOR_UPDATE;
                    event.common.timestamp = timestamp;
                    event.gsensor.which = joystick->instance_id;
                    event.gsensor.sensor = type;
                    num_values = SDL_min(num_values,
                                         SDL_arraysize(event.gsensor.data));
                    SDL_memset(event.gsensor.data, 0,
                               sizeof(event.gsensor.data));
                    SDL_memcpy(event.gsensor.data, data,
                               num_values * sizeof(*data));
                    event.gsensor.sensor_timestamp = sensor_timestamp;
                    SDL_PushEvent(&event);
                }
            }
            break;
        }
    }
}

static void SDL_LoadVIDPIDListFromHint(const char *hint, int *num_entries, int *max_entries, Uint32 **entries)
{
    Uint32 entry;
    char *spot;
    char *file = NULL;

    if (hint && *hint == '@') {
        spot = file = (char *)SDL_LoadFile(hint + 1, NULL);
    } else {
        spot = (char *)hint;
    }

    if (!spot) {
        return;
    }

    while ((spot = SDL_strstr(spot, "0x")) != NULL) {
        entry = (Uint16)SDL_strtol(spot, &spot, 0);
        entry <<= 16;
        spot = SDL_strstr(spot, "0x");
        if (!spot) {
            break;
        }
        entry |= (Uint16)SDL_strtol(spot, &spot, 0);

        if (*num_entries == *max_entries) {
            int new_max_entries = *max_entries + 16;
            Uint32 *new_entries = (Uint32 *)SDL_realloc(*entries, new_max_entries * sizeof(**entries));
            if (!new_entries) {
                // Out of memory, go with what we have already
                break;
            }
            *entries = new_entries;
            *max_entries = new_max_entries;
        }
        (*entries)[(*num_entries)++] = entry;
    }

    if (file) {
        SDL_free(file);
    }
}

void SDL_LoadVIDPIDListFromHints(SDL_vidpid_list *list, const char *included_list, const char *excluded_list)
{
    // Empty the list
    list->num_included_entries = 0;
    list->num_excluded_entries = 0;

    // Add the initial entries
    if (list->num_initial_entries > 0) {
        if (list->num_included_entries < list->num_initial_entries) {
            Uint32 *entries = (Uint32 *)SDL_malloc(list->num_initial_entries * sizeof(*entries));
            if (entries) {
                SDL_memcpy(entries, list->initial_entries, list->num_initial_entries * sizeof(*entries));
                list->included_entries = entries;
                list->num_included_entries = list->num_initial_entries;
                list->max_included_entries = list->num_initial_entries;
            }
        }
    }

    // Add the included entries from the hint
    SDL_LoadVIDPIDListFromHint(included_list, &list->num_included_entries, &list->max_included_entries, &list->included_entries);

    // Add the excluded entries from the hint
    SDL_LoadVIDPIDListFromHint(excluded_list, &list->num_excluded_entries, &list->max_excluded_entries, &list->excluded_entries);
}

static void SDLCALL SDL_VIDPIDIncludedHintChanged(void *userdata, const char *name, const char *oldValue, const char *hint)
{
    SDL_vidpid_list *list = (SDL_vidpid_list *)userdata;
    const char *included_list = hint;
    const char *excluded_list = NULL;

    if (!list->initialized) {
        return;
    }

    if (list->excluded_hint_name) {
        excluded_list = SDL_GetHint(list->excluded_hint_name);
    }
    SDL_LoadVIDPIDListFromHints(list, included_list, excluded_list);
}

static void SDLCALL SDL_VIDPIDExcludedHintChanged(void *userdata, const char *name, const char *oldValue, const char *hint)
{
    SDL_vidpid_list *list = (SDL_vidpid_list *)userdata;
    const char *included_list = NULL;
    const char *excluded_list = hint;

    if (!list->initialized) {
        return;
    }

    if (list->included_hint_name) {
        included_list = SDL_GetHint(list->included_hint_name);
    }
    SDL_LoadVIDPIDListFromHints(list, included_list, excluded_list);
}

void SDL_LoadVIDPIDList(SDL_vidpid_list *list)
{
    const char *included_list = NULL;
    const char *excluded_list = NULL;

    if (list->included_hint_name) {
        SDL_AddHintCallback(list->included_hint_name, SDL_VIDPIDIncludedHintChanged, list);
    }

    if (list->excluded_hint_name) {
        SDL_AddHintCallback(list->excluded_hint_name, SDL_VIDPIDExcludedHintChanged, list);
    }

    list->initialized = true;

    if (list->included_hint_name) {
        included_list = SDL_GetHint(list->included_hint_name);
    }
    if (list->excluded_hint_name) {
        excluded_list = SDL_GetHint(list->excluded_hint_name);
    }
    SDL_LoadVIDPIDListFromHints(list, included_list, excluded_list);
}

bool SDL_VIDPIDInList(Uint16 vendor_id, Uint16 product_id, const SDL_vidpid_list *list)
{
    int i;
    Uint32 vidpid = MAKE_VIDPID(vendor_id, product_id);

    for (i = 0; i < list->num_excluded_entries; ++i) {
        if (vidpid == list->excluded_entries[i]) {
            return false;
        }
    }
    for (i = 0; i < list->num_included_entries; ++i) {
        if (vidpid == list->included_entries[i]) {
            return true;
        }
    }
    return false;
}

void SDL_FreeVIDPIDList(SDL_vidpid_list *list)
{
    if (list->included_hint_name) {
        SDL_RemoveHintCallback(list->included_hint_name, SDL_VIDPIDIncludedHintChanged, list);
    }

    if (list->excluded_hint_name) {
        SDL_RemoveHintCallback(list->excluded_hint_name, SDL_VIDPIDExcludedHintChanged, list);
    }

    if (list->included_entries) {
        SDL_free(list->included_entries);
        list->included_entries = NULL;
        list->num_included_entries = 0;
        list->max_included_entries = 0;
    }

    if (list->excluded_entries) {
        SDL_free(list->excluded_entries);
        list->excluded_entries = NULL;
        list->num_excluded_entries = 0;
        list->max_excluded_entries = 0;
    }

    list->initialized = false;
}
