On Thu, 24 Apr 2014 19:55:37 +0000, Lars T. Kyllingstad wrote: > Is it possible to temporarily prevent the garbage collector from > collecting a memory block even if there are no references to it? > > The use case is as follows: I want to call a C library function which > expects to take ownership of a buffer. It looks something like this: > > alias FreeFunc = extern(C) void function(void*, void*) > nothrow; > > extern(C) void foo(void* buf, size_t len, > FreeFunc free, void* ctx) nothrow; > > Here, 'buf' is a pointer to the buffer, 'len' is the length of the > buffer, 'free' is a function to deallocate the buffer when the library > is done with it, and 'ctx' is a user-supplied context pointer. Upon > deallocation, 'free' receives two parameters; the pointer to the buffer > and the context pointer. The latter can be anything, even null, as it > is just passed to 'free' and not used for anything else. > > Here is the problem: I want to be able to use a garbage-collected > dynamic array with this function, but I don't want to have to retain a > reference to it in my program. (I don't know when the C library will > call the free function.) In other words, I want something like this: > > extern(C) void myFree(void* ptr, void* ctx) > { > enableGCFor(ptr); > } > > auto arr = new int[123]; > disableGCFor(arr); > foo(arr.ptr, arr.length, &myFree, null); > arr = null; > > Is this at all possible? > > Thanks, > Lars
You can use GC.addRoot() from core.memory before passing the pointer to the C function, then use GC.removeRoot in your myFree function.