Suppose I have a wrapper object like this:
private val CLEANER = java.lang.ref.Cleaner.create()
internal typealias Ptr = Long
private external fun acquireResource(): Ptr
private external fun disposeResource(nativePtr: Ptr)
/* ... */
class Resource private constructor (private val nativePtr: Ptr):
Closeable, AutoCloseable
{
companion object {
fun create(): Resource {
return Resource(acquireResource())
}
}
private val cleanable = CLEANER.register(this, object: Runnable {
private val nativePtr = [email protected]
override fun run() {
disposeResource(nativePtr)
}
})
override fun close() {
cleanable.clean()
}
/* ... */
}
Now suppose I want to write a method internal fun release(): Ptr that makes the Resource give up ownership on nativePtr and then return it: in other words, when the Resource on which I called release is garbage-collected, its nativePtr pointer should not be disposed. (I intend that the Resource object should not be used after release is called, though I don’t see any way to enforce this.) This would allow me to pass the Ptr to an API that will manage its lifetime from then on.
How can I write release, preferably in an atomic/thread-safe manner? Is it even compatible with Cleaner?
(In other words, I am looking for an API equivalent to JavaScript’s FinalizationRegistry.prototype.unregister.)