From mboxrd@z Thu Jan 1 00:00:00 1970 From: Ivan Gorinov Date: Wed, 30 May 2018 15:50:08 -0700 Subject: [U-Boot] [PATCH] x86: Add 64-bit setjmp/longjmp implementation Message-ID: <20180530225008.GA14660@intel.com> List-Id: MIME-Version: 1.0 Content-Type: text/plain; charset="us-ascii" Content-Transfer-Encoding: 7bit To: u-boot@lists.denx.de Add setjmp/longjmp functions for x86_64, based on existing 32-bit implementation. Signed-off-by: Ivan Gorinov --- arch/x86/cpu/x86_64/setjmp.S | 56 +++++++++++++++++++++++++++++++++++++++++++ arch/x86/cpu/x86_64/setjmp.c | 19 --------------- arch/x86/include/asm/setjmp.h | 17 +++++++++++++ 3 files changed, 73 insertions(+), 19 deletions(-) create mode 100644 arch/x86/cpu/x86_64/setjmp.S delete mode 100644 arch/x86/cpu/x86_64/setjmp.c diff --git a/arch/x86/cpu/x86_64/setjmp.S b/arch/x86/cpu/x86_64/setjmp.S new file mode 100644 index 0000000..e10ee49 --- /dev/null +++ b/arch/x86/cpu/x86_64/setjmp.S @@ -0,0 +1,56 @@ +/* + * Based on arch/x86/cpu/i386/setjmp.S by H. Peter Anvin + * + * SPDX-License-Identifier: GPL-2.0 + */ + +/* + * The jmp_buf is assumed to contain the following, in order: + * + * %rsp + * %rbp + * %rbx + * %r12 + * %r13 + * %r14 + * %r15 + */ + +.text +.align 8 +.globl setjmp +.type setjmp, @function + +setjmp: + pop %rcx + movq %rcx, (%rdi) /* Return address */ + movq %rsp, 8 (%rdi) /* Post-return %rsp! */ + movq %rbp, 16 (%rdi) + movq %rbx, 24 (%rdi) + movq %r12, 32 (%rdi) + movq %r13, 40 (%rdi) + movq %r14, 48 (%rdi) + movq %r15, 56 (%rdi) + xorq %rax, %rax /* Return value */ + jmpq *%rcx + +/* Provide function size if needed */ +.size setjmp, .-setjmp + +.align 8 +.globl longjmp +.type longjmp, @function + +longjmp: + movq 32 (%rdi), %r12 + movq 40 (%rdi), %r13 + movq 48 (%rdi), %r14 + movq 56 (%rdi), %r15 + movq 16 (%rdi), %rbp + movq 24 (%rdi), %rbx + movq 8 (%rdi), %rsp + movq (%rdi), %rcx + movq %rsi, %rdi + jmpq *%rcx + + .size longjmp, .-longjmp diff --git a/arch/x86/cpu/x86_64/setjmp.c b/arch/x86/cpu/x86_64/setjmp.c deleted file mode 100644 index 5d4a74a..0000000 --- a/arch/x86/cpu/x86_64/setjmp.c +++ /dev/null @@ -1,19 +0,0 @@ -// SPDX-License-Identifier: GPL-2.0+ -/* - * Copyright (c) 2016 Google, Inc - */ - -#include -#include - -int setjmp(struct jmp_buf_data *jmp_buf) -{ - printf("WARNING: setjmp() is not supported\n"); - - return 0; -} - -void longjmp(struct jmp_buf_data *jmp_buf, int val) -{ - printf("WARNING: longjmp() is not supported\n"); -} diff --git a/arch/x86/include/asm/setjmp.h b/arch/x86/include/asm/setjmp.h index f25975f..49c36c1 100644 --- a/arch/x86/include/asm/setjmp.h +++ b/arch/x86/include/asm/setjmp.h @@ -8,6 +8,21 @@ #ifndef __setjmp_h #define __setjmp_h +#ifdef CONFIG_X86_64 + +struct jmp_buf_data { + unsigned long __rip; + unsigned long __rsp; + unsigned long __rbp; + unsigned long __rbx; + unsigned long __r12; + unsigned long __r13; + unsigned long __r14; + unsigned long __r15; +}; + +#else + struct jmp_buf_data { unsigned int __ebx; unsigned int __esp; @@ -17,6 +32,8 @@ struct jmp_buf_data { unsigned int __eip; }; +#endif + int setjmp(struct jmp_buf_data *jmp_buf); void longjmp(struct jmp_buf_data *jmp_buf, int val); -- 2.7.4