/* Renesas M32C target-dependent code for GDB, the GNU debugger.
- Copyright 2004, 2005, 2007, 2008 Free Software Foundation, Inc.
+ Copyright 2004, 2005, 2007, 2008, 2009 Free Software Foundation, Inc.
This file is part of GDB.
/* The builtin_type_mumble variables are sometimes uninitialized when
this is called, so we avoid using them. */
- tdep->voyd = init_type (TYPE_CODE_VOID, 1, 0, "void", NULL);
- tdep->ptr_voyd = init_type (TYPE_CODE_PTR, gdbarch_ptr_bit (arch) / 8,
- TYPE_FLAG_UNSIGNED, NULL, NULL);
+ tdep->voyd = arch_type (arch, TYPE_CODE_VOID, 1, "void");
+ tdep->ptr_voyd
+ = arch_type (arch, TYPE_CODE_PTR, gdbarch_ptr_bit (arch), NULL);
TYPE_TARGET_TYPE (tdep->ptr_voyd) = tdep->voyd;
+ TYPE_UNSIGNED (tdep->ptr_voyd) = 1;
tdep->func_voyd = lookup_function_type (tdep->voyd);
sprintf (type_name, "%s_data_addr_t",
gdbarch_bfd_arch_info (arch)->printable_name);
tdep->data_addr_reg_type
- = init_type (TYPE_CODE_PTR, data_addr_reg_bits / 8,
- TYPE_FLAG_UNSIGNED, xstrdup (type_name), NULL);
+ = arch_type (arch, TYPE_CODE_PTR, data_addr_reg_bits, xstrdup (type_name));
TYPE_TARGET_TYPE (tdep->data_addr_reg_type) = tdep->voyd;
+ TYPE_UNSIGNED (tdep->data_addr_reg_type) = 1;
sprintf (type_name, "%s_code_addr_t",
gdbarch_bfd_arch_info (arch)->printable_name);
tdep->code_addr_reg_type
- = init_type (TYPE_CODE_PTR, code_addr_reg_bits / 8,
- TYPE_FLAG_UNSIGNED, xstrdup (type_name), NULL);
+ = arch_type (arch, TYPE_CODE_PTR, code_addr_reg_bits, xstrdup (type_name));
TYPE_TARGET_TYPE (tdep->code_addr_reg_type) = tdep->func_voyd;
+ TYPE_UNSIGNED (tdep->code_addr_reg_type) = 1;
- tdep->uint8 = init_type (TYPE_CODE_INT, 1, TYPE_FLAG_UNSIGNED,
- "uint8_t", NULL);
- tdep->uint16 = init_type (TYPE_CODE_INT, 2, TYPE_FLAG_UNSIGNED,
- "uint16_t", NULL);
- tdep->int8 = init_type (TYPE_CODE_INT, 1, 0, "int8_t", NULL);
- tdep->int16 = init_type (TYPE_CODE_INT, 2, 0, "int16_t", NULL);
- tdep->int32 = init_type (TYPE_CODE_INT, 4, 0, "int32_t", NULL);
- tdep->int64 = init_type (TYPE_CODE_INT, 8, 0, "int64_t", NULL);
+ tdep->uint8 = arch_integer_type (arch, 8, 1, "uint8_t");
+ tdep->uint16 = arch_integer_type (arch, 16, 1, "uint16_t");
+ tdep->int8 = arch_integer_type (arch, 8, 0, "int8_t");
+ tdep->int16 = arch_integer_type (arch, 16, 0, "int16_t");
+ tdep->int32 = arch_integer_type (arch, 32, 0, "int32_t");
+ tdep->int64 = arch_integer_type (arch, 64, 0, "int64_t");
}
}
-int
+static int
m32c_register_reggroup_p (struct gdbarch *gdbarch, int regnum,
struct reggroup *group)
{
set_gdbarch_pseudo_register_write (arch, m32c_pseudo_register_write);
set_gdbarch_register_sim_regno (arch, m32c_register_sim_regno);
set_gdbarch_stab_reg_to_regnum (arch, m32c_debug_info_reg_to_regnum);
- set_gdbarch_dwarf_reg_to_regnum (arch, m32c_debug_info_reg_to_regnum);
set_gdbarch_dwarf2_reg_to_regnum (arch, m32c_debug_info_reg_to_regnum);
set_gdbarch_register_reggroup_p (arch, m32c_register_reggroup_p);
/* Analyze the function prologue for ARCH at START, going no further
than LIMIT, and place a description of what we found in
PROLOGUE. */
-void
+static void
m32c_analyze_prologue (struct gdbarch *arch,
CORE_ADDR start, CORE_ADDR limit,
struct m32c_prologue *prologue)
st.fb = pv_register (tdep->fb->num, 0);
st.sp = pv_register (tdep->sp->num, 0);
st.pc = pv_register (tdep->pc->num, 0);
- st.stack = make_pv_area (tdep->sp->num);
+ st.stack = make_pv_area (tdep->sp->num, gdbarch_addr_bit (arch));
back_to = make_cleanup_free_pv_area (st.stack);
/* Record that the call instruction has saved the return address on
static CORE_ADDR
-m32c_skip_prologue (CORE_ADDR ip)
+m32c_skip_prologue (struct gdbarch *gdbarch, CORE_ADDR ip)
{
char *name;
CORE_ADDR func_addr, func_end, sal_end;
return ip;
/* Find end by prologue analysis. */
- m32c_analyze_prologue (current_gdbarch, ip, func_end, &p);
+ m32c_analyze_prologue (gdbarch, ip, func_end, &p);
/* Find end by line info. */
- sal_end = skip_prologue_using_sal (ip);
+ sal_end = skip_prologue_using_sal (gdbarch, ip);
/* Return whichever is lower. */
if (sal_end != 0 && sal_end != ip && sal_end < p.prologue_end)
return sal_end;
/* Stack unwinding. */
static struct m32c_prologue *
-m32c_analyze_frame_prologue (struct frame_info *next_frame,
+m32c_analyze_frame_prologue (struct frame_info *this_frame,
void **this_prologue_cache)
{
if (! *this_prologue_cache)
{
- CORE_ADDR func_start = frame_func_unwind (next_frame, NORMAL_FRAME);
- CORE_ADDR stop_addr = frame_pc_unwind (next_frame);
+ CORE_ADDR func_start = get_frame_func (this_frame);
+ CORE_ADDR stop_addr = get_frame_pc (this_frame);
/* If we couldn't find any function containing the PC, then
just initialize the prologue cache, but don't do anything. */
stop_addr = func_start;
*this_prologue_cache = FRAME_OBSTACK_ZALLOC (struct m32c_prologue);
- m32c_analyze_prologue (get_frame_arch (next_frame),
+ m32c_analyze_prologue (get_frame_arch (this_frame),
func_start, stop_addr, *this_prologue_cache);
}
static CORE_ADDR
-m32c_frame_base (struct frame_info *next_frame,
+m32c_frame_base (struct frame_info *this_frame,
void **this_prologue_cache)
{
struct m32c_prologue *p
- = m32c_analyze_frame_prologue (next_frame, this_prologue_cache);
- struct gdbarch_tdep *tdep = gdbarch_tdep (get_frame_arch (next_frame));
+ = m32c_analyze_frame_prologue (this_frame, this_prologue_cache);
+ struct gdbarch_tdep *tdep = gdbarch_tdep (get_frame_arch (this_frame));
/* In functions that use alloca, the distance between the stack
pointer and the frame base varies dynamically, so we can't use
case prologue_with_frame_ptr:
{
CORE_ADDR fb
- = frame_unwind_register_unsigned (next_frame, tdep->fb->num);
+ = get_frame_register_unsigned (this_frame, tdep->fb->num);
return fb - p->frame_ptr_offset;
}
case prologue_sans_frame_ptr:
{
CORE_ADDR sp
- = frame_unwind_register_unsigned (next_frame, tdep->sp->num);
+ = get_frame_register_unsigned (this_frame, tdep->sp->num);
return sp - p->frame_size;
}
static void
-m32c_this_id (struct frame_info *next_frame,
+m32c_this_id (struct frame_info *this_frame,
void **this_prologue_cache,
struct frame_id *this_id)
{
- CORE_ADDR base = m32c_frame_base (next_frame, this_prologue_cache);
+ CORE_ADDR base = m32c_frame_base (this_frame, this_prologue_cache);
if (base)
- *this_id = frame_id_build (base,
- frame_func_unwind (next_frame, NORMAL_FRAME));
+ *this_id = frame_id_build (base, get_frame_func (this_frame));
/* Otherwise, leave it unset, and that will terminate the backtrace. */
}
-static void
-m32c_prev_register (struct frame_info *next_frame,
- void **this_prologue_cache,
- int regnum, int *optimizedp,
- enum lval_type *lvalp, CORE_ADDR *addrp,
- int *realnump, gdb_byte *bufferp)
+static struct value *
+m32c_prev_register (struct frame_info *this_frame,
+ void **this_prologue_cache, int regnum)
{
- struct gdbarch_tdep *tdep = gdbarch_tdep (get_frame_arch (next_frame));
+ struct gdbarch_tdep *tdep = gdbarch_tdep (get_frame_arch (this_frame));
struct m32c_prologue *p
- = m32c_analyze_frame_prologue (next_frame, this_prologue_cache);
- CORE_ADDR frame_base = m32c_frame_base (next_frame, this_prologue_cache);
- int reg_size = register_size (get_frame_arch (next_frame), regnum);
+ = m32c_analyze_frame_prologue (this_frame, this_prologue_cache);
+ CORE_ADDR frame_base = m32c_frame_base (this_frame, this_prologue_cache);
+ int reg_size = register_size (get_frame_arch (this_frame), regnum);
if (regnum == tdep->sp->num)
- {
- *optimizedp = 0;
- *lvalp = not_lval;
- *addrp = 0;
- *realnump = -1;
- if (bufferp)
- store_unsigned_integer (bufferp, reg_size, frame_base);
- }
+ return frame_unwind_got_constant (this_frame, regnum, frame_base);
/* If prologue analysis says we saved this register somewhere,
return a description of the stack slot holding it. */
- else if (p->reg_offset[regnum] != 1)
- {
- *optimizedp = 0;
- *lvalp = lval_memory;
- *addrp = frame_base + p->reg_offset[regnum];
- *realnump = -1;
- if (bufferp)
- get_frame_memory (next_frame, *addrp, bufferp, reg_size);
- }
+ if (p->reg_offset[regnum] != 1)
+ return frame_unwind_got_memory (this_frame, regnum,
+ frame_base + p->reg_offset[regnum]);
/* Otherwise, presume we haven't changed the value of this
register, and get it from the next frame. */
- else
- {
- *optimizedp = 0;
- *lvalp = lval_register;
- *addrp = 0;
- *realnump = regnum;
- if (bufferp)
- frame_unwind_register (next_frame, *realnump, bufferp);
- }
+ return frame_unwind_got_register (this_frame, regnum, regnum);
}
static const struct frame_unwind m32c_unwind = {
NORMAL_FRAME,
m32c_this_id,
- m32c_prev_register
+ m32c_prev_register,
+ NULL,
+ default_frame_sniffer
};
-static const struct frame_unwind *
-m32c_frame_sniffer (struct frame_info *next_frame)
-{
- return &m32c_unwind;
-}
-
-
static CORE_ADDR
m32c_unwind_pc (struct gdbarch *arch, struct frame_info *next_frame)
{
CORE_ADDR struct_addr)
{
struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
+ enum bfd_endian byte_order = gdbarch_byte_order (gdbarch);
unsigned long mach = gdbarch_bfd_arch_info (gdbarch)->mach;
CORE_ADDR cfa;
int i;
{
struct type *func_type = value_type (function);
+ /* Dereference function pointer types. */
+ if (TYPE_CODE (func_type) == TYPE_CODE_PTR)
+ func_type = TYPE_TARGET_TYPE (func_type);
+
gdb_assert (TYPE_CODE (func_type) == TYPE_CODE_FUNC ||
TYPE_CODE (func_type) == TYPE_CODE_METHOD);
{
int ptr_len = TYPE_LENGTH (tdep->ptr_voyd);
sp -= ptr_len;
- write_memory_unsigned_integer (sp, ptr_len, struct_addr);
+ write_memory_unsigned_integer (sp, ptr_len, byte_order, struct_addr);
}
/* Push the arguments. */
sure it ends up in the least significant end of r1. (GDB
should avoid assuming endianness, even on uni-endian
processors.) */
- ULONGEST u = extract_unsigned_integer (arg_bits, arg_size);
+ ULONGEST u = extract_unsigned_integer (arg_bits, arg_size,
+ byte_order);
struct m32c_reg *reg = (mach == bfd_mach_m16c) ? tdep->r1 : tdep->r0;
regcache_cooked_write_unsigned (regcache, reg->num, u);
}
/* Push the return address. */
sp -= tdep->ret_addr_bytes;
- write_memory_unsigned_integer (sp, tdep->ret_addr_bytes, bp_addr);
+ write_memory_unsigned_integer (sp, tdep->ret_addr_bytes, byte_order,
+ bp_addr);
/* Update the stack pointer. */
regcache_cooked_write_unsigned (regcache, tdep->sp->num, sp);
static struct frame_id
-m32c_unwind_dummy_id (struct gdbarch *gdbarch, struct frame_info *next_frame)
+m32c_dummy_id (struct gdbarch *gdbarch, struct frame_info *this_frame)
{
/* This needs to return a frame ID whose PC is the return address
passed to m32c_push_dummy_call, and whose stack_addr is the SP
m32c_unwind_sp gives us the CFA, which is the value the SP had
before the return address was pushed. */
- return frame_id_build (m32c_unwind_sp (gdbarch, next_frame),
- frame_pc_unwind (next_frame));
+ struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
+ CORE_ADDR sp = get_frame_register_unsigned (this_frame, tdep->sp->num);
+ return frame_id_build (sp, get_frame_pc (this_frame));
}
static enum return_value_convention
m32c_return_value (struct gdbarch *gdbarch,
+ struct type *func_type,
struct type *valtype,
struct regcache *regcache,
gdb_byte *readbuf,
const gdb_byte *writebuf)
{
struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
+ enum bfd_endian byte_order = gdbarch_byte_order (gdbarch);
enum return_value_convention conv;
ULONGEST valtype_len = TYPE_LENGTH (valtype);
{
ULONGEST u;
regcache_cooked_read_unsigned (regcache, tdep->r0->num, &u);
- store_unsigned_integer (readbuf, valtype_len, u);
+ store_unsigned_integer (readbuf, valtype_len, byte_order, u);
}
else
{
/* Anything that fits in r0 is returned there. */
if (valtype_len <= TYPE_LENGTH (tdep->r0->type))
{
- ULONGEST u = extract_unsigned_integer (writebuf, valtype_len);
+ ULONGEST u = extract_unsigned_integer (writebuf, valtype_len,
+ byte_order);
regcache_cooked_write_unsigned (regcache, tdep->r0->num, u);
}
else
static CORE_ADDR
m32c_skip_trampoline_code (struct frame_info *frame, CORE_ADDR stop_pc)
{
- struct gdbarch_tdep *tdep = gdbarch_tdep (current_gdbarch);
+ struct gdbarch *gdbarch = get_frame_arch (frame);
+ struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
+ enum bfd_endian byte_order = gdbarch_byte_order (gdbarch);
/* It would be nicer to simply look up the addresses of known
trampolines once, and then compare stop_pc with them. However,
m32c_jsri*16*. */
CORE_ADDR sp = get_frame_sp (get_current_frame ());
CORE_ADDR target
- = read_memory_unsigned_integer (sp + tdep->ret_addr_bytes, 2);
+ = read_memory_unsigned_integer (sp + tdep->ret_addr_bytes,
+ 2, byte_order);
/* What we have now is the address of a jump instruction.
What we need is the destination of that jump.
The opcode is 1 byte, and the destination is the next 3 bytes.
*/
- target = read_memory_unsigned_integer (target + 1, 3);
+ target = read_memory_unsigned_integer (target + 1, 3, byte_order);
return target;
}
}
programmer! :) */
static void
-m32c_m16c_address_to_pointer (struct type *type, gdb_byte *buf, CORE_ADDR addr)
+m32c_m16c_address_to_pointer (struct gdbarch *gdbarch,
+ struct type *type, gdb_byte *buf, CORE_ADDR addr)
{
+ enum bfd_endian byte_order = gdbarch_byte_order (gdbarch);
enum type_code target_code;
gdb_assert (TYPE_CODE (type) == TYPE_CODE_PTR ||
TYPE_CODE (type) == TYPE_CODE_REF);
if (! func_msym)
error ("Cannot convert code address %s to function pointer:\n"
"couldn't find a symbol at that address, to find trampoline.",
- paddr_nz (addr));
+ paddress (gdbarch, addr));
func_name = SYMBOL_LINKAGE_NAME (func_msym);
tramp_name = xmalloc (strlen (func_name) + 5);
if (! tramp_msym)
error ("Cannot convert code address %s to function pointer:\n"
"couldn't find trampoline named '%s.plt'.",
- paddr_nz (addr), func_name);
+ paddress (gdbarch, addr), func_name);
/* The trampoline's address is our pointer. */
addr = SYMBOL_VALUE_ADDRESS (tramp_msym);
}
- store_unsigned_integer (buf, TYPE_LENGTH (type), addr);
+ store_unsigned_integer (buf, TYPE_LENGTH (type), byte_order, addr);
}
static CORE_ADDR
-m32c_m16c_pointer_to_address (struct type *type, const gdb_byte *buf)
+m32c_m16c_pointer_to_address (struct gdbarch *gdbarch,
+ struct type *type, const gdb_byte *buf)
{
+ enum bfd_endian byte_order = gdbarch_byte_order (gdbarch);
CORE_ADDR ptr;
enum type_code target_code;
gdb_assert (TYPE_CODE (type) == TYPE_CODE_PTR ||
TYPE_CODE (type) == TYPE_CODE_REF);
- ptr = extract_unsigned_integer (buf, TYPE_LENGTH (type));
+ ptr = extract_unsigned_integer (buf, TYPE_LENGTH (type), byte_order);
target_code = TYPE_CODE (TYPE_TARGET_TYPE (type));
return ptr;
}
-void
+static void
m32c_virtual_frame_pointer (struct gdbarch *gdbarch, CORE_ADDR pc,
int *frame_regnum,
LONGEST *frame_offset)
know which, but I do know that the prologue analyzer works better.
MVS 04/13/06
*/
- frame_unwind_append_sniffer (arch, dwarf2_frame_sniffer);
+ dwarf2_append_sniffers (arch);
#endif
- frame_unwind_append_sniffer (arch, m32c_frame_sniffer);
+ frame_unwind_append_unwinder (arch, &m32c_unwind);
/* Inferior calls. */
set_gdbarch_push_dummy_call (arch, m32c_push_dummy_call);
set_gdbarch_return_value (arch, m32c_return_value);
- set_gdbarch_unwind_dummy_id (arch, m32c_unwind_dummy_id);
+ set_gdbarch_dummy_id (arch, m32c_dummy_id);
/* Trampolines. */
set_gdbarch_skip_trampoline_code (arch, m32c_skip_trampoline_code);
set_gdbarch_virtual_frame_pointer (arch, m32c_virtual_frame_pointer);
+ /* m32c function boundary addresses are not necessarily even.
+ Therefore, the `vbit', which indicates a pointer to a virtual
+ member function, is stored in the delta field, rather than as
+ the low bit of a function pointer address.
+
+ In order to verify this, see the definition of
+ TARGET_PTRMEMFUNC_VBIT_LOCATION in gcc/defaults.h along with the
+ definition of FUNCTION_BOUNDARY in gcc/config/m32c/m32c.h. */
+ set_gdbarch_vbit_in_delta (arch, 1);
+
return arch;
}
+/* Provide a prototype to silence -Wmissing-prototypes. */
+extern initialize_file_ftype _initialize_m32c_tdep;
void
_initialize_m32c_tdep (void)