struct trad_frame_cache *this_cache,
CORE_ADDR func);
+static int mips_linux_sigframe_validate (const struct tramp_frame *self,
+ struct frame_info *this_frame,
+ CORE_ADDR *pc);
+
+static int micromips_linux_sigframe_validate (const struct tramp_frame *self,
+ struct frame_info *this_frame,
+ CORE_ADDR *pc);
+
#define MIPS_NR_LINUX 4000
#define MIPS_NR_N64_LINUX 5000
#define MIPS_NR_N32_LINUX 6000
#define MIPS_INST_LI_V0_N32_RT_SIGRETURN 0x24020000 + MIPS_NR_N32_rt_sigreturn
#define MIPS_INST_SYSCALL 0x0000000c
+#define MICROMIPS_INST_LI_V0 0x3040
+#define MICROMIPS_INST_POOL32A 0x0000
+#define MICROMIPS_INST_SYSCALL 0x8b7c
+
static const struct tramp_frame mips_linux_o32_sigframe = {
SIGTRAMP_FRAME,
4,
{ MIPS_INST_SYSCALL, -1 },
{ TRAMP_SENTINEL_INSN, -1 }
},
- mips_linux_o32_sigframe_init
+ mips_linux_o32_sigframe_init,
+ mips_linux_sigframe_validate
};
static const struct tramp_frame mips_linux_o32_rt_sigframe = {
{ MIPS_INST_LI_V0_RT_SIGRETURN, -1 },
{ MIPS_INST_SYSCALL, -1 },
{ TRAMP_SENTINEL_INSN, -1 } },
- mips_linux_o32_sigframe_init
+ mips_linux_o32_sigframe_init,
+ mips_linux_sigframe_validate
};
static const struct tramp_frame mips_linux_n32_rt_sigframe = {
{ MIPS_INST_SYSCALL, -1 },
{ TRAMP_SENTINEL_INSN, -1 }
},
- mips_linux_n32n64_sigframe_init
+ mips_linux_n32n64_sigframe_init,
+ mips_linux_sigframe_validate
};
static const struct tramp_frame mips_linux_n64_rt_sigframe = {
{ MIPS_INST_SYSCALL, -1 },
{ TRAMP_SENTINEL_INSN, -1 }
},
- mips_linux_n32n64_sigframe_init
+ mips_linux_n32n64_sigframe_init,
+ mips_linux_sigframe_validate
+};
+
+static const struct tramp_frame micromips_linux_o32_sigframe = {
+ SIGTRAMP_FRAME,
+ 2,
+ {
+ { MICROMIPS_INST_LI_V0, -1 },
+ { MIPS_NR_sigreturn, -1 },
+ { MICROMIPS_INST_POOL32A, -1 },
+ { MICROMIPS_INST_SYSCALL, -1 },
+ { TRAMP_SENTINEL_INSN, -1 }
+ },
+ mips_linux_o32_sigframe_init,
+ micromips_linux_sigframe_validate
+};
+
+static const struct tramp_frame micromips_linux_o32_rt_sigframe = {
+ SIGTRAMP_FRAME,
+ 2,
+ {
+ { MICROMIPS_INST_LI_V0, -1 },
+ { MIPS_NR_rt_sigreturn, -1 },
+ { MICROMIPS_INST_POOL32A, -1 },
+ { MICROMIPS_INST_SYSCALL, -1 },
+ { TRAMP_SENTINEL_INSN, -1 }
+ },
+ mips_linux_o32_sigframe_init,
+ micromips_linux_sigframe_validate
+};
+
+static const struct tramp_frame micromips_linux_n32_rt_sigframe = {
+ SIGTRAMP_FRAME,
+ 2,
+ {
+ { MICROMIPS_INST_LI_V0, -1 },
+ { MIPS_NR_N32_rt_sigreturn, -1 },
+ { MICROMIPS_INST_POOL32A, -1 },
+ { MICROMIPS_INST_SYSCALL, -1 },
+ { TRAMP_SENTINEL_INSN, -1 }
+ },
+ mips_linux_n32n64_sigframe_init,
+ micromips_linux_sigframe_validate
+};
+
+static const struct tramp_frame micromips_linux_n64_rt_sigframe = {
+ SIGTRAMP_FRAME,
+ 2,
+ {
+ { MICROMIPS_INST_LI_V0, -1 },
+ { MIPS_NR_N64_rt_sigreturn, -1 },
+ { MICROMIPS_INST_POOL32A, -1 },
+ { MICROMIPS_INST_SYSCALL, -1 },
+ { TRAMP_SENTINEL_INSN, -1 }
+ },
+ mips_linux_n32n64_sigframe_init,
+ micromips_linux_sigframe_validate
};
/* *INDENT-OFF* */
const struct mips_regnum *regs = mips_regnum (gdbarch);
CORE_ADDR regs_base;
- if (self == &mips_linux_o32_sigframe)
+ if (self == &mips_linux_o32_sigframe
+ || self == µmips_linux_o32_sigframe)
sigcontext_base = frame_sp + SIGFRAME_SIGCONTEXT_OFFSET;
else
sigcontext_base = frame_sp + RTSIGFRAME_SIGCONTEXT_OFFSET;
CORE_ADDR sigcontext_base;
const struct mips_regnum *regs = mips_regnum (gdbarch);
- if (self == &mips_linux_n32_rt_sigframe)
+ if (self == &mips_linux_n32_rt_sigframe
+ || self == µmips_linux_n32_rt_sigframe)
sigcontext_base = frame_sp + N32_SIGFRAME_SIGCONTEXT_OFFSET;
else
sigcontext_base = frame_sp + N64_SIGFRAME_SIGCONTEXT_OFFSET;
trad_frame_set_id (this_cache, frame_id_build (frame_sp, func));
}
+/* Implement struct tramp_frame's "validate" method for standard MIPS code. */
+
+static int
+mips_linux_sigframe_validate (const struct tramp_frame *self,
+ struct frame_info *this_frame,
+ CORE_ADDR *pc)
+{
+ return mips_pc_is_mips (*pc);
+}
+
+/* Implement struct tramp_frame's "validate" method for microMIPS code. */
+
+static int
+micromips_linux_sigframe_validate (const struct tramp_frame *self,
+ struct frame_info *this_frame,
+ CORE_ADDR *pc)
+{
+ return mips_pc_is_micromips (get_frame_arch (this_frame), *pc);
+}
+
/* Implement the "write_pc" gdbarch method. */
static void
mips_linux_get_longjmp_target);
set_solib_svr4_fetch_link_map_offsets
(gdbarch, svr4_ilp32_fetch_link_map_offsets);
+ tramp_frame_prepend_unwinder (gdbarch, µmips_linux_o32_sigframe);
+ tramp_frame_prepend_unwinder (gdbarch,
+ µmips_linux_o32_rt_sigframe);
tramp_frame_prepend_unwinder (gdbarch, &mips_linux_o32_sigframe);
tramp_frame_prepend_unwinder (gdbarch, &mips_linux_o32_rt_sigframe);
set_xml_syscall_file_name (gdbarch, "syscalls/mips-o32-linux.xml");
except that the quiet/signalling NaN bit is reversed (GDB
does not distinguish between quiet and signalling NaNs). */
set_gdbarch_long_double_format (gdbarch, floatformats_ia64_quad);
+ tramp_frame_prepend_unwinder (gdbarch,
+ µmips_linux_n32_rt_sigframe);
tramp_frame_prepend_unwinder (gdbarch, &mips_linux_n32_rt_sigframe);
set_xml_syscall_file_name (gdbarch, "syscalls/mips-n32-linux.xml");
break;
except that the quiet/signalling NaN bit is reversed (GDB
does not distinguish between quiet and signalling NaNs). */
set_gdbarch_long_double_format (gdbarch, floatformats_ia64_quad);
+ tramp_frame_prepend_unwinder (gdbarch,
+ µmips_linux_n64_rt_sigframe);
tramp_frame_prepend_unwinder (gdbarch, &mips_linux_n64_rt_sigframe);
set_xml_syscall_file_name (gdbarch, "syscalls/mips-n64-linux.xml");
break;