@@ -116,7 +116,7 @@ struct Loaded {
116
116
Elf64_Phdr ph [25 ];
117
117
};
118
118
119
- static struct {
119
+ struct {
120
120
atomic_uint once ;
121
121
bool is_supported ;
122
122
struct CosmoTib * tib ;
@@ -125,9 +125,10 @@ static struct {
125
125
int (* dlclose )(void * );
126
126
char * (* dlerror )(void );
127
127
jmp_buf jb ;
128
- } foreign ;
128
+ } __foreign ;
129
129
130
130
long __sysv2nt14 ();
131
+ long foreign_tramp ();
131
132
132
133
static _Thread_local char dlerror_buf [128 ];
133
134
@@ -156,28 +157,6 @@ static int is_file_newer_than(const char *path, const char *other) {
156
157
return timespec_cmp (st1 .st_mtim , st2 .st_mtim ) > 0 ;
157
158
}
158
159
159
- // on system five we sadly need this brutal trampoline
160
- // todo(jart): add tls trampoline to sigaction() handlers
161
- // todo(jart): morph binary to get tls from host c library
162
- static long foreign_tramp (long a , long b , long c , long d , long e ,
163
- long func (long , long , long , long , long , double ,
164
- double , double , double , double , double ),
165
- double A , double B , double C , double D , double E ,
166
- double F ) {
167
- long res ;
168
- BLOCK_SIGNALS ;
169
- #ifdef __x86_64__
170
- struct CosmoTib * tib = __get_tls ();
171
- __set_tls (foreign .tib );
172
- #endif
173
- res = func (a , b , c , d , e , A , B , C , D , E , F );
174
- #ifdef __x86_64__
175
- __set_tls (tib );
176
- #endif
177
- ALLOW_SIGNALS ;
178
- return res ;
179
- }
180
-
181
160
static unsigned elf2prot (unsigned x ) {
182
161
unsigned r = 0 ;
183
162
if (x & PF_R ) r += PROT_READ ;
@@ -308,11 +287,11 @@ static long *push_strs(long *sp, char **list, int count) {
308
287
}
309
288
310
289
static wontreturn dontinstrument void foreign_helper (void * * p ) {
311
- foreign .dlopen = p [0 ];
312
- foreign .dlsym = p [1 ];
313
- foreign .dlclose = p [2 ];
314
- foreign .dlerror = p [3 ];
315
- longjmp (foreign .jb , 1 );
290
+ __foreign .dlopen = p [0 ];
291
+ __foreign .dlsym = p [1 ];
292
+ __foreign .dlclose = p [2 ];
293
+ __foreign .dlerror = p [3 ];
294
+ longjmp (__foreign .jb , 1 );
316
295
}
317
296
318
297
static dontinline void elf_exec (const char * file , char * * envp ) {
@@ -515,19 +494,19 @@ static uint8_t *movimm(uint8_t p[static 16], int reg, uint64_t val) {
515
494
static void * foreign_thunk_sysv (void * func ) {
516
495
uint8_t * code , * p ;
517
496
#ifdef __x86_64__
518
- // movabs $func,%r9
497
+ // movabs $func,%rax
519
498
// movabs $foreign_tramp,%r10
520
499
// jmp *%r10
521
500
if (!(p = code = foreign_alloc (23 ))) return 0 ; // 10 + 10 + 3 = 23
522
- p = movimm (p , 9 , (uintptr_t )func );
501
+ p = movimm (p , 0 , (uintptr_t )func );
523
502
p = movimm (p , 10 , (uintptr_t )foreign_tramp );
524
503
* p ++ = 0x41 ;
525
504
* p ++ = 0xff ;
526
505
* p ++ = 0xe2 ;
527
506
#elif defined(__aarch64__ )
528
507
__jit_begin ();
529
508
if ((p = code = foreign_alloc (36 ))) {
530
- p = movimm (p , 5 , (uintptr_t )func );
509
+ p = movimm (p , 8 , (uintptr_t )func );
531
510
p = movimm (p , 10 , (uintptr_t )foreign_tramp );
532
511
* (uint32_t * )p = 0xd61f0140 ; // br x10
533
512
__clear_cache (code , p + 4 );
@@ -671,19 +650,19 @@ static bool foreign_setup(void) {
671
650
#ifdef __x86_64__
672
651
struct CosmoTib * cosmo_tib = __get_tls ();
673
652
#endif
674
- if (!setjmp (foreign .jb )) {
653
+ if (!setjmp (__foreign .jb )) {
675
654
elf_exec (exe , environ );
676
655
return false; // if elf_exec() returns, it failed
677
656
}
678
657
#ifdef __x86_64__
679
- foreign .tib = __get_tls ();
658
+ __foreign .tib = __get_tls ();
680
659
__set_tls (cosmo_tib );
681
660
#endif
682
- foreign .dlopen = foreign_thunk_sysv (foreign .dlopen );
683
- foreign .dlsym = foreign_thunk_sysv (foreign .dlsym );
684
- foreign .dlclose = foreign_thunk_sysv (foreign .dlclose );
685
- foreign .dlerror = foreign_thunk_sysv (foreign .dlerror );
686
- foreign .is_supported = true;
661
+ __foreign .dlopen = foreign_thunk_sysv (__foreign .dlopen );
662
+ __foreign .dlsym = foreign_thunk_sysv (__foreign .dlsym );
663
+ __foreign .dlclose = foreign_thunk_sysv (__foreign .dlclose );
664
+ __foreign .dlerror = foreign_thunk_sysv (__foreign .dlerror );
665
+ __foreign .is_supported = true;
687
666
return true;
688
667
}
689
668
@@ -693,8 +672,8 @@ static void foreign_once(void) {
693
672
694
673
static bool foreign_init (void ) {
695
674
bool res ;
696
- cosmo_once (& foreign .once , foreign_once );
697
- if (!(res = foreign .is_supported )) {
675
+ cosmo_once (& __foreign .once , foreign_once );
676
+ if (!(res = __foreign .is_supported )) {
698
677
dlerror_set ("dlopen() isn't supported on this platform" );
699
678
}
700
679
return res ;
@@ -824,7 +803,7 @@ void *cosmo_dlopen(const char *path, int mode) {
824
803
dlerror_set ("dlopen() isn't supported on OpenBSD yet" );
825
804
res = 0 ;
826
805
} else if (foreign_init ()) {
827
- res = foreign .dlopen (path , mode );
806
+ res = __foreign .dlopen (path , mode );
828
807
} else {
829
808
res = 0 ;
830
809
}
@@ -854,7 +833,7 @@ void *cosmo_dlsym(void *handle, const char *name) {
854
833
dlerror_set ("dlopen() isn't supported on x86-64 MacOS" );
855
834
func = 0 ;
856
835
} else if (foreign_init ()) {
857
- if ((func = foreign .dlsym (handle , name ))) {
836
+ if ((func = __foreign .dlsym (handle , name ))) {
858
837
func = foreign_thunk_sysv (func );
859
838
}
860
839
} else {
@@ -880,7 +859,7 @@ int cosmo_dlclose(void *handle) {
880
859
dlerror_set ("dlopen() isn't supported on x86-64 MacOS" );
881
860
res = -1 ;
882
861
} else if (foreign_init ()) {
883
- res = foreign .dlclose (handle );
862
+ res = __foreign .dlclose (handle );
884
863
} else {
885
864
res = -1 ;
886
865
}
@@ -898,7 +877,7 @@ char *cosmo_dlerror(void) {
898
877
} else if (IsWindows () || IsXnu ()) {
899
878
res = dlerror_buf ;
900
879
} else if (foreign_init ()) {
901
- res = foreign .dlerror ();
880
+ res = __foreign .dlerror ();
902
881
res = dlerror_set (res );
903
882
} else {
904
883
res = dlerror_buf ;
0 commit comments