Compatibility with LLVM libunwind
This commit is contained in:
parent
4e94dd4265
commit
5a8686eaf9
|
@ -51,6 +51,8 @@ SECTIONS
|
||||||
__ex_table : { *(__ex_table) }
|
__ex_table : { *(__ex_table) }
|
||||||
|
|
||||||
.eh_frame_hdr : { *(.eh_frame_hdr) }
|
.eh_frame_hdr : { *(.eh_frame_hdr) }
|
||||||
|
__eh_frame_hdr_start = SIZEOF(.eh_frame_hdr) > 0 ? ADDR(.eh_frame_hdr) : 0;
|
||||||
|
__eh_frame_hdr_end = SIZEOF(.eh_frame_hdr) > 0 ? . : 0;
|
||||||
|
|
||||||
. = ALIGN(0x1000);
|
. = ALIGN(0x1000);
|
||||||
|
|
||||||
|
@ -91,7 +93,9 @@ SECTIONS
|
||||||
/* exception frames for C++ */
|
/* exception frames for C++ */
|
||||||
.eh_frame : {
|
.eh_frame : {
|
||||||
__eh_frame_start__ = .;
|
__eh_frame_start__ = .;
|
||||||
|
__eh_frame_start = .;
|
||||||
KEEP (*(.eh_frame))
|
KEEP (*(.eh_frame))
|
||||||
|
__eh_frame_end = .;
|
||||||
LONG(0)
|
LONG(0)
|
||||||
} : rw
|
} : rw
|
||||||
|
|
||||||
|
|
|
@ -3,6 +3,16 @@ include_rules
|
||||||
DEFINES = -ffunction-sections -fno-strict-aliasing -g -fPIC
|
DEFINES = -ffunction-sections -fno-strict-aliasing -g -fPIC
|
||||||
# drop the standard defines to avoid -nostdinc
|
# drop the standard defines to avoid -nostdinc
|
||||||
|
|
||||||
|
export LIBCXX
|
||||||
|
export LIBCXXABI
|
||||||
|
export LIBUNWIND
|
||||||
|
|
||||||
|
INCLUDES += -I$LIBCXX/include/c++/v1
|
||||||
|
INCLUDES += -I$LIBCXXABI/include
|
||||||
|
|
||||||
|
LLVM_LIBS += $LIBCXXABI/lib/libc++abi.a
|
||||||
|
LLVM_LIBS += $LIBUNWIND/lib/libunwind.a
|
||||||
|
|
||||||
: foreach *.cc |> !cxx |> {supc++}
|
: foreach *.cc |> !cxx |> {supc++}
|
||||||
|
|
||||||
#
|
#
|
||||||
|
@ -18,11 +28,7 @@ KEEP_SYMBOLS = \
|
||||||
-u _ZTVN10__cxxabiv119__pointer_type_infoE \
|
-u _ZTVN10__cxxabiv119__pointer_type_infoE \
|
||||||
-u _ZTSN10__cxxabiv120__function_type_infoE \
|
-u _ZTSN10__cxxabiv120__function_type_infoE \
|
||||||
|
|
||||||
LIBCXX_GCC = \
|
: {supc++} |> $(LD) $(LD_MARCH) $(KEEP_SYMBOLS) -r %f $(LLVM_LIBS) -o %o |> supc++.tmp
|
||||||
`$(CXX) $(CC_MARCH) -print-file-name=libsupc++.a` \
|
|
||||||
`$(CXX) $(CC_MARCH) -print-file-name=libgcc_eh.a` \
|
|
||||||
|
|
||||||
: {supc++} |> $(LD) $(LD_MARCH) $(KEEP_SYMBOLS) -r %f $(LIBCXX_GCC) -o %o |> supc++.tmp
|
|
||||||
|
|
||||||
#
|
#
|
||||||
# Here we define all symbols we want to hide in libsupc++ and libgcc_eh
|
# Here we define all symbols we want to hide in libsupc++ and libgcc_eh
|
||||||
|
@ -63,7 +69,8 @@ EH_SYMBOLS += \
|
||||||
|
|
||||||
REDEF_SYMBOLS = `echo $(EH_SYMBOLS) | awk -v RS=' ' '{ print "--redefine-sym "$1"=_cxx_"$1 }'`
|
REDEF_SYMBOLS = `echo $(EH_SYMBOLS) | awk -v RS=' ' '{ print "--redefine-sym "$1"=_cxx_"$1 }'`
|
||||||
|
|
||||||
: supc++.tmp |> $(OBJCOPY) $(LOCAL_SYMBOLS) $(REDEF_SYMBOLS) %f %o |> supc++.o {obj}
|
export OBJCOPY
|
||||||
|
: supc++.tmp |> $OBJCOPY $(LOCAL_SYMBOLS) $(REDEF_SYMBOLS) %f %o |> supc++.o {obj}
|
||||||
|
|
||||||
: foreach *.c |> !cc |> {obj}
|
: foreach *.c |> !cc |> {obj}
|
||||||
|
|
||||||
|
|
|
@ -66,8 +66,14 @@ typedef unsigned long Block_header;
|
||||||
|
|
||||||
extern "C" void *malloc(size_t size)
|
extern "C" void *malloc(size_t size)
|
||||||
{
|
{
|
||||||
/* enforce size to be a multiple of 4 bytes */
|
/*
|
||||||
size = (size + 3) & ~3;
|
* Use a double-word aligned allocations as required by the Itanium C++ ABI.
|
||||||
|
*
|
||||||
|
* See https://itanium-cxx-abi.github.io/cxx-abi/abi-eh.html#base-data
|
||||||
|
*/
|
||||||
|
|
||||||
|
constexpr size_t align_mask = sizeof(long)*2 - 1;
|
||||||
|
size = (size + align_mask) & ~align_mask;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* We store the size of the allocation at the very
|
* We store the size of the allocation at the very
|
||||||
|
@ -75,13 +81,21 @@ extern "C" void *malloc(size_t size)
|
||||||
* the subsequent address. This way, we can retrieve
|
* the subsequent address. This way, we can retrieve
|
||||||
* the size information when freeing the block.
|
* the size information when freeing the block.
|
||||||
*/
|
*/
|
||||||
unsigned long real_size = size + sizeof(Block_header);
|
unsigned long real_size = size + sizeof(Block_header)*2;
|
||||||
void *addr = 0;
|
void *addr = 0;
|
||||||
if (!cxx_heap().alloc(real_size, &addr))
|
if (!cxx_heap().alloc(real_size, &addr))
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
*(Block_header *)addr = real_size;
|
*(Block_header *)addr = real_size;
|
||||||
return (Block_header *)addr + 1;
|
|
||||||
|
return (Block_header *)addr + 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
extern "C" int posix_memalign(void **dest, size_t /*align*/, size_t size)
|
||||||
|
{
|
||||||
|
*dest = malloc(size);
|
||||||
|
return *dest ? 0 : 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -97,7 +111,7 @@ extern "C" void free(void *ptr)
|
||||||
{
|
{
|
||||||
if (!ptr) return;
|
if (!ptr) return;
|
||||||
|
|
||||||
unsigned long *addr = ((unsigned long *)ptr) - 1;
|
unsigned long *addr = ((unsigned long *)ptr) - 2;
|
||||||
cxx_heap().free(addr, *addr);
|
cxx_heap().free(addr, *addr);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -113,7 +127,7 @@ extern "C" void *realloc(void *ptr, Genode::size_t size)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* determine size of old block content (without header) */
|
/* determine size of old block content (without header) */
|
||||||
unsigned long old_size = *((Block_header *)ptr - 1)
|
unsigned long old_size = *((Block_header *)ptr - 2)
|
||||||
- sizeof(Block_header);
|
- sizeof(Block_header);
|
||||||
|
|
||||||
/* do not reallocate if new size is less than the current size */
|
/* do not reallocate if new size is less than the current size */
|
||||||
|
|
|
@ -62,9 +62,9 @@ extern "C" int __cxa_atexit(void(*func)(void*), void *arg,
|
||||||
extern int genode___cxa_finalize(void *dso);
|
extern int genode___cxa_finalize(void *dso);
|
||||||
|
|
||||||
|
|
||||||
extern "C" void __cxa_finalize(void *dso)
|
extern "C" int __cxa_finalize(void *dso)
|
||||||
{
|
{
|
||||||
genode___cxa_finalize(dso);
|
return genode___cxa_finalize(dso);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -127,6 +127,17 @@ extern "C" void abort(void)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
extern "C" int fflush(void*) {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
extern "C" int fprintf(void*, const char *msg, ...) {
|
||||||
|
Genode::warning("C++ runtime: ", msg);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
extern "C" int fputc(int, void*) {
|
extern "C" int fputc(int, void*) {
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
@ -215,6 +226,12 @@ extern "C" int strcmp(const char *s1, const char *s2)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
extern "C" char *getenv(const char *)
|
||||||
|
{
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Needed by ARM EABI (gcc-4.4 Codesourcery release1039)
|
* Needed by ARM EABI (gcc-4.4 Codesourcery release1039)
|
||||||
*/
|
*/
|
||||||
|
@ -225,6 +242,42 @@ extern "C" int sprintf(char *, const char *, ...)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Needed by Clang/Libunwind/Libc++abi
|
||||||
|
*/
|
||||||
|
|
||||||
|
extern "C" {
|
||||||
|
|
||||||
|
|
||||||
|
void __assert(const char *, const char *, int, const char *) {
|
||||||
|
std::terminate();
|
||||||
|
}
|
||||||
|
|
||||||
|
int tolower(int c) { return c; }
|
||||||
|
int isdigit(int) { return 0; }
|
||||||
|
int isxdigit(int) { return 0; }
|
||||||
|
int islower(int) { return 0; }
|
||||||
|
|
||||||
|
|
||||||
|
int snprintf(char *, size_t, const char *, ...) { return 0; }
|
||||||
|
|
||||||
|
int vfprintf(FILE *, const char *msg, va_list)
|
||||||
|
{
|
||||||
|
Genode::warning("C++ runtime: ", msg);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
struct Dl_info;
|
||||||
|
int dladdr(const void *, Dl_info *) { return 0; }
|
||||||
|
|
||||||
|
struct pthread_rwlock_t;
|
||||||
|
int pthread_rwlock_rdlock(pthread_rwlock_t *) { return 0; }
|
||||||
|
int pthread_rwlock_unlock(pthread_rwlock_t *) { return 0; }
|
||||||
|
int pthread_rwlock_wrlock(pthread_rwlock_t *) { return 0; }
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
/**********************************
|
/**********************************
|
||||||
** Support for stack protection **
|
** Support for stack protection **
|
||||||
**********************************/
|
**********************************/
|
||||||
|
|
|
@ -67,7 +67,7 @@ void operator delete (void *ptr, Deallocator &dealloc) { try_dealloc(ptr, deall
|
||||||
* implementation of the 'stdcxx' library instead. To make this possible, the
|
* implementation of the 'stdcxx' library instead. To make this possible, the
|
||||||
* 'delete (void *)' implementation in the 'cxx' library must be 'weak'.
|
* 'delete (void *)' implementation in the 'cxx' library must be 'weak'.
|
||||||
*/
|
*/
|
||||||
__attribute__((weak)) void operator delete (void *)
|
__attribute__((weak)) void operator delete (void *) noexcept
|
||||||
{
|
{
|
||||||
Genode::error("cxx: operator delete (void *) called - not implemented. "
|
Genode::error("cxx: operator delete (void *) called - not implemented. "
|
||||||
"A working implementation is available in the 'stdcxx' library.");
|
"A working implementation is available in the 'stdcxx' library.");
|
||||||
|
|
Loading…
Reference in New Issue
Block a user