Boost logo

Boost :

From: Darren Cook (darren_at_[hidden])
Date: 2003-05-08 03:43:45


> 4. In case an assertion has failed, two actions will occur:
> - first, the assertion will be logged
> - second, a message will be show to the user, and the user can choose from
> multiple actions, like Ignore, Retry, Abort, etc.
>
> These are SEPARATE actions, and are both customizable.
> Customization can happen at RUNTIME.

In my own assert library I added options for logging, but in the end never
used that and always had it throw an exception. This is nice for two reasons:
   1. MFC debugger catches it and allows me to go back up the call stack to
where the assert happened. (I'm still struggling with gdb but I think it can
be set to do the same?)

   2. Boost::test will catch the exception; if I want to test a function
asserts with bad inputs I can use BOOST_CHECK_THROW.

So I'd like to see three separate actions, and be allowed to switch off the
first two (with a compile-time flag).

Given that, I'm wondering if instead of hard-coding two or three actions
that can be customized if you wouldn't be better allowing any number of
callbacks to be registered, and then supplying some ready-made callbacks to do:
   1. logging
   2. user prompting
   3. throw exceptions

Not sure how difficult that is to implement however. Also I cannot think of
a 4th thing you'd want to do, so maybe this is not such a good idea.

> ------------------------
> 10. specifying all ASSERT's arguments
>
> When using BOOST_ASSERT, you should specify all arguments involved in the
> assert; otherwise, if the assertion fails, you might not get enough
> information.
>
> Example:
> // OK - all 3 params have been cared for
> BOOST_ASSERT( (i > 1) || (j < 0) || (k != i) )(i)(j)(k);
>
> // bad - in case an assertion fails, not enough info is outputted!
> // (k is not outputted)
> BOOST_ASSERT( (i > 1) || (j < 0) || (k != i) )(i)(j);
>
> (compile-time switch, can be on/off; on by default)

I didn't follow this one - are you saying the compiler will complain about
the bad assert that doesn't include "(k)"? If you could do that you wouldn't
need the user to specify the variables at all would you?

> We can have a "fatal error" level, in which case an exception could be
> triggered.

I thought all asserts should be considered fatal, so as suggested above I
think BOOST_ASSERT should always throw an exception, and maybe you need
BOOST_WARNING for non-fatal conditions you'd like logged or to inform the
user about.

> I'll allow for custom printing of variables (when an assertion fails).
> ...
> For instance, for a non-null pointer, you might want to print (some of) its
> contents. Or, for an STL container, to print its elements (or at least its
> size)

This is interesting; what syntax do you have in mind for using this?

For some types of objects it might be useful to specify a function to call
if it asserts; I often have a debug_info() function in my classes. E.g.
   BOOST_ASSERT(obj.status()==0)(obj.debug_info())

Will that work if debug_info() returns void?

Darren

P.S. I like everything else you proposed, and the BOOST_ASSERT name is fine.
Though if aiming for inclusion in C++ standard in the future maybe
SMART_ASSERT or similar is better?


Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk