2004-03-22 Andrew Cagney <cagney@redhat.com>
[external/binutils.git] / gdb / xstormy16-tdep.c
1 /* Target-dependent code for the Sanyo Xstormy16a (LC590000) processor.
2
3    Copyright 2001, 2002, 2003, 2004 Free Software Foundation, Inc.
4
5    This file is part of GDB.
6
7    This program is free software; you can redistribute it and/or modify
8    it under the terms of the GNU General Public License as published by
9    the Free Software Foundation; either version 2 of the License, or
10    (at your option) any later version.
11
12    This program is distributed in the hope that it will be useful,
13    but WITHOUT ANY WARRANTY; without even the implied warranty of
14    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15    GNU General Public License for more details.
16
17    You should have received a copy of the GNU General Public License
18    along with this program; if not, write to the Free Software
19    Foundation, Inc., 59 Temple Place - Suite 330,
20    Boston, MA 02111-1307, USA.  */
21
22 #include "defs.h"
23 #include "value.h"
24 #include "inferior.h"
25 #include "arch-utils.h"
26 #include "regcache.h"
27 #include "gdbcore.h"
28 #include "objfiles.h"
29 #include "dis-asm.h"
30
31 struct gdbarch_tdep
32 {
33   /* gdbarch target dependent data here. Currently unused for Xstormy16. */
34 };
35
36 /* Extra info which is saved in each frame_info. */
37 struct frame_extra_info
38 {
39   int framesize;
40   int frameless_p;
41 };
42
43 enum gdb_regnum
44 {
45   /* Xstormy16 has 16 general purpose registers (R0-R15) plus PC.
46      Functions will return their values in register R2-R7 as they fit.
47      Otherwise a hidden pointer to an big enough area is given as argument
48      to the function in r2. Further arguments are beginning in r3 then.
49      R13 is used as frame pointer when GCC compiles w/o optimization
50      R14 is used as "PSW", displaying the CPU status.
51      R15 is used implicitely as stack pointer. */
52   E_R0_REGNUM,
53   E_R1_REGNUM,
54   E_R2_REGNUM, E_1ST_ARG_REGNUM = E_R2_REGNUM, E_PTR_RET_REGNUM = E_R2_REGNUM,
55   E_R3_REGNUM,
56   E_R4_REGNUM,
57   E_R5_REGNUM,
58   E_R6_REGNUM,
59   E_R7_REGNUM, E_LST_ARG_REGNUM = E_R7_REGNUM,
60   E_R8_REGNUM,
61   E_R9_REGNUM,
62   E_R10_REGNUM,
63   E_R11_REGNUM,
64   E_R12_REGNUM,
65   E_R13_REGNUM, E_FP_REGNUM = E_R13_REGNUM,
66   E_R14_REGNUM, E_PSW_REGNUM = E_R14_REGNUM,
67   E_R15_REGNUM, E_SP_REGNUM = E_R15_REGNUM,
68   E_PC_REGNUM,
69   E_NUM_REGS
70 };
71
72 /* Size of instructions, registers, etc. */
73 enum
74 {
75   xstormy16_inst_size = 2,
76   xstormy16_reg_size = 2,
77   xstormy16_pc_size = 4
78 };
79
80 /* Size of return datatype which fits into the remaining return registers. */
81 #define E_MAX_RETTYPE_SIZE(regnum)      ((E_LST_ARG_REGNUM - (regnum) + 1) \
82                                         * xstormy16_reg_size)
83
84 /* Size of return datatype which fits into all return registers. */
85 enum
86 {
87   E_MAX_RETTYPE_SIZE_IN_REGS = E_MAX_RETTYPE_SIZE (E_R2_REGNUM)
88 };
89
90
91 /* Size of all registers as a whole. */
92 enum
93 {
94   E_ALL_REGS_SIZE = (E_NUM_REGS - 1) * xstormy16_reg_size + xstormy16_pc_size
95 };
96
97 /* Function: xstormy16_register_name
98    Returns the name of the standard Xstormy16 register N. */
99
100 static const char *
101 xstormy16_register_name (int regnum)
102 {
103   static char *register_names[] = {
104     "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7",
105     "r8", "r9", "r10", "r11", "r12", "r13",
106     "psw", "sp", "pc"
107   };
108
109   if (regnum < 0 ||
110       regnum >= sizeof (register_names) / sizeof (register_names[0]))
111     internal_error (__FILE__, __LINE__,
112                     "xstormy16_register_name: illegal register number %d",
113                     regnum);
114   else
115     return register_names[regnum];
116
117 }
118
119 /* Function: xstormy16_register_byte 
120    Returns the byte position in the register cache for register N. */
121
122 static int
123 xstormy16_register_byte (int regnum)
124 {
125   if (regnum < 0 || regnum >= E_NUM_REGS)
126     internal_error (__FILE__, __LINE__,
127                     "xstormy16_register_byte: illegal register number %d",
128                     regnum);
129   else
130     /* All registers occupy 2 bytes in the regcache except for PC
131        which is the last one. Therefore the byte position is still
132        simply a multiple of 2. */
133     return regnum * xstormy16_reg_size;
134 }
135
136 /* Function: xstormy16_register_raw_size
137    Returns the number of bytes occupied by the register on the target. */
138
139 static int
140 xstormy16_register_raw_size (int regnum)
141 {
142   if (regnum < 0 || regnum >= E_NUM_REGS)
143     internal_error (__FILE__, __LINE__,
144                     "xstormy16_register_raw_size: illegal register number %d",
145                     regnum);
146   /* Only the PC has 4 Byte, all other registers 2 Byte. */
147   else if (regnum == E_PC_REGNUM)
148     return xstormy16_pc_size;
149   else
150     return xstormy16_reg_size;
151 }
152
153 /* Function: xstormy16_reg_virtual_type 
154    Returns the default type for register N. */
155
156 static struct type *
157 xstormy16_reg_virtual_type (int regnum)
158 {
159   if (regnum < 0 || regnum >= E_NUM_REGS)
160     internal_error (__FILE__, __LINE__,
161                     "xstormy16_register_virtual_type: illegal register number %d",
162                     regnum);
163   else if (regnum == E_PC_REGNUM)
164     return builtin_type_uint32;
165   else
166     return builtin_type_uint16;
167 }
168
169 /* Function: xstormy16_get_saved_register
170    Find a register's saved value on the call stack. */
171
172 static void
173 xstormy16_get_saved_register (char *raw_buffer,
174                               int *optimized,
175                               CORE_ADDR *addrp,
176                               struct frame_info *fi,
177                               int regnum, enum lval_type *lval)
178 {
179   deprecated_generic_get_saved_register (raw_buffer, optimized, addrp, fi, regnum, lval);
180 }
181
182 /* Function: xstormy16_type_is_scalar
183    Makes the decision if a given type is a scalar types.  Scalar
184    types are returned in the registers r2-r7 as they fit. */
185
186 static int
187 xstormy16_type_is_scalar (struct type *t)
188 {
189   return (TYPE_CODE(t) != TYPE_CODE_STRUCT
190           && TYPE_CODE(t) != TYPE_CODE_UNION
191           && TYPE_CODE(t) != TYPE_CODE_ARRAY);
192 }
193
194 /* Function: xstormy16_extract_return_value
195    Copy the function's return value into VALBUF. 
196    This function is called only in the context of "target function calls",
197    ie. when the debugger forces a function to be called in the child, and
198    when the debugger forces a function to return prematurely via the
199    "return" command. */
200
201 static void
202 xstormy16_extract_return_value (struct type *type, char *regbuf, char *valbuf)
203 {
204   CORE_ADDR return_buffer;
205   int offset = 0;
206
207   if (xstormy16_type_is_scalar (type)
208       && TYPE_LENGTH (type) <= E_MAX_RETTYPE_SIZE_IN_REGS)
209     {
210       /* Scalar return values of <= 12 bytes are returned in 
211          E_1ST_ARG_REGNUM to E_LST_ARG_REGNUM. */
212       memcpy (valbuf,
213               &regbuf[DEPRECATED_REGISTER_BYTE (E_1ST_ARG_REGNUM)] + offset,
214               TYPE_LENGTH (type));
215     }
216   else
217     {
218       /* Aggregates and return values > 12 bytes are returned in memory,
219          pointed to by R2. */
220       return_buffer =
221         extract_unsigned_integer (regbuf + DEPRECATED_REGISTER_BYTE (E_PTR_RET_REGNUM),
222                                   DEPRECATED_REGISTER_RAW_SIZE (E_PTR_RET_REGNUM));
223
224       read_memory (return_buffer, valbuf, TYPE_LENGTH (type));
225     }
226 }
227
228 /* Function: xstormy16_push_arguments
229    Setup the function arguments for GDB to call a function in the inferior.
230    Called only in the context of a target function call from the debugger.
231    Returns the value of the SP register after the args are pushed.
232 */
233
234 static CORE_ADDR
235 xstormy16_push_arguments (int nargs, struct value **args, CORE_ADDR sp,
236                           int struct_return, CORE_ADDR struct_addr)
237 {
238   CORE_ADDR stack_dest = sp;
239   int argreg = E_1ST_ARG_REGNUM;
240   int i, j;
241   int typelen, slacklen;
242   char *val;
243
244   /* If struct_return is true, then the struct return address will
245      consume one argument-passing register.  */
246   if (struct_return)
247     argreg++;
248
249   /* Arguments are passed in R2-R7 as they fit. If an argument doesn't
250      fit in the remaining registers we're switching over to the stack.
251      No argument is put on stack partially and as soon as we switched
252      over to stack no further argument is put in a register even if it
253      would fit in the remaining unused registers. */
254   for (i = 0; i < nargs && argreg <= E_LST_ARG_REGNUM; i++)
255     {
256       typelen = TYPE_LENGTH (VALUE_ENCLOSING_TYPE (args[i]));
257       if (typelen > E_MAX_RETTYPE_SIZE (argreg))
258         break;
259
260       /* Put argument into registers wordwise. */
261       val = VALUE_CONTENTS (args[i]);
262       for (j = 0; j < typelen; j += xstormy16_reg_size)
263         write_register (argreg++,
264                         extract_unsigned_integer (val + j,
265                                                   typelen - j ==
266                                                   1 ? 1 :
267                                                   xstormy16_reg_size));
268     }
269
270   /* Align SP */
271   if (stack_dest & 1)
272     ++stack_dest;
273
274   /* Loop backwards through remaining arguments and push them on the stack,
275      wordaligned. */
276   for (j = nargs - 1; j >= i; j--)
277     {
278       typelen = TYPE_LENGTH (VALUE_ENCLOSING_TYPE (args[j]));
279       slacklen = typelen & 1;
280       val = alloca (typelen + slacklen);
281       memcpy (val, VALUE_CONTENTS (args[j]), typelen);
282       memset (val + typelen, 0, slacklen);
283
284       /* Now write this data to the stack. The stack grows upwards. */
285       write_memory (stack_dest, val, typelen + slacklen);
286       stack_dest += typelen + slacklen;
287     }
288
289   /* And that should do it.  Return the new stack pointer. */
290   return stack_dest;
291 }
292
293 /* Function: xstormy16_push_return_address (pc)
294    Setup the return address for GDB to call a function in the inferior.
295    Called only in the context of a target function call from the debugger.
296    Returns the value of the SP register when the operation is finished
297    (which may or may not be the same as before).
298 */
299
300 static CORE_ADDR
301 xstormy16_push_return_address (CORE_ADDR pc, CORE_ADDR sp)
302 {
303   unsigned char buf[xstormy16_pc_size];
304
305   store_unsigned_integer (buf, xstormy16_pc_size, entry_point_address ());
306   write_memory (sp, buf, xstormy16_pc_size);
307   return sp + xstormy16_pc_size;
308 }
309
310 /* Function: xstormy16_pop_frame
311    Destroy the innermost (Top-Of-Stack) stack frame, restoring the 
312    machine state that was in effect before the frame was created. 
313    Used in the contexts of the "return" command, and of 
314    target function calls from the debugger.
315 */
316
317 static void
318 xstormy16_pop_frame (void)
319 {
320   struct frame_info *fi = get_current_frame ();
321   int i;
322
323   if (fi == NULL)
324     return;                     /* paranoia */
325
326   if (DEPRECATED_PC_IN_CALL_DUMMY (get_frame_pc (fi), get_frame_base (fi),
327                                    get_frame_base (fi)))
328     {
329       deprecated_pop_dummy_frame ();
330     }
331   else
332     {
333       /* Restore the saved regs. */
334       for (i = 0; i < NUM_REGS; i++)
335         if (deprecated_get_frame_saved_regs (fi)[i])
336           {
337             if (i == SP_REGNUM)
338               write_register (i, deprecated_get_frame_saved_regs (fi)[i]);
339             else if (i == E_PC_REGNUM)
340               write_register (i, read_memory_integer (deprecated_get_frame_saved_regs (fi)[i],
341                                                       xstormy16_pc_size));
342             else
343               write_register (i, read_memory_integer (deprecated_get_frame_saved_regs (fi)[i],
344                                                       xstormy16_reg_size));
345           }
346       /* Restore the PC */
347       write_register (PC_REGNUM, DEPRECATED_FRAME_SAVED_PC (fi));
348       flush_cached_frames ();
349     }
350   return;
351 }
352
353 /* Function: xstormy16_store_struct_return
354    Copy the (struct) function return value to its destined location. 
355    Called only in the context of a target function call from the debugger.
356 */
357
358 static void
359 xstormy16_store_struct_return (CORE_ADDR addr, CORE_ADDR sp)
360 {
361   write_register (E_PTR_RET_REGNUM, addr);
362 }
363
364 /* Function: xstormy16_store_return_value
365    Copy the function return value from VALBUF into the 
366    proper location for a function return. 
367    Called only in the context of the "return" command.
368 */
369
370 static void
371 xstormy16_store_return_value (struct type *type, char *valbuf)
372 {
373   CORE_ADDR return_buffer;
374   char buf[xstormy16_reg_size];
375
376   if (xstormy16_type_is_scalar (type) && TYPE_LENGTH (type) == 1)
377     {
378       /* Add leading zeros to the value. */
379       memset (buf, 0, xstormy16_reg_size);
380       memcpy (buf, valbuf, 1);
381       deprecated_write_register_gen (E_1ST_ARG_REGNUM, buf);
382     }
383   else if (xstormy16_type_is_scalar (type) &&
384            TYPE_LENGTH (type) <= E_MAX_RETTYPE_SIZE_IN_REGS)
385     deprecated_write_register_bytes (DEPRECATED_REGISTER_BYTE (E_1ST_ARG_REGNUM),
386                                      valbuf, TYPE_LENGTH (type));
387   else
388     {
389       return_buffer = read_register (E_PTR_RET_REGNUM);
390       write_memory (return_buffer, valbuf, TYPE_LENGTH (type));
391     }
392 }
393
394 /* Function: xstormy16_extract_struct_value_address
395    Returns the address in which a function should return a struct value. 
396    Used in the contexts of the "return" command, and of 
397    target function calls from the debugger.
398 */
399
400 static CORE_ADDR
401 xstormy16_extract_struct_value_address (struct regcache *regcache)
402 {
403   /* FIXME: cagney/2004-01-17: Does the ABI guarantee that the return
404      address regster is preserved across function calls?  Probably
405      not, making this function wrong.  */
406   ULONGEST val;
407   regcache_raw_read_unsigned (regcache, E_PTR_RET_REGNUM, &val);
408   return val;
409 }
410
411 /* Function: xstormy16_use_struct_convention 
412    Returns non-zero if the given struct type will be returned using
413    a special convention, rather than the normal function return method. 
414    7sed in the contexts of the "return" command, and of 
415    target function calls from the debugger.
416 */
417
418 static int
419 xstormy16_use_struct_convention (int gcc_p, struct type *type)
420 {
421   return !xstormy16_type_is_scalar (type)
422     || TYPE_LENGTH (type) > E_MAX_RETTYPE_SIZE_IN_REGS;
423 }
424
425 /* Function: frame_saved_register
426    Returns the value that regnum had in frame fi
427    (saved in fi or in one of its children).  
428 */
429
430 static CORE_ADDR
431 xstormy16_frame_saved_register (struct frame_info *fi, int regnum)
432 {
433   int size = xstormy16_register_raw_size (regnum);
434   char *buf = (char *) alloca (size);
435
436   deprecated_generic_get_saved_register (buf, NULL, NULL, fi, regnum, NULL);
437   return (CORE_ADDR) extract_unsigned_integer (buf, size);
438 }
439
440 /* Function: xstormy16_scan_prologue
441    Decode the instructions within the given address range.
442    Decide when we must have reached the end of the function prologue.
443    If a frame_info pointer is provided, fill in its saved_regs etc.
444
445    Returns the address of the first instruction after the prologue. 
446 */
447
448 static CORE_ADDR
449 xstormy16_scan_prologue (CORE_ADDR start_addr, CORE_ADDR end_addr,
450                          struct frame_info *fi, int *frameless)
451 {
452   CORE_ADDR sp = 0, fp = 0;
453   CORE_ADDR next_addr;
454   ULONGEST inst, inst2;
455   LONGEST offset;
456   int regnum;
457
458   if (frameless)
459     *frameless = 1;
460   if (fi)
461     {
462       /* In a call dummy, don't touch the frame. */
463       if (DEPRECATED_PC_IN_CALL_DUMMY (get_frame_pc (fi), get_frame_base (fi),
464                                        get_frame_base (fi)))
465         return start_addr;
466
467       /* Grab the frame-relative values of SP and FP, needed below. 
468          The frame_saved_register function will find them on the
469          stack or in the registers as appropriate. */
470       sp = xstormy16_frame_saved_register (fi, E_SP_REGNUM);
471       fp = xstormy16_frame_saved_register (fi, E_FP_REGNUM);
472
473       /* Initialize framesize with size of PC put on stack by CALLF inst. */
474       get_frame_extra_info (fi)->framesize = xstormy16_pc_size;
475     }
476   for (next_addr = start_addr;
477        next_addr < end_addr; next_addr += xstormy16_inst_size)
478     {
479       inst = read_memory_unsigned_integer (next_addr, xstormy16_inst_size);
480       inst2 = read_memory_unsigned_integer (next_addr + xstormy16_inst_size,
481                                             xstormy16_inst_size);
482
483       if (inst >= 0x0082 && inst <= 0x008d)     /* push r2 .. push r13 */
484         {
485           if (fi)
486             {
487               regnum = inst & 0x000f;
488               deprecated_get_frame_saved_regs (fi)[regnum] = get_frame_extra_info (fi)->framesize;
489               get_frame_extra_info (fi)->framesize += xstormy16_reg_size;
490             }
491         }
492
493       /* optional stack allocation for args and local vars <= 4 byte */
494       else if (inst == 0x301f || inst == 0x303f)        /* inc r15, #0x1/#0x3 */
495         {
496           if (fi)               /* Record the frame size. */
497             get_frame_extra_info (fi)->framesize += ((inst & 0x0030) >> 4) + 1;
498         }
499
500       /* optional stack allocation for args and local vars > 4 && < 16 byte */
501       else if ((inst & 0xff0f) == 0x510f)       /* 51Hf   add r15, #0xH */
502         {
503           if (fi)               /* Record the frame size. */
504             get_frame_extra_info (fi)->framesize += (inst & 0x00f0) >> 4;
505         }
506
507       /* optional stack allocation for args and local vars >= 16 byte */
508       else if (inst == 0x314f && inst2 >= 0x0010)       /* 314f HHHH  add r15, #0xH */
509         {
510           if (fi)               /* Record the frame size. */
511             get_frame_extra_info (fi)->framesize += inst2;
512           next_addr += xstormy16_inst_size;
513         }
514
515       else if (inst == 0x46fd)  /* mov r13, r15 */
516         {
517           if (fi)               /* Record that the frame pointer is in use. */
518             get_frame_extra_info (fi)->frameless_p = 0;
519           if (frameless)
520             *frameless = 0;
521         }
522
523       /* optional copying of args in r2-r7 to r10-r13 */
524       /* Probably only in optimized case but legal action for prologue */
525       else if ((inst & 0xff00) == 0x4600        /* 46SD   mov rD, rS */
526                && (inst & 0x00f0) >= 0x0020 && (inst & 0x00f0) <= 0x0070
527                && (inst & 0x000f) >= 0x00a0 && (inst & 0x000f) <= 0x000d)
528         ;
529
530       /* optional copying of args in r2-r7 to stack */
531       /* 72DS HHHH   mov.b (rD, 0xHHHH), r(S-8) (bit3 always 1, bit2-0 = reg) */
532       /* 73DS HHHH   mov.w (rD, 0xHHHH), r(S-8) */
533       else if ((inst & 0xfed8) == 0x72d8 && (inst & 0x0007) >= 2)
534         {
535           if (fi)
536             {
537               regnum = inst & 0x0007;
538               /* Only 12 of 16 bits of the argument are used for the
539                  signed offset. */
540               offset = (LONGEST) (inst2 & 0x0fff);
541               if (offset & 0x0800)
542                 offset -= 0x1000;
543
544               deprecated_get_frame_saved_regs (fi)[regnum] = get_frame_extra_info (fi)->framesize + offset;
545             }
546           next_addr += xstormy16_inst_size;
547         }
548
549 #if 0
550       /* 2001-08-10: Not part of the prologue anymore due to change in
551          ABI. r8 and r9 are not used for argument passing anymore. */
552
553       /* optional copying of r8, r9 to stack */
554       /* 46S7; 73Df HHHH   mov.w r7,rS; mov.w (rD, 0xHHHH), r7 D=8,9; S=13,15 */
555       /* 46S7; 72df HHHH   mov.w r7,rS; mov.b (rD, 0xHHHH), r7 D=8,9; S=13,15 */
556       else if ((inst & 0xffef) == 0x4687 && (inst2 & 0xfedf) == 0x72df)
557         {
558           next_addr += xstormy16_inst_size;
559           if (fi)
560             {
561               regnum = (inst & 0x00f0) >> 4;
562               inst = inst2;
563               inst2 = read_memory_unsigned_integer (next_addr
564                                                     + xstormy16_inst_size,
565                                                     xstormy16_inst_size);
566               /* Only 12 of 16 bits of the argument are used for the
567                  signed offset. */
568               offset = (LONGEST) (inst2 & 0x0fff);
569               if (offset & 0x0800)
570                 offset -= 0x1000;
571
572               fi->saved_regs[regnum] = fi->extra_info->framesize + offset;
573             }
574           next_addr += xstormy16_inst_size;
575         }
576 #endif
577
578       else                      /* Not a prologue instruction. */
579         break;
580     }
581
582   if (fi)
583     {
584       /* Special handling for the "saved" address of the SP:
585          The SP is of course never saved on the stack at all, so
586          by convention what we put here is simply the previous 
587          _value_ of the SP (as opposed to an address where the
588          previous value would have been pushed).  */
589       if (get_frame_extra_info (fi)->frameless_p)
590         {
591           deprecated_get_frame_saved_regs (fi)[E_SP_REGNUM] = sp - get_frame_extra_info (fi)->framesize;
592           deprecated_update_frame_base_hack (fi, sp);
593         }
594       else
595         {
596           deprecated_get_frame_saved_regs (fi)[E_SP_REGNUM] = fp - get_frame_extra_info (fi)->framesize;
597           deprecated_update_frame_base_hack (fi, fp);
598         }
599
600       /* So far only offsets to the beginning of the frame are
601          saved in the saved_regs. Now we now the relation between
602          sp, fp and framesize. We know the beginning of the frame
603          so we can translate the register offsets to real addresses. */
604       for (regnum = 0; regnum < E_SP_REGNUM; ++regnum)
605         if (deprecated_get_frame_saved_regs (fi)[regnum])
606           deprecated_get_frame_saved_regs (fi)[regnum] += deprecated_get_frame_saved_regs (fi)[E_SP_REGNUM];
607
608       /* Save address of PC on stack. */
609       deprecated_get_frame_saved_regs (fi)[E_PC_REGNUM] = deprecated_get_frame_saved_regs (fi)[E_SP_REGNUM];
610     }
611
612   return next_addr;
613 }
614
615 /* Function: xstormy16_skip_prologue
616    If the input address is in a function prologue, 
617    returns the address of the end of the prologue;
618    else returns the input address.
619
620    Note: the input address is likely to be the function start, 
621    since this function is mainly used for advancing a breakpoint
622    to the first line, or stepping to the first line when we have
623    stepped into a function call.  */
624
625 static CORE_ADDR
626 xstormy16_skip_prologue (CORE_ADDR pc)
627 {
628   CORE_ADDR func_addr = 0, func_end = 0;
629   char *func_name;
630
631   if (find_pc_partial_function (pc, &func_name, &func_addr, &func_end))
632     {
633       struct symtab_and_line sal;
634       struct symbol *sym;
635
636       /* Don't trust line number debug info in frameless functions. */
637       int frameless = 1;
638       CORE_ADDR plg_end = xstormy16_scan_prologue (func_addr, func_end,
639                                                    NULL, &frameless);
640       if (frameless)
641         return plg_end;
642
643       /* Found a function.  */
644       sym = lookup_symbol (func_name, NULL, VAR_DOMAIN, NULL, NULL);
645       /* Don't use line number debug info for assembly source files. */
646       if (sym && SYMBOL_LANGUAGE (sym) != language_asm)
647         {
648           sal = find_pc_line (func_addr, 0);
649           if (sal.end && sal.end < func_end)
650             {
651               /* Found a line number, use it as end of prologue.  */
652               return sal.end;
653             }
654         }
655       /* No useable line symbol.  Use result of prologue parsing method. */
656       return plg_end;
657     }
658
659   /* No function symbol -- just return the PC. */
660
661   return (CORE_ADDR) pc;
662 }
663
664 /* The epilogue is defined here as the area at the end of a function,
665    either on the `ret' instruction itself or after an instruction which
666    destroys the function's stack frame. */
667 static int
668 xstormy16_in_function_epilogue_p (struct gdbarch *gdbarch, CORE_ADDR pc)
669 {
670   CORE_ADDR addr, func_addr = 0, func_end = 0;
671
672   if (find_pc_partial_function (pc, NULL, &func_addr, &func_end))
673     {
674       ULONGEST inst, inst2;
675       CORE_ADDR addr = func_end - xstormy16_inst_size;
676
677       /* The Xstormy16 epilogue is max. 14 bytes long. */
678       if (pc < func_end - 7 * xstormy16_inst_size)
679         return 0;
680
681       /* Check if we're on a `ret' instruction.  Otherwise it's
682          too dangerous to proceed. */
683       inst = read_memory_unsigned_integer (addr, xstormy16_inst_size);
684       if (inst != 0x0003)
685         return 0;
686
687       while ((addr -= xstormy16_inst_size) >= func_addr)
688         {
689           inst = read_memory_unsigned_integer (addr, xstormy16_inst_size);
690           if (inst >= 0x009a && inst <= 0x009d) /* pop r10...r13 */
691             continue;
692           if (inst == 0x305f || inst == 0x307f) /* dec r15, #0x1/#0x3 */
693             break;
694           inst2 = read_memory_unsigned_integer (addr - xstormy16_inst_size,
695                                                 xstormy16_inst_size);
696           if (inst2 == 0x314f && inst >= 0x8000)        /* add r15, neg. value */
697             {
698               addr -= xstormy16_inst_size;
699               break;
700             }
701           return 0;
702         }
703       if (pc > addr)
704         return 1;
705     }
706   return 0;
707 }
708
709 /* Function: xstormy16_frame_init_saved_regs
710    Set up the 'saved_regs' array.
711    This is a data structure containing the addresses on the stack 
712    where each register has been saved, for each stack frame.  
713    Registers that have not been saved will have zero here.
714    The stack register is special: rather than the address where the 
715    stack register has been saved, saved_regs[SP_REGNUM] will have the
716    actual value of the previous frame's stack register. 
717
718    This function may be called in any context where the saved register
719    values may be needed (backtrace, frame_info, frame_register).  On
720    many targets, it is called directly by init_extra_frame_info, in
721    part because the information may be needed immediately by
722    frame_chain.  */
723
724 static void
725 xstormy16_frame_init_saved_regs (struct frame_info *fi)
726 {
727   CORE_ADDR func_addr, func_end;
728
729   if (!deprecated_get_frame_saved_regs (fi))
730     {
731       frame_saved_regs_zalloc (fi);
732
733       /* Find the beginning of this function, so we can analyze its
734          prologue. */
735       if (find_pc_partial_function (get_frame_pc (fi), NULL, &func_addr, &func_end))
736         xstormy16_scan_prologue (func_addr, get_frame_pc (fi), fi, NULL);
737       /* Else we're out of luck (can't debug completely stripped code). 
738          FIXME. */
739     }
740 }
741
742 /* Function: xstormy16_frame_saved_pc
743    Returns the return address for the selected frame. 
744    Called by frame_info, legacy_frame_chain_valid, and sometimes by
745    get_prev_frame.  */
746
747 static CORE_ADDR
748 xstormy16_frame_saved_pc (struct frame_info *fi)
749 {
750   CORE_ADDR saved_pc;
751
752   if (DEPRECATED_PC_IN_CALL_DUMMY (get_frame_pc (fi), get_frame_base (fi),
753                                    get_frame_base (fi)))
754     {
755       saved_pc = deprecated_read_register_dummy (get_frame_pc (fi),
756                                                  get_frame_base (fi),
757                                                  E_PC_REGNUM);
758     }
759   else
760     {
761       saved_pc = read_memory_unsigned_integer (deprecated_get_frame_saved_regs (fi)[E_PC_REGNUM],
762                                                xstormy16_pc_size);
763     }
764
765   return saved_pc;
766 }
767
768 /* Function: xstormy16_init_extra_frame_info
769    This is the constructor function for the frame_info struct, 
770    called whenever a new frame_info is created (from create_new_frame,
771    and from get_prev_frame).
772 */
773
774 static void
775 xstormy16_init_extra_frame_info (int fromleaf, struct frame_info *fi)
776 {
777   if (!get_frame_extra_info (fi))
778     {
779       frame_extra_info_zalloc (fi, sizeof (struct frame_extra_info));
780       get_frame_extra_info (fi)->framesize = 0;
781       get_frame_extra_info (fi)->frameless_p = 1;       /* Default frameless, detect framed */
782
783       /* By default, the fi->frame is set to the value of the FP reg by gdb.
784          This may not always be right; we may be in a frameless function,
785          or we may be in the prologue, before the FP has been set up.
786          Unfortunately, we can't make this determination without first
787          calling scan_prologue, and we can't do that unles we know the
788          get_frame_pc (fi).  */
789
790       if (!get_frame_pc (fi))
791         {
792           /* Sometimes we are called from get_prev_frame without
793              the PC being set up first.  Long history, don't ask.
794              Fortunately this will never happen from the outermost
795              frame, so we should be able to get the saved pc from
796              the next frame. */
797           if (get_next_frame (fi))
798             deprecated_update_frame_pc_hack (fi, xstormy16_frame_saved_pc (get_next_frame (fi)));
799         }
800
801       /* Take care of the saved_regs right here (non-lazy). */
802       xstormy16_frame_init_saved_regs (fi);
803     }
804 }
805
806 /* Function: xstormy16_frame_chain
807    Returns a pointer to the stack frame of the calling function.
808    Called only from get_prev_frame.  Needed for backtrace, "up", etc.
809 */
810
811 static CORE_ADDR
812 xstormy16_frame_chain (struct frame_info *fi)
813 {
814   if (DEPRECATED_PC_IN_CALL_DUMMY (get_frame_pc (fi), get_frame_base (fi),
815                                    get_frame_base (fi)))
816     {
817       /* Call dummy's frame is the same as caller's.  */
818       return get_frame_base (fi);
819     }
820   else
821     {
822       /* Return computed offset from this frame's fp. */
823       return get_frame_base (fi) - get_frame_extra_info (fi)->framesize;
824     }
825 }
826
827 static int
828 xstormy16_frame_chain_valid (CORE_ADDR chain, struct frame_info *thisframe)
829 {
830   return chain < 0x8000 && DEPRECATED_FRAME_SAVED_PC (thisframe) >= 0x8000 &&
831     (get_frame_extra_info (thisframe)->frameless_p ||
832      get_frame_base (thisframe) - get_frame_extra_info (thisframe)->framesize == chain);
833 }
834
835 /* Function: xstormy16_saved_pc_after_call Returns the previous PC
836    immediately after a function call.  This function is meant to
837    bypass the regular frame_register() mechanism, ie. it is meant to
838    work even if the frame isn't complete.  Called by
839    step_over_function, and sometimes by get_prev_frame.  */
840
841 static CORE_ADDR
842 xstormy16_saved_pc_after_call (struct frame_info *ignore)
843 {
844   CORE_ADDR sp, pc, tmp;
845
846   sp = read_register (E_SP_REGNUM) - xstormy16_pc_size;
847   pc = read_memory_integer (sp, xstormy16_pc_size);
848
849   /* Skip over jump table entry if necessary.  */
850   if ((tmp = SKIP_TRAMPOLINE_CODE (pc)))
851     pc = tmp;
852
853   return pc;
854 }
855
856 const static unsigned char *
857 xstormy16_breakpoint_from_pc (CORE_ADDR *pcptr, int *lenptr)
858 {
859   static unsigned char breakpoint[] = { 0x06, 0x0 };
860   *lenptr = sizeof (breakpoint);
861   return breakpoint;
862 }
863
864 /* Given a pointer to a jump table entry, return the address
865    of the function it jumps to.  Return 0 if not found. */
866 static CORE_ADDR
867 xstormy16_resolve_jmp_table_entry (CORE_ADDR faddr)
868 {
869   struct obj_section *faddr_sect = find_pc_section (faddr);
870
871   if (faddr_sect)
872     {
873       LONGEST inst, inst2, addr;
874       char buf[2 * xstormy16_inst_size];
875
876       /* Return faddr if it's not pointing into the jump table. */
877       if (strcmp (faddr_sect->the_bfd_section->name, ".plt"))
878         return faddr;
879
880       if (!target_read_memory (faddr, buf, sizeof buf))
881         {
882           inst = extract_unsigned_integer (buf, xstormy16_inst_size);
883           inst2 = extract_unsigned_integer (buf + xstormy16_inst_size,
884                                             xstormy16_inst_size);
885           addr = inst2 << 8 | (inst & 0xff);
886           return addr;
887         }
888     }
889   return 0;
890 }
891
892 /* Given a function's address, attempt to find (and return) the
893    address of the corresponding jump table entry.  Return 0 if
894    not found. */
895 static CORE_ADDR
896 xstormy16_find_jmp_table_entry (CORE_ADDR faddr)
897 {
898   struct obj_section *faddr_sect = find_pc_section (faddr);
899
900   if (faddr_sect)
901     {
902       struct obj_section *osect;
903
904       /* Return faddr if it's already a pointer to a jump table entry. */
905       if (!strcmp (faddr_sect->the_bfd_section->name, ".plt"))
906         return faddr;
907
908       ALL_OBJFILE_OSECTIONS (faddr_sect->objfile, osect)
909       {
910         if (!strcmp (osect->the_bfd_section->name, ".plt"))
911           break;
912       }
913
914       if (osect < faddr_sect->objfile->sections_end)
915         {
916           CORE_ADDR addr;
917           for (addr = osect->addr;
918                addr < osect->endaddr; addr += 2 * xstormy16_inst_size)
919             {
920               int status;
921               LONGEST inst, inst2, faddr2;
922               char buf[2 * xstormy16_inst_size];
923
924               if (target_read_memory (addr, buf, sizeof buf))
925                 return 0;
926               inst = extract_unsigned_integer (buf, xstormy16_inst_size);
927               inst2 = extract_unsigned_integer (buf + xstormy16_inst_size,
928                                                 xstormy16_inst_size);
929               faddr2 = inst2 << 8 | (inst & 0xff);
930               if (faddr == faddr2)
931                 return addr;
932             }
933         }
934     }
935   return 0;
936 }
937
938 static CORE_ADDR
939 xstormy16_skip_trampoline_code (CORE_ADDR pc)
940 {
941   int tmp = xstormy16_resolve_jmp_table_entry (pc);
942
943   if (tmp && tmp != pc)
944     return tmp;
945   return 0;
946 }
947
948 static int
949 xstormy16_in_solib_call_trampoline (CORE_ADDR pc, char *name)
950 {
951   return xstormy16_skip_trampoline_code (pc) != 0;
952 }
953
954 static CORE_ADDR
955 xstormy16_pointer_to_address (struct type *type, const void *buf)
956 {
957   enum type_code target = TYPE_CODE (TYPE_TARGET_TYPE (type));
958   CORE_ADDR addr = extract_unsigned_integer (buf, TYPE_LENGTH (type));
959
960   if (target == TYPE_CODE_FUNC || target == TYPE_CODE_METHOD)
961     {
962       CORE_ADDR addr2 = xstormy16_resolve_jmp_table_entry (addr);
963       if (addr2)
964         addr = addr2;
965     }
966
967   return addr;
968 }
969
970 static void
971 xstormy16_address_to_pointer (struct type *type, void *buf, CORE_ADDR addr)
972 {
973   enum type_code target = TYPE_CODE (TYPE_TARGET_TYPE (type));
974
975   if (target == TYPE_CODE_FUNC || target == TYPE_CODE_METHOD)
976     {
977       CORE_ADDR addr2 = xstormy16_find_jmp_table_entry (addr);
978       if (addr2)
979         addr = addr2;
980     }
981   store_unsigned_integer (buf, TYPE_LENGTH (type), addr);
982 }
983
984 static CORE_ADDR
985 xstormy16_stack_align (CORE_ADDR addr)
986 {
987   if (addr & 1)
988     ++addr;
989   return addr;
990 }
991
992 static void
993 xstormy16_save_dummy_frame_tos (CORE_ADDR sp)
994 {
995   generic_save_dummy_frame_tos (sp - xstormy16_pc_size);
996 }
997
998 /* Function: xstormy16_gdbarch_init
999    Initializer function for the xstormy16 gdbarch vector.
1000    Called by gdbarch.  Sets up the gdbarch vector(s) for this target. */
1001
1002 static struct gdbarch *
1003 xstormy16_gdbarch_init (struct gdbarch_info info, struct gdbarch_list *arches)
1004 {
1005   static LONGEST call_dummy_words[1] = { 0 };
1006   struct gdbarch_tdep *tdep = NULL;
1007   struct gdbarch *gdbarch;
1008
1009   /* find a candidate among the list of pre-declared architectures. */
1010   arches = gdbarch_list_lookup_by_info (arches, &info);
1011   if (arches != NULL)
1012     return (arches->gdbarch);
1013
1014 #if 0
1015   tdep = (struct gdbarch_tdep *) xmalloc (sizeof (struct gdbarch_tdep));
1016 #endif
1017
1018   gdbarch = gdbarch_alloc (&info, 0);
1019
1020   /* NOTE: cagney/2002-12-06: This can be deleted when this arch is
1021      ready to unwind the PC first (see frame.c:get_prev_frame()).  */
1022   set_gdbarch_deprecated_init_frame_pc (gdbarch, deprecated_init_frame_pc_default);
1023
1024   /*
1025    * Basic register fields and methods.
1026    */
1027
1028   set_gdbarch_num_regs (gdbarch, E_NUM_REGS);
1029   set_gdbarch_num_pseudo_regs (gdbarch, 0);
1030   set_gdbarch_sp_regnum (gdbarch, E_SP_REGNUM);
1031   set_gdbarch_deprecated_fp_regnum (gdbarch, E_FP_REGNUM);
1032   set_gdbarch_pc_regnum (gdbarch, E_PC_REGNUM);
1033   set_gdbarch_register_name (gdbarch, xstormy16_register_name);
1034   set_gdbarch_deprecated_register_size (gdbarch, xstormy16_reg_size);
1035   set_gdbarch_deprecated_register_bytes (gdbarch, E_ALL_REGS_SIZE);
1036   set_gdbarch_deprecated_register_byte (gdbarch, xstormy16_register_byte);
1037   set_gdbarch_deprecated_register_raw_size (gdbarch, xstormy16_register_raw_size);
1038   set_gdbarch_deprecated_max_register_raw_size (gdbarch, xstormy16_pc_size);
1039   set_gdbarch_deprecated_register_virtual_size (gdbarch, xstormy16_register_raw_size);
1040   set_gdbarch_deprecated_max_register_virtual_size (gdbarch, 4);
1041   set_gdbarch_deprecated_register_virtual_type (gdbarch, xstormy16_reg_virtual_type);
1042
1043   /*
1044    * Frame Info
1045    */
1046   set_gdbarch_deprecated_init_extra_frame_info (gdbarch,
1047                                      xstormy16_init_extra_frame_info);
1048   set_gdbarch_deprecated_frame_init_saved_regs (gdbarch,
1049                                      xstormy16_frame_init_saved_regs);
1050   set_gdbarch_deprecated_frame_chain (gdbarch, xstormy16_frame_chain);
1051   set_gdbarch_deprecated_get_saved_register (gdbarch, xstormy16_get_saved_register);
1052   set_gdbarch_deprecated_saved_pc_after_call (gdbarch, xstormy16_saved_pc_after_call);
1053   set_gdbarch_deprecated_frame_saved_pc (gdbarch, xstormy16_frame_saved_pc);
1054   set_gdbarch_skip_prologue (gdbarch, xstormy16_skip_prologue);
1055   set_gdbarch_deprecated_frame_chain_valid (gdbarch, xstormy16_frame_chain_valid);
1056
1057   set_gdbarch_in_function_epilogue_p (gdbarch,
1058                                       xstormy16_in_function_epilogue_p);
1059
1060   /* 
1061    * Miscelany
1062    */
1063   /* Stack grows up. */
1064   set_gdbarch_inner_than (gdbarch, core_addr_greaterthan);
1065
1066   /*
1067    * Call Dummies
1068    * 
1069    * These values and methods are used when gdb calls a target function.  */
1070   set_gdbarch_deprecated_push_return_address (gdbarch, xstormy16_push_return_address);
1071   set_gdbarch_deprecated_extract_return_value (gdbarch, xstormy16_extract_return_value);
1072   set_gdbarch_deprecated_push_arguments (gdbarch, xstormy16_push_arguments);
1073   set_gdbarch_deprecated_pop_frame (gdbarch, xstormy16_pop_frame);
1074   set_gdbarch_deprecated_store_struct_return (gdbarch, xstormy16_store_struct_return);
1075   set_gdbarch_deprecated_store_return_value (gdbarch, xstormy16_store_return_value);
1076   set_gdbarch_deprecated_extract_struct_value_address (gdbarch, xstormy16_extract_struct_value_address);
1077   set_gdbarch_use_struct_convention (gdbarch,
1078                                      xstormy16_use_struct_convention);
1079   set_gdbarch_deprecated_call_dummy_words (gdbarch, call_dummy_words);
1080   set_gdbarch_deprecated_sizeof_call_dummy_words (gdbarch, 0);
1081   set_gdbarch_breakpoint_from_pc (gdbarch, xstormy16_breakpoint_from_pc);
1082
1083   set_gdbarch_char_signed (gdbarch, 0);
1084   set_gdbarch_int_bit (gdbarch, 2 * TARGET_CHAR_BIT);
1085   set_gdbarch_ptr_bit (gdbarch, 2 * TARGET_CHAR_BIT);
1086   set_gdbarch_addr_bit (gdbarch, 4 * TARGET_CHAR_BIT);
1087   set_gdbarch_long_double_bit (gdbarch, 8 * TARGET_CHAR_BIT);
1088
1089   set_gdbarch_address_to_pointer (gdbarch, xstormy16_address_to_pointer);
1090   set_gdbarch_pointer_to_address (gdbarch, xstormy16_pointer_to_address);
1091
1092   set_gdbarch_deprecated_stack_align (gdbarch, xstormy16_stack_align);
1093
1094   set_gdbarch_deprecated_save_dummy_frame_tos (gdbarch, xstormy16_save_dummy_frame_tos);
1095
1096   set_gdbarch_skip_trampoline_code (gdbarch, xstormy16_skip_trampoline_code);
1097
1098   set_gdbarch_in_solib_call_trampoline (gdbarch,
1099                                         xstormy16_in_solib_call_trampoline);
1100
1101   /* Should be using push_dummy_call.  */
1102   set_gdbarch_deprecated_dummy_write_sp (gdbarch, deprecated_write_sp);
1103
1104   set_gdbarch_print_insn (gdbarch, print_insn_xstormy16);
1105
1106   return gdbarch;
1107 }
1108
1109 /* Function: _initialize_xstormy16_tdep
1110    Initializer function for the Sanyo Xstormy16a module.
1111    Called by gdb at start-up. */
1112
1113 extern initialize_file_ftype _initialize_xstormy16_tdep; /* -Wmissing-prototypes */
1114
1115 void
1116 _initialize_xstormy16_tdep (void)
1117 {
1118   register_gdbarch_init (bfd_arch_xstormy16, xstormy16_gdbarch_init);
1119 }