bug-gnulib
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Bug-gnulib] Re: alloca


From: Simon Josefsson
Subject: [Bug-gnulib] Re: alloca
Date: Wed, 12 Nov 2003 22:22:46 +0100
User-agent: Gnus/5.1003 (Gnus v5.10.3) Emacs/21.3.50 (gnu/linux)

Bruno Haible <address@hidden> writes:

> Hi Simon,

Hello Bruno, thanks for your answers.

>> Would it be useful to allow a alloca module mode of operation where it
>> is used unconditionally, even on GNU platforms?  The reason is that
>> the gnulib alloca (really xalloc) gives a useful error message,
>> whereas the GCC inline alloca exit the program with a segmentation
>> fault.  I wouldn't want to use alloca unless reasonable error checking
>> is done.
>
> You should know that lib/alloca.c not only uses xmalloc(), it also leaks
> memory. (Because it cleans up the past allocations only when you invoke
> alloca() again, from a point with smaller stack depth.)

Yes, I'm aware of this, but considering the alternatives it seems like
the best solution, at least for me.  I tried to think of a better
approach than guessing the stack depth, but even guessing the stack
depth seemed like a quite ingenious solution, so I haven't come up
with anything better.

Some "cleanup" alloca CPP macro to put within functions that uses
alloca could be possible though.  It might be possible to write a
pre-processor that fixes *.c files in this way automatically.

> Therefore I'd recommend:
>
>   1) If you want useful error messages in case of failure, and you are
>      not worried by allocation speed, use xmalloc().

This is what I use now, but it does make code more unreadable.  Either
I have to clean memory by using goto's.  A slightly cleaner approach
is to split the function into a high-level part that allocates things
and then invoke a low-level part that does its job, and then the
high-level part deallocates memory if the low-level part failed.  In
some places this leads to many nesting levels, making the code
unreadable again.  And there is the memory leak if longjmp is used
within a nested function.  The alloca() idiom is nice, if it was
reliable.

>      1.1) If furthermore you want to avoid memory leaks, either insert free()
>           calls in your program, or use a garbage collector like Boehm's GC.

I have considered this from time to time, but I haven't actually tried
this, because:

1) it is not portable, and it acknowledge that it can never be fully
   portable.  This is probably my main problem with it.

2) it might obscure memory related bugs, if I use the Boehm GC for all
   malloc()'s.  I'm not sure if, e.g., valgrind can detect and work
   together with Boehm's GC, but something like it would be necessary,
   I think.  (I'm thinking of the case where you write to supposedly
   deallocated storage.  With Boehm it might not be deallocated yet,
   so valgrind, or the actual operating system, might not notice the
   flaw, and you get even weirder bugs to debug.)

3) using it within libraries that return malloc()'d data to the
   application appear complicated (although probably I'm just
   uneducated about this point).  Should it force the application to
   use Boehm?

4) Code bloat.  For a small library, that just want to use alloca()
   internally to improve code readability, including a GC seems
   overkill.

There are probably other minor issues I'm forgetting right now.

>   2) If you want to avoid segmentation fault due to alloca of large chunks,
>      and allocation speed is still important, then use a hybrid approach:
>      alloca() for small sizes and xmalloc() for larger ones.
>
> You can find a C++ example for the approach (2) in the appended file, taken
> from CLN. In C it's less pretty.

This approach might be better for me, if (like I think Paul also
asked) it is possible to automatically detect safe values for
alloca().

Having a new GCC inline'd function 'void *alloca_safe(size_t SIZE)',
that can return NULL if there is not enough stack space might be the
best.  Then one could write some logic that would fall back to
xmalloc() when necessary, or just abort and ask the user to increase
the stack space.  Considering that GNU systems have dynamically
increasing stack space, if I recall correctly, the abort-with-error
approach would work perfectly on GNU systems, and only rarely fail on
non-GNU systems.





reply via email to

[Prev in Thread] Current Thread [Next in Thread]