#include "regcache.h"
-#define GDB_MULTI_ARCH 0
+#define GDB_MULTI_ARCH GDB_MULTI_ARCH_PARTIAL
/* Generic 68000 stuff, to be included by other tm-*.h files. */
-struct frame_info;
+/* struct frame_info; */
+
+/* D0_REGNM and A0_REGNUM must be defined here because they are
+ used by the monitor. */
+
+#define D0_REGNUM 0
+#define A0_REGNUM 8
/* Sequence of bytes for breakpoint instruction.
This is a TRAP instruction. The last 4 bits (0xf below) is the
vector. Systems which don't use 0xf should define BPT_VECTOR
themselves before including this file. */
+#if !GDB_MULTI_ARCH
#if !defined (BPT_VECTOR)
#define BPT_VECTOR 0xf
#endif
#if !defined (REMOTE_BPT_VECTOR)
#define REMOTE_BPT_VECTOR 1
#endif
+#endif
+#if !GDB_MULTI_ARCH
#if !defined (REMOTE_BREAKPOINT)
#define REMOTE_BREAKPOINT {0x4e, (0x40 | REMOTE_BPT_VECTOR)}
#endif
+#endif
+#if !GDB_MULTI_ARCH
#define REGISTER_BYTES_FP (16*4 + 8 + 8*12 + 3*4)
#define REGISTER_BYTES_NOFP (16*4 + 8)
#define NUM_FREGS (NUM_REGS-24)
+
/* This was determined by experimentation on hp300 BSD 4.3. Perhaps
it corresponds to some offset in /usr/include/sys/user.h or
something like that. Using some system include file would
#define SP_ARG0 (1 * 4)
#define TARGET_M68K
-
+#endif
#if !GDB_MULTI_ARCH
#define TARGET_LONG_DOUBLE_FORMAT &floatformat_m68881_ext
#ifndef REGISTER_BYTES
#define REGISTER_BYTES (16*4 + 8 + 8*12 + 3*4)
#endif
-#endif //multi-arch
+#endif /* multi-arch */
/* Index within `registers' of the first byte of the space for
register N. */
/* Largest value REGISTER_VIRTUAL_SIZE can have. */
#define MAX_REGISTER_VIRTUAL_SIZE 12
-#endif //multi-arch
+#endif /* multi-arch */
/* Return the GDB type object for the "standard" data type of data
in register N. This should be int for D0-D7, long double for FP0-FP7,
to be actual register numbers as far as the user is concerned
but do serve to get the desired values when passed to read_register. */
+#if !GDB_MULTI_ARCH
-#define D0_REGNUM 0
-#define A0_REGNUM 8
#define A1_REGNUM 9
-#if !GDB_MULTI_ARCH
#define FP_REGNUM 14 /* Contains address of executing stack frame */
#define SP_REGNUM 15 /* Contains address of top of stack */
#define PS_REGNUM 16 /* Contains processor status */
#define PC_REGNUM 17 /* Contains program counter */
#define FP0_REGNUM 18 /* Floating point register 0 */
-#endif
#define FPC_REGNUM 26 /* 68881 control register */
#define FPS_REGNUM 27 /* 68881 status register */
#define FPI_REGNUM 28 /* 68881 iaddr register */
-
+#endif
/* Store the address of the place in which to copy the structure the
subroutine will return. This is called from call_function. */
(TYPE_LENGTH(TYPE) >= 4 ? 0 : 4 - TYPE_LENGTH(TYPE)), \
TYPE_LENGTH(TYPE))
#endif
-#endif //multi-arch
+#endif /* multi-arch */
/* Write into appropriate registers a function return value
of type TYPE, given in virtual format. Assumes floats are passed
as a CORE_ADDR (or an expression that can be used as one). */
#define DEPRECATED_EXTRACT_STRUCT_VALUE_ADDRESS(REGBUF) (*(CORE_ADDR *)(REGBUF))
-#endif //multi-arch
+#endif /* multi-arch */
\f
/* Describe the pointer in each stack frame to the previous stack frame
(its caller). */
#define P_FMOVM 0xf237
#define P_TRAP 0x4e40
+
+/* Register numbers of various important registers.
+ Note that some of these values are "real" register numbers,
+ and correspond to the general registers of the machine,
+ and some are "phony" register numbers which are too large
+ to be actual register numbers as far as the user is concerned
+ but do serve to get the desired values when passed to read_register. */
+
+/* Note: Since they are used in files other than this (monitor files),
+ D0_REGNUM and A0_REGNUM are currently defined in tm-m68k.h. */
+
enum
{
+ E_A1_REGNUM = 9,
E_FP_REGNUM = 14, /* Contains address of executing stack frame */
E_SP_REGNUM = 15, /* Contains address of top of stack */
E_PS_REGNUM = 16, /* Contains processor status */
E_PC_REGNUM = 17, /* Contains program counter */
- E_FP0_REGNUM = 18 /* Floating point register 0 */
+ E_FP0_REGNUM = 18, /* Floating point register 0 */
+ E_FPC_REGNUM = 26, /* 68881 control register */
+ E_FPS_REGNUM = 27, /* 68881 status register */
+ E_FPI_REGNUM = 28
};
+#define REGISTER_BYTES_FP (16*4 + 8 + 8*12 + 3*4)
+#define REGISTER_BYTES_NOFP (16*4 + 8)
+
+#define NUM_FREGS (NUM_REGS-24)
+
+/* Offset from SP to first arg on stack at first instruction of a function */
+
+#define SP_ARG0 (1 * 4)
+
+/* This was determined by experimentation on hp300 BSD 4.3. Perhaps
+ it corresponds to some offset in /usr/include/sys/user.h or
+ something like that. Using some system include file would
+ have the advantage of probably being more robust in the face
+ of OS upgrades, but the disadvantage of being wrong for
+ cross-debugging. */
+
+#define SIG_PC_FP_OFFSET 530
+
+#define TARGET_M68K
+
+
+#if !defined (BPT_VECTOR)
+#define BPT_VECTOR 0xf
+#endif
+
+#if !defined (REMOTE_BPT_VECTOR)
+#define REMOTE_BPT_VECTOR 1
+#endif
+
+
void m68k_frame_init_saved_regs (struct frame_info *frame_info);
+
+/* gdbarch_breakpoint_from_pc is set to m68k_local_breakpoint_from_pc
+ so m68k_remote_breakpoint_from_pc is currently not used. */
+
+const static unsigned char *
+m68k_remote_breakpoint_from_pc (CORE_ADDR *pcptr, int *lenptr)
+{
+ static unsigned char break_insn[] = {0x4e, (0x40 | REMOTE_BPT_VECTOR)};
+ *lenptr = sizeof (break_insn);
+ return break_insn;
+}
+
+const static unsigned char *
+m68k_local_breakpoint_from_pc (CORE_ADDR *pcptr, int *lenptr)
+{
+ static unsigned char break_insn[] = {0x4e, (0x40 | BPT_VECTOR)};
+ *lenptr = sizeof (break_insn);
+ return break_insn;
+}
+
+
static int
m68k_register_bytes_ok (numbytes)
{
static struct type *
m68k_register_virtual_type (int regnum)
{
- if ((unsigned) regnum >= FPC_REGNUM)
+ if ((unsigned) regnum >= E_FPC_REGNUM)
return lookup_pointer_type (builtin_type_void);
else if ((unsigned) regnum >= FP0_REGNUM)
return builtin_type_long_double;
static int
m68k_register_byte (int regnum)
{
- if (regnum >= FPC_REGNUM)
- return (((regnum - FPC_REGNUM) * 4) + 168);
+ if (regnum >= E_FPC_REGNUM)
+ return (((regnum - E_FPC_REGNUM) * 4) + 168);
else if (regnum >= FP0_REGNUM)
return (((regnum - FP0_REGNUM) * 12) + 72);
else
static void
m68k_store_struct_return (CORE_ADDR addr, CORE_ADDR sp)
{
- write_register (A1_REGNUM, addr);
+ write_register (E_A1_REGNUM, addr);
}
/* Extract from an array regbuf containing the (raw) register state
register int regi;
char *from;
- for (regi = FP0_REGNUM; regi < FPC_REGNUM; regi++)
+ for (regi = FP0_REGNUM; regi < E_FPC_REGNUM; regi++)
{
from = (char *) &(fpregsetp->f_fpregs[regi - FP0_REGNUM][0]);
supply_register (regi, from);
}
- supply_register (FPC_REGNUM, (char *) &(fpregsetp->f_pcr));
- supply_register (FPS_REGNUM, (char *) &(fpregsetp->f_psr));
- supply_register (FPI_REGNUM, (char *) &(fpregsetp->f_fpiaddr));
+ supply_register (E_FPC_REGNUM, (char *) &(fpregsetp->f_pcr));
+ supply_register (E_FPS_REGNUM, (char *) &(fpregsetp->f_psr));
+ supply_register (E_FPI_REGNUM, (char *) &(fpregsetp->f_fpiaddr));
}
/* Given a pointer to a floating point register set in /proc format
char *to;
char *from;
- for (regi = FP0_REGNUM; regi < FPC_REGNUM; regi++)
+ for (regi = FP0_REGNUM; regi < E_FPC_REGNUM; regi++)
{
if ((regno == -1) || (regno == regi))
{
memcpy (to, from, REGISTER_RAW_SIZE (regi));
}
}
- if ((regno == -1) || (regno == FPC_REGNUM))
+ if ((regno == -1) || (regno == E_FPC_REGNUM))
{
- fpregsetp->f_pcr = *(int *) ®isters[REGISTER_BYTE (FPC_REGNUM)];
+ fpregsetp->f_pcr = *(int *) ®isters[REGISTER_BYTE (E_FPC_REGNUM)];
}
- if ((regno == -1) || (regno == FPS_REGNUM))
+ if ((regno == -1) || (regno == E_FPS_REGNUM))
{
- fpregsetp->f_psr = *(int *) ®isters[REGISTER_BYTE (FPS_REGNUM)];
+ fpregsetp->f_psr = *(int *) ®isters[REGISTER_BYTE (E_FPS_REGNUM)];
}
- if ((regno == -1) || (regno == FPI_REGNUM))
+ if ((regno == -1) || (regno == E_FPI_REGNUM))
{
- fpregsetp->f_fpiaddr = *(int *) ®isters[REGISTER_BYTE (FPI_REGNUM)];
+ fpregsetp->f_fpiaddr = *(int *) ®isters[REGISTER_BYTE (E_FPI_REGNUM)];
}
}
set_gdbarch_skip_prologue (gdbarch, m68k_skip_prologue);
set_gdbarch_saved_pc_after_call (gdbarch, m68k_saved_pc_after_call);
+ set_gdbarch_breakpoint_from_pc (gdbarch, m68k_local_breakpoint_from_pc);
/* Stack grows down. */
set_gdbarch_inner_than (gdbarch, core_addr_lessthan);