1*5796c8dcSSimon Schubert /* Exception (throw catch) mechanism, for GDB, the GNU debugger. 2*5796c8dcSSimon Schubert 3*5796c8dcSSimon Schubert Copyright (C) 1986, 1988, 1989, 1990, 1991, 1992, 1993, 1994, 1995, 1996, 4*5796c8dcSSimon Schubert 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 5*5796c8dcSSimon Schubert 2009 Free Software Foundation, Inc. 6*5796c8dcSSimon Schubert 7*5796c8dcSSimon Schubert This file is part of GDB. 8*5796c8dcSSimon Schubert 9*5796c8dcSSimon Schubert This program is free software; you can redistribute it and/or modify 10*5796c8dcSSimon Schubert it under the terms of the GNU General Public License as published by 11*5796c8dcSSimon Schubert the Free Software Foundation; either version 3 of the License, or 12*5796c8dcSSimon Schubert (at your option) any later version. 13*5796c8dcSSimon Schubert 14*5796c8dcSSimon Schubert This program is distributed in the hope that it will be useful, 15*5796c8dcSSimon Schubert but WITHOUT ANY WARRANTY; without even the implied warranty of 16*5796c8dcSSimon Schubert MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17*5796c8dcSSimon Schubert GNU General Public License for more details. 18*5796c8dcSSimon Schubert 19*5796c8dcSSimon Schubert You should have received a copy of the GNU General Public License 20*5796c8dcSSimon Schubert along with this program. If not, see <http://www.gnu.org/licenses/>. */ 21*5796c8dcSSimon Schubert 22*5796c8dcSSimon Schubert #ifndef EXCEPTIONS_H 23*5796c8dcSSimon Schubert #define EXCEPTIONS_H 24*5796c8dcSSimon Schubert 25*5796c8dcSSimon Schubert #include "ui-out.h" 26*5796c8dcSSimon Schubert #include <setjmp.h> 27*5796c8dcSSimon Schubert 28*5796c8dcSSimon Schubert /* Reasons for calling throw_exceptions(). NOTE: all reason values 29*5796c8dcSSimon Schubert must be less than zero. enum value 0 is reserved for internal use 30*5796c8dcSSimon Schubert as the return value from an initial setjmp(). The function 31*5796c8dcSSimon Schubert catch_exceptions() reserves values >= 0 as legal results from its 32*5796c8dcSSimon Schubert wrapped function. */ 33*5796c8dcSSimon Schubert 34*5796c8dcSSimon Schubert enum return_reason 35*5796c8dcSSimon Schubert { 36*5796c8dcSSimon Schubert /* User interrupt. */ 37*5796c8dcSSimon Schubert RETURN_QUIT = -2, 38*5796c8dcSSimon Schubert /* Any other error. */ 39*5796c8dcSSimon Schubert RETURN_ERROR 40*5796c8dcSSimon Schubert }; 41*5796c8dcSSimon Schubert 42*5796c8dcSSimon Schubert #define RETURN_MASK(reason) (1 << (int)(-reason)) 43*5796c8dcSSimon Schubert #define RETURN_MASK_QUIT RETURN_MASK (RETURN_QUIT) 44*5796c8dcSSimon Schubert #define RETURN_MASK_ERROR RETURN_MASK (RETURN_ERROR) 45*5796c8dcSSimon Schubert #define RETURN_MASK_ALL (RETURN_MASK_QUIT | RETURN_MASK_ERROR) 46*5796c8dcSSimon Schubert typedef int return_mask; 47*5796c8dcSSimon Schubert 48*5796c8dcSSimon Schubert /* Describe all exceptions. */ 49*5796c8dcSSimon Schubert 50*5796c8dcSSimon Schubert enum errors { 51*5796c8dcSSimon Schubert GDB_NO_ERROR, 52*5796c8dcSSimon Schubert /* Any generic error, the corresponding text is in 53*5796c8dcSSimon Schubert exception.message. */ 54*5796c8dcSSimon Schubert GENERIC_ERROR, 55*5796c8dcSSimon Schubert NOT_FOUND_ERROR, 56*5796c8dcSSimon Schubert 57*5796c8dcSSimon Schubert /* Thread library lacks support necessary for finding thread local 58*5796c8dcSSimon Schubert storage. */ 59*5796c8dcSSimon Schubert TLS_NO_LIBRARY_SUPPORT_ERROR, 60*5796c8dcSSimon Schubert 61*5796c8dcSSimon Schubert /* Load module not found while attempting to find thread local storage. */ 62*5796c8dcSSimon Schubert TLS_LOAD_MODULE_NOT_FOUND_ERROR, 63*5796c8dcSSimon Schubert 64*5796c8dcSSimon Schubert /* Thread local storage has not been allocated yet. */ 65*5796c8dcSSimon Schubert TLS_NOT_ALLOCATED_YET_ERROR, 66*5796c8dcSSimon Schubert 67*5796c8dcSSimon Schubert /* Something else went wrong while attempting to find thread local 68*5796c8dcSSimon Schubert storage. The ``struct gdb_exception'' message field provides 69*5796c8dcSSimon Schubert more detail. */ 70*5796c8dcSSimon Schubert TLS_GENERIC_ERROR, 71*5796c8dcSSimon Schubert 72*5796c8dcSSimon Schubert /* Problem parsing an XML document. */ 73*5796c8dcSSimon Schubert XML_PARSE_ERROR, 74*5796c8dcSSimon Schubert 75*5796c8dcSSimon Schubert /* Error accessing memory. */ 76*5796c8dcSSimon Schubert MEMORY_ERROR, 77*5796c8dcSSimon Schubert 78*5796c8dcSSimon Schubert /* Add more errors here. */ 79*5796c8dcSSimon Schubert NR_ERRORS 80*5796c8dcSSimon Schubert }; 81*5796c8dcSSimon Schubert 82*5796c8dcSSimon Schubert struct gdb_exception 83*5796c8dcSSimon Schubert { 84*5796c8dcSSimon Schubert enum return_reason reason; 85*5796c8dcSSimon Schubert enum errors error; 86*5796c8dcSSimon Schubert const char *message; 87*5796c8dcSSimon Schubert }; 88*5796c8dcSSimon Schubert 89*5796c8dcSSimon Schubert /* A pre-defined non-exception. */ 90*5796c8dcSSimon Schubert extern const struct gdb_exception exception_none; 91*5796c8dcSSimon Schubert 92*5796c8dcSSimon Schubert /* Wrap set/long jmp so that it's more portable (internal to 93*5796c8dcSSimon Schubert exceptions). */ 94*5796c8dcSSimon Schubert 95*5796c8dcSSimon Schubert #if defined(HAVE_SIGSETJMP) 96*5796c8dcSSimon Schubert #define EXCEPTIONS_SIGJMP_BUF sigjmp_buf 97*5796c8dcSSimon Schubert #define EXCEPTIONS_SIGSETJMP(buf) sigsetjmp((buf), 1) 98*5796c8dcSSimon Schubert #define EXCEPTIONS_SIGLONGJMP(buf,val) siglongjmp((buf), (val)) 99*5796c8dcSSimon Schubert #else 100*5796c8dcSSimon Schubert #define EXCEPTIONS_SIGJMP_BUF jmp_buf 101*5796c8dcSSimon Schubert #define EXCEPTIONS_SIGSETJMP(buf) setjmp(buf) 102*5796c8dcSSimon Schubert #define EXCEPTIONS_SIGLONGJMP(buf,val) longjmp((buf), (val)) 103*5796c8dcSSimon Schubert #endif 104*5796c8dcSSimon Schubert 105*5796c8dcSSimon Schubert /* Functions to drive the exceptions state m/c (internal to 106*5796c8dcSSimon Schubert exceptions). */ 107*5796c8dcSSimon Schubert EXCEPTIONS_SIGJMP_BUF *exceptions_state_mc_init (struct ui_out *func_uiout, 108*5796c8dcSSimon Schubert volatile struct gdb_exception * 109*5796c8dcSSimon Schubert exception, 110*5796c8dcSSimon Schubert return_mask mask); 111*5796c8dcSSimon Schubert int exceptions_state_mc_action_iter (void); 112*5796c8dcSSimon Schubert int exceptions_state_mc_action_iter_1 (void); 113*5796c8dcSSimon Schubert 114*5796c8dcSSimon Schubert /* Macro to wrap up standard try/catch behavior. 115*5796c8dcSSimon Schubert 116*5796c8dcSSimon Schubert The double loop lets us correctly handle code "break"ing out of the 117*5796c8dcSSimon Schubert try catch block. (It works as the "break" only exits the inner 118*5796c8dcSSimon Schubert "while" loop, the outer for loop detects this handling it 119*5796c8dcSSimon Schubert correctly.) Of course "return" and "goto" are not so lucky. 120*5796c8dcSSimon Schubert 121*5796c8dcSSimon Schubert For instance: 122*5796c8dcSSimon Schubert 123*5796c8dcSSimon Schubert *INDENT-OFF* 124*5796c8dcSSimon Schubert 125*5796c8dcSSimon Schubert volatile struct gdb_exception e; 126*5796c8dcSSimon Schubert TRY_CATCH (e, RETURN_MASK_ERROR) 127*5796c8dcSSimon Schubert { 128*5796c8dcSSimon Schubert } 129*5796c8dcSSimon Schubert switch (e.reason) 130*5796c8dcSSimon Schubert { 131*5796c8dcSSimon Schubert case RETURN_ERROR: ... 132*5796c8dcSSimon Schubert } 133*5796c8dcSSimon Schubert 134*5796c8dcSSimon Schubert */ 135*5796c8dcSSimon Schubert 136*5796c8dcSSimon Schubert #define TRY_CATCH(EXCEPTION,MASK) \ 137*5796c8dcSSimon Schubert { \ 138*5796c8dcSSimon Schubert EXCEPTIONS_SIGJMP_BUF *buf = \ 139*5796c8dcSSimon Schubert exceptions_state_mc_init (uiout, &(EXCEPTION), (MASK)); \ 140*5796c8dcSSimon Schubert EXCEPTIONS_SIGSETJMP (*buf); \ 141*5796c8dcSSimon Schubert } \ 142*5796c8dcSSimon Schubert while (exceptions_state_mc_action_iter ()) \ 143*5796c8dcSSimon Schubert while (exceptions_state_mc_action_iter_1 ()) 144*5796c8dcSSimon Schubert 145*5796c8dcSSimon Schubert /* *INDENT-ON* */ 146*5796c8dcSSimon Schubert 147*5796c8dcSSimon Schubert 148*5796c8dcSSimon Schubert /* If E is an exception, print it's error message on the specified 149*5796c8dcSSimon Schubert stream. for _fprintf, prefix the message with PREFIX... */ 150*5796c8dcSSimon Schubert extern void exception_print (struct ui_file *file, struct gdb_exception e); 151*5796c8dcSSimon Schubert extern void exception_fprintf (struct ui_file *file, struct gdb_exception e, 152*5796c8dcSSimon Schubert const char *prefix, 153*5796c8dcSSimon Schubert ...) ATTR_FORMAT (printf, 3, 4); 154*5796c8dcSSimon Schubert 155*5796c8dcSSimon Schubert /* Throw an exception (as described by "struct gdb_exception"). Will 156*5796c8dcSSimon Schubert execute a LONG JUMP to the inner most containing exception handler 157*5796c8dcSSimon Schubert established using catch_exceptions() (or similar). 158*5796c8dcSSimon Schubert 159*5796c8dcSSimon Schubert Code normally throws an exception using error() et.al. For various 160*5796c8dcSSimon Schubert reaons, GDB also contains code that throws an exception directly. 161*5796c8dcSSimon Schubert For instance, the remote*.c targets contain CNTRL-C signal handlers 162*5796c8dcSSimon Schubert that propogate the QUIT event up the exception chain. ``This could 163*5796c8dcSSimon Schubert be a good thing or a dangerous thing.'' -- the Existential 164*5796c8dcSSimon Schubert Wombat. */ 165*5796c8dcSSimon Schubert 166*5796c8dcSSimon Schubert extern NORETURN void throw_exception (struct gdb_exception exception) ATTR_NORETURN; 167*5796c8dcSSimon Schubert extern NORETURN void throw_verror (enum errors, const char *fmt, va_list ap) 168*5796c8dcSSimon Schubert ATTR_NORETURN ATTR_FORMAT (printf, 2, 0); 169*5796c8dcSSimon Schubert extern NORETURN void throw_vfatal (const char *fmt, va_list ap) 170*5796c8dcSSimon Schubert ATTR_NORETURN ATTR_FORMAT (printf, 1, 0); 171*5796c8dcSSimon Schubert extern NORETURN void throw_error (enum errors error, const char *fmt, 172*5796c8dcSSimon Schubert ...) ATTR_NORETURN ATTR_FORMAT (printf, 2, 3); 173*5796c8dcSSimon Schubert 174*5796c8dcSSimon Schubert /* Instead of deprecated_throw_reason, code should use catch_exception 175*5796c8dcSSimon Schubert and throw_exception. */ 176*5796c8dcSSimon Schubert extern NORETURN void deprecated_throw_reason (enum return_reason reason) ATTR_NORETURN; 177*5796c8dcSSimon Schubert 178*5796c8dcSSimon Schubert /* Call FUNC(UIOUT, FUNC_ARGS) but wrapped within an exception 179*5796c8dcSSimon Schubert handler. If an exception (enum return_reason) is thrown using 180*5796c8dcSSimon Schubert throw_exception() than all cleanups installed since 181*5796c8dcSSimon Schubert catch_exceptions() was entered are invoked, the (-ve) exception 182*5796c8dcSSimon Schubert value is then returned by catch_exceptions. If FUNC() returns 183*5796c8dcSSimon Schubert normally (with a positive or zero return value) then that value is 184*5796c8dcSSimon Schubert returned by catch_exceptions(). It is an internal_error() for 185*5796c8dcSSimon Schubert FUNC() to return a negative value. 186*5796c8dcSSimon Schubert 187*5796c8dcSSimon Schubert For the period of the FUNC() call: UIOUT is installed as the output 188*5796c8dcSSimon Schubert builder; ERRSTRING is installed as the error/quit message; and a 189*5796c8dcSSimon Schubert new cleanup_chain is established. The old values are restored 190*5796c8dcSSimon Schubert before catch_exceptions() returns. 191*5796c8dcSSimon Schubert 192*5796c8dcSSimon Schubert The variant catch_exceptions_with_msg() is the same as 193*5796c8dcSSimon Schubert catch_exceptions() but adds the ability to return an allocated 194*5796c8dcSSimon Schubert copy of the gdb error message. This is used when a silent error is 195*5796c8dcSSimon Schubert issued and the caller wants to manually issue the error message. 196*5796c8dcSSimon Schubert 197*5796c8dcSSimon Schubert MASK specifies what to catch; it is normally set to 198*5796c8dcSSimon Schubert RETURN_MASK_ALL, if for no other reason than that the code which 199*5796c8dcSSimon Schubert calls catch_errors might not be set up to deal with a quit which 200*5796c8dcSSimon Schubert isn't caught. But if the code can deal with it, it generally 201*5796c8dcSSimon Schubert should be RETURN_MASK_ERROR, unless for some reason it is more 202*5796c8dcSSimon Schubert useful to abort only the portion of the operation inside the 203*5796c8dcSSimon Schubert catch_errors. Note that quit should return to the command line 204*5796c8dcSSimon Schubert fairly quickly, even if some further processing is being done. 205*5796c8dcSSimon Schubert 206*5796c8dcSSimon Schubert FIXME; cagney/2001-08-13: The need to override the global UIOUT 207*5796c8dcSSimon Schubert builder variable should just go away. 208*5796c8dcSSimon Schubert 209*5796c8dcSSimon Schubert This function supersedes catch_errors(). 210*5796c8dcSSimon Schubert 211*5796c8dcSSimon Schubert This function uses SETJMP() and LONGJUMP(). */ 212*5796c8dcSSimon Schubert 213*5796c8dcSSimon Schubert struct ui_out; 214*5796c8dcSSimon Schubert typedef int (catch_exceptions_ftype) (struct ui_out *ui_out, void *args); 215*5796c8dcSSimon Schubert extern int catch_exceptions (struct ui_out *uiout, 216*5796c8dcSSimon Schubert catch_exceptions_ftype *func, void *func_args, 217*5796c8dcSSimon Schubert return_mask mask); 218*5796c8dcSSimon Schubert typedef void (catch_exception_ftype) (struct ui_out *ui_out, void *args); 219*5796c8dcSSimon Schubert extern int catch_exceptions_with_msg (struct ui_out *uiout, 220*5796c8dcSSimon Schubert catch_exceptions_ftype *func, 221*5796c8dcSSimon Schubert void *func_args, 222*5796c8dcSSimon Schubert char **gdberrmsg, 223*5796c8dcSSimon Schubert return_mask mask); 224*5796c8dcSSimon Schubert 225*5796c8dcSSimon Schubert /* This function, in addition, suppresses the printing of the captured 226*5796c8dcSSimon Schubert error message. It's up to the client to print it. */ 227*5796c8dcSSimon Schubert 228*5796c8dcSSimon Schubert extern struct gdb_exception catch_exception (struct ui_out *uiout, 229*5796c8dcSSimon Schubert catch_exception_ftype *func, 230*5796c8dcSSimon Schubert void *func_args, 231*5796c8dcSSimon Schubert return_mask mask); 232*5796c8dcSSimon Schubert 233*5796c8dcSSimon Schubert /* If CATCH_ERRORS_FTYPE throws an error, catch_errors() returns zero 234*5796c8dcSSimon Schubert otherwize the result from CATCH_ERRORS_FTYPE is returned. It is 235*5796c8dcSSimon Schubert probably useful for CATCH_ERRORS_FTYPE to always return a non-zero 236*5796c8dcSSimon Schubert value. It's unfortunate that, catch_errors() does not return an 237*5796c8dcSSimon Schubert indication of the exact exception that it caught - quit_flag might 238*5796c8dcSSimon Schubert help. 239*5796c8dcSSimon Schubert 240*5796c8dcSSimon Schubert This function is superseded by catch_exceptions(). */ 241*5796c8dcSSimon Schubert 242*5796c8dcSSimon Schubert typedef int (catch_errors_ftype) (void *); 243*5796c8dcSSimon Schubert extern int catch_errors (catch_errors_ftype *, void *, char *, return_mask); 244*5796c8dcSSimon Schubert 245*5796c8dcSSimon Schubert /* Template to catch_errors() that wraps calls to command 246*5796c8dcSSimon Schubert functions. */ 247*5796c8dcSSimon Schubert 248*5796c8dcSSimon Schubert typedef void (catch_command_errors_ftype) (char *, int); 249*5796c8dcSSimon Schubert extern int catch_command_errors (catch_command_errors_ftype *func, char *command, int from_tty, return_mask); 250*5796c8dcSSimon Schubert 251*5796c8dcSSimon Schubert #endif 252