* mips-tdep.c (fetch_mips_16): Use unmake_compact_addr.
[platform/upstream/binutils.git] / gdb / score-tdep.c
1 /* Target-dependent code for the S+core architecture, for GDB,
2    the GNU Debugger.
3
4    Copyright (C) 2006-2013 Free Software Foundation, Inc.
5
6    Contributed by Qinwei (qinwei@sunnorth.com.cn)
7    Contributed by Ching-Peng Lin (cplin@sunplus.com)
8
9    This file is part of GDB.
10
11    This program is free software; you can redistribute it and/or modify
12    it under the terms of the GNU General Public License as published by
13    the Free Software Foundation; either version 3 of the License, or
14    (at your option) any later version.
15
16    This program is distributed in the hope that it will be useful,
17    but WITHOUT ANY WARRANTY; without even the implied warranty of
18    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
19    GNU General Public License for more details.
20
21    You should have received a copy of the GNU General Public License
22    along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
23
24 #include "defs.h"
25 #include "gdb_assert.h"
26 #include "inferior.h"
27 #include "symtab.h"
28 #include "objfiles.h"
29 #include "gdbcore.h"
30 #include "target.h"
31 #include "arch-utils.h"
32 #include "regcache.h"
33 #include "regset.h"
34 #include "dis-asm.h"
35 #include "frame-unwind.h"
36 #include "frame-base.h"
37 #include "trad-frame.h"
38 #include "dwarf2-frame.h"
39 #include "score-tdep.h"
40
41 #define G_FLD(_i,_ms,_ls) \
42     ((unsigned)((_i) << (31 - (_ms))) >> (31 - (_ms) + (_ls)))
43
44 typedef struct{
45   unsigned long long v;
46   unsigned long long raw;
47   unsigned int len;
48 }inst_t;
49
50 struct score_frame_cache
51 {
52   CORE_ADDR base;
53   CORE_ADDR fp;
54   struct trad_frame_saved_reg *saved_regs;
55 };
56
57 static int target_mach = bfd_mach_score7;
58
59 static struct type *
60 score_register_type (struct gdbarch *gdbarch, int regnum)
61 {
62   gdb_assert (regnum >= 0 
63               && regnum < ((target_mach == bfd_mach_score7)
64                            ? SCORE7_NUM_REGS : SCORE3_NUM_REGS));
65   return builtin_type (gdbarch)->builtin_uint32;
66 }
67
68 static CORE_ADDR
69 score_unwind_sp (struct gdbarch *gdbarch, struct frame_info *next_frame)
70 {
71   return frame_unwind_register_unsigned (next_frame, SCORE_SP_REGNUM);
72 }
73
74 static CORE_ADDR
75 score_unwind_pc (struct gdbarch *gdbarch, struct frame_info *next_frame)
76 {
77   return frame_unwind_register_unsigned (next_frame, SCORE_PC_REGNUM);
78 }
79
80 static const char *
81 score7_register_name (struct gdbarch *gdbarch, int regnum)
82 {
83   const char *score_register_names[] = {
84     "r0",  "r1",  "r2",  "r3",  "r4",  "r5",  "r6",  "r7",
85     "r8",  "r9",  "r10", "r11", "r12", "r13", "r14", "r15",
86     "r16", "r17", "r18", "r19", "r20", "r21", "r22", "r23",
87     "r24", "r25", "r26", "r27", "r28", "r29", "r30", "r31",
88
89     "PSR",     "COND",  "ECR",     "EXCPVEC", "CCR",
90     "EPC",     "EMA",   "TLBLOCK", "TLBPT",   "PEADDR",
91     "TLBRPT",  "PEVN",  "PECTX",   "LIMPFN",  "LDMPFN", 
92     "PREV",    "DREG",  "PC",      "DSAVE",   "COUNTER",
93     "LDCR",    "STCR",  "CEH",     "CEL",
94   };
95
96   gdb_assert (regnum >= 0 && regnum < SCORE7_NUM_REGS);
97   return score_register_names[regnum];
98 }
99
100 static const char *
101 score3_register_name (struct gdbarch *gdbarch, int regnum)
102 {
103   const char *score_register_names[] = {
104     "r0",  "r1",  "r2",  "r3",  "r4",  "r5",  "r6",  "r7",
105     "r8",  "r9",  "r10", "r11", "r12", "r13", "r14", "r15",
106     "r16", "r17", "r18", "r19", "r20", "r21", "r22", "r23",
107     "r24", "r25", "r26", "r27", "r28", "r29", "r30", "r31",
108
109     "PSR",      "COND",   "ECR",   "EXCPVEC",  "CCR",
110     "EPC",      "EMA",    "PREV",  "DREG",     "DSAVE",
111     "COUNTER",  "LDCR",   "STCR",  "CEH",      "CEL",
112     "",         "",       "PC",
113   };
114
115   gdb_assert (regnum >= 0 && regnum < SCORE3_NUM_REGS);
116   return score_register_names[regnum];
117 }
118
119 #if WITH_SIM
120 static int
121 score_register_sim_regno (struct gdbarch *gdbarch, int regnum)
122 {
123   gdb_assert (regnum >= 0 
124               && regnum < ((target_mach == bfd_mach_score7)
125                            ? SCORE7_NUM_REGS : SCORE3_NUM_REGS));
126   return regnum;
127 }
128 #endif
129
130 static int
131 score_print_insn (bfd_vma memaddr, struct disassemble_info *info)
132 {
133   if (info->endian == BFD_ENDIAN_BIG)
134     return print_insn_big_score (memaddr, info);
135   else
136     return print_insn_little_score (memaddr, info);
137 }
138
139 static inst_t *
140 score7_fetch_inst (struct gdbarch *gdbarch, CORE_ADDR addr, gdb_byte *memblock)
141 {
142   enum bfd_endian byte_order = gdbarch_byte_order (gdbarch);
143   static inst_t inst = { 0, 0, 0 };
144   gdb_byte buf[SCORE_INSTLEN] = { 0 };
145   int big;
146   int ret;
147
148   if (target_has_execution && memblock != NULL)
149     {
150       /* Fetch instruction from local MEMBLOCK.  */
151       memcpy (buf, memblock, SCORE_INSTLEN);
152     }
153   else
154     {
155       /* Fetch instruction from target.  */
156       ret = target_read_memory (addr & ~0x3, buf, SCORE_INSTLEN);
157       if (ret)
158         {
159           error (_("Error: target_read_memory in file:%s, line:%d!"),
160                   __FILE__, __LINE__);
161           return 0;
162         }
163     }
164
165   inst.raw = extract_unsigned_integer (buf, SCORE_INSTLEN, byte_order);
166   inst.len = (inst.raw & 0x80008000) ? 4 : 2;
167   inst.v = ((inst.raw >> 16 & 0x7FFF) << 15) | (inst.raw & 0x7FFF); 
168   big = (byte_order == BFD_ENDIAN_BIG);
169   if (inst.len == 2)
170     {
171       if (big ^ ((addr & 0x2) == 2))
172         inst.v = G_FLD (inst.v, 29, 15);
173       else
174         inst.v = G_FLD (inst.v, 14, 0);
175     }
176   return &inst;
177 }
178
179 static inst_t *
180 score3_adjust_pc_and_fetch_inst (CORE_ADDR *pcptr, int *lenptr,
181                                  enum bfd_endian byte_order)
182 {
183   static inst_t inst = { 0, 0, 0 };
184
185   struct breakplace
186   {
187     int break_offset;
188     int inst_len;
189   };
190   /*     raw        table 1 (column 2, 3, 4)
191     *  0  1  0  *   # 2
192     *  0  1  1  0   # 3
193     0  1  1  0  *   # 6
194                     table 2 (column 1, 2, 3)
195     *  0  0  *  *   # 0, 4
196     0  1  0  *  *   # 2
197     1  1  0  *  *   # 6
198    */
199
200   static const struct breakplace bk_table[16] =
201     {
202       /* table 1 */
203       {0, 0},
204       {0, 0},
205       {0, 4},
206       {0, 6},
207       {0, 0},
208       {0, 0},
209       {-2, 6},
210       {0, 0},
211       /* table 2 */
212       {0, 2},
213       {0, 0},
214       {-2, 4},
215       {0, 0},
216       {0, 2},
217       {0, 0},
218       {-4, 6},
219       {0, 0}
220     };
221
222 #define EXTRACT_LEN 2
223   CORE_ADDR adjust_pc = *pcptr & ~0x1;
224   gdb_byte buf[5][EXTRACT_LEN] =
225     {
226       {'\0', '\0'},
227       {'\0', '\0'},
228       {'\0', '\0'},
229       {'\0', '\0'},
230       {'\0', '\0'}
231     };
232   int ret;
233   unsigned int raw;
234   unsigned int cbits = 0;
235   int bk_index;
236   int i, count;
237
238   inst.v = 0;
239   inst.raw = 0;
240   inst.len = 0;
241
242   adjust_pc -= 4;
243   for (i = 0; i < 5; i++)
244     {
245       ret = target_read_memory (adjust_pc + 2 * i, buf[i], EXTRACT_LEN);
246       if (ret != 0)
247         {
248           buf[i][0] = '\0';
249           buf[i][1] = '\0';
250           if (i == 2)
251             error (_("Error: target_read_memory in file:%s, line:%d!"),
252                    __FILE__, __LINE__);
253         }
254
255       raw = extract_unsigned_integer (buf[i], EXTRACT_LEN, byte_order);
256       cbits = (cbits << 1) | (raw >> 15); 
257     }
258   adjust_pc += 4;
259
260   if (cbits & 0x4)
261     {
262       /* table 1 */
263       cbits = (cbits >> 1) & 0x7;
264       bk_index = cbits;
265     }
266   else
267     {
268       /* table 2 */
269       cbits = (cbits >> 2) & 0x7;
270       bk_index = cbits + 8; 
271     }
272
273   gdb_assert (!((bk_table[bk_index].break_offset == 0)
274                 && (bk_table[bk_index].inst_len == 0)));
275
276   inst.len = bk_table[bk_index].inst_len;
277
278   i = (bk_table[bk_index].break_offset + 4) / 2;
279   count = inst.len / 2;
280   for (; count > 0; i++, count--)
281     {
282       inst.raw = (inst.raw << 16)
283                  | extract_unsigned_integer (buf[i], EXTRACT_LEN, byte_order);
284     }
285
286   switch (inst.len)
287     {
288     case 2:
289       inst.v = inst.raw & 0x7FFF;
290       break;
291     case 4:
292       inst.v = ((inst.raw >> 16 & 0x7FFF) << 15) | (inst.raw & 0x7FFF);
293       break;
294     case 6:
295       inst.v = ((inst.raw >> 32 & 0x7FFF) << 30)
296                | ((inst.raw >> 16 & 0x7FFF) << 15) | (inst.raw & 0x7FFF);
297       break;
298     }
299
300   if (pcptr)
301     *pcptr = adjust_pc + bk_table[bk_index].break_offset;
302   if (lenptr)
303     *lenptr = bk_table[bk_index].inst_len;
304
305 #undef EXTRACT_LEN
306
307   return &inst;
308 }
309
310 static const gdb_byte *
311 score7_breakpoint_from_pc (struct gdbarch *gdbarch, CORE_ADDR *pcptr,
312                            int *lenptr)
313 {
314   enum bfd_endian byte_order = gdbarch_byte_order (gdbarch);
315   gdb_byte buf[SCORE_INSTLEN] = { 0 };
316   int ret;
317   unsigned int raw;
318
319   if ((ret = target_read_memory (*pcptr & ~0x3, buf, SCORE_INSTLEN)) != 0)
320     {
321       error (_("Error: target_read_memory in file:%s, line:%d!"),
322              __FILE__, __LINE__);
323     }
324   raw = extract_unsigned_integer (buf, SCORE_INSTLEN, byte_order);
325
326   if (byte_order == BFD_ENDIAN_BIG)
327     {
328       if (!(raw & 0x80008000))
329         {
330           /* 16bits instruction.  */
331           static gdb_byte big_breakpoint16[] = { 0x60, 0x02 };
332           *pcptr &= ~0x1;
333           *lenptr = sizeof (big_breakpoint16);
334           return big_breakpoint16;
335         }
336       else
337         {
338           /* 32bits instruction.  */
339           static gdb_byte big_breakpoint32[] = { 0x80, 0x00, 0x80, 0x06 };
340           *pcptr &= ~0x3;
341           *lenptr = sizeof (big_breakpoint32);
342           return big_breakpoint32;
343         }
344     }
345   else
346     {
347       if (!(raw & 0x80008000))
348         {
349           /* 16bits instruction.  */
350           static gdb_byte little_breakpoint16[] = { 0x02, 0x60 };
351           *pcptr &= ~0x1;
352           *lenptr = sizeof (little_breakpoint16);
353           return little_breakpoint16;
354         }
355       else
356         {
357           /* 32bits instruction.  */
358           static gdb_byte little_breakpoint32[] = { 0x06, 0x80, 0x00, 0x80 };
359           *pcptr &= ~0x3;
360           *lenptr = sizeof (little_breakpoint32);
361           return little_breakpoint32;
362         }
363     }
364 }
365
366 static const gdb_byte *
367 score3_breakpoint_from_pc (struct gdbarch *gdbarch, CORE_ADDR *pcptr,
368                            int *lenptr)
369 {
370   enum bfd_endian byte_order = gdbarch_byte_order (gdbarch);
371   CORE_ADDR adjust_pc = *pcptr; 
372   int len;
373   static gdb_byte score_break_insns[6][6] = {
374     /* The following three instructions are big endian.  */
375     { 0x00, 0x20 },
376     { 0x80, 0x00, 0x00, 0x06 },
377     { 0x80, 0x00, 0x80, 0x00, 0x00, 0x00 },
378     /* The following three instructions are little endian.  */
379     { 0x20, 0x00 },
380     { 0x00, 0x80, 0x06, 0x00 },
381     { 0x00, 0x80, 0x00, 0x80, 0x00, 0x00 }};
382
383   gdb_byte *p = NULL;
384   int index = 0;
385
386   score3_adjust_pc_and_fetch_inst (&adjust_pc, &len, byte_order);
387
388   index = ((byte_order == BFD_ENDIAN_BIG) ? 0 : 3) + (len / 2 - 1);
389   p = score_break_insns[index];
390
391   *pcptr = adjust_pc;
392   *lenptr = len;
393
394   return p;
395 }
396
397 static CORE_ADDR
398 score_adjust_breakpoint_address (struct gdbarch *gdbarch, CORE_ADDR bpaddr)
399 {
400   CORE_ADDR adjust_pc = bpaddr; 
401
402   if (target_mach == bfd_mach_score3)
403     score3_adjust_pc_and_fetch_inst (&adjust_pc, NULL,
404                                      gdbarch_byte_order (gdbarch));
405   else
406     adjust_pc = align_down (adjust_pc, 2);
407   
408   return adjust_pc;
409 }
410
411 static CORE_ADDR
412 score_frame_align (struct gdbarch *gdbarch, CORE_ADDR addr)
413 {
414   return align_down (addr, 16);
415 }
416
417 static void
418 score_xfer_register (struct regcache *regcache, int regnum, int length,
419                      enum bfd_endian endian, gdb_byte *readbuf,
420                      const gdb_byte *writebuf, int buf_offset)
421 {
422   int reg_offset = 0;
423   gdb_assert (regnum >= 0 
424               && regnum < ((target_mach == bfd_mach_score7)
425                            ? SCORE7_NUM_REGS : SCORE3_NUM_REGS));
426
427   switch (endian)
428     {
429     case BFD_ENDIAN_BIG:
430       reg_offset = SCORE_REGSIZE - length;
431       break;
432     case BFD_ENDIAN_LITTLE:
433       reg_offset = 0;
434       break;
435     case BFD_ENDIAN_UNKNOWN:
436       reg_offset = 0;
437       break;
438     default:
439       error (_("Error: score_xfer_register in file:%s, line:%d!"),
440              __FILE__, __LINE__);
441     }
442
443   if (readbuf != NULL)
444     regcache_cooked_read_part (regcache, regnum, reg_offset, length,
445                                readbuf + buf_offset);
446   if (writebuf != NULL)
447     regcache_cooked_write_part (regcache, regnum, reg_offset, length,
448                                 writebuf + buf_offset);
449 }
450
451 static enum return_value_convention
452 score_return_value (struct gdbarch *gdbarch, struct value *function,
453                     struct type *type, struct regcache *regcache,
454                     gdb_byte * readbuf, const gdb_byte * writebuf)
455 {
456   if (TYPE_CODE (type) == TYPE_CODE_STRUCT
457       || TYPE_CODE (type) == TYPE_CODE_UNION
458       || TYPE_CODE (type) == TYPE_CODE_ARRAY)
459     return RETURN_VALUE_STRUCT_CONVENTION;
460   else
461     {
462       int offset;
463       int regnum;
464       for (offset = 0, regnum = SCORE_A0_REGNUM;
465            offset < TYPE_LENGTH (type);
466            offset += SCORE_REGSIZE, regnum++)
467         {
468           int xfer = SCORE_REGSIZE;
469
470           if (offset + xfer > TYPE_LENGTH (type))
471             xfer = TYPE_LENGTH (type) - offset;
472           score_xfer_register (regcache, regnum, xfer,
473                                gdbarch_byte_order(gdbarch),
474                                readbuf, writebuf, offset);
475         }
476       return RETURN_VALUE_REGISTER_CONVENTION;
477     }
478 }
479
480 static struct frame_id
481 score_dummy_id (struct gdbarch *gdbarch, struct frame_info *this_frame)
482 {
483   return frame_id_build (get_frame_register_unsigned (this_frame,
484                                                       SCORE_SP_REGNUM),
485                          get_frame_pc (this_frame));
486 }
487
488 static int
489 score_type_needs_double_align (struct type *type)
490 {
491   enum type_code typecode = TYPE_CODE (type);
492
493   if ((typecode == TYPE_CODE_INT && TYPE_LENGTH (type) == 8)
494       || (typecode == TYPE_CODE_FLT && TYPE_LENGTH (type) == 8))
495     return 1;
496   else if (typecode == TYPE_CODE_STRUCT || typecode == TYPE_CODE_UNION)
497     {
498       int i, n;
499
500       n = TYPE_NFIELDS (type);
501       for (i = 0; i < n; i++)
502         if (score_type_needs_double_align (TYPE_FIELD_TYPE (type, i)))
503           return 1;
504       return 0;
505     }
506   return 0;
507 }
508
509 static CORE_ADDR
510 score_push_dummy_call (struct gdbarch *gdbarch, struct value *function,
511                        struct regcache *regcache, CORE_ADDR bp_addr,
512                        int nargs, struct value **args, CORE_ADDR sp,
513                        int struct_return, CORE_ADDR struct_addr)
514 {
515   enum bfd_endian byte_order = gdbarch_byte_order (gdbarch);
516   int argnum;
517   int argreg;
518   int arglen = 0;
519   CORE_ADDR stack_offset = 0;
520   CORE_ADDR addr = 0;
521
522   /* Step 1, Save RA.  */
523   regcache_cooked_write_unsigned (regcache, SCORE_RA_REGNUM, bp_addr);
524
525   /* Step 2, Make space on the stack for the args.  */
526   struct_addr = align_down (struct_addr, 16);
527   sp = align_down (sp, 16);
528   for (argnum = 0; argnum < nargs; argnum++)
529     arglen += align_up (TYPE_LENGTH (value_type (args[argnum])),
530                         SCORE_REGSIZE);
531   sp -= align_up (arglen, 16);
532
533   argreg = SCORE_BEGIN_ARG_REGNUM;
534
535   /* Step 3, Check if struct return then save the struct address to
536      r4 and increase the stack_offset by 4.  */
537   if (struct_return)
538     {
539       regcache_cooked_write_unsigned (regcache, argreg++, struct_addr);
540       stack_offset += SCORE_REGSIZE;
541     }
542
543   /* Step 4, Load arguments:
544      If arg length is too long (> 4 bytes), then split the arg and
545      save every parts.  */
546   for (argnum = 0; argnum < nargs; argnum++)
547     {
548       struct value *arg = args[argnum];
549       struct type *arg_type = check_typedef (value_type (arg));
550       enum type_code typecode = TYPE_CODE (arg_type);
551       const gdb_byte *val = value_contents (arg);
552       int downward_offset = 0;
553       int odd_sized_struct_p;
554       int arg_last_part_p = 0;
555
556       arglen = TYPE_LENGTH (arg_type);
557       odd_sized_struct_p = (arglen > SCORE_REGSIZE
558                             && arglen % SCORE_REGSIZE != 0);
559
560       /* If a arg should be aligned to 8 bytes (long long or double),
561          the value should be put to even register numbers.  */
562       if (score_type_needs_double_align (arg_type))
563         {
564           if (argreg & 1)
565             argreg++;
566         }
567
568       /* If sizeof a block < SCORE_REGSIZE, then Score GCC will chose
569          the default "downward"/"upward" method:
570
571          Example:
572
573          struct struc
574          {
575            char a; char b; char c;
576          } s = {'a', 'b', 'c'};
577
578          Big endian:    s = {X, 'a', 'b', 'c'}
579          Little endian: s = {'a', 'b', 'c', X}
580
581          Where X is a hole.  */
582
583       if (gdbarch_byte_order(gdbarch) == BFD_ENDIAN_BIG
584           && (typecode == TYPE_CODE_STRUCT
585               || typecode == TYPE_CODE_UNION)
586           && argreg > SCORE_LAST_ARG_REGNUM
587           && arglen < SCORE_REGSIZE)
588         downward_offset += (SCORE_REGSIZE - arglen);
589
590       while (arglen > 0)
591         {
592           int partial_len = arglen < SCORE_REGSIZE ? arglen : SCORE_REGSIZE;
593           ULONGEST regval = extract_unsigned_integer (val, partial_len,
594                                                       byte_order);
595
596           /* The last part of a arg should shift left when
597              gdbarch_byte_order is BFD_ENDIAN_BIG.  */
598           if (byte_order == BFD_ENDIAN_BIG
599               && arg_last_part_p == 1
600               && (typecode == TYPE_CODE_STRUCT
601                   || typecode == TYPE_CODE_UNION))
602             regval <<= ((SCORE_REGSIZE - partial_len) * TARGET_CHAR_BIT);
603
604           /* Always increase the stack_offset and save args to stack.  */
605           addr = sp + stack_offset + downward_offset;
606           write_memory (addr, val, partial_len);
607
608           if (argreg <= SCORE_LAST_ARG_REGNUM)
609             {
610               regcache_cooked_write_unsigned (regcache, argreg++, regval);
611               if (arglen > SCORE_REGSIZE && arglen < SCORE_REGSIZE * 2)
612                 arg_last_part_p = 1;
613             }
614
615           val += partial_len;
616           arglen -= partial_len;
617           stack_offset += align_up (partial_len, SCORE_REGSIZE);
618         }
619     }
620
621   /* Step 5, Save SP.  */
622   regcache_cooked_write_unsigned (regcache, SCORE_SP_REGNUM, sp);
623
624   return sp;
625 }
626
627 static CORE_ADDR
628 score7_skip_prologue (struct gdbarch *gdbarch, CORE_ADDR pc)
629 {
630   CORE_ADDR cpc = pc;
631   int iscan = 32, stack_sub = 0;
632   while (iscan-- > 0)
633     {
634       inst_t *inst = score7_fetch_inst (gdbarch, cpc, NULL);
635       if (!inst)
636         break;
637       if ((inst->len == 4) && !stack_sub
638           && (G_FLD (inst->v, 29, 25) == 0x1
639               && G_FLD (inst->v, 24, 20) == 0x0))
640         {
641           /* addi r0, offset */
642           stack_sub = cpc + SCORE_INSTLEN;
643           pc = cpc + SCORE_INSTLEN;
644         }
645       else if ((inst->len == 4)
646                && (G_FLD (inst->v, 29, 25) == 0x0)
647                && (G_FLD (inst->v, 24, 20) == 0x2)
648                && (G_FLD (inst->v, 19, 15) == 0x0)
649                && (G_FLD (inst->v, 14, 10) == 0xF)
650                && (G_FLD (inst->v, 9, 0) == 0x56))
651         {
652           /* mv r2, r0  */
653           pc = cpc + SCORE_INSTLEN;
654           break;
655         }
656       else if ((inst->len == 2)
657                && (G_FLD (inst->v, 14, 12) == 0x0)
658                && (G_FLD (inst->v, 11, 8) == 0x2)
659                && (G_FLD (inst->v, 7, 4) == 0x0)
660                && (G_FLD (inst->v, 3, 0) == 0x3))
661         {
662           /* mv! r2, r0 */
663           pc = cpc + SCORE16_INSTLEN;
664           break;
665         }
666       else if ((inst->len == 2)
667                && ((G_FLD (inst->v, 14, 12) == 3)    /* j15 form */
668                    || (G_FLD (inst->v, 14, 12) == 4) /* b15 form */
669                    || (G_FLD (inst->v, 14, 12) == 0x0
670                        && G_FLD (inst->v, 3, 0) == 0x4))) /* br! */
671         break;
672       else if ((inst->len == 4)
673                && ((G_FLD (inst->v, 29, 25) == 2)    /* j32 form */
674                    || (G_FLD (inst->v, 29, 25) == 4) /* b32 form */
675                    || (G_FLD (inst->v, 29, 25) == 0x0
676                        && G_FLD (inst->v, 6, 1) == 0x4)))  /* br */
677         break;
678
679       cpc += (inst->len == 2) ? SCORE16_INSTLEN : SCORE_INSTLEN;
680     }
681   return pc;
682 }
683
684 static CORE_ADDR
685 score3_skip_prologue (struct gdbarch *gdbarch, CORE_ADDR pc)
686 {
687   CORE_ADDR cpc = pc;
688   int iscan = 32, stack_sub = 0;
689   while (iscan-- > 0)
690     {
691       inst_t *inst
692         = score3_adjust_pc_and_fetch_inst (&cpc, NULL,
693                                            gdbarch_byte_order (gdbarch));
694
695       if (!inst)
696         break;
697       if (inst->len == 4 && !stack_sub
698           && (G_FLD (inst->v, 29, 25) == 0x1)
699           && (G_FLD (inst->v, 19, 17) == 0x0)
700           && (G_FLD (inst->v, 24, 20) == 0x0))
701         {
702           /* addi r0, offset */
703           stack_sub = cpc + inst->len;
704           pc = cpc + inst->len;
705         }
706       else if (inst->len == 4
707                && (G_FLD (inst->v, 29, 25) == 0x0)
708                && (G_FLD (inst->v, 24, 20) == 0x2)
709                && (G_FLD (inst->v, 19, 15) == 0x0)
710                && (G_FLD (inst->v, 14, 10) == 0xF)
711                && (G_FLD (inst->v, 9, 0) == 0x56))
712         {
713           /* mv r2, r0  */
714           pc = cpc + inst->len;
715           break;
716         }
717       else if ((inst->len == 2)
718                && (G_FLD (inst->v, 14, 10) == 0x10)
719                && (G_FLD (inst->v, 9, 5) == 0x2)
720                && (G_FLD (inst->v, 4, 0) == 0x0))
721         {
722           /* mv! r2, r0 */
723           pc = cpc + inst->len;
724           break;
725         }
726       else if (inst->len == 2
727                && ((G_FLD (inst->v, 14, 12) == 3) /* b15 form */
728                    || (G_FLD (inst->v, 14, 12) == 0x0
729                        && G_FLD (inst->v, 11, 5) == 0x4))) /* br! */
730         break;
731       else if (inst->len == 4
732                && ((G_FLD (inst->v, 29, 25) == 2)    /* j32 form */
733                    || (G_FLD (inst->v, 29, 25) == 4))) /* b32 form */
734         break;
735
736       cpc += inst->len;
737     }
738   return pc;
739 }
740
741 static int
742 score7_in_function_epilogue_p (struct gdbarch *gdbarch, CORE_ADDR cur_pc)
743 {
744   inst_t *inst = score7_fetch_inst (gdbarch, cur_pc, NULL);
745
746   if (inst->v == 0x23)
747     return 1;   /* mv! r0, r2 */
748   else if (G_FLD (inst->v, 14, 12) == 0x2
749            && G_FLD (inst->v, 3, 0) == 0xa)
750     return 1;   /* pop! */
751   else if (G_FLD (inst->v, 14, 12) == 0x0
752            && G_FLD (inst->v, 7, 0) == 0x34)
753     return 1;   /* br! r3 */
754   else if (G_FLD (inst->v, 29, 15) == 0x2
755            && G_FLD (inst->v, 6, 1) == 0x2b)
756     return 1;   /* mv r0, r2 */
757   else if (G_FLD (inst->v, 29, 25) == 0x0
758            && G_FLD (inst->v, 6, 1) == 0x4
759            && G_FLD (inst->v, 19, 15) == 0x3)
760     return 1;   /* br r3 */
761   else
762     return 0;
763 }
764
765 static int
766 score3_in_function_epilogue_p (struct gdbarch *gdbarch, CORE_ADDR cur_pc)
767 {
768   CORE_ADDR pc = cur_pc;
769   inst_t *inst
770     = score3_adjust_pc_and_fetch_inst (&pc, NULL,
771                                        gdbarch_byte_order (gdbarch));
772
773   if (inst->len == 2
774       && (G_FLD (inst->v, 14, 10) == 0x10)
775       && (G_FLD (inst->v, 9, 5) == 0x0)
776       && (G_FLD (inst->v, 4, 0) == 0x2))
777     return 1;   /* mv! r0, r2 */
778   else if (inst->len == 4
779            && (G_FLD (inst->v, 29, 25) == 0x0)
780            && (G_FLD (inst->v, 24, 20) == 0x2)
781            && (G_FLD (inst->v, 19, 15) == 0x0)
782            && (G_FLD (inst->v, 14, 10) == 0xF)
783            && (G_FLD (inst->v, 9, 0) == 0x56))
784     return 1;   /* mv r0, r2 */
785   else if (inst->len == 2
786            && (G_FLD (inst->v, 14, 12) == 0x0)
787            && (G_FLD (inst->v, 11, 5) == 0x2))
788     return 1;   /* pop! */
789   else if (inst->len == 2
790            && (G_FLD (inst->v, 14, 12) == 0x0)
791            && (G_FLD (inst->v, 11, 7) == 0x0)
792            && (G_FLD (inst->v, 6, 5) == 0x2))
793     return 1;   /* rpop! */
794   else if (inst->len == 2
795            && (G_FLD (inst->v, 14, 12) == 0x0)
796            && (G_FLD (inst->v, 11, 5) == 0x4)
797            && (G_FLD (inst->v, 4, 0) == 0x3))
798     return 1;   /* br! r3 */
799   else if (inst->len == 4
800            && (G_FLD (inst->v, 29, 25) == 0x0)
801            && (G_FLD (inst->v, 24, 20) == 0x0)
802            && (G_FLD (inst->v, 19, 15) == 0x3)
803            && (G_FLD (inst->v, 14, 10) == 0xF)
804            && (G_FLD (inst->v, 9, 0) == 0x8))
805     return 1;   /* br r3 */
806   else
807     return 0;
808 }
809
810 static gdb_byte *
811 score7_malloc_and_get_memblock (CORE_ADDR addr, CORE_ADDR size)
812 {
813   int ret;
814   gdb_byte *memblock = NULL;
815
816   if (size < 0)
817     {
818       error (_("Error: malloc size < 0 in file:%s, line:%d!"),
819              __FILE__, __LINE__);
820       return NULL;
821     }
822   else if (size == 0)
823     return NULL;
824
825   memblock = xmalloc (size);
826   memset (memblock, 0, size);
827   ret = target_read_memory (addr & ~0x3, memblock, size);
828   if (ret)
829     {
830       error (_("Error: target_read_memory in file:%s, line:%d!"),
831              __FILE__, __LINE__);
832       return NULL;
833     }
834   return memblock;
835 }
836
837 static void
838 score7_free_memblock (gdb_byte *memblock)
839 {
840   xfree (memblock);
841 }
842
843 static void
844 score7_adjust_memblock_ptr (gdb_byte **memblock, CORE_ADDR prev_pc,
845                            CORE_ADDR cur_pc)
846 {
847   if (prev_pc == -1)
848     {
849       /* First time call this function, do nothing.  */
850     }
851   else if (cur_pc - prev_pc == 2 && (cur_pc & 0x3) == 0)
852     {
853       /* First 16-bit instruction, then 32-bit instruction.  */
854       *memblock += SCORE_INSTLEN;
855     }
856   else if (cur_pc - prev_pc == 4)
857     {
858       /* Is 32-bit instruction, increase MEMBLOCK by 4.  */
859       *memblock += SCORE_INSTLEN;
860     }
861 }
862
863 static void
864 score7_analyze_prologue (CORE_ADDR startaddr, CORE_ADDR pc,
865                         struct frame_info *this_frame,
866                         struct score_frame_cache *this_cache)
867 {
868   struct gdbarch *gdbarch = get_frame_arch (this_frame);
869   CORE_ADDR sp;
870   CORE_ADDR fp;
871   CORE_ADDR cur_pc = startaddr;
872
873   int sp_offset = 0;
874   int ra_offset = 0;
875   int fp_offset = 0;
876   int ra_offset_p = 0;
877   int fp_offset_p = 0;
878   int inst_len = 0;
879
880   gdb_byte *memblock = NULL;
881   gdb_byte *memblock_ptr = NULL;
882   CORE_ADDR prev_pc = -1;
883
884   /* Allocate MEMBLOCK if PC - STARTADDR > 0.  */
885   memblock_ptr = memblock =
886     score7_malloc_and_get_memblock (startaddr, pc - startaddr);
887
888   sp = get_frame_register_unsigned (this_frame, SCORE_SP_REGNUM);
889   fp = get_frame_register_unsigned (this_frame, SCORE_FP_REGNUM);
890
891   for (; cur_pc < pc; prev_pc = cur_pc, cur_pc += inst_len)
892     {
893       inst_t *inst = NULL;
894       if (memblock != NULL)
895         {
896           /* Reading memory block from target succefully and got all
897              the instructions(from STARTADDR to PC) needed.  */
898           score7_adjust_memblock_ptr (&memblock, prev_pc, cur_pc);
899           inst = score7_fetch_inst (gdbarch, cur_pc, memblock);
900         }
901       else
902         {
903           /* Otherwise, we fetch 4 bytes from target, and GDB also
904              work correctly.  */
905           inst = score7_fetch_inst (gdbarch, cur_pc, NULL);
906         }
907
908       /* FIXME: make a full-power prologue analyzer.  */
909       if (inst->len == 2)
910         {
911           inst_len = SCORE16_INSTLEN;
912
913           if (G_FLD (inst->v, 14, 12) == 0x2
914               && G_FLD (inst->v, 3, 0) == 0xe)
915             {
916               /* push! */
917               sp_offset += 4;
918
919               if (G_FLD (inst->v, 11, 7) == 0x6
920                   && ra_offset_p == 0)
921                 {
922                   /* push! r3, [r0] */
923                   ra_offset = sp_offset;
924                   ra_offset_p = 1;
925                 }
926               else if (G_FLD (inst->v, 11, 7) == 0x4
927                        && fp_offset_p == 0)
928                 {
929                   /* push! r2, [r0] */
930                   fp_offset = sp_offset;
931                   fp_offset_p = 1;
932                 }
933             }
934           else if (G_FLD (inst->v, 14, 12) == 0x2
935                    && G_FLD (inst->v, 3, 0) == 0xa)
936             {
937               /* pop! */
938               sp_offset -= 4;
939             }
940           else if (G_FLD (inst->v, 14, 7) == 0xc1
941                    && G_FLD (inst->v, 2, 0) == 0x0)
942             {
943               /* subei! r0, n */
944               sp_offset += (int) pow (2, G_FLD (inst->v, 6, 3));
945             }
946           else if (G_FLD (inst->v, 14, 7) == 0xc0
947                    && G_FLD (inst->v, 2, 0) == 0x0)
948             {
949               /* addei! r0, n */
950               sp_offset -= (int) pow (2, G_FLD (inst->v, 6, 3));
951             }
952         }
953       else
954         {
955           inst_len = SCORE_INSTLEN;
956
957           if (G_FLD(inst->v, 29, 25) == 0x3
958               && G_FLD(inst->v, 2, 0) == 0x4
959               && G_FLD(inst->v, 19, 15) == 0)
960             {
961                 /* sw rD, [r0, offset]+ */
962                 sp_offset += SCORE_INSTLEN;
963
964                 if (G_FLD(inst->v, 24, 20) == 0x3)
965                   {
966                       /* rD = r3 */
967                       if (ra_offset_p == 0)
968                         {
969                             ra_offset = sp_offset;
970                             ra_offset_p = 1;
971                         }
972                   }
973                 else if (G_FLD(inst->v, 24, 20) == 0x2)
974                   {
975                       /* rD = r2 */
976                       if (fp_offset_p == 0)
977                         {
978                             fp_offset = sp_offset;
979                             fp_offset_p = 1;
980                         }
981                   }
982             }
983           else if (G_FLD(inst->v, 29, 25) == 0x14
984                    && G_FLD(inst->v, 19,15) == 0)
985             {
986                 /* sw rD, [r0, offset] */
987                 if (G_FLD(inst->v, 24, 20) == 0x3)
988                   {
989                       /* rD = r3 */
990                       ra_offset = sp_offset - G_FLD(inst->v, 14, 0);
991                       ra_offset_p = 1;
992                   }
993                 else if (G_FLD(inst->v, 24, 20) == 0x2)
994                   {
995                       /* rD = r2 */
996                       fp_offset = sp_offset - G_FLD(inst->v, 14, 0);
997                       fp_offset_p = 1;
998                   }
999             }
1000           else if (G_FLD (inst->v, 29, 15) == 0x1c60
1001                    && G_FLD (inst->v, 2, 0) == 0x0)
1002             {
1003               /* lw r3, [r0]+, 4 */
1004               sp_offset -= SCORE_INSTLEN;
1005               ra_offset_p = 1;
1006             }
1007           else if (G_FLD (inst->v, 29, 15) == 0x1c40
1008                    && G_FLD (inst->v, 2, 0) == 0x0)
1009             {
1010               /* lw r2, [r0]+, 4 */
1011               sp_offset -= SCORE_INSTLEN;
1012               fp_offset_p = 1;
1013             }
1014
1015           else if (G_FLD (inst->v, 29, 17) == 0x100
1016                    && G_FLD (inst->v, 0, 0) == 0x0)
1017             {
1018               /* addi r0, -offset */
1019               sp_offset += 65536 - G_FLD (inst->v, 16, 1);
1020             }
1021           else if (G_FLD (inst->v, 29, 17) == 0x110
1022                    && G_FLD (inst->v, 0, 0) == 0x0)
1023             {
1024               /* addi r2, offset */
1025               if (pc - cur_pc > 4)
1026                 {
1027                   unsigned int save_v = inst->v;
1028                   inst_t *inst2 =
1029                     score7_fetch_inst (gdbarch, cur_pc + SCORE_INSTLEN, NULL);
1030                   if (inst2->v == 0x23)
1031                     {
1032                       /* mv! r0, r2 */
1033                       sp_offset -= G_FLD (save_v, 16, 1);
1034                     }
1035                 }
1036             }
1037         }
1038     }
1039
1040   /* Save RA.  */
1041   if (ra_offset_p == 1)
1042     {
1043       if (this_cache->saved_regs[SCORE_PC_REGNUM].addr == -1)
1044         this_cache->saved_regs[SCORE_PC_REGNUM].addr =
1045           sp + sp_offset - ra_offset;
1046     }
1047   else
1048     {
1049       this_cache->saved_regs[SCORE_PC_REGNUM] =
1050         this_cache->saved_regs[SCORE_RA_REGNUM];
1051     }
1052
1053   /* Save FP.  */
1054   if (fp_offset_p == 1)
1055     {
1056       if (this_cache->saved_regs[SCORE_FP_REGNUM].addr == -1)
1057         this_cache->saved_regs[SCORE_FP_REGNUM].addr =
1058           sp + sp_offset - fp_offset;
1059     }
1060
1061   /* Save SP and FP.  */
1062   this_cache->base = sp + sp_offset;
1063   this_cache->fp = fp;
1064
1065   /* Don't forget to free MEMBLOCK if we allocated it.  */
1066   if (memblock_ptr != NULL)
1067     score7_free_memblock (memblock_ptr);
1068 }
1069
1070 static void
1071 score3_analyze_prologue (CORE_ADDR startaddr, CORE_ADDR pc,
1072                         struct frame_info *this_frame,
1073                         struct score_frame_cache *this_cache)
1074 {
1075   CORE_ADDR sp;
1076   CORE_ADDR fp;
1077   CORE_ADDR cur_pc = startaddr;
1078   enum bfd_endian byte_order
1079     = gdbarch_byte_order (get_frame_arch (this_frame));
1080
1081   int sp_offset = 0;
1082   int ra_offset = 0;
1083   int fp_offset = 0;
1084   int ra_offset_p = 0;
1085   int fp_offset_p = 0;
1086   int inst_len = 0;
1087
1088   CORE_ADDR prev_pc = -1;
1089
1090   sp = get_frame_register_unsigned (this_frame, SCORE_SP_REGNUM);
1091   fp = get_frame_register_unsigned (this_frame, SCORE_FP_REGNUM);
1092
1093   for (; cur_pc < pc; prev_pc = cur_pc, cur_pc += inst_len)
1094     {
1095       inst_t *inst = NULL;
1096
1097       inst = score3_adjust_pc_and_fetch_inst (&cur_pc, &inst_len, byte_order);
1098
1099       /* FIXME: make a full-power prologue analyzer.  */
1100       if (inst->len == 2)
1101         {
1102           if (G_FLD (inst->v, 14, 12) == 0x0
1103               && G_FLD (inst->v, 11, 7) == 0x0
1104               && G_FLD (inst->v, 6, 5) == 0x3)
1105             {
1106               /* push! */
1107               sp_offset += 4;
1108
1109               if (G_FLD (inst->v, 4, 0) == 0x3
1110                   && ra_offset_p == 0)
1111                 {
1112                   /* push! r3, [r0] */
1113                   ra_offset = sp_offset;
1114                   ra_offset_p = 1;
1115                 }
1116               else if (G_FLD (inst->v, 4, 0) == 0x2
1117                        && fp_offset_p == 0)
1118                 {
1119                   /* push! r2, [r0] */
1120                   fp_offset = sp_offset;
1121                   fp_offset_p = 1;
1122                 }
1123             }
1124           else if (G_FLD (inst->v, 14, 12) == 0x6
1125                    && G_FLD (inst->v, 11, 10) == 0x3)
1126             {
1127               /* rpush! */
1128               int start_r = G_FLD (inst->v, 9, 5);
1129               int cnt = G_FLD (inst->v, 4, 0);
1130      
1131               if ((ra_offset_p == 0)
1132                   && (start_r <= SCORE_RA_REGNUM)
1133                   && (SCORE_RA_REGNUM < start_r + cnt))
1134                 {
1135                   /* rpush! contains r3 */
1136                   ra_offset_p = 1;
1137                   ra_offset = sp_offset + 4 * (SCORE_RA_REGNUM - start_r) + 4;
1138                 }
1139
1140               if ((fp_offset_p == 0)
1141                   && (start_r <= SCORE_FP_REGNUM)
1142                   && (SCORE_FP_REGNUM < start_r + cnt))
1143                 {
1144                   /* rpush! contains r2 */
1145                   fp_offset_p = 1;
1146                   fp_offset = sp_offset + 4 * (SCORE_FP_REGNUM - start_r) + 4;
1147                 }
1148
1149               sp_offset += 4 * cnt;
1150             }
1151           else if (G_FLD (inst->v, 14, 12) == 0x0
1152                    && G_FLD (inst->v, 11, 7) == 0x0
1153                    && G_FLD (inst->v, 6, 5) == 0x2)
1154             {
1155               /* pop! */
1156               sp_offset -= 4;
1157             }
1158           else if (G_FLD (inst->v, 14, 12) == 0x6
1159                    && G_FLD (inst->v, 11, 10) == 0x2)
1160             {
1161               /* rpop! */
1162               sp_offset -= 4 * G_FLD (inst->v, 4, 0);
1163             }
1164           else if (G_FLD (inst->v, 14, 12) == 0x5
1165                    && G_FLD (inst->v, 11, 10) == 0x3
1166                    && G_FLD (inst->v, 9, 6) == 0x0)
1167             {
1168               /* addi! r0, -offset */
1169               int imm = G_FLD (inst->v, 5, 0);
1170               if (imm >> 5)
1171                 imm = -(0x3F - imm + 1);
1172               sp_offset -= imm;
1173             }
1174           else if (G_FLD (inst->v, 14, 12) == 0x5
1175                    && G_FLD (inst->v, 11, 10) == 0x3
1176                    && G_FLD (inst->v, 9, 6) == 0x2)
1177             {
1178               /* addi! r2, offset */
1179               if (pc - cur_pc >= 2)
1180                 {
1181                   unsigned int save_v = inst->v;
1182                   inst_t *inst2;
1183                   
1184                   cur_pc += inst->len;
1185                   inst2 = score3_adjust_pc_and_fetch_inst (&cur_pc, NULL,
1186                                                            byte_order);
1187
1188                   if (inst2->len == 2
1189                       && G_FLD (inst2->v, 14, 10) == 0x10
1190                       && G_FLD (inst2->v, 9, 5) == 0x0
1191                       && G_FLD (inst2->v, 4, 0) == 0x2)
1192                     {
1193                       /* mv! r0, r2 */
1194                       int imm = G_FLD (inst->v, 5, 0);
1195                       if (imm >> 5)
1196                         imm = -(0x3F - imm + 1);
1197                       sp_offset -= imm;
1198                     }
1199                 }
1200             }
1201         }
1202       else if (inst->len == 4)
1203         {
1204           if (G_FLD (inst->v, 29, 25) == 0x3
1205               && G_FLD (inst->v, 2, 0) == 0x4
1206               && G_FLD (inst->v, 24, 20) == 0x3
1207               && G_FLD (inst->v, 19, 15) == 0x0)
1208             {
1209               /* sw r3, [r0, offset]+ */
1210               sp_offset += inst->len;
1211               if (ra_offset_p == 0)
1212                 {
1213                   ra_offset = sp_offset;
1214                   ra_offset_p = 1;
1215                 }
1216             }
1217           else if (G_FLD (inst->v, 29, 25) == 0x3
1218                    && G_FLD (inst->v, 2, 0) == 0x4
1219                    && G_FLD (inst->v, 24, 20) == 0x2
1220                    && G_FLD (inst->v, 19, 15) == 0x0)
1221             {
1222               /* sw r2, [r0, offset]+ */
1223               sp_offset += inst->len;
1224               if (fp_offset_p == 0)
1225                 {
1226                   fp_offset = sp_offset;
1227                   fp_offset_p = 1;
1228                 }
1229             }
1230           else if (G_FLD (inst->v, 29, 25) == 0x7
1231                    && G_FLD (inst->v, 2, 0) == 0x0
1232                    && G_FLD (inst->v, 24, 20) == 0x3
1233                    && G_FLD (inst->v, 19, 15) == 0x0)
1234             {
1235               /* lw r3, [r0]+, 4 */
1236               sp_offset -= inst->len;
1237               ra_offset_p = 1;
1238             }
1239           else if (G_FLD (inst->v, 29, 25) == 0x7
1240                    && G_FLD (inst->v, 2, 0) == 0x0
1241                    && G_FLD (inst->v, 24, 20) == 0x2
1242                    && G_FLD (inst->v, 19, 15) == 0x0)
1243             {
1244               /* lw r2, [r0]+, 4 */
1245               sp_offset -= inst->len;
1246               fp_offset_p = 1;
1247             }
1248           else if (G_FLD (inst->v, 29, 25) == 0x1
1249                    && G_FLD (inst->v, 19, 17) == 0x0
1250                    && G_FLD (inst->v, 24, 20) == 0x0
1251                    && G_FLD (inst->v, 0, 0) == 0x0)
1252             {
1253               /* addi r0, -offset */
1254               int imm = G_FLD (inst->v, 16, 1);
1255               if (imm >> 15)
1256                 imm = -(0xFFFF - imm + 1);
1257               sp_offset -= imm;
1258             }
1259           else if (G_FLD (inst->v, 29, 25) == 0x1
1260                    && G_FLD (inst->v, 19, 17) == 0x0
1261                    && G_FLD (inst->v, 24, 20) == 0x2
1262                    && G_FLD (inst->v, 0, 0) == 0x0)
1263             {
1264               /* addi r2, offset */
1265               if (pc - cur_pc >= 2)
1266                 {
1267                   unsigned int save_v = inst->v;
1268                   inst_t *inst2;
1269                   
1270                   cur_pc += inst->len;
1271                   inst2 = score3_adjust_pc_and_fetch_inst (&cur_pc, NULL,
1272                                                            byte_order);
1273
1274                   if (inst2->len == 2
1275                       && G_FLD (inst2->v, 14, 10) == 0x10
1276                       && G_FLD (inst2->v, 9, 5) == 0x0
1277                       && G_FLD (inst2->v, 4, 0) == 0x2)
1278                     {
1279                       /* mv! r0, r2 */
1280                       int imm = G_FLD (inst->v, 16, 1);
1281                       if (imm >> 15)
1282                         imm = -(0xFFFF - imm + 1);
1283                       sp_offset -= imm;
1284                     }
1285                 }
1286             }
1287         }
1288     }
1289
1290   /* Save RA.  */
1291   if (ra_offset_p == 1)
1292     {
1293       if (this_cache->saved_regs[SCORE_PC_REGNUM].addr == -1)
1294         this_cache->saved_regs[SCORE_PC_REGNUM].addr =
1295           sp + sp_offset - ra_offset;
1296     }
1297   else
1298     {
1299       this_cache->saved_regs[SCORE_PC_REGNUM] =
1300         this_cache->saved_regs[SCORE_RA_REGNUM];
1301     }
1302
1303   /* Save FP.  */
1304   if (fp_offset_p == 1)
1305     {
1306       if (this_cache->saved_regs[SCORE_FP_REGNUM].addr == -1)
1307         this_cache->saved_regs[SCORE_FP_REGNUM].addr =
1308           sp + sp_offset - fp_offset;
1309     }
1310
1311   /* Save SP and FP.  */
1312   this_cache->base = sp + sp_offset;
1313   this_cache->fp = fp;
1314 }
1315
1316 static struct score_frame_cache *
1317 score_make_prologue_cache (struct frame_info *this_frame, void **this_cache)
1318 {
1319   struct score_frame_cache *cache;
1320
1321   if ((*this_cache) != NULL)
1322     return (*this_cache);
1323
1324   cache = FRAME_OBSTACK_ZALLOC (struct score_frame_cache);
1325   (*this_cache) = cache;
1326   cache->saved_regs = trad_frame_alloc_saved_regs (this_frame);
1327
1328   /* Analyze the prologue.  */
1329   {
1330     const CORE_ADDR pc = get_frame_pc (this_frame);
1331     CORE_ADDR start_addr;
1332
1333     find_pc_partial_function (pc, NULL, &start_addr, NULL);
1334     if (start_addr == 0)
1335       return cache;
1336
1337     if (target_mach == bfd_mach_score3)
1338       score3_analyze_prologue (start_addr, pc, this_frame, *this_cache);
1339     else
1340       score7_analyze_prologue (start_addr, pc, this_frame, *this_cache);
1341   }
1342
1343   /* Save SP.  */
1344   trad_frame_set_value (cache->saved_regs, SCORE_SP_REGNUM, cache->base);
1345
1346   return (*this_cache);
1347 }
1348
1349 static void
1350 score_prologue_this_id (struct frame_info *this_frame, void **this_cache,
1351                         struct frame_id *this_id)
1352 {
1353   struct score_frame_cache *info = score_make_prologue_cache (this_frame,
1354                                                               this_cache);
1355   (*this_id) = frame_id_build (info->base, get_frame_func (this_frame));
1356 }
1357
1358 static struct value *
1359 score_prologue_prev_register (struct frame_info *this_frame,
1360                               void **this_cache, int regnum)
1361 {
1362   struct score_frame_cache *info = score_make_prologue_cache (this_frame,
1363                                                               this_cache);
1364   return trad_frame_get_prev_register (this_frame, info->saved_regs, regnum);
1365 }
1366
1367 static const struct frame_unwind score_prologue_unwind =
1368 {
1369   NORMAL_FRAME,
1370   default_frame_unwind_stop_reason,
1371   score_prologue_this_id,
1372   score_prologue_prev_register,
1373   NULL,
1374   default_frame_sniffer,
1375   NULL
1376 };
1377
1378 static CORE_ADDR
1379 score_prologue_frame_base_address (struct frame_info *this_frame,
1380                                    void **this_cache)
1381 {
1382   struct score_frame_cache *info =
1383     score_make_prologue_cache (this_frame, this_cache);
1384   return info->fp;
1385 }
1386
1387 static const struct frame_base score_prologue_frame_base =
1388 {
1389   &score_prologue_unwind,
1390   score_prologue_frame_base_address,
1391   score_prologue_frame_base_address,
1392   score_prologue_frame_base_address,
1393 };
1394
1395 static const struct frame_base *
1396 score_prologue_frame_base_sniffer (struct frame_info *this_frame)
1397 {
1398   return &score_prologue_frame_base;
1399 }
1400
1401 /* Core file support (dirty hack)
1402   
1403    The core file MUST be generated by GNU/Linux on S+core.  */
1404
1405 static void
1406 score7_linux_supply_gregset(const struct regset *regset,
1407                 struct regcache *regcache,
1408                 int regnum, const void *gregs_buf, size_t len)
1409 {
1410   int regno;
1411   elf_gregset_t *gregs;
1412
1413   gdb_assert (regset != NULL);
1414   gdb_assert ((regcache != NULL) && (gregs_buf != NULL));
1415
1416   gregs = (elf_gregset_t *) gregs_buf;
1417
1418   for (regno = 0; regno < 32; regno++)
1419     if (regnum == -1 || regnum == regno)
1420       regcache_raw_supply (regcache, regno, gregs->regs + regno);
1421
1422   {
1423     struct sreg {
1424       int regnum;
1425       void *buf;
1426     } sregs [] = {
1427       { 55, &(gregs->cel) },  /* CEL */
1428       { 54, &(gregs->ceh) },  /* CEH */
1429       { 53, &(gregs->sr0) },  /* sr0, i.e. cnt or COUNTER */
1430       { 52, &(gregs->sr1) },  /* sr1, i.e. lcr or LDCR */
1431       { 51, &(gregs->sr1) },  /* sr2, i.e. scr or STCR */
1432
1433       /* Exception occured at this address, exactly the PC we want */
1434       { 49, &(gregs->cp0_epc) }, /* PC */
1435
1436       { 38, &(gregs->cp0_ema) }, /* EMA */
1437       { 37, &(gregs->cp0_epc) }, /* EPC */
1438       { 34, &(gregs->cp0_ecr) }, /* ECR */
1439       { 33, &(gregs->cp0_condition) }, /* COND */
1440       { 32, &(gregs->cp0_psr) }, /* PSR */
1441     };
1442
1443     for (regno = 0; regno < sizeof(sregs)/sizeof(sregs[0]); regno++)
1444       if (regnum == -1 || regnum == sregs[regno].regnum)
1445         regcache_raw_supply (regcache,
1446                              sregs[regno].regnum, sregs[regno].buf);
1447   }
1448 }
1449
1450 /* Return the appropriate register set from the core section identified
1451    by SECT_NAME and SECT_SIZE.  */
1452
1453 static const struct regset *
1454 score7_linux_regset_from_core_section(struct gdbarch *gdbarch,
1455                     const char *sect_name, size_t sect_size)
1456 {
1457   struct gdbarch_tdep *tdep;
1458
1459   gdb_assert (gdbarch != NULL);
1460   gdb_assert (sect_name != NULL);
1461
1462   tdep = gdbarch_tdep (gdbarch);
1463
1464   if (strcmp(sect_name, ".reg") == 0 && sect_size == sizeof(elf_gregset_t))
1465     {
1466       if (tdep->gregset == NULL)
1467         tdep->gregset = regset_alloc (gdbarch,
1468                                       score7_linux_supply_gregset, NULL);
1469       return tdep->gregset;
1470     }
1471
1472   return NULL;
1473 }
1474
1475 static struct gdbarch *
1476 score_gdbarch_init (struct gdbarch_info info, struct gdbarch_list *arches)
1477 {
1478   struct gdbarch *gdbarch;
1479   struct gdbarch_tdep *tdep;
1480   target_mach = info.bfd_arch_info->mach;
1481
1482   arches = gdbarch_list_lookup_by_info (arches, &info);
1483   if (arches != NULL)
1484     {
1485       return (arches->gdbarch);
1486     }
1487   tdep = xcalloc(1, sizeof(struct gdbarch_tdep));
1488   gdbarch = gdbarch_alloc (&info, tdep);
1489
1490   set_gdbarch_short_bit (gdbarch, 16);
1491   set_gdbarch_int_bit (gdbarch, 32);
1492   set_gdbarch_float_bit (gdbarch, 32);
1493   set_gdbarch_double_bit (gdbarch, 64);
1494   set_gdbarch_long_double_bit (gdbarch, 64);
1495 #if WITH_SIM
1496   set_gdbarch_register_sim_regno (gdbarch, score_register_sim_regno);
1497 #endif
1498   set_gdbarch_pc_regnum (gdbarch, SCORE_PC_REGNUM);
1499   set_gdbarch_sp_regnum (gdbarch, SCORE_SP_REGNUM);
1500   set_gdbarch_adjust_breakpoint_address (gdbarch,
1501                                          score_adjust_breakpoint_address);
1502   set_gdbarch_register_type (gdbarch, score_register_type);
1503   set_gdbarch_frame_align (gdbarch, score_frame_align);
1504   set_gdbarch_inner_than (gdbarch, core_addr_lessthan);
1505   set_gdbarch_unwind_sp (gdbarch, score_unwind_sp);
1506   set_gdbarch_unwind_pc (gdbarch, score_unwind_pc);
1507   set_gdbarch_print_insn (gdbarch, score_print_insn);
1508
1509   switch (target_mach)
1510     {
1511     case bfd_mach_score7:
1512       set_gdbarch_breakpoint_from_pc (gdbarch, score7_breakpoint_from_pc);
1513       set_gdbarch_skip_prologue (gdbarch, score7_skip_prologue);
1514       set_gdbarch_in_function_epilogue_p (gdbarch,
1515                                           score7_in_function_epilogue_p);
1516       set_gdbarch_register_name (gdbarch, score7_register_name);
1517       set_gdbarch_num_regs (gdbarch, SCORE7_NUM_REGS);
1518       /* Core file support.  */
1519       set_gdbarch_regset_from_core_section (gdbarch,
1520                                             score7_linux_regset_from_core_section);
1521       break;
1522
1523     case bfd_mach_score3:
1524       set_gdbarch_breakpoint_from_pc (gdbarch, score3_breakpoint_from_pc);
1525       set_gdbarch_skip_prologue (gdbarch, score3_skip_prologue);
1526       set_gdbarch_in_function_epilogue_p (gdbarch,
1527                                           score3_in_function_epilogue_p);
1528       set_gdbarch_register_name (gdbarch, score3_register_name);
1529       set_gdbarch_num_regs (gdbarch, SCORE3_NUM_REGS);
1530       break;
1531     }
1532
1533   /* Watchpoint hooks.  */
1534   set_gdbarch_have_nonsteppable_watchpoint (gdbarch, 1);
1535
1536   /* Dummy frame hooks.  */
1537   set_gdbarch_return_value (gdbarch, score_return_value);
1538   set_gdbarch_call_dummy_location (gdbarch, AT_ENTRY_POINT);
1539   set_gdbarch_dummy_id (gdbarch, score_dummy_id);
1540   set_gdbarch_push_dummy_call (gdbarch, score_push_dummy_call);
1541
1542   /* Normal frame hooks.  */
1543   dwarf2_append_unwinders (gdbarch);
1544   frame_base_append_sniffer (gdbarch, dwarf2_frame_base_sniffer);
1545   frame_unwind_append_unwinder (gdbarch, &score_prologue_unwind);
1546   frame_base_append_sniffer (gdbarch, score_prologue_frame_base_sniffer);
1547
1548   return gdbarch;
1549 }
1550
1551 extern initialize_file_ftype _initialize_score_tdep;
1552
1553 void
1554 _initialize_score_tdep (void)
1555 {
1556   gdbarch_register (bfd_arch_score, score_gdbarch_init, NULL);
1557 }