/* $info$ tags: thunklibs|fex_malloc desc: Handles allocations between guest and host thunks $end_info$ */ #include #include #include #include #include "common/Host.h" #include #include "Types.h" #include "thunkgen_host_libfex_malloc.inl" void fexfn_impl_libfex_malloc_fex_get_allocation_ptrs(AllocationPtrs* Ptrs); extern "C" { // FEX allocation routines extern MallocPtr FEX_Malloc_Ptr; extern FreePtr FEX_Free_Ptr; extern CallocPtr FEX_Calloc_Ptr; extern MemalignPtr FEX_Memalign_Ptr; extern ReallocPtr FEX_Realloc_Ptr; extern VallocPtr FEX_Valloc_Ptr; extern PosixMemalignPtr FEX_PosixMemalign_Ptr; extern AlignedAllocPtr FEX_AlignedAlloc_Ptr; extern MallocUsablePtr FEX_MallocUsable_Ptr; } extern "C" { AllocationPtrs AllocationPointers { .Malloc = FEX_Malloc_Ptr, .Free = FEX_Free_Ptr, .Calloc = FEX_Calloc_Ptr, .Memalign = FEX_Memalign_Ptr, .Realloc = FEX_Realloc_Ptr, .Valloc = FEX_Valloc_Ptr, .PosixMemalign = FEX_PosixMemalign_Ptr, .AlignedAlloc = FEX_AlignedAlloc_Ptr, .MallocUsable = FEX_MallocUsable_Ptr, }; // Our allocators #define ALIAS(fn) __attribute__((alias(#fn), used)) #define PREALIAS(fn) ALIAS(fn) void* fex_malloc(size_t Size) { return AllocationPointers.Malloc(Size); } void* __libc_malloc(size_t Size) __attribute__((alias("fex_malloc"), used)); void* malloc(size_t Size) __attribute__((alias("fex_malloc"), used)); void fex_free(void* p) { AllocationPointers.Free(p); } void __libc_free(void* ptr) PREALIAS(fex_free); void __GI___libc_free(void* ptr) PREALIAS(fex_free); void free(void* ptr) PREALIAS(fex_free); void* fex_calloc(size_t n, size_t size) { return AllocationPointers.Calloc(n, size); } void* __libc_calloc(size_t n, size_t size) PREALIAS(fex_calloc); void* calloc(size_t n, size_t size) PREALIAS(fex_calloc); void* fex_memalign(size_t align, size_t s) { return AllocationPointers.Memalign(align, s); } void* __libc_memalign(size_t align, size_t s) PREALIAS(fex_memalign); void* memalign(size_t align, size_t s) PREALIAS(fex_memalign); void* fex_realloc(void* ptr, size_t size) { return AllocationPointers.Realloc(ptr, size); } void* __libc_realloc(void* ptr, size_t size) PREALIAS(fex_realloc); void* realloc(void* ptr, size_t size) PREALIAS(fex_realloc); void* fex_valloc(size_t size) { return AllocationPointers.Valloc(size); } void* __libc_valloc(size_t size) PREALIAS(fex_valloc); void* valloc(size_t size) PREALIAS(fex_valloc); int fex_posix_memalign(void** r, size_t a, size_t s) { return AllocationPointers.PosixMemalign(r, a, s); } int __posix_memalign(void** r, size_t a, size_t s) PREALIAS(fex_posix_memalign); int posix_memalign(void** r, size_t a, size_t s) PREALIAS(fex_posix_memalign); void* fex_aligned_alloc(size_t a, size_t s) { return AllocationPointers.AlignedAlloc(a, s); } void* aligned_alloc(size_t a, size_t s) PREALIAS(fex_aligned_alloc); size_t fex_malloc_usable_size(void* ptr) { return AllocationPointers.MallocUsable(ptr); } size_t __malloc_usable_size(void* ptr) { return fex_malloc_usable_size(ptr); } size_t malloc_usable_size(void* ptr) { return fex_malloc_usable_size(ptr); } static void fexfn_unpack_libfex_malloc_malloc(void* argsv) { struct arg_t { size_t a_0; void* rv; }; auto args = (arg_t*)argsv; args->rv = AllocationPointers.Malloc(args->a_0); } static void fexfn_unpack_libfex_malloc_free(void* argsv) { struct arg_t { void* a_0; }; auto args = (arg_t*)argsv; AllocationPointers.Free(args->a_0); } static void fexfn_unpack_libfex_malloc_calloc(void* argsv) { struct arg_t { size_t a_0; size_t a_1; void* rv; }; auto args = (arg_t*)argsv; args->rv = AllocationPointers.Calloc(args->a_0, args->a_1); } static void fexfn_unpack_libfex_malloc_memalign(void* argsv) { struct arg_t { size_t a_0; size_t a_1; void* rv; }; auto args = (arg_t*)argsv; args->rv = AllocationPointers.Memalign(args->a_0, args->a_1); } static void fexfn_unpack_libfex_malloc_realloc(void* argsv) { struct arg_t { void* a_0; size_t a_1; void* rv; }; auto args = (arg_t*)argsv; args->rv = AllocationPointers.Realloc(args->a_0, args->a_1); } static void fexfn_unpack_libfex_malloc_valloc(void* argsv) { struct arg_t { size_t a_0; void* rv; }; auto args = (arg_t*)argsv; args->rv = AllocationPointers.Valloc(args->a_0); } static void fexfn_unpack_libfex_malloc_posix_memalign(void* argsv) { struct arg_t { void** a_0; size_t a_1; size_t a_2; int rv; }; auto args = (arg_t*)argsv; args->rv = AllocationPointers.PosixMemalign(args->a_0, args->a_1, args->a_2); } static void fexfn_unpack_libfex_malloc_aligned_alloc(void* argsv) { struct arg_t { size_t a_0; size_t a_1; void* rv; }; auto args = (arg_t*)argsv; args->rv = AllocationPointers.AlignedAlloc(args->a_0, args->a_1); } static void fexfn_unpack_libfex_malloc_malloc_usable_size(void* argsv) { struct arg_t { void* a_0; size_t rv; }; auto args = (arg_t*)argsv; args->rv = AllocationPointers.MallocUsable(args->a_0); } void (*__free_hook)(void* ptr) = fex_free; void* (*__malloc_hook)(size_t size) = fex_malloc; void* (*__realloc_hook)(void* ptr, size_t size) = fex_realloc; void* (*__memalign_hook)(size_t alignment, size_t size) = fex_memalign; } void fexfn_impl_libfex_malloc_fex_get_allocation_ptrs(AllocationPtrs* Ptrs) { *Ptrs = AllocationPointers; } static void init_lib() { // Set pointers AllocationPointers.Malloc = FEX_Malloc_Ptr; AllocationPointers.Free = FEX_Free_Ptr; AllocationPointers.Calloc = FEX_Calloc_Ptr; AllocationPointers.Memalign = FEX_Memalign_Ptr; AllocationPointers.Realloc = FEX_Realloc_Ptr; AllocationPointers.Valloc = FEX_Valloc_Ptr; AllocationPointers.PosixMemalign = FEX_PosixMemalign_Ptr; AllocationPointers.AlignedAlloc = FEX_AlignedAlloc_Ptr; AllocationPointers.MallocUsable = FEX_MallocUsable_Ptr; } EXPORTS(libfex_malloc) LOAD_LIB_INIT(init_lib)