Skip to content

Commit

Permalink
Delete the function exit_fatal. Replace it with a new Parrot_x_panic_…
Browse files Browse the repository at this point in the history
…and_exit (may be renamed). Add a new macro PARROT_FORCE_EXIT to use in place of the libc exit(i) routine, which should not be used on all platforms
  • Loading branch information
Whiteknight committed May 10, 2012
1 parent c77b11f commit b1e9b39
Show file tree
Hide file tree
Showing 9 changed files with 61 additions and 87 deletions.
8 changes: 0 additions & 8 deletions include/parrot/exceptions.h
Expand Up @@ -127,12 +127,6 @@ void do_panic(
ARGIN_NULLOK(const char *file),
unsigned int line);

PARROT_EXPORT
PARROT_DOES_NOT_RETURN
PARROT_COLD
void exit_fatal(int exitcode, ARGIN(const char *format), ...)
__attribute__nonnull__(2);

PARROT_EXPORT
PARROT_DOES_NOT_RETURN_WHEN_FALSE
void Parrot_assert(
Expand Down Expand Up @@ -241,8 +235,6 @@ STRING * Parrot_ex_build_complete_backtrace_string(PARROT_INTERP,

void Parrot_print_backtrace(void);
#define ASSERT_ARGS_do_panic __attribute__unused__ int _ASSERT_ARGS_CHECK = (0)
#define ASSERT_ARGS_exit_fatal __attribute__unused__ int _ASSERT_ARGS_CHECK = (\
PARROT_ASSERT_ARG(format))
#define ASSERT_ARGS_Parrot_assert __attribute__unused__ int _ASSERT_ARGS_CHECK = (\
PARROT_ASSERT_ARG(condition_string) \
, PARROT_ASSERT_ARG(file))
Expand Down
21 changes: 17 additions & 4 deletions include/parrot/exit.h
Expand Up @@ -22,6 +22,12 @@ typedef struct _handler_node_t {
struct _handler_node_t *next;
} handler_node_t;

/* This macro is used to exit Parrot, when all else fails. This is a last
resort. This may be platform specific if certain systems cannot just call
the libc exit() function
*/
#define PARROT_FORCE_EXIT(x) exit(x)

/* HEADERIZER BEGIN: src/exit.c */
/* Don't modify between HEADERIZER BEGIN / HEADERIZER END. Your changes will be lost. */

Expand All @@ -39,8 +45,7 @@ void Parrot_x_exit(PARROT_INTERP, int status)
PARROT_EXPORT
PARROT_DOES_NOT_RETURN
PARROT_COLD
void Parrot_x_jump_out(PARROT_INTERP, int status)
__attribute__nonnull__(1);
void Parrot_x_jump_out(NULLOK_INTERP, int status);

PARROT_EXPORT
void Parrot_x_on_exit(PARROT_INTERP,
Expand All @@ -49,16 +54,24 @@ void Parrot_x_on_exit(PARROT_INTERP,
__attribute__nonnull__(1)
__attribute__nonnull__(2);

void Parrot_x_panic_and_exit(
NULLOK_INTERP,
int exitcode,
ARGIN(const char * format),
...)
__attribute__nonnull__(3);

#define ASSERT_ARGS_Parrot_x_execute_on_exit_handlers \
__attribute__unused__ int _ASSERT_ARGS_CHECK = (\
PARROT_ASSERT_ARG(interp))
#define ASSERT_ARGS_Parrot_x_exit __attribute__unused__ int _ASSERT_ARGS_CHECK = (\
PARROT_ASSERT_ARG(interp))
#define ASSERT_ARGS_Parrot_x_jump_out __attribute__unused__ int _ASSERT_ARGS_CHECK = (\
PARROT_ASSERT_ARG(interp))
#define ASSERT_ARGS_Parrot_x_jump_out __attribute__unused__ int _ASSERT_ARGS_CHECK = (0)
#define ASSERT_ARGS_Parrot_x_on_exit __attribute__unused__ int _ASSERT_ARGS_CHECK = (\
PARROT_ASSERT_ARG(interp) \
, PARROT_ASSERT_ARG(function))
#define ASSERT_ARGS_Parrot_x_panic_and_exit __attribute__unused__ int _ASSERT_ARGS_CHECK = (\
PARROT_ASSERT_ARG(format))
/* Don't modify between HEADERIZER BEGIN / HEADERIZER END. Your changes will be lost. */
/* HEADERIZER END: src/exit.c */

Expand Down
4 changes: 2 additions & 2 deletions src/alarm.c
Expand Up @@ -67,7 +67,7 @@ Parrot_alarm_init(void)
sa.sa_flags = SA_RESTART;

if (sigaction(SIGALRM, &sa, 0) == -1)
exit_fatal(1, "sigaction failed in Parrot_timers_init");
Parrot_x_panic_and_exit(NULL, 1, "sigaction failed in Parrot_timers_init");

Parrot_alarm_unmask(NULL);
#endif
Expand Down Expand Up @@ -107,7 +107,7 @@ posix_alarm_set(FLOATVAL wait)
Parrot_alarm_callback(SIGALRM);
}
else
exit_fatal(1, "setitimer failed in set_posix_alarm");
Parrot_x_panic_and_exit(NULL, 1, "setitimer failed in set_posix_alarm");
}
#endif
}
Expand Down
41 changes: 3 additions & 38 deletions src/exceptions.c
Expand Up @@ -311,7 +311,7 @@ flow is passed to it. Handlers can be either C-level or PIR-level routines. If
no suitable handler is found, Parrot exits with the stored exception error
message.
See also C<exit_fatal()>, which signals fatal errors, and
See also C<src/exit.c> and
C<Parrot_ex_throw_from_op> which throws an exception from within an op.
The 'invoke' vtable function doesn't actually execute a
Expand Down Expand Up @@ -383,7 +383,7 @@ Throws an exception from an opcode, with an error message constructed
from a format string and arguments. Constructs an Exception PMC, and passes it
to C<Parrot_ex_throw_from_op>.
See also C<Parrot_ex_throw_from_c> and C<exit_fatal()>.
See also C<Parrot_ex_throw_from_c> and C<src/exit.c>.
=cut
Expand Down Expand Up @@ -417,7 +417,7 @@ decides that is appropriate, or zero to make the error non-resumable.
C<exitcode> is a C<exception_type_enum> value. Constructs an Exception PMC
and passes it to C<Parrot_ex_throw_from_c>.
See also C<Parrot_ex_throw_from_op> and C<exit_fatal()>.
See also C<Parrot_ex_throw_from_op> and C<src/exit.c>.
=cut
Expand Down Expand Up @@ -656,41 +656,6 @@ Parrot_print_backtrace(void)
#endif /* ifdef PARROT_HAS_BACKTRACE */
}

/*
=item C<void exit_fatal(int exitcode, const char *format, ...)>
Signal a fatal error condition. This should only be used with dire errors that
cannot throw an exception (because no interpreter is available, or the nature
of the error would interfere with the exception system).
This involves printing an error message to stderr, and calling C<exit> to exit
the process with the given exitcode. It is not possible for Parrot bytecode to
intercept a fatal error (for that, use C<Parrot_ex_throw_from_c_args>).
C<exit_fatal> does not call C<Parrot_x_exit> to invoke exit handlers (that would
require an interpreter).
=cut
*/

PARROT_EXPORT
PARROT_DOES_NOT_RETURN
PARROT_COLD
void
exit_fatal(int exitcode, ARGIN(const char *format), ...)
{
ASSERT_ARGS(exit_fatal)
va_list arglist;
va_start(arglist, format);
vfprintf(stderr, format, arglist);
fprintf(stderr, "\n");
/* caution against output swap (with PDB_backtrace) */
fflush(stderr);
va_end(arglist);
exit(exitcode);
}

/* The DUMPCORE macro is defined for most platforms, but defined here if not
* found elsewhere, so we're sure it's safe to call. */

Expand Down
23 changes: 19 additions & 4 deletions src/exit.c
Expand Up @@ -52,7 +52,7 @@ Parrot_x_on_exit(PARROT_INTERP, ARGIN(exit_handler_f function), ARGIN_NULLOK(voi

/*
=item C<void Parrot_x_jump_out(PARROT_INTERP, int status)>
=item C<void Parrot_x_jump_out(NULLOK_INTERP, int status)>
Jumps out returning to the caller api function. Do not execute registered
on-exit handlers.
Expand All @@ -65,14 +65,14 @@ PARROT_EXPORT
PARROT_DOES_NOT_RETURN
PARROT_COLD
void
Parrot_x_jump_out(PARROT_INTERP, int status)
Parrot_x_jump_out(NULLOK_INTERP, int status)
{
ASSERT_ARGS(Parrot_x_jump_out)

if (interp->api_jmp_buf)
if (interp && interp->api_jmp_buf)
longjmp(*(interp->api_jmp_buf), 1);
else
exit(status);
PARROT_FORCE_EXIT(status);
}

/*
Expand Down Expand Up @@ -139,6 +139,21 @@ Parrot_x_execute_on_exit_handlers(PARROT_INTERP, int status)
Parrot_unblock_GC_sweep(interp);
}

void
Parrot_x_panic_and_exit(NULLOK_INTERP, int exitcode, ARGIN(const char * format), ...)
{
ASSERT_ARGS(Parrot_x_panic_and_exit)

va_list arglist;
va_start(arglist, format);
vfprintf(stderr, format, arglist);
fprintf(stderr, "\n");
fflush(stderr);
va_end(arglist);

Parrot_x_jump_out(interp, exitcode);
}


/*
Expand Down
7 changes: 4 additions & 3 deletions src/packfile/api.c
Expand Up @@ -1265,9 +1265,10 @@ PackFile_set_header(ARGOUT(PackFile_Header *header))
# if (NUMVAL_SIZE == 16)
header->floattype = FLOATTYPE_16;
# else
exit_fatal(1, "PackFile_set_header: Unsupported floattype NUMVAL_SIZE=%d,"
" PARROT_BIGENDIAN=%s\n", NUMVAL_SIZE,
PARROT_BIGENDIAN ? "big-endian" : "little-endian");
Parrot_x_panic_and_exit(NULL, 1,
"PackFile_set_header: Unsupported floattype NUMVAL_SIZE=%d,"
" PARROT_BIGENDIAN=%s\n", NUMVAL_SIZE,
PARROT_BIGENDIAN ? "big-endian" : "little-endian");
# endif
# endif
#endif
Expand Down
24 changes: 12 additions & 12 deletions src/packfile/pf_items.c
Expand Up @@ -603,7 +603,7 @@ cvt_num16_num8(ARGOUT(unsigned char *dest), ARGIN(const unsigned char *src))
#ifdef __LCC__
int expo2;
#endif
exit_fatal(1, "cvt_num16_num8: long double conversion unsupported");
Parrot_x_panic_and_exit(NULL, 1, "cvt_num16_num8: long double conversion unsupported");

/* Have only 12-byte long double, or no long double at all. Need to disect it */

Expand Down Expand Up @@ -823,7 +823,7 @@ cvt_num12_num8_le(ARGOUT(unsigned char *dest), ARGIN(const unsigned char *src))
unsigned char b[12];
fetch_buf_le_12(b, src); /* TODO test endianize */
cvt_num12_num8(dest, b);
exit_fatal(1, "cvt_num12_num8_le: long double conversion unsupported");
Parrot_x_panic_and_exit(NULL, 1, "cvt_num12_num8_le: long double conversion unsupported");
}
#endif

Expand All @@ -849,7 +849,7 @@ cvt_num16_num8_le(ARGOUT(unsigned char *dest), ARGIN(const unsigned char *src))
unsigned char b[16];
fetch_buf_le_16(b, src);
cvt_num16_num8(dest, b);
exit_fatal(1, "cvt_num16_num8_le: long double conversion unsupported");
Parrot_x_panic_and_exit(NULL, 1, "cvt_num16_num8_le: long double conversion unsupported");
}
#endif

Expand Down Expand Up @@ -1699,7 +1699,7 @@ PackFile_assign_transforms(ARGMOD(PackFile *pf))
break;
# endif
default:
exit_fatal(1,
Parrot_x_panic_and_exit(NULL, 1,
"PackFile_unpack: unsupported float conversion %d to %d, "
"PARROT_BIGENDIAN=%d\n",
NUMVAL_SIZE, pf->header->floattype, PARROT_BIGENDIAN);
Expand Down Expand Up @@ -1736,7 +1736,7 @@ PackFile_assign_transforms(ARGMOD(PackFile *pf))
break;
# endif
default:
exit_fatal(1,
Parrot_x_panic_and_exit(NULL, 1,
"PackFile_unpack: unsupported float conversion %d to %d, "
"PARROT_BIGENDIAN=%d\n",
NUMVAL_SIZE, pf->header->floattype, PARROT_BIGENDIAN);
Expand All @@ -1761,7 +1761,7 @@ PackFile_assign_transforms(ARGMOD(PackFile *pf))
pf->fetch_nv = fetch_buf_be_8;
break;
case FLOATTYPE_12:
exit_fatal(1, "PackFile_unpack: invalid floattype 1 big-endian");
Parrot_x_panic_and_exit(NULL, 1, "PackFile_unpack: invalid floattype 1 big-endian");
break;
case FLOATTYPE_16:
pf->fetch_nv = cvt_num16_num8_be;
Expand All @@ -1772,7 +1772,7 @@ PackFile_assign_transforms(ARGMOD(PackFile *pf))
pf->fetch_nv = cvt_num8_num12_be;
break;
case FLOATTYPE_12:
exit_fatal(1, "PackFile_unpack: invalid floattype 1 big-endian");
Parrot_x_panic_and_exit(NULL, 1, "PackFile_unpack: invalid floattype 1 big-endian");
break;
case FLOATTYPE_16:
pf->fetch_nv = cvt_num16_num12_be;
Expand All @@ -1783,14 +1783,14 @@ PackFile_assign_transforms(ARGMOD(PackFile *pf))
pf->fetch_nv = cvt_num8_num16_be;
break;
case FLOATTYPE_12:
exit_fatal(1, "PackFile_unpack: invalid floattype 1 big-endian");
Parrot_x_panic_and_exit(NULL, 1, "PackFile_unpack: invalid floattype 1 big-endian");
break;
case FLOATTYPE_16:
pf->fetch_nv = fetch_buf_be_16;
break;
# endif
default:
exit_fatal(1,
Parrot_x_panic_and_exit(NULL, 1,
"PackFile_unpack: unsupported float conversion %d to %d, "
"PARROT_BIGENDIAN=%d\n",
NUMVAL_SIZE, pf->header->floattype, PARROT_BIGENDIAN);
Expand Down Expand Up @@ -1837,7 +1837,7 @@ PackFile_assign_transforms(ARGMOD(PackFile *pf))
break;
# endif
default:
exit_fatal(1,
Parrot_x_panic_and_exit(NULL, 1,
"PackFile_unpack: unsupported float conversion %d to %d, "
"PARROT_BIGENDIAN=%d\n",
NUMVAL_SIZE, pf->header->floattype, PARROT_BIGENDIAN);
Expand Down Expand Up @@ -1887,7 +1887,7 @@ fetch_iv_le(INTVAL w)
r |= (w & 0xff00000000000000) >> 56;
return r;
# else
exit_fatal(1, "Unsupported INTVAL_SIZE=%d\n",
Parrot_x_panic_and_exit(NULL, 1, "Unsupported INTVAL_SIZE=%d\n",
INTVAL_SIZE);
# endif
# endif
Expand Down Expand Up @@ -1930,7 +1930,7 @@ fetch_iv_be(INTVAL w)
r |= (w & 0xff00000000000000) >> 56;
return r;
# else
exit_fatal(1, "Unsupported INTVAL_SIZE=%d\n", INTVAL_SIZE);
Parrot_x_panic_and_exit(NULL, 1, "Unsupported INTVAL_SIZE=%d\n", INTVAL_SIZE);
# endif
# endif
#endif
Expand Down
3 changes: 2 additions & 1 deletion src/platform/win32/env.c
Expand Up @@ -82,7 +82,8 @@ Parrot_setenv(PARROT_INTERP, STRING *str_name, STRING *str_value)
}
else {
mem_sys_free(envstring);
exit_fatal(1, "Unable to set environment variable %s=%s",
Parrot_x_panic_and_exit(interp, 1,
"Unable to set environment variable %s=%s",
name, value);
}
}
Expand Down
17 changes: 2 additions & 15 deletions t/src/basic.t
Expand Up @@ -13,7 +13,7 @@ my $parrot_config = "parrot_config" . $PConfig{o};

plan skip_all => 'src/parrot_config.o does not exist' unless -e catfile("src", $parrot_config);

plan tests => 2;
plan tests => 1;

=head1 NAME
Expand All @@ -25,7 +25,7 @@ t/src/basic.t - Basics
=head1 DESCRIPTION
Tests C<printf> and C<exit_fatal> functions.
Tests C<printf>
=cut

Expand All @@ -43,19 +43,6 @@ CODE
Hello, World!
OUTPUT

c_output_is( <<'CODE', <<'OUTPUT', "direct exit_fatal call" );
#include <parrot/parrot.h>
#include <parrot/exceptions.h>
int
main(int argc, const char* argv[])
{
exit_fatal(0, "Blow'd Up(tm)"); /* ' */
}
CODE
Blow'd Up(tm)
OUTPUT
# for $EDITOR '

# Local Variables:
Expand Down

0 comments on commit b1e9b39

Please sign in to comment.