The pointer refers to a byte array. The
MutableByteArray# field
means that the
MutableByteArray# is reachable (by GC) whenever
the
ForeignPtr is reachable. When the
ForeignPtr becomes
unreachable, the runtime's normal GC recovers the memory backing it.
Here, the finalizer function intended to be used to
free()
any ancillary *unmanaged* memory pointed to by the
MutableByteArray#. See the
zlib library for an example
of this use.
- Invariant: The Addr# in the parent ForeignPtr is an
interior pointer into this MutableByteArray#.
- Invariant: The MutableByteArray# is pinned, so the
Addr# does not get invalidated by the GC moving the byte
array.
- Invariant: A MutableByteArray# must not be associated with
more than one set of finalizers. For example, this is sound:
incrGood :: ForeignPtr Word8 -> ForeignPtr Word8
incrGood (ForeignPtr p (MallocPtr m f)) = ForeignPtr (plusPtr p 1) (MallocPtr m f)
But this is unsound:
incrBad :: ForeignPtr Word8 -> IO (ForeignPtr Word8)
incrBad (ForeignPtr p (MallocPtr m _)) = do
f <- newIORef NoFinalizers
pure (ForeignPtr p (MallocPtr m f))