2011-08-04 Pedro Alves <pedro@codesourcery.com>
[deliverable/binutils-gdb.git] / gdb / exceptions.c
CommitLineData
60250e8b
AC
1/* Exception (throw catch) mechanism, for GDB, the GNU debugger.
2
6aba47ca 3 Copyright (C) 1986, 1988, 1989, 1990, 1991, 1992, 1993, 1994, 1995, 1996,
0fb0cc75 4 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008,
7b6bb8da 5 2009, 2010, 2011 Free Software Foundation, Inc.
60250e8b
AC
6
7 This file is part of GDB.
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
a9762ec7 11 the Free Software Foundation; either version 3 of the License, or
60250e8b
AC
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
a9762ec7 20 along with this program. If not, see <http://www.gnu.org/licenses/>. */
60250e8b
AC
21
22#include "defs.h"
23#include "exceptions.h"
60250e8b
AC
24#include "breakpoint.h"
25#include "target.h"
26#include "inferior.h"
27#include "annotate.h"
28#include "ui-out.h"
29#include "gdb_assert.h"
db5f402d 30#include "gdb_string.h"
e06e2353 31#include "serial.h"
347bddb7 32#include "gdbthread.h"
60250e8b 33
7b871fab 34const struct gdb_exception exception_none = { 0, GDB_NO_ERROR, NULL };
c1043fc2 35
db5f402d
AC
36/* Possible catcher states. */
37enum catcher_state {
38 /* Initial state, a new catcher has just been created. */
39 CATCHER_CREATED,
40 /* The catch code is running. */
41 CATCHER_RUNNING,
42 CATCHER_RUNNING_1,
43 /* The catch code threw an exception. */
44 CATCHER_ABORTING
45};
46
47/* Possible catcher actions. */
48enum catcher_action {
49 CATCH_ITER,
50 CATCH_ITER_1,
51 CATCH_THROWING
52};
53
54struct catcher
55{
56 enum catcher_state state;
2a78bfb5 57 /* Jump buffer pointing back at the exception handler. */
6941d02a 58 EXCEPTIONS_SIGJMP_BUF buf;
8a076db9 59 /* Status buffer belonging to the exception handler. */
71fff37b 60 volatile struct gdb_exception *exception;
db5f402d
AC
61 /* Saved/current state. */
62 int mask;
db5f402d 63 struct cleanup *saved_cleanup_chain;
db5f402d
AC
64 /* Back link. */
65 struct catcher *prev;
66};
67
60250e8b 68/* Where to go for throw_exception(). */
db5f402d
AC
69static struct catcher *current_catcher;
70
6941d02a 71EXCEPTIONS_SIGJMP_BUF *
f9679975 72exceptions_state_mc_init (volatile struct gdb_exception *exception,
6941d02a 73 return_mask mask)
db5f402d
AC
74{
75 struct catcher *new_catcher = XZALLOC (struct catcher);
76
2a78bfb5
AC
77 /* Start with no exception, save it's address. */
78 exception->reason = 0;
7b871fab 79 exception->error = GDB_NO_ERROR;
2a78bfb5
AC
80 exception->message = NULL;
81 new_catcher->exception = exception;
82
db5f402d
AC
83 new_catcher->mask = mask;
84
db5f402d 85 /* Prevent error/quit during FUNC from calling cleanups established
0963b4bd 86 prior to here. */
db5f402d
AC
87 new_catcher->saved_cleanup_chain = save_cleanups ();
88
89 /* Push this new catcher on the top. */
90 new_catcher->prev = current_catcher;
91 current_catcher = new_catcher;
92 new_catcher->state = CATCHER_CREATED;
93
94 return &new_catcher->buf;
95}
96
97static void
98catcher_pop (void)
99{
100 struct catcher *old_catcher = current_catcher;
d7f9d729 101
db5f402d
AC
102 current_catcher = old_catcher->prev;
103
104 /* Restore the cleanup chain, the error/quit messages, and the uiout
0963b4bd 105 builder, to their original states. */
db5f402d
AC
106
107 restore_cleanups (old_catcher->saved_cleanup_chain);
108
db5f402d
AC
109 xfree (old_catcher);
110}
111
112/* Catcher state machine. Returns non-zero if the m/c should be run
113 again, zero if it should abort. */
114
6941d02a
AC
115static int
116exceptions_state_mc (enum catcher_action action)
db5f402d
AC
117{
118 switch (current_catcher->state)
119 {
120 case CATCHER_CREATED:
121 switch (action)
122 {
123 case CATCH_ITER:
124 /* Allow the code to run the catcher. */
125 current_catcher->state = CATCHER_RUNNING;
126 return 1;
127 default:
e2e0b3e5 128 internal_error (__FILE__, __LINE__, _("bad state"));
db5f402d
AC
129 }
130 case CATCHER_RUNNING:
131 switch (action)
132 {
133 case CATCH_ITER:
134 /* No error/quit has occured. Just clean up. */
135 catcher_pop ();
136 return 0;
137 case CATCH_ITER_1:
138 current_catcher->state = CATCHER_RUNNING_1;
139 return 1;
140 case CATCH_THROWING:
141 current_catcher->state = CATCHER_ABORTING;
142 /* See also throw_exception. */
143 return 1;
144 default:
e2e0b3e5 145 internal_error (__FILE__, __LINE__, _("bad switch"));
db5f402d
AC
146 }
147 case CATCHER_RUNNING_1:
148 switch (action)
149 {
150 case CATCH_ITER:
151 /* The did a "break" from the inner while loop. */
152 catcher_pop ();
153 return 0;
154 case CATCH_ITER_1:
155 current_catcher->state = CATCHER_RUNNING;
156 return 0;
157 case CATCH_THROWING:
158 current_catcher->state = CATCHER_ABORTING;
159 /* See also throw_exception. */
160 return 1;
161 default:
e2e0b3e5 162 internal_error (__FILE__, __LINE__, _("bad switch"));
db5f402d
AC
163 }
164 case CATCHER_ABORTING:
165 switch (action)
166 {
167 case CATCH_ITER:
168 {
71fff37b 169 struct gdb_exception exception = *current_catcher->exception;
d7f9d729 170
2a78bfb5 171 if (current_catcher->mask & RETURN_MASK (exception.reason))
db5f402d
AC
172 {
173 /* Exit normally if this catcher can handle this
174 exception. The caller analyses the func return
175 values. */
176 catcher_pop ();
177 return 0;
178 }
179 /* The caller didn't request that the event be caught,
180 relay the event to the next containing
0963b4bd 181 catch_errors(). */
db5f402d 182 catcher_pop ();
2a78bfb5 183 throw_exception (exception);
db5f402d
AC
184 }
185 default:
e2e0b3e5 186 internal_error (__FILE__, __LINE__, _("bad state"));
db5f402d
AC
187 }
188 default:
e2e0b3e5 189 internal_error (__FILE__, __LINE__, _("bad switch"));
db5f402d
AC
190 }
191}
60250e8b 192
6941d02a
AC
193int
194exceptions_state_mc_action_iter (void)
195{
196 return exceptions_state_mc (CATCH_ITER);
197}
198
199int
200exceptions_state_mc_action_iter_1 (void)
201{
202 return exceptions_state_mc (CATCH_ITER_1);
203}
204
2a78bfb5 205/* Return EXCEPTION to the nearest containing catch_errors(). */
60250e8b 206
c25c4a8b 207void
71fff37b 208throw_exception (struct gdb_exception exception)
60250e8b 209{
347bddb7
PA
210 struct thread_info *tp = NULL;
211
60250e8b
AC
212 quit_flag = 0;
213 immediate_quit = 0;
214
347bddb7 215 if (!ptid_equal (inferior_ptid, null_ptid))
e09875d4 216 tp = find_thread_ptid (inferior_ptid);
347bddb7 217
60250e8b
AC
218 /* Perhaps it would be cleaner to do this via the cleanup chain (not sure
219 I can think of a reason why that is vital, though). */
347bddb7 220 if (tp != NULL)
16c381f0 221 {
0963b4bd 222 /* Clear queued breakpoint commands. */
16c381f0
JK
223 bpstat_clear_actions (tp->control.stop_bpstat);
224 }
60250e8b
AC
225
226 disable_current_display ();
227 do_cleanups (ALL_CLEANUPS);
60250e8b 228
60250e8b
AC
229 /* Jump to the containing catch_errors() call, communicating REASON
230 to that call via setjmp's return value. Note that REASON can't
0963b4bd 231 be zero, by definition in defs.h. */
6941d02a 232 exceptions_state_mc (CATCH_THROWING);
2a78bfb5 233 *current_catcher->exception = exception;
6941d02a 234 EXCEPTIONS_SIGLONGJMP (current_catcher->buf, exception.reason);
2a78bfb5
AC
235}
236
6b1b7650
AC
237static char *last_message;
238
c25c4a8b 239void
315a522e 240deprecated_throw_reason (enum return_reason reason)
2a78bfb5 241{
71fff37b 242 struct gdb_exception exception;
d7f9d729 243
2a78bfb5
AC
244 memset (&exception, 0, sizeof exception);
245
246 exception.reason = reason;
247 switch (reason)
248 {
249 case RETURN_QUIT:
250 break;
251 case RETURN_ERROR:
252 exception.error = GENERIC_ERROR;
2a78bfb5
AC
253 break;
254 default:
e2e0b3e5 255 internal_error (__FILE__, __LINE__, _("bad switch"));
2a78bfb5
AC
256 }
257
258 throw_exception (exception);
60250e8b
AC
259}
260
6b1b7650 261static void
c6da7a6d 262print_flush (void)
6b1b7650 263{
e06e2353
AC
264 struct serial *gdb_stdout_serial;
265
c6da7a6d
AC
266 if (deprecated_error_begin_hook)
267 deprecated_error_begin_hook ();
268 target_terminal_ours ();
e06e2353
AC
269
270 /* We want all output to appear now, before we print the error. We
271 have 3 levels of buffering we have to flush (it's possible that
272 some of these should be changed to flush the lower-level ones
273 too): */
274
275 /* 1. The _filtered buffer. */
276 wrap_here ("");
277
278 /* 2. The stdio buffer. */
c6da7a6d 279 gdb_flush (gdb_stdout);
e06e2353
AC
280 gdb_flush (gdb_stderr);
281
282 /* 3. The system-level buffer. */
283 gdb_stdout_serial = serial_fdopen (1);
cade9e54
PB
284 if (gdb_stdout_serial)
285 {
286 serial_drain_output (gdb_stdout_serial);
287 serial_un_fdopen (gdb_stdout_serial);
288 }
e06e2353 289
c6da7a6d 290 annotate_error_begin ();
6b1b7650
AC
291}
292
9cbc821d 293static void
71fff37b 294print_exception (struct ui_file *file, struct gdb_exception e)
9cbc821d
AC
295{
296 /* KLUGE: cagney/2005-01-13: Write the string out one line at a time
297 as that way the MI's behavior is preserved. */
298 const char *start;
299 const char *end;
d7f9d729 300
9cbc821d
AC
301 for (start = e.message; start != NULL; start = end)
302 {
303 end = strchr (start, '\n');
304 if (end == NULL)
305 fputs_filtered (start, file);
306 else
307 {
308 end++;
309 ui_file_write (file, start, end - start);
310 }
311 }
c6da7a6d 312 fprintf_filtered (file, "\n");
e48f5bee
AC
313
314 /* Now append the annotation. */
315 switch (e.reason)
316 {
317 case RETURN_QUIT:
318 annotate_quit ();
319 break;
320 case RETURN_ERROR:
321 /* Assume that these are all errors. */
322 annotate_error ();
323 break;
324 default:
325 internal_error (__FILE__, __LINE__, _("Bad switch."));
326 }
9cbc821d
AC
327}
328
8a076db9 329void
71fff37b 330exception_print (struct ui_file *file, struct gdb_exception e)
8a076db9
AC
331{
332 if (e.reason < 0 && e.message != NULL)
333 {
c6da7a6d 334 print_flush ();
9cbc821d 335 print_exception (file, e);
9cbc821d
AC
336 }
337}
8a076db9 338
9cbc821d 339void
71fff37b 340exception_fprintf (struct ui_file *file, struct gdb_exception e,
9cbc821d
AC
341 const char *prefix, ...)
342{
343 if (e.reason < 0 && e.message != NULL)
344 {
345 va_list args;
c6da7a6d
AC
346
347 print_flush ();
9cbc821d
AC
348
349 /* Print the prefix. */
350 va_start (args, prefix);
351 vfprintf_filtered (file, prefix, args);
352 va_end (args);
353
354 print_exception (file, e);
8a076db9
AC
355 }
356}
357
2c0b251b 358static void
e48f5bee 359print_any_exception (struct ui_file *file, const char *prefix,
71fff37b 360 struct gdb_exception e)
e48f5bee
AC
361{
362 if (e.reason < 0 && e.message != NULL)
363 {
364 target_terminal_ours ();
0963b4bd 365 wrap_here (""); /* Force out any buffered output. */
e48f5bee
AC
366 gdb_flush (gdb_stdout);
367 annotate_error_begin ();
368
369 /* Print the prefix. */
370 if (prefix != NULL && prefix[0] != '\0')
371 fputs_filtered (prefix, file);
372 print_exception (file, e);
373 }
374}
375
c25c4a8b 376static void ATTRIBUTE_NORETURN ATTRIBUTE_PRINTF (3, 0)
3af1e0e3
AC
377throw_it (enum return_reason reason, enum errors error, const char *fmt,
378 va_list ap)
6b1b7650 379{
71fff37b 380 struct gdb_exception e;
17d92a02 381 char *new_message;
6b1b7650 382
17d92a02
AC
383 /* Save the message. Create the new message before deleting the
384 old, the new message may include the old message text. */
385 new_message = xstrvprintf (fmt, ap);
6b1b7650 386 xfree (last_message);
17d92a02 387 last_message = new_message;
c6da7a6d
AC
388
389 /* Create the exception. */
390 e.reason = reason;
391 e.error = error;
392 e.message = last_message;
6b1b7650 393
6b1b7650 394 /* Throw the exception. */
6b1b7650
AC
395 throw_exception (e);
396}
397
c25c4a8b 398void
6b1b7650
AC
399throw_verror (enum errors error, const char *fmt, va_list ap)
400{
3af1e0e3 401 throw_it (RETURN_ERROR, error, fmt, ap);
6b1b7650
AC
402}
403
c25c4a8b 404void
6b1b7650
AC
405throw_vfatal (const char *fmt, va_list ap)
406{
7b871fab 407 throw_it (RETURN_QUIT, GDB_NO_ERROR, fmt, ap);
6b1b7650
AC
408}
409
c25c4a8b 410void
05ff989b 411throw_error (enum errors error, const char *fmt, ...)
6b1b7650 412{
05ff989b 413 va_list args;
d7f9d729 414
05ff989b 415 va_start (args, fmt);
3af1e0e3 416 throw_it (RETURN_ERROR, error, fmt, args);
05ff989b 417 va_end (args);
6b1b7650
AC
418}
419
787274f0
DE
420/* Call FUNC(UIOUT, FUNC_ARGS) but wrapped within an exception
421 handler. If an exception (enum return_reason) is thrown using
422 throw_exception() than all cleanups installed since
423 catch_exceptions() was entered are invoked, the (-ve) exception
424 value is then returned by catch_exceptions. If FUNC() returns
425 normally (with a positive or zero return value) then that value is
426 returned by catch_exceptions(). It is an internal_error() for
427 FUNC() to return a negative value.
428
429 See exceptions.h for further usage details.
60250e8b
AC
430
431 Must not be called with immediate_quit in effect (bad things might
432 happen, say we got a signal in the middle of a memcpy to quit_return).
433 This is an OK restriction; with very few exceptions immediate_quit can
787274f0 434 be replaced by judicious use of QUIT. */
60250e8b
AC
435
436/* MAYBE: cagney/1999-11-05: catch_errors() in conjunction with
7a9dd1b2 437 error() et al. could maintain a set of flags that indicate the
60250e8b
AC
438 current state of each of the longjmp buffers. This would give the
439 longjmp code the chance to detect a longjmp botch (before it gets
440 to longjmperror()). Prior to 1999-11-05 this wasn't possible as
441 code also randomly used a SET_TOP_LEVEL macro that directly
0963b4bd 442 initialized the longjmp buffers. */
60250e8b 443
60250e8b
AC
444int
445catch_exceptions (struct ui_out *uiout,
446 catch_exceptions_ftype *func,
447 void *func_args,
60250e8b
AC
448 return_mask mask)
449{
1c3c7ee7 450 return catch_exceptions_with_msg (uiout, func, func_args, NULL, mask);
60250e8b
AC
451}
452
453int
f9679975 454catch_exceptions_with_msg (struct ui_out *func_uiout,
60250e8b
AC
455 catch_exceptions_ftype *func,
456 void *func_args,
60250e8b
AC
457 char **gdberrmsg,
458 return_mask mask)
459{
71fff37b 460 volatile struct gdb_exception exception;
2a78bfb5 461 volatile int val = 0;
f9679975 462 struct ui_out *saved_uiout;
d7f9d729 463
f9679975 464 /* Save and override the global ``struct ui_out'' builder. */
79a45e25
PA
465 saved_uiout = current_uiout;
466 current_uiout = func_uiout;
f9679975
PA
467
468 TRY_CATCH (exception, RETURN_MASK_ALL)
6941d02a 469 {
79a45e25 470 val = (*func) (current_uiout, func_args);
6941d02a 471 }
f9679975
PA
472
473 /* Restore the global builder. */
79a45e25 474 current_uiout = saved_uiout;
f9679975
PA
475
476 if (exception.reason < 0 && (mask & RETURN_MASK (exception.reason)) == 0)
477 {
478 /* The caller didn't request that the event be caught.
479 Rethrow. */
480 throw_exception (exception);
481 }
482
e48f5bee 483 print_any_exception (gdb_stderr, NULL, exception);
60250e8b 484 gdb_assert (val >= 0);
2a78bfb5
AC
485 gdb_assert (exception.reason <= 0);
486 if (exception.reason < 0)
487 {
488 /* If caller wants a copy of the low-level error message, make
489 one. This is used in the case of a silent error whereby the
490 caller may optionally want to issue the message. */
491 if (gdberrmsg != NULL)
6b1b7650
AC
492 {
493 if (exception.message != NULL)
494 *gdberrmsg = xstrdup (exception.message);
495 else
496 *gdberrmsg = NULL;
497 }
2a78bfb5
AC
498 return exception.reason;
499 }
60250e8b
AC
500 return val;
501}
502
787274f0
DE
503/* This function is superseded by catch_exceptions(). */
504
60250e8b
AC
505int
506catch_errors (catch_errors_ftype *func, void *func_args, char *errstring,
507 return_mask mask)
508{
2a78bfb5 509 volatile int val = 0;
71fff37b 510 volatile struct gdb_exception exception;
f9679975 511 struct ui_out *saved_uiout;
d7f9d729 512
f9679975 513 /* Save the global ``struct ui_out'' builder. */
79a45e25 514 saved_uiout = current_uiout;
f9679975
PA
515
516 TRY_CATCH (exception, RETURN_MASK_ALL)
6941d02a
AC
517 {
518 val = func (func_args);
519 }
f9679975
PA
520
521 /* Restore the global builder. */
79a45e25 522 current_uiout = saved_uiout;
f9679975
PA
523
524 if (exception.reason < 0 && (mask & RETURN_MASK (exception.reason)) == 0)
525 {
526 /* The caller didn't request that the event be caught.
527 Rethrow. */
528 throw_exception (exception);
529 }
530
e48f5bee 531 print_any_exception (gdb_stderr, errstring, exception);
2a78bfb5 532 if (exception.reason != 0)
60250e8b
AC
533 return 0;
534 return val;
535}
536
60250e8b
AC
537int
538catch_command_errors (catch_command_errors_ftype * command,
539 char *arg, int from_tty, return_mask mask)
540{
71fff37b 541 volatile struct gdb_exception e;
d7f9d729 542
6941d02a
AC
543 TRY_CATCH (e, mask)
544 {
545 command (arg, from_tty);
546 }
5a14cc1a
AC
547 print_any_exception (gdb_stderr, NULL, e);
548 if (e.reason < 0)
549 return 0;
550 return 1;
60250e8b 551}
This page took 0.575923 seconds and 4 git commands to generate.