TempAlloc and druntime GC

dsimcha dsimcha at yahoo.com
Mon Jan 19 15:17:18 PST 2009


== Quote from Sean Kelly (sean at invisibleduck.org)'s article
> The data range of every execution context in druntime is tracked by the GC
> via a linked-list of structs that look roughly like this:
> struct Context
> {
>     void*        begin;
>     void*        end;
>     Context* next;
> }
> The stack of each kernel thread has one, as does each user thread (Fiber).
Currently,
> this is all internal, but I could expose an API along these lines:
> void attachContext( Context* );
> void detachContext( Context* );
> Each ThreadAlloc range would have its own Context struct which it would attach
> on creation and detach upon destruction.  You're still paying for a mutex call
> to attach and detach the struct, but the begin and end pointers can be modified
> at will, which gets rid of the problem with addRange, etc.
> I suppose I could add this to the interface of GC as well, instead of sticking
yet more
> logic in core.thread.

The problem with this is that I'd ideally like to control whether each
TempAlloc-allocated object is scanned by the GC individually, rather than scanning
the entire used portion of the TempAlloc stack.  Having to create and store a
context struct for every object would be incredibly inefficient.  Scanning the
entire used portion would be incredibly conservative.

At an implementation level, TempAlloc already uses an array of void*s internally
to track what it's allocated (only one per object, in an array, not a linked list)
so that it can be freed properly.  Since TempAlloc allocates using 16-byte
alignment, I was planning to avoid any extra overhead by storing the scan/noscan
bits in the low order bits of these pointers.

One more note:  It would also be greatly appreciated if you would expose a version
of GC.malloc that returns null on failure instead of throwing an exception.  For
performance, TempAlloc treats out of memory as non-recoverable.  This is necessary
because, since scope statements are often used to manage freeing, the performance
hit from having TempAlloc-related functions be throwing would be too large.  Also,
making TempAlloc functions non-throwing by catching outOfMemoryErrors and aborting
is in itself expensive.

Furthermore, I just realized (literally while I was writing this post) that C's
malloc (which I use only b/c it doesn't throw) doesn't always return 16-byte
aligned pointers like druntime's.  Ideally, I'd like to stop using the C heap and
start using the druntime heap, but I can't do that until there is a non-throwing
implementation of GC.malloc.



More information about the Digitalmars-d mailing list