oxiz_theories/theory.rs
1//! Theory trait and common types
2
3use oxiz_core::ast::TermId;
4use oxiz_core::error::Result;
5
6/// Unique identifier for a theory
7#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
8pub enum TheoryId {
9 /// Boolean theory (always present)
10 Bool,
11 /// Equality with Uninterpreted Functions
12 EUF,
13 /// Linear Real Arithmetic
14 LRA,
15 /// Linear Integer Arithmetic
16 LIA,
17 /// BitVectors
18 BV,
19 /// Arrays
20 Arrays,
21 /// Floating-Point (IEEE 754)
22 FP,
23 /// Algebraic Datatypes
24 Datatype,
25 /// Strings and Regular Expressions
26 Strings,
27}
28
29/// Result of a theory check
30#[derive(Debug, Clone)]
31pub enum TheoryResult {
32 /// The theory constraints are satisfiable
33 Sat,
34 /// The theory constraints are unsatisfiable with explanation
35 Unsat(Vec<TermId>),
36 /// Need to propagate these literals
37 Propagate(Vec<(TermId, Vec<TermId>)>),
38 /// Unknown (incomplete theory)
39 Unknown,
40}
41
42/// Trait for theory solvers
43pub trait Theory: Send + Sync {
44 /// Get the theory identifier
45 fn id(&self) -> TheoryId;
46
47 /// Get the name of this theory
48 fn name(&self) -> &str;
49
50 /// Check if this theory can handle a term
51 fn can_handle(&self, term: TermId) -> bool;
52
53 /// Assert a term as true
54 fn assert_true(&mut self, term: TermId) -> Result<TheoryResult>;
55
56 /// Assert a term as false
57 fn assert_false(&mut self, term: TermId) -> Result<TheoryResult>;
58
59 /// Check consistency of current assertions
60 fn check(&mut self) -> Result<TheoryResult>;
61
62 /// Push a context level
63 fn push(&mut self);
64
65 /// Pop a context level
66 fn pop(&mut self);
67
68 /// Reset the theory solver
69 fn reset(&mut self);
70
71 /// Get the current model (if satisfiable)
72 fn get_model(&self) -> Vec<(TermId, TermId)> {
73 Vec::new()
74 }
75}
76
77/// Equality notification for Nelson-Oppen theory combination
78/// When one theory derives that two terms are equal, it notifies other theories
79#[derive(Debug, Clone, Copy, PartialEq, Eq)]
80pub struct EqualityNotification {
81 /// Left-hand side of the equality
82 pub lhs: TermId,
83 /// Right-hand side of the equality
84 pub rhs: TermId,
85 /// The reason/justification for this equality (for proof generation)
86 pub reason: Option<TermId>,
87}
88
89/// Interface for theory combination via Nelson-Oppen
90/// Theories implement this to participate in equality sharing
91pub trait TheoryCombination {
92 /// Notify the theory of a new equality derived by another theory
93 /// Returns true if the equality was accepted and processed
94 fn notify_equality(&mut self, eq: EqualityNotification) -> bool;
95
96 /// Get all equalities derived by this theory that should be shared
97 /// These are equalities between terms that appear in multiple theories
98 fn get_shared_equalities(&self) -> Vec<EqualityNotification>;
99
100 /// Check if a term is relevant to this theory
101 fn is_relevant(&self, term: TermId) -> bool;
102}