Record Class LockIdentityValue
- All Implemented Interfaces:
AbstractValue
MutexLock object(s) a variable may currently
refer to at a given program point.
The identityTokens set carries every identity the variable could
have. In the common case the set is a singleton (one known lock); branch
joins, polymorphic-getter resolution, and call-site argument bindings
introduce multi-element sets. Phase C.3 iterates the cross-product of
outer × inner identities when applying the deadlock verdict — if any pair
forms a cycle (E08252) or a cross-thread same-lock pattern (E08253) the
error fires.
Each element is one of two token shapes:
- Allocation token — an opaque
Objectreference, freshly minted perMutexLock(...)constructor call site. Compared by Java==.ISymbolreferences (for field-rooted and capture-rooted receivers) follow the same rule — A.4 freshness guarantees one symbol per allocation. PlaceholderToken— symbolic identity for a parameter whose underlying object is unknown until resolved at a call site. Compared structurally on parameter FQN.
Why custom token equality and not the JDK Set contract:
Symbol.equals(Object) is structural by name +
category + genus + mutability. Two distinct fields both named lock
on different classes would compare equal under that contract. If we relied
on default HashSet/Set.copyOf semantics, those two
physically-distinct locks would silently collapse to one element, missing a
potential lock-order cycle. So this record stores its tokens in a
deduplicated backing collection that enforces the per-token-type equality
rules below (tokensEqual(Object, Object), tokenHash(Object)) and overrides
equals/hashCode to use the same rules for set-level
comparison. The public identityTokens() accessor returns an
unmodifiable view; iterators preserve insertion order.
Why set-union lattice for deadlock detection: the usual constant-folding lattice widens to TOP when paths disagree because the downstream consumer only acts on certainty. Deadlock detection is the opposite — it acts on possibility. If any execution path could pair the outer hold with an inner enter that forms a cycle, we want to warn. So the join unions sets rather than widening; the verdict iterates all pairs; one bad pair is enough.
-
Constructor Summary
ConstructorsConstructorDescriptionLockIdentityValue(Set<Object> identityTokens) Creates an instance of aLockIdentityValuerecord class. -
Method Summary
Modifier and TypeMethodDescriptionbooleanIndicates whether some other object is "equal to" this one.evaluateCondition(String operator, AbstractValue operand) Evaluate whether this abstract value satisfies a comparison condition.static LockIdentityValuefromTokens(Iterable<? extends Object> tokens) Build a value from a collection of tokens, applying token-rule dedup.inthashCode()Returns a hash code value for this object.booleanConvenience accessor:truewhen at least one element of the set is aPlaceholderToken.Returns the value of theidentityTokensrecord component.booleanisBottom()Check if this value represents an unreachable program point.booleanisKnown()Check if this value represents a known state (not TOP and not BOTTOM).join(AbstractValue other) Join this value with another at a branch convergence point.static LockIdentityValueSingleton factory — wraps one identity token.(package private) static intToken hash consistent withtokensEqual(Object, Object): structural hash forPlaceholderToken, identity hash for everything else.(package private) static booleantokensEqual(Object a, Object b) Token equality: structural forPlaceholderToken, identity (==) for everything else.toString()Returns a string representation of this record class.Methods inherited from interface AbstractValue
isKnownSet
-
Constructor Details
-
LockIdentityValue
-
-
Method Details
-
of
Singleton factory — wraps one identity token. Used for the common case where a variable has exactly one possible identity at this program point. -
fromTokens
Build a value from a collection of tokens, applying token-rule dedup. -
hasPlaceholder
public boolean hasPlaceholder()Convenience accessor:truewhen at least one element of the set is aPlaceholderToken. A set may carry mixed token types (an allocation + a placeholder, post-substitution at a polymorphic call site). -
join
Description copied from interface:AbstractValueJoin this value with another at a branch convergence point. Returns the least upper bound of the two values.Key rules:
- BOTTOM join X = X (unreachable path is ignored)
- X join BOTTOM = X
- TOP join X = TOP
- Constant(a) join Constant(a) = Constant(a) (both agree)
- Constant(a) join Constant(b) = TOP (disagreement)
- Specified by:
joinin interfaceAbstractValue
-
evaluateCondition
Description copied from interface:AbstractValueEvaluate whether this abstract value satisfies a comparison condition.- Specified by:
evaluateConditionin interfaceAbstractValue- Parameters:
operator- the comparison operator (==, <>, <, >, etc.)operand- the right-hand side value to compare against- Returns:
- TRUE if condition is always satisfied, FALSE if never satisfied, UNKNOWN if indeterminate
-
isKnown
public boolean isKnown()Description copied from interface:AbstractValueCheck if this value represents a known state (not TOP and not BOTTOM).- Specified by:
isKnownin interfaceAbstractValue
-
isBottom
public boolean isBottom()Description copied from interface:AbstractValueCheck if this value represents an unreachable program point.- Specified by:
isBottomin interfaceAbstractValue
-
equals
Indicates whether some other object is "equal to" this one. The objects are equal if the other object is of the same class and if all the record components are equal. All components in this record class are compared withObjects::equals(Object,Object). -
hashCode
-
toString
-
tokensEqual
Token equality: structural forPlaceholderToken, identity (==) for everything else. -
tokenHash
Token hash consistent withtokensEqual(Object, Object): structural hash forPlaceholderToken, identity hash for everything else. -
identityTokens
-