/** * @file CppABI.cpp * @author apio (cloudapio.eu) * @brief Implementation of some C++ ABI internal functions, mainly __cxa_atexit. * * @copyright Copyright (c) 2023, the Luna authors. * */ typedef void* (*cxa_atexit_func_t)(void*); struct cxa_atexit_entry { cxa_atexit_func_t function; void* argument; void* dso_handle; }; #define CXA_ATEXIT_MAX 64 int cxa_atexit_entry_count = 0; cxa_atexit_entry cxa_atexit_entries[CXA_ATEXIT_MAX]; extern "C" { void __gxx_personality_v0() { } int __cxa_atexit(cxa_atexit_func_t func, void* arg, void* dso) { if (cxa_atexit_entry_count >= CXA_ATEXIT_MAX) return -1; cxa_atexit_entries[cxa_atexit_entry_count].function = func; cxa_atexit_entries[cxa_atexit_entry_count].argument = arg; cxa_atexit_entries[cxa_atexit_entry_count].dso_handle = dso; cxa_atexit_entry_count++; return 0; } void __cxa_finalize(void* f) { int i = cxa_atexit_entry_count; if (!f) { while (i--) { if (cxa_atexit_entries[i].function) { cxa_atexit_entries[i].function(cxa_atexit_entries[i].argument); } } } else { while (i--) { if (cxa_atexit_entries[i].function == (cxa_atexit_func_t)f) { cxa_atexit_entries[i].function(cxa_atexit_entries[i].argument); cxa_atexit_entries[i].function = 0; } } } } }