mirror of
https://github.com/decompals/wibo.git
synced 2025-12-11 22:43:58 +00:00
Fully functional guest<->host trampolines
This commit is contained in:
264
dll/crt.cpp
264
dll/crt.cpp
@@ -1,5 +1,8 @@
|
||||
#include "crt.h"
|
||||
|
||||
#include "common.h"
|
||||
#include "context.h"
|
||||
#include "crt_trampolines.h"
|
||||
#include "kernel32/internal.h"
|
||||
#include "modules.h"
|
||||
|
||||
@@ -11,29 +14,6 @@
|
||||
#include <unistd.h>
|
||||
#include <vector>
|
||||
|
||||
typedef void (*_PVFV)();
|
||||
typedef int (*_PIFV)();
|
||||
typedef void (*_invalid_parameter_handler)(const uint16_t *, const uint16_t *, const uint16_t *, unsigned int,
|
||||
uintptr_t);
|
||||
|
||||
extern char **environ;
|
||||
|
||||
namespace msvcrt {
|
||||
int WIN_ENTRY puts(const char *str);
|
||||
}
|
||||
|
||||
typedef enum _crt_app_type {
|
||||
_crt_unknown_app,
|
||||
_crt_console_app,
|
||||
_crt_gui_app,
|
||||
} _crt_app_type;
|
||||
|
||||
typedef enum _crt_argv_mode {
|
||||
_crt_argv_no_arguments,
|
||||
_crt_argv_unexpanded_arguments,
|
||||
_crt_argv_expanded_arguments,
|
||||
} _crt_argv_mode;
|
||||
|
||||
namespace crt {
|
||||
|
||||
int _commode = 0;
|
||||
@@ -42,33 +22,24 @@ int _fmode = 0;
|
||||
std::vector<_PVFV> atexitFuncs;
|
||||
_invalid_parameter_handler invalidParameterHandler = nullptr;
|
||||
|
||||
void WIN_ENTRY _initterm(const _PVFV *ppfn, const _PVFV *end) {
|
||||
void CDECL _initterm(const _PVFV *ppfn, const _PVFV *end) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("_initterm(%p, %p)\n", ppfn, end);
|
||||
auto *tib = wibo::getThreadTibForHost();
|
||||
do {
|
||||
if (_PVFV pfn = *++ppfn) {
|
||||
DEBUG_LOG("-> calling %p\n", pfn);
|
||||
{
|
||||
GUEST_CONTEXT_GUARD(tib);
|
||||
pfn();
|
||||
}
|
||||
call__PVFV(pfn);
|
||||
}
|
||||
} while (ppfn < end);
|
||||
}
|
||||
|
||||
int WIN_ENTRY _initterm_e(const _PIFV *ppfn, const _PIFV *end) {
|
||||
int CDECL _initterm_e(const _PIFV *ppfn, const _PIFV *end) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("_initterm_e(%p, %p)\n", ppfn, end);
|
||||
auto *tib = wibo::getThreadTibForHost();
|
||||
do {
|
||||
if (_PIFV pfn = *++ppfn) {
|
||||
DEBUG_LOG("-> calling %p\n", pfn);
|
||||
int err = 0;
|
||||
{
|
||||
GUEST_CONTEXT_GUARD(tib);
|
||||
err = pfn();
|
||||
}
|
||||
int err = call__PIFV(pfn);
|
||||
if (err)
|
||||
return err;
|
||||
}
|
||||
@@ -77,44 +48,44 @@ int WIN_ENTRY _initterm_e(const _PIFV *ppfn, const _PIFV *end) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
void WIN_ENTRY _set_app_type(_crt_app_type type) {
|
||||
void CDECL _set_app_type(_crt_app_type type) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("STUB: _set_app_type(%i)\n", type);
|
||||
}
|
||||
|
||||
int WIN_ENTRY _set_fmode(int mode) {
|
||||
int CDECL _set_fmode(int mode) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("_set_fmode(%i)\n", mode);
|
||||
_fmode = mode;
|
||||
return 0;
|
||||
}
|
||||
|
||||
int *WIN_ENTRY __p__commode() {
|
||||
int *CDECL __p__commode() {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("__p__commode()\n");
|
||||
return &_commode;
|
||||
}
|
||||
|
||||
int *WIN_ENTRY __p__fmode() {
|
||||
int *CDECL __p__fmode() {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("__p__fmode()\n");
|
||||
return &_fmode;
|
||||
}
|
||||
|
||||
int WIN_ENTRY _crt_atexit(void (*func)()) {
|
||||
int CDECL _crt_atexit(void (*func)()) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("_crt_atexit(%p)\n", func);
|
||||
atexitFuncs.push_back(func);
|
||||
return 0;
|
||||
}
|
||||
|
||||
int WIN_ENTRY _configure_narrow_argv(_crt_argv_mode mode) {
|
||||
int CDECL _configure_narrow_argv(_crt_argv_mode mode) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("STUB: _configure_narrow_argv(%i)\n", mode);
|
||||
return 0;
|
||||
}
|
||||
|
||||
_invalid_parameter_handler WIN_ENTRY _set_invalid_parameter_handler(_invalid_parameter_handler newHandler) {
|
||||
_invalid_parameter_handler CDECL _set_invalid_parameter_handler(_invalid_parameter_handler newHandler) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("STUB: _set_invalid_parameter_handler(%p)\n", newHandler);
|
||||
_invalid_parameter_handler oldHandler = invalidParameterHandler;
|
||||
@@ -122,213 +93,203 @@ _invalid_parameter_handler WIN_ENTRY _set_invalid_parameter_handler(_invalid_par
|
||||
return oldHandler;
|
||||
}
|
||||
|
||||
int WIN_ENTRY _controlfp_s(unsigned int *currentControl, unsigned int newControl, unsigned int mask) {
|
||||
int CDECL _controlfp_s(unsigned int *currentControl, unsigned int newControl, unsigned int mask) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("STUB: _controlfp_s(%p, %u, %u)\n", currentControl, newControl, mask);
|
||||
return 0;
|
||||
}
|
||||
|
||||
int WIN_ENTRY _configthreadlocale(int per_thread_locale_type) {
|
||||
int CDECL _configthreadlocale(int per_thread_locale_type) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("STUB: _configthreadlocale(%i)\n", per_thread_locale_type);
|
||||
return 0;
|
||||
}
|
||||
|
||||
int WIN_ENTRY _initialize_narrow_environment() {
|
||||
int CDECL _initialize_narrow_environment() {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("STUB: _initialize_narrow_environment()\n");
|
||||
return 0;
|
||||
}
|
||||
|
||||
int WIN_ENTRY _set_new_mode(int newhandlermode) {
|
||||
int CDECL _set_new_mode(int newhandlermode) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("STUB: _set_new_mode(%i)\n", newhandlermode);
|
||||
return 0;
|
||||
}
|
||||
|
||||
char **WIN_ENTRY _get_initial_narrow_environment() {
|
||||
char **CDECL _get_initial_narrow_environment() {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("_get_initial_narrow_environment()\n");
|
||||
return environ;
|
||||
}
|
||||
|
||||
char ***WIN_ENTRY __p__environ() {
|
||||
char ***CDECL __p__environ() {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("__p__environ()\n");
|
||||
return &environ;
|
||||
}
|
||||
|
||||
char ***WIN_ENTRY __p___argv() {
|
||||
char ***CDECL __p___argv() {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("__p___argv()\n");
|
||||
return &wibo::argv;
|
||||
}
|
||||
|
||||
int *WIN_ENTRY __p___argc() {
|
||||
int *CDECL __p___argc() {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("__p___argc()\n");
|
||||
return &wibo::argc;
|
||||
}
|
||||
|
||||
size_t WIN_ENTRY strlen(const char *str) {
|
||||
SIZE_T CDECL strlen(const char *str) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
VERBOSE_LOG("strlen(%p)\n", str);
|
||||
return ::strlen(str);
|
||||
}
|
||||
|
||||
int WIN_ENTRY strcmp(const char *lhs, const char *rhs) {
|
||||
int CDECL strcmp(const char *lhs, const char *rhs) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
VERBOSE_LOG("strcmp(%p, %p)\n", lhs, rhs);
|
||||
return ::strcmp(lhs, rhs);
|
||||
}
|
||||
|
||||
int WIN_ENTRY strncmp(const char *lhs, const char *rhs, size_t count) {
|
||||
int CDECL strncmp(const char *lhs, const char *rhs, SIZE_T count) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
VERBOSE_LOG("strncmp(%p, %p, %zu)\n", lhs, rhs, count);
|
||||
return ::strncmp(lhs, rhs, count);
|
||||
}
|
||||
|
||||
char *WIN_ENTRY strcpy(char *dest, const char *src) {
|
||||
char *CDECL strcpy(char *dest, const char *src) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
VERBOSE_LOG("strcpy(%p, %p)\n", dest, src);
|
||||
return ::strcpy(dest, src);
|
||||
}
|
||||
|
||||
char *WIN_ENTRY strncpy(char *dest, const char *src, size_t count) {
|
||||
char *CDECL strncpy(char *dest, const char *src, SIZE_T count) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
VERBOSE_LOG("strncpy(%p, %p, %zu)\n", dest, src, count);
|
||||
return ::strncpy(dest, src, count);
|
||||
}
|
||||
|
||||
const char *WIN_ENTRY strrchr(const char *str, int ch) {
|
||||
const char *CDECL strrchr(const char *str, int ch) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
VERBOSE_LOG("strrchr(%p, %i)\n", str, ch);
|
||||
return ::strrchr(str, ch);
|
||||
}
|
||||
|
||||
void *WIN_ENTRY malloc(size_t size) {
|
||||
void *CDECL malloc(SIZE_T size) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
VERBOSE_LOG("malloc(%zu)\n", size);
|
||||
return ::malloc(size);
|
||||
}
|
||||
|
||||
void *WIN_ENTRY calloc(size_t count, size_t size) {
|
||||
void *CDECL calloc(SIZE_T count, SIZE_T size) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
VERBOSE_LOG("calloc(%zu, %zu)\n", count, size);
|
||||
return ::calloc(count, size);
|
||||
}
|
||||
|
||||
void *WIN_ENTRY realloc(void *ptr, size_t newSize) {
|
||||
void *CDECL realloc(void *ptr, SIZE_T newSize) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
VERBOSE_LOG("realloc(%p, %zu)\n", ptr, newSize);
|
||||
return ::realloc(ptr, newSize);
|
||||
}
|
||||
|
||||
void WIN_ENTRY free(void *ptr) {
|
||||
void CDECL free(void *ptr) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
VERBOSE_LOG("free(%p)\n", ptr);
|
||||
::free(ptr);
|
||||
}
|
||||
|
||||
void *WIN_ENTRY memcpy(void *dest, const void *src, size_t count) {
|
||||
void *CDECL memcpy(void *dest, const void *src, SIZE_T count) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
VERBOSE_LOG("memcpy(%p, %p, %zu)\n", dest, src, count);
|
||||
return std::memcpy(dest, src, count);
|
||||
}
|
||||
|
||||
void *WIN_ENTRY memmove(void *dest, const void *src, size_t count) {
|
||||
void *CDECL memmove(void *dest, const void *src, SIZE_T count) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
VERBOSE_LOG("memmove(%p, %p, %zu)\n", dest, src, count);
|
||||
return std::memmove(dest, src, count);
|
||||
}
|
||||
|
||||
void *WIN_ENTRY memset(void *dest, int ch, size_t count) {
|
||||
void *CDECL memset(void *dest, int ch, SIZE_T count) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
VERBOSE_LOG("memset(%p, %i, %zu)\n", dest, ch, count);
|
||||
return std::memset(dest, ch, count);
|
||||
}
|
||||
|
||||
int WIN_ENTRY memcmp(const void *lhs, const void *rhs, size_t count) {
|
||||
int CDECL memcmp(const void *lhs, const void *rhs, SIZE_T count) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
VERBOSE_LOG("memcmp(%p, %p, %zu)\n", lhs, rhs, count);
|
||||
return std::memcmp(lhs, rhs, count);
|
||||
}
|
||||
|
||||
int WIN_ENTRY __setusermatherr(void *handler) {
|
||||
int CDECL __setusermatherr(void *handler) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("STUB: __setusermatherr(%p)\n", handler);
|
||||
return 0;
|
||||
}
|
||||
|
||||
int WIN_ENTRY _initialize_onexit_table(void *table) {
|
||||
int CDECL _initialize_onexit_table(void *table) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("STUB: _initialize_onexit_table(%p)\n", table);
|
||||
wibo::registerOnExitTable(table);
|
||||
return 0;
|
||||
}
|
||||
|
||||
int WIN_ENTRY _register_onexit_function(void *table, void (*func)()) {
|
||||
int CDECL _register_onexit_function(void *table, void (*func)()) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("STUB: _register_onexit_function(%p, %p)\n", table, func);
|
||||
wibo::addOnExitFunction(table, func);
|
||||
return 0;
|
||||
}
|
||||
|
||||
int WIN_ENTRY _execute_onexit_table(void *table) {
|
||||
int CDECL _execute_onexit_table(void *table) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("STUB: _execute_onexit_table(%p)\n", table);
|
||||
wibo::executeOnExitTable(table);
|
||||
return 0;
|
||||
}
|
||||
|
||||
void WIN_ENTRY exit(int status) {
|
||||
void CDECL exit(int status) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("exit(%i)\n", status);
|
||||
auto *tib = wibo::getThreadTibForHost();
|
||||
for (auto it = atexitFuncs.rbegin(); it != atexitFuncs.rend(); ++it) {
|
||||
DEBUG_LOG("Calling atexit function %p\n", *it);
|
||||
{
|
||||
GUEST_CONTEXT_GUARD(tib);
|
||||
(*it)();
|
||||
}
|
||||
call__PVFV(*it);
|
||||
}
|
||||
kernel32::exitInternal(status);
|
||||
}
|
||||
|
||||
void WIN_ENTRY _cexit() {
|
||||
void CDECL _cexit() {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("_cexit()\n");
|
||||
auto *tib = wibo::getThreadTibForHost();
|
||||
for (auto it = atexitFuncs.rbegin(); it != atexitFuncs.rend(); ++it) {
|
||||
DEBUG_LOG("Calling atexit function %p\n", *it);
|
||||
{
|
||||
GUEST_CONTEXT_GUARD(tib);
|
||||
(*it)();
|
||||
}
|
||||
call__PVFV(*it);
|
||||
}
|
||||
}
|
||||
|
||||
void WIN_ENTRY _exit(int status) {
|
||||
void CDECL _exit(int status) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("_exit(%i)\n", status);
|
||||
kernel32::exitInternal(status);
|
||||
}
|
||||
|
||||
void WIN_ENTRY abort(void) {
|
||||
void CDECL abort() {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("abort()\n");
|
||||
std::abort();
|
||||
}
|
||||
|
||||
using signal_handler = void (*)(int);
|
||||
|
||||
signal_handler WIN_ENTRY signal(int signum, signal_handler handler) {
|
||||
signal_handler CDECL signal(int signum, signal_handler handler) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("signal(%i, %p)\n", signum, handler);
|
||||
return std::signal(signum, handler);
|
||||
}
|
||||
|
||||
void *WIN_ENTRY __acrt_iob_func(unsigned int index) {
|
||||
void *CDECL __acrt_iob_func(unsigned int index) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("__acrt_iob_func(%u)\n", index);
|
||||
if (index == 0)
|
||||
@@ -340,15 +301,15 @@ void *WIN_ENTRY __acrt_iob_func(unsigned int index) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
int WIN_ENTRY __stdio_common_vfprintf(unsigned long long options, FILE *stream, const char *format, void *locale,
|
||||
va_list args) {
|
||||
int CDECL __stdio_common_vfprintf(unsigned long long options, FILE *stream, const char *format, void *locale,
|
||||
va_list args) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("__stdio_common_vfprintf(%llu, %p, %s, %p, %p)\n", options, stream, format, locale, args);
|
||||
return vfprintf(stream, format, args);
|
||||
}
|
||||
|
||||
int WIN_ENTRY __stdio_common_vsprintf(unsigned long long options, char *buffer, size_t len, const char *format,
|
||||
void *locale, va_list args) {
|
||||
int CDECL __stdio_common_vsprintf(unsigned long long options, char *buffer, SIZE_T len, const char *format,
|
||||
void *locale, va_list args) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("__stdio_common_vsprintf(%llu, %p, %zu, %s, %p, ...)\n", options, buffer, len, format, locale);
|
||||
if (!buffer || !format)
|
||||
@@ -356,113 +317,38 @@ int WIN_ENTRY __stdio_common_vsprintf(unsigned long long options, char *buffer,
|
||||
int result = vsnprintf(buffer, len, format, args);
|
||||
if (result < 0)
|
||||
return -1;
|
||||
if (len > 0 && static_cast<size_t>(result) >= len)
|
||||
if (len > 0 && static_cast<SIZE_T>(result) >= len)
|
||||
return -1;
|
||||
return result;
|
||||
}
|
||||
|
||||
int WIN_ENTRY qsort(void *base, size_t num, size_t size, int (*compar)(const void *, const void *)) {
|
||||
static thread_local sort_compare currentCompare = nullptr;
|
||||
|
||||
static int doCompare(const void *a, const void *b) { return call_sort_compare(currentCompare, a, b); }
|
||||
|
||||
void CDECL qsort(void *base, SIZE_T num, SIZE_T size, sort_compare compare) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
DEBUG_LOG("qsort(%p, %zu, %zu, %p)\n", base, num, size, compar);
|
||||
::qsort(base, num, size, compar);
|
||||
DEBUG_LOG("qsort(%p, %zu, %zu, %p)\n", base, num, size, compare);
|
||||
currentCompare = compare;
|
||||
::qsort(base, num, size, doCompare);
|
||||
}
|
||||
|
||||
int CDECL puts(const char *str) {
|
||||
HOST_CONTEXT_GUARD();
|
||||
if (!str) {
|
||||
str = "(null)";
|
||||
}
|
||||
DEBUG_LOG("puts(%s)\n", str);
|
||||
if (std::fputs(str, stdout) < 0)
|
||||
return EOF;
|
||||
if (std::fputc('\n', stdout) == EOF)
|
||||
return EOF;
|
||||
return 0;
|
||||
}
|
||||
|
||||
} // namespace crt
|
||||
|
||||
static void *resolveByName(const char *name) {
|
||||
if (strcmp(name, "_initterm") == 0)
|
||||
return (void *)crt::_initterm;
|
||||
if (strcmp(name, "_initterm_e") == 0)
|
||||
return (void *)crt::_initterm_e;
|
||||
if (strcmp(name, "_set_app_type") == 0)
|
||||
return (void *)crt::_set_app_type;
|
||||
if (strcmp(name, "_set_fmode") == 0)
|
||||
return (void *)crt::_set_fmode;
|
||||
if (strcmp(name, "__p__commode") == 0)
|
||||
return (void *)crt::__p__commode;
|
||||
if (strcmp(name, "__p__fmode") == 0)
|
||||
return (void *)crt::__p__fmode;
|
||||
if (strcmp(name, "_crt_atexit") == 0)
|
||||
return (void *)crt::_crt_atexit;
|
||||
if (strcmp(name, "_configure_narrow_argv") == 0)
|
||||
return (void *)crt::_configure_narrow_argv;
|
||||
if (strcmp(name, "_set_invalid_parameter_handler") == 0)
|
||||
return (void *)crt::_set_invalid_parameter_handler;
|
||||
if (strcmp(name, "_controlfp_s") == 0)
|
||||
return (void *)crt::_controlfp_s;
|
||||
if (strcmp(name, "_configthreadlocale") == 0)
|
||||
return (void *)crt::_configthreadlocale;
|
||||
if (strcmp(name, "_initialize_narrow_environment") == 0)
|
||||
return (void *)crt::_initialize_narrow_environment;
|
||||
if (strcmp(name, "_set_new_mode") == 0)
|
||||
return (void *)crt::_set_new_mode;
|
||||
if (strcmp(name, "_get_initial_narrow_environment") == 0)
|
||||
return (void *)crt::_get_initial_narrow_environment;
|
||||
if (strcmp(name, "__p__environ") == 0)
|
||||
return (void *)crt::__p__environ;
|
||||
if (strcmp(name, "__p___argv") == 0)
|
||||
return (void *)crt::__p___argv;
|
||||
if (strcmp(name, "__p___argc") == 0)
|
||||
return (void *)crt::__p___argc;
|
||||
if (strcmp(name, "strlen") == 0)
|
||||
return (void *)crt::strlen;
|
||||
if (strcmp(name, "strcmp") == 0)
|
||||
return (void *)crt::strcmp;
|
||||
if (strcmp(name, "strncmp") == 0)
|
||||
return (void *)crt::strncmp;
|
||||
if (strcmp(name, "strcpy") == 0)
|
||||
return (void *)crt::strcpy;
|
||||
if (strcmp(name, "strncpy") == 0)
|
||||
return (void *)crt::strncpy;
|
||||
if (strcmp(name, "strrchr") == 0)
|
||||
return (void *)crt::strrchr;
|
||||
if (strcmp(name, "malloc") == 0)
|
||||
return (void *)crt::malloc;
|
||||
if (strcmp(name, "calloc") == 0)
|
||||
return (void *)crt::calloc;
|
||||
if (strcmp(name, "realloc") == 0)
|
||||
return (void *)crt::realloc;
|
||||
if (strcmp(name, "free") == 0)
|
||||
return (void *)crt::free;
|
||||
if (strcmp(name, "memcpy") == 0)
|
||||
return (void *)crt::memcpy;
|
||||
if (strcmp(name, "memmove") == 0)
|
||||
return (void *)crt::memmove;
|
||||
if (strcmp(name, "memset") == 0)
|
||||
return (void *)crt::memset;
|
||||
if (strcmp(name, "memcmp") == 0)
|
||||
return (void *)crt::memcmp;
|
||||
if (strcmp(name, "exit") == 0)
|
||||
return (void *)crt::exit;
|
||||
if (strcmp(name, "_cexit") == 0)
|
||||
return (void *)crt::_cexit;
|
||||
if (strcmp(name, "_exit") == 0)
|
||||
return (void *)crt::_exit;
|
||||
if (strcmp(name, "abort") == 0)
|
||||
return (void *)crt::abort;
|
||||
if (strcmp(name, "signal") == 0)
|
||||
return (void *)crt::signal;
|
||||
if (strcmp(name, "__acrt_iob_func") == 0)
|
||||
return (void *)crt::__acrt_iob_func;
|
||||
if (strcmp(name, "__stdio_common_vfprintf") == 0)
|
||||
return (void *)crt::__stdio_common_vfprintf;
|
||||
if (strcmp(name, "__stdio_common_vsprintf") == 0)
|
||||
return (void *)crt::__stdio_common_vsprintf;
|
||||
if (strcmp(name, "puts") == 0)
|
||||
return (void *)msvcrt::puts;
|
||||
if (strcmp(name, "__setusermatherr") == 0)
|
||||
return (void *)crt::__setusermatherr;
|
||||
if (strcmp(name, "_initialize_onexit_table") == 0)
|
||||
return (void *)crt::_initialize_onexit_table;
|
||||
if (strcmp(name, "_register_onexit_function") == 0)
|
||||
return (void *)crt::_register_onexit_function;
|
||||
if (strcmp(name, "_execute_onexit_table") == 0)
|
||||
return (void *)crt::_execute_onexit_table;
|
||||
if (strcmp(name, "qsort") == 0)
|
||||
return (void *)crt::qsort;
|
||||
return nullptr;
|
||||
}
|
||||
#include "crt_trampolines.h"
|
||||
|
||||
extern const wibo::ModuleStub lib_crt = {
|
||||
(const char *[]){
|
||||
@@ -477,6 +363,6 @@ extern const wibo::ModuleStub lib_crt = {
|
||||
"api-ms-win-crt-utility-l1-1-0",
|
||||
nullptr,
|
||||
},
|
||||
resolveByName,
|
||||
crtThunkByName,
|
||||
nullptr,
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user