xref: /aosp_15_r20/external/musl/src/thread/sh/__set_thread_area.c (revision c9945492fdd68bbe62686c5b452b4dc1be3f8453)
1 #include "pthread_impl.h"
2 #include "libc.h"
3 #include <elf.h>
4 
5 /* Also perform sh-specific init */
6 
7 #define CPU_HAS_LLSC 0x0040
8 #define CPU_HAS_CAS_L 0x0400
9 
10 extern hidden const char __sh_cas_gusa[], __sh_cas_llsc[], __sh_cas_imask[], __sh_cas_cas_l[];
11 
12 hidden const void *__sh_cas_ptr;
13 
14 hidden unsigned __sh_nommu;
15 
__set_thread_area(void * p)16 int __set_thread_area(void *p)
17 {
18 	size_t *aux;
19 	__asm__ __volatile__ ( "ldc %0, gbr" : : "r"(p) : "memory" );
20 #ifndef __SH4A__
21 	__sh_cas_ptr = __sh_cas_gusa;
22 #if !defined(__SH3__) && !defined(__SH4__)
23 	for (aux=libc.auxv; *aux; aux+=2) {
24 		if (*aux != AT_PLATFORM) continue;
25 		const char *s = (void *)aux[1];
26 		if (s[0]!='s' || s[1]!='h' || s[2]!='2' || s[3]-'0'<10u) break;
27 		__sh_cas_ptr = __sh_cas_imask;
28 		__sh_nommu = 1;
29 	}
30 #endif
31 	if (__hwcap & CPU_HAS_CAS_L)
32 		__sh_cas_ptr = __sh_cas_cas_l;
33 	else if (__hwcap & CPU_HAS_LLSC)
34 		__sh_cas_ptr = __sh_cas_llsc;
35 #endif
36 	return 0;
37 }
38