Trait mmtk::vm::slot::Slot

source ·
pub trait Slot: Copy + Send + Debug + PartialEq + Eq + Hash {
    // Required methods
    fn load(&self) -> Option<ObjectReference>;
    fn store(&self, object: ObjectReference);

    // Provided methods
    fn prefetch_load(&self) { ... }
    fn prefetch_store(&self) { ... }
}
Expand description

A Slot represents a slot in an object (a.k.a. a field), on the stack (i.e. a local variable) or any other places (such as global variables). A slot may hold an object reference. We can load the object reference from it, and we can update the object reference in it after the GC moves the object.

For some VMs, a slot may sometimes not hold an object reference. For example, it can hold a special NULL pointer which does not point to any object, or it can hold a tagged non-reference value, such as small integers and special values such as true, false, null (a.k.a. “none”, “nil”, etc. for other VMs), undefined, etc.

This intends to abstract out the differences of reference field representation among different VMs. If the VM represent a reference field as a word that holds the pointer to the object, it can use the default SimpleSlot we provide. In some cases, the VM need to implement its own Slot instances.

For example:

  • The VM uses compressed pointer (Compressed OOP in OpenJDK’s terminology), where the heap size is limited, and a 64-bit pointer is stored in a 32-bit slot.
  • The VM uses tagged pointer, where some bits of a word are used as metadata while the rest are used as pointer.
  • A field holds a pointer to the middle of an object (an object field, or an array element, or some arbitrary offset) for some reasons.

When loading, Slot::load shall decode its internal representation to a “regular” ObjectReference. The implementation can do this with any appropriate operations, usually shifting and masking bits or subtracting offset from the address. By doing this conversion, MMTk can implement GC algorithms in a VM-neutral way, knowing only ObjectReference.

When GC moves object, Slot::store shall convert the updated ObjectReference back to the slot-specific representation. Compressed pointers remain compressed; tagged pointers preserve their tag bits; and offsetted pointers keep their offsets.

The methods of this trait are called on hot paths. Please ensure they have high performance. Use inlining when appropriate.

Note: this trait only concerns the representation (i.e. the shape) of the slot, not its semantics, such as whether it holds strong or weak references. If a VM holds a weak reference in a word as a pointer, it can also use SimpleSlot for weak reference fields.

Required Methods§

source

fn load(&self) -> Option<ObjectReference>

Load object reference from the slot.

If the slot is not holding an object reference (For example, if it is holding NULL or a tagged non-reference value. See trait-level doc comment.), this method should return None.

If the slot holds an object reference with tag bits, the returned value shall be the object reference with the tag bits removed.

source

fn store(&self, object: ObjectReference)

Store the object reference object into the slot.

If the slot holds an object reference with tag bits, this method must preserve the tag bits while updating the object reference so that it points to the forwarded object given by the parameter object.

FIXME: This design is inefficient for handling object references with tag bits. Consider introducing a new updating function to do the load, trace and store in one function. See: https://github.com/mmtk/mmtk-core/issues/1033

FIXME: This method is currently used by both moving GC algorithms and the subsuming write barrier (crate::memory_manager::object_reference_write). The two reference writing operations have different semantics, and need to be implemented differently if the VM supports offsetted or tagged references. See: https://github.com/mmtk/mmtk-core/issues/1038

Provided Methods§

source

fn prefetch_load(&self)

Prefetch the slot so that a subsequent load will be faster.

source

fn prefetch_store(&self)

Prefetch the slot so that a subsequent store will be faster.

Object Safety§

This trait is not object safe.

Implementors§

source§

impl Slot for Address

For backword compatibility, we let Address implement Slot with the same semantics as SimpleSlot so that existing bindings that use Address as Slot can continue to work.

However, we should use SimpleSlot directly instead of using Address. The purpose of the Address type is to represent an address in memory. It is not directly related to fields that hold references to other objects. Calling load() and store() on an Address does not indicate how many bytes to load or store, or how to interpret those bytes. On the other hand, SimpleSlot is all about how to access a field that holds a reference represented simply as an ObjectReference. The intention and the semantics are clearer with SimpleSlot.

source§

impl Slot for SimpleSlot