diff options
36 files changed, 1175 insertions, 0 deletions
diff --git a/arch/nt64/atomic.h b/arch/nt64/atomic.h new file mode 100644 index 0000000..a2b141a --- /dev/null +++ b/arch/nt64/atomic.h @@ -0,0 +1,7 @@ +#ifndef _INTERNAL_ATOMIC_NT64_H +#define _INTERNAL_ATOMIC_NT64_H + +#include "../x86_64/atomic.h" + +#endif + diff --git a/arch/nt64/psxglue.h b/arch/nt64/psxglue.h new file mode 100644 index 0000000..73ad2b0 --- /dev/null +++ b/arch/nt64/psxglue.h @@ -0,0 +1,63 @@ +#ifndef _PSXGLUE_H_ +#define _PSXGLUE_H_ + +#define __PSXOPT_NATIVE 0x0 +#define __PSXOPT_POSIX 0x1 +#define __PSXOPT_TTYDBG 0x2 +#define __PSXOPT_LDSO 0x4 + +typedef int __ldso_dladdr(const void * addr, void * info); +typedef int __ldso_dlinfo(void * dso, int req, void * res); +typedef void * __ldso_dlsym(void * p, const char * s, void * ra); +typedef void * __ldso_dlopen(const char * file, int mode); +typedef int __ldso_dlclose(void *p); +typedef char * __ldso_dlerror(void); +typedef void __ldso_reset_tls(void); + +typedef void __psx_convert_thread(void); +typedef void __psx_unmapself(void *, void *); +typedef void * __psx_get_osfhandle(int fd); + +struct __ldso_vtbl { + __ldso_dladdr * dladdr; + __ldso_dlinfo * dlinfo; + __ldso_dlsym * dlsym; + __ldso_dlopen * dlopen; + __ldso_dlclose * dlclose; + __ldso_dlerror * dlerror; + __ldso_reset_tls * reset_tls; +}; + +struct __psx_vtbl { + __psx_convert_thread * convert_thread; + __psx_unmapself * unmapself; + __psx_get_osfhandle * get_osfhandle; +}; + +struct __psx_context { + int size; + int options; + void *** sys_vtbl; + struct __ldso_vtbl * ldso_vtbl; + struct __psx_vtbl * psx_vtbl; + unsigned int teb_sys_idx; + unsigned int teb_libc_idx; + void * pthread_surrogate_fn; + void * pthread_create_fn; +}; + +struct __tlca { + void * pthread_self; + int * pthread_set_child_tid; + int * pthread_clear_child_tid; + char * pthread_tls; + char ***pthread_dtls; +}; + +typedef int __psx_init_routine( + int * argc, + char *** argv, + char *** envp, + struct __psx_context * ctx); + +#endif diff --git a/arch/nt64/pthread_arch.h b/arch/nt64/pthread_arch.h new file mode 100644 index 0000000..98babcd --- /dev/null +++ b/arch/nt64/pthread_arch.h @@ -0,0 +1,74 @@ +#include <stddef.h> + +#define TP_ADJ(p) (p) +#define CANCEL_REG_IP 16 + +extern uintptr_t __teb_sys_idx; +extern uintptr_t __teb_libc_idx; + +struct __os_tib { + void * exception_list; + void * stack_base; + void * stack_limit; +}; + +static __inline__ void * __os_get_teb_address(void) +{ + void * ptrRet; + __asm__ __volatile__ ( + "mov %%gs:0x30, %0\n\t" + : "=r" (ptrRet) : : + ); + return ptrRet; +} + + +static inline void __pthread_convert(void) +{ + /* (third-party thread support) */ + __asm__ __volatile__ ( + "push %rax\n\t" + "movq __psx_vtbl,%rax\n\t" + "call *(%rax)\n\t" + "pop %rax\n\t" + ); +} + + +static inline struct pthread ** __psx_tlca(void) +{ + struct pthread ** ptlca; + struct __os_tib * tib; + void ** slots; + void *** xslots; + uintptr_t sys_idx; + + tib = __os_get_teb_address(); + sys_idx = __teb_sys_idx; + + if (sys_idx < 64) { + slots = (void **)((uintptr_t)tib + 0x1480); + ptlca = (struct pthread **)(slots[sys_idx]); + } else { + xslots = (void ***)((uintptr_t)tib + 0x1780); + slots = *xslots; + ptlca = (struct pthread **)(slots[sys_idx - 64]); + } + + return ptlca; +} + + +static inline struct pthread * __pthread_self(void) +{ + struct pthread ** ptlca; + + ptlca = __psx_tlca(); + if (ptlca) return *ptlca; + + /* (third-party thread) */ + __pthread_convert(); + ptlca = __psx_tlca(); + return *ptlca; +} + diff --git a/arch/nt64/reloc.h b/arch/nt64/reloc.h new file mode 100644 index 0000000..20abf44 --- /dev/null +++ b/arch/nt64/reloc.h @@ -0,0 +1,6 @@ +#define LDSO_ARCH "PE32+" + +static int remap_rel(int type) +{ + return 0; +} diff --git a/arch/nt64/src/crt_glue.c b/arch/nt64/src/crt_glue.c new file mode 100644 index 0000000..e8a07de --- /dev/null +++ b/arch/nt64/src/crt_glue.c @@ -0,0 +1,87 @@ +#include <unistd.h> +#include <pthread.h> +#include "atomic.h" +#include "syscall.h" +#include "psxglue.h" +#include "pthread_impl.h" + +extern struct __ldso_vtbl * __ldso_vtbl; +extern struct __psx_vtbl * __psx_vtbl; + +typedef int __app_main(); +typedef int __pthread_surrogate_routine(struct pthread *); + +extern int _init(void); +static int __pthread_surrogate_init(struct pthread * self); + +extern int __libc_start_main( + void * main, + int argc, + char ** argv); + +void __libc_entry_routine( + __app_main * __main, + __psx_init_routine * __psx_init_routine, + int options) +{ + int argc; + char ** argv; + char ** envp; + struct __psx_context ctx; + + /* ctx init */ + ctx.size = sizeof(ctx); + ctx.options = options; + ctx.pthread_create_fn = pthread_create; + ctx.pthread_surrogate_fn= __pthread_surrogate_init; + + /* __psx_init must succeed... */ + if (__psx_init_routine(&argc,&argv,&envp,&ctx)) + a_crash(); + + /* ...and conform */ + else if (envp != argv + (argc + 1)) + a_crash(); + + /* dso init routines */ + _init(); + + /* write once */ + __syscall_vtbl = (unsigned long **)ctx.sys_vtbl; + __ldso_vtbl = ctx.ldso_vtbl; + __psx_vtbl = ctx.psx_vtbl; + __teb_sys_idx = ctx.teb_sys_idx; + __teb_libc_idx = ctx.teb_libc_idx; + + /* enter libc */ + __libc_start_main(__main,argc,argv); + + /* guard */ + a_crash(); +} + +static int __pthread_surrogate_init(struct pthread * self) +{ + /** + * invoked by psxscl upon creation of a surrogate libc + * thread, which in turn may only call pthread_create(); + * + * the purpose of this mecahnism is to support a scenario + * where a third-party library creates a non-posix thread + * which then calls, be it directly or via a callback + * function, a libc api that depends on a valid + * pthread_self. + * + * self: a pointer to an already zero'ed memory page + * + * struct pthread relevant members: + * -------------------------------- + * cancel (already zero) + * canary (already zero) + * + * pthread_create() reference: + * 1a47ed15eebf96d0c8d5de4aea54108bc8cc3f53 + **/ + + return 0; +} diff --git a/arch/nt64/src/crt_pe.c b/arch/nt64/src/crt_pe.c new file mode 100644 index 0000000..0dc75a4 --- /dev/null +++ b/arch/nt64/src/crt_pe.c @@ -0,0 +1,7 @@ +#include "pthread_impl.h" +#include <threads.h> + +void * __pthread_getspecific_impl(pthread_key_t k) +{ + return (__pthread_self())->tsd[k]; +} diff --git a/arch/nt64/src/crt_tls.c b/arch/nt64/src/crt_tls.c new file mode 100644 index 0000000..15183d3 --- /dev/null +++ b/arch/nt64/src/crt_tls.c @@ -0,0 +1,27 @@ +#include <stdint.h> +#include <stddef.h> +#include "psxglue.h" +#include "pthread_arch.h" + +typedef unsigned int __tls_word __attribute__((mode(word))); +typedef unsigned int __tls_ptr __attribute__((mode(pointer))); + +struct __emutls_object +{ + __tls_word size; + __tls_word align; + ptrdiff_t offset; + void * defval; +}; + +void * __emutls_get_address (struct __emutls_object * obj) +{ + int dsoidx = obj->align & 0xFFFF0000; + struct __tlca * tlca = (struct __tlca *)__psx_tlca(); + + if (dsoidx) + return (*tlca->pthread_dtls)[dsoidx >> 16] + obj->offset; + else + return tlca->pthread_tls + obj->offset; +} + diff --git a/arch/nt64/src/libc_entry_point.c b/arch/nt64/src/libc_entry_point.c new file mode 100644 index 0000000..0929cc4 --- /dev/null +++ b/arch/nt64/src/libc_entry_point.c @@ -0,0 +1,10 @@ +typedef unsigned int uint32_t; + +int __libc_entry_point( + void * hinstance, + uint32_t reason, + void * reserved) +{ + return 1; +} + diff --git a/arch/nt64/src/syscall_disp.c b/arch/nt64/src/syscall_disp.c new file mode 100644 index 0000000..cb9655d --- /dev/null +++ b/arch/nt64/src/syscall_disp.c @@ -0,0 +1,22 @@ +#include <stdint.h> +#include <stddef.h> +#include "syscall.h" +#include "psxglue.h" + +extern struct __psx_vtbl * __psx_vtbl; + +void __unmapself(void * base, size_t size) +{ + __psx_vtbl->unmapself(base,size); +} + +uintptr_t __syscall_disp(long n, + uintptr_t a1, + uintptr_t a2, + uintptr_t a3, + uintptr_t a4, + uintptr_t a5, + uintptr_t a6) +{ + return __syscall(n,a1,a2,a3,a4,a5,a6); +} diff --git a/arch/nt64/src/vtbl.c b/arch/nt64/src/vtbl.c new file mode 100644 index 0000000..028f153 --- /dev/null +++ b/arch/nt64/src/vtbl.c @@ -0,0 +1,12 @@ +#include "psxglue.h" + +unsigned long ** __syscall_vtbl = 0; +struct __ldso_vtbl * __ldso_vtbl = 0; +struct __psx_vtbl * __psx_vtbl = 0; +unsigned long __teb_sys_idx = 0; +unsigned long __teb_libc_idx = 0; + +void ___chkstk_ms(void) +{ +} + diff --git a/arch/nt64/syscall_arch.h b/arch/nt64/syscall_arch.h new file mode 100644 index 0000000..9c8fea4 --- /dev/null +++ b/arch/nt64/syscall_arch.h @@ -0,0 +1,63 @@ +extern unsigned long ** __syscall_vtbl; + +typedef long __syscall0_fn(void); +typedef long __syscall1_fn(long a1); +typedef long __syscall2_fn(long a1, long a2); +typedef long __syscall3_fn(long a1, long a2, long a3); +typedef long __syscall4_fn(long a1, long a2, long a3, long a4); +typedef long __syscall5_fn(long a1, long a2, long a3, long a4, long a5); +typedef long __syscall6_fn(long a1, long a2, long a3, long a4, long a5, long a6); + +#define sysfn_from_fn(x) \ + x * sysfn = (x *)__syscall_vtbl[n] + +static __inline long __syscall0(long n) +{ + sysfn_from_fn(__syscall0_fn); + return sysfn(); +} + +static __inline long __syscall1(long n, long a1) +{ + sysfn_from_fn(__syscall1_fn); + return sysfn(a1); +} + +static __inline long __syscall2(long n, long a1, long a2) +{ + sysfn_from_fn(__syscall2_fn); + return sysfn(a1, a2); +} + +static __inline long __syscall3(long n, long a1, long a2, long a3) +{ + sysfn_from_fn(__syscall3_fn); + return sysfn(a1, a2, a3); +} + +static __inline long __syscall4(long n, long a1, long a2, long a3, long a4) +{ + sysfn_from_fn(__syscall4_fn); + return sysfn(a1, a2, a3, a4); +} + +static __inline long __syscall5(long n, long a1, long a2, long a3, long a4, long a5) +{ + sysfn_from_fn(__syscall5_fn); + return sysfn(a1, a2, a3, a4, a5); +} + +static __inline long __syscall6(long n, long a1, long a2, long a3, long a4, long a5, long a6) +{ + sysfn_from_fn(__syscall6_fn); + return sysfn(a1, a2, a3, a4, a5, a6); +} + + +#define __SYSCALL_LL_E(x) (x) +#define __SYSCALL_LL_O(x) (x) + + +#define VDSO_USEFUL +#define VDSO_CGT_SYM "__clock_gettime" +#define VDSO_CGT_VER "LINUX_2.6" diff --git a/crt/nt64/Scrt1.c b/crt/nt64/Scrt1.c new file mode 100644 index 0000000..ff5789f --- /dev/null +++ b/crt/nt64/Scrt1.c @@ -0,0 +1,2 @@ +#define LIBC_STATIC +#include "crt1.c" diff --git a/crt/nt64/crt1.c b/crt/nt64/crt1.c new file mode 100644 index 0000000..6d22669 --- /dev/null +++ b/crt/nt64/crt1.c @@ -0,0 +1,33 @@ +#ifdef LIBC_STATIC +#define __external_routine +#else +#define __external_routine __attribute__((dllimport)) +#endif + +#include "psxglue.h" + +/** + * options: posix session, fallback terminal emulator + * x86_64-nt64-midipix-gcc --target-help | grep -A2 posix +**/ + +static const int __disabled = 0; +extern const int __crtopt_posix __attribute((weak,alias("__disabled"))); +extern const int __crtopt_ttydbg __attribute((weak,alias("__disabled"))); + +int main(); + +__external_routine +__psx_init_routine __psx_init; + +__external_routine +void __libc_entry_routine(void *,void *,int); + +void _start(void) +{ + __libc_entry_routine( + main, + __psx_init, + __crtopt_posix | __crtopt_ttydbg); +} + diff --git a/crt/nt64/crtdev.c b/crt/nt64/crtdev.c new file mode 100644 index 0000000..8aa80e6 --- /dev/null +++ b/crt/nt64/crtdev.c @@ -0,0 +1,3 @@ +#include "psxglue.h" + +const int __crtopt_ttydbg = __PSXOPT_TTYDBG; diff --git a/crt/nt64/crte.s b/crt/nt64/crte.s new file mode 100644 index 0000000..9753213 --- /dev/null +++ b/crt/nt64/crte.s @@ -0,0 +1,19 @@ +.text +.globl _so_entry_point +_so_entry_point: + cmp $0x1,%edx + jne dso_main_routine + mov %edx,%eax + ret + +__dso_main_routine: + ret + + .weak dso_main_routine + .set dso_main_routine,__dso_main_routine + +.section .midipix + .quad dso_main_routine + .quad _so_entry_point + .quad _init + .quad _fini diff --git a/crt/nt64/crti.s b/crt/nt64/crti.s new file mode 100644 index 0000000..14fdd90 --- /dev/null +++ b/crt/nt64/crti.s @@ -0,0 +1,41 @@ +.text +.globl _pei386_runtime_relocator +_pei386_runtime_relocator: + ret + +.globl _init +_init: + call .init + ret + +.globl _fini +_fini: + call .fini + ret + +.section .init + xor %rax,%rax + push %rax + push %rcx + push %rdx + nop + nop + +.section .fini + xor %rax,%rax + push %rax + push %rcx + push %rdx + nop + nop + +.section .midipix + .ascii "e35ed272" + .ascii "9e55" + .ascii "46c1" + .ascii "8251" + .ascii "022a59e6c480" + .long 0 + .long 1 + .long 0 + .long 0 diff --git a/crt/nt64/crtn.s b/crt/nt64/crtn.s new file mode 100644 index 0000000..b2c7790 --- /dev/null +++ b/crt/nt64/crtn.s @@ -0,0 +1,13 @@ +.section .init + pop %rdx + pop %rcx + pop %r10 + or %r10,%rax + ret + +.section .fini + pop %rdx + pop %rcx + pop %r10 + or %r10,%rax + ret diff --git a/crt/nt64/crtposix.c b/crt/nt64/crtposix.c new file mode 100644 index 0000000..b8e5113 --- /dev/null +++ b/crt/nt64/crtposix.c @@ -0,0 +1,3 @@ +#include "psxglue.h" + +const int __crtopt_posix = __PSXOPT_POSIX; diff --git a/musl.lzy b/musl.lzy new file mode 100644 index 0000000..b3f0f4e --- /dev/null +++ b/musl.lzy @@ -0,0 +1,389 @@ +# lazy mark: project recipe +lz_project_rules() +{ + lz_rules="all install install_no_complex \ + libc libc_shared libc_static \ + libc_no_complex libc_shared_no_complex libc_static_no_complex" +} + + +lz_project_definitions() +{ + lz_cflags_common="-std=c99 -pipe -ffreestanding -nostdinc -D_XOPEN_SOURCE=700 -fomit-frame-pointer" + + lz_cflags_include_common="-I$lz_project_dir/src/internal \ + -I$lz_project_dir/arch/$lz_arch \ + -I$lz_project_dir/include \ + -I$lz_build_dir/arch/$lz_arch \ + -I$lz_build_dir/include" + + musl_empty_lib_names="m rt pthread crypt util xnet resolv dl" + musl_cflags_crt="-fPIC" + musl_cflags_shared="-fPIC -DSHARED" + + if [ "$lz_pecoff_winnt"x = yesx ]; then + pe_excluded_symbols="__libc_entry_point" + pe_excluded_symbols="$pe_excluded_symbols,__syscall_vtbl" + pe_excluded_symbols="$pe_excluded_symbols,__ldso_vtbl" + pe_excluded_symbols="$pe_excluded_symbols,__psx_vtbl" + pe_excluded_symbols="$pe_excluded_symbols,__teb_sys_idx" + pe_excluded_symbols="$pe_excluded_symbols,__teb_libc_idx" + pe_excluded_symbols="$pe_excluded_symbols,__vm_lock_impl" + pe_excluded_symbols="$pe_excluded_symbols,__vm_unlock_impl" + + musl_libc_so_ldflags="-shared -e __libc_entry_point -Bsymbolic-functions \ + --subsystem windows \ + --output-def $lz_build_dir/lib/libc.so.def \ + --out-implib $lz_build_dir/lib/libc.lib.a \ + --exclude-symbols=$pe_excluded_symbols" + else + musl_libc_so_ldflags="-shared -e _start -Bsymbolic-functions" + fi + + musl_libc_src_dirs="src arch/$lz_arch/src arch/$lz_arch/weak" + musl_libc_mem_files="src/string/memcpy.c src/string/memmove.c src/string/memcmp.c src/string/memset.c" + + + lz_flag_tests_begin + + for musl_test_flag in "-frounding-math" "-fexcess-precision=standard"; do + lz_compiler_supports_flag $lz_c_compiler "$musl_test_flag" \ + && lz_cflags_common="$lz_cflags_common $musl_test_flag" + done + + for musl_test_flag in "-fno-tree-loop-distribute-patterns"; do + lz_compiler_supports_flag $lz_c_compiler "$musl_test_flag" \ + && musl_cflags_memops="$musl_cflags_memops $musl_test_flag" + done + + for musl_test_flag in "--hash-style=both"; do + lz_linker_supports_flag $lz_c_compiler $lz_ld "$musl_test_flag" \ + && musl_libc_so_ldflags="$musl_libc_so_ldflags $musl_test_flag" + done + + lz_flag_tests_end + + + if [ "$lz_debug"x = yesx ]; then + lz_cflags_debug="$lz_toolchain_cflags_debug" + else + lz_cflags_common="$lz_cflags_common -Os" + fi + + # names of binary files and/or utilities + musl_libc_a_name="$lz_build_dir/lib/libc$lz_stlib_ext" + musl_libc_so_name="$lz_build_dir/lib/libc$lz_dylib_ext" + + # temporary files to store meta information + musl_libc_so_obj_list=libc.so.objs + musl_libc_so_src_list=libc.so.src.lst + + musl_libc_a_obj_list=libc.a.objs + musl_libc_a_src_list=libc.a.src.lst + + musl_crt_obj_list=crt.objs + musl_crt_src_list=crt.src.lst + + musl_install_sh=$lz_project_dir/tools/install.sh + musl_ldso="$lz_syslibdir/ld-musl-$lz_arch$lz_subarch.so.1" +} + + +musl_headers() +{ + if [ -f $lz_build_dir/headers.tag ]; then + lz_ok && return + fi + + mkdir -p $lz_build_dir/include + cp -r -t $lz_build_dir/include $lz_project_dir/arch/$lz_arch/bits + + touch $lz_build_dir/headers.tag +} + + +musl_alltypes() +{ + if [ -f $lz_build_dir/alltypes.tag ]; then + lz_ok && return + fi + + sed -f $lz_project_dir/tools/mkalltypes.sed \ + $lz_build_dir/include/bits/alltypes.h.in \ + $lz_project_dir/include/alltypes.h.in > \ + $lz_build_dir/include/bits/alltypes.h + + touch $lz_build_dir/alltypes.tag +} + + +musl_version() +{ + if [ -f $lz_build_dir/version.tag ]; then + lz_ok && return + fi + + lz_pushd $lz_project_dir + lzp_version=`sh tools/version.sh` + lz_popd + + printf '#define VERSION "%s"\n' $lzp_version \ + > $lz_build_dir/include/version.h + + touch $lz_build_dir/version.tag +} + + +musl_empty_libs() +{ + if [ -f $lz_build_dir/empty_libs.tag ]; then + lz_ok && return + fi + + for lzp_lib_name in $musl_empty_lib_names; do + lzp_lib_file_name=$lz_build_dir/lib/lib$lzp_lib_name.a + rm -f $lzp_lib_file_name + $lz_ar rc $lzp_lib_file_name + done + + touch $lz_build_dir/empty_libs.tag +} + +musl_crt() +{ + musl_headers + musl_alltypes + + lz_cflags_extra="$musl_cflags_crt" + lz_src_dirs="crt" + + lz_compile "$musl_crt_obj_list" "$musl_crt_src_list" "$lz_stobj_ext" +} + + +musl_libc_common() +{ + musl_headers + musl_alltypes + musl_version +} + + +musl_libc_shared() +{ + musl_libc_common + musl_crt + + # memory functions + lz_cflags_extra="$musl_cflags_shared" + lz_cflags_special="$musl_cflags_memops" + lz_src_files="$musl_libc_mem_files" + lz_src_dirs=$lz_ignore_src_dirs + + lz_compile "$musl_libc_so_obj_list" "$musl_libc_so_src_list" "$lz_dyobj_ext" + + lz_src_files= + lz_cflags_special= + + # regular source files + lz_cumulative_obj_list=yes + lz_src_dirs=$musl_libc_src_dirs + lz_exclude_src_files="$musl_libc_mem_files" + lz_compiler_rt_libs="$lz_compiler_rt_libs $lz_link_libgcc" + + if [ "$lz_pecoff_winnt"x = yesx ]; then + musl_crti_objs="musl_crti_objs.lst" + musl_crtn_objs="musl_crtn_objs.lst" + echo 'crt/crti.o' > $musl_crti_objs + echo 'crt/crtn.o' > $musl_crtn_objs + else + musl_crti_objs= + musl_crtn_objs= + fi + + rm -f "$musl_libc_so_name" + + lz_compile "$musl_libc_so_obj_list" "$musl_libc_so_src_list" "$lz_dyobj_ext" + lz_link "$musl_crti_objs $musl_libc_so_obj_list $musl_crtn_objs" \ + "$musl_libc_so_src_list" \ + "$musl_libc_so_name" \ + "$musl_libc_so_ldflags" \ + "$lz_compiler_rt_libs" \ + "$lz_arch_dynamic_syscall_libs" +} + + +musl_libc_static() +{ + musl_libc_common + + # memory functions + lz_cflags_special="$musl_cflags_memops" + lz_src_files="$musl_libc_mem_files" + lz_src_dirs=$lz_ignore_src_dirs + + lz_compile "$musl_libc_a_obj_list" "$musl_libc_a_src_list" "$lz_stobj_ext" + lz_src_files= + lz_cflags_special= + + # regular source files + lz_cumulative_obj_list=yes + lz_src_dirs=$musl_libc_src_dirs + lz_exclude_src_files="$musl_libc_mem_files" + + rm -f "$musl_libc_a_name" + + lz_compile "$musl_libc_a_obj_list" "$musl_libc_a_src_list" "$lz_stobj_ext" + lz_archive "$musl_libc_a_obj_list" "$musl_libc_a_src_list" "$musl_libc_a_name" + + if [ "$lz_pecoff_winnt"x = yesx ]; then + if [ "$lz_arch_dynamic_syscall_libs"x != x ]; then + $lz_ar rc "$musl_libc_a_name" "$lz_arch_static_syscall_libs" + fi + fi +} + + +musl_libc_shared_no_complex() +{ + lz_link_libgcc= + lz_exclude_src_dirs="src/complex" + musl_libc_shared +} + + +musl_libc_static_no_complex() +{ + lz_exclude_src_dirs="src/complex" + musl_libc_static +} + + +musl_libc() +{ + lz_link_libgcc="--as-needed `$lz_c_compiler -print-file-name=libgcc.a`" + lz_step musl_crt + lz_step musl_libc_shared + lz_step musl_libc_static + lz_step musl_empty_libs +} + + +musl_libc_no_complex() +{ + lz_step musl_crt + lz_step musl_libc_shared_no_complex + lz_step musl_libc_static_no_complex + lz_step musl_empty_libs +} + + +musl_all() +{ + lz_step musl_libc +} + + +musl_install_crt() +{ + lz_pushd $lz_build_dir/crt + + musl_crt_files=`cat $lz_build_dir/crt.objs` + + for lzp_crt_file in $musl_crt_files; do + lzp_crt_obj_file=`basename $lzp_crt_file` + $musl_install_sh -D $lzp_crt_obj_file $lz_libdir/$lzp_crt_obj_file + done + + lz_popd +} + + +musl_install_libs() +{ + lz_pushd $lz_build_dir/lib + + for lzp_lib_file in "c" $musl_empty_lib_names; do + $musl_install_sh -D -m 644 lib$lzp_lib_file$lz_stlib_ext $lz_libdir/lib$lzp_lib_file$lz_stlib_ext + done + + $musl_install_sh -D -m 755 libc$lz_dylib_ext $lz_libdir/libc$lz_dylib_ext + + if [ "$lz_pecoff_winnt"x = yesx ]; then + # also install the import library + $musl_install_sh -D -m 644 libc$lz_implib_ext $lz_libdir/libc$lz_implib_ext + fi + + lz_popd +} + + +musl_install_ldso() +{ + $musl_install_sh -D -l $lz_libdir/libc$lz_dylib_ext $musl_ldso + $musl_install_sh -D -l $lz_libdir/libc$lz_dylib_ext $lz_bindir/ldd +} + + +musl_install_headers() +{ + lz_pushd $lz_project_dir/include + + musl_include_files=`find . -type f` + + for lzp_include_file in $musl_include_files; do + $musl_install_sh -D -m 644 $lzp_include_file $lz_includedir/$lzp_include_file + done + + lz_popd +} + + +musl_install_arch_headers() +{ + lz_pushd $lz_build_dir/include + + musl_include_files=`find ./bits -type f ! -name *.h.in` + + for lzp_include_file in $musl_include_files; do + $musl_install_sh -D -m 644 $lzp_include_file $lz_includedir/$lzp_include_file + done + + lz_popd +} + + +musl_install_specs() +{ + sh $lz_project_dir/tools/musl-gcc.specs.sh \ + $(readlink -f "$lz_includedir") \ + $(readlink -f "$lz_libdir") \ + $(readlink -f "$musl_ldso") \ + > $lz_libdir/musl-gcc.specs +} + + +musl_install_common() +{ + lz_step musl_install_crt + lz_step musl_install_libs + lz_step musl_install_ldso + lz_step musl_install_headers + lz_step musl_install_arch_headers + lz_step musl_install_specs +} + + +musl_install() +{ + lz_step musl_all + lz_step musl_install_common +} + + +musl_install_no_complex() +{ + lz_step musl_libc_no_complex + lz_step musl_install_common +} + diff --git a/src/env/nt64/__environ.s b/src/env/nt64/__environ.s new file mode 100644 index 0000000..28ac875 --- /dev/null +++ b/src/env/nt64/__environ.s @@ -0,0 +1,11 @@ +.globl ___environ +.globl __environ +.globl _environ +.globl environ + +.data +___environ: +__environ: +_environ: +environ: + .quad 0 diff --git a/src/fcntl/nt64/posix_fadvise.c b/src/fcntl/nt64/posix_fadvise.c new file mode 100644 index 0000000..c95d7f4 --- /dev/null +++ b/src/fcntl/nt64/posix_fadvise.c @@ -0,0 +1,14 @@ +#include "fcntl.h" +#include "syscall_arch.h" + +int posix_fadvise (int fd, off_t base, off_t len, int advice) +{ + /** + * __syscall is needed here due to the odd semantics + * of posix_fadvise(), which for us means calling + * __sys_fadvise() directly. + **/ + + return 0; /* __sys_fadvise (fd, base, len, advice); */ +} + diff --git a/src/internal/nt64/libc.c b/src/internal/nt64/libc.c new file mode 100644 index 0000000..43face8 --- /dev/null +++ b/src/internal/nt64/libc.c @@ -0,0 +1,7 @@ +#include "../libc.h" + +/* todo: teach the linker to export weak symbols */ +#undef weak_alias +#define weak_alias(old,new) extern __typeof(old) new __attribute__((alias(#old))) + +#include "../libc.c" diff --git a/src/internal/nt64/syscall.s b/src/internal/nt64/syscall.s new file mode 100644 index 0000000..ce3827b --- /dev/null +++ b/src/internal/nt64/syscall.s @@ -0,0 +1,5 @@ +.text +.global __syscall + +__syscall: + jmp __syscall_disp diff --git a/src/ldso/nt64/dl_iterate_phdr.c b/src/ldso/nt64/dl_iterate_phdr.c new file mode 100644 index 0000000..f98a509 --- /dev/null +++ b/src/ldso/nt64/dl_iterate_phdr.c @@ -0,0 +1,10 @@ +#include <stddef.h> +#include <dlfcn.h> +#include <link.h> + +typedef int __ldso_phdr_callback(struct dl_phdr_info * info, size_t size, void * data); + +int dl_iterate_phdr(__ldso_phdr_callback * callback, void * data) +{ + return -1; +} diff --git a/src/ldso/nt64/dynlink.c b/src/ldso/nt64/dynlink.c new file mode 100644 index 0000000..e5329e6 --- /dev/null +++ b/src/ldso/nt64/dynlink.c @@ -0,0 +1,58 @@ +#define _BSD_SOURCE + +#include <dlfcn.h> +#include "pthread_impl.h" + +int __dladdr(const void * addr, Dl_info * info) +{ + return 0; +} + +int __dlinfo(void * dso, int req, void * res) +{ + return 0; +} + +void *__dlsym(void * restrict p, const char * restrict s, void * restrict ra) +{ + return 0; +} + +void * dlopen(const char * file, int mode) +{ + return 0; +} + +int dlclose(void *p) +{ + return 0; +} + +char * dlerror(void) +{ + return 0; +} + +void __reset_tls(void) +{ +} + +void *__copy_tls(unsigned char * mem) +{ + /** + * this is always the simple case, since: + * emutls is based on PE named sections; and + * tls allocation and initialization are handled by clone(2) + **/ + + pthread_t td; + void ** dtv; + + dtv = (void **)mem; + dtv[0] = 0; + + td = (void *)(dtv + 1); + td->dtv = dtv; + + return td; +} diff --git a/src/ldso/nt64/start.s b/src/ldso/nt64/start.s new file mode 100644 index 0000000..32dc52f --- /dev/null +++ b/src/ldso/nt64/start.s @@ -0,0 +1,2 @@ +# standard dynamic loader is not required +# optional dynamic loader [to be] provided by libldso/libpsxscl diff --git a/src/ldso/nt64/tlsdesc.c b/src/ldso/nt64/tlsdesc.c new file mode 100644 index 0000000..7015e30 --- /dev/null +++ b/src/ldso/nt64/tlsdesc.c @@ -0,0 +1,8 @@ +#include <stddef.h> + +ptrdiff_t __tlsdesc_static(void) +{ + return 0; +} + +ptrdiff_t __tlsdesc_dynamic(void) __attribute__((alias("__tlsdesc_static"))); diff --git a/src/setjmp/nt64/longjmp.s b/src/setjmp/nt64/longjmp.s new file mode 100644 index 0000000..0fcf52e --- /dev/null +++ b/src/setjmp/nt64/longjmp.s @@ -0,0 +1,28 @@ +.text +.globl __longjmp +.globl _longjmp +.globl longjmp + +__longjmp: +_longjmp: +longjmp: + test %edx, %edx # is val zero? + jne 1f # no: return val + xor $1, %edx # yes: return one + +1: + mov %edx, %eax # return value + +2: + mov 0x10(%rcx), %rbx # restore regs + mov 0x18(%rcx), %rbp + mov 0x20(%rcx), %rdi + mov 0x28(%rcx), %rsi + mov 0x30(%rcx), %r12 + mov 0x38(%rcx), %r13 + mov 0x40(%rcx), %r14 + mov 0x48(%rcx), %r15 + + mov 0x08(%rcx), %rsp # saved stack pointer + mov (%rcx), %rdx # return address + jmp *%rdx # return diff --git a/src/setjmp/nt64/setjmp.s b/src/setjmp/nt64/setjmp.s new file mode 100644 index 0000000..3e8a1ea --- /dev/null +++ b/src/setjmp/nt64/setjmp.s @@ -0,0 +1,23 @@ +.text +.globl __setjmp +.globl _setjmp +.globl setjmp + +__setjmp: +_setjmp: +setjmp: + pop (%rcx) # return address + mov %rsp, 0x08(%rcx) # caller's stack pointer + push (%rcx) # restore own stack pointer + + mov %rbx, 0x10(%rcx) + mov %rbp, 0x18(%rcx) + mov %rdi, 0x20(%rcx) + mov %rsi, 0x28(%rcx) + mov %r12, 0x30(%rcx) + mov %r13, 0x38(%rcx) + mov %r14, 0x40(%rcx) + mov %r15, 0x48(%rcx) + + xor %eax, %eax + ret diff --git a/src/thread/nt64/__set_thread_area.c b/src/thread/nt64/__set_thread_area.c new file mode 100644 index 0000000..c50f6c6 --- /dev/null +++ b/src/thread/nt64/__set_thread_area.c @@ -0,0 +1,13 @@ +#include <errno.h> +#include "pthread_impl.h" + +int __set_thread_area(void * p) +{ + struct pthread ** ptlca; + + ptlca = __psx_tlca(); + if (!ptlca) return -ESRCH; + + *ptlca = p; + return 0; +} diff --git a/src/thread/nt64/__tls_get_addr.c b/src/thread/nt64/__tls_get_addr.c new file mode 100644 index 0000000..ad8d845 --- /dev/null +++ b/src/thread/nt64/__tls_get_addr.c @@ -0,0 +1,2 @@ +/* using a custom, register-based __emutls_get_address */ +typedef int dummy; diff --git a/src/thread/nt64/clone.c b/src/thread/nt64/clone.c new file mode 100644 index 0000000..d460855 --- /dev/null +++ b/src/thread/nt64/clone.c @@ -0,0 +1,62 @@ +#include <syscall.h> + +struct pt_regs { + unsigned long r15; + unsigned long r14; + unsigned long r13; + unsigned long r12; + unsigned long rbp; + unsigned long rbx; + unsigned long r11; + unsigned long r10; + unsigned long r9; + unsigned long r8; + unsigned long rax; + unsigned long rcx; + unsigned long rdx; + unsigned long rsi; + unsigned long rdi; + unsigned long orig_rax; + unsigned long rip; + unsigned long cs; + unsigned long eflags; + unsigned long rsp; + unsigned long ss; +}; + +typedef long __sys_clone( + unsigned long flags, + void * child_stack, + void * ptid, + void * ctid, + struct pt_regs *regs); + +typedef int __entry_point(void *); + +extern unsigned long ** __syscall_vtbl; + +int __clone( + __entry_point * fn, + void * child_stack, + int flags, + void * arg, + int * ptid, + void * pthread_self_addr, + int * ctid) +{ + struct pt_regs regs; + __sys_clone * pfn_clone; + + regs.rip = (unsigned long)fn; + regs.rcx = (unsigned long)arg; + regs.rdx = (unsigned long)pthread_self_addr; + + pfn_clone = (__sys_clone *)(__syscall_vtbl[SYS_clone]); + + return (int)pfn_clone( + flags, + child_stack, + ptid, + ctid, + ®s); +} diff --git a/src/thread/nt64/pthread_detach.c b/src/thread/nt64/pthread_detach.c new file mode 100644 index 0000000..85db4cb --- /dev/null +++ b/src/thread/nt64/pthread_detach.c @@ -0,0 +1,6 @@ +#include "../pthread_detach.c" + +int __pthread_detach_impl(pthread_t t) +{ + return thrd_detach(t); +} diff --git a/src/thread/nt64/pthread_equal.c b/src/thread/nt64/pthread_equal.c new file mode 100644 index 0000000..a8fcd79 --- /dev/null +++ b/src/thread/nt64/pthread_equal.c @@ -0,0 +1,6 @@ +#include "../pthread_equal.c" + +int __pthread_equal_impl(pthread_t a, pthread_t b) +{ + return thrd_equal(a,b); +} diff --git a/src/thread/nt64/pthread_self.c b/src/thread/nt64/pthread_self.c new file mode 100644 index 0000000..23fbc53 --- /dev/null +++ b/src/thread/nt64/pthread_self.c @@ -0,0 +1,10 @@ +#include "pthread_impl.h" +#include <threads.h> +#include "libc.h" + +pthread_t pthread_self() +{ + return __pthread_self(); +} + +weak_alias(pthread_self, thrd_current); diff --git a/src/thread/nt64/syscall_cp.s b/src/thread/nt64/syscall_cp.s new file mode 100644 index 0000000..b8b7039 --- /dev/null +++ b/src/thread/nt64/syscall_cp.s @@ -0,0 +1,29 @@ +.text +.globl __syscall_cp_asm +.globl __cp_begin +.globl __cp_end + +__syscall_cp_asm: +__cp_begin: + movq (%rcx), %rcx /* check content of ptr */ + test %ecx, %ecx + jnz __cancel /* thread is pending cancellation */ + + movq %rdx, %rcx/* move water */ + movq %r8, %rdx/* from one glass */ + movq %r9, %r8 /* to another */ + movq 0x28(%rsp), %r9 + + movq 0x30(%rsp),%rax + movq %rax, 0x28(%rsp) + + movq 0x38(%rsp),%r10 + movq %r10, 0x30(%rsp) + + movq 0x40(%rsp),%r10 + movq %r10, 0x38(%rsp) + + jmp __syscall + +__cp_end: + ret |