/*
  Simple DirectMedia Layer
  Copyright (C) 1997-2026 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"

// System independent thread management routines for SDL

#include "SDL_thread_c.h"
#include "SDL_systhread.h"
#include "../SDL_error_c.h"

// The storage is local to the thread, but the IDs are global for the process

static SDL_AtomicInt SDL_tls_allocated;
static SDL_AtomicInt SDL_tls_id;

void SDL_InitTLSData(void)
{
    SDL_SYS_InitTLSData();
}

void *SDL_GetTLS(SDL_TLSID *id)
{
    SDL_TLSData *storage;
    int storage_index;

    CHECK_PARAM(id == NULL) {
        SDL_InvalidParamError("id");
        return NULL;
    }

    storage_index = SDL_GetAtomicInt(id) - 1;
    storage = SDL_SYS_GetTLSData();
    if (!storage || storage_index < 0 || storage_index >= storage->limit) {
        return NULL;
    }
    return storage->array[storage_index].data;
}

bool SDL_SetTLS(SDL_TLSID *id, const void *value, SDL_TLSDestructorCallback destructor)
{
    SDL_TLSData *storage;
    int storage_index;

    CHECK_PARAM(id == NULL) {
        return SDL_InvalidParamError("id");
    }

    /* Make sure TLS is initialized.
     * There's a race condition here if you are calling this from non-SDL threads
     * and haven't called SDL_Init() on your main thread, but such is life.
     */
    SDL_InitTLSData();

    // Get the storage index associated with the ID in a thread-safe way
    storage_index = SDL_GetAtomicInt(id) - 1;
    if (storage_index < 0) {
        int new_id = (SDL_AtomicIncRef(&SDL_tls_id) + 1);

        SDL_CompareAndSwapAtomicInt(id, 0, new_id);

        /* If there was a race condition we'll have wasted an ID, but every thread
         * will have the same storage index for this id.
         */
        storage_index = SDL_GetAtomicInt(id) - 1;
    } else {
        // Make sure we don't allocate an ID clobbering this one
        int tls_id = SDL_GetAtomicInt(&SDL_tls_id);
        while (storage_index >= tls_id) {
            if (SDL_CompareAndSwapAtomicInt(&SDL_tls_id, tls_id, storage_index + 1)) {
                break;
            }
            tls_id = SDL_GetAtomicInt(&SDL_tls_id);
        }
    }

    // Get the storage for the current thread
    storage = SDL_SYS_GetTLSData();
    if (!storage || storage_index >= storage->limit) {
        unsigned int i, oldlimit, newlimit;
        SDL_TLSData *new_storage;

        oldlimit = storage ? storage->limit : 0;
        newlimit = (storage_index + TLS_ALLOC_CHUNKSIZE);
        new_storage = (SDL_TLSData *)SDL_realloc(storage, sizeof(*storage) + newlimit * sizeof(storage->array[0]));
        if (!new_storage) {
            return false;
        }
        storage = new_storage;
        storage->limit = newlimit;
        for (i = oldlimit; i < newlimit; ++i) {
            storage->array[i].data = NULL;
            storage->array[i].destructor = NULL;
        }
        if (!SDL_SYS_SetTLSData(storage)) {
            SDL_free(storage);
            return false;
        }
        SDL_AtomicIncRef(&SDL_tls_allocated);
    }

    storage->array[storage_index].data = SDL_const_cast(void *, value);
    storage->array[storage_index].destructor = destructor;
    return true;
}

void SDL_CleanupTLS(void)
{
    SDL_TLSData *storage;

    // Cleanup the storage for the current thread
    storage = SDL_SYS_GetTLSData();
    if (storage) {
        int i;
        for (i = 0; i < storage->limit; ++i) {
            if (storage->array[i].destructor) {
                storage->array[i].destructor(storage->array[i].data);
            }
        }
        SDL_SYS_SetTLSData(NULL);
        SDL_free(storage);
        (void)SDL_AtomicDecRef(&SDL_tls_allocated);
    }
}

void SDL_QuitTLSData(void)
{
    SDL_CleanupTLS();

    if (SDL_GetAtomicInt(&SDL_tls_allocated) == 0) {
        SDL_SYS_QuitTLSData();
    } else {
        // Some thread hasn't called SDL_CleanupTLS()
    }
}

/* This is a generic implementation of thread-local storage which doesn't
   require additional OS support.

   It is not especially efficient and doesn't clean up thread-local storage
   as threads exit.  If there is a real OS that doesn't support thread-local
   storage this implementation should be improved to be production quality.
*/

typedef struct SDL_TLSEntry
{
    SDL_ThreadID thread;
    SDL_TLSData *storage;
    struct SDL_TLSEntry *next;
} SDL_TLSEntry;

static SDL_Mutex *SDL_generic_TLS_mutex;
static SDL_TLSEntry *SDL_generic_TLS;

void SDL_Generic_InitTLSData(void)
{
    if (!SDL_generic_TLS_mutex) {
        SDL_generic_TLS_mutex = SDL_CreateMutex();
    }
}

SDL_TLSData *SDL_Generic_GetTLSData(void)
{
    SDL_ThreadID thread = SDL_GetCurrentThreadID();
    SDL_TLSEntry *entry;
    SDL_TLSData *storage = NULL;

    SDL_LockMutex(SDL_generic_TLS_mutex);
    for (entry = SDL_generic_TLS; entry; entry = entry->next) {
        if (entry->thread == thread) {
            storage = entry->storage;
            break;
        }
    }
    SDL_UnlockMutex(SDL_generic_TLS_mutex);

    return storage;
}

bool SDL_Generic_SetTLSData(SDL_TLSData *data)
{
    SDL_ThreadID thread = SDL_GetCurrentThreadID();
    SDL_TLSEntry *prev, *entry;
    bool result = true;

    SDL_LockMutex(SDL_generic_TLS_mutex);
    prev = NULL;
    for (entry = SDL_generic_TLS; entry; entry = entry->next) {
        if (entry->thread == thread) {
            if (data) {
                entry->storage = data;
            } else {
                if (prev) {
                    prev->next = entry->next;
                } else {
                    SDL_generic_TLS = entry->next;
                }
                SDL_free(entry);
            }
            break;
        }
        prev = entry;
    }
    if (!entry && data) {
        entry = (SDL_TLSEntry *)SDL_malloc(sizeof(*entry));
        if (entry) {
            entry->thread = thread;
            entry->storage = data;
            entry->next = SDL_generic_TLS;
            SDL_generic_TLS = entry;
        } else {
            result = false;
        }
    }
    SDL_UnlockMutex(SDL_generic_TLS_mutex);

    return result;
}

void SDL_Generic_QuitTLSData(void)
{
    SDL_TLSEntry *entry;

    // This should have been cleaned up by the time we get here
    SDL_assert(!SDL_generic_TLS);
    if (SDL_generic_TLS) {
        SDL_LockMutex(SDL_generic_TLS_mutex);
        for (entry = SDL_generic_TLS; entry; ) {
            SDL_TLSEntry *next = entry->next;
            SDL_free(entry->storage);
            SDL_free(entry);
            entry = next;
        }
        SDL_generic_TLS = NULL;
        SDL_UnlockMutex(SDL_generic_TLS_mutex);
    }

    if (SDL_generic_TLS_mutex) {
        SDL_DestroyMutex(SDL_generic_TLS_mutex);
        SDL_generic_TLS_mutex = NULL;
    }
}

// Non-thread-safe global error variable
static SDL_error *SDL_GetStaticErrBuf(void)
{
    static SDL_error SDL_global_error;
    static char SDL_global_error_str1[128];
    static char SDL_global_error_str2[128];
    SDL_global_error.info[0].str = SDL_global_error_str1;
    SDL_global_error.info[0].len = sizeof(SDL_global_error_str1);
    SDL_global_error.info[1].str = SDL_global_error_str2;
    SDL_global_error.info[1].len = sizeof(SDL_global_error_str2);
    return &SDL_global_error;
}

#ifndef SDL_THREADS_DISABLED
static void SDLCALL SDL_FreeErrBuf(void *data)
{
    SDL_error *errbuf = (SDL_error *)data;
    if (errbuf->info[0].str) {
        errbuf->free_func(errbuf->info[0].str);
    }
    if (errbuf->info[1].str) {
        errbuf->free_func(errbuf->info[1].str);
    }
    errbuf->free_func(errbuf);
}
#endif

// Routine to get the thread-specific error variable
SDL_error *SDL_GetErrBuf(bool create)
{
#ifdef SDL_THREADS_DISABLED
    return SDL_GetStaticErrBuf();
#else
    static SDL_TLSID tls_errbuf;
    SDL_error *errbuf;

    errbuf = (SDL_error *)SDL_GetTLS(&tls_errbuf);
    if (!errbuf) {
        if (!create) {
            return NULL;
        }

        /* Get the original memory functions for this allocation because the lifetime
         * of the error buffer may span calls to SDL_SetMemoryFunctions() by the app
         */
        SDL_realloc_func realloc_func;
        SDL_free_func free_func;
        SDL_GetOriginalMemoryFunctions(NULL, NULL, &realloc_func, &free_func);

        errbuf = (SDL_error *)realloc_func(NULL, sizeof(*errbuf));
        if (!errbuf) {
            return SDL_GetStaticErrBuf();
        }
        SDL_zerop(errbuf);
        errbuf->realloc_func = realloc_func;
        errbuf->free_func = free_func;
        SDL_SetTLS(&tls_errbuf, errbuf, SDL_FreeErrBuf);
    }
    return errbuf;
#endif // SDL_THREADS_DISABLED
}

static bool ThreadValid(SDL_Thread *thread)
{
    return SDL_ObjectValid(thread, SDL_OBJECT_TYPE_THREAD);
}

void SDL_RunThread(SDL_Thread *thread)
{
    void *userdata = thread->userdata;
    int(SDLCALL *userfunc)(void *) = thread->userfunc;

    int *statusloc = &thread->status;

    // Perform any system-dependent setup - this function may not fail
    SDL_SYS_SetupThread(thread->name);

    // Run the function
    *statusloc = userfunc(userdata);

    // Clean up thread-local storage
    SDL_CleanupTLS();

    // Mark us as ready to be joined (or detached)
    if (!SDL_CompareAndSwapAtomicInt(&thread->state, SDL_THREAD_ALIVE, SDL_THREAD_COMPLETE)) {
        // Clean up if something already detached us.
        if (SDL_GetAtomicInt(&thread->state) == SDL_THREAD_DETACHED) {
            SDL_free(thread->name); // Can't free later, we've already cleaned up TLS
            SDL_free(thread);
        }
    }
}

SDL_Thread *SDL_CreateThreadWithPropertiesRuntime(SDL_PropertiesID props,
                              SDL_FunctionPointer pfnBeginThread,
                              SDL_FunctionPointer pfnEndThread)
{
    // rather than check this in every backend, just make sure it's correct upfront. Only allow non-NULL if Windows, or Microsoft GDK.
    #if !defined(SDL_PLATFORM_WINDOWS)
    if (pfnBeginThread || pfnEndThread) {
        SDL_SetError("_beginthreadex/_endthreadex not supported on this platform");
        return NULL;
    }
    #endif

    SDL_ThreadFunction fn = (SDL_ThreadFunction) SDL_GetPointerProperty(props, SDL_PROP_THREAD_CREATE_ENTRY_FUNCTION_POINTER, NULL);
    const char *name = SDL_GetStringProperty(props, SDL_PROP_THREAD_CREATE_NAME_STRING, NULL);
    const size_t stacksize = (size_t) SDL_GetNumberProperty(props, SDL_PROP_THREAD_CREATE_STACKSIZE_NUMBER, 0);
    void *userdata = SDL_GetPointerProperty(props, SDL_PROP_THREAD_CREATE_USERDATA_POINTER, NULL);

    if (!fn) {
        SDL_SetError("Thread entry function is NULL");
        return NULL;
    }

    SDL_InitMainThread();

    SDL_Thread *thread = (SDL_Thread *)SDL_calloc(1, sizeof(*thread));
    if (!thread) {
        return NULL;
    }
    thread->status = -1;
    SDL_SetAtomicInt(&thread->state, SDL_THREAD_ALIVE);

    // Set up the arguments for the thread
    if (name) {
        thread->name = SDL_strdup(name);
        if (!thread->name) {
            SDL_free(thread);
            return NULL;
        }
    }

    thread->userfunc = fn;
    thread->userdata = userdata;
    thread->stacksize = stacksize;

    SDL_SetObjectValid(thread, SDL_OBJECT_TYPE_THREAD, true);

    // Create the thread and go!
    if (!SDL_SYS_CreateThread(thread, pfnBeginThread, pfnEndThread)) {
        // Oops, failed.  Gotta free everything
        SDL_SetObjectValid(thread, SDL_OBJECT_TYPE_THREAD, false);
        SDL_free(thread->name);
        SDL_free(thread);
		return NULL;
    }

    // Everything is running now
    return thread;
}

SDL_Thread *SDL_CreateThreadRuntime(SDL_ThreadFunction fn,
                 const char *name, void *userdata,
                 SDL_FunctionPointer pfnBeginThread,
                 SDL_FunctionPointer pfnEndThread)
{
    const SDL_PropertiesID props = SDL_CreateProperties();
    SDL_SetPointerProperty(props, SDL_PROP_THREAD_CREATE_ENTRY_FUNCTION_POINTER, (void *) fn);
    SDL_SetStringProperty(props, SDL_PROP_THREAD_CREATE_NAME_STRING, name);
    SDL_SetPointerProperty(props, SDL_PROP_THREAD_CREATE_USERDATA_POINTER, userdata);
    SDL_Thread *thread = SDL_CreateThreadWithPropertiesRuntime(props, pfnBeginThread, pfnEndThread);
    SDL_DestroyProperties(props);
    return thread;
}

// internal helper function, not in the public API.
SDL_Thread *SDL_CreateThreadWithStackSize(SDL_ThreadFunction fn, const char *name, size_t stacksize, void *userdata)
{
    const SDL_PropertiesID props = SDL_CreateProperties();
    SDL_SetPointerProperty(props, SDL_PROP_THREAD_CREATE_ENTRY_FUNCTION_POINTER, (void *) fn);
    SDL_SetStringProperty(props, SDL_PROP_THREAD_CREATE_NAME_STRING, name);
    SDL_SetPointerProperty(props, SDL_PROP_THREAD_CREATE_USERDATA_POINTER, userdata);
    SDL_SetNumberProperty(props, SDL_PROP_THREAD_CREATE_STACKSIZE_NUMBER, (Sint64) stacksize);
    SDL_Thread *thread = SDL_CreateThreadWithProperties(props);
    SDL_DestroyProperties(props);
    return thread;
}

SDL_ThreadID SDL_GetThreadID(SDL_Thread *thread)
{
    SDL_ThreadID id = 0;

    if (thread) {
        if (ThreadValid(thread)) {
            id = thread->threadid;
        }
    } else {
        id = SDL_GetCurrentThreadID();
    }
    return id;
}

const char *SDL_GetThreadName(SDL_Thread *thread)
{
    if (ThreadValid(thread)) {
        return SDL_GetPersistentString(thread->name);
    } else {
        return NULL;
    }
}

bool SDL_SetCurrentThreadPriority(SDL_ThreadPriority priority)
{
    return SDL_SYS_SetThreadPriority(priority);
}

void SDL_WaitThread(SDL_Thread *thread, int *status)
{
    if (!ThreadValid(thread)) {
        if (status) {
            *status = -1;
        }
        return;
    }

    SDL_SYS_WaitThread(thread);
    if (status) {
        *status = thread->status;
    }
    SDL_SetObjectValid(thread, SDL_OBJECT_TYPE_THREAD, false);
    SDL_free(thread->name);
    SDL_free(thread);
}

SDL_ThreadState SDL_GetThreadState(SDL_Thread *thread)
{
    if (!ThreadValid(thread)) {
        return SDL_THREAD_UNKNOWN;
    }

    return (SDL_ThreadState)SDL_GetAtomicInt(&thread->state);
}

void SDL_DetachThread(SDL_Thread *thread)
{
    if (!ThreadValid(thread)) {
        return;
    }

    // Grab dibs if the state is alive+joinable.
    if (SDL_CompareAndSwapAtomicInt(&thread->state, SDL_THREAD_ALIVE, SDL_THREAD_DETACHED)) {
        // The thread may vanish at any time, it's no longer valid
        SDL_SetObjectValid(thread, SDL_OBJECT_TYPE_THREAD, false);
        SDL_SYS_DetachThread(thread);
    } else {
        // all other states are pretty final, see where we landed.
        SDL_ThreadState thread_state = SDL_GetThreadState(thread);
        if (thread_state == SDL_THREAD_DETACHED) {
            return; // already detached (you shouldn't call this twice!)
        } else if (thread_state == SDL_THREAD_COMPLETE) {
            SDL_WaitThread(thread, NULL); // already done, clean it up.
        }
    }
}

void SDL_WaitSemaphore(SDL_Semaphore *sem)
{
    SDL_WaitSemaphoreTimeoutNS(sem, -1);
}

bool SDL_TryWaitSemaphore(SDL_Semaphore *sem)
{
    return SDL_WaitSemaphoreTimeoutNS(sem, 0);
}

bool SDL_WaitSemaphoreTimeout(SDL_Semaphore *sem, Sint32 timeoutMS)
{
    Sint64 timeoutNS;

    if (timeoutMS >= 0) {
        timeoutNS = SDL_MS_TO_NS(timeoutMS);
    } else {
        timeoutNS = -1;
    }
    return SDL_WaitSemaphoreTimeoutNS(sem, timeoutNS);
}

void SDL_WaitCondition(SDL_Condition *cond, SDL_Mutex *mutex)
{
    SDL_WaitConditionTimeoutNS(cond, mutex, -1);
}

bool SDL_WaitConditionTimeout(SDL_Condition *cond, SDL_Mutex *mutex, Sint32 timeoutMS)
{
    Sint64 timeoutNS;

    if (timeoutMS >= 0) {
        timeoutNS = SDL_MS_TO_NS(timeoutMS);
    } else {
        timeoutNS = -1;
    }
    return SDL_WaitConditionTimeoutNS(cond, mutex, timeoutNS);
}

bool SDL_ShouldInit(SDL_InitState *state)
{
    while (SDL_GetAtomicInt(&state->status) != SDL_INIT_STATUS_INITIALIZED) {
        if (SDL_CompareAndSwapAtomicInt(&state->status, SDL_INIT_STATUS_UNINITIALIZED, SDL_INIT_STATUS_INITIALIZING)) {
            state->thread = SDL_GetCurrentThreadID();
            return true;
        }

        // Wait for the other thread to complete transition
        SDL_Delay(1);
    }
    return false;
}

bool SDL_ShouldQuit(SDL_InitState *state)
{
    while (SDL_GetAtomicInt(&state->status) != SDL_INIT_STATUS_UNINITIALIZED) {
        if (SDL_CompareAndSwapAtomicInt(&state->status, SDL_INIT_STATUS_INITIALIZED, SDL_INIT_STATUS_UNINITIALIZING)) {
            state->thread = SDL_GetCurrentThreadID();
            return true;
        }

        // Wait for the other thread to complete transition
        SDL_Delay(1);
    }
    return false;
}

void SDL_SetInitialized(SDL_InitState *state, bool initialized)
{
    SDL_assert(state->thread == SDL_GetCurrentThreadID());

    if (initialized) {
        SDL_SetAtomicInt(&state->status, SDL_INIT_STATUS_INITIALIZED);
    } else {
        SDL_SetAtomicInt(&state->status, SDL_INIT_STATUS_UNINITIALIZED);
    }
}

