[fpc-devel] Suggestion: reference counted objects
Sven Barth
pascaldragon at googlemail.com
Sat Sep 27 18:33:57 CEST 2014
On 27.09.2014 17:00, Constantine Yannakopoulos wrote:
> On Sat, Sep 27, 2014 at 4:36 PM, Sven Barth <pascaldragon at googlemail.com
> <mailto:pascaldragon at googlemail.com>> wrote:
>
> There are however some nasty problems inside constructors and
> destructors, because "Self" is reference counted as well (and should
> be after all as we don't want the instance to be destroyed behind
> our backs suddenly).
>
>
> The parenthesis can happen in Delphi interfaced objects as well. It is
> perfectly possible to lose the object from under your feet if the code
> of one of its methods leads to references reaching zero (e.g. removal
> from a strong-ref'd list). If such a possibility exists the developer
> needs to manually _AddRef/_Release (e.g. store Self in a local interface
> variable) if they need to access Self after that point, and that is
> perfectly OK. The only way to avoid that would be to emit code at a
> compiler-generated implicit try-finally block to _AddRef/_Release, which
> is a bad idea IMHO as it adds overhead when it won't be required for
> 99.99% of cases.
That's what the compiler currently does though, because it treats Self
just a like a normal reference counted variable... Will need to check
what I need to do do switch that of ;)
> As for destructors, the way refcounting is implemented in Delphi it
> prohibits performing _Addref/_Release (e.g. pass an interface variable
> of Self to an external method) in them because this will cause infinite
> recursion.
Huh? Delphi really prohibits such things inside the destructor? Would
you mind to share an example (possibly including error messages), please?
> This problem has an easy solution: Override BeforeDestruction
> and set RefCount to a positive value, 1 or MaxInt div 2 (not -1,
> consider the sequence _AddRef[0], _AddRef[1], _Release[0-bang],
> _Release[AV]) after calling inherited (which checks for 0). Since the
> object destruction process has already started due to RefCount reaching
> zero, refcounting is useless at this point and can be safely disabled.
> You could consider doing this in your implementation.
I've done a different approach already: the decrease helper sets
refcount to -1 directly before it calls the destructor and both the
increase and the decrease helper check for -1. Considering that it's
currently only a proof of concept I can live with the performance impact
that comparison might have.
Regards,
Sven
More information about the fpc-devel
mailing list