Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Tools/nelson oppen (not ready for review) #28

Open
wants to merge 84 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
84 commits
Select commit Hold shift + click to select a range
89ed827
varsat/meta-aux: Stub out file
nishantjr Sep 26, 2018
d6f0cb5
varsat/foform => meta/foform: update meta/foform; have varsat/foform …
nishantjr Sep 26, 2018
10a9a83
meta/{foform,kind-ops} varsat/var-sat: Atom -> Lit
nishantjr Sep 26, 2018
94f3816
meta/foform: split QFFOFORM from FOFORM
Sep 28, 2018
2ec0c39
meta/foform: split QFFOFORMSET from FOFORMSET
Sep 28, 2018
cd267b4
varsat/{var-sat,numbers}: switch `pr FOFORM => QFFOFORM .`
Sep 28, 2018
90458d5
meta/foform: split QFFORM-OPERATIONS from FOFORM-OPERATIONS
Sep 28, 2018
159ad83
meta/foform, varsat/var-sat: restrict more modules to QFForm
Sep 28, 2018
997c88c
meta/foform: split QFFOFORM-SUBSTITUTION from FOFORM-SUBSTITUTION
Sep 28, 2018
48c3e41
meta/foform: more than just renamings allowed in FOForm substitutions
Sep 28, 2018
7f7b63f
meta/foform: lower FOFORMSUBSTITUTION-PAIR to QFFOFORMSUBSTITUTION-PAIR
Sep 28, 2018
6c9f704
meta/foform, varsat/var-sat: lower FOFORM-SUBSTITUTIONSET => QFFOFORM…
Sep 28, 2018
6764d0c
meta/foform, varsat/var-sat: split QFFOFORM-DEFINEDOPS from FOFORM-DE…
Sep 28, 2018
c150020
meta/foform, varsat/var-sat: split QFFOFORMSIMPLIFY(-IMPL) from FOFOR…
Sep 28, 2018
19a6e3e
tests/.../meta/eqform: flesh out testing harness module
nishantjr Sep 29, 2018
398814d
meta/eqform: EQFORM-OPERATIONS: Port wellFormed, normalize, vars and …
nishantjr Sep 29, 2018
c0f83b8
meta/eqform: add `reduce` and tests
Sep 29, 2018
49d56a0
meta/eqform: port {QFFO => EQ}FORM-SET-OPERATIONS
Sep 29, 2018
d82a48a
varsat/var-sat: minimize imports
Sep 29, 2018
f611f3a
meta/eqform: lift `_<<_` to FormSet, SubstitutionSet
Sep 29, 2018
d90ba9e
meta/eqform: more trivial simplifications
Sep 29, 2018
5006db2
meta/eqform: mark partial functions
Sep 29, 2018
f0abd87
varsat/var-sat: remove call to simplify which does not affect the tests
Sep 29, 2018
56419b6
tests/.../varsat/var-sat: more tests
Sep 30, 2018
29b83b4
varsat/var-sat: switch over to depending on EQFORM
Sep 29, 2018
9e0a301
!!! var-sat query that gets stuck.
nishantjr Sep 30, 2018
efb382a
tools/meta/nelson-oppen-combination: tangle and testing infrastructure
nishantjr May 22, 2018
ea0b29c
tests/nelson-oppen-combination: Begin implementation
nishantjr Feb 14, 2018
29f7aea
tools/nelson-oppen-combination: simplify $no.tagged -> $no.basicSat
nishantjr Apr 22, 2018
398a959
tools/nelson-oppen-combination: $nosat.simplified => $nosat.dnf
nishantjr Apr 23, 2018
c60601e
tools/nelson-oppen-combination: Write some documentation
nishantjr Apr 23, 2018
65497ec
tools/nelson-oppen-combination: `and-then` is more readable than `if_…
nishantjr Apr 23, 2018
15a5d99
tools/nelson-oppen-combination: TaggedFormulaSet uses semicolon for u…
nishantjr Apr 23, 2018
8e248f1
tools/nelson-oppen-combination: More if_then_else => and-then
nishantjr Apr 23, 2018
500e365
tools/nelson-oppen-combination: Only split for theories tagged 'conve…
nishantjr Apr 23, 2018
86b9f96
tools/nelson-oppen-combination: Rename make-equalities => candidate-e…
nishantjr Apr 24, 2018
35aeec0
tools/nelson-oppen-combination: Rename var `DISJ?` => `CANDEQ` to ref…
nishantjr Apr 24, 2018
2b91365
tools/nelson-oppen-combination: Document inteference rules
nishantjr May 22, 2018
7887139
tests/nelson-oppen-combination: Split the integer-list combination te…
nishantjr Apr 25, 2018
fd4017c
nelson-oppen-uninterpreted-funcs: Demonstration of NO with uninterpre…
nishantjr Apr 25, 2018
f06dd44
nelson-oppen-matrix example
nishantjr Apr 26, 2018
68a0daf
! src/Mixfix/yices2_Bindings.cc: Change yices config to allow nonline…
nishantjr Jun 5, 2018
4e906e4
systems/nelson-oppen: example showing "all real invertible matrices h…
nishantjr Jun 5, 2018
f625e66
TTT meta/cterms: purify: Handle breaking of disequalities
nishantjr Jun 5, 2018
799005e
tools/nelson-oppen-combination: foform-to-smt: Convert tt to 'true
nishantjr Jun 5, 2018
c5a5530
meta/nelson-oppen: Print attribute for all inference steps
nishantjr Jun 5, 2018
232e0fa
meta/nelson-oppen-combination: When vars are identified, substitute o…
nishantjr Jun 5, 2018
8cdd027
meta/nelson-oppen-combination: addConvexTag: Be more discriminating a…
nishantjr Jun 5, 2018
f0044bd
meta/nelson-oppen-combination: Add `nelson-oppen-valid`
nishantjr Jun 5, 2018
c24790a
old matrix
nishantjr Jun 5, 2018
16fee1e
uninterpreted-funcs -> uninterpreted-bijections
nishantjr Jun 5, 2018
cab3ec3
nelson-oppen: foform-to-smt: 'tt.Bool* is not part of FOForm
nishantjr Jun 12, 2018
45b0007
TTT meta/cterms: break-eqatoms: Generate additional extra variables t…
nishantjr Jun 20, 2018
282dc5a
TTT meta/purification: Handle some TruthAtoms
nishantjr Jun 20, 2018
bfbc17f
GAUSIAN-INT, text
nishantjr Jun 21, 2018
9387b14
Remove failed experiments
nishantjr Jun 21, 2018
10e5d60
contrib/systems.md/hereditarily-finite-set.md: Non-trivial example of…
nishantjr Apr 22, 2018
a873ae9
update text
nishantjr Jun 24, 2018
fb3de19
integer-list: text; example checks validity instead of satisfiability
nishantjr Jun 24, 2018
b6f2be5
test/Misc/Makefile: smtTest fails with Yices' MCSAT
nishantjr Jun 24, 2018
e94a55e
lexical-trichotomy: Failed example (purification does not support cto…
nishantjr Jun 24, 2018
7a3fc86
tests/systems/nelson-oppen: Own Makefile.am
nishantjr Jun 25, 2018
4df4dd9
tests/systems/nelson-oppen: empty expected files
nishantjr Jun 25, 2018
2425753
set print attribute on
nishantjr Jun 25, 2018
0b74719
integer-list: Make note that example has become trivial
nishantjr Jun 25, 2018
0641d16
checks for other tests
nishantjr Jun 25, 2018
3afc987
empty expected files
nishantjr Jun 25, 2018
6738115
contrib/.../hfs: print attribute
nishantjr Jun 25, 2018
a8f47c7
Update test results (CVC4)
nishantjr Jun 25, 2018
5c81285
Update test results
nishantjr Jun 25, 2018
0a536b1
nelson-oppen: Modify text a bit
nishantjr Jun 25, 2018
1b55664
Update test results
nishantjr Jun 29, 2018
22eb108
systems.md/nelson-oppen: Add output to text
nishantjr Jun 29, 2018
7396e8a
Update test results
nishantjr Jul 2, 2018
140c9e0
Update test results
nishantjr Jul 2, 2018
d0e40fb
More text
nishantjr Jul 4, 2018
c9b52c2
More of Jose's suggestions
nishantjr Jul 10, 2018
12feecd
Update test results
nishantjr Jul 10, 2018
d68b8fc
Formatting; Jose's changes 2
nishantjr Jul 12, 2018
60a7787
tests are in maude files
nishantjr Sep 25, 2018
9f7cb30
build: add tests that need smt
nishantjr Sep 25, 2018
7f23dae
Remove test runner
nishantjr Sep 30, 2018
ed41d93
!!! move to eq form
nishantjr Sep 26, 2018
ea077fa
build: Make sure we build with mcsat for non-linear arithmetic support
nishantjr Sep 20, 2019
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions TODO.md
Original file line number Diff line number Diff line change
Expand Up @@ -44,3 +44,9 @@ Amorphous
switch between Maude packages.

- Increase inter-opability of Maude files.


Nelson Oppen
============

- Generalize to multiple modules
10 changes: 9 additions & 1 deletion build
Original file line number Diff line number Diff line change
Expand Up @@ -60,7 +60,7 @@ build_yices2() {
mkdir -p $build_dir
( cd "$yices2_dir"
autoconf
./configure --prefix="$build_dir"
./configure --enable-mcsat --prefix="$build_dir"
make -s -j4
make -s install
)
Expand Down Expand Up @@ -121,12 +121,20 @@ build_test_smt() {
build_maude_cvc4
build_tangle
build_test tests/Misc/smtTest
build_test tests/tools/meta/nelson-oppen/hereditarily-finite-set
build_test tests/tools/meta/nelson-oppen/integer-list
build_test tests/tools/meta/nelson-oppen/lexical-trichotomy-law
build_test tests/tools/meta/nelson-oppen/matrix

build_clean
build_deps
build_maude_yices2
build_tangle
build_test tests/Misc/smtTest
build_test tests/tools/meta/nelson-oppen/hereditarily-finite-set
build_test tests/tools/meta/nelson-oppen/integer-list
build_test tests/tools/meta/nelson-oppen/lexical-trichotomy-law
build_test tests/tools/meta/nelson-oppen/matrix

git checkout -- src/Mixfix/tokenizer.cc
}
Expand Down
1 change: 1 addition & 0 deletions configure.ac
Original file line number Diff line number Diff line change
Expand Up @@ -415,6 +415,7 @@ AC_CONFIG_FILES([Makefile
tests/tools/varsat/Makefile
tests/tools/fvp/Makefile
tests/systems/Makefile
tests/systems/nelson-oppen/Makefile
])

AC_OUTPUT
249 changes: 249 additions & 0 deletions contrib/systems.md/nelson-oppen/hereditarily-finite-set.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,249 @@
Hereditarily Finite Sets with Reals
-----------------------------------

In this example, we demonstrate the combination algorithm with non-convex theories -- non-linear
real arithmetic and hereditarily finite sets. Hereditarily finite sets is an example of a theory not
currently definable in CVC4 or Yices2 because of its use of algebraic data types modulo axioms like
associativity-commutativity and having FVP equations. Hereditarily finite sets (HFS) are a model of
set theory without the axiom of infinity. Although hereditarily finite sets are expressive enough to
encode constructs like the integers and the natural numbers, its initial model is a countable model
and so cannot encode the real numbers.

```test
set include BOOL off .

fmod HEREDITARILY-FINITE-SET is
sort MyBool .
op tt : -> MyBool [ctor] .
op ff : -> MyBool [ctor] .
```

We have three sorts, `X`, the parametric sort, `Set`s and `Magma`s.
Both `X`s and `Set`s are `Magma`s.

``` {.test .njr-thesis}
sorts X Set Magma .
subsorts X Set < Magma .
```

```test
vars M M' M'' : Magma .
vars S : Set .
```

The elements of a hereditarily finite set can be elements of the parameter sort `X` of "atomic
elements", or can be other hereditarily constructed inductively from the following three
constructors. First, `empty` is a `Set`:

``` {.test .njr-thesis}
op empty : -> Set [ctor] .
```

Second, the union operator is an associative, commutative and idemopotent operator:

``` {.test .njr-thesis}
op _ , _ : Magma Magma -> Magma [ctor assoc comm] .
----------------------------------------------------------------------------
eq M , M , M' = M , M' [variant] .
eq M , M = M [variant] .
```

Finally, a `Set` may be constructed from any `Magma` by enclosing it in braces.

``` {.test .njr-thesis}
op { _ } : Magma -> Set [ctor] .
```

We also have a subset operator and the various equations (not detailed here) defining it:

``` {.test .njr-thesis}
op _ C= _ : Magma Magma -> MyBool .
```

```test
----------------------------------------------------------------------------
eq empty C= M = tt [variant] .
eq { M } C= { M, M' } = tt [variant] .

eq { M } C= { M } = tt [variant] .
eq { M } C= empty = ff [variant] .

eq { M, M' } C= { M, M'' }
= { M' } C= { M, M'' } [variant] .
eq { M, M' } C= { M }
= { M' } C= { M } [variant] .

--- Since `var-sat` does not support `[owise]`, we do not implement the equation
--- for handling the negative case. Since the theory is OS-Compact, we can just let
--- the predicate get stuck, partially evaluated.

op _ U _ : Set Set -> Set .
----------------------------------------------------------------------------
eq empty U S = S [variant] .
eq { M } U { M' } = { M, M' } [variant] .
```

```test
endfm

```

```test
fmod TEST-HEREDITARILY-FINITE-SET-SANITY is
protecting HEREDITARILY-FINITE-SET .
protecting BOOL .
vars M M' : Magma .
endfm

reduce M, M', M == M, M' .
reduce { { empty }, { { empty } }, empty }
== { { empty }, { { empty } }, empty }
.

reduce empty C= { empty } == tt .
reduce { empty } C= empty .
reduce { empty } C= { { empty } } .
reduce { empty } C= { empty, { empty } } == tt .
reduce { empty } C= { { empty }, { { empty } } } .
reduce { M, M' } C= { M, M' } .

reduce { empty, empty } C= { empty } .

--- Nelson Oppen
--- ------------
---
--- We must trick `var-sat` into thinking that the `X` sort is countable.
```

We instantiate this module with `Real`s as a subsort of `X`:

``` {.test .njr-thesis}
fmod HFS-REAL is
including HEREDITARILY-FINITE-SET .
sorts Real .
subsorts Real < X .

op fake-0 : -> Real [ctor] .
op fake-s : Real -> Real [ctor] .
endfm
```

```test
load ../../../contrib/tools/meta/nelson-oppen-combination

fmod HEREDITARILY-FINITE-SET-TEST-VARSAT is
protecting BOOL .
protecting VAR-SAT .
protecting HFS-REAL .
vars M M' : Magma .
endfm

--- TODO: This does not reduce as I expect it to
reduce upTerm({ X:Real, Y:Real, Z:Real } C= { X:Real }) .

reduce upTerm({ X:Real, Y:Real, Z:Real } C= { A:Real }) .
reduce upTerm({ X:Real, Y:Real, Z:Real } ) .

reduce var-sat( upModule('HFS-REAL, true)
, upTerm({ empty , M } C= { empty }) ?= 'tt.MyBool
) .
reduce var-sat( upModule('HFS-REAL, true)
, upTerm({ empty , M } C= { empty }) ?= 'tt.MyBool
/\ upTerm(M) != 'empty.Set
) .
reduce var-sat( upModule('HFS-REAL, true)
, upTerm({ empty , M } C= { empty , M' }) ?= 'tt.MyBool
) .

--- get variants { X:Magma, Y:Magma, Z:Magma } .
--- --- Lots and lots of variants? or variant computation is slow?
--- reduce var-sat( upModule('HFS-REAL, true)
--- , upTerm({ X:Magma, Y:Magma, Z:Magma } C= { X:Magma }) ?= 'tt.MyBool
--- ) == true .

reduce var-sat( upModule('HFS-REAL, true)
, upTerm({ X:Real, Y:Real, Z:Real }) ?= upTerm({ X:Real })
) == true .

reduce var-sat( upModule('HFS-REAL, true)
, upTerm({ X:Real, Y:Real, Z:Real } C= { X:Real }) ?= 'tt.MyBool
) == true .
```

Finally, we check the satisfiability of the formula $\{ x^2 , y^2, z^2 \} \subseteq \{ a \} \land x \ne y$. i.e. "is
it possible for the set of squares of three numbers, two of which must be distinct, to be a
subset of a set with a single element." This is indeed possible, since every positive real number
has two distinct square roots. Since set union is idempotent, if the two distinct numbers are
additive inverses of each other and the third is equal to either, then the proposition would indeed
be satisfied.

```test
set print attribute on .
```

Our query is:

``` {.test .njr-thesis}
reduce in NELSON-OPPEN-COMBINATION :
nelson-oppen-sat( ( tagged(tt, ('mod > 'REAL) ; ('check-sat > 'smt-sat))
, tagged(tt, ('mod > 'HFS-REAL); ('check-sat > 'var-sat))
)
, ( '_C=_[ '`{_`}['_`,_[ '_*_ [ 'Z:Real, 'Z:Real ]
, '_*_ [ 'X:Real, 'X:Real ]
, '_*_ [ 'Y:Real, 'Y:Real ]
]]
, '`{_`}['A:Real]]
?= 'tt.MyBool
)
/\ 'X:Real != 'Y:Real
) .
```

This purifies to:

```njr-thesis
'x2:Real ?= '_*_['X:Real,'X:Real]
/\ 'y2:Real ?= '_*_['Y:Real,'Y:Real]
/\ 'z2:Real ?= '_*_['Z:Real,'Z:Real]
/\ 'X:Real != 'Y:Real,
```

in the theory of the hereditarily finite sets, and to:

```njr-thesis
'tt.MyBool ?= '_C=_['`{_`}['_`,_['z2:Real,'x2:Real,'y2:Real]],'`{_`}['A:Real]]
/\ 'X:Real != 'Y:Real

```

in the theory of the reals.

Initially, a few equalities are propagated from the theory of hereditarily finite sets:

```njr-thesis
'HFS-REAL: => 'x2:Real ?= 'y2:Real
'HFS-REAL: => 'y2:Real ?= 'z2:Real
'HFS-REAL: => 'z2:Real ?= 'A:Real
```

Since no more identifications of variables are implied on their own and the theories are not convex,
the algorithm must check whether a disjunction of identifications is implied by either of the
theories, and indeed $x = z \lor y = z$ is implied. The algorithm splits the search space on the
remaining candidate equalities ($a = x$, $a = y$, $a = z$, $x = y$, $z = z$ and $y = z$). It first
tries the case where $a = x$ and finds that there are satisfiabile arrangements (this can happen
when $a = x = 1$). It then splits the search space again, but finds that there are no arrangements
$a = y$ possible (since that implies that $x = y$). However the case where $a = z$ is satisfiable.
This causes the the equality $x = z$ to be propagated. Now, since no further equalities or
disjunctions thereof hold, the algorithm concludes that the formula is satisfiable.

```
Split? 'A:Real ?= 'X:Real \/ 'A:Real ?= 'Y:Real \/ 'A:Real ?= 'Z:Real \/ 'X:Real ?= 'Y:Real \/ 'X:Real ?= 'Z:Real \/ 'Y:Real ?= 'Z:Real
Split: 'HFS-REAL : 'A:Real ?= 'X:Real
Split? 'A:Real ?= 'Y:Real \/ 'A:Real ?= 'Z:Real \/ 'X:Real ?= 'Y:Real \/ 'X:Real ?= 'Z:Real \/ 'Y:Real ?= 'Z:Real
Split: 'HFS-REAL : 'A:Real ?= 'Y:Real
Split: 'HFS-REAL : 'A:Real ?= 'Z:Real
EqualityProp: 'HFS-REAL: => 'X:Real ?= 'Z:Real
Split? 'A:Real ?= 'Y:Real \/ 'Y:Real ?= 'Z:Real
rewrites: 36007 in 4943ms cpu (4951ms real) (7284 rewrites/second)
result Bool: (true).Bool
```
92 changes: 92 additions & 0 deletions contrib/systems.md/nelson-oppen/integer-list.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,92 @@
Combining Integers with Lists
-----------------------------

\newcommand \head {\text{head}}

In this example we demonstrate the Nelson-Oppen combination where one of the theories involved is
not convex and the split rule needs to be applied to get the correct result. Here, lists are a
convex theory, but the integers with order are now.

```test
load ../../../contrib/tools/meta/nelson-oppen-combination.maude
```

We implement the lists as a theory that has the finite variant property and use variant based
satisfiability to decide its formulae. Here, the head function returns the first element of the
list.

```{.test .njr-thesis}
fmod INTEGER-LIST is
sort Integer .

--- Convince var-sat we are infinite
op fake-0 : -> Integer [ctor] .
op fake-s : Integer -> Integer [ctor] .

sort IntegerList NeIntegerList .
subsort Integer < NeIntegerList < IntegerList .
op _ _ : NeIntegerList NeIntegerList -> NeIntegerList [ctor assoc] .
op nil : -> IntegerList [ctor] .

op head : NeIntegerList -> Integer .
var N : Integer . var L : NeIntegerList .
eq head(N) = N [variant] .
eq head(N L) = N [variant] .
endfm
```

For the integers, we use one of the external SMT solvers, CVC4 for checking satisfiability.

```test
fmod TEST-NO-SMT-LIST is
protecting REAL-INTEGER .
protecting INTEGER-LIST .
protecting NELSON-OPPEN-COMBINATION .
protecting META-LEVEL .
endfm

reduce nelson-oppen-sat(( tagged(tt, ('mod > 'INTEGER-LIST); ('check-sat > 'var-sat))
, tagged(tt, ('mod > 'INTEGER ); ('check-sat > 'smt-sat))),
'_-_ [ '_*_ [ '2.Integer , 'head[ 'L:NeIntegerList ] ]
, '_*_ [ '2.Integer , 'head[ 'M:NeIntegerList ] ] ]
?= '1.Integer)
== false
.
reduce nelson-oppen-sat(( tagged(tt, ('mod > 'INTEGER-LIST); 'check-sat > 'var-sat)
, tagged(tt, ('mod > 'INTEGER ); 'check-sat > 'smt-sat)),
'_-_ [ '_*_ [ '2.Integer , 'head[ 'L:NeIntegerList ] ]
, '_*_ [ '2.Integer , 'head[ 'M:NeIntegerList ] ] ]
?= '0.Integer)
== true
.

reduce nelson-oppen-sat(( tagged(tt, ('mod > 'INTEGER-LIST); 'check-sat > 'var-sat)
, tagged(tt, ('mod > 'INTEGER ); 'check-sat > 'smt-sat)),
'_-_ [ 'head[ 'L:NeIntegerList ]
, '_*_ [ '2.Integer , 'head[ 'M:NeIntegerList ] ] ]
?= '0.Integer)
== true
.
```

We use Nelson-Oppen to mechanically prove that
$1 \le \head(L) \land
\head(L) \le 2
\limplies \head(L) = 1 \lor \head(L) = 2$

\colorbox{red}{XXX: This example has become trivial (has no equalities to propagate) since we made the change to
the purification that added the extra equalities}

``` {.test .njr-thesis}
set print attribute on .
reduce nelson-oppen-valid(( tagged(tt, (('mod > 'INTEGER-LIST); 'check-sat > 'var-sat))
, tagged(tt, (('mod > 'INTEGER ); 'check-sat > 'smt-sat))),
( '_<=_ [ '1.Integer , 'head[ 'L:NeIntegerList ] ] ?= 'true.Boolean
/\ '_<=_ [ 'head[ 'L:NeIntegerList ] , '2.Integer ] ?= 'true.Boolean
)
=> ( 'head[ 'L:NeIntegerList ] ?= '1.Integer
\/ 'head[ 'L:NeIntegerList ] ?= '2.Integer
)
) .
```

Loading