Cortex.Pulse.Closure
On this page
Imports
import Cortex.Pulse.FrontierOverview
Failure closure propagates failed status through the fixed topology while
leaving terminal successes and skipped/rewritten nodes intact. This is
the structural part of the runtime's propagateFailure: it says nothing
about failure payloads, retry policy, or operator-facing diagnostics.
Context
The closure operator is the main Paper 1 recovery law: once a node fails, every still-propagatable descendant must fail too. The model keeps the operator extensional and proves the closure/fixed-point facts needed by recovery.
Theorem Split
The page defines failed ancestors, defines the closure operator, proves that one pass is failure-complete, and finishes with idempotence.
namespace Cortex.Pulsevariable {ν : Type u} {payload : Type v}Failed-Ancestor Model
hasFailedAncestor G state node means the node has a strict failed ancestor.
def hasFailedAncestor
(G : DAG ν)
(state : GraphState ν payload)
(node : ν) : Prop :=
∃ failedNode : ν,
state.status failedNode = NodeStatus.failed ∧ G.reaches failedNode node
failureClosureComplete G state means failure is closed over propagatable descendants.
A state is failure-closed when propagatable descendants of failed nodes are already marked failed.
def failureClosureComplete
(G : DAG ν)
(state : GraphState ν payload) : Prop :=
∀ failedNode node : ν,
state.status failedNode = NodeStatus.failed →
G.reaches failedNode node →
NodeStatus.propagatable (state.status node) →
state.status node = NodeStatus.failedClosure Operator
propagateStatus G state node is the single-node failure-closure status update.
noncomputable def propagateStatus
(G : DAG ν)
(state : GraphState ν payload)
(node : ν) : NodeStatus := ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadnode:ν⊢ NodeStatus
classical
All goals completed! 🐙
propagateFailure G state propagates failure to pending or waiting descendants.
noncomputable def propagateFailure
(G : DAG ν)
(state : GraphState ν payload) : GraphState ν payload where
status := fun node => propagateStatus G state node
output := state.outputClosure Facts
propagateFailure_preserves_failed shows existing failed nodes stay failed.
theorem propagateFailure_preserves_failed
(G : DAG ν)
(state : GraphState ν payload)
{node : ν}
(hFailed : state.status node = NodeStatus.failed) :
(propagateFailure G state).status node = NodeStatus.failed := ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadnode:νhFailed:state.status node = NodeStatus.failed⊢ (propagateFailure G state).status node = NodeStatus.failed
classical
All goals completed! 🐙
propagateFailure_marks_failed_descendant marks propagatable failed descendants.
theorem propagateFailure_marks_failed_descendant
(G : DAG ν)
(state : GraphState ν payload)
{node : ν}
(hPropagatable : NodeStatus.propagatable (state.status node))
(hAncestor : hasFailedAncestor G state node) :
(propagateFailure G state).status node = NodeStatus.failed := ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadnode:νhPropagatable:(state.status node).propagatablehAncestor:hasFailedAncestor G state node⊢ (propagateFailure G state).status node = NodeStatus.failed
classical
All goals completed! 🐙
propagatable_of_propagate recovers original propagatability after propagation.
theorem propagatable_of_propagate
(G : DAG ν)
(state : GraphState ν payload)
{node : ν}
(hPropagatable :
NodeStatus.propagatable ((propagateFailure G state).status node)) :
NodeStatus.propagatable (state.status node) := ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadnode:νhPropagatable:((propagateFailure G state).status node).propagatable⊢ (state.status node).propagatable
classical
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadnode:νhPropagatable:((propagateFailure G state).status node).propagatablehClosed:(state.status node).propagatable ∧ hasFailedAncestor G state node⊢ (state.status node).propagatableν:Type upayload:Type vG:DAG νstate:GraphState ν payloadnode:νhPropagatable:((propagateFailure G state).status node).propagatablehClosed:¬((state.status node).propagatable ∧ hasFailedAncestor G state node)⊢ (state.status node).propagatable
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadnode:νhPropagatable:((propagateFailure G state).status node).propagatablehClosed:(state.status node).propagatable ∧ hasFailedAncestor G state node⊢ (state.status node).propagatable All goals completed! 🐙
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadnode:νhPropagatable:((propagateFailure G state).status node).propagatablehClosed:¬((state.status node).propagatable ∧ hasFailedAncestor G state node)⊢ (state.status node).propagatable All goals completed! 🐙
failed_after_propagate_origin identifies why a node is failed after propagation.
Every failed node after propagation either was failed already or had an original failed ancestor.
theorem failed_after_propagate
(G : DAG ν)
(state : GraphState ν payload)
{node : ν}
(hFailed : (propagateFailure G state).status node = NodeStatus.failed) :
state.status node = NodeStatus.failed ∨ hasFailedAncestor G state node := ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadnode:νhFailed:(propagateFailure G state).status node = NodeStatus.failed⊢ state.status node = NodeStatus.failed ∨ hasFailedAncestor G state node
classical
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadnode:νhFailed:(propagateFailure G state).status node = NodeStatus.failedhClosed:(state.status node).propagatable ∧ hasFailedAncestor G state node⊢ state.status node = NodeStatus.failed ∨ hasFailedAncestor G state nodeν:Type upayload:Type vG:DAG νstate:GraphState ν payloadnode:νhFailed:(propagateFailure G state).status node = NodeStatus.failedhClosed:¬((state.status node).propagatable ∧ hasFailedAncestor G state node)⊢ state.status node = NodeStatus.failed ∨ hasFailedAncestor G state node
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadnode:νhFailed:(propagateFailure G state).status node = NodeStatus.failedhClosed:(state.status node).propagatable ∧ hasFailedAncestor G state node⊢ state.status node = NodeStatus.failed ∨ hasFailedAncestor G state node All goals completed! 🐙
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadnode:νhFailed:(propagateFailure G state).status node = NodeStatus.failedhClosed:¬((state.status node).propagatable ∧ hasFailedAncestor G state node)⊢ state.status node = NodeStatus.failed ∨ hasFailedAncestor G state node have hOriginal : state.status node = NodeStatus.failed := ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadnode:νhFailed:(propagateFailure G state).status node = NodeStatus.failed⊢ state.status node = NodeStatus.failed ∨ hasFailedAncestor G state node
All goals completed! 🐙
All goals completed! 🐙
failed_after_propagate_has_original_failed_ancestor traces propagated failures.
A failed node produced by propagation still traces back to an original failed ancestor for every descendant it reaches.
theorem hasFailedAncestor_of_failed_after_reaches
(G : DAG ν)
(state : GraphState ν payload)
{failedNode node : ν}
(hFailed : (propagateFailure G state).status failedNode = NodeStatus.failed)
(hReach : G.reaches failedNode node) :
hasFailedAncestor G state node := ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadfailedNode:νnode:νhFailed:(propagateFailure G state).status failedNode = NodeStatus.failedhReach:G.reaches failedNode node⊢ hasFailedAncestor G state node
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadfailedNode:νnode:νhFailed:(propagateFailure G state).status failedNode = NodeStatus.failedhReach:G.reaches failedNode nodehOriginalFailed:state.status failedNode = NodeStatus.failed⊢ hasFailedAncestor G state nodeν:Type upayload:Type vG:DAG νstate:GraphState ν payloadfailedNode:νnode:νhFailed:(propagateFailure G state).status failedNode = NodeStatus.failedhReach:G.reaches failedNode nodehAncestor:hasFailedAncestor G state failedNode⊢ hasFailedAncestor G state node
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadfailedNode:νnode:νhFailed:(propagateFailure G state).status failedNode = NodeStatus.failedhReach:G.reaches failedNode nodehOriginalFailed:state.status failedNode = NodeStatus.failed⊢ hasFailedAncestor G state node All goals completed! 🐙
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadfailedNode:νnode:νhFailed:(propagateFailure G state).status failedNode = NodeStatus.failedhReach:G.reaches failedNode nodehAncestor:hasFailedAncestor G state failedNode⊢ hasFailedAncestor G state node ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadfailedNode:νnode:νhFailed:(propagateFailure G state).status failedNode = NodeStatus.failedhReach:G.reaches failedNode noderoot:νhRootFailed:state.status root = NodeStatus.failedhRootReach:G.reaches root failedNode⊢ hasFailedAncestor G state node
All goals completed! 🐙
hasFailedAncestor_monotone lifts failed ancestors through failure-growth.
theorem hasFailedAncestor_monotone
(G : DAG ν)
{left right : GraphState ν payload}
(hLe : GraphState.failureLe left right)
{node : ν}
(hAncestor : hasFailedAncestor G left node) :
hasFailedAncestor G right node := ν:Type upayload:Type vG:DAG νleft:GraphState ν payloadright:GraphState ν payloadhLe:left.failureLe rightnode:νhAncestor:hasFailedAncestor G left node⊢ hasFailedAncestor G right node
ν:Type upayload:Type vG:DAG νleft:GraphState ν payloadright:GraphState ν payloadhLe:left.failureLe rightnode:νfailedNode:νhFailed:left.status failedNode = NodeStatus.failedhReach:G.reaches failedNode node⊢ hasFailedAncestor G right node
All goals completed! 🐙
propagateFailure_extensive proves propagation is extensive over failed nodes.
Use this closure-law theorem when a proof only needs preservation of the
already-failed set. Use propagateFailure_monotone for whole-state
failure-growth reasoning through GraphState.failureLe.
theorem propagateFailure_extensive
(G : DAG ν)
(state : GraphState ν payload) :
∀ node : ν,
state.status node = NodeStatus.failed →
(propagateFailure G state).status node = NodeStatus.failed := ν:Type upayload:Type vG:DAG νstate:GraphState ν payload⊢ ∀ (node : ν), state.status node = NodeStatus.failed → (propagateFailure G state).status node = NodeStatus.failed
intro node ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadnode:νhFailed:state.status node = NodeStatus.failed⊢ (propagateFailure G state).status node = NodeStatus.failed
All goals completed! 🐙
propagateStatus_monotone proves node-local failure propagation is monotone.
theorem propagateStatus_monotone
(G : DAG ν)
{left right : GraphState ν payload}
(hLe : GraphState.failureLe left right)
(node : ν) :
NodeStatus.failureLe (propagateStatus G left node) (propagateStatus G right node) := ν:Type upayload:Type vG:DAG νleft:GraphState ν payloadright:GraphState ν payloadhLe:left.failureLe rightnode:ν⊢ (propagateStatus G left node).failureLe (propagateStatus G right node)
classical
ν:Type upayload:Type vG:DAG νleft:GraphState ν payloadright:GraphState ν payloadhLe:left.failureLe rightnode:νhLeftClosed:(left.status node).propagatable ∧ hasFailedAncestor G left node⊢ (propagateStatus G left node).failureLe (propagateStatus G right node)ν:Type upayload:Type vG:DAG νleft:GraphState ν payloadright:GraphState ν payloadhLe:left.failureLe rightnode:νhLeftClosed:¬((left.status node).propagatable ∧ hasFailedAncestor G left node)⊢ (propagateStatus G left node).failureLe (propagateStatus G right node)
ν:Type upayload:Type vG:DAG νleft:GraphState ν payloadright:GraphState ν payloadhLe:left.failureLe rightnode:νhLeftClosed:(left.status node).propagatable ∧ hasFailedAncestor G left node⊢ (propagateStatus G left node).failureLe (propagateStatus G right node) have hRightFailed : propagateStatus G right node = NodeStatus.failed := ν:Type upayload:Type vG:DAG νleft:GraphState ν payloadright:GraphState ν payloadhLe:left.failureLe rightnode:ν⊢ (propagateStatus G left node).failureLe (propagateStatus G right node)
ν:Type upayload:Type vG:DAG νleft:GraphState ν payloadright:GraphState ν payloadhLe:left.failureLe rightnode:νhLeftClosed:(left.status node).propagatable ∧ hasFailedAncestor G left nodehSame:left.status node = right.status node⊢ propagateStatus G right node = NodeStatus.failedν:Type upayload:Type vG:DAG νleft:GraphState ν payloadright:GraphState ν payloadhLe:left.failureLe rightnode:νhLeftClosed:(left.status node).propagatable ∧ hasFailedAncestor G left nodehFailure:(left.status node).propagatable ∧ right.status node = NodeStatus.failed⊢ propagateStatus G right node = NodeStatus.failed
ν:Type upayload:Type vG:DAG νleft:GraphState ν payloadright:GraphState ν payloadhLe:left.failureLe rightnode:νhLeftClosed:(left.status node).propagatable ∧ hasFailedAncestor G left nodehSame:left.status node = right.status node⊢ propagateStatus G right node = NodeStatus.failed have hRightClosed :
NodeStatus.propagatable (right.status node) ∧ hasFailedAncestor G right node := ν:Type upayload:Type vG:DAG νleft:GraphState ν payloadright:GraphState ν payloadhLe:left.failureLe rightnode:ν⊢ (propagateStatus G left node).failureLe (propagateStatus G right node)
ν:Type upayload:Type vG:DAG νleft:GraphState ν payloadright:GraphState ν payloadhLe:left.failureLe rightnode:νhLeftClosed:(left.status node).propagatable ∧ hasFailedAncestor G left nodehSame:left.status node = right.status node⊢ (right.status node).propagatableν:Type upayload:Type vG:DAG νleft:GraphState ν payloadright:GraphState ν payloadhLe:left.failureLe rightnode:νhLeftClosed:(left.status node).propagatable ∧ hasFailedAncestor G left nodehSame:left.status node = right.status node⊢ hasFailedAncestor G right node
ν:Type upayload:Type vG:DAG νleft:GraphState ν payloadright:GraphState ν payloadhLe:left.failureLe rightnode:νhLeftClosed:(left.status node).propagatable ∧ hasFailedAncestor G left nodehSame:left.status node = right.status node⊢ (right.status node).propagatable All goals completed! 🐙
ν:Type upayload:Type vG:DAG νleft:GraphState ν payloadright:GraphState ν payloadhLe:left.failureLe rightnode:νhLeftClosed:(left.status node).propagatable ∧ hasFailedAncestor G left nodehSame:left.status node = right.status node⊢ hasFailedAncestor G right node All goals completed! 🐙
All goals completed! 🐙
ν:Type upayload:Type vG:DAG νleft:GraphState ν payloadright:GraphState ν payloadhLe:left.failureLe rightnode:νhLeftClosed:(left.status node).propagatable ∧ hasFailedAncestor G left nodehFailure:(left.status node).propagatable ∧ right.status node = NodeStatus.failed⊢ propagateStatus G right node = NodeStatus.failed ν:Type upayload:Type vG:DAG νleft:GraphState ν payloadright:GraphState ν payloadhLe:left.failureLe rightnode:νhLeftClosed:(left.status node).propagatable ∧ hasFailedAncestor G left node_hLeftPropagatable:(left.status node).propagatablehRightStatus:right.status node = NodeStatus.failed⊢ propagateStatus G right node = NodeStatus.failed
All goals completed! 🐙
have hLeftFailed : propagateStatus G left node = NodeStatus.failed := ν:Type upayload:Type vG:DAG νleft:GraphState ν payloadright:GraphState ν payloadhLe:left.failureLe rightnode:ν⊢ (propagateStatus G left node).failureLe (propagateStatus G right node)
All goals completed! 🐙
ν:Type upayload:Type vG:DAG νleft:GraphState ν payloadright:GraphState ν payloadhLe:left.failureLe rightnode:νhLeftClosed:(left.status node).propagatable ∧ hasFailedAncestor G left nodehRightFailed:propagateStatus G right node = NodeStatus.failedhLeftFailed:propagateStatus G left node = NodeStatus.failed⊢ NodeStatus.failed.failureLe NodeStatus.failed
All goals completed! 🐙
ν:Type upayload:Type vG:DAG νleft:GraphState ν payloadright:GraphState ν payloadhLe:left.failureLe rightnode:νhLeftClosed:¬((left.status node).propagatable ∧ hasFailedAncestor G left node)⊢ (propagateStatus G left node).failureLe (propagateStatus G right node) ν:Type upayload:Type vG:DAG νleft:GraphState ν payloadright:GraphState ν payloadhLe:left.failureLe rightnode:νhLeftClosed:¬((left.status node).propagatable ∧ hasFailedAncestor G left node)hRightClosed:(right.status node).propagatable ∧ hasFailedAncestor G right node⊢ (propagateStatus G left node).failureLe (propagateStatus G right node)ν:Type upayload:Type vG:DAG νleft:GraphState ν payloadright:GraphState ν payloadhLe:left.failureLe rightnode:νhLeftClosed:¬((left.status node).propagatable ∧ hasFailedAncestor G left node)hRightClosed:¬((right.status node).propagatable ∧ hasFailedAncestor G right node)⊢ (propagateStatus G left node).failureLe (propagateStatus G right node)
ν:Type upayload:Type vG:DAG νleft:GraphState ν payloadright:GraphState ν payloadhLe:left.failureLe rightnode:νhLeftClosed:¬((left.status node).propagatable ∧ hasFailedAncestor G left node)hRightClosed:(right.status node).propagatable ∧ hasFailedAncestor G right node⊢ (propagateStatus G left node).failureLe (propagateStatus G right node) ν:Type upayload:Type vG:DAG νleft:GraphState ν payloadright:GraphState ν payloadhLe:left.failureLe rightnode:νhLeftClosed:¬((left.status node).propagatable ∧ hasFailedAncestor G left node)hRightClosed:(right.status node).propagatable ∧ hasFailedAncestor G right nodehLeftPropagatable:(left.status node).propagatable⊢ (propagateStatus G left node).failureLe (propagateStatus G right node)
All goals completed! 🐙
ν:Type upayload:Type vG:DAG νleft:GraphState ν payloadright:GraphState ν payloadhLe:left.failureLe rightnode:νhLeftClosed:¬((left.status node).propagatable ∧ hasFailedAncestor G left node)hRightClosed:¬((right.status node).propagatable ∧ hasFailedAncestor G right node)⊢ (propagateStatus G left node).failureLe (propagateStatus G right node) All goals completed! 🐙
propagateFailure_monotone proves failure closure is monotone over failure-growth.
theorem propagateFailure_monotone
(G : DAG ν)
{left right : GraphState ν payload}
(hLe : GraphState.failureLe left right) :
GraphState.failureLe (propagateFailure G left) (propagateFailure G right) := ν:Type upayload:Type vG:DAG νleft:GraphState ν payloadright:GraphState ν payloadhLe:left.failureLe right⊢ (propagateFailure G left).failureLe (propagateFailure G right)
ν:Type upayload:Type vG:DAG νleft:GraphState ν payloadright:GraphState ν payloadhLe:left.failureLe rightnode:ν⊢ ((propagateFailure G left).status node).failureLe ((propagateFailure G right).status node)
All goals completed! 🐙
propagateFailure_failureClosureComplete proves propagation reaches closure.
theorem propagateFailure_failureClosureComplete
(G : DAG ν)
(state : GraphState ν payload) :
failureClosureComplete G (propagateFailure G state) := ν:Type upayload:Type vG:DAG νstate:GraphState ν payload⊢ failureClosureComplete G (propagateFailure G state)
intro failedNode ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadfailedNode:νnode:ν⊢ (propagateFailure G state).status failedNode = NodeStatus.failed →
G.reaches failedNode node →
((propagateFailure G state).status node).propagatable → (propagateFailure G state).status node = NodeStatus.failed ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadfailedNode:νnode:νhFailed:(propagateFailure G state).status failedNode = NodeStatus.failed⊢ G.reaches failedNode node →
((propagateFailure G state).status node).propagatable → (propagateFailure G state).status node = NodeStatus.failed ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadfailedNode:νnode:νhFailed:(propagateFailure G state).status failedNode = NodeStatus.failedhReach:G.reaches failedNode node⊢ ((propagateFailure G state).status node).propagatable → (propagateFailure G state).status node = NodeStatus.failed ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadfailedNode:νnode:νhFailed:(propagateFailure G state).status failedNode = NodeStatus.failedhReach:G.reaches failedNode nodehPropagatable:((propagateFailure G state).status node).propagatable⊢ (propagateFailure G state).status node = NodeStatus.failed
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadfailedNode:νnode:νhFailed:(propagateFailure G state).status failedNode = NodeStatus.failedhReach:G.reaches failedNode nodehPropagatable:((propagateFailure G state).status node).propagatablehAncestor:hasFailedAncestor G state node⊢ (propagateFailure G state).status node = NodeStatus.failed
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadfailedNode:νnode:νhFailed:(propagateFailure G state).status failedNode = NodeStatus.failedhReach:G.reaches failedNode nodehPropagatable:((propagateFailure G state).status node).propagatablehAncestor:hasFailedAncestor G state nodehOriginalPropagatable:(state.status node).propagatable⊢ (propagateFailure G state).status node = NodeStatus.failed
All goals completed! 🐙Normalization Preservation
propagateFailure_preserves_noRunning preserves the absence of running nodes.
theorem propagateFailure_preserves_noRunning
(G : DAG ν)
(state : GraphState ν payload)
(hNoRunning : GraphState.noRunningNodes state) :
GraphState.noRunningNodes (propagateFailure G state) := ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhNoRunning:state.noRunningNodes⊢ (propagateFailure G state).noRunningNodes
classical
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhNoRunning:state.noRunningNodesnode:ν⊢ (propagateFailure G state).status node ≠ NodeStatus.running
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhNoRunning:state.noRunningNodesnode:νhClosed:(state.status node).propagatable ∧ hasFailedAncestor G state node⊢ (propagateFailure G state).status node ≠ NodeStatus.runningν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhNoRunning:state.noRunningNodesnode:νhClosed:¬((state.status node).propagatable ∧ hasFailedAncestor G state node)⊢ (propagateFailure G state).status node ≠ NodeStatus.running
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhNoRunning:state.noRunningNodesnode:νhClosed:(state.status node).propagatable ∧ hasFailedAncestor G state node⊢ (propagateFailure G state).status node ≠ NodeStatus.running ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhNoRunning:state.noRunningNodesnode:νhClosed:(state.status node).propagatable ∧ hasFailedAncestor G state nodehRunning:(propagateFailure G state).status node = NodeStatus.running⊢ False
All goals completed! 🐙
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhNoRunning:state.noRunningNodesnode:νhClosed:¬((state.status node).propagatable ∧ hasFailedAncestor G state node)⊢ (propagateFailure G state).status node ≠ NodeStatus.running All goals completed! 🐙
propagateFailure_preserves_noInterrupted preserves the absence of interrupted nodes.
theorem propagateFailure_preserves_noInterrupted
(G : DAG ν)
(state : GraphState ν payload)
(hNoInterrupted : GraphState.noInterruptedNodes state) :
GraphState.noInterruptedNodes (propagateFailure G state) := ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhNoInterrupted:state.noInterruptedNodes⊢ (propagateFailure G state).noInterruptedNodes
classical
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhNoInterrupted:state.noInterruptedNodesnode:ν⊢ (propagateFailure G state).status node ≠ NodeStatus.interrupted
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhNoInterrupted:state.noInterruptedNodesnode:νhClosed:(state.status node).propagatable ∧ hasFailedAncestor G state node⊢ (propagateFailure G state).status node ≠ NodeStatus.interruptedν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhNoInterrupted:state.noInterruptedNodesnode:νhClosed:¬((state.status node).propagatable ∧ hasFailedAncestor G state node)⊢ (propagateFailure G state).status node ≠ NodeStatus.interrupted
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhNoInterrupted:state.noInterruptedNodesnode:νhClosed:(state.status node).propagatable ∧ hasFailedAncestor G state node⊢ (propagateFailure G state).status node ≠ NodeStatus.interrupted ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhNoInterrupted:state.noInterruptedNodesnode:νhClosed:(state.status node).propagatable ∧ hasFailedAncestor G state nodehInterrupted:(propagateFailure G state).status node = NodeStatus.interrupted⊢ False
All goals completed! 🐙
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhNoInterrupted:state.noInterruptedNodesnode:νhClosed:¬((state.status node).propagatable ∧ hasFailedAncestor G state node)⊢ (propagateFailure G state).status node ≠ NodeStatus.interrupted All goals completed! 🐙
propagateFailure_preserves_topologyDomain preserves off-topology absence.
theorem propagateFailure_preserves_topologyDomain
(G : DAG ν)
(state : GraphState ν payload)
(hDomain : GraphState.topologyDomain G state) :
GraphState.topologyDomain G (propagateFailure G state) := ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhDomain:GraphState.topologyDomain G state⊢ GraphState.topologyDomain G (propagateFailure G state)
classical
intro node ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhDomain:GraphState.topologyDomain G statenode:νhNotMem:node ∉ G.nodes⊢ (propagateFailure G state).status node = NodeStatus.pending ∧ (propagateFailure G state).output node = none
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhDomain:GraphState.topologyDomain G statenode:νhNotMem:node ∉ G.nodeshStatus:state.status node = NodeStatus.pendinghOutput:state.output node = none⊢ (propagateFailure G state).status node = NodeStatus.pending ∧ (propagateFailure G state).output node = none
have hNoAncestor : ¬ hasFailedAncestor G state node := ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhDomain:GraphState.topologyDomain G state⊢ GraphState.topologyDomain G (propagateFailure G state)
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhDomain:GraphState.topologyDomain G statenode:νhNotMem:node ∉ G.nodeshStatus:state.status node = NodeStatus.pendinghOutput:state.output node = nonehAncestor:hasFailedAncestor G state node⊢ False
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhDomain:GraphState.topologyDomain G statenode:νhNotMem:node ∉ G.nodeshStatus:state.status node = NodeStatus.pendinghOutput:state.output node = none_failedNode:ν_hFailed:state.status _failedNode = NodeStatus.failedhReach:G.reaches _failedNode node⊢ False
All goals completed! 🐙
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhDomain:GraphState.topologyDomain G statenode:νhNotMem:node ∉ G.nodeshStatus:state.status node = NodeStatus.pendinghOutput:state.output node = nonehNoAncestor:¬hasFailedAncestor G state node⊢ (propagateFailure G state).status node = NodeStatus.pendingν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhDomain:GraphState.topologyDomain G statenode:νhNotMem:node ∉ G.nodeshStatus:state.status node = NodeStatus.pendinghOutput:state.output node = nonehNoAncestor:¬hasFailedAncestor G state node⊢ (propagateFailure G state).output node = none
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhDomain:GraphState.topologyDomain G statenode:νhNotMem:node ∉ G.nodeshStatus:state.status node = NodeStatus.pendinghOutput:state.output node = nonehNoAncestor:¬hasFailedAncestor G state node⊢ (propagateFailure G state).status node = NodeStatus.pending All goals completed! 🐙
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhDomain:GraphState.topologyDomain G statenode:νhNotMem:node ∉ G.nodeshStatus:state.status node = NodeStatus.pendinghOutput:state.output node = nonehNoAncestor:¬hasFailedAncestor G state node⊢ (propagateFailure G state).output node = none All goals completed! 🐙
propagateFailure_preserves_outputsRespectStatuses preserves output ownership.
theorem propagateFailure_preserves_outputsRespectStatuses
(G : DAG ν)
(state : GraphState ν payload)
(hOutputs : GraphState.outputsRespectStatuses state) :
GraphState.outputsRespectStatuses (propagateFailure G state) := ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsRespectStatuses⊢ (propagateFailure G state).outputsRespectStatuses
classical
intro node ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsRespectStatusesnode:νvalue:payload⊢ (propagateFailure G state).output node = some value → ((propagateFailure G state).status node).mayHaveOutput ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsRespectStatusesnode:νvalue:payloadhOutput:(propagateFailure G state).output node = some value⊢ ((propagateFailure G state).status node).mayHaveOutput
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsRespectStatusesnode:νvalue:payloadhOutput:(propagateFailure G state).output node = some valuehClosed:(state.status node).propagatable ∧ hasFailedAncestor G state node⊢ ((propagateFailure G state).status node).mayHaveOutputν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsRespectStatusesnode:νvalue:payloadhOutput:(propagateFailure G state).output node = some valuehClosed:¬((state.status node).propagatable ∧ hasFailedAncestor G state node)⊢ ((propagateFailure G state).status node).mayHaveOutput
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsRespectStatusesnode:νvalue:payloadhOutput:(propagateFailure G state).output node = some valuehClosed:(state.status node).propagatable ∧ hasFailedAncestor G state node⊢ ((propagateFailure G state).status node).mayHaveOutput ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsRespectStatusesnode:νvalue:payloadhOutput:(propagateFailure G state).output node = some valuehClosed:(state.status node).propagatable ∧ hasFailedAncestor G state nodehMayHaveOutput:(state.status node).mayHaveOutput⊢ ((propagateFailure G state).status node).mayHaveOutput
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsRespectStatusesnode:νvalue:payloadhOutput:(propagateFailure G state).output node = some valuehClosed:(state.status node).propagatable ∧ hasFailedAncestor G state nodehMayHaveOutput:(state.status node).mayHaveOutputhStatus:state.status node = NodeStatus.pending⊢ ((propagateFailure G state).status node).mayHaveOutputν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsRespectStatusesnode:νvalue:payloadhOutput:(propagateFailure G state).output node = some valuehClosed:(state.status node).propagatable ∧ hasFailedAncestor G state nodehMayHaveOutput:(state.status node).mayHaveOutputhStatus:state.status node = NodeStatus.running⊢ ((propagateFailure G state).status node).mayHaveOutputν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsRespectStatusesnode:νvalue:payloadhOutput:(propagateFailure G state).output node = some valuehClosed:(state.status node).propagatable ∧ hasFailedAncestor G state nodehMayHaveOutput:(state.status node).mayHaveOutputhStatus:state.status node = NodeStatus.completed⊢ ((propagateFailure G state).status node).mayHaveOutputν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsRespectStatusesnode:νvalue:payloadhOutput:(propagateFailure G state).output node = some valuehClosed:(state.status node).propagatable ∧ hasFailedAncestor G state nodehMayHaveOutput:(state.status node).mayHaveOutputhStatus:state.status node = NodeStatus.failed⊢ ((propagateFailure G state).status node).mayHaveOutputν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsRespectStatusesnode:νvalue:payloadhOutput:(propagateFailure G state).output node = some valuehClosed:(state.status node).propagatable ∧ hasFailedAncestor G state nodehMayHaveOutput:(state.status node).mayHaveOutputhStatus:state.status node = NodeStatus.skipped⊢ ((propagateFailure G state).status node).mayHaveOutputν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsRespectStatusesnode:νvalue:payloadhOutput:(propagateFailure G state).output node = some valuehClosed:(state.status node).propagatable ∧ hasFailedAncestor G state nodehMayHaveOutput:(state.status node).mayHaveOutputhStatus:state.status node = NodeStatus.interrupted⊢ ((propagateFailure G state).status node).mayHaveOutputν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsRespectStatusesnode:νvalue:payloadhOutput:(propagateFailure G state).output node = some valuehClosed:(state.status node).propagatable ∧ hasFailedAncestor G state nodehMayHaveOutput:(state.status node).mayHaveOutputhStatus:state.status node = NodeStatus.waiting⊢ ((propagateFailure G state).status node).mayHaveOutputν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsRespectStatusesnode:νvalue:payloadhOutput:(propagateFailure G state).output node = some valuehClosed:(state.status node).propagatable ∧ hasFailedAncestor G state nodehMayHaveOutput:(state.status node).mayHaveOutputhStatus:state.status node = NodeStatus.rewritten⊢ ((propagateFailure G state).status node).mayHaveOutput ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsRespectStatusesnode:νvalue:payloadhOutput:(propagateFailure G state).output node = some valuehClosed:(state.status node).propagatable ∧ hasFailedAncestor G state nodehMayHaveOutput:(state.status node).mayHaveOutputhStatus:state.status node = NodeStatus.pending⊢ ((propagateFailure G state).status node).mayHaveOutputν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsRespectStatusesnode:νvalue:payloadhOutput:(propagateFailure G state).output node = some valuehClosed:(state.status node).propagatable ∧ hasFailedAncestor G state nodehMayHaveOutput:(state.status node).mayHaveOutputhStatus:state.status node = NodeStatus.running⊢ ((propagateFailure G state).status node).mayHaveOutputν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsRespectStatusesnode:νvalue:payloadhOutput:(propagateFailure G state).output node = some valuehClosed:(state.status node).propagatable ∧ hasFailedAncestor G state nodehMayHaveOutput:(state.status node).mayHaveOutputhStatus:state.status node = NodeStatus.completed⊢ ((propagateFailure G state).status node).mayHaveOutputν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsRespectStatusesnode:νvalue:payloadhOutput:(propagateFailure G state).output node = some valuehClosed:(state.status node).propagatable ∧ hasFailedAncestor G state nodehMayHaveOutput:(state.status node).mayHaveOutputhStatus:state.status node = NodeStatus.failed⊢ ((propagateFailure G state).status node).mayHaveOutputν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsRespectStatusesnode:νvalue:payloadhOutput:(propagateFailure G state).output node = some valuehClosed:(state.status node).propagatable ∧ hasFailedAncestor G state nodehMayHaveOutput:(state.status node).mayHaveOutputhStatus:state.status node = NodeStatus.skipped⊢ ((propagateFailure G state).status node).mayHaveOutputν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsRespectStatusesnode:νvalue:payloadhOutput:(propagateFailure G state).output node = some valuehClosed:(state.status node).propagatable ∧ hasFailedAncestor G state nodehMayHaveOutput:(state.status node).mayHaveOutputhStatus:state.status node = NodeStatus.interrupted⊢ ((propagateFailure G state).status node).mayHaveOutputν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsRespectStatusesnode:νvalue:payloadhOutput:(propagateFailure G state).output node = some valuehClosed:(state.status node).propagatable ∧ hasFailedAncestor G state nodehMayHaveOutput:(state.status node).mayHaveOutputhStatus:state.status node = NodeStatus.waiting⊢ ((propagateFailure G state).status node).mayHaveOutputν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsRespectStatusesnode:νvalue:payloadhOutput:(propagateFailure G state).output node = some valuehClosed:(state.status node).propagatable ∧ hasFailedAncestor G state nodehMayHaveOutput:(state.status node).mayHaveOutputhStatus:state.status node = NodeStatus.rewritten⊢ ((propagateFailure G state).status node).mayHaveOutput
All goals completed! 🐙
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsRespectStatusesnode:νvalue:payloadhOutput:(propagateFailure G state).output node = some valuehClosed:¬((state.status node).propagatable ∧ hasFailedAncestor G state node)⊢ ((propagateFailure G state).status node).mayHaveOutput All goals completed! 🐙
propagateFailure_preserves_outputsCompleteForStatuses preserves required outputs.
theorem propagateFailure_preserves_outputsCompleteForStatuses
(G : DAG ν)
(state : GraphState ν payload)
(hOutputs : GraphState.outputsCompleteForStatuses state) :
GraphState.outputsCompleteForStatuses (propagateFailure G state) := ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsCompleteForStatuses⊢ (propagateFailure G state).outputsCompleteForStatuses
classical
intro node ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsCompleteForStatusesnode:νhRequiresOutput:((propagateFailure G state).status node).requiresOutput⊢ ∃ value, (propagateFailure G state).output node = some value
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsCompleteForStatusesnode:νhRequiresOutput:((propagateFailure G state).status node).requiresOutputhClosed:(state.status node).propagatable ∧ hasFailedAncestor G state node⊢ ∃ value, (propagateFailure G state).output node = some valueν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsCompleteForStatusesnode:νhRequiresOutput:((propagateFailure G state).status node).requiresOutputhClosed:¬((state.status node).propagatable ∧ hasFailedAncestor G state node)⊢ ∃ value, (propagateFailure G state).output node = some value
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsCompleteForStatusesnode:νhRequiresOutput:((propagateFailure G state).status node).requiresOutputhClosed:(state.status node).propagatable ∧ hasFailedAncestor G state node⊢ ∃ value, (propagateFailure G state).output node = some value All goals completed! 🐙
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsCompleteForStatusesnode:νhRequiresOutput:((propagateFailure G state).status node).requiresOutputhClosed:¬((state.status node).propagatable ∧ hasFailedAncestor G state node)⊢ ∃ value, (propagateFailure G state).output node = some value have hOriginalRequires :
NodeStatus.requiresOutput (state.status node) := ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsCompleteForStatuses⊢ (propagateFailure G state).outputsCompleteForStatuses
All goals completed! 🐙
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsCompleteForStatusesnode:νhRequiresOutput:((propagateFailure G state).status node).requiresOutputhClosed:¬((state.status node).propagatable ∧ hasFailedAncestor G state node)hOriginalRequires:(state.status node).requiresOutputvalue:payloadhOutput:state.output node = some value⊢ ∃ value, (propagateFailure G state).output node = some value
exact ⟨value, ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhOutputs:state.outputsCompleteForStatusesnode:νhRequiresOutput:((propagateFailure G state).status node).requiresOutputhClosed:¬((state.status node).propagatable ∧ hasFailedAncestor G state node)hOriginalRequires:(state.status node).requiresOutputvalue:payloadhOutput:state.output node = some value⊢ (propagateFailure G state).output node = some value All goals completed! 🐙⟩Idempotence
propagateFailure_of_failureClosureComplete makes failure-closed states fixed points.
theorem propagateFailure_of_failureClosureComplete
(G : DAG ν)
(state : GraphState ν payload)
(hComplete : failureClosureComplete G state) :
propagateFailure G state = state := ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhComplete:failureClosureComplete G state⊢ propagateFailure G state = state
classical
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhComplete:failureClosureComplete G statenode:ν⊢ (propagateFailure G state).status node = state.status nodeν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhComplete:failureClosureComplete G statenode:νa✝:payload⊢ (propagateFailure G state).output node = some a✝ ↔ state.output node = some a✝
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhComplete:failureClosureComplete G statenode:ν⊢ (propagateFailure G state).status node = state.status node ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhComplete:failureClosureComplete G statenode:νhClosed:(state.status node).propagatable ∧ hasFailedAncestor G state node⊢ (propagateFailure G state).status node = state.status nodeν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhComplete:failureClosureComplete G statenode:νhClosed:¬((state.status node).propagatable ∧ hasFailedAncestor G state node)⊢ (propagateFailure G state).status node = state.status node
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhComplete:failureClosureComplete G statenode:νhClosed:(state.status node).propagatable ∧ hasFailedAncestor G state node⊢ (propagateFailure G state).status node = state.status node ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhComplete:failureClosureComplete G statenode:νhClosed:(state.status node).propagatable ∧ hasFailedAncestor G state nodefailedNode:νhFailed:state.status failedNode = NodeStatus.failedhReach:G.reaches failedNode node⊢ (propagateFailure G state).status node = state.status node
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhComplete:failureClosureComplete G statenode:νhClosed:(state.status node).propagatable ∧ hasFailedAncestor G state nodefailedNode:νhFailed:state.status failedNode = NodeStatus.failedhReach:G.reaches failedNode nodehNodeFailed:state.status node = NodeStatus.failed⊢ (propagateFailure G state).status node = state.status node
All goals completed! 🐙
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhComplete:failureClosureComplete G statenode:νhClosed:¬((state.status node).propagatable ∧ hasFailedAncestor G state node)⊢ (propagateFailure G state).status node = state.status node All goals completed! 🐙
ν:Type upayload:Type vG:DAG νstate:GraphState ν payloadhComplete:failureClosureComplete G statenode:νa✝:payload⊢ (propagateFailure G state).output node = some a✝ ↔ state.output node = some a✝ All goals completed! 🐙
propagateFailure_idempotent proves failure propagation is idempotent.
theorem propagateFailure_idempotent
(G : DAG ν)
(state : GraphState ν payload) :
propagateFailure G (propagateFailure G state) = propagateFailure G state := ν:Type upayload:Type vG:DAG νstate:GraphState ν payload⊢ propagateFailure G (propagateFailure G state) = propagateFailure G state
All goals completed! 🐙end Cortex.Pulse