Skip to content

Commit 7d1894b

Browse files
Term api and io world (#38)
* chore: remove obsolete `ioWorld` parameters in FFI * chore: catch more C++ exceptions, format C++ * feat: fix/augment `Term` api * chore(test): add `Term` unit tests * chore: improve test syntax-ext, simplify tests * feat: finish lifting the `Term` api (except `getStringValue`), with tests
1 parent 478b1ed commit 7d1894b

File tree

13 files changed

+2739
-954
lines changed

13 files changed

+2739
-954
lines changed

cvc5.lean

Lines changed: 405 additions & 30 deletions
Large diffs are not rendered by default.

cvc5Test/Init.lean

Lines changed: 22 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -129,7 +129,9 @@ scoped syntax
129129
macro_rules
130130
| `(command|
131131
$[ $outputComment:docComment ]?
132-
test! $[ [ $fileId:ident , $testId:ident ] ]? $[$tmIdent?:ident =>]? $code:term
132+
test! $[ [ $fileId:ident , $testId:ident ] ]?
133+
$[$tmIdent?:ident $[$solverIdent?:ident]? =>]?
134+
$code:term
133135
) => do
134136
let errPrefStrLit :=
135137
match (fileId, testId) with
@@ -139,10 +141,25 @@ macro_rules
139141
let runFun ← `(term| cvc5.Env.run)
140142
let toRun ←
141143
if let some tmIdent := tmIdent? then
142-
`(do
143-
let $tmIdent:ident ← TermManager.new
144-
$code:term
145-
)
144+
let boolIdent := `bool |> Lean.mkIdent
145+
let intIdent := `int |> Lean.mkIdent
146+
let realIdent := `real |> Lean.mkIdent
147+
let uninterpretedIdent := `uninterpreted |> Lean.mkIdent
148+
if let some (some solverIdent) := solverIdent? then
149+
`(do
150+
let $tmIdent:ident ← TermManager.new
151+
let $solverIdent:ident ← Solver.new $tmIdent
152+
let $boolIdent ← $tmIdent:ident |>.getBooleanSort
153+
let $intIdent ← $tmIdent:ident |>.getIntegerSort
154+
let $realIdent ← $tmIdent:ident |>.getRealSort
155+
let $uninterpretedIdent ← $tmIdent:ident |>.mkUninterpretedSort "u"
156+
$code:term
157+
)
158+
else
159+
`(do
160+
let $tmIdent:ident ← TermManager.new
161+
$code:term
162+
)
146163
else `(do $code:term)
147164

148165
`(

cvc5Test/MkTerms1.lean

Lines changed: 20 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -10,10 +10,10 @@ def mkTerms1 : IO Unit := Env.runIO do
1010
← tm.mkBoolean true,
1111
← tm.mkBoolean false,
1212
)
13-
assertEq tru.getKind boolKind
14-
assertEq tru.getSort.toString "Bool"
15-
assertEq fls.getKind boolKind
16-
assertEq fls.getSort.toString "Bool"
13+
assertEq (← tru.getKind) boolKind
14+
assertEq (← tru.getSort).toString "Bool"
15+
assertEq (← fls.getKind) boolKind
16+
assertEq (← fls.getSort).toString "Bool"
1717

1818
let intKind := Kind.CONST_INTEGER
1919

@@ -23,30 +23,30 @@ def mkTerms1 : IO Unit := Env.runIO do
2323
← tm.mkInteger 7,
2424
← tm.mkInteger 11,
2525
)
26-
assertEq one.getKind intKind
27-
assertEq one.getSort.toString "Int"
28-
assertEq three.getKind intKind
29-
assertEq three.getSort.toString "Int"
30-
assertEq seven.getKind intKind
31-
assertEq seven.getSort.toString "Int"
32-
assertEq eleven.getKind intKind
33-
assertEq eleven.getSort.toString "Int"
26+
assertEq (← one.getKind) intKind
27+
assertEq (← one.getSort).toString "Int"
28+
assertEq (← three.getKind) intKind
29+
assertEq (← three.getSort).toString "Int"
30+
assertEq (← seven.getKind) intKind
31+
assertEq (← seven.getSort).toString "Int"
32+
assertEq (← eleven.getKind) intKind
33+
assertEq (← eleven.getSort).toString "Int"
3434

3535
let ite1 ← tm.mkTerm Kind.ITE #[fls, three, seven]
36-
assertEq ite1.getKind Kind.ITE
37-
assertEq ite1.getSort.toString "Int"
36+
assertEq (← ite1.getKind) Kind.ITE
37+
assertEq (← ite1.getSort).toString "Int"
3838

3939
let eq1 ← tm.mkTerm Kind.EQUAL #[ite1, eleven]
40-
assertEq eq1.getKind Kind.EQUAL
41-
assertEq eq1.getSort.toString "Bool"
40+
assertEq (← eq1.getKind) Kind.EQUAL
41+
assertEq (← eq1.getSort).toString "Bool"
4242

4343
let eq1' ← tm.mkTerm Kind.EQUAL #[ite1, eleven, one]
44-
assertEq eq1'.getKind Kind.AND
45-
assertEq eq1'.getSort.toString "Bool"
44+
assertEq (← eq1'.getKind) Kind.AND
45+
assertEq (← eq1'.getSort).toString "Bool"
4646

4747
let ite2 ← tm.mkTerm Kind.ITE #[tru, eq1, fls]
48-
assertEq ite2.getKind Kind.ITE
49-
assertEq ite2.getSort.toString "Bool"
48+
assertEq (← ite2.getKind) Kind.ITE
49+
assertEq (← ite2.getSort).toString "Bool"
5050

5151
#guard_msgs in
5252
#eval mkTerms1

cvc5Test/Unit/ApiCommand.lean

Lines changed: 3 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -18,8 +18,7 @@ def parseCommand (parser : InputParser) (s : String) : Env Command := do
1818
parser.appendIncrementalStringInput s
1919
parser.nextCommand
2020

21-
test![TestApiBlackCommand, invoke] tm => do
22-
let solver ← Solver.new tm
21+
test![TestApiBlackCommand, invoke] tm solver => do
2322
let parser ← InputParser.new solver
2423
let sm ← parser.getSymbolManager
2524
parser.setIncrementalStringInput
@@ -34,16 +33,14 @@ test![TestApiBlackCommand, invoke] tm => do
3433
assertError "Only one set-logic is allowed." do
3534
parseCommand parser "(set-logic QF_LRA)"
3635

37-
test![TestApiBlackCommand, toString] tm => do
38-
let solver ← Solver.new tm
36+
test![TestApiBlackCommand, toString] tm solver => do
3937
let parser ← InputParser.new solver
4038
parser.setIncrementalStringInput
4139
let cmd ← parseCommand parser "(set-logic QF_LIA)"
4240
assertFalse cmd.isNull
4341
assertEq cmd.toString "(set-logic QF_LIA)"
4442

45-
test![TestApiBlackCommand, getCommandName] tm => do
46-
let solver ← Solver.new tm
43+
test![TestApiBlackCommand, getCommandName] tm solver => do
4744
-- not in original test, silences the stderr warnings since the logic is not set otherwise
4845
solver.setLogic "ALL"
4946
let parser ← InputParser.new solver

cvc5Test/Unit/ApiInputParser.lean

Lines changed: 15 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -22,14 +22,12 @@ def parseLogicCommand (parser : InputParser) (logic : String) : Env Command := d
2222
test![TestApiBlackInputParser, constructSymbolManager] tm => do
2323
let _ ← SymbolManager.new tm
2424

25-
test![TestApiBlackInputParser, setFileInput] tm => do
26-
let solver ← Solver.new tm
25+
test![TestApiBlackInputParser, setFileInput] tm solver => do
2726
let parser ← InputParser.new solver
2827
assertError "Couldn't open file: nonexistent.smt2" do
2928
parser.setFileInput "nonexistent.smt2"
3029

31-
test![TestApiBlackInputParser, setStreamInput] tm => do
32-
let solver ← Solver.new tm
30+
test![TestApiBlackInputParser, setStreamInput] tm solver => do
3331
let parser ← InputParser.new solver
3432
let symbols ← parser.getSymbolManager
3533
let s := "(set-logic QF_LIA)\n(declare-fun a () Bool)\n(declare-fun b () Bool)\n"
@@ -43,8 +41,7 @@ test![TestApiBlackInputParser, setStreamInput] tm => do
4341
loop ()
4442
assertTrue (← parser.isDone)
4543

46-
test![TestApiBlackInputParser, setStreamInput'] tm => do
47-
let solver ← Solver.new tm
44+
test![TestApiBlackInputParser, setStreamInput'] tm solver => do
4845
let parser ← InputParser.new solver
4946
let symbols ← parser.getSymbolManager
5047
let s := "(set-logic QF_LIA)\n(declare-fun a () Bool)\n(declare-fun b () Bool)\n"
@@ -59,8 +56,7 @@ test![TestApiBlackInputParser, setStreamInput'] tm => do
5956
loop ()
6057
assertTrue (← parser.isDone)
6158

62-
test![TestApiBlackInputParser, setAndAppendIncrementalStringInput] tm => do
63-
let solver ← Solver.new tm
59+
test![TestApiBlackInputParser, setAndAppendIncrementalStringInput] tm solver => do
6460
let parser ← InputParser.new solver
6561
let symbols ← parser.getSymbolManager
6662
parser.setIncrementalStringInput (name := "input_parser_black")
@@ -82,8 +78,7 @@ test![TestApiBlackInputParser, setAndAppendIncrementalStringInput] tm => do
8278
assertTrue cmd.isNull
8379
assertTrue (← parser.isDone)
8480

85-
test![TestApiBlackInputParser, setAndAppendIncrementalStringInputInterleave] tm => do
86-
let solver ← Solver.new tm
81+
test![TestApiBlackInputParser, setAndAppendIncrementalStringInputInterleave] tm solver => do
8782
let parser ← InputParser.new solver
8883
let symbols ← parser.getSymbolManager
8984
parser.setIncrementalStringInput (name := "input_parser_black")
@@ -105,14 +100,12 @@ test![TestApiBlackInputParser, setAndAppendIncrementalStringInputInterleave] tm
105100
assertTrue cmd.isNull
106101
assertTrue (← parser.isDone)
107102

108-
test![TestApiBlackInputParser, appendIncrementalNoSet] tm => do
109-
let solver ← Solver.new tm
103+
test![TestApiBlackInputParser, appendIncrementalNoSet] tm solver => do
110104
let parser ← InputParser.new solver
111105
assertError "Input to parser not initialized" do
112106
parser.appendIncrementalStringInput "(set-logic ALL)"
113107

114-
test![TestApiBlackInputParser, setStringInput] tm => do
115-
let solver ← Solver.new tm
108+
test![TestApiBlackInputParser, setStringInput] tm solver => do
116109
let parser ← InputParser.new solver
117110
let symbols ← parser.getSymbolManager
118111
parser.setStringInput "(set-logic ALL)" (name := "input_parser_black")
@@ -122,32 +115,28 @@ test![TestApiBlackInputParser, setStringInput] tm => do
122115
let cmd ← parser.nextCommand
123116
assertTrue cmd.isNull
124117

125-
test![TestApiBlackInputParser, nextCommandNoInput] tm => do
126-
let solver ← Solver.new tm
118+
test![TestApiBlackInputParser, nextCommandNoInput] tm solver => do
127119
let parser ← InputParser.new solver
128120
parser.setStringInput "" (name := "input_parser_black")
129121
let cmd ← parser.nextCommand
130122
assertTrue cmd.isNull
131123

132-
test![TestApiBlackInputParser, nextCommandNoIncrementalInput] tm => do
133-
let solver ← Solver.new tm
124+
test![TestApiBlackInputParser, nextCommandNoIncrementalInput] tm solver => do
134125
let parser ← InputParser.new solver
135126
parser.setIncrementalStringInput (name := "input_parser_black")
136127
let cmd ← parser.nextCommand
137128
assertTrue cmd.isNull
138129
let term ← parser.nextTerm
139130
assertTrue term.isNull
140131

141-
test![TestApiBlackInputParser, nextTerm] tm => do
142-
let solver ← Solver.new tm
132+
test![TestApiBlackInputParser, nextTerm] tm solver => do
143133
let parser ← InputParser.new solver
144134
assertError "Input to parser not initialized" parser.nextTerm
145135
parser.setStringInput "" (name := "input_parser_black")
146136
let term ← parser.nextTerm
147137
assertTrue term.isNull
148138

149-
test![TestApiBlackInputParser, nextTerm2] tm => do
150-
let solver ← Solver.new tm
139+
test![TestApiBlackInputParser, nextTerm2] tm solver => do
151140
-- adding a set-logic compared to the original test to silence warnings
152141
solver.setLogic "ALL"
153142
let parser ← InputParser.new solver
@@ -166,7 +155,7 @@ test![TestApiBlackInputParser, nextTerm2] tm => do
166155
parser.appendIncrementalStringInput "(+ a 1)\n"
167156
let term ← assertOk parser.nextTerm
168157
assertFalse term.isNull
169-
assertEq term.getKind Kind.ADD
158+
assertEq (← term.getKind) Kind.ADD
170159
parser.appendIncrementalStringInput "(+ b 1)\n"
171160
assertError "Symbol 'b' not declared as a variable" parser.nextTerm
172161

@@ -215,8 +204,7 @@ test![TestApiBlackInputParser, setAndAppendIncrementalStringInput] tm => do
215204
"Logic mismatch when initializing InputParser.\n\
216205
The solver's logic: QF_LRA\nThe symbol manager's logic: QF_LIA"
217206

218-
test![TestApiBlackInputParser, incrementalSetString] tm => do
219-
let solver ← Solver.new tm
207+
test![TestApiBlackInputParser, incrementalSetString] tm solver => do
220208
let parser ← InputParser.new solver
221209
let symbols ← parser.getSymbolManager
222210
let mut out := ""
@@ -230,8 +218,7 @@ test![TestApiBlackInputParser, incrementalSetString] tm => do
230218
out := s!"{out}{output}"
231219
assertEq out ""
232220

233-
test![TestApiBlackInputParser, getDeclaredTermsAndSorts] tm => do
234-
let solver ← Solver.new tm
221+
test![TestApiBlackInputParser, getDeclaredTermsAndSorts] tm solver => do
235222
let parser ← InputParser.new solver
236223
let symbols ← parser.getSymbolManager
237224
parser.setIncrementalStringInput (name := "input_parser_black")
@@ -246,4 +233,4 @@ test![TestApiBlackInputParser, getDeclaredTermsAndSorts] tm => do
246233
let terms ← symbols.getDeclaredTerms
247234
assertEq sorts.size 1
248235
assertEq terms.size 1
249-
assertEq terms[0]!.getSort sorts[0]!
236+
assertEq (← terms[0]!.getSort) sorts[0]!

cvc5Test/Unit/ApiProof.lean

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -104,21 +104,21 @@ test![TestApiBlackProof, getRewriteRule] tm => do
104104

105105
assertOkDiscard proof.getRewriteRule
106106

107-
test![TestApiBlackProof, getResult] solver => do
108-
let proof ← createProof solver
107+
test![TestApiBlackProof, getResult] tm => do
108+
let proof ← createProof tm
109109
let _ := proof.getResult
110110

111-
test![TestApiBlackProof, getChildren] solver => do
112-
let proof ← createProof solver
111+
test![TestApiBlackProof, getChildren] tm => do
112+
let proof ← createProof tm
113113
let children := proof.getChildren
114114
assertFalse children.isEmpty
115115

116-
test![TestApiBlackProof, getArguments] solver => do
117-
let proof ← createProof solver
116+
test![TestApiBlackProof, getArguments] tm => do
117+
let proof ← createProof tm
118118
let _ := proof.getArguments
119119

120-
test![TestApiBlackProof, equalhash] solver => do
121-
let x ← createProof solver
120+
test![TestApiBlackProof, equalhash] tm => do
121+
let x ← createProof tm
122122
let kids := x.getChildren
123123
if h : 0 < kids.size then
124124
let y := kids[0]

cvc5Test/Unit/ApiResult.lean

Lines changed: 8 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -11,10 +11,8 @@ test![TestApiBlackResult, isNull] do
1111
-- lean API does not expose null results
1212
assertTrue true
1313

14-
test![TestApiBlackResult, equalHash] tm => do
15-
let solver ← Solver.new tm
16-
let u ← tm.mkUninterpretedSort "u"
17-
let x ← solver.declareFun "x" #[] u
14+
test![TestApiBlackResult, equalHash] tm solver => do
15+
let x ← solver.declareFun "x" #[] uninterpreted
1816
let x_eq_x ← tm.mkTerm .EQUAL #[x, x]
1917
solver.assertFormula x_eq_x
2018
-- skipping null-result-related checks
@@ -32,10 +30,8 @@ test![TestApiBlackResult, equalHash] tm => do
3230
assertNe res1.hash res3.hash
3331
assertNe res2.hash res3.hash
3432

35-
test![TestApiBlackResult, isSat] tm => do
36-
let solver ← Solver.new tm
37-
let u ← tm.mkUninterpretedSort "u"
38-
let x ← solver.declareFun "x" #[] u
33+
test![TestApiBlackResult, isSat] tm solver => do
34+
let x ← solver.declareFun "x" #[] uninterpreted
3935
solver.assertFormula (← tm.mkTerm .EQUAL #[x, x])
4036
let res ← solver.checkSat
4137
assertTrue res.isSat
@@ -47,10 +43,8 @@ test![TestApiBlackResult, isSat] tm => do
4743
assertEq ue.toString "UNKNOWN_REASON"
4844
assertEq res.getUnknownExplanation? none
4945

50-
test![TestApiBlackResult, isUnsat] tm => do
51-
let solver ← Solver.new tm
52-
let u ← tm.mkUninterpretedSort "u"
53-
let x ← solver.declareFun "x" #[] u
46+
test![TestApiBlackResult, isUnsat] tm solver => do
47+
let x ← solver.declareFun "x" #[] uninterpreted
5448
solver.assertFormula (← tm.mkTerm .NOT #[← tm.mkTerm .EQUAL #[x, x]])
5549
let res ← solver.checkSat
5650
assertFalse res.isSat
@@ -62,13 +56,11 @@ test![TestApiBlackResult, isUnsat] tm => do
6256
assertEq ue.toString "UNKNOWN_REASON"
6357
assertEq res.getUnknownExplanation? none
6458

65-
test![TestApiBlackResult, isUnknown] tm => do
66-
let solver ← Solver.new tm
59+
test![TestApiBlackResult, isUnknown] tm solver => do
6760
solver.setLogic "QF_NIA"
6861
solver.setOption "incremental" "false"
6962
solver.setOption "solve-real-as-int" "true"
70-
let realSort ← tm.getRealSort
71-
let x ← solver.declareFun "x" #[] realSort
63+
let x ← solver.declareFun "x" #[] real
7264
let zero := ← tm.mkReal 0
7365
let one := ← tm.mkReal 1
7466
solver.assertFormula (← tm.mkTerm .LT #[zero, x])

0 commit comments

Comments
 (0)