XPConnect object wrapping: Difference between revisions

Jump to navigation Jump to search
m
Line 36: Line 36:
# The reference the <tt>JSObject</tt>'s private slot has to the <tt>XPCWrappedNative</tt>.
# The reference the <tt>JSObject</tt>'s private slot has to the <tt>XPCWrappedNative</tt>.


This models a simple fact: for the <tt>XPCWrappedNative</tt> to die, both the C++ XPCOM world ''and'' the JS heap ought to have forgetten about it. If either side still sees it, it should stay alive.
This models a simple fact: for the <tt>XPCWrappedNative</tt> to die, both the C++ XPCOM world ''and'' the JS heap ought to have forgotten about it. If either side still sees it, it should stay alive.


Thus the <tt>JSObject</tt> keeps the <tt>XPCWrappedNative</tt> alive, and the <tt>XPCWrappedNative</tt> keeps the <tt>nsISupports</tt> that it's pointing to alive. But there's an important detail: the <tt>XPCWrappedNative</tt> does ''not'' directly keep the <tt>JSObject</tt> alive. Doing so unconditionally -- for example rooting the <tt>JSObject</tt> -- would give rise to a cyclic graph: the pair of objects would keep each other alive indefinitely. So the <tt>XPCWrappedNative</tt> holds a pointer to the <tt>JSObject</tt>, but doesn't root it.
Thus the <tt>JSObject</tt> keeps the <tt>XPCWrappedNative</tt> alive, and the <tt>XPCWrappedNative</tt> keeps the <tt>nsISupports</tt> that it's pointing to alive. But there's an important detail: the <tt>XPCWrappedNative</tt> does ''not'' directly keep the <tt>JSObject</tt> alive. Doing so unconditionally -- for example rooting the <tt>JSObject</tt> -- would give rise to a cyclic graph: the pair of objects would keep each other alive indefinitely. So the <tt>XPCWrappedNative</tt> holds a pointer to the <tt>JSObject</tt>, but doesn't root it.
Confirmed users
162

edits

Navigation menu