--- On Wed, 4/28/10, Andrei Alexandrescu <[email protected]> wrote:
> On 04/28/2010 04:17 PM, Robert
> Clipsham wrote:
> > There's a GNU library for handling this, libsigsegv (
> > http://libsigsegv.sourceforge.net/ ). I
> took the liberty of downloading
> > and inspecting this, it's 5659 LoC to handle segfaults
> (So say, 3000 if
> > we rewrote it in D :P). That's a lot of extra code to
> handle a segfault
> > for unittests. Add to this not all platforms support
> it, and it needs
> > reimplementing on every platform. If you want this
> code in
> > druntime/phobos then you'll have to write it from
> scratch due to
> > licensing issues and be unable to look at this well
> written/tested
> > library as a reference... It seems like a lot of extra
> effort for
> > something I maintain should be done with a debugger.
>
> Ouch.
This is not important. A library to print out the last unit test failure is
really easy. printf is not required, write will be sufficient. All it needs
is a little compiler help.
At the beginning of every unit test, the compiler should insert the following
code:
unittest { __unittestFile = __FILE__; __unittestLine = __LINE__;
...
}
Then, during unittest, the runtime inserts a signal handler for SEGV:
__gshared string __unittestFile = "";
__gshared uint __unittestLine = 0;
__gshared string msg = "unittest SEGV: ";
extern(C) void unittestSegv(int sig)
{
char[11] lineno;
int linenostart = 0;
do
{
lineno[$-1-linenolength] = '0' + __unittestLine % 10;
__unittestLine /= 10;
--linenostart;
} while(__unittestLine > 0);
write(2, msg.ptr, msg.length);
write(2, __unittestFile.ptr, __unittestFile.length);
write(2, "@", 1);
write(2, lineno.ptr + linenostart, lineno.length - linenostart);
write(2, "\n", 1);
exit(1);
}
Note that performance problems due to instrumentation or bloating does not
matter whatsoever, because unittest mode is not normal. You only ever compile
with unittest mode when you are testing unittests, not when you are trying to
run a program.
The point is, something simple that at least displays some info is better than
nothing. Saying someone should use a debugger is both useless after the fact
(the program already crashed!) and doesn't really apply to unittesting.
Unittesting is not the normal mode of operation, so making an exception there
does not muddy any principles. The unit test system should make a best effort
to report any failures. If the program somehow corrupts the global variables,
then the worst that happens is the signal handler segfaults, and you get the
same error message you get now. Then you can use a debugger :)
Note that this just reports the start of the unit test that failed, not where
the actual failure occurs. This should be plenty info in most cases, you can
and should have multiple unit test functions in each module.
-Steve
_______________________________________________
dmd-internals mailing list
[email protected]
http://lists.puremagic.com/mailman/listinfo/dmd-internals