libcontext: Initial support for Apple Silicon

The assembly for apple_arm64 is adapted from linux_arm64 target with small modifications:

1. Re-enable FPU conditional save/restore as apple_x86_64 does
2. Workaround limitation in relocation in assembly for clang
This commit is contained in:
Jiajie Chen 2021-01-04 19:17:17 +08:00 committed by Seth Hillbrand
parent 31dd04fa96
commit ce8039c327
2 changed files with 94 additions and 0 deletions

View File

@ -531,6 +531,97 @@ __asm (
#endif
#if defined(LIBCONTEXT_PLATFORM_apple_arm64) && defined(LIBCONTEXT_COMPILER_gcc)
__asm (
".cpu generic+fp+simd\n"
".text\n"
".align 2\n"
".global _jump_fcontext\n"
"_jump_fcontext:\n"
" # prepare stack for GP + FPU\n"
" sub sp, sp, #0xb0\n"
" # test if fpu env should be preserved\n"
" cmp w3, #0\n"
" b.eq 1f\n"
" # save d8 - d15\n"
" stp d8, d9, [sp, #0x00]\n"
" stp d10, d11, [sp, #0x10]\n"
" stp d12, d13, [sp, #0x20]\n"
" stp d14, d15, [sp, #0x30]\n"
"1:\n"
" # save x19-x30\n"
" stp x19, x20, [sp, #0x40]\n"
" stp x21, x22, [sp, #0x50]\n"
" stp x23, x24, [sp, #0x60]\n"
" stp x25, x26, [sp, #0x70]\n"
" stp x27, x28, [sp, #0x80]\n"
" stp x29, x30, [sp, #0x90]\n"
" # save LR as PC\n"
" str x30, [sp, #0xa0]\n"
" # store RSP (pointing to context-data) in first argument (x0).\n"
" # STR cannot have sp as a target register\n"
" mov x4, sp\n"
" str x4, [x0]\n"
" # restore RSP (pointing to context-data) from A2 (x1)\n"
" mov sp, x1\n"
" # test if fpu env should be preserved\n"
" cmp w3, #0\n"
" b.eq 2f\n"
" # load d8 - d15\n"
" ldp d8, d9, [sp, #0x00]\n"
" ldp d10, d11, [sp, #0x10]\n"
" ldp d12, d13, [sp, #0x20]\n"
" ldp d14, d15, [sp, #0x30]\n"
"2:\n"
" # load x19-x30\n"
" ldp x19, x20, [sp, #0x40]\n"
" ldp x21, x22, [sp, #0x50]\n"
" ldp x23, x24, [sp, #0x60]\n"
" ldp x25, x26, [sp, #0x70]\n"
" ldp x27, x28, [sp, #0x80]\n"
" ldp x29, x30, [sp, #0x90]\n"
" # use third arg as return value after jump\n"
" # and as first arg in context function\n"
" mov x0, x2\n"
" # load pc\n"
" ldr x4, [sp, #0xa0]\n"
" # restore stack from GP + FPU\n"
" add sp, sp, #0xb0\n"
" ret x4\n"
);
#endif
#if defined(LIBCONTEXT_PLATFORM_apple_arm64) && defined(LIBCONTEXT_COMPILER_gcc)
__asm (
".cpu generic+fp+simd\n"
".text\n"
".align 2\n"
".global _make_fcontext\n"
"_make_fcontext:\n"
" # shift address in x0 (allocated stack) to lower 16 byte boundary\n"
" and x0, x0, ~0xF\n"
" # reserve space for context-data on context-stack\n"
" sub x0, x0, #0xb0\n"
" # third arg of make_fcontext() == address of context-function\n"
" # store address as a PC to jump in\n"
" str x2, [x0, #0xa0]\n"
" # save address of finish as return-address for context-function\n"
" # will be entered after context-function returns (LR register)\n"
" # need to relocate manually because of Clang limitation\n"
" adrp x1, finish@PAGE\n"
" add x1, x1, finish@PAGEOFF\n"
" str x1, [x0, #0x98]\n"
" ret x30 \n"
"finish:\n"
" # exit code is zero\n"
" mov x0, #0\n"
" # exit application\n"
" bl _exit\n"
);
#endif
#if defined(LIBCONTEXT_PLATFORM_linux_arm32) && defined(LIBCONTEXT_COMPILER_gcc)
__asm (
".text\n"

View File

@ -73,6 +73,9 @@
#elif defined(__x86_64__)
#define LIBCONTEXT_PLATFORM_apple_x86_64
#define LIBCONTEXT_CALL_CONVENTION
#elif __aarch64__
#define LIBCONTEXT_PLATFORM_apple_arm64
#define LIBCONTEXT_CALL_CONVENTION
#endif
#endif
#elif defined (_MSC_VER)