[libc-commits] [libc] [libc][arm] implement a basic setjmp/longjmp (PR #93220)
Simon Tatham via libc-commits
libc-commits at lists.llvm.org
Tue May 28 03:15:44 PDT 2024
================
@@ -0,0 +1,68 @@
+
+//===-- Implementation of longjmp -----------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "src/setjmp/longjmp.h"
+#include "src/__support/common.h"
+
+namespace LIBC_NAMESPACE {
+
+#if defined(__thumb__) && __ARM_ARCH_ISA_THUMB == 1
+
+[[gnu::naked, gnu::target("thumb")]]
+LLVM_LIBC_FUNCTION(void, longjmp, (__jmp_buf * buf, int val)) {
+ asm(R"(
+ # Reload r4, r5, r6, r7.
+ ldmia r0!, {r4, r5, r6, r7}
+
+ # Reload r8, r9, r10. They cannot appear in register lists so load them
+ # into the lower registers, then move them into place.
+ ldmia r0!, {r1, r2, r3}
+ mov r8, r1
+ mov r9, r2
+ mov r10, r3
+
+ # Reload r11, sp, lr. They cannot appear in register lists so load them
+ # into the lower registers, then move them into place.
+ ldmia r0!, {r1, r2, r3}
+ mov r11, r1
+ mov sp, r2
+ mov lr, r3
+
+ # return val ?: 1;
+ movs r0, r1
----------------
statham-arm wrote:
This use of r1 ought to be accessing the value passed in to `longjmp` as a parameter. But that's not what's in r1 right now. The previous two `ldmia` both clobbered it. At the point of this instruction, the value in r1 is whatever value the jmp_buf had saved for r11.
https://github.com/llvm/llvm-project/pull/93220
More information about the libc-commits
mailing list