mirror of
https://github.com/priyanshujain/sanderling.git
synced 2026-10-02 19:17:10 +00:00
feat(ltl): formula AST and step evaluator for v0.1
Supports Always over Pure/Thunk leaves; eventually/next/bounds deferred. Once a thunk returns false under an Always, the verdict latches to violated so the runner can surface the offending step without later observations masking it.
This commit is contained in:
1 parent
cee90694da
commit
0c277b2833
3 files changed
+223
No files matched your search
@@ -0,0 +1,60 @@
|
||||
package ltl
|
||||
|
||||
import "fmt"
|
||||
|
||||
type Verdict int
|
||||
|
||||
const (
|
||||
VerdictHolds Verdict = iota
|
||||
VerdictViolated
|
||||
)
|
||||
|
||||
func (v Verdict) String() string {
|
||||
switch v {
|
||||
case VerdictHolds:
|
||||
return "holds"
|
||||
case VerdictViolated:
|
||||
return "violated"
|
||||
default:
|
||||
return fmt.Sprintf("verdict(%d)", int(v))
|
||||
}
|
||||
}
|
||||
|
||||
// Evaluator folds a formula across observed steps. v0.1 semantics:
|
||||
// Always(P) is satisfied if P held at every observed step; once P is false,
|
||||
// the verdict latches to Violated.
|
||||
type Evaluator struct {
|
||||
formula Formula
|
||||
violated bool
|
||||
}
|
||||
|
||||
func NewEvaluator(formula Formula) *Evaluator {
|
||||
return &Evaluator{formula: formula}
|
||||
}
|
||||
|
||||
// Observe evaluates the formula against the current state and returns the
|
||||
// running verdict. Once Violated, subsequent calls keep returning Violated
|
||||
// regardless of what later observations look like.
|
||||
func (e *Evaluator) Observe() Verdict {
|
||||
if e.violated {
|
||||
return VerdictViolated
|
||||
}
|
||||
if !holdsAtCurrentStep(e.formula) {
|
||||
e.violated = true
|
||||
return VerdictViolated
|
||||
}
|
||||
return VerdictHolds
|
||||
}
|
||||
|
||||
func holdsAtCurrentStep(formula Formula) bool {
|
||||
switch concrete := formula.(type) {
|
||||
case AlwaysFormula:
|
||||
return holdsAtCurrentStep(concrete.Inner)
|
||||
case PureFormula:
|
||||
return concrete.Value
|
||||
case ThunkFormula:
|
||||
return concrete.Func()
|
||||
default:
|
||||
panic(fmt.Sprintf("ltl: unsupported formula type %T", formula))
|
||||
}
|
||||
}
|
||||
Reference in new issue
Block a user