[PING][PATCH][RFC] vterminate use of malloc-less demangler
Simon Baldwin
simonb@google.com
Fri Mar 2 17:44:00 GMT 2007
Benjamin Kosnik wrote:
>
>> Testing this work is, unfortunately, rather tricky. I do have a
>> simple test case, appended below, that allows me to confirm manually
>> that __verbose_terminate_handler is operating without heap use.
>>
>> This test, however, is hard to fit into any test framework. First,
>> it aborts whether or not it's successful; that's the nature of
>> changing termination code. Second, it relies on MALLOC_CHECK_,
>> making it Linux only and not portable. And third, it relies on
>> carnal knowledge of libc's heap organization in order to "lightly"
>> corrupt the heap without overdoing it.
>>
>> Some of these restrictions might be avoidable. For example,
>> interposing malloc, realloc, free, and calloc catches calls to heap
>> functions in the same way as MALLOC_CHECK_, so could make the test
>> slightly more portable. This still isn't fully portable across all
>> platforms, though, and may require platform-specific link options
>> even where practical. Likewise, the abort() can be caught with a
>> SIGABRT handler, but again is not portable. I experimented with a
>> test based on these ideas, but it's probably too complex to be reliable.
>>
>> There seems to be no identifiable current vterminate.cc test I can
>> extend for this patch. If you have other ideas for how to add a
>> suitable test to the libstdc++ test suite, please let me know.
>
>
> I cannot, at the moment, sorry. Also, your test case does not
> reproduce the issue for me, on FC6.
>
> I get:
>
> %./a.out
> malloc: using debugging hooks
> *** glibc detected *** ./a.out: malloc: top chunk is corrupt:
> 0x08d40088 ***
Did you link the test program with a libstdc++ that contains my patch?
If not, then you have successfully reproduced the issue -- this is it.
Without the patch, __cxa_demangle(), called from __verbose_terminate(),
will attempt to allocate memory to hold the result of demangling.
Because the test program deliberately corrupts the heap and sets
MALLOC_CHECK_, demangling will then fail to allocate, and give an error
like that above.
With the patch, and linking the test program to a patched libstdc++.a,
you'll see
%./a.out
malloc: using debugging hooks
terminate called after throwing an instance of 'std::bad_alloc'
what(): St9bad_alloc
Aborted
indicating that name demangling and other termination handling still
function even in the presence of a corrupted and unusable heap.
>>> 2) Are you planning on making this new function available to other
>>> users besides the verbose terminate handler? If so, the declaration
>>> should go below cxa_demangle in cxxabi.h and the function should be
>>> exported. If not, the declaration should be removed.
>>
>>
>>
>> The __gcclibcxx_demangle_callback() function is intended as a private
>> contract between glibc and libstdc++. There's no plan to use it
>> elsewhere. Callback-based demangling for general use is provided by
>> cplus_demangle_v3_callback(), supplied by libiberty's
>> include/demangle.h as an extension to the existing
>> cplus_demangle_v3(). Moving the declaration of
>> __gcclibcxx_demangle_callback() to cxxabi.h is also slightly
>> misleading, as the function isn't actually part of the defined ABI.
>>
>> The current declaration can't be removed if not placed in cxxabi.h --
>> this would prevent the vterminate.cc from compiling.
>
>
> [snip]
>
>> There don't appear to be any other functions that are private
>> contracts between glibc and libstdc++, so this name seems
>> reasonable. In particular, it's not part of the C++ ABI, so naming
>> it __cxa_... was deemed unacceptable. (In practice, it's actually a
>> variant of __cxa_demangle(), but has to have a different name as the
>> specification of __cxa_demangle() doesn't permit malloc-less operation).
>
>
> I think you should re-evaluate your approach with this patch. I think
> this malloc-free demangler addition should be obvious to people using
> the cxxabi.h interfaces.
>
> In overview, libiberty and libsupc++/libstdc++ share the demangler
> code. However, libstdc++ has an API-defined interface to the
> demangler, in __cxa_demangle from cxxabi.h. You're augmenting this,
> much like other non-ABI extensions (__cxa_cdtor_return_type,
> __cxa_cdtor_type), and admittedly so from your last parenthetical bit
> above.
>
> And, I think this is a good thing: clearly, there are issues with
> __cxa_demangle's memory management facilities. There's even been
> previous attempts to deal with this in libsupc++, with this. See
> gcc-3.4.0's struct demangle in libstdc++-v3/ext/demangle.h etc etc.
>
> I'm of the opinion that something like __cxa_demangle_no_alloc, ie
> something much simpler and direct, without all the callback goo, would
> be a much cleaner route to get where you want to go. Then, you could
> use this no-alloc routine in __verbose_terminate_handler. Or,
> __cxa_demangle_callback if you can convince me that there is ever
> going to be more than one callback...
__cxa_demangle_callback() was the original name of this demangler
function, but this was rejected as part of the review of libiberty
revision 121305, which changed it to _gcclibcxx_demangle_callback().
The rationale is that since this function is not part of the ia64 ABI,
it should not be named as though it is.
Please explain how you envision a demangling interface that explicitly
avoids both allocations and callbacks. In particular, how should it
return or otherwise handle the demangled string?
> In addition, I think this addition should be mentioned here:
> http://gcc.gnu.org/onlinedocs/libstdc++/18_support/howto.html#6
This is relevant only for functions that are described by cxxabi.h. As
noted above, this addition isn't, since it's not part of the ABI.
Conventional client code access to allocation-less demangling is
provided by the libiberty functions cplus_demangle_v3_callback(),
java_demangle_v3_callback(), and cplus_demangle_print_callback(), all
analogous to the existing libiberty functions that return allocated
strings -- cplus_demangle_v3(), java_demangle_v3(), and
cplus_demangle_print().
More information about the Libstdc++
mailing list