z3 0.0.20160427 → 0.0.20161008

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (68) hide show
  1. checksums.yaml +4 -4
  2. data/.rspec +2 -0
  3. data/Rakefile +56 -0
  4. data/examples/bit_tricks +21 -38
  5. data/examples/circuit_problems +170 -0
  6. data/lib/z3/ast.rb +21 -3
  7. data/lib/z3/context.rb +9 -7
  8. data/lib/z3/exception.rb +1 -2
  9. data/lib/z3/expr/arith_expr.rb +29 -11
  10. data/lib/z3/expr/array_expr.rb +5 -0
  11. data/lib/z3/expr/bitvec_expr.rb +293 -13
  12. data/lib/z3/expr/bool_expr.rb +30 -6
  13. data/lib/z3/expr/expr.rb +155 -2
  14. data/lib/z3/expr/float_expr.rb +185 -0
  15. data/lib/z3/expr/int_expr.rb +20 -5
  16. data/lib/z3/expr/real_expr.rb +1 -3
  17. data/lib/z3/expr/rounding_mode_expr.rb +5 -0
  18. data/lib/z3/expr/set_expr.rb +66 -0
  19. data/lib/z3/func_decl.rb +5 -5
  20. data/lib/z3/goal.rb +64 -0
  21. data/lib/z3/interface.rb +21 -222
  22. data/lib/z3/low_level.rb +84 -58
  23. data/lib/z3/low_level_auto.rb +1509 -1563
  24. data/lib/z3/model.rb +39 -37
  25. data/lib/z3/printer.rb +54 -12
  26. data/lib/z3/probe.rb +69 -0
  27. data/lib/z3/solver.rb +20 -20
  28. data/lib/z3/sort/array_sort.rb +24 -0
  29. data/lib/z3/sort/bitvec_sort.rb +1 -1
  30. data/lib/z3/sort/float_sort.rb +92 -0
  31. data/lib/z3/sort/rounding_mode_sort.rb +41 -0
  32. data/lib/z3/sort/set_sort.rb +31 -0
  33. data/lib/z3/sort/sort.rb +39 -5
  34. data/lib/z3/tactic.rb +69 -0
  35. data/lib/z3/very_low_level.rb +33 -29
  36. data/lib/z3/very_low_level_auto.rb +505 -517
  37. data/lib/z3.rb +13 -0
  38. data/spec/array_expr_spec.rb +18 -0
  39. data/spec/array_sort_spec.rb +11 -0
  40. data/spec/bitvec_expr_spec.rb +196 -44
  41. data/spec/bitvec_sort_spec.rb +29 -27
  42. data/spec/bool_expr_spec.rb +57 -55
  43. data/spec/bool_sort_spec.rb +17 -15
  44. data/spec/coverage_helper.rb +11 -0
  45. data/spec/expr_spec.rb +151 -147
  46. data/spec/float_expr_spec.rb +167 -0
  47. data/spec/float_sort_spec.rb +44 -0
  48. data/spec/goal_spec.rb +17 -0
  49. data/spec/int_expr_spec.rb +76 -63
  50. data/spec/int_sort_spec.rb +16 -14
  51. data/spec/integration/algebra_problems_spec.rb +4 -4
  52. data/spec/integration/cicruit_problem_spec.rb +23 -0
  53. data/spec/integration/geometry_problem_spec.rb +4 -4
  54. data/spec/integration/kinematics_problems_spec.rb +3 -3
  55. data/spec/model_spec.rb +39 -37
  56. data/spec/printer_spec.rb +49 -18
  57. data/spec/probe_spec.rb +17 -0
  58. data/spec/real_expr_spec.rb +59 -51
  59. data/spec/real_sort_spec.rb +22 -20
  60. data/spec/rounding_mode_expr_spec.rb +16 -0
  61. data/spec/rounding_mode_sort_spec.rb +13 -0
  62. data/spec/set_expr_spec.rb +61 -0
  63. data/spec/set_sort_spec.rb +27 -0
  64. data/spec/solver_spec.rb +37 -27
  65. data/spec/sort_spec.rb +38 -36
  66. data/spec/spec_helper.rb +59 -2
  67. data/spec/tactic_spec.rb +9 -0
  68. metadata +44 -4
data/lib/z3/model.rb CHANGED
@@ -1,51 +1,53 @@
1
- class Z3::Model
2
- include Enumerable
1
+ module Z3
2
+ class Model
3
+ include Enumerable
3
4
 
4
- attr_reader :_model
5
- def initialize(_model)
6
- @_model = _model
7
- end
5
+ attr_reader :_model
6
+ def initialize(_model)
7
+ @_model = _model
8
+ end
8
9
 
9
- def num_consts
10
- Z3::LowLevel.model_get_num_consts(self)
11
- end
10
+ def num_consts
11
+ LowLevel.model_get_num_consts(self)
12
+ end
12
13
 
13
- def consts
14
- (0...num_consts).map do |i|
15
- Z3::FuncDecl.new(Z3::LowLevel.model_get_const_decl(self, i))
14
+ def consts
15
+ (0...num_consts).map do |i|
16
+ FuncDecl.new(LowLevel.model_get_const_decl(self, i))
17
+ end
16
18
  end
17
- end
18
19
 
19
- def num_sorts
20
- Z3::LowLevel.model_get_num_sorts(self)
21
- end
20
+ def num_sorts
21
+ LowLevel.model_get_num_sorts(self)
22
+ end
22
23
 
23
- def num_funcs
24
- Z3::LowLevel.model_get_num_funcs(self)
25
- end
24
+ def num_funcs
25
+ LowLevel.model_get_num_funcs(self)
26
+ end
26
27
 
27
- def model_eval(ast, model_completion=false)
28
- Z3::Expr.new_from_pointer(Z3::LowLevel.model_eval(self, ast, model_completion))
29
- end
28
+ def model_eval(ast, model_completion=false)
29
+ Expr.new_from_pointer(LowLevel.model_eval(self, ast, model_completion))
30
+ end
30
31
 
31
- def [](ast)
32
- model_eval(ast)
33
- end
32
+ def [](ast)
33
+ model_eval(ast)
34
+ end
34
35
 
35
- def to_s
36
- "Z3::Model<#{ map{|n,v| "#{n}=#{v}"}.join(", ") }>"
37
- end
36
+ def to_s
37
+ "Z3::Model<#{ map{|n,v| "#{n}=#{v}"}.join(", ") }>"
38
+ end
38
39
 
39
- def inspect
40
- to_s
41
- end
40
+ def inspect
41
+ to_s
42
+ end
42
43
 
43
- def each
44
- consts.sort_by(&:name).each do |c|
45
- yield(
46
- c.range.var(c.name),
47
- Z3::Expr.new_from_pointer(Z3::LowLevel.model_get_const_interp(self, c))
48
- )
44
+ def each
45
+ consts.sort_by(&:name).each do |c|
46
+ yield(
47
+ c.range.var(c.name),
48
+ Expr.new_from_pointer(LowLevel.model_get_const_interp(self, c))
49
+ )
50
+ end
49
51
  end
50
52
  end
51
53
  end
data/lib/z3/printer.rb CHANGED
@@ -1,26 +1,68 @@
1
1
  module Z3
2
2
  class Printer
3
3
  def format(a)
4
+ format_ast(a).to_s
5
+ end
6
+
7
+ private
8
+
9
+ class PrintedExpr
10
+ attr_reader :str, :priority
11
+ def initialize(str, priority=false)
12
+ @str = str
13
+ @priority = priority
14
+ end
15
+ def to_s
16
+ @str
17
+ end
18
+ def enforce_parentheses
19
+ if @priority
20
+ "(#{@str})"
21
+ else
22
+ @str
23
+ end
24
+ end
25
+ end
26
+
27
+ def format_ast(a)
4
28
  case a.ast_kind
5
29
  when :numeral
6
- format_numeral(a)
30
+ PrintedExpr.new(Z3::LowLevel.get_numeral_string(a))
7
31
  when :app
8
- a.sexpr
9
- when :var
10
- a.sexpr
11
- when :quantifier
12
- a.sexpr
13
- when :func_decl
14
- a.sexpr
15
- when :unknown
16
- a.sexpr
32
+ format_app(a)
33
+ when :var, :quantifier, :func_decl, :unknown
34
+ PrintedExpr.new(a.sexpr)
17
35
  else
18
36
  raise Z3::Exception, "Unknown AST kind #{a.ast_kind}"
19
37
  end
20
38
  end
21
39
 
22
- def format_numeral(a)
23
- Z3::LowLevel.get_numeral_string(a)
40
+ def format_app(a)
41
+ if LowLevel::is_algebraic_number(a)
42
+ PrintedExpr.new(LowLevel::get_numeral_decimal_string(a, 10))
43
+ elsif LowLevel::is_as_array(a)
44
+ decl = FuncDecl.new( LowLevel::get_as_array_func_decl(a) )
45
+ PrintedExpr.new(decl.sexpr.gsub(/k!\d+/, "k!"))
46
+ elsif a.func_decl.name == "fp.numeral" and a.sort.is_a?(FloatSort)
47
+ s = a.significand_string
48
+ e = a.exponent_string
49
+ e = "+#{e}" if e[0] != "-"
50
+ PrintedExpr.new("#{s}B#{e}")
51
+ else
52
+ decl = a.func_decl
53
+ name = decl.name
54
+ args = a.arguments.map{|x| format_ast(x)}
55
+ return PrintedExpr.new(name, false) if args.size == 0
56
+ # All operators
57
+ if name !~ /[a-z0-9]/
58
+ if args.size == 2
59
+ return PrintedExpr.new("#{args[0].enforce_parentheses} #{name} #{args[1].enforce_parentheses}", true)
60
+ elsif args.size == 1
61
+ return PrintedExpr.new("#{name}#{args[0].enforce_parentheses}", true)
62
+ end
63
+ end
64
+ PrintedExpr.new("#{name}(#{args.join(", ")})")
65
+ end
24
66
  end
25
67
  end
26
68
  end
data/lib/z3/probe.rb ADDED
@@ -0,0 +1,69 @@
1
+ module Z3
2
+ class Probe
3
+ attr_reader :_probe
4
+ def initialize(_probe)
5
+ @_probe = _probe
6
+ LowLevel.probe_inc_ref(self)
7
+ end
8
+
9
+ def &(other)
10
+ raise Z3::Exception, "Probe required" unless other.is_a?(Probe)
11
+ Probe.new LowLevel.probe_and(self, other)
12
+ end
13
+
14
+ def |(other)
15
+ raise Z3::Exception, "Probe required" unless other.is_a?(Probe)
16
+ Probe.new LowLevel.probe_or(self, other)
17
+ end
18
+
19
+ def ~
20
+ Probe.new LowLevel.probe_not(self)
21
+ end
22
+
23
+ def ==(other)
24
+ raise Z3::Exception, "Probe required" unless other.is_a?(Probe)
25
+ Probe.new LowLevel.probe_eq(self, other)
26
+ end
27
+
28
+ def >=(other)
29
+ raise Z3::Exception, "Probe required" unless other.is_a?(Probe)
30
+ Probe.new LowLevel.probe_ge(self, other)
31
+ end
32
+
33
+ def >(other)
34
+ raise Z3::Exception, "Probe required" unless other.is_a?(Probe)
35
+ Probe.new LowLevel.probe_gt(self, other)
36
+ end
37
+
38
+ def <=(other)
39
+ raise Z3::Exception, "Probe required" unless other.is_a?(Probe)
40
+ Probe.new LowLevel.probe_le(self, other)
41
+ end
42
+
43
+ def <(other)
44
+ raise Z3::Exception, "Probe required" unless other.is_a?(Probe)
45
+ Probe.new LowLevel.probe_lt(self, other)
46
+ end
47
+
48
+ def apply(goal)
49
+ raise Z3::Exception, "Goal required" unless goal.is_a?(Goal)
50
+ LowLevel.probe_apply(self, goal)
51
+ end
52
+
53
+ class <<self
54
+ def const(num)
55
+ raise Z3::Exception, "Number required" unless num.is_a?(Numeric)
56
+ new LowLevel.probe_const(num.to_f)
57
+ end
58
+
59
+ def names
60
+ (0...LowLevel.get_num_probes).map{|i| LowLevel.get_probe_name(i) }
61
+ end
62
+
63
+ def named(str)
64
+ raise Z3::Exception, "#{str} not on list of known probes, available: #{names.join(" ")}" unless names.include?(str)
65
+ new LowLevel.mk_probe(str)
66
+ end
67
+ end
68
+ end
69
+ end
data/lib/z3/solver.rb CHANGED
@@ -2,39 +2,44 @@ module Z3
2
2
  class Solver
3
3
  attr_reader :_solver
4
4
  def initialize
5
- @_solver = Z3::LowLevel.mk_solver
6
- Z3::LowLevel.solver_inc_ref(self)
5
+ @_solver = LowLevel.mk_solver
6
+ LowLevel.solver_inc_ref(self)
7
7
  end
8
8
 
9
9
  def push
10
- Z3::LowLevel.solver_push(self)
10
+ LowLevel.solver_push(self)
11
11
  end
12
12
 
13
13
  def pop(n=1)
14
- Z3::LowLevel.solver_pop(self, n)
14
+ LowLevel.solver_pop(self, n)
15
15
  end
16
16
 
17
17
  def reset
18
- Z3::LowLevel.solver_reset(self)
18
+ LowLevel.solver_reset(self)
19
19
  end
20
20
 
21
21
  def assert(ast)
22
- Z3::LowLevel.solver_assert(self, ast)
22
+ LowLevel.solver_assert(self, ast)
23
23
  end
24
24
 
25
25
  def check
26
- check_sat_results(Z3::LowLevel.solver_check(self))
26
+ check_sat_results(LowLevel.solver_check(self))
27
27
  end
28
28
 
29
29
  def model
30
30
  Z3::Model.new(
31
- Z3::LowLevel.solver_get_model(self)
31
+ LowLevel.solver_get_model(self)
32
32
  )
33
33
  end
34
34
 
35
35
  def assertions
36
- _ast_vector = Z3::LowLevel.solver_get_assertions(self)
37
- Z3::LowLevel.unpack_ast_vector(_ast_vector)
36
+ _ast_vector = LowLevel.solver_get_assertions(self)
37
+ LowLevel.unpack_ast_vector(_ast_vector)
38
+ end
39
+
40
+ def statistics
41
+ _stats = LowLevel::solver_get_statistics(self)
42
+ LowLevel.unpack_statistics(_stats)
38
43
  end
39
44
 
40
45
  def prove!(ast)
@@ -60,16 +65,11 @@ module Z3
60
65
  private
61
66
 
62
67
  def check_sat_results(r)
63
- case r
64
- when 1
65
- :sat
66
- when 0
67
- :unknown
68
- when -1
69
- :unsat
70
- else
71
- raise "Wrong SAT result #{r}"
72
- end
68
+ {
69
+ -1 => :unsat,
70
+ 0 => :unknown,
71
+ 1 => :sat,
72
+ }[r] or raise Z3::Exception, "Wrong SAT result #{r}"
73
73
  end
74
74
  end
75
75
  end
@@ -0,0 +1,24 @@
1
+ module Z3
2
+ class ArraySort < Sort
3
+ attr_reader :key_sort, :value_sort
4
+ def initialize(key_sort, value_sort)
5
+ @key_sort = key_sort
6
+ @value_sort = value_sort
7
+ super LowLevel.mk_array_sort(key_sort, value_sort)
8
+ end
9
+
10
+ def expr_class
11
+ ArrayExpr
12
+ end
13
+
14
+ def to_s
15
+ "Array(#{key_sort}, #{value_sort})"
16
+ end
17
+
18
+ def inspect
19
+ "ArraySort(#{key_sort}, #{value_sort})"
20
+ end
21
+
22
+ public_class_method :new
23
+ end
24
+ end
@@ -30,7 +30,7 @@ module Z3
30
30
 
31
31
  def >(other)
32
32
  raise ArgumentError unless other.is_a?(Sort)
33
- return true if other.is_a?(IntSort)
33
+ return true if other.is_a?(IntSort) # This is nasty...
34
34
  return true if other.is_a?(BitvecSort) and size > other.size
35
35
  false
36
36
  end
@@ -0,0 +1,92 @@
1
+ module Z3
2
+ class FloatSort < Sort
3
+ def initialize(e, s=nil)
4
+ if s.nil?
5
+ case e
6
+ when 16
7
+ super LowLevel.mk_fpa_sort_16
8
+ when 32
9
+ super LowLevel.mk_fpa_sort_32
10
+ when 64
11
+ super LowLevel.mk_fpa_sort_64
12
+ when 128
13
+ super LowLevel.mk_fpa_sort_128
14
+ when :half
15
+ super LowLevel.mk_fpa_sort_half
16
+ when :single
17
+ super LowLevel.mk_fpa_sort_single
18
+ when :double
19
+ super LowLevel.mk_fpa_sort_double
20
+ when :quadruple
21
+ super LowLevel.mk_fpa_sort_quadruple
22
+ else
23
+ raise "Unknown float type #{e}, use FloatSort.new(exponent_bits, significant_bits)"
24
+ end
25
+ else
26
+ super LowLevel.mk_fpa_sort(e, s)
27
+ end
28
+ end
29
+
30
+ def expr_class
31
+ FloatExpr
32
+ end
33
+
34
+ def from_const(val)
35
+ if val.is_a?(Float)
36
+ new LowLevel.mk_fpa_numeral_double(val, self)
37
+ elsif val.is_a?(Integer)
38
+ val_f = val.to_f
39
+ # FIXME, there are other constructors
40
+ raise Z3::Exception, "Out of range" unless val_f == val
41
+ new LowLevel.mk_fpa_numeral_double(val_f, self)
42
+ else
43
+ raise Z3::Exception, "Cannot convert #{val.class} to #{self.class}"
44
+ end
45
+ end
46
+
47
+ def >(other)
48
+ raise ArgumentError unless other.is_a?(Sort)
49
+ return true if other.is_a?(IntSort) # This is nasty...
50
+ return true if other.is_a?(RealSort) # This is nasty...
51
+ false
52
+ end
53
+
54
+ def ebits
55
+ LowLevel.fpa_get_ebits(self)
56
+ end
57
+
58
+ def sbits
59
+ LowLevel.fpa_get_sbits(self)
60
+ end
61
+
62
+ def to_s
63
+ "Float(#{ebits}, #{sbits})"
64
+ end
65
+
66
+ def inspect
67
+ "FloatSort(#{ebits}, #{sbits})"
68
+ end
69
+
70
+ def nan
71
+ new LowLevel.mk_fpa_nan(self)
72
+ end
73
+
74
+ def positive_infinity
75
+ new LowLevel.mk_fpa_inf(self, false)
76
+ end
77
+
78
+ def negative_infinity
79
+ new LowLevel.mk_fpa_inf(self, true)
80
+ end
81
+
82
+ def positive_zero
83
+ new LowLevel.mk_fpa_zero(self, false)
84
+ end
85
+
86
+ def negative_zero
87
+ new LowLevel.mk_fpa_zero(self, true)
88
+ end
89
+
90
+ public_class_method :new
91
+ end
92
+ end
@@ -0,0 +1,41 @@
1
+ module Z3
2
+ class RoundingModeSort < Sort
3
+ def initialize
4
+ super LowLevel.mk_fpa_rounding_mode_sort
5
+ end
6
+
7
+ def expr_class
8
+ RoundingModeExpr
9
+ end
10
+
11
+ def to_s
12
+ "RoundingMode"
13
+ end
14
+
15
+ def inspect
16
+ "RoundingModeSort"
17
+ end
18
+
19
+ def nearest_ties_away
20
+ RoundingModeExpr.new(LowLevel.mk_fpa_round_nearest_ties_to_away, self)
21
+ end
22
+
23
+ def nearest_ties_even
24
+ RoundingModeExpr.new(LowLevel.mk_fpa_round_nearest_ties_to_even, self)
25
+ end
26
+
27
+ def towards_zero
28
+ RoundingModeExpr.new(LowLevel.mk_fpa_round_toward_zero, self)
29
+ end
30
+
31
+ def towards_negative
32
+ RoundingModeExpr.new(LowLevel.mk_fpa_round_toward_negative, self)
33
+ end
34
+
35
+ def towards_positive
36
+ RoundingModeExpr.new(LowLevel.mk_fpa_round_toward_positive, self)
37
+ end
38
+
39
+ public_class_method :new
40
+ end
41
+ end
@@ -0,0 +1,31 @@
1
+ module Z3
2
+ class SetSort < Sort
3
+ attr_reader :element_sort
4
+ def initialize(element_sort)
5
+ @element_sort = element_sort
6
+ super LowLevel.mk_set_sort(element_sort)
7
+ end
8
+
9
+ def expr_class
10
+ SetExpr
11
+ end
12
+
13
+ def to_s
14
+ "Set(#{element_sort})"
15
+ end
16
+
17
+ def inspect
18
+ "SetSort(#{element_sort})"
19
+ end
20
+
21
+ def Empty
22
+ new(LowLevel.mk_empty_set(self))
23
+ end
24
+
25
+ def Full
26
+ new(LowLevel.mk_full_set(self))
27
+ end
28
+
29
+ public_class_method :new
30
+ end
31
+ end
data/lib/z3/sort/sort.rb CHANGED
@@ -41,7 +41,15 @@ module Z3
41
41
  end
42
42
 
43
43
  def to_s
44
- LowLevel.sort_to_string(self)
44
+ LowLevel.ast_to_string(self)
45
+ end
46
+
47
+ def eql?(other)
48
+ self == other
49
+ end
50
+
51
+ def hash
52
+ self.class.hash
45
53
  end
46
54
 
47
55
  def inspect
@@ -50,8 +58,8 @@ module Z3
50
58
 
51
59
  def var(name)
52
60
  new(
53
- Z3::LowLevel.mk_const(
54
- Z3::LowLevel.mk_string_symbol(name),
61
+ LowLevel.mk_const(
62
+ LowLevel.mk_string_symbol(name),
55
63
  self,
56
64
  )
57
65
  )
@@ -71,8 +79,20 @@ module Z3
71
79
  raise Z3::Exception, "Can't convert #{v.sort} into #{self}"
72
80
  end
73
81
 
82
+ def cast(a)
83
+ if a.is_a?(Expr)
84
+ if a.sort == self
85
+ a
86
+ else
87
+ from_value(a)
88
+ end
89
+ else
90
+ from_const(a)
91
+ end
92
+ end
93
+
74
94
  def self.from_pointer(_sort)
75
- kind = Z3::VeryLowLevel.Z3_get_sort_kind(Z3::LowLevel._ctx_pointer, _sort)
95
+ kind = VeryLowLevel.Z3_get_sort_kind(LowLevel._ctx_pointer, _sort)
76
96
  case kind
77
97
  when 1
78
98
  BoolSort.new
@@ -81,8 +101,22 @@ module Z3
81
101
  when 3
82
102
  RealSort.new
83
103
  when 4
84
- n = Z3::VeryLowLevel.Z3_get_bv_sort_size(Z3::LowLevel._ctx_pointer, _sort)
104
+ n = VeryLowLevel.Z3_get_bv_sort_size(LowLevel._ctx_pointer, _sort)
85
105
  BitvecSort.new(n)
106
+ when 5
107
+ domain = from_pointer(VeryLowLevel.Z3_get_array_sort_domain(LowLevel._ctx_pointer, _sort))
108
+ range = from_pointer(VeryLowLevel.Z3_get_array_sort_range(LowLevel._ctx_pointer, _sort))
109
+ if range == BoolSort.new
110
+ SetSort.new(domain)
111
+ else
112
+ ArraySort.new(domain, range)
113
+ end
114
+ when 9
115
+ e = VeryLowLevel.Z3_fpa_get_ebits(LowLevel._ctx_pointer, _sort)
116
+ s = VeryLowLevel.Z3_fpa_get_sbits(LowLevel._ctx_pointer, _sort)
117
+ FloatSort.new(e, s)
118
+ when 10
119
+ RoundingModeSort.new
86
120
  else
87
121
  raise "Unknown sort kind #{kind}"
88
122
  end
data/lib/z3/tactic.rb ADDED
@@ -0,0 +1,69 @@
1
+ module Z3
2
+ class Tactic
3
+ attr_reader :tactic
4
+ def initialize(_tactic)
5
+ @_tactic = _tactic
6
+ end
7
+
8
+ def help
9
+ LowLevel.tactic_get_help(self)
10
+ end
11
+
12
+ def or_else(other)
13
+ raise Z3::Exception, "Tactic required" unless other.is_a?(Tactic)
14
+ Tactic.new LowLevel.tactic_or_else(self, other)
15
+ end
16
+
17
+ def and_then(other)
18
+ raise Z3::Exception, "Tactic required" unless other.is_a?(Tactic)
19
+ Tactic.new LowLevel.tactic_and_then(self, other)
20
+ end
21
+
22
+ def parallel_and_then(other)
23
+ raise Z3::Exception, "Tactic required" unless other.is_a?(Tactic)
24
+ Tactic.new LowLevel.tactic_par_and_then(self, other)
25
+ end
26
+
27
+ def repeat(num)
28
+ raise Z3::Exception, "Nonnegative Integer required" unless num.is_a?(Integer) and num >= 0
29
+ Tactic.new LowLevel.tactic_repeat(self, num)
30
+ end
31
+
32
+ def try_for(time_ms)
33
+ raise Z3::Exception, "Nonnegative Integer required" unless time_ms.is_a?(Integer) and time_ms >= 0
34
+ Tactic.new LowLevel.tactic_try_for(self, time_ms)
35
+ end
36
+
37
+ class << self
38
+ def fail
39
+ new LowLevel.tactic_fail
40
+ end
41
+
42
+ def fail_if(probe)
43
+ raise Z3::Exception, "Prope required" unless probe.is_a?(Probe)
44
+ new LowLevel.tactic_fail_if(probe)
45
+ end
46
+
47
+ def fail_if_not_decided
48
+ new LowLevel.tactic_fail_if_not_decided
49
+ end
50
+
51
+ def skip
52
+ new LowLevel.tactic_skip
53
+ end
54
+
55
+ def when(probe, tactic)
56
+ raise Z3::Exception, "Prope required" unless probe.is_a?(Probe)
57
+ raise Z3::Exception, "Tactic required" unless tactic.is_a?(Tactic)
58
+ new LowLevel.tactic_when(probe, tactic)
59
+ end
60
+
61
+ def cond(probe, tactic1, tactic2)
62
+ raise Z3::Exception, "Prope required" unless probe.is_a?(Probe)
63
+ raise Z3::Exception, "Tactic required" unless tactic1.is_a?(Tactic)
64
+ raise Z3::Exception, "Tactic required" unless tactic2.is_a?(Tactic)
65
+ new LowLevel.tactic_cond(probe, tactic1, tactic2)
66
+ end
67
+ end
68
+ end
69
+ end