Back to home page

OSCL-LXR

 
 

    


0001 // SPDX-License-Identifier: GPL-2.0-or-later
0002 /*
0003  * Mapping of DWARF debug register numbers into register names.
0004  *
0005  * Copyright (C) 2010 Ian Munsie, IBM Corporation.
0006  */
0007 
0008 #include <stddef.h>
0009 #include <errno.h>
0010 #include <string.h>
0011 #include <dwarf-regs.h>
0012 #include <linux/ptrace.h>
0013 #include <linux/kernel.h>
0014 #include <linux/stringify.h>
0015 
0016 struct pt_regs_dwarfnum {
0017     const char *name;
0018     unsigned int dwarfnum;
0019     unsigned int ptregs_offset;
0020 };
0021 
0022 #define REG_DWARFNUM_NAME(r, num)                   \
0023         {.name = __stringify(%)__stringify(r), .dwarfnum = num,         \
0024         .ptregs_offset = offsetof(struct pt_regs, r)}
0025 #define GPR_DWARFNUM_NAME(num)                      \
0026         {.name = __stringify(%gpr##num), .dwarfnum = num,       \
0027         .ptregs_offset = offsetof(struct pt_regs, gpr[num])}
0028 #define REG_DWARFNUM_END {.name = NULL, .dwarfnum = 0, .ptregs_offset = 0}
0029 
0030 /*
0031  * Reference:
0032  * http://refspecs.linuxfoundation.org/ELF/ppc64/PPC-elf64abi-1.9.html
0033  */
0034 static const struct pt_regs_dwarfnum regdwarfnum_table[] = {
0035     GPR_DWARFNUM_NAME(0),
0036     GPR_DWARFNUM_NAME(1),
0037     GPR_DWARFNUM_NAME(2),
0038     GPR_DWARFNUM_NAME(3),
0039     GPR_DWARFNUM_NAME(4),
0040     GPR_DWARFNUM_NAME(5),
0041     GPR_DWARFNUM_NAME(6),
0042     GPR_DWARFNUM_NAME(7),
0043     GPR_DWARFNUM_NAME(8),
0044     GPR_DWARFNUM_NAME(9),
0045     GPR_DWARFNUM_NAME(10),
0046     GPR_DWARFNUM_NAME(11),
0047     GPR_DWARFNUM_NAME(12),
0048     GPR_DWARFNUM_NAME(13),
0049     GPR_DWARFNUM_NAME(14),
0050     GPR_DWARFNUM_NAME(15),
0051     GPR_DWARFNUM_NAME(16),
0052     GPR_DWARFNUM_NAME(17),
0053     GPR_DWARFNUM_NAME(18),
0054     GPR_DWARFNUM_NAME(19),
0055     GPR_DWARFNUM_NAME(20),
0056     GPR_DWARFNUM_NAME(21),
0057     GPR_DWARFNUM_NAME(22),
0058     GPR_DWARFNUM_NAME(23),
0059     GPR_DWARFNUM_NAME(24),
0060     GPR_DWARFNUM_NAME(25),
0061     GPR_DWARFNUM_NAME(26),
0062     GPR_DWARFNUM_NAME(27),
0063     GPR_DWARFNUM_NAME(28),
0064     GPR_DWARFNUM_NAME(29),
0065     GPR_DWARFNUM_NAME(30),
0066     GPR_DWARFNUM_NAME(31),
0067     REG_DWARFNUM_NAME(msr,   66),
0068     REG_DWARFNUM_NAME(ctr,   109),
0069     REG_DWARFNUM_NAME(link,  108),
0070     REG_DWARFNUM_NAME(xer,   101),
0071     REG_DWARFNUM_NAME(dar,   119),
0072     REG_DWARFNUM_NAME(dsisr, 118),
0073     REG_DWARFNUM_END,
0074 };
0075 
0076 /**
0077  * get_arch_regstr() - lookup register name from it's DWARF register number
0078  * @n:  the DWARF register number
0079  *
0080  * get_arch_regstr() returns the name of the register in struct
0081  * regdwarfnum_table from it's DWARF register number. If the register is not
0082  * found in the table, this returns NULL;
0083  */
0084 const char *get_arch_regstr(unsigned int n)
0085 {
0086     const struct pt_regs_dwarfnum *roff;
0087     for (roff = regdwarfnum_table; roff->name != NULL; roff++)
0088         if (roff->dwarfnum == n)
0089             return roff->name;
0090     return NULL;
0091 }
0092 
0093 int regs_query_register_offset(const char *name)
0094 {
0095     const struct pt_regs_dwarfnum *roff;
0096     for (roff = regdwarfnum_table; roff->name != NULL; roff++)
0097         if (!strcmp(roff->name, name))
0098             return roff->ptregs_offset;
0099     return -EINVAL;
0100 }