Imported Upstream version 7.9
[platform/upstream/gdb.git] / sim / arm / wrapper.c
1 /* run front end support for arm
2    Copyright (C) 1995-2015 Free Software Foundation, Inc.
3
4    This file is part of ARM SIM.
5
6    This program is free software; you can redistribute it and/or modify
7    it under the terms of the GNU General Public License as published by
8    the Free Software Foundation; either version 3 of the License, or
9    (at your option) any later version.
10
11    This program is distributed in the hope that it will be useful,
12    but WITHOUT ANY WARRANTY; without even the implied warranty of
13    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14    GNU General Public License for more details.
15
16    You should have received a copy of the GNU General Public License
17    along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
18
19 /* This file provides the interface between the simulator and
20    run.c and gdb (when the simulator is linked with gdb).
21    All simulator interaction should go through this file.  */
22
23 #include "config.h"
24 #include <stdio.h>
25 #include <stdarg.h>
26 #include <string.h>
27 #include <bfd.h>
28 #include <signal.h>
29 #include "gdb/callback.h"
30 #include "gdb/remote-sim.h"
31 #include "armdefs.h"
32 #include "armemu.h"
33 #include "dbg_rdi.h"
34 #include "ansidecl.h"
35 #include "sim-utils.h"
36 #include "run-sim.h"
37 #include "gdb/sim-arm.h"
38 #include "gdb/signals.h"
39 #include "libiberty.h"
40 #include "iwmmxt.h"
41
42 host_callback *sim_callback;
43
44 static struct ARMul_State *state;
45
46 /* Who is using the simulator.  */
47 static SIM_OPEN_KIND sim_kind;
48
49 /* argv[0] */
50 static char *myname;
51
52 /* Memory size in bytes.  */
53 static int mem_size = (1 << 21);
54
55 /* Non-zero to display start up banner, and maybe other things.  */
56 static int verbosity;
57
58 /* Non-zero to set big endian mode.  */
59 static int big_endian;
60
61 int stop_simulator;
62
63 #include "dis-asm.h"
64
65 int trace = 0;
66 int disas = 0;
67 int trace_funcs = 0;
68
69 static struct disassemble_info  info;
70 static char opbuf[1000];
71
72 static int
73 op_printf (char *buf, char *fmt, ...)
74 {
75   int ret;
76   va_list ap;
77
78   va_start (ap, fmt);
79   ret = vsprintf (opbuf + strlen (opbuf), fmt, ap);
80   va_end (ap);
81   return ret;
82 }
83
84 static int
85 sim_dis_read (bfd_vma                     memaddr ATTRIBUTE_UNUSED,
86               bfd_byte *                  ptr,
87               unsigned int                length,
88               struct disassemble_info *   info)
89 {
90   ARMword val = (ARMword) *((ARMword *) info->application_data);
91
92   while (length--)
93     {
94       * ptr ++ = val & 0xFF;
95       val >>= 8;
96     }
97   return 0;
98 }
99
100 void
101 print_insn (ARMword instr)
102 {
103   int size;
104
105   opbuf[0] = 0;
106   info.application_data = & instr;
107   size = print_insn_little_arm (0, & info);
108   fprintf (stderr, " %*s\n", size, opbuf);
109 }
110
111 /* Cirrus DSP registers.
112
113    We need to define these registers outside of maverick.c because
114    maverick.c might not be linked in unless --target=arm9e-* in which
115    case wrapper.c will not compile because it tries to access Cirrus
116    registers.  This should all go away once we get the Cirrus and ARM
117    Coprocessor to coexist in armcopro.c-- aldyh.  */
118
119 struct maverick_regs
120 {
121   union
122   {
123     int i;
124     float f;
125   } upper;
126   
127   union
128   {
129     int i;
130     float f;
131   } lower;
132 };
133
134 union maverick_acc_regs
135 {
136   long double ld;               /* Acc registers are 72-bits.  */
137 };
138
139 struct maverick_regs     DSPregs[16];
140 union maverick_acc_regs  DSPacc[4];
141 ARMword DSPsc;
142
143 static void
144 init (void)
145 {
146   static int done;
147
148   if (!done)
149     {
150       ARMul_EmulateInit ();
151       state = ARMul_NewState ();
152       state->bigendSig = (big_endian ? HIGH : LOW);
153       ARMul_MemoryInit (state, mem_size);
154       ARMul_OSInit (state);
155       state->verbose = verbosity;
156       done = 1;
157     }
158 }
159
160 /* Set verbosity level of simulator.
161    This is not intended to produce detailed tracing or debugging information.
162    Just summaries.  */
163 /* FIXME: common/run.c doesn't do this yet.  */
164
165 void
166 sim_set_verbose (int v)
167 {
168   verbosity = v;
169 }
170
171 /* Set the memory size to SIZE bytes.
172    Must be called before initializing simulator.  */
173 /* FIXME: Rename to sim_set_mem_size.  */
174
175 void
176 sim_size (int size)
177 {
178   mem_size = size;
179 }
180
181 void
182 ARMul_ConsolePrint (ARMul_State * state,
183                     const char * format,
184                     ...)
185 {
186   va_list ap;
187
188   if (state->verbose)
189     {
190       va_start (ap, format);
191       vprintf (format, ap);
192       va_end (ap);
193     }
194 }
195
196 ARMword
197 ARMul_Debug (ARMul_State * state ATTRIBUTE_UNUSED,
198              ARMword       pc    ATTRIBUTE_UNUSED,
199              ARMword       instr ATTRIBUTE_UNUSED)
200 {
201   return 0;
202 }
203
204 int
205 sim_write (SIM_DESC sd ATTRIBUTE_UNUSED,
206            SIM_ADDR addr,
207            const unsigned char * buffer,
208            int size)
209 {
210   int i;
211
212   init ();
213
214   for (i = 0; i < size; i++)
215     ARMul_SafeWriteByte (state, addr + i, buffer[i]);
216
217   return size;
218 }
219
220 int
221 sim_read (SIM_DESC sd ATTRIBUTE_UNUSED,
222           SIM_ADDR addr,
223           unsigned char * buffer,
224           int size)
225 {
226   int i;
227
228   init ();
229
230   for (i = 0; i < size; i++)
231     buffer[i] = ARMul_SafeReadByte (state, addr + i);
232
233   return size;
234 }
235
236 int
237 sim_trace (SIM_DESC sd ATTRIBUTE_UNUSED)
238 {
239   trace = 1;
240   sim_resume (sd, 0, 0);
241   return 1;
242 }
243
244 int
245 sim_stop (SIM_DESC sd ATTRIBUTE_UNUSED)
246 {
247   state->Emulate = STOP;
248   stop_simulator = 1;
249   return 1;
250 }
251
252 void
253 sim_resume (SIM_DESC sd ATTRIBUTE_UNUSED,
254             int step,
255             int siggnal ATTRIBUTE_UNUSED)
256 {
257   state->EndCondition = 0;
258   stop_simulator = 0;
259
260   if (step)
261     {
262       state->Reg[15] = ARMul_DoInstr (state);
263       if (state->EndCondition == 0)
264         state->EndCondition = RDIError_BreakpointReached;
265     }
266   else
267     {
268       state->NextInstr = RESUME;        /* treat as PC change */
269       state->Reg[15] = ARMul_DoProg (state);
270     }
271
272   FLUSHPIPE;
273 }
274
275 SIM_RC
276 sim_create_inferior (SIM_DESC sd ATTRIBUTE_UNUSED,
277                      struct bfd * abfd,
278                      char ** argv,
279                      char ** env)
280 {
281   int argvlen = 0;
282   int mach;
283   char **arg;
284
285   init ();
286
287   if (abfd != NULL)
288     {
289       ARMul_SetPC (state, bfd_get_start_address (abfd));
290       mach = bfd_get_mach (abfd);
291     }
292   else
293     {
294       ARMul_SetPC (state, 0);   /* ??? */
295       mach = 0;
296     }
297
298   switch (mach)
299     {
300     default:
301       (*sim_callback->printf_filtered)
302         (sim_callback,
303          "Unknown machine type '%d'; please update sim_create_inferior.\n",
304          mach);
305       /* fall through */
306
307     case 0:
308       /* We wouldn't set the machine type with earlier toolchains, so we
309          explicitly select a processor capable of supporting all ARMs in
310          32bit mode.  */
311       ARMul_SelectProcessor (state, ARM_v5_Prop | ARM_v5e_Prop | ARM_v6_Prop);
312       break;
313
314     case bfd_mach_arm_XScale:
315       ARMul_SelectProcessor (state, ARM_v5_Prop | ARM_v5e_Prop | ARM_XScale_Prop | ARM_v6_Prop);
316       break;
317
318     case bfd_mach_arm_iWMMXt2:
319     case bfd_mach_arm_iWMMXt:
320       {
321         extern int SWI_vector_installed;
322         ARMword i;
323
324         if (! SWI_vector_installed)
325           {
326             /* Intialise the hardware vectors to zero.  */
327             if (! SWI_vector_installed)
328               for (i = ARMul_ResetV; i <= ARMFIQV; i += 4)
329                 ARMul_WriteWord (state, i, 0);
330
331             /* ARM_WriteWord will have detected the write to the SWI vector,
332                but we want SWI_vector_installed to remain at 0 so that thumb
333                mode breakpoints will work.  */
334             SWI_vector_installed = 0;
335           }
336       }
337       ARMul_SelectProcessor (state, ARM_v5_Prop | ARM_v5e_Prop | ARM_XScale_Prop | ARM_iWMMXt_Prop);
338       break;
339
340     case bfd_mach_arm_ep9312:
341       ARMul_SelectProcessor (state, ARM_v4_Prop | ARM_ep9312_Prop);
342       break;
343
344     case bfd_mach_arm_5:
345       if (bfd_family_coff (abfd))
346         {
347           /* This is a special case in order to support COFF based ARM toolchains.
348              The COFF header does not have enough room to store all the different
349              kinds of ARM cpu, so the XScale, v5T and v5TE architectures all default
350              to v5.  (See coff_set_flags() in bdf/coffcode.h).  So if we see a v5
351              machine type here, we assume it could be any of the above architectures
352              and so select the most feature-full.  */
353           ARMul_SelectProcessor (state, ARM_v5_Prop | ARM_v5e_Prop | ARM_XScale_Prop);
354           break;
355         }
356       /* Otherwise drop through.  */
357
358     case bfd_mach_arm_5T:
359       ARMul_SelectProcessor (state, ARM_v5_Prop);
360       break;
361
362     case bfd_mach_arm_5TE:
363       ARMul_SelectProcessor (state, ARM_v5_Prop | ARM_v5e_Prop);
364       break;
365
366     case bfd_mach_arm_4:
367     case bfd_mach_arm_4T:
368       ARMul_SelectProcessor (state, ARM_v4_Prop);
369       break;
370
371     case bfd_mach_arm_3:
372     case bfd_mach_arm_3M:
373       ARMul_SelectProcessor (state, ARM_Lock_Prop);
374       break;
375
376     case bfd_mach_arm_2:
377     case bfd_mach_arm_2a:
378       ARMul_SelectProcessor (state, ARM_Fix26_Prop);
379       break;
380     }
381
382   if (   mach != bfd_mach_arm_3
383       && mach != bfd_mach_arm_3M
384       && mach != bfd_mach_arm_2
385       && mach != bfd_mach_arm_2a)
386     {
387       /* Reset mode to ARM.  A gdb user may rerun a program that had entered
388          THUMB mode from the start and cause the ARM-mode startup code to be
389          executed in THUMB mode.  */
390       ARMul_SetCPSR (state, SVC32MODE);
391     }
392   
393   memset (& info, 0, sizeof (info));
394   INIT_DISASSEMBLE_INFO (info, stdout, op_printf);
395   info.read_memory_func = sim_dis_read;
396   info.arch = bfd_get_arch (abfd);
397   info.mach = bfd_get_mach (abfd);
398   info.endian_code = BFD_ENDIAN_LITTLE;
399   if (info.mach == 0)
400     info.arch = bfd_arch_arm;
401   disassemble_init_for_target (& info);
402
403   if (argv != NULL)
404     {
405       /* Set up the command line by laboriously stringing together
406          the environment carefully picked apart by our caller.  */
407
408       /* Free any old stuff.  */
409       if (state->CommandLine != NULL)
410         {
411           free (state->CommandLine);
412           state->CommandLine = NULL;
413         }
414
415       /* See how much we need.  */
416       for (arg = argv; *arg != NULL; arg++)
417         argvlen += strlen (*arg) + 1;
418
419       /* Allocate it.  */
420       state->CommandLine = malloc (argvlen + 1);
421       if (state->CommandLine != NULL)
422         {
423           arg = argv;
424           state->CommandLine[0] = '\0';
425
426           for (arg = argv; *arg != NULL; arg++)
427             {
428               strcat (state->CommandLine, *arg);
429               strcat (state->CommandLine, " ");
430             }
431         }
432     }
433
434   if (env != NULL)
435     {
436       /* Now see if there's a MEMSIZE spec in the environment.  */
437       while (*env)
438         {
439           if (strncmp (*env, "MEMSIZE=", sizeof ("MEMSIZE=") - 1) == 0)
440             {
441               char *end_of_num;
442
443               /* Set up memory limit.  */
444               state->MemSize =
445                 strtoul (*env + sizeof ("MEMSIZE=") - 1, &end_of_num, 0);
446             }
447           env++;
448         }
449     }
450
451   return SIM_RC_OK;
452 }
453
454 void
455 sim_info (SIM_DESC sd ATTRIBUTE_UNUSED,
456           int verbose ATTRIBUTE_UNUSED)
457 {
458 }
459
460 static int
461 frommem (struct ARMul_State *state, unsigned char *memory)
462 {
463   if (state->bigendSig == HIGH)
464     return (memory[0] << 24) | (memory[1] << 16)
465       | (memory[2] << 8) | (memory[3] << 0);
466   else
467     return (memory[3] << 24) | (memory[2] << 16)
468       | (memory[1] << 8) | (memory[0] << 0);
469 }
470
471 static void
472 tomem (struct ARMul_State *state,
473        unsigned char *memory,
474        int val)
475 {
476   if (state->bigendSig == HIGH)
477     {
478       memory[0] = val >> 24;
479       memory[1] = val >> 16;
480       memory[2] = val >> 8;
481       memory[3] = val >> 0;
482     }
483   else
484     {
485       memory[3] = val >> 24;
486       memory[2] = val >> 16;
487       memory[1] = val >> 8;
488       memory[0] = val >> 0;
489     }
490 }
491
492 int
493 sim_store_register (SIM_DESC sd ATTRIBUTE_UNUSED,
494                     int rn,
495                     unsigned char *memory,
496                     int length)
497 {
498   init ();
499
500   switch ((enum sim_arm_regs) rn)
501     {
502     case SIM_ARM_R0_REGNUM:
503     case SIM_ARM_R1_REGNUM:
504     case SIM_ARM_R2_REGNUM:
505     case SIM_ARM_R3_REGNUM:
506     case SIM_ARM_R4_REGNUM:
507     case SIM_ARM_R5_REGNUM:
508     case SIM_ARM_R6_REGNUM:
509     case SIM_ARM_R7_REGNUM:
510     case SIM_ARM_R8_REGNUM:
511     case SIM_ARM_R9_REGNUM:
512     case SIM_ARM_R10_REGNUM:
513     case SIM_ARM_R11_REGNUM:
514     case SIM_ARM_R12_REGNUM:
515     case SIM_ARM_R13_REGNUM:
516     case SIM_ARM_R14_REGNUM:
517     case SIM_ARM_R15_REGNUM: /* PC */
518     case SIM_ARM_FP0_REGNUM:
519     case SIM_ARM_FP1_REGNUM:
520     case SIM_ARM_FP2_REGNUM:
521     case SIM_ARM_FP3_REGNUM:
522     case SIM_ARM_FP4_REGNUM:
523     case SIM_ARM_FP5_REGNUM:
524     case SIM_ARM_FP6_REGNUM:
525     case SIM_ARM_FP7_REGNUM:
526     case SIM_ARM_FPS_REGNUM:
527       ARMul_SetReg (state, state->Mode, rn, frommem (state, memory));
528       break;
529
530     case SIM_ARM_PS_REGNUM:
531       state->Cpsr = frommem (state, memory);
532       ARMul_CPSRAltered (state);
533       break;
534
535     case SIM_ARM_MAVERIC_COP0R0_REGNUM:
536     case SIM_ARM_MAVERIC_COP0R1_REGNUM:
537     case SIM_ARM_MAVERIC_COP0R2_REGNUM:
538     case SIM_ARM_MAVERIC_COP0R3_REGNUM:
539     case SIM_ARM_MAVERIC_COP0R4_REGNUM:
540     case SIM_ARM_MAVERIC_COP0R5_REGNUM:
541     case SIM_ARM_MAVERIC_COP0R6_REGNUM:
542     case SIM_ARM_MAVERIC_COP0R7_REGNUM:
543     case SIM_ARM_MAVERIC_COP0R8_REGNUM:
544     case SIM_ARM_MAVERIC_COP0R9_REGNUM:
545     case SIM_ARM_MAVERIC_COP0R10_REGNUM:
546     case SIM_ARM_MAVERIC_COP0R11_REGNUM:
547     case SIM_ARM_MAVERIC_COP0R12_REGNUM:
548     case SIM_ARM_MAVERIC_COP0R13_REGNUM:
549     case SIM_ARM_MAVERIC_COP0R14_REGNUM:
550     case SIM_ARM_MAVERIC_COP0R15_REGNUM:
551       memcpy (& DSPregs [rn - SIM_ARM_MAVERIC_COP0R0_REGNUM],
552               memory, sizeof (struct maverick_regs));
553       return sizeof (struct maverick_regs);
554
555     case SIM_ARM_MAVERIC_DSPSC_REGNUM:
556       memcpy (&DSPsc, memory, sizeof DSPsc);
557       return sizeof DSPsc;
558
559     case SIM_ARM_IWMMXT_COP0R0_REGNUM:
560     case SIM_ARM_IWMMXT_COP0R1_REGNUM:
561     case SIM_ARM_IWMMXT_COP0R2_REGNUM:
562     case SIM_ARM_IWMMXT_COP0R3_REGNUM:
563     case SIM_ARM_IWMMXT_COP0R4_REGNUM:
564     case SIM_ARM_IWMMXT_COP0R5_REGNUM:
565     case SIM_ARM_IWMMXT_COP0R6_REGNUM:
566     case SIM_ARM_IWMMXT_COP0R7_REGNUM:
567     case SIM_ARM_IWMMXT_COP0R8_REGNUM:
568     case SIM_ARM_IWMMXT_COP0R9_REGNUM:
569     case SIM_ARM_IWMMXT_COP0R10_REGNUM:
570     case SIM_ARM_IWMMXT_COP0R11_REGNUM:
571     case SIM_ARM_IWMMXT_COP0R12_REGNUM:
572     case SIM_ARM_IWMMXT_COP0R13_REGNUM:
573     case SIM_ARM_IWMMXT_COP0R14_REGNUM:
574     case SIM_ARM_IWMMXT_COP0R15_REGNUM:
575     case SIM_ARM_IWMMXT_COP1R0_REGNUM:
576     case SIM_ARM_IWMMXT_COP1R1_REGNUM:
577     case SIM_ARM_IWMMXT_COP1R2_REGNUM:
578     case SIM_ARM_IWMMXT_COP1R3_REGNUM:
579     case SIM_ARM_IWMMXT_COP1R4_REGNUM:
580     case SIM_ARM_IWMMXT_COP1R5_REGNUM:
581     case SIM_ARM_IWMMXT_COP1R6_REGNUM:
582     case SIM_ARM_IWMMXT_COP1R7_REGNUM:
583     case SIM_ARM_IWMMXT_COP1R8_REGNUM:
584     case SIM_ARM_IWMMXT_COP1R9_REGNUM:
585     case SIM_ARM_IWMMXT_COP1R10_REGNUM:
586     case SIM_ARM_IWMMXT_COP1R11_REGNUM:
587     case SIM_ARM_IWMMXT_COP1R12_REGNUM:
588     case SIM_ARM_IWMMXT_COP1R13_REGNUM:
589     case SIM_ARM_IWMMXT_COP1R14_REGNUM:
590     case SIM_ARM_IWMMXT_COP1R15_REGNUM:
591       return Store_Iwmmxt_Register (rn - SIM_ARM_IWMMXT_COP0R0_REGNUM, memory);
592
593     default:
594       return 0;
595     }
596
597   return length;
598 }
599
600 int
601 sim_fetch_register (SIM_DESC sd ATTRIBUTE_UNUSED,
602                     int rn,
603                     unsigned char *memory,
604                     int length)
605 {
606   ARMword regval;
607   int len = length;
608
609   init ();
610
611   switch ((enum sim_arm_regs) rn)
612     {
613     case SIM_ARM_R0_REGNUM:
614     case SIM_ARM_R1_REGNUM:
615     case SIM_ARM_R2_REGNUM:
616     case SIM_ARM_R3_REGNUM:
617     case SIM_ARM_R4_REGNUM:
618     case SIM_ARM_R5_REGNUM:
619     case SIM_ARM_R6_REGNUM:
620     case SIM_ARM_R7_REGNUM:
621     case SIM_ARM_R8_REGNUM:
622     case SIM_ARM_R9_REGNUM:
623     case SIM_ARM_R10_REGNUM:
624     case SIM_ARM_R11_REGNUM:
625     case SIM_ARM_R12_REGNUM:
626     case SIM_ARM_R13_REGNUM:
627     case SIM_ARM_R14_REGNUM:
628     case SIM_ARM_R15_REGNUM: /* PC */
629       regval = ARMul_GetReg (state, state->Mode, rn);
630       break;
631
632     case SIM_ARM_FP0_REGNUM:
633     case SIM_ARM_FP1_REGNUM:
634     case SIM_ARM_FP2_REGNUM:
635     case SIM_ARM_FP3_REGNUM:
636     case SIM_ARM_FP4_REGNUM:
637     case SIM_ARM_FP5_REGNUM:
638     case SIM_ARM_FP6_REGNUM:
639     case SIM_ARM_FP7_REGNUM:
640     case SIM_ARM_FPS_REGNUM:
641       memset (memory, 0, length);
642       return 0;
643
644     case SIM_ARM_PS_REGNUM:
645       regval = ARMul_GetCPSR (state);
646       break;
647
648     case SIM_ARM_MAVERIC_COP0R0_REGNUM:
649     case SIM_ARM_MAVERIC_COP0R1_REGNUM:
650     case SIM_ARM_MAVERIC_COP0R2_REGNUM:
651     case SIM_ARM_MAVERIC_COP0R3_REGNUM:
652     case SIM_ARM_MAVERIC_COP0R4_REGNUM:
653     case SIM_ARM_MAVERIC_COP0R5_REGNUM:
654     case SIM_ARM_MAVERIC_COP0R6_REGNUM:
655     case SIM_ARM_MAVERIC_COP0R7_REGNUM:
656     case SIM_ARM_MAVERIC_COP0R8_REGNUM:
657     case SIM_ARM_MAVERIC_COP0R9_REGNUM:
658     case SIM_ARM_MAVERIC_COP0R10_REGNUM:
659     case SIM_ARM_MAVERIC_COP0R11_REGNUM:
660     case SIM_ARM_MAVERIC_COP0R12_REGNUM:
661     case SIM_ARM_MAVERIC_COP0R13_REGNUM:
662     case SIM_ARM_MAVERIC_COP0R14_REGNUM:
663     case SIM_ARM_MAVERIC_COP0R15_REGNUM:
664       memcpy (memory, & DSPregs [rn - SIM_ARM_MAVERIC_COP0R0_REGNUM],
665               sizeof (struct maverick_regs));
666       return sizeof (struct maverick_regs);
667
668     case SIM_ARM_MAVERIC_DSPSC_REGNUM:
669       memcpy (memory, & DSPsc, sizeof DSPsc);
670       return sizeof DSPsc;
671
672     case SIM_ARM_IWMMXT_COP0R0_REGNUM:
673     case SIM_ARM_IWMMXT_COP0R1_REGNUM:
674     case SIM_ARM_IWMMXT_COP0R2_REGNUM:
675     case SIM_ARM_IWMMXT_COP0R3_REGNUM:
676     case SIM_ARM_IWMMXT_COP0R4_REGNUM:
677     case SIM_ARM_IWMMXT_COP0R5_REGNUM:
678     case SIM_ARM_IWMMXT_COP0R6_REGNUM:
679     case SIM_ARM_IWMMXT_COP0R7_REGNUM:
680     case SIM_ARM_IWMMXT_COP0R8_REGNUM:
681     case SIM_ARM_IWMMXT_COP0R9_REGNUM:
682     case SIM_ARM_IWMMXT_COP0R10_REGNUM:
683     case SIM_ARM_IWMMXT_COP0R11_REGNUM:
684     case SIM_ARM_IWMMXT_COP0R12_REGNUM:
685     case SIM_ARM_IWMMXT_COP0R13_REGNUM:
686     case SIM_ARM_IWMMXT_COP0R14_REGNUM:
687     case SIM_ARM_IWMMXT_COP0R15_REGNUM:
688     case SIM_ARM_IWMMXT_COP1R0_REGNUM:
689     case SIM_ARM_IWMMXT_COP1R1_REGNUM:
690     case SIM_ARM_IWMMXT_COP1R2_REGNUM:
691     case SIM_ARM_IWMMXT_COP1R3_REGNUM:
692     case SIM_ARM_IWMMXT_COP1R4_REGNUM:
693     case SIM_ARM_IWMMXT_COP1R5_REGNUM:
694     case SIM_ARM_IWMMXT_COP1R6_REGNUM:
695     case SIM_ARM_IWMMXT_COP1R7_REGNUM:
696     case SIM_ARM_IWMMXT_COP1R8_REGNUM:
697     case SIM_ARM_IWMMXT_COP1R9_REGNUM:
698     case SIM_ARM_IWMMXT_COP1R10_REGNUM:
699     case SIM_ARM_IWMMXT_COP1R11_REGNUM:
700     case SIM_ARM_IWMMXT_COP1R12_REGNUM:
701     case SIM_ARM_IWMMXT_COP1R13_REGNUM:
702     case SIM_ARM_IWMMXT_COP1R14_REGNUM:
703     case SIM_ARM_IWMMXT_COP1R15_REGNUM:
704       return Fetch_Iwmmxt_Register (rn - SIM_ARM_IWMMXT_COP0R0_REGNUM, memory);
705
706     default:
707       return 0;
708     }
709
710   while (len)
711     {
712       tomem (state, memory, regval);
713
714       len -= 4;
715       memory += 4;
716       regval = 0;
717     }  
718
719   return length;
720 }
721
722 typedef struct
723 {
724   char *        swi_option;
725   unsigned int  swi_mask;
726 } swi_options;
727
728 #define SWI_SWITCH      "--swi-support"
729
730 static swi_options options[] =
731   {
732     { "none",    0 },
733     { "demon",   SWI_MASK_DEMON },
734     { "angel",   SWI_MASK_ANGEL },
735     { "redboot", SWI_MASK_REDBOOT },
736     { "all",     -1 },
737     { "NONE",    0 },
738     { "DEMON",   SWI_MASK_DEMON },
739     { "ANGEL",   SWI_MASK_ANGEL },
740     { "REDBOOT", SWI_MASK_REDBOOT },
741     { "ALL",     -1 }
742   };
743
744
745 int
746 sim_target_parse_command_line (int argc, char ** argv)
747 {
748   int i;
749
750   for (i = 1; i < argc; i++)
751     {
752       char * ptr = argv[i];
753       int arg;
754
755       if ((ptr == NULL) || (* ptr != '-'))
756         break;
757
758       if (strcmp (ptr, "-t") == 0)
759         {
760           trace = 1;
761           continue;
762         }
763       
764       if (strcmp (ptr, "-z") == 0)
765         {
766           /* Remove this option from the argv array.  */
767           for (arg = i; arg < argc; arg ++)
768             argv[arg] = argv[arg + 1];
769           argc --;
770           i --;
771           trace_funcs = 1;
772           continue;
773         }
774       
775       if (strcmp (ptr, "-d") == 0)
776         {
777           /* Remove this option from the argv array.  */
778           for (arg = i; arg < argc; arg ++)
779             argv[arg] = argv[arg + 1];
780           argc --;
781           i --;
782           disas = 1;
783           continue;
784         }
785
786       if (strncmp (ptr, SWI_SWITCH, sizeof SWI_SWITCH - 1) != 0)
787         continue;
788
789       if (ptr[sizeof SWI_SWITCH - 1] == 0)
790         {
791           /* Remove this option from the argv array.  */
792           for (arg = i; arg < argc; arg ++)
793             argv[arg] = argv[arg + 1];
794           argc --;
795           
796           ptr = argv[i];
797         }
798       else
799         ptr += sizeof SWI_SWITCH;
800
801       swi_mask = 0;
802       
803       while (* ptr)
804         {
805           int i;
806
807           for (i = sizeof options / sizeof options[0]; i--;)
808             if (strncmp (ptr, options[i].swi_option,
809                          strlen (options[i].swi_option)) == 0)
810               {
811                 swi_mask |= options[i].swi_mask;
812                 ptr += strlen (options[i].swi_option);
813
814                 if (* ptr == ',')
815                   ++ ptr;
816
817                 break;
818               }
819
820           if (i < 0)
821             break;
822         }
823
824       if (* ptr != 0)
825         fprintf (stderr, "Ignoring swi options: %s\n", ptr);
826       
827       /* Remove this option from the argv array.  */
828       for (arg = i; arg < argc; arg ++)
829         argv[arg] = argv[arg + 1];
830       argc --;
831       i --;
832     }
833   return argc;
834 }
835
836 static void
837 sim_target_parse_arg_array (char ** argv)
838 {
839   int i;
840
841   for (i = 0; argv[i]; i++)
842     ;
843
844   sim_target_parse_command_line (i, argv);
845 }
846
847 void
848 sim_target_display_usage (int help)
849 {
850   FILE *stream = help ? stdout : stderr;
851
852   fprintf (stream, "%s=<list>  Comma seperated list of SWI protocols to supoport.\n\
853                 This list can contain: NONE, DEMON, ANGEL, REDBOOT and/or ALL.\n",
854            SWI_SWITCH);
855   fprintf (stream, "-d\t\tEnable disassembly of instructions during tracing.\n");
856   fprintf (stream, "-z\t\tTrace entering and leaving functions.\n\n");
857 }
858
859 SIM_DESC
860 sim_open (SIM_OPEN_KIND   kind,
861           host_callback * ptr,
862           struct bfd *    abfd,
863           char **         argv)
864 {
865   sim_kind = kind;
866
867   if (myname)
868     free (myname);
869   myname = (char *) xstrdup (argv[0]);
870
871   sim_callback = ptr;
872
873 #ifdef SIM_TARGET_SWITCHES
874   sim_target_parse_arg_array (argv);
875 #endif
876   
877   /* Decide upon the endian-ness of the processor.
878      If we can, get the information from the bfd itself.
879      Otherwise look to see if we have been given a command
880      line switch that tells us.  Otherwise default to little endian.  */
881   if (abfd != NULL)
882     big_endian = bfd_big_endian (abfd);
883   else if (argv[1] != NULL)
884     {
885       int i;
886
887       /* Scan for endian-ness and memory-size switches.  */
888       for (i = 0; (argv[i] != NULL) && (argv[i][0] != 0); i++)
889         if (argv[i][0] == '-' && argv[i][1] == 'E')
890           {
891             char c;
892
893             if ((c = argv[i][2]) == 0)
894               {
895                 ++i;
896                 c = argv[i][0];
897               }
898
899             switch (c)
900               {
901               case 0:
902                 sim_callback->printf_filtered
903                   (sim_callback, "No argument to -E option provided\n");
904                 break;
905
906               case 'b':
907               case 'B':
908                 big_endian = 1;
909                 break;
910
911               case 'l':
912               case 'L':
913                 big_endian = 0;
914                 break;
915
916               default:
917                 sim_callback->printf_filtered
918                   (sim_callback, "Unrecognised argument to -E option\n");
919                 break;
920               }
921           }
922         else if (argv[i][0] == '-' && argv[i][1] == 'm')
923           {
924             if (argv[i][2] != '\0')
925               sim_size (atoi (&argv[i][2]));
926             else if (argv[i + 1] != NULL)
927               {
928                 sim_size (atoi (argv[i + 1]));
929                 i++;
930               }
931             else
932               {
933                 sim_callback->printf_filtered (sim_callback,
934                                                "Missing argument to -m option\n");
935                 return NULL;
936               }
937               
938           }
939     }
940
941   return (SIM_DESC) 1;
942 }
943
944 void
945 sim_close (SIM_DESC sd ATTRIBUTE_UNUSED,
946            int quitting ATTRIBUTE_UNUSED)
947 {
948   if (myname)
949     free (myname);
950   myname = NULL;
951 }
952
953 SIM_RC
954 sim_load (SIM_DESC sd,
955           const char *prog,
956           bfd *abfd,
957           int from_tty ATTRIBUTE_UNUSED)
958 {
959   bfd *prog_bfd;
960
961   prog_bfd = sim_load_file (sd, myname, sim_callback, prog, abfd,
962                             sim_kind == SIM_OPEN_DEBUG, 0, sim_write);
963   if (prog_bfd == NULL)
964     return SIM_RC_FAIL;
965   ARMul_SetPC (state, bfd_get_start_address (prog_bfd));
966   if (abfd == NULL)
967     bfd_close (prog_bfd);
968   return SIM_RC_OK;
969 }
970
971 void
972 sim_stop_reason (SIM_DESC sd ATTRIBUTE_UNUSED,
973                  enum sim_stop *reason,
974                  int *sigrc)
975 {
976   if (stop_simulator)
977     {
978       *reason = sim_stopped;
979       *sigrc = GDB_SIGNAL_INT;
980     }
981   else if (state->EndCondition == 0)
982     {
983       *reason = sim_exited;
984       *sigrc = state->Reg[0] & 255;
985     }
986   else
987     {
988       *reason = sim_stopped;
989       if (state->EndCondition == RDIError_BreakpointReached)
990         *sigrc = GDB_SIGNAL_TRAP;
991       else if (   state->EndCondition == RDIError_DataAbort
992                || state->EndCondition == RDIError_AddressException)
993         *sigrc = GDB_SIGNAL_BUS;
994       else
995         *sigrc = 0;
996     }
997 }
998
999 void
1000 sim_do_command (SIM_DESC sd ATTRIBUTE_UNUSED,
1001                 const char *cmd ATTRIBUTE_UNUSED)
1002 {  
1003   (*sim_callback->printf_filtered)
1004     (sim_callback,
1005      "This simulator does not accept any commands.\n");
1006 }
1007
1008 void
1009 sim_set_callbacks (host_callback *ptr)
1010 {
1011   sim_callback = ptr;
1012 }
1013
1014 char **
1015 sim_complete_command (SIM_DESC sd, const char *text, const char *word)
1016 {
1017   return NULL;
1018 }