From 6ec0a1f8f48fb8eceb6281d579ddd4bb083b2411 Mon Sep 17 00:00:00 2001 From: Weimin Pan Date: Fri, 10 Feb 2023 15:43:53 -0800 Subject: sframebt: Factor register access code into a header file ChangeLog: * libsframe/sframe-backtrace-regs.h: New file. * libsframe/sframe-backtrace.c: Use the new abstractions. --- libsframe/sframe-backtrace-regs.h | 77 +++++++++++++++++++++++++++++++++++++++ libsframe/sframe-backtrace.c | 21 ++++------- 2 files changed, 84 insertions(+), 14 deletions(-) create mode 100644 libsframe/sframe-backtrace-regs.h diff --git a/libsframe/sframe-backtrace-regs.h b/libsframe/sframe-backtrace-regs.h new file mode 100644 index 0000000..1932869 --- /dev/null +++ b/libsframe/sframe-backtrace-regs.h @@ -0,0 +1,77 @@ +/* The SFrame backtracer - accessing target registers. + + Copyright (C) 2022 Free Software Foundation, Inc. + + This file is part of libsframebt. + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . */ + +#include +#include + +#if defined (__x86_64__) + +static inline uint64_t +get_context_pc (ucontext_t *cp) +{ + return cp->uc_mcontext.gregs[REG_RIP]; +} + +static inline uint64_t +get_context_rsp (ucontext_t *cp) +{ + return cp->uc_mcontext.gregs[REG_RSP]; +} + +static inline uint64_t +get_context_rfp (ucontext_t *cp) +{ + return cp->uc_mcontext.gregs[REG_RBP]; +} + +static inline uint64_t +get_context_ra (ucontext_t *cp) +{ + return 0; /* SFRAME_CFA_FIXED_RA_INVALID */ +} + +#elif defined (__aarch64__) + +static inline uint64_t +get_context_pc (ucontext_t *cp) +{ + return cp->uc_mcontext.pc; +} + +static inline uint64_t +get_context_rsp (ucontext_t *cp) +{ + return cp->uc_mcontext.sp; +} + +static inline uint64_t +get_context_rfp (ucontext_t *cp) +{ +#define UNWIND_AARCH64_X29 29 /* 64-bit frame pointer. */ + return cp->uc_mcontext.regs[UNWIND_AARCH64_X29]; +} + +static inline uint64_t +get_context_ra (ucontext_t *cp) +{ +#define UNWIND_AARCH64_X30 30 /* 64-bit link pointer. */ + return cp->uc_mcontext.regs[UNWIND_AARCH64_X30]; +} + +#endif diff --git a/libsframe/sframe-backtrace.c b/libsframe/sframe-backtrace.c index 1280b00..65fa018 100644 --- a/libsframe/sframe-backtrace.c +++ b/libsframe/sframe-backtrace.c @@ -33,6 +33,7 @@ #include "ansidecl.h" #include "sframe-api.h" #include "sframe-backtrace-api.h" +#include "sframe-backtrace-regs.h" #ifndef PT_SFRAME #define PT_SFRAME 0x6474e554 /* FIXME. */ @@ -41,7 +42,7 @@ #define _sf_printflike_(string_index, first_to_check) ATTRIBUTE_PRINTF (1, 2) static bool _sframe_unwind_debug; /* Control for printing out debug info. */ -static int no_of_entries = NUM_OF_DSOS; +static const int no_of_entries = NUM_OF_DSOS; /* SFrame decode data for the main module or a DSO. */ struct sframe_decode_data @@ -460,7 +461,7 @@ sframe_unwind (struct sframe_unwind_info *sf, void **ra_lst, sframe_decoder_ctx *ctx; int cfa_offset, rfp_offset, errnum, i, count; sframe_frame_row_entry fred, *frep = &fred; - uint64_t pc, rfp, rsp, cfi_vma; + uint64_t pc, rfp, rsp, ra, cfi_vma; ucontext_t context, *cp = &context; if (sf == NULL || ra_lst == NULL || ra_size == NULL) @@ -477,18 +478,10 @@ sframe_unwind (struct sframe_unwind_info *sf, void **ra_lst, } sframe_bt_set_errno (errp, SFRAME_BT_OK); -#if defined (__x86_64__) - pc = cp->uc_mcontext.gregs[REG_RIP]; - rsp = cp->uc_mcontext.gregs[REG_RSP]; - rfp = cp->uc_mcontext.gregs[REG_RBP]; -#elif defined (__aarch64__) -#define UNWIND_AARCH64_X29 29 /* 64-bit frame pointer. */ -#define UNWIND_AARCH64_X30 30 /* 64-bit link pointer. */ - pc = cp->uc_mcontext.pc; - rsp = cp->uc_mcontext.sp; - rfp = cp->uc_mcontext.regs[UNWIND_AARCH64_X29]; - uint64_t ra = cp->uc_mcontext.regs[UNWIND_AARCH64_X30]; -#endif + pc = get_context_pc (cp); + rsp = get_context_rsp (cp); + rfp = get_context_rfp (cp); + ra = get_context_ra (cp); /* Load and set up the decoder. */ ctx = sframe_load_ctx (sf, pc); -- cgit v1.1