Yarn: Implement fiber context switching for Windows, macOS, Linux and Android. Windows uses OSFiber_windows.hpp. macOS and Linux uses OSFiber_asm_* or OSFiber_ucontext.hpp Android has no support for makecontext / swapcontext, and so relies on the OSFiber_asm_* implementations. Unlike makecontext, swapcontext or the Windows fiber APIs, these assembly implementations *do not* save or restore signal masks, floating-point control or status registers, FS and GS segment registers, thread-local storage state nor any SIMD registers. This should not be a problem as the yarn scheduler requires fibers to be executed on a single thread. Bug: b/139010488 Change-Id: I5f890ffe4f069361a7eeae64567a77be3a4ba008 Reviewed-on: https://swiftshader-review.googlesource.com/c/SwiftShader/+/34771 Tested-by: Ben Clayton <bclayton@google.com> Reviewed-by: Nicolas Capens <nicolascapens@google.com> Kokoro-Presubmit: kokoro <noreply+kokoro@google.com>
diff --git a/src/Yarn/OSFiber_asm_aarch64.c b/src/Yarn/OSFiber_asm_aarch64.c new file mode 100644 index 0000000..7b09c58 --- /dev/null +++ b/src/Yarn/OSFiber_asm_aarch64.c
@@ -0,0 +1,33 @@ +// Copyright 2019 The SwiftShader Authors. All Rights Reserved. +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#if defined(__aarch64__) + +#include "OSFiber_asm_aarch64.h" + +void yarn_fiber_trampoline(void(*target)(void*), void* arg) +{ + target(arg); +} + +void yarn_fiber_set_target(struct yarn_fiber_context* ctx, void* stack, uint32_t stack_size, void(*target)(void*), void* arg) +{ + uintptr_t* stack_top = (uintptr_t*)((uint8_t*)(stack) + stack_size); + ctx->LR = (uintptr_t)&yarn_fiber_trampoline; + ctx->r0 = (uintptr_t)target; + ctx->r1 = (uintptr_t)arg; + ctx->SP = ((uintptr_t)stack_top) & ~(uintptr_t)15; +} + +#endif // defined(__aarch64__)