39dcdea7114fbc8b54f3bbac0e4baab45ba28e5a
[deliverable/binutils-gdb.git] / sim / rx / main.c
1 /* main.c --- main function for stand-alone RX simulator.
2
3 Copyright (C) 2005, 2007, 2008, 2009, 2010, 2011
4 Free Software Foundation, Inc.
5 Contributed by Red Hat, Inc.
6
7 This file is part of the GNU simulators.
8
9 This program is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation; either version 3 of the License, or
12 (at your option) any later version.
13
14 This program is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
18
19 You should have received a copy of the GNU General Public License
20 along with this program. If not, see <http://www.gnu.org/licenses/>. */
21
22
23 #include "config.h"
24 #include <stdio.h>
25 #include <string.h>
26 #ifdef HAVE_STDLIB_H
27 #include <stdlib.h>
28 #endif
29 #ifdef HAVE_UNISTD_H
30 #include <unistd.h>
31 #endif
32 #include <assert.h>
33 #include <setjmp.h>
34 #include <signal.h>
35 #ifdef HAVE_GETOPT_H
36 #include <getopt.h>
37 #endif
38
39 #include "bfd.h"
40
41 #include "cpu.h"
42 #include "mem.h"
43 #include "misc.h"
44 #include "load.h"
45 #include "trace.h"
46 #include "err.h"
47
48 static int disassemble = 0;
49
50 /* This must be higher than any other option index. */
51 #define OPT_ACT 400
52
53 #define ACT(E,A) (OPT_ACT + SIM_ERR_##E * SIM_ERRACTION_NUM_ACTIONS + SIM_ERRACTION_##A)
54
55 static struct option sim_options[] =
56 {
57 { "end-sim-args", 0, NULL, 'E' },
58 { "exit-null-deref", 0, NULL, ACT(NULL_POINTER_DEREFERENCE,EXIT) },
59 { "warn-null-deref", 0, NULL, ACT(NULL_POINTER_DEREFERENCE,WARN) },
60 { "ignore-null-deref", 0, NULL, ACT(NULL_POINTER_DEREFERENCE,IGNORE) },
61 { "exit-unwritten-pages", 0, NULL, ACT(READ_UNWRITTEN_PAGES,EXIT) },
62 { "warn-unwritten-pages", 0, NULL, ACT(READ_UNWRITTEN_PAGES,WARN) },
63 { "ignore-unwritten-pages", 0, NULL, ACT(READ_UNWRITTEN_PAGES,IGNORE) },
64 { "exit-unwritten-bytes", 0, NULL, ACT(READ_UNWRITTEN_BYTES,EXIT) },
65 { "warn-unwritten-bytes", 0, NULL, ACT(READ_UNWRITTEN_BYTES,WARN) },
66 { "ignore-unwritten-bytes", 0, NULL, ACT(READ_UNWRITTEN_BYTES,IGNORE) },
67 { "exit-corrupt-stack", 0, NULL, ACT(CORRUPT_STACK,EXIT) },
68 { "warn-corrupt-stack", 0, NULL, ACT(CORRUPT_STACK,WARN) },
69 { "ignore-corrupt-stack", 0, NULL, ACT(CORRUPT_STACK,IGNORE) },
70 { 0, 0, 0, 0 }
71 };
72
73 static void
74 done (int exit_code)
75 {
76 if (verbose)
77 {
78 stack_heap_stats ();
79 mem_usage_stats ();
80 /* Only use comma separated numbers when being very verbose.
81 Comma separated numbers are hard to parse in awk scripts. */
82 if (verbose > 1)
83 printf ("insns: %14s\n", comma (rx_cycles));
84 else
85 printf ("insns: %u\n", rx_cycles);
86
87 pipeline_stats ();
88 }
89 exit (exit_code);
90 }
91
92 int
93 main (int argc, char **argv)
94 {
95 int o;
96 int save_trace;
97 bfd *prog;
98 int rc;
99
100 /* By default, we exit when an execution error occurs. */
101 execution_error_init_standalone ();
102
103 while ((o = getopt_long (argc, argv, "tvdeEwi", sim_options, NULL)) != -1)
104 {
105 if (o == 'E')
106 /* Stop processing the command line. This is so that any remaining
107 words on the command line that look like arguments will be passed
108 on to the program being simulated. */
109 break;
110
111 if (o >= OPT_ACT)
112 {
113 int e, a;
114
115 o -= OPT_ACT;
116 e = o / SIM_ERRACTION_NUM_ACTIONS;
117 a = o % SIM_ERRACTION_NUM_ACTIONS;
118 execution_error_set_action (e, a);
119 }
120 else switch (o)
121 {
122 case 't':
123 trace++;
124 break;
125 case 'v':
126 verbose++;
127 break;
128 case 'd':
129 disassemble++;
130 break;
131 case 'e':
132 execution_error_init_standalone ();
133 break;
134 case 'w':
135 execution_error_warn_all ();
136 break;
137 case 'i':
138 execution_error_ignore_all ();
139 break;
140 case '?':
141 {
142 int i;
143 fprintf (stderr,
144 "usage: run [options] program [arguments]\n");
145 fprintf (stderr,
146 "\t-v\t- increase verbosity.\n"
147 "\t-t\t- trace.\n"
148 "\t-d\t- disassemble.\n"
149 "\t-E\t- stop processing sim args\n"
150 "\t-e\t- exit on all execution errors.\n"
151 "\t-w\t- warn (do not exit) on all execution errors.\n"
152 "\t-i\t- ignore all execution errors.\n");
153 for (i=0; sim_options[i].name; i++)
154 fprintf (stderr, "\t--%s\n", sim_options[i].name);
155 exit (1);
156 }
157 }
158 }
159
160 prog = bfd_openr (argv[optind], 0);
161 if (!prog)
162 {
163 fprintf (stderr, "Can't read %s\n", argv[optind]);
164 exit (1);
165 }
166
167 if (!bfd_check_format (prog, bfd_object))
168 {
169 fprintf (stderr, "%s not a rx program\n", argv[optind]);
170 exit (1);
171 }
172
173 init_regs ();
174
175 rx_in_gdb = 0;
176 save_trace = trace;
177 trace = 0;
178 rx_load (prog);
179 trace = save_trace;
180
181 sim_disasm_init (prog);
182
183 enable_counting = verbose;
184
185 rc = setjmp (decode_jmp_buf);
186
187 if (rc == 0)
188 {
189 if (!trace && !disassemble)
190 {
191 /* This will longjmp to the above if an exception
192 happens. */
193 for (;;)
194 decode_opcode ();
195 }
196 else
197 while (1)
198 {
199
200 if (trace)
201 printf ("\n");
202
203 if (disassemble)
204 {
205 enable_counting = 0;
206 sim_disasm_one ();
207 enable_counting = verbose;
208 }
209
210 rc = decode_opcode ();
211
212 if (trace)
213 trace_register_changes ();
214 }
215 }
216
217 if (RX_HIT_BREAK (rc))
218 done (1);
219 else if (RX_EXITED (rc))
220 done (RX_EXIT_STATUS (rc));
221 else if (RX_STOPPED (rc))
222 {
223 if (verbose)
224 printf("Stopped on signal %d\n", RX_STOP_SIG (rc));
225 exit(1);
226 }
227 done (0);
228 exit (0);
229 }
This page took 0.040337 seconds and 4 git commands to generate.