Object-Monitor Implementation

This is blog 3 in the OpenJ9 locking/synchronization series (blog 1). It covers a data structure named object-monitor which is used to enforce synchronization for the Java objects. Before reading this blog, one needs to have knowledge about the system-monitors (blog 2). Please read the blog on the system-monitors before reading this blog.

In OpenJ9, object-monitors (J9ObjectMonitor) are implemented using three-tier spinning and tasuki (bi-modal) locks. Tasuki locks are derived from thin/flat locks. So, it is helpful to understand how thin/flat locks before diving into tasuki locks. Refer to the references below to explore thin/flat and tasuki locks [1][2][3].

An object-monitor can operate in two states: flat and inflated, which highlights the bi-modal characteristics. A lock-word represents a thin/flat lock, and it is used in the flat state where a maximum of one thread can spin on the lock-word if there is brief lock contention. A lock-word becomes insufficient when a single thread can no longer acquire the object-monitor by spinning on the lock-word or more than one thread try to acquire the object-monitor simultaneously. In such cases, the object-monitor transitions from the flat to inflated state where a system-monitor is used to enforce synchronization using the operating system (OS) structures such as mutexes, condition variables, semaphores, etc. Once the lock contention subsides i.e. the lock-word can be relied on to acquire the object-monitor, then the object-monitor’s state reverts from the inflated to flat state, which is referred as deflation. The figure below illustrates the state transition in the object-monitors.

State transition in object-monitors (based on tasuki locks)

Generally, a lock-word is stored in an object’s header. With the lock nursery not all objects have a lock-word in the object’s header. In such cases, there is an alternate lock-word in the J9ObjectMonitor structure which links an object to its system-monitor.

The system-monitors (omrthread_monitor_t) are lazy initialized.

A simplified view of the object-monitor is shown in the table below:

FlatLightweightLock-word; compare-and-swap operation.
FlatHeavyweightSystem-monitor; blocking enter with time-out; transition from flat to inflated state when the lock is released.
InflatedLightweightSystem-monitor; try-enter.
InflatedHeavyweightSystem-monitor; blocking enter.

The lightweight lock implementation in the flat state allows the just-in-time (JIT) compiler to inline a fast check for acquiring the lock

When a thread transitions to using the flat heavyweight state, then all subsequent threads bypass the flat lightweight state, and go directly to the flat heavyweight state until the lock is inflated.

In the inflated state, the lock reverts to the flat state when there are no threads waiting to acquire the lock. This is managed using a deflation policy. The different deflation policies are shown below:

asap Deflate as soon as possible.
never Never deflate once inflated.
smart Minimize transitions between the inflated and deflated states using the inflation and deflation history.

The default deflation policy is asap across all the platforms. The deflation policy can be changed using the following command line option:

java -Xthr:deflationPolicy=<POLICY> ...

A system-monitor and object-monitor have their own lock-words. Unlike the complicated lock-word of an object-monitor, a system-monitor’s lock-word only stores the lock state since it is not bi-modal. When a thread tries to acquire an object-monitor,

  • It may spin in the flat or inflated states.
  • It may spin in the flat state followed by spinning in the inflated state.
  • Each of the lock states employ three-tier spinning.

[References] The following works cover thin and tasuki locks:

  1. Thin locks (bi-modal) reduce the most common case of locking to a single compare-and-swap operation:
  2. Tasuki (bi-modal) locks allow inflation without busy-wait and deflation; they are an extension of thin locks:
  3. Java Locks: Analysis and Acceleration by Kiyokuni Kawachiya [PHD; based on tasuki/thin locks; new features include lock reservation and asymmetric locks].


Suggested Readings

The next blog in the OpenJ9 locking/synchronization series covers the three-tier spinning (blog 4) feature, which provides incrementally larger wait-intervals between attempts to acquire a lock while spinning.

[Note] Not all the command line options, mentioned above, may have customer support. Some options are only available for experimental work.

5 Replies to “Object-Monitor Implementation”

Leave a Reply