123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213 |
- /* Target dependent code for ARC architecture, for GDB.
- Copyright 2005-2022 Free Software Foundation, Inc.
- Contributed by Synopsys Inc.
- This file is part of GDB.
- 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 <http://www.gnu.org/licenses/>. */
- #ifndef ARC_TDEP_H
- #define ARC_TDEP_H
- /* Need disassemble_info. */
- #include "dis-asm.h"
- #include "gdbarch.h"
- #include "arch/arc.h"
- /* To simplify GDB code this enum assumes that internal regnums should be same
- as architectural register numbers, i.e. PCL regnum is 63. This allows to
- use internal GDB regnums as architectural numbers when dealing with
- instruction encodings, for example when analyzing what are the registers
- saved in function prologue. */
- enum arc_regnum
- {
- /* Core registers. */
- ARC_R0_REGNUM = 0,
- ARC_R1_REGNUM = 1,
- ARC_R4_REGNUM = 4,
- ARC_R7_REGNUM = 7,
- ARC_R9_REGNUM = 9,
- ARC_R13_REGNUM = 13,
- ARC_R16_REGNUM = 16,
- ARC_R25_REGNUM = 25,
- /* Global data pointer. */
- ARC_GP_REGNUM,
- /* Frame pointer. */
- ARC_FP_REGNUM,
- /* Stack pointer. */
- ARC_SP_REGNUM,
- /* Return address from interrupt. */
- ARC_ILINK_REGNUM,
- ARC_R30_REGNUM,
- /* Return address from function. */
- ARC_BLINK_REGNUM,
- /* Accumulator registers. */
- ARC_R58_REGNUM = 58,
- ARC_R59_REGNUM,
- /* Zero-delay loop counter. */
- ARC_LP_COUNT_REGNUM = 60,
- /* Reserved register number. There should never be a register with such
- number, this name is needed only for a sanity check in
- arc_cannot_(fetch|store)_register. */
- ARC_RESERVED_REGNUM,
- /* Long-immediate value. This is not a physical register - if instruction
- has register 62 as an operand, then this operand is a literal value
- stored in the instruction memory right after the instruction itself.
- This value is required in this enumeration as an architectural number
- for instruction analysis. */
- ARC_LIMM_REGNUM,
- /* Program counter, aligned to 4-bytes, read-only. */
- ARC_PCL_REGNUM,
- ARC_LAST_CORE_REGNUM = ARC_PCL_REGNUM,
- /* AUX registers. */
- /* Actual program counter. */
- ARC_PC_REGNUM,
- ARC_FIRST_AUX_REGNUM = ARC_PC_REGNUM,
- /* Status register. */
- ARC_STATUS32_REGNUM,
- /* Zero-delay loop start instruction. */
- ARC_LP_START_REGNUM,
- /* Zero-delay loop next-after-last instruction. */
- ARC_LP_END_REGNUM,
- /* Branch target address. */
- ARC_BTA_REGNUM,
- /* Exception return address. */
- ARC_ERET_REGNUM,
- ARC_LAST_AUX_REGNUM = ARC_ERET_REGNUM,
- ARC_LAST_REGNUM = ARC_LAST_AUX_REGNUM,
- /* Additional ABI constants. */
- ARC_FIRST_ARG_REGNUM = ARC_R0_REGNUM,
- ARC_LAST_ARG_REGNUM = ARC_R7_REGNUM,
- ARC_FIRST_CALLEE_SAVED_REGNUM = ARC_R13_REGNUM,
- ARC_LAST_CALLEE_SAVED_REGNUM = ARC_R25_REGNUM,
- };
- /* Number of bytes in ARC register. All ARC registers are considered 32-bit.
- Those registers, which are actually shorter has zero-on-read for extra bits.
- Longer registers are represented as pairs of 32-bit registers. */
- #define ARC_REGISTER_SIZE 4
- /* STATUS32 register: hardware loops disabled bit. */
- #define ARC_STATUS32_L_MASK (1 << 12)
- /* STATUS32 register: current instruction is a delay slot. */
- #define ARC_STATUS32_DE_MASK (1 << 6)
- /* Special value for register offset arrays. */
- #define ARC_OFFSET_NO_REGISTER (-1)
- #define arc_print(fmt, args...) gdb_printf (gdb_stdlog, fmt, ##args)
- extern bool arc_debug;
- /* Print an "arc" debug statement. */
- #define arc_debug_printf(fmt, ...) \
- debug_prefixed_printf_cond (arc_debug, "arc", fmt, ##__VA_ARGS__)
- /* Target-dependent information. */
- struct arc_gdbarch_tdep : gdbarch_tdep
- {
- /* Offset to PC value in jump buffer. If this is negative, longjmp
- support will be disabled. */
- int jb_pc = 0;
- /* Whether target has hardware (aka zero-delay) loops. */
- bool has_hw_loops = false;
- /* Detect sigtramp. */
- bool (*is_sigtramp) (struct frame_info *) = nullptr;
- /* Get address of sigcontext for sigtramp. */
- CORE_ADDR (*sigcontext_addr) (struct frame_info *) = nullptr;
- /* Offset of registers in `struct sigcontext'. */
- const int *sc_reg_offset = nullptr;
- /* Number of registers in sc_reg_offsets. Most likely a ARC_LAST_REGNUM,
- but in theory it could be less, so it is kept separate. */
- int sc_num_regs = 0;
- };
- /* Utility functions used by other ARC-specific modules. */
- static inline int
- arc_mach_is_arc600 (struct gdbarch *gdbarch)
- {
- return (gdbarch_bfd_arch_info (gdbarch)->mach == bfd_mach_arc_arc600
- || gdbarch_bfd_arch_info (gdbarch)->mach == bfd_mach_arc_arc601);
- }
- static inline int
- arc_mach_is_arc700 (struct gdbarch *gdbarch)
- {
- return gdbarch_bfd_arch_info (gdbarch)->mach == bfd_mach_arc_arc700;
- }
- static inline int
- arc_mach_is_arcv2 (struct gdbarch *gdbarch)
- {
- return gdbarch_bfd_arch_info (gdbarch)->mach == bfd_mach_arc_arcv2;
- }
- /* ARC EM and ARC HS are unique BFD arches, however they share the same machine
- number as "ARCv2". */
- static inline bool
- arc_arch_is_hs (const struct bfd_arch_info* arch)
- {
- return startswith (arch->printable_name, "HS");
- }
- static inline bool
- arc_arch_is_em (const struct bfd_arch_info* arch)
- {
- return startswith (arch->printable_name, "EM");
- }
- /* Function to access ARC disassembler. Underlying opcodes disassembler will
- print an instruction into stream specified in the INFO, so if it is
- undesired, then this stream should be set to some invisible stream, but it
- can't be set to an actual NULL value - that would cause a crash. */
- int arc_delayed_print_insn (bfd_vma addr, struct disassemble_info *info);
- /* Return properly initialized disassemble_info for ARC disassembler - it will
- not print disassembled instructions to stderr. */
- struct disassemble_info arc_disassemble_info (struct gdbarch *gdbarch);
- /* Get branch/jump target address for the INSN. Note that this function
- returns branch target and doesn't evaluate if this branch is taken or not.
- For the indirect jumps value depends in register state, hence can change.
- It is an error to call this function for a non-branch instruction. */
- CORE_ADDR arc_insn_get_branch_target (const struct arc_instruction &insn);
- /* Get address of next instruction after INSN, assuming linear execution (no
- taken branches). If instruction has a delay slot, then returned value will
- point at the instruction in delay slot. That is - "address of instruction +
- instruction length with LIMM". */
- CORE_ADDR arc_insn_get_linear_next_pc (const struct arc_instruction &insn);
- /* Create an arc_arch_features instance from the provided data. */
- arc_arch_features arc_arch_features_create (const bfd *abfd,
- const unsigned long mach);
- #endif /* ARC_TDEP_H */
|