OpenCores
URL https://opencores.org/ocsvn/openrisc_2011-10-31/openrisc_2011-10-31/trunk

Subversion Repositories openrisc_2011-10-31

[/] [openrisc/] [trunk/] [gnu-src/] [gdb-7.1/] [gdb/] [m68hc11-tdep.c] - Blame information for rev 227

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 227 jeremybenn
/* Target-dependent code for Motorola 68HC11 & 68HC12
2
 
3
   Copyright (C) 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2007, 2008, 2009,
4
   2010 Free Software Foundation, Inc.
5
 
6
   Contributed by Stephane Carrez, stcarrez@nerim.fr
7
 
8
   This file is part of GDB.
9
 
10
   This program is free software; you can redistribute it and/or modify
11
   it under the terms of the GNU General Public License as published by
12
   the Free Software Foundation; either version 3 of the License, or
13
   (at your option) any later version.
14
 
15
   This program is distributed in the hope that it will be useful,
16
   but WITHOUT ANY WARRANTY; without even the implied warranty of
17
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18
   GNU General Public License for more details.
19
 
20
   You should have received a copy of the GNU General Public License
21
   along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
22
 
23
 
24
#include "defs.h"
25
#include "frame.h"
26
#include "frame-unwind.h"
27
#include "frame-base.h"
28
#include "dwarf2-frame.h"
29
#include "trad-frame.h"
30
#include "symtab.h"
31
#include "gdbtypes.h"
32
#include "gdbcmd.h"
33
#include "gdbcore.h"
34
#include "gdb_string.h"
35
#include "value.h"
36
#include "inferior.h"
37
#include "dis-asm.h"  
38
#include "symfile.h"
39
#include "objfiles.h"
40
#include "arch-utils.h"
41
#include "regcache.h"
42
#include "reggroups.h"
43
 
44
#include "target.h"
45
#include "opcode/m68hc11.h"
46
#include "elf/m68hc11.h"
47
#include "elf-bfd.h"
48
 
49
/* Macros for setting and testing a bit in a minimal symbol.
50
   For 68HC11/68HC12 we have two flags that tell which return
51
   type the function is using.  This is used for prologue and frame
52
   analysis to compute correct stack frame layout.
53
 
54
   The MSB of the minimal symbol's "info" field is used for this purpose.
55
 
56
   MSYMBOL_SET_RTC      Actually sets the "RTC" bit.
57
   MSYMBOL_SET_RTI      Actually sets the "RTI" bit.
58
   MSYMBOL_IS_RTC       Tests the "RTC" bit in a minimal symbol.
59
   MSYMBOL_IS_RTI       Tests the "RTC" bit in a minimal symbol.  */
60
 
61
#define MSYMBOL_SET_RTC(msym)                                           \
62
        MSYMBOL_TARGET_FLAG_1 (msym) = 1
63
 
64
#define MSYMBOL_SET_RTI(msym)                                           \
65
        MSYMBOL_TARGET_FLAG_2 (msym) = 1
66
 
67
#define MSYMBOL_IS_RTC(msym)                            \
68
        MSYMBOL_TARGET_FLAG_1 (msym)
69
 
70
#define MSYMBOL_IS_RTI(msym)                            \
71
        MSYMBOL_TARGET_FLAG_2 (msym)
72
 
73
enum insn_return_kind {
74
  RETURN_RTS,
75
  RETURN_RTC,
76
  RETURN_RTI
77
};
78
 
79
 
80
/* Register numbers of various important registers.  */
81
 
82
#define HARD_X_REGNUM   0
83
#define HARD_D_REGNUM   1
84
#define HARD_Y_REGNUM   2
85
#define HARD_SP_REGNUM  3
86
#define HARD_PC_REGNUM  4
87
 
88
#define HARD_A_REGNUM   5
89
#define HARD_B_REGNUM   6
90
#define HARD_CCR_REGNUM 7
91
 
92
/* 68HC12 page number register.
93
   Note: to keep a compatibility with gcc register naming, we must
94
   not have to rename FP and other soft registers.  The page register
95
   is a real hard register and must therefore be counted by gdbarch_num_regs.
96
   For this it has the same number as Z register (which is not used).  */
97
#define HARD_PAGE_REGNUM 8
98
#define M68HC11_LAST_HARD_REG (HARD_PAGE_REGNUM)
99
 
100
/* Z is replaced by X or Y by gcc during machine reorg.
101
   ??? There is no way to get it and even know whether
102
   it's in X or Y or in ZS.  */
103
#define SOFT_Z_REGNUM        8
104
 
105
/* Soft registers.  These registers are special.  There are treated
106
   like normal hard registers by gcc and gdb (ie, within dwarf2 info).
107
   They are physically located in memory.  */
108
#define SOFT_FP_REGNUM       9
109
#define SOFT_TMP_REGNUM     10
110
#define SOFT_ZS_REGNUM      11
111
#define SOFT_XY_REGNUM      12
112
#define SOFT_UNUSED_REGNUM  13
113
#define SOFT_D1_REGNUM      14
114
#define SOFT_D32_REGNUM     (SOFT_D1_REGNUM+31)
115
#define M68HC11_MAX_SOFT_REGS 32
116
 
117
#define M68HC11_NUM_REGS        (8)
118
#define M68HC11_NUM_PSEUDO_REGS (M68HC11_MAX_SOFT_REGS+5)
119
#define M68HC11_ALL_REGS        (M68HC11_NUM_REGS+M68HC11_NUM_PSEUDO_REGS)
120
 
121
#define M68HC11_REG_SIZE    (2)
122
 
123
#define M68HC12_NUM_REGS        (9)
124
#define M68HC12_NUM_PSEUDO_REGS ((M68HC11_MAX_SOFT_REGS+5)+1-1)
125
#define M68HC12_HARD_PC_REGNUM  (SOFT_D32_REGNUM+1)
126
 
127
struct insn_sequence;
128
struct gdbarch_tdep
129
  {
130
    /* Stack pointer correction value.  For 68hc11, the stack pointer points
131
       to the next push location.  An offset of 1 must be applied to obtain
132
       the address where the last value is saved.  For 68hc12, the stack
133
       pointer points to the last value pushed.  No offset is necessary.  */
134
    int stack_correction;
135
 
136
    /* Description of instructions in the prologue.  */
137
    struct insn_sequence *prologue;
138
 
139
    /* True if the page memory bank register is available
140
       and must be used.  */
141
    int use_page_register;
142
 
143
    /* ELF flags for ABI.  */
144
    int elf_flags;
145
  };
146
 
147
#define STACK_CORRECTION(gdbarch) (gdbarch_tdep (gdbarch)->stack_correction)
148
#define USE_PAGE_REGISTER(gdbarch) (gdbarch_tdep (gdbarch)->use_page_register)
149
 
150
struct m68hc11_unwind_cache
151
{
152
  /* The previous frame's inner most stack address.  Used as this
153
     frame ID's stack_addr.  */
154
  CORE_ADDR prev_sp;
155
  /* The frame's base, optionally used by the high-level debug info.  */
156
  CORE_ADDR base;
157
  CORE_ADDR pc;
158
  int size;
159
  int prologue_type;
160
  CORE_ADDR return_pc;
161
  CORE_ADDR sp_offset;
162
  int frameless;
163
  enum insn_return_kind return_kind;
164
 
165
  /* Table indicating the location of each and every register.  */
166
  struct trad_frame_saved_reg *saved_regs;
167
};
168
 
169
/* Table of registers for 68HC11.  This includes the hard registers
170
   and the soft registers used by GCC.  */
171
static char *
172
m68hc11_register_names[] =
173
{
174
  "x",    "d",    "y",    "sp",   "pc",   "a",    "b",
175
  "ccr",  "page", "frame","tmp",  "zs",   "xy",   0,
176
  "d1",   "d2",   "d3",   "d4",   "d5",   "d6",   "d7",
177
  "d8",   "d9",   "d10",  "d11",  "d12",  "d13",  "d14",
178
  "d15",  "d16",  "d17",  "d18",  "d19",  "d20",  "d21",
179
  "d22",  "d23",  "d24",  "d25",  "d26",  "d27",  "d28",
180
  "d29",  "d30",  "d31",  "d32"
181
};
182
 
183
struct m68hc11_soft_reg
184
{
185
  const char *name;
186
  CORE_ADDR   addr;
187
};
188
 
189
static struct m68hc11_soft_reg soft_regs[M68HC11_ALL_REGS];
190
 
191
#define M68HC11_FP_ADDR soft_regs[SOFT_FP_REGNUM].addr
192
 
193
static int soft_min_addr;
194
static int soft_max_addr;
195
static int soft_reg_initialized = 0;
196
 
197
/* Look in the symbol table for the address of a pseudo register
198
   in memory.  If we don't find it, pretend the register is not used
199
   and not available.  */
200
static void
201
m68hc11_get_register_info (struct m68hc11_soft_reg *reg, const char *name)
202
{
203
  struct minimal_symbol *msymbol;
204
 
205
  msymbol = lookup_minimal_symbol (name, NULL, NULL);
206
  if (msymbol)
207
    {
208
      reg->addr = SYMBOL_VALUE_ADDRESS (msymbol);
209
      reg->name = xstrdup (name);
210
 
211
      /* Keep track of the address range for soft registers.  */
212
      if (reg->addr < (CORE_ADDR) soft_min_addr)
213
        soft_min_addr = reg->addr;
214
      if (reg->addr > (CORE_ADDR) soft_max_addr)
215
        soft_max_addr = reg->addr;
216
    }
217
  else
218
    {
219
      reg->name = 0;
220
      reg->addr = 0;
221
    }
222
}
223
 
224
/* Initialize the table of soft register addresses according
225
   to the symbol table.  */
226
  static void
227
m68hc11_initialize_register_info (void)
228
{
229
  int i;
230
 
231
  if (soft_reg_initialized)
232
    return;
233
 
234
  soft_min_addr = INT_MAX;
235
  soft_max_addr = 0;
236
  for (i = 0; i < M68HC11_ALL_REGS; i++)
237
    {
238
      soft_regs[i].name = 0;
239
    }
240
 
241
  m68hc11_get_register_info (&soft_regs[SOFT_FP_REGNUM], "_.frame");
242
  m68hc11_get_register_info (&soft_regs[SOFT_TMP_REGNUM], "_.tmp");
243
  m68hc11_get_register_info (&soft_regs[SOFT_ZS_REGNUM], "_.z");
244
  soft_regs[SOFT_Z_REGNUM] = soft_regs[SOFT_ZS_REGNUM];
245
  m68hc11_get_register_info (&soft_regs[SOFT_XY_REGNUM], "_.xy");
246
 
247
  for (i = SOFT_D1_REGNUM; i < M68HC11_MAX_SOFT_REGS; i++)
248
    {
249
      char buf[10];
250
 
251
      sprintf (buf, "_.d%d", i - SOFT_D1_REGNUM + 1);
252
      m68hc11_get_register_info (&soft_regs[i], buf);
253
    }
254
 
255
  if (soft_regs[SOFT_FP_REGNUM].name == 0)
256
    warning (_("No frame soft register found in the symbol table.\n"
257
               "Stack backtrace will not work."));
258
  soft_reg_initialized = 1;
259
}
260
 
261
/* Given an address in memory, return the soft register number if
262
   that address corresponds to a soft register.  Returns -1 if not.  */
263
static int
264
m68hc11_which_soft_register (CORE_ADDR addr)
265
{
266
  int i;
267
 
268
  if (addr < soft_min_addr || addr > soft_max_addr)
269
    return -1;
270
 
271
  for (i = SOFT_FP_REGNUM; i < M68HC11_ALL_REGS; i++)
272
    {
273
      if (soft_regs[i].name && soft_regs[i].addr == addr)
274
        return i;
275
    }
276
  return -1;
277
}
278
 
279
/* Fetch a pseudo register.  The 68hc11 soft registers are treated like
280
   pseudo registers.  They are located in memory.  Translate the register
281
   fetch into a memory read.  */
282
static void
283
m68hc11_pseudo_register_read (struct gdbarch *gdbarch,
284
                              struct regcache *regcache,
285
                              int regno, gdb_byte *buf)
286
{
287
  enum bfd_endian byte_order = gdbarch_byte_order (gdbarch);
288
 
289
  /* The PC is a pseudo reg only for 68HC12 with the memory bank
290
     addressing mode.  */
291
  if (regno == M68HC12_HARD_PC_REGNUM)
292
    {
293
      ULONGEST pc;
294
      const int regsize = 4;
295
 
296
      regcache_cooked_read_unsigned (regcache, HARD_PC_REGNUM, &pc);
297
      if (pc >= 0x8000 && pc < 0xc000)
298
        {
299
          ULONGEST page;
300
 
301
          regcache_cooked_read_unsigned (regcache, HARD_PAGE_REGNUM, &page);
302
          pc -= 0x8000;
303
          pc += (page << 14);
304
          pc += 0x1000000;
305
        }
306
      store_unsigned_integer (buf, regsize, byte_order, pc);
307
      return;
308
    }
309
 
310
  m68hc11_initialize_register_info ();
311
 
312
  /* Fetch a soft register: translate into a memory read.  */
313
  if (soft_regs[regno].name)
314
    {
315
      target_read_memory (soft_regs[regno].addr, buf, 2);
316
    }
317
  else
318
    {
319
      memset (buf, 0, 2);
320
    }
321
}
322
 
323
/* Store a pseudo register.  Translate the register store
324
   into a memory write.  */
325
static void
326
m68hc11_pseudo_register_write (struct gdbarch *gdbarch,
327
                               struct regcache *regcache,
328
                               int regno, const gdb_byte *buf)
329
{
330
  enum bfd_endian byte_order = gdbarch_byte_order (gdbarch);
331
 
332
  /* The PC is a pseudo reg only for 68HC12 with the memory bank
333
     addressing mode.  */
334
  if (regno == M68HC12_HARD_PC_REGNUM)
335
    {
336
      const int regsize = 4;
337
      char *tmp = alloca (regsize);
338
      CORE_ADDR pc;
339
 
340
      memcpy (tmp, buf, regsize);
341
      pc = extract_unsigned_integer (tmp, regsize, byte_order);
342
      if (pc >= 0x1000000)
343
        {
344
          pc -= 0x1000000;
345
          regcache_cooked_write_unsigned (regcache, HARD_PAGE_REGNUM,
346
                                          (pc >> 14) & 0x0ff);
347
          pc &= 0x03fff;
348
          regcache_cooked_write_unsigned (regcache, HARD_PC_REGNUM,
349
                                          pc + 0x8000);
350
        }
351
      else
352
        regcache_cooked_write_unsigned (regcache, HARD_PC_REGNUM, pc);
353
      return;
354
    }
355
 
356
  m68hc11_initialize_register_info ();
357
 
358
  /* Store a soft register: translate into a memory write.  */
359
  if (soft_regs[regno].name)
360
    {
361
      const int regsize = 2;
362
      char *tmp = alloca (regsize);
363
      memcpy (tmp, buf, regsize);
364
      target_write_memory (soft_regs[regno].addr, tmp, regsize);
365
    }
366
}
367
 
368
static const char *
369
m68hc11_register_name (struct gdbarch *gdbarch, int reg_nr)
370
{
371
  if (reg_nr == M68HC12_HARD_PC_REGNUM && USE_PAGE_REGISTER (gdbarch))
372
    return "pc";
373
  if (reg_nr == HARD_PC_REGNUM && USE_PAGE_REGISTER (gdbarch))
374
    return "ppc";
375
 
376
  if (reg_nr < 0)
377
    return NULL;
378
  if (reg_nr >= M68HC11_ALL_REGS)
379
    return NULL;
380
 
381
  m68hc11_initialize_register_info ();
382
 
383
  /* If we don't know the address of a soft register, pretend it
384
     does not exist.  */
385
  if (reg_nr > M68HC11_LAST_HARD_REG && soft_regs[reg_nr].name == 0)
386
    return NULL;
387
  return m68hc11_register_names[reg_nr];
388
}
389
 
390
static const unsigned char *
391
m68hc11_breakpoint_from_pc (struct gdbarch *gdbarch, CORE_ADDR *pcptr,
392
                            int *lenptr)
393
{
394
  static unsigned char breakpoint[] = {0x0};
395
 
396
  *lenptr = sizeof (breakpoint);
397
  return breakpoint;
398
}
399
 
400
 
401
/* 68HC11 & 68HC12 prologue analysis.
402
 
403
 */
404
#define MAX_CODES 12
405
 
406
/* 68HC11 opcodes.  */
407
#undef M6811_OP_PAGE2
408
#define M6811_OP_PAGE2   (0x18)
409
#define M6811_OP_LDX     (0xde)
410
#define M6811_OP_LDX_EXT (0xfe)
411
#define M6811_OP_PSHX    (0x3c)
412
#define M6811_OP_STS     (0x9f)
413
#define M6811_OP_STS_EXT (0xbf)
414
#define M6811_OP_TSX     (0x30)
415
#define M6811_OP_XGDX    (0x8f)
416
#define M6811_OP_ADDD    (0xc3)
417
#define M6811_OP_TXS     (0x35)
418
#define M6811_OP_DES     (0x34)
419
 
420
/* 68HC12 opcodes.  */
421
#define M6812_OP_PAGE2   (0x18)
422
#define M6812_OP_MOVW    (0x01)
423
#define M6812_PB_PSHW    (0xae)
424
#define M6812_OP_STS     (0x5f)
425
#define M6812_OP_STS_EXT (0x7f)
426
#define M6812_OP_LEAS    (0x1b)
427
#define M6812_OP_PSHX    (0x34)
428
#define M6812_OP_PSHY    (0x35)
429
 
430
/* Operand extraction.  */
431
#define OP_DIRECT      (0x100) /* 8-byte direct addressing.  */
432
#define OP_IMM_LOW     (0x200) /* Low part of 16-bit constant/address.  */
433
#define OP_IMM_HIGH    (0x300) /* High part of 16-bit constant/address.  */
434
#define OP_PBYTE       (0x400) /* 68HC12 indexed operand.  */
435
 
436
/* Identification of the sequence.  */
437
enum m6811_seq_type
438
{
439
  P_LAST = 0,
440
  P_SAVE_REG,  /* Save a register on the stack.  */
441
  P_SET_FRAME, /* Setup the frame pointer.  */
442
  P_LOCAL_1,   /* Allocate 1 byte for locals.  */
443
  P_LOCAL_2,   /* Allocate 2 bytes for locals.  */
444
  P_LOCAL_N    /* Allocate N bytes for locals.  */
445
};
446
 
447
struct insn_sequence {
448
  enum m6811_seq_type type;
449
  unsigned length;
450
  unsigned short code[MAX_CODES];
451
};
452
 
453
/* Sequence of instructions in the 68HC11 function prologue.  */
454
static struct insn_sequence m6811_prologue[] = {
455
  /* Sequences to save a soft-register.  */
456
  { P_SAVE_REG, 3, { M6811_OP_LDX, OP_DIRECT,
457
                     M6811_OP_PSHX } },
458
  { P_SAVE_REG, 5, { M6811_OP_PAGE2, M6811_OP_LDX, OP_DIRECT,
459
                     M6811_OP_PAGE2, M6811_OP_PSHX } },
460
  { P_SAVE_REG, 4, { M6811_OP_LDX_EXT, OP_IMM_HIGH, OP_IMM_LOW,
461
                     M6811_OP_PSHX } },
462
  { P_SAVE_REG, 6, { M6811_OP_PAGE2, M6811_OP_LDX_EXT, OP_IMM_HIGH, OP_IMM_LOW,
463
                     M6811_OP_PAGE2, M6811_OP_PSHX } },
464
 
465
  /* Sequences to allocate local variables.  */
466
  { P_LOCAL_N,  7, { M6811_OP_TSX,
467
                     M6811_OP_XGDX,
468
                     M6811_OP_ADDD, OP_IMM_HIGH, OP_IMM_LOW,
469
                     M6811_OP_XGDX,
470
                     M6811_OP_TXS } },
471
  { P_LOCAL_N, 11, { M6811_OP_PAGE2, M6811_OP_TSX,
472
                     M6811_OP_PAGE2, M6811_OP_XGDX,
473
                     M6811_OP_ADDD, OP_IMM_HIGH, OP_IMM_LOW,
474
                     M6811_OP_PAGE2, M6811_OP_XGDX,
475
                     M6811_OP_PAGE2, M6811_OP_TXS } },
476
  { P_LOCAL_1,  1, { M6811_OP_DES } },
477
  { P_LOCAL_2,  1, { M6811_OP_PSHX } },
478
  { P_LOCAL_2,  2, { M6811_OP_PAGE2, M6811_OP_PSHX } },
479
 
480
  /* Initialize the frame pointer.  */
481
  { P_SET_FRAME, 2, { M6811_OP_STS, OP_DIRECT } },
482
  { P_SET_FRAME, 3, { M6811_OP_STS_EXT, OP_IMM_HIGH, OP_IMM_LOW } },
483
  { P_LAST, 0, { 0 } }
484
};
485
 
486
 
487
/* Sequence of instructions in the 68HC12 function prologue.  */
488
static struct insn_sequence m6812_prologue[] = {
489
  { P_SAVE_REG,  5, { M6812_OP_PAGE2, M6812_OP_MOVW, M6812_PB_PSHW,
490
                      OP_IMM_HIGH, OP_IMM_LOW } },
491
  { P_SET_FRAME, 2, { M6812_OP_STS, OP_DIRECT } },
492
  { P_SET_FRAME, 3, { M6812_OP_STS_EXT, OP_IMM_HIGH, OP_IMM_LOW } },
493
  { P_LOCAL_N,   2, { M6812_OP_LEAS, OP_PBYTE } },
494
  { P_LOCAL_2,   1, { M6812_OP_PSHX } },
495
  { P_LOCAL_2,   1, { M6812_OP_PSHY } },
496
  { P_LAST, 0 }
497
};
498
 
499
 
500
/* Analyze the sequence of instructions starting at the given address.
501
   Returns a pointer to the sequence when it is recognized and
502
   the optional value (constant/address) associated with it.  */
503
static struct insn_sequence *
504
m68hc11_analyze_instruction (struct gdbarch *gdbarch,
505
                             struct insn_sequence *seq, CORE_ADDR pc,
506
                             CORE_ADDR *val)
507
{
508
  enum bfd_endian byte_order = gdbarch_byte_order (gdbarch);
509
  unsigned char buffer[MAX_CODES];
510
  unsigned bufsize;
511
  unsigned j;
512
  CORE_ADDR cur_val;
513
  short v = 0;
514
 
515
  bufsize = 0;
516
  for (; seq->type != P_LAST; seq++)
517
    {
518
      cur_val = 0;
519
      for (j = 0; j < seq->length; j++)
520
        {
521
          if (bufsize < j + 1)
522
            {
523
              buffer[bufsize] = read_memory_unsigned_integer (pc + bufsize,
524
                                                              1, byte_order);
525
              bufsize++;
526
            }
527
          /* Continue while we match the opcode.  */
528
          if (seq->code[j] == buffer[j])
529
            continue;
530
 
531
          if ((seq->code[j] & 0xf00) == 0)
532
            break;
533
 
534
          /* Extract a sequence parameter (address or constant).  */
535
          switch (seq->code[j])
536
            {
537
            case OP_DIRECT:
538
              cur_val = (CORE_ADDR) buffer[j];
539
              break;
540
 
541
            case OP_IMM_HIGH:
542
              cur_val = cur_val & 0x0ff;
543
              cur_val |= (buffer[j] << 8);
544
              break;
545
 
546
            case OP_IMM_LOW:
547
              cur_val &= 0x0ff00;
548
              cur_val |= buffer[j];
549
              break;
550
 
551
            case OP_PBYTE:
552
              if ((buffer[j] & 0xE0) == 0x80)
553
                {
554
                  v = buffer[j] & 0x1f;
555
                  if (v & 0x10)
556
                    v |= 0xfff0;
557
                }
558
              else if ((buffer[j] & 0xfe) == 0xf0)
559
                {
560
                  v = read_memory_unsigned_integer (pc + j + 1, 1, byte_order);
561
                  if (buffer[j] & 1)
562
                    v |= 0xff00;
563
                }
564
              else if (buffer[j] == 0xf2)
565
                {
566
                  v = read_memory_unsigned_integer (pc + j + 1, 2, byte_order);
567
                }
568
              cur_val = v;
569
              break;
570
            }
571
        }
572
 
573
      /* We have a full match.  */
574
      if (j == seq->length)
575
        {
576
          *val = cur_val;
577
          return seq;
578
        }
579
    }
580
  return 0;
581
}
582
 
583
/* Return the instruction that the function at the PC is using.  */
584
static enum insn_return_kind
585
m68hc11_get_return_insn (CORE_ADDR pc)
586
{
587
  struct minimal_symbol *sym;
588
 
589
  /* A flag indicating that this is a STO_M68HC12_FAR or STO_M68HC12_INTERRUPT
590
     function is stored by elfread.c in the high bit of the info field.
591
     Use this to decide which instruction the function uses to return.  */
592
  sym = lookup_minimal_symbol_by_pc (pc);
593
  if (sym == 0)
594
    return RETURN_RTS;
595
 
596
  if (MSYMBOL_IS_RTC (sym))
597
    return RETURN_RTC;
598
  else if (MSYMBOL_IS_RTI (sym))
599
    return RETURN_RTI;
600
  else
601
    return RETURN_RTS;
602
}
603
 
604
/* Analyze the function prologue to find some information
605
   about the function:
606
    - the PC of the first line (for m68hc11_skip_prologue)
607
    - the offset of the previous frame saved address (from current frame)
608
    - the soft registers which are pushed.  */
609
static CORE_ADDR
610
m68hc11_scan_prologue (struct gdbarch *gdbarch, CORE_ADDR pc,
611
                       CORE_ADDR current_pc, struct m68hc11_unwind_cache *info)
612
{
613
  LONGEST save_addr;
614
  CORE_ADDR func_end;
615
  int size;
616
  int found_frame_point;
617
  int saved_reg;
618
  int done = 0;
619
  struct insn_sequence *seq_table;
620
 
621
  info->size = 0;
622
  info->sp_offset = 0;
623
  if (pc >= current_pc)
624
    return current_pc;
625
 
626
  size = 0;
627
 
628
  m68hc11_initialize_register_info ();
629
  if (pc == 0)
630
    {
631
      info->size = 0;
632
      return pc;
633
    }
634
 
635
  seq_table = gdbarch_tdep (gdbarch)->prologue;
636
 
637
  /* The 68hc11 stack is as follows:
638
 
639
 
640
     |           |
641
     +-----------+
642
     |           |
643
     | args      |
644
     |           |
645
     +-----------+
646
     | PC-return |
647
     +-----------+
648
     | Old frame |
649
     +-----------+
650
     |           |
651
     | Locals    |
652
     |           |
653
     +-----------+ <--- current frame
654
     |           |
655
 
656
     With most processors (like 68K) the previous frame can be computed
657
     easily because it is always at a fixed offset (see link/unlink).
658
     That is, locals are accessed with negative offsets, arguments are
659
     accessed with positive ones.  Since 68hc11 only supports offsets
660
     in the range [0..255], the frame is defined at the bottom of
661
     locals (see picture).
662
 
663
     The purpose of the analysis made here is to find out the size
664
     of locals in this function.  An alternative to this is to use
665
     DWARF2 info.  This would be better but I don't know how to
666
     access dwarf2 debug from this function.
667
 
668
     Walk from the function entry point to the point where we save
669
     the frame.  While walking instructions, compute the size of bytes
670
     which are pushed.  This gives us the index to access the previous
671
     frame.
672
 
673
     We limit the search to 128 bytes so that the algorithm is bounded
674
     in case of random and wrong code.  We also stop and abort if
675
     we find an instruction which is not supposed to appear in the
676
     prologue (as generated by gcc 2.95, 2.96).
677
  */
678
  func_end = pc + 128;
679
  found_frame_point = 0;
680
  info->size = 0;
681
  save_addr = 0;
682
  while (!done && pc + 2 < func_end)
683
    {
684
      struct insn_sequence *seq;
685
      CORE_ADDR val;
686
 
687
      seq = m68hc11_analyze_instruction (gdbarch, seq_table, pc, &val);
688
      if (seq == 0)
689
        break;
690
 
691
      /* If we are within the instruction group, we can't advance the
692
         pc nor the stack offset.  Otherwise the caller's stack computed
693
         from the current stack can be wrong.  */
694
      if (pc + seq->length > current_pc)
695
        break;
696
 
697
      pc = pc + seq->length;
698
      if (seq->type == P_SAVE_REG)
699
        {
700
          if (found_frame_point)
701
            {
702
              saved_reg = m68hc11_which_soft_register (val);
703
              if (saved_reg < 0)
704
                break;
705
 
706
              save_addr -= 2;
707
              if (info->saved_regs)
708
                info->saved_regs[saved_reg].addr = save_addr;
709
            }
710
          else
711
            {
712
              size += 2;
713
            }
714
        }
715
      else if (seq->type == P_SET_FRAME)
716
        {
717
          found_frame_point = 1;
718
          info->size = size;
719
        }
720
      else if (seq->type == P_LOCAL_1)
721
        {
722
          size += 1;
723
        }
724
      else if (seq->type == P_LOCAL_2)
725
        {
726
          size += 2;
727
        }
728
      else if (seq->type == P_LOCAL_N)
729
        {
730
          /* Stack pointer is decremented for the allocation.  */
731
          if (val & 0x8000)
732
            size -= (int) (val) | 0xffff0000;
733
          else
734
            size -= val;
735
        }
736
    }
737
  if (found_frame_point == 0)
738
    info->sp_offset = size;
739
  else
740
    info->sp_offset = -1;
741
  return pc;
742
}
743
 
744
static CORE_ADDR
745
m68hc11_skip_prologue (struct gdbarch *gdbarch, CORE_ADDR pc)
746
{
747
  CORE_ADDR func_addr, func_end;
748
  struct symtab_and_line sal;
749
  struct m68hc11_unwind_cache tmp_cache = { 0 };
750
 
751
  /* If we have line debugging information, then the end of the
752
     prologue should be the first assembly instruction of the
753
     first source line.  */
754
  if (find_pc_partial_function (pc, NULL, &func_addr, &func_end))
755
    {
756
      sal = find_pc_line (func_addr, 0);
757
      if (sal.end && sal.end < func_end)
758
        return sal.end;
759
    }
760
 
761
  pc = m68hc11_scan_prologue (gdbarch, pc, (CORE_ADDR) -1, &tmp_cache);
762
  return pc;
763
}
764
 
765
static CORE_ADDR
766
m68hc11_unwind_pc (struct gdbarch *gdbarch, struct frame_info *next_frame)
767
{
768
  ULONGEST pc;
769
 
770
  pc = frame_unwind_register_unsigned (next_frame, gdbarch_pc_regnum (gdbarch));
771
  return pc;
772
}
773
 
774
/* Put here the code to store, into fi->saved_regs, the addresses of
775
   the saved registers of frame described by FRAME_INFO.  This
776
   includes special registers such as pc and fp saved in special ways
777
   in the stack frame.  sp is even more special: the address we return
778
   for it IS the sp for the next frame. */
779
 
780
static struct m68hc11_unwind_cache *
781
m68hc11_frame_unwind_cache (struct frame_info *this_frame,
782
                            void **this_prologue_cache)
783
{
784
  struct gdbarch *gdbarch = get_frame_arch (this_frame);
785
  ULONGEST prev_sp;
786
  ULONGEST this_base;
787
  struct m68hc11_unwind_cache *info;
788
  CORE_ADDR current_pc;
789
  int i;
790
 
791
  if ((*this_prologue_cache))
792
    return (*this_prologue_cache);
793
 
794
  info = FRAME_OBSTACK_ZALLOC (struct m68hc11_unwind_cache);
795
  (*this_prologue_cache) = info;
796
  info->saved_regs = trad_frame_alloc_saved_regs (this_frame);
797
 
798
  info->pc = get_frame_func (this_frame);
799
 
800
  info->size = 0;
801
  info->return_kind = m68hc11_get_return_insn (info->pc);
802
 
803
  /* The SP was moved to the FP.  This indicates that a new frame
804
     was created.  Get THIS frame's FP value by unwinding it from
805
     the next frame.  */
806
  this_base = get_frame_register_unsigned (this_frame, SOFT_FP_REGNUM);
807
  if (this_base == 0)
808
    {
809
      info->base = 0;
810
      return info;
811
    }
812
 
813
  current_pc = get_frame_pc (this_frame);
814
  if (info->pc != 0)
815
    m68hc11_scan_prologue (gdbarch, info->pc, current_pc, info);
816
 
817
  info->saved_regs[HARD_PC_REGNUM].addr = info->size;
818
 
819
  if (info->sp_offset != (CORE_ADDR) -1)
820
    {
821
      info->saved_regs[HARD_PC_REGNUM].addr = info->sp_offset;
822
      this_base = get_frame_register_unsigned (this_frame, HARD_SP_REGNUM);
823
      prev_sp = this_base + info->sp_offset + 2;
824
      this_base += STACK_CORRECTION (gdbarch);
825
    }
826
  else
827
    {
828
      /* The FP points at the last saved register.  Adjust the FP back
829
         to before the first saved register giving the SP.  */
830
      prev_sp = this_base + info->size + 2;
831
 
832
      this_base += STACK_CORRECTION (gdbarch);
833
      if (soft_regs[SOFT_FP_REGNUM].name)
834
        info->saved_regs[SOFT_FP_REGNUM].addr = info->size - 2;
835
   }
836
 
837
  if (info->return_kind == RETURN_RTC)
838
    {
839
      prev_sp += 1;
840
      info->saved_regs[HARD_PAGE_REGNUM].addr = info->size;
841
      info->saved_regs[HARD_PC_REGNUM].addr = info->size + 1;
842
    }
843
  else if (info->return_kind == RETURN_RTI)
844
    {
845
      prev_sp += 7;
846
      info->saved_regs[HARD_CCR_REGNUM].addr = info->size;
847
      info->saved_regs[HARD_D_REGNUM].addr = info->size + 1;
848
      info->saved_regs[HARD_X_REGNUM].addr = info->size + 3;
849
      info->saved_regs[HARD_Y_REGNUM].addr = info->size + 5;
850
      info->saved_regs[HARD_PC_REGNUM].addr = info->size + 7;
851
    }
852
 
853
  /* Add 1 here to adjust for the post-decrement nature of the push
854
     instruction.*/
855
  info->prev_sp = prev_sp;
856
 
857
  info->base = this_base;
858
 
859
  /* Adjust all the saved registers so that they contain addresses and not
860
     offsets.  */
861
  for (i = 0;
862
       i < gdbarch_num_regs (gdbarch)
863
           + gdbarch_num_pseudo_regs (gdbarch) - 1;
864
       i++)
865
    if (trad_frame_addr_p (info->saved_regs, i))
866
      {
867
        info->saved_regs[i].addr += this_base;
868
      }
869
 
870
  /* The previous frame's SP needed to be computed.  Save the computed
871
     value.  */
872
  trad_frame_set_value (info->saved_regs, HARD_SP_REGNUM, info->prev_sp);
873
 
874
  return info;
875
}
876
 
877
/* Given a GDB frame, determine the address of the calling function's
878
   frame.  This will be used to create a new GDB frame struct.  */
879
 
880
static void
881
m68hc11_frame_this_id (struct frame_info *this_frame,
882
                       void **this_prologue_cache,
883
                       struct frame_id *this_id)
884
{
885
  struct m68hc11_unwind_cache *info
886
    = m68hc11_frame_unwind_cache (this_frame, this_prologue_cache);
887
  CORE_ADDR base;
888
  CORE_ADDR func;
889
  struct frame_id id;
890
 
891
  /* The FUNC is easy.  */
892
  func = get_frame_func (this_frame);
893
 
894
  /* Hopefully the prologue analysis either correctly determined the
895
     frame's base (which is the SP from the previous frame), or set
896
     that base to "NULL".  */
897
  base = info->prev_sp;
898
  if (base == 0)
899
    return;
900
 
901
  id = frame_id_build (base, func);
902
  (*this_id) = id;
903
}
904
 
905
static struct value *
906
m68hc11_frame_prev_register (struct frame_info *this_frame,
907
                             void **this_prologue_cache, int regnum)
908
{
909
  struct value *value;
910
  struct m68hc11_unwind_cache *info
911
    = m68hc11_frame_unwind_cache (this_frame, this_prologue_cache);
912
 
913
  value = trad_frame_get_prev_register (this_frame, info->saved_regs, regnum);
914
 
915
  /* Take into account the 68HC12 specific call (PC + page).  */
916
  if (regnum == HARD_PC_REGNUM
917
      && info->return_kind == RETURN_RTC
918
      && USE_PAGE_REGISTER (get_frame_arch (this_frame)))
919
    {
920
      CORE_ADDR pc = value_as_long (value);
921
      if (pc >= 0x08000 && pc < 0x0c000)
922
        {
923
          CORE_ADDR page;
924
 
925
          release_value (value);
926
          value_free (value);
927
 
928
          value = trad_frame_get_prev_register (this_frame, info->saved_regs,
929
                                                HARD_PAGE_REGNUM);
930
          page = value_as_long (value);
931
          release_value (value);
932
          value_free (value);
933
 
934
          pc -= 0x08000;
935
          pc += ((page & 0x0ff) << 14);
936
          pc += 0x1000000;
937
 
938
          return frame_unwind_got_constant (this_frame, regnum, pc);
939
        }
940
    }
941
 
942
  return value;
943
}
944
 
945
static const struct frame_unwind m68hc11_frame_unwind = {
946
  NORMAL_FRAME,
947
  m68hc11_frame_this_id,
948
  m68hc11_frame_prev_register,
949
  NULL,
950
  default_frame_sniffer
951
};
952
 
953
static CORE_ADDR
954
m68hc11_frame_base_address (struct frame_info *this_frame, void **this_cache)
955
{
956
  struct m68hc11_unwind_cache *info
957
    = m68hc11_frame_unwind_cache (this_frame, this_cache);
958
 
959
  return info->base;
960
}
961
 
962
static CORE_ADDR
963
m68hc11_frame_args_address (struct frame_info *this_frame, void **this_cache)
964
{
965
  CORE_ADDR addr;
966
  struct m68hc11_unwind_cache *info
967
    = m68hc11_frame_unwind_cache (this_frame, this_cache);
968
 
969
  addr = info->base + info->size;
970
  if (info->return_kind == RETURN_RTC)
971
    addr += 1;
972
  else if (info->return_kind == RETURN_RTI)
973
    addr += 7;
974
 
975
  return addr;
976
}
977
 
978
static const struct frame_base m68hc11_frame_base = {
979
  &m68hc11_frame_unwind,
980
  m68hc11_frame_base_address,
981
  m68hc11_frame_base_address,
982
  m68hc11_frame_args_address
983
};
984
 
985
static CORE_ADDR
986
m68hc11_unwind_sp (struct gdbarch *gdbarch, struct frame_info *next_frame)
987
{
988
  ULONGEST sp;
989
  sp = frame_unwind_register_unsigned (next_frame, HARD_SP_REGNUM);
990
  return sp;
991
}
992
 
993
/* Assuming THIS_FRAME is a dummy, return the frame ID of that dummy
994
   frame.  The frame ID's base needs to match the TOS value saved by
995
   save_dummy_frame_tos(), and the PC match the dummy frame's breakpoint.  */
996
 
997
static struct frame_id
998
m68hc11_dummy_id (struct gdbarch *gdbarch, struct frame_info *this_frame)
999
{
1000
  ULONGEST tos;
1001
  CORE_ADDR pc = get_frame_pc (this_frame);
1002
 
1003
  tos = get_frame_register_unsigned (this_frame, SOFT_FP_REGNUM);
1004
  tos += 2;
1005
  return frame_id_build (tos, pc);
1006
}
1007
 
1008
 
1009
/* Get and print the register from the given frame.  */
1010
static void
1011
m68hc11_print_register (struct gdbarch *gdbarch, struct ui_file *file,
1012
                        struct frame_info *frame, int regno)
1013
{
1014
  LONGEST rval;
1015
 
1016
  if (regno == HARD_PC_REGNUM || regno == HARD_SP_REGNUM
1017
      || regno == SOFT_FP_REGNUM || regno == M68HC12_HARD_PC_REGNUM)
1018
    rval = get_frame_register_unsigned (frame, regno);
1019
  else
1020
    rval = get_frame_register_signed (frame, regno);
1021
 
1022
  if (regno == HARD_A_REGNUM || regno == HARD_B_REGNUM
1023
      || regno == HARD_CCR_REGNUM || regno == HARD_PAGE_REGNUM)
1024
    {
1025
      fprintf_filtered (file, "0x%02x   ", (unsigned char) rval);
1026
      if (regno != HARD_CCR_REGNUM)
1027
        print_longest (file, 'd', 1, rval);
1028
    }
1029
  else
1030
    {
1031
      if (regno == HARD_PC_REGNUM && gdbarch_tdep (gdbarch)->use_page_register)
1032
        {
1033
          ULONGEST page;
1034
 
1035
          page = get_frame_register_unsigned (frame, HARD_PAGE_REGNUM);
1036
          fprintf_filtered (file, "0x%02x:%04x ", (unsigned) page,
1037
                            (unsigned) rval);
1038
        }
1039
      else
1040
        {
1041
          fprintf_filtered (file, "0x%04x ", (unsigned) rval);
1042
          if (regno != HARD_PC_REGNUM && regno != HARD_SP_REGNUM
1043
              && regno != SOFT_FP_REGNUM && regno != M68HC12_HARD_PC_REGNUM)
1044
            print_longest (file, 'd', 1, rval);
1045
        }
1046
    }
1047
 
1048
  if (regno == HARD_CCR_REGNUM)
1049
    {
1050
      /* CCR register */
1051
      int C, Z, N, V;
1052
      unsigned char l = rval & 0xff;
1053
 
1054
      fprintf_filtered (file, "%c%c%c%c%c%c%c%c   ",
1055
                        l & M6811_S_BIT ? 'S' : '-',
1056
                        l & M6811_X_BIT ? 'X' : '-',
1057
                        l & M6811_H_BIT ? 'H' : '-',
1058
                        l & M6811_I_BIT ? 'I' : '-',
1059
                        l & M6811_N_BIT ? 'N' : '-',
1060
                        l & M6811_Z_BIT ? 'Z' : '-',
1061
                        l & M6811_V_BIT ? 'V' : '-',
1062
                        l & M6811_C_BIT ? 'C' : '-');
1063
      N = (l & M6811_N_BIT) != 0;
1064
      Z = (l & M6811_Z_BIT) != 0;
1065
      V = (l & M6811_V_BIT) != 0;
1066
      C = (l & M6811_C_BIT) != 0;
1067
 
1068
      /* Print flags following the h8300  */
1069
      if ((C | Z) == 0)
1070
        fprintf_filtered (file, "u> ");
1071
      else if ((C | Z) == 1)
1072
        fprintf_filtered (file, "u<= ");
1073
      else if (C == 0)
1074
        fprintf_filtered (file, "u< ");
1075
 
1076
      if (Z == 0)
1077
        fprintf_filtered (file, "!= ");
1078
      else
1079
        fprintf_filtered (file, "== ");
1080
 
1081
      if ((N ^ V) == 0)
1082
        fprintf_filtered (file, ">= ");
1083
      else
1084
        fprintf_filtered (file, "< ");
1085
 
1086
      if ((Z | (N ^ V)) == 0)
1087
        fprintf_filtered (file, "> ");
1088
      else
1089
        fprintf_filtered (file, "<= ");
1090
    }
1091
}
1092
 
1093
/* Same as 'info reg' but prints the registers in a different way.  */
1094
static void
1095
m68hc11_print_registers_info (struct gdbarch *gdbarch, struct ui_file *file,
1096
                              struct frame_info *frame, int regno, int cpregs)
1097
{
1098
  if (regno >= 0)
1099
    {
1100
      const char *name = gdbarch_register_name (gdbarch, regno);
1101
 
1102
      if (!name || !*name)
1103
        return;
1104
 
1105
      fprintf_filtered (file, "%-10s ", name);
1106
      m68hc11_print_register (gdbarch, file, frame, regno);
1107
      fprintf_filtered (file, "\n");
1108
    }
1109
  else
1110
    {
1111
      int i, nr;
1112
 
1113
      fprintf_filtered (file, "PC=");
1114
      m68hc11_print_register (gdbarch, file, frame, HARD_PC_REGNUM);
1115
 
1116
      fprintf_filtered (file, " SP=");
1117
      m68hc11_print_register (gdbarch, file, frame, HARD_SP_REGNUM);
1118
 
1119
      fprintf_filtered (file, " FP=");
1120
      m68hc11_print_register (gdbarch, file, frame, SOFT_FP_REGNUM);
1121
 
1122
      fprintf_filtered (file, "\nCCR=");
1123
      m68hc11_print_register (gdbarch, file, frame, HARD_CCR_REGNUM);
1124
 
1125
      fprintf_filtered (file, "\nD=");
1126
      m68hc11_print_register (gdbarch, file, frame, HARD_D_REGNUM);
1127
 
1128
      fprintf_filtered (file, " X=");
1129
      m68hc11_print_register (gdbarch, file, frame, HARD_X_REGNUM);
1130
 
1131
      fprintf_filtered (file, " Y=");
1132
      m68hc11_print_register (gdbarch, file, frame, HARD_Y_REGNUM);
1133
 
1134
      if (gdbarch_tdep (gdbarch)->use_page_register)
1135
        {
1136
          fprintf_filtered (file, "\nPage=");
1137
          m68hc11_print_register (gdbarch, file, frame, HARD_PAGE_REGNUM);
1138
        }
1139
      fprintf_filtered (file, "\n");
1140
 
1141
      nr = 0;
1142
      for (i = SOFT_D1_REGNUM; i < M68HC11_ALL_REGS; i++)
1143
        {
1144
          /* Skip registers which are not defined in the symbol table.  */
1145
          if (soft_regs[i].name == 0)
1146
            continue;
1147
 
1148
          fprintf_filtered (file, "D%d=", i - SOFT_D1_REGNUM + 1);
1149
          m68hc11_print_register (gdbarch, file, frame, i);
1150
          nr++;
1151
          if ((nr % 8) == 7)
1152
            fprintf_filtered (file, "\n");
1153
          else
1154
            fprintf_filtered (file, " ");
1155
        }
1156
      if (nr && (nr % 8) != 7)
1157
        fprintf_filtered (file, "\n");
1158
    }
1159
}
1160
 
1161
static CORE_ADDR
1162
m68hc11_push_dummy_call (struct gdbarch *gdbarch, struct value *function,
1163
                         struct regcache *regcache, CORE_ADDR bp_addr,
1164
                         int nargs, struct value **args, CORE_ADDR sp,
1165
                         int struct_return, CORE_ADDR struct_addr)
1166
{
1167
  enum bfd_endian byte_order = gdbarch_byte_order (gdbarch);
1168
  int argnum;
1169
  int first_stack_argnum;
1170
  struct type *type;
1171
  char *val;
1172
  int len;
1173
  char buf[2];
1174
 
1175
  first_stack_argnum = 0;
1176
  if (struct_return)
1177
    {
1178
      regcache_cooked_write_unsigned (regcache, HARD_D_REGNUM, struct_addr);
1179
    }
1180
  else if (nargs > 0)
1181
    {
1182
      type = value_type (args[0]);
1183
      len = TYPE_LENGTH (type);
1184
 
1185
      /* First argument is passed in D and X registers.  */
1186
      if (len <= 4)
1187
        {
1188
          ULONGEST v;
1189
 
1190
          v = extract_unsigned_integer (value_contents (args[0]),
1191
                                        len, byte_order);
1192
          first_stack_argnum = 1;
1193
 
1194
          regcache_cooked_write_unsigned (regcache, HARD_D_REGNUM, v);
1195
          if (len > 2)
1196
            {
1197
              v >>= 16;
1198
              regcache_cooked_write_unsigned (regcache, HARD_X_REGNUM, v);
1199
            }
1200
        }
1201
    }
1202
 
1203
  for (argnum = nargs - 1; argnum >= first_stack_argnum; argnum--)
1204
    {
1205
      type = value_type (args[argnum]);
1206
      len = TYPE_LENGTH (type);
1207
 
1208
      if (len & 1)
1209
        {
1210
          static char zero = 0;
1211
 
1212
          sp--;
1213
          write_memory (sp, &zero, 1);
1214
        }
1215
      val = (char*) value_contents (args[argnum]);
1216
      sp -= len;
1217
      write_memory (sp, val, len);
1218
    }
1219
 
1220
  /* Store return address.  */
1221
  sp -= 2;
1222
  store_unsigned_integer (buf, 2, byte_order, bp_addr);
1223
  write_memory (sp, buf, 2);
1224
 
1225
  /* Finally, update the stack pointer...  */
1226
  sp -= STACK_CORRECTION (gdbarch);
1227
  regcache_cooked_write_unsigned (regcache, HARD_SP_REGNUM, sp);
1228
 
1229
  /* ...and fake a frame pointer.  */
1230
  regcache_cooked_write_unsigned (regcache, SOFT_FP_REGNUM, sp);
1231
 
1232
  /* DWARF2/GCC uses the stack address *before* the function call as a
1233
     frame's CFA.  */
1234
  return sp + 2;
1235
}
1236
 
1237
 
1238
/* Return the GDB type object for the "standard" data type
1239
   of data in register N.  */
1240
 
1241
static struct type *
1242
m68hc11_register_type (struct gdbarch *gdbarch, int reg_nr)
1243
{
1244
  switch (reg_nr)
1245
    {
1246
    case HARD_PAGE_REGNUM:
1247
    case HARD_A_REGNUM:
1248
    case HARD_B_REGNUM:
1249
    case HARD_CCR_REGNUM:
1250
      return builtin_type (gdbarch)->builtin_uint8;
1251
 
1252
    case M68HC12_HARD_PC_REGNUM:
1253
      return builtin_type (gdbarch)->builtin_uint32;
1254
 
1255
    default:
1256
      return builtin_type (gdbarch)->builtin_uint16;
1257
    }
1258
}
1259
 
1260
static void
1261
m68hc11_store_return_value (struct type *type, struct regcache *regcache,
1262
                            const void *valbuf)
1263
{
1264
  int len;
1265
 
1266
  len = TYPE_LENGTH (type);
1267
 
1268
  /* First argument is passed in D and X registers.  */
1269
  if (len <= 2)
1270
    regcache_raw_write_part (regcache, HARD_D_REGNUM, 2 - len, len, valbuf);
1271
  else if (len <= 4)
1272
    {
1273
      regcache_raw_write_part (regcache, HARD_X_REGNUM, 4 - len,
1274
                               len - 2, valbuf);
1275
      regcache_raw_write (regcache, HARD_D_REGNUM, (char*) valbuf + (len - 2));
1276
    }
1277
  else
1278
    error (_("return of value > 4 is not supported."));
1279
}
1280
 
1281
 
1282
/* Given a return value in `regcache' with a type `type',
1283
   extract and copy its value into `valbuf'.  */
1284
 
1285
static void
1286
m68hc11_extract_return_value (struct type *type, struct regcache *regcache,
1287
                              void *valbuf)
1288
{
1289
  int len = TYPE_LENGTH (type);
1290
  char buf[M68HC11_REG_SIZE];
1291
 
1292
  regcache_raw_read (regcache, HARD_D_REGNUM, buf);
1293
  switch (len)
1294
    {
1295
    case 1:
1296
      memcpy (valbuf, buf + 1, 1);
1297
      break;
1298
 
1299
    case 2:
1300
      memcpy (valbuf, buf, 2);
1301
      break;
1302
 
1303
    case 3:
1304
      memcpy ((char*) valbuf + 1, buf, 2);
1305
      regcache_raw_read (regcache, HARD_X_REGNUM, buf);
1306
      memcpy (valbuf, buf + 1, 1);
1307
      break;
1308
 
1309
    case 4:
1310
      memcpy ((char*) valbuf + 2, buf, 2);
1311
      regcache_raw_read (regcache, HARD_X_REGNUM, buf);
1312
      memcpy (valbuf, buf, 2);
1313
      break;
1314
 
1315
    default:
1316
      error (_("bad size for return value"));
1317
    }
1318
}
1319
 
1320
static enum return_value_convention
1321
m68hc11_return_value (struct gdbarch *gdbarch, struct type *func_type,
1322
                      struct type *valtype, struct regcache *regcache,
1323
                      gdb_byte *readbuf, const gdb_byte *writebuf)
1324
{
1325
  if (TYPE_CODE (valtype) == TYPE_CODE_STRUCT
1326
      || TYPE_CODE (valtype) == TYPE_CODE_UNION
1327
      || TYPE_CODE (valtype) == TYPE_CODE_ARRAY
1328
      || TYPE_LENGTH (valtype) > 4)
1329
    return RETURN_VALUE_STRUCT_CONVENTION;
1330
  else
1331
    {
1332
      if (readbuf != NULL)
1333
        m68hc11_extract_return_value (valtype, regcache, readbuf);
1334
      if (writebuf != NULL)
1335
        m68hc11_store_return_value (valtype, regcache, writebuf);
1336
      return RETURN_VALUE_REGISTER_CONVENTION;
1337
    }
1338
}
1339
 
1340
/* Test whether the ELF symbol corresponds to a function using rtc or
1341
   rti to return.  */
1342
 
1343
static void
1344
m68hc11_elf_make_msymbol_special (asymbol *sym, struct minimal_symbol *msym)
1345
{
1346
  unsigned char flags;
1347
 
1348
  flags = ((elf_symbol_type *)sym)->internal_elf_sym.st_other;
1349
  if (flags & STO_M68HC12_FAR)
1350
    MSYMBOL_SET_RTC (msym);
1351
  if (flags & STO_M68HC12_INTERRUPT)
1352
    MSYMBOL_SET_RTI (msym);
1353
}
1354
 
1355
static int
1356
gdb_print_insn_m68hc11 (bfd_vma memaddr, disassemble_info *info)
1357
{
1358
  if (info->arch == bfd_arch_m68hc11)
1359
    return print_insn_m68hc11 (memaddr, info);
1360
  else
1361
    return print_insn_m68hc12 (memaddr, info);
1362
}
1363
 
1364
 
1365
 
1366
/* 68HC11/68HC12 register groups.
1367
   Identify real hard registers and soft registers used by gcc.  */
1368
 
1369
static struct reggroup *m68hc11_soft_reggroup;
1370
static struct reggroup *m68hc11_hard_reggroup;
1371
 
1372
static void
1373
m68hc11_init_reggroups (void)
1374
{
1375
  m68hc11_hard_reggroup = reggroup_new ("hard", USER_REGGROUP);
1376
  m68hc11_soft_reggroup = reggroup_new ("soft", USER_REGGROUP);
1377
}
1378
 
1379
static void
1380
m68hc11_add_reggroups (struct gdbarch *gdbarch)
1381
{
1382
  reggroup_add (gdbarch, m68hc11_hard_reggroup);
1383
  reggroup_add (gdbarch, m68hc11_soft_reggroup);
1384
  reggroup_add (gdbarch, general_reggroup);
1385
  reggroup_add (gdbarch, float_reggroup);
1386
  reggroup_add (gdbarch, all_reggroup);
1387
  reggroup_add (gdbarch, save_reggroup);
1388
  reggroup_add (gdbarch, restore_reggroup);
1389
  reggroup_add (gdbarch, vector_reggroup);
1390
  reggroup_add (gdbarch, system_reggroup);
1391
}
1392
 
1393
static int
1394
m68hc11_register_reggroup_p (struct gdbarch *gdbarch, int regnum,
1395
                             struct reggroup *group)
1396
{
1397
  /* We must save the real hard register as well as gcc
1398
     soft registers including the frame pointer.  */
1399
  if (group == save_reggroup || group == restore_reggroup)
1400
    {
1401
      return (regnum <= gdbarch_num_regs (gdbarch)
1402
              || ((regnum == SOFT_FP_REGNUM
1403
                   || regnum == SOFT_TMP_REGNUM
1404
                   || regnum == SOFT_ZS_REGNUM
1405
                   || regnum == SOFT_XY_REGNUM)
1406
                  && m68hc11_register_name (gdbarch, regnum)));
1407
    }
1408
 
1409
  /* Group to identify gcc soft registers (d1..dN).  */
1410
  if (group == m68hc11_soft_reggroup)
1411
    {
1412
      return regnum >= SOFT_D1_REGNUM
1413
             && m68hc11_register_name (gdbarch, regnum);
1414
    }
1415
 
1416
  if (group == m68hc11_hard_reggroup)
1417
    {
1418
      return regnum == HARD_PC_REGNUM || regnum == HARD_SP_REGNUM
1419
        || regnum == HARD_X_REGNUM || regnum == HARD_D_REGNUM
1420
        || regnum == HARD_Y_REGNUM || regnum == HARD_CCR_REGNUM;
1421
    }
1422
  return default_register_reggroup_p (gdbarch, regnum, group);
1423
}
1424
 
1425
static struct gdbarch *
1426
m68hc11_gdbarch_init (struct gdbarch_info info,
1427
                      struct gdbarch_list *arches)
1428
{
1429
  struct gdbarch *gdbarch;
1430
  struct gdbarch_tdep *tdep;
1431
  int elf_flags;
1432
 
1433
  soft_reg_initialized = 0;
1434
 
1435
  /* Extract the elf_flags if available.  */
1436
  if (info.abfd != NULL
1437
      && bfd_get_flavour (info.abfd) == bfd_target_elf_flavour)
1438
    elf_flags = elf_elfheader (info.abfd)->e_flags;
1439
  else
1440
    elf_flags = 0;
1441
 
1442
  /* try to find a pre-existing architecture */
1443
  for (arches = gdbarch_list_lookup_by_info (arches, &info);
1444
       arches != NULL;
1445
       arches = gdbarch_list_lookup_by_info (arches->next, &info))
1446
    {
1447
      if (gdbarch_tdep (arches->gdbarch)->elf_flags != elf_flags)
1448
        continue;
1449
 
1450
      return arches->gdbarch;
1451
    }
1452
 
1453
  /* Need a new architecture. Fill in a target specific vector.  */
1454
  tdep = (struct gdbarch_tdep *) xmalloc (sizeof (struct gdbarch_tdep));
1455
  gdbarch = gdbarch_alloc (&info, tdep);
1456
  tdep->elf_flags = elf_flags;
1457
 
1458
  switch (info.bfd_arch_info->arch)
1459
    {
1460
    case bfd_arch_m68hc11:
1461
      tdep->stack_correction = 1;
1462
      tdep->use_page_register = 0;
1463
      tdep->prologue = m6811_prologue;
1464
      set_gdbarch_addr_bit (gdbarch, 16);
1465
      set_gdbarch_num_pseudo_regs (gdbarch, M68HC11_NUM_PSEUDO_REGS);
1466
      set_gdbarch_pc_regnum (gdbarch, HARD_PC_REGNUM);
1467
      set_gdbarch_num_regs (gdbarch, M68HC11_NUM_REGS);
1468
      break;
1469
 
1470
    case bfd_arch_m68hc12:
1471
      tdep->stack_correction = 0;
1472
      tdep->use_page_register = elf_flags & E_M68HC12_BANKS;
1473
      tdep->prologue = m6812_prologue;
1474
      set_gdbarch_addr_bit (gdbarch, elf_flags & E_M68HC12_BANKS ? 32 : 16);
1475
      set_gdbarch_num_pseudo_regs (gdbarch,
1476
                                   elf_flags & E_M68HC12_BANKS
1477
                                   ? M68HC12_NUM_PSEUDO_REGS
1478
                                   : M68HC11_NUM_PSEUDO_REGS);
1479
      set_gdbarch_pc_regnum (gdbarch, elf_flags & E_M68HC12_BANKS
1480
                             ? M68HC12_HARD_PC_REGNUM : HARD_PC_REGNUM);
1481
      set_gdbarch_num_regs (gdbarch, elf_flags & E_M68HC12_BANKS
1482
                            ? M68HC12_NUM_REGS : M68HC11_NUM_REGS);
1483
      break;
1484
 
1485
    default:
1486
      break;
1487
    }
1488
 
1489
  /* Initially set everything according to the ABI.
1490
     Use 16-bit integers since it will be the case for most
1491
     programs.  The size of these types should normally be set
1492
     according to the dwarf2 debug information.  */
1493
  set_gdbarch_short_bit (gdbarch, 16);
1494
  set_gdbarch_int_bit (gdbarch, elf_flags & E_M68HC11_I32 ? 32 : 16);
1495
  set_gdbarch_float_bit (gdbarch, 32);
1496
  set_gdbarch_double_bit (gdbarch, elf_flags & E_M68HC11_F64 ? 64 : 32);
1497
  set_gdbarch_long_double_bit (gdbarch, 64);
1498
  set_gdbarch_long_bit (gdbarch, 32);
1499
  set_gdbarch_ptr_bit (gdbarch, 16);
1500
  set_gdbarch_long_long_bit (gdbarch, 64);
1501
 
1502
  /* Characters are unsigned.  */
1503
  set_gdbarch_char_signed (gdbarch, 0);
1504
 
1505
  set_gdbarch_unwind_pc (gdbarch, m68hc11_unwind_pc);
1506
  set_gdbarch_unwind_sp (gdbarch, m68hc11_unwind_sp);
1507
 
1508
  /* Set register info.  */
1509
  set_gdbarch_fp0_regnum (gdbarch, -1);
1510
 
1511
  set_gdbarch_sp_regnum (gdbarch, HARD_SP_REGNUM);
1512
  set_gdbarch_register_name (gdbarch, m68hc11_register_name);
1513
  set_gdbarch_register_type (gdbarch, m68hc11_register_type);
1514
  set_gdbarch_pseudo_register_read (gdbarch, m68hc11_pseudo_register_read);
1515
  set_gdbarch_pseudo_register_write (gdbarch, m68hc11_pseudo_register_write);
1516
 
1517
  set_gdbarch_push_dummy_call (gdbarch, m68hc11_push_dummy_call);
1518
 
1519
  set_gdbarch_return_value (gdbarch, m68hc11_return_value);
1520
  set_gdbarch_skip_prologue (gdbarch, m68hc11_skip_prologue);
1521
  set_gdbarch_inner_than (gdbarch, core_addr_lessthan);
1522
  set_gdbarch_breakpoint_from_pc (gdbarch, m68hc11_breakpoint_from_pc);
1523
  set_gdbarch_print_insn (gdbarch, gdb_print_insn_m68hc11);
1524
 
1525
  m68hc11_add_reggroups (gdbarch);
1526
  set_gdbarch_register_reggroup_p (gdbarch, m68hc11_register_reggroup_p);
1527
  set_gdbarch_print_registers_info (gdbarch, m68hc11_print_registers_info);
1528
 
1529
  /* Hook in the DWARF CFI frame unwinder.  */
1530
  dwarf2_append_unwinders (gdbarch);
1531
 
1532
  frame_unwind_append_unwinder (gdbarch, &m68hc11_frame_unwind);
1533
  frame_base_set_default (gdbarch, &m68hc11_frame_base);
1534
 
1535
  /* Methods for saving / extracting a dummy frame's ID.  The ID's
1536
     stack address must match the SP value returned by
1537
     PUSH_DUMMY_CALL, and saved by generic_save_dummy_frame_tos.  */
1538
  set_gdbarch_dummy_id (gdbarch, m68hc11_dummy_id);
1539
 
1540
  /* Return the unwound PC value.  */
1541
  set_gdbarch_unwind_pc (gdbarch, m68hc11_unwind_pc);
1542
 
1543
  /* Minsymbol frobbing.  */
1544
  set_gdbarch_elf_make_msymbol_special (gdbarch,
1545
                                        m68hc11_elf_make_msymbol_special);
1546
 
1547
  set_gdbarch_believe_pcc_promotion (gdbarch, 1);
1548
 
1549
  return gdbarch;
1550
}
1551
 
1552
extern initialize_file_ftype _initialize_m68hc11_tdep; /* -Wmissing-prototypes */
1553
 
1554
void
1555
_initialize_m68hc11_tdep (void)
1556
{
1557
  register_gdbarch_init (bfd_arch_m68hc11, m68hc11_gdbarch_init);
1558
  register_gdbarch_init (bfd_arch_m68hc12, m68hc11_gdbarch_init);
1559
  m68hc11_init_reggroups ();
1560
}
1561
 

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.