Theory Voblint_Domain.Reachability_Lift
theory Reachability_Lift
imports State_Concretization "HOL-Library.Monad_Syntax"
begin
section ‹Explicit reachability over an abstract carrier›
text ‹
The outer ‹Bot› represents an unreachable control-flow point; ‹Lifted a›
represents a reachable point carrying ‹a›. The construction provides the
order, joins, solver updates, concretization, and normalized transfer
combinators independently of any particular abstract-state representation.
›
text ‹
Mirrors Goblint's lifted-domain construction
(@{url ‹https://github.com/goblint/analyzer/blob/master/src/framework/analyses.ml›}):
‹module Dom (LD: Lattice.S) = struct include Lattice.LiftConf (...) (LD) ... end›, whose
outer ‹`Bot› means dead code and whose ‹unlift› only accepts ‹`Lifted x›. Reachability is
carried as an explicit tag on top of the analysis-local state, not rediscovered from the
state's own contents. ‹Bot› mirrors Goblint's lifted ‹`Bot›; ‹Lifted› mirrors ‹`Lifted›.
Goblint's lift also carries an outer ‹`Top›, but not merely as a substitute for a missing
payload ‹top›: ‹Lattice.LiftConf›'s ‹join›/‹widen› fall back to ‹`Top› whenever the base
domain's own ‹join›/‹widen› raises ‹TopValue› or ‹Uncomparable›, i.e. whenever the base
domain is partial enough that two of its values have no expressible join, and ‹unlift›
rejects ‹`Top› exactly like ‹`Bot›. Every @{class numeric_domain} instance here is instead a
total ‹bounded_semilattice_sup_bot› with its own ‹top›: ‹⊔› and ‹∇› always return a value,
so a lifted operation here can never fail the way Goblint's can, and ‹Lifted top› already
says everything an outer ‹`Top› would. This lift therefore stays two-valued. At the raw
lifted representation, ‹Bot› is strictly below every ‹Lifted a›
regardless of ‹a› -- including ‹Lifted bot›, which remains distinct from ‹Bot› even
though ‹a› is itself locally bottom -- since dead-by-construction and
reachable-but-locally-bottom are the two concepts this lift exists to keep separate. The
normalization discipline developed below (‹normalize_lift›, ‹normalized_lift›) then
layers a stronger, Voblint-specific invariant on top: every solver-facing payload an
arbitrary caller-supplied predicate ‹empty_pred› classifies as bottom is additionally
canonicalized to structural ‹Bot›, so ‹Lifted a› with an ‹empty_pred›-bottom ‹a› never
actually escapes a value-producing step in practice, even though the raw datatype and
order permit it. This theory does not know or assume that ‹empty_pred› means semantic
emptiness -- ‹Nonrelational_Reachability› is where ‹empty_pred› is instantiated to
‹is_empty_state› and proved to coincide with an empty concretization.
›
subsection ‹The lifted order and lattice structure›