]> git.ipfire.org Git - thirdparty/binutils-gdb.git/blame - sim/common/run.c
sim:
[thirdparty/binutils-gdb.git] / sim / common / run.c
CommitLineData
c906108c 1/* run front end support for all the simulators.
6aba47ca 2 Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001,
9b254dd1 3 2002, 2003, 2004, 2007, 2008 Free Software Foundation, Inc.
c906108c
SS
4
5This program is free software; you can redistribute it and/or modify
6it under the terms of the GNU General Public License as published by
4744ac1b
JB
7the Free Software Foundation; either version 3 of the License, or
8(at your option) any later version.
c906108c
SS
9
10This program is distributed in the hope that it will be useful,
11but WITHOUT ANY WARRANTY; without even the implied warranty of
12MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13GNU General Public License for more details.
14
4744ac1b
JB
15You should have received a copy of the GNU General Public License
16along with this program. If not, see <http://www.gnu.org/licenses/>. */
c906108c
SS
17
18/* Steve Chamberlain sac@cygnus.com,
19 and others at Cygnus. */
20
41ee5402
DJ
21#ifdef HAVE_CONFIG_H
22#include "cconfig.h"
c906108c 23#include "tconfig.h"
41ee5402 24#endif
c906108c
SS
25
26#include <signal.h>
27#include <stdio.h>
28#ifdef __STDC__
29#include <stdarg.h>
30#else
31#include <varargs.h>
32#endif
33
34#ifdef HAVE_STDLIB_H
35#include <stdlib.h>
36#endif
37
38#ifdef HAVE_STRING_H
39#include <string.h>
40#else
41#ifdef HAVE_STRINGS_H
42#include <strings.h>
43#endif
44#endif
45
46#include "libiberty.h"
47#include "bfd.h"
3c25f8c7
AC
48#include "gdb/callback.h"
49#include "gdb/remote-sim.h"
6d358e86 50#include "ansidecl.h"
de4112fa 51#include "run-sim.h"
6efef468 52#include "version.h"
c906108c 53
6efef468
JM
54static void usage PARAMS ((int help));
55static void print_version PARAMS ((void));
c906108c
SS
56extern int optind;
57extern char *optarg;
58
59extern host_callback default_callback;
60
61static char *myname;
62
c906108c
SS
63extern int getopt ();
64
7a292a7a 65#ifdef NEED_UI_LOOP_HOOK
dbec3bef 66/* Gdb foolery. This is only needed for gdb using a gui. */
0aaa4a81 67int (*deprecated_ui_loop_hook) PARAMS ((int signo));
7a292a7a
SS
68#endif
69
c906108c
SS
70static SIM_DESC sd;
71
72static RETSIGTYPE
6d358e86 73cntrl_c (int sig ATTRIBUTE_UNUSED)
c906108c
SS
74{
75 if (! sim_stop (sd))
76 {
77 fprintf (stderr, "Quit!\n");
78 exit (1);
79 }
80}
81
82int
83main (ac, av)
84 int ac;
85 char **av;
86{
87 RETSIGTYPE (*prev_sigint) ();
88 bfd *abfd;
89 int i;
90 int verbose = 0;
91 int trace = 0;
baa7ae6f
AC
92#ifdef SIM_HAVE_ENVIRONMENT
93 int operating_p = 0;
94#endif
c906108c
SS
95 char *name;
96 static char *no_args[4];
97 char **sim_argv = &no_args[0];
98 char **prog_args;
99 enum sim_stop reason;
100 int sigrc;
101
102 myname = av[0] + strlen (av[0]);
103 while (myname > av[0] && myname[-1] != '/')
104 --myname;
105
106 /* The first element of sim_open's argv is the program name. */
107 no_args[0] = av[0];
108#ifdef SIM_HAVE_BIENDIAN
109 no_args[1] = "-E";
110 no_args[2] = "set-later";
111#endif
112
113 /* FIXME: This is currently being migrated into sim_open.
114 Simulators that use functions such as sim_size() still require
dbec3bef 115 this. */
c906108c
SS
116 default_callback.init (&default_callback);
117 sim_set_callbacks (&default_callback);
118
de4112fa
NC
119#ifdef SIM_TARGET_SWITCHES
120 ac = sim_target_parse_command_line (ac, av);
121#endif
122
6efef468
JM
123 for (i = 1; av[i]; ++i)
124 {
125 if (strcmp (av[i], "--help") == 0)
126 {
127 usage (1);
128 }
129 else if (strcmp (av[i], "--version") == 0)
130 {
131 print_version ();
132 return 0;
133 }
134 }
135
c906108c
SS
136 /* FIXME: This is currently being rewritten to have each simulator
137 do all argv processing. */
138
dbec3bef 139 while ((i = getopt (ac, av, "a:c:m:op:s:tv")) != EOF)
c906108c
SS
140 switch (i)
141 {
142 case 'a':
143 /* FIXME: Temporary hack. */
144 {
145 int len = strlen (av[0]) + strlen (optarg);
146 char *argbuf = (char *) alloca (len + 2 + 50);
147 sprintf (argbuf, "%s %s", av[0], optarg);
148#ifdef SIM_HAVE_BIENDIAN
149 /* The desired endianness must be passed to sim_open.
150 The value for "set-later" is set when we know what it is.
151 -E support isn't yet part of the published interface. */
152 strcat (argbuf, " -E set-later");
153#endif
154 sim_argv = buildargv (argbuf);
155 }
156 break;
157#ifdef SIM_HAVE_SIMCACHE
158 case 'c':
159 sim_set_simcache_size (atoi (optarg));
160 break;
161#endif
162 case 'm':
163 /* FIXME: Rename to sim_set_mem_size. */
164 sim_size (atoi (optarg));
165 break;
baa7ae6f
AC
166#ifdef SIM_HAVE_ENVIRONMENT
167 case 'o':
168 /* Operating enironment where any signals are delivered to the
dbec3bef 169 target. */
baa7ae6f
AC
170 operating_p = 1;
171 break;
d25b1553 172#endif
c906108c
SS
173#ifdef SIM_HAVE_PROFILE
174 case 'p':
175 sim_set_profile (atoi (optarg));
176 break;
177 case 's':
178 sim_set_profile_size (atoi (optarg));
179 break;
180#endif
181 case 't':
182 trace = 1;
c906108c
SS
183 break;
184 case 'v':
185 /* Things that are printed with -v are the kinds of things that
186 gcc -v prints. This is not meant to include detailed tracing
187 or debugging information, just summaries. */
188 verbose = 1;
189 /* sim_set_verbose (1); */
190 break;
191 /* FIXME: Quick hack, to be replaced by more general facility. */
c906108c 192 default:
6efef468 193 usage (0);
c906108c
SS
194 }
195
196 ac -= optind;
197 av += optind;
198 if (ac <= 0)
6efef468 199 usage (0);
c906108c
SS
200
201 name = *av;
202 prog_args = av;
203
204 if (verbose)
205 {
206 printf ("%s %s\n", myname, name);
207 }
208
209 abfd = bfd_openr (name, 0);
dbec3bef 210 if (!abfd)
c906108c 211 {
dbec3bef 212 fprintf (stderr, "%s: can't open %s: %s\n",
c906108c
SS
213 myname, name, bfd_errmsg (bfd_get_error ()));
214 exit (1);
215 }
216
217 if (!bfd_check_format (abfd, bfd_object))
218 {
219 fprintf (stderr, "%s: can't load %s: %s\n",
220 myname, name, bfd_errmsg (bfd_get_error ()));
221 exit (1);
222 }
223
224#ifdef SIM_HAVE_BIENDIAN
225 /* The endianness must be passed to sim_open because one may wish to
226 examine/set registers before calling sim_load [which is the other
227 place where one can determine endianness]. We previously passed the
228 endianness via global `target_byte_order' but that's not a clean
229 interface. */
230 for (i = 1; sim_argv[i + 1] != NULL; ++i)
231 continue;
232 if (bfd_big_endian (abfd))
233 sim_argv[i] = "big";
234 else
235 sim_argv[i] = "little";
236#endif
237
238 /* Ensure that any run-time initialisation that needs to be
dbec3bef 239 performed by the simulator can occur. */
c906108c
SS
240 sd = sim_open (SIM_OPEN_STANDALONE, &default_callback, abfd, sim_argv);
241 if (sd == 0)
242 exit (1);
243
244 if (sim_load (sd, name, abfd, 0) == SIM_RC_FAIL)
245 exit (1);
246
247 if (sim_create_inferior (sd, abfd, prog_args, NULL) == SIM_RC_FAIL)
248 exit (1);
249
baa7ae6f
AC
250#ifdef SIM_HAVE_ENVIRONMENT
251 /* NOTE: An old simulator supporting the operating environment MUST
252 provide sim_set_trace() and not sim_trace(). That way
dbec3bef 253 sim_stop_reason() can be used to determine any stop reason. */
baa7ae6f
AC
254 if (trace)
255 sim_set_trace ();
781c552e 256 sigrc = 0;
baa7ae6f
AC
257 do
258 {
259 prev_sigint = signal (SIGINT, cntrl_c);
260 sim_resume (sd, 0, sigrc);
261 signal (SIGINT, prev_sigint);
262 sim_stop_reason (sd, &reason, &sigrc);
263 }
264 while (operating_p && reason == sim_stopped && sigrc != SIGINT);
265#else
c906108c
SS
266 if (trace)
267 {
268 int done = 0;
7fc5b5ad 269 prev_sigint = signal (SIGINT, cntrl_c);
c906108c
SS
270 while (!done)
271 {
272 done = sim_trace (sd);
273 }
7fc5b5ad 274 signal (SIGINT, prev_sigint);
baa7ae6f 275 sim_stop_reason (sd, &reason, &sigrc);
c906108c
SS
276 }
277 else
278 {
baa7ae6f 279 prev_sigint = signal (SIGINT, cntrl_c);
781c552e 280 sigrc = 0;
baa7ae6f
AC
281 sim_resume (sd, 0, sigrc);
282 signal (SIGINT, prev_sigint);
283 sim_stop_reason (sd, &reason, &sigrc);
c906108c 284 }
baa7ae6f 285#endif
c906108c
SS
286
287 if (verbose)
288 sim_info (sd, 0);
c906108c
SS
289 sim_close (sd, 0);
290
291 /* If reason is sim_exited, then sigrc holds the exit code which we want
292 to return. If reason is sim_stopped or sim_signalled, then sigrc holds
293 the signal that the simulator received; we want to return that to
294 indicate failure. */
295
c906108c
SS
296 /* Why did we stop? */
297 switch (reason)
298 {
299 case sim_signalled:
300 case sim_stopped:
301 if (sigrc != 0)
dbec3bef 302 fprintf (stderr, "program stopped with signal %d.\n", sigrc);
c906108c
SS
303 break;
304
305 case sim_exited:
306 break;
307
308 case sim_running:
dbec3bef 309 case sim_polling: /* These indicate a serious problem. */
c906108c
SS
310 abort ();
311 break;
312
313 }
c906108c
SS
314
315 return sigrc;
316}
317
318static void
6efef468 319usage (int help)
c906108c 320{
6efef468
JM
321 FILE *stream = help ? stdout : stderr;
322
323 fprintf (stream, "Usage: %s [options] program [program args]\n", myname);
324 fprintf (stream, "Options:\n");
325 fprintf (stream, "-a args Pass `args' to simulator.\n");
c906108c 326#ifdef SIM_HAVE_SIMCACHE
6efef468 327 fprintf (stream, "-c size Set simulator cache size to `size'.\n");
c906108c 328#endif
6efef468 329 fprintf (stream, "-m size Set memory size of simulator, in bytes.\n");
baa7ae6f 330#ifdef SIM_HAVE_ENVIRONMENT
6efef468 331 fprintf (stream, "-o Select operating (kernel) environment.\n");
baa7ae6f 332#endif
c906108c 333#ifdef SIM_HAVE_PROFILE
6efef468
JM
334 fprintf (stream, "-p freq Set profiling frequency.\n");
335 fprintf (stream, "-s size Set profiling size.\n");
c906108c 336#endif
6efef468
JM
337 fprintf (stream, "-t Perform instruction tracing.\n");
338 fprintf (stream, " Note: Very few simulators support tracing.\n");
339 fprintf (stream, "-v Verbose output.\n");
340 fprintf (stream, "\n");
341 fprintf (stream, "program args Arguments to pass to simulated program.\n");
342 fprintf (stream, " Note: Very few simulators support this.\n");
de4112fa 343#ifdef SIM_TARGET_SWITCHES
6efef468
JM
344 fprintf (stream, "\nTarget specific options:\n");
345 sim_target_display_usage (help);
de4112fa 346#endif
6efef468
JM
347
348 if (help && REPORT_BUGS_TO[0])
349 printf ("Report bugs to %s\n", REPORT_BUGS_TO);
350
351 exit (help ? 0 : 1);
352}
353
354static void
355print_version ()
356{
357 printf ("GNU simulator %s%s\n", PKGVERSION, version);
c906108c 358}