@@ -126,12 +126,25 @@ dis_asm_read_memory (bfd_vma memaddr, gdb_byte *myaddr, unsigned int len,
return target_read_code (memaddr, myaddr, len);
}
-/* Like memory_error with slightly different parameters. */
+/* Like memory_error with slightly different parameters, but it longjmp
+ out of the opcodes callback. */
static void
dis_asm_memory_error (int err, bfd_vma memaddr,
- struct disassemble_info *info)
+ struct disassemble_info *info) GDB_NOEXCEPT
{
- memory_error (TARGET_XFER_E_IO, memaddr);
+ struct gdb_exception exception = exception_none;
+
+ TRY
+ {
+ memory_error (TARGET_XFER_E_IO, memaddr);
+ }
+ CATCH (ex, RETURN_MASK_ALL)
+ {
+ exception = ex;
+ }
+ END_CATCH
+
+ throw_exception_sjlj (exception);
}
/* Like print_address with slightly different parameters. */
@@ -143,6 +156,45 @@ dis_asm_print_address (bfd_vma addr, struct disassemble_info *info)
print_address (gdbarch, addr, (struct ui_file *) info->stream);
}
+/* Wrapper of gdbarch_print_insn, save its return value in *LEN if no
+ exception is thrown out of gdbarch_print_insn. */
+
+static struct gdb_exception
+disasm_print_insn_noexcept (struct gdbarch *gdbarch, bfd_vma vma,
+ struct disassemble_info *info,
+ int *len) GDB_NOEXCEPT
+{
+ struct gdb_exception gdb_expt = exception_none;
+
+ TRY_SJLJ
+ {
+ *len = gdbarch_print_insn (gdbarch, vma, info);
+ }
+ CATCH_SJLJ (ex, RETURN_MASK_ALL)
+ {
+ gdb_expt = ex;
+ }
+ END_CATCH_SJLJ
+
+ return gdb_expt;
+}
+
+int
+disasm_print_insn (struct gdbarch *gdbarch, bfd_vma vma,
+ struct disassemble_info *info)
+{
+ int len;
+
+ struct gdb_exception gdb_expt
+ = disasm_print_insn_noexcept (gdbarch, vma, info, &len);
+
+ /* Rethrow using the normal EH mechanism. */
+ if (gdb_expt.reason < 0)
+ throw_exception (gdb_expt);
+
+ return len;
+}
+
static int
compare_lines (const void *mle1p, const void *mle2p)
{
@@ -253,7 +305,7 @@ gdb_pretty_print_insn (struct gdbarch *gdbarch, struct ui_out *uiout,
struct cleanup *cleanups =
make_cleanup_ui_file_delete (opcode_stream);
- size = gdbarch_print_insn (gdbarch, pc, di);
+ size = disasm_print_insn (gdbarch, pc, di);
end_pc = pc + size;
for (;pc < end_pc; ++pc)
@@ -272,7 +324,7 @@ gdb_pretty_print_insn (struct gdbarch *gdbarch, struct ui_out *uiout,
do_cleanups (cleanups);
}
else
- size = gdbarch_print_insn (gdbarch, pc, di);
+ size = disasm_print_insn (gdbarch, pc, di);
ui_out_field_stream (uiout, "inst", stb);
ui_file_rewind (stb);
@@ -833,7 +885,7 @@ gdb_print_insn (struct gdbarch *gdbarch, CORE_ADDR memaddr,
int length;
di = gdb_disassemble_info (gdbarch, stream);
- length = gdbarch_print_insn (gdbarch, memaddr, &di);
+ length = disasm_print_insn (gdbarch, memaddr, &di);
if (branch_delay_insns)
{
if (di.insn_info_valid)
@@ -914,5 +966,5 @@ gdb_buffered_insn_length (struct gdbarch *gdbarch,
gdb_buffered_insn_length_init_dis (gdbarch, &di, insn, max_len, addr);
- return gdbarch_print_insn (gdbarch, addr, &di);
+ return disasm_print_insn (gdbarch, addr, &di);
}
@@ -83,4 +83,10 @@ extern int gdb_buffered_insn_length (struct gdbarch *gdbarch,
const gdb_byte *insn, int max_len,
CORE_ADDR memaddr);
+/* Print the instruction at address VMA. Returns the length of the
+ instruction in bytes. */
+
+extern int disasm_print_insn (struct gdbarch *gdbarch, bfd_vma vma,
+ struct disassemble_info *info);
+
#endif
@@ -73,14 +73,6 @@ static void async_stop_sig (gdb_client_data);
#endif
static void async_sigterm_handler (gdb_client_data arg);
-#ifndef __cplusplus
-# define GDB_NOEXCEPT
-#elif __cplusplus < 201103L
-# define GDB_NOEXCEPT throw ()
-#else
-# define GDB_NOEXCEPT noexcept
-#endif
-
/* Instead of invoking (and waiting for) readline to read the command
line and pass it back for processing, we use readline's alternate
interface, via callback functions, so that the event loop can react
@@ -88,4 +88,12 @@ extern int catch_exceptions_with_msg (struct ui_out *uiout,
typedef int (catch_errors_ftype) (void *);
extern int catch_errors (catch_errors_ftype *, void *, char *, return_mask);
+#ifndef __cplusplus
+# define GDB_NOEXCEPT
+#elif __cplusplus < 201103L
+# define GDB_NOEXCEPT throw ()
+#else
+# define GDB_NOEXCEPT noexcept
+#endif
+
#endif
@@ -123,18 +123,6 @@ gdbscm_disasm_read_memory (bfd_vma memaddr, bfd_byte *myaddr,
return status != NULL ? -1 : 0;
}
-/* disassemble_info.memory_error_func for gdbscm_print_insn_from_port.
- Technically speaking, we don't need our own memory_error_func,
- but to not provide one would leave a subtle dependency in the code.
- This function exists to keep a clear boundary. */
-
-static void
-gdbscm_disasm_memory_error (int status, bfd_vma memaddr,
- struct disassemble_info *info)
-{
- memory_error (TARGET_XFER_E_IO, memaddr);
-}
-
/* disassemble_info.print_address_func for gdbscm_print_insn_from_port.
Since we need to use our own application_data value, we need to supply
this routine as well. */
@@ -174,10 +162,9 @@ gdbscm_print_insn_from_port (struct gdbarch *gdbarch,
data.offset = offset;
di.application_data = &data;
di.read_memory_func = gdbscm_disasm_read_memory;
- di.memory_error_func = gdbscm_disasm_memory_error;
di.print_address_func = gdbscm_disasm_print_address;
- length = gdbarch_print_insn (gdbarch, memaddr, &di);
+ length = disasm_print_insn (gdbarch, memaddr, &di);
if (branch_delay_insns)
{