== Quote from Sean Kelly ([email protected])'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.
