On 6 February 2014 00:04, <"Ola Fosheim Grøstad\" <ola.fosheim.grostad+dlang@gmail.com>"@puremagic.com> wrote:
On Wednesday, 5 February 2014 at 12:40:13 UTC, Manu wrote:
Counter question; why approach it this way?
Is there a reason that it needs to be of one kind or the other?

Sure, you could make all allocations with RC enabled make space for a counter at a negative offset (ptr-offset), but that would not work with C structs or internal pointers and aligned data might hog a bit of extra space.

Perhaps match a very particular and unlikely bit pattern in the negative offset to know if it is RC or not?
Or I wonder if there's opportunity to pinch a single bit from pointers to mark that it is raw or RC allocated? Probably fine on 64bit. 32bit probably needs to match a bit pattern or something.

Aligned data is a challenge. I have often wondered if it would be feasible to access the RC via a pointer hash or something, and keep it in a side table... sounds tricky, but I wonder if it's possible.

You also need to handle internal pointers to embedded objects and arrays of objects (not pointers to objects). How do you ref count those? I guess you could switch all pointers into (allocated_base,offset) tuples and special case (ptr,0).

That's a good point. This is probably the trickiest detail. Maybe a clever way to make any pointer within the allocated range hash to the right index in the side table I referred to above. That sounds like a tricky hashing function, and probably slow.
Fat pointers might be necessary. That's a bit annoying. Hmmm...

Rather than (allocated_base, offset), I suspect (pointer, offset_from_base) would be better; typical dereferences would have no penalty.

You could do like C++, have the ref counter be a separate object. Then record the properties of the pointer (such as offset), then have special magic checks for deallocation: testing for internal reference then decrease the real ref counter of the parent rather than deallocate. This is quite compatible with having a GC, you could free the object only when proven safe and just ignore it and leave it for GC when you cannot prove it.

You mean like the smart pointer double indirection? I really don't like the double indirection, but it's a possibility. Or did I misunderstand?

IMHO you proabably need to redesign the language in order to support transparent or efficient automatic memory handling. If you retain C-legacy, you also retain manual memory handling or a limited set of opportunites for automatic garbage collection.

I'm sure there's a clever solution out there which would allow the ARC to detect if it's a raw C pointer or not...