2

Assuming I'm in a C++ program, I want to convert these reports to exceptions. Is using a C++ throw statement a reasonable way to do it, or am I stuck just redirecting to stderr?

Matt Chambers
  • 2,229
  • 1
  • 25
  • 43
  • Who is supposed to catch it? It is typically going to be called after main() has returned. This is a debugging function, you're running in a well controlled environment. – Hans Passant Aug 05 '11 at 21:32
  • I'm mainly thinking of calls like ASSERT[E] which are rarely outside main(). – Matt Chambers Aug 05 '11 at 22:10
  • That's not a throw. There can be a *lot* of them, gets old quickly. What's wrong with the default handler? – Hans Passant Aug 05 '11 at 23:14
  • 1
    @Hans Passant: In this case, I'm running unit tests. When I get a debug assert, I want it treated like any other error, i.e. an exception. I don't want some custom Abort/Retry/Ignore dialog for a Windows app and a stderr message for a console app. – Matt Chambers Aug 07 '11 at 01:48

1 Answers1

4

No, you can not throw C++ exceptions from your hook.

It may work some of the time - but in general - when the hook is invoked the CRT is in an indeterminate state and may no longer be able to throw or handle exceptions. Throwing an exception when the CRT is in trouble, is a similar scenario to throwing an exception from the destructor of an object, that has been called during stack unwinding, due to an exception. Also, the depths of the CRT is not an appropriate place to throw C++ exceptions, doing so might leave the runtime in a bad state - if it wasn't already!

What you should do is the following:

int no_dialog_box_but_act_as_if_it_had_appeared_and_abort_was_clicked (int /* nRptType */,
                                                                       char *szMsg, 
                                                                       int * /* retVal */)
{
    fprintf (stderr, "CRT: %s\n", szMsg);

    /* raise abort signal */
    raise (SIGABRT);

    /* We usually won't get here, but it's possible that
    SIGABRT was ignored.  So exit the program anyway. */
    _exit (3);
}
user1976
  • 353
  • 4
  • 15