mbt-gen 0.0.13 → 0.0.14
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.
- checksums.yaml +4 -4
- data/lib/mbt-gen.rb +42 -19
- data/lib/regexp-to-smtlib.rb +3 -3
- data/lib/solver-lib.rb +4 -4
- metadata +2 -2
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 4dab888f896a820078b818a69beb6c96832509be151437332a64efe493c99c43
|
|
4
|
+
data.tar.gz: 7bb0d5281265df6171e316c4c5cf5b2f6ef909bee7549cb6213c3d61e79c46fe
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: e14470e1741ccc1dfede14112f045bb952f42afbb4c8d55af8ac42bcf4517ae4de9fe0fedd6b3296c3a51651665c8d2d3a996e51fa7be892e7a9dea6890d28c7
|
|
7
|
+
data.tar.gz: 6e723168766e1dc4414e9e25344e9a3f2abc4b6704e5d25bb85e19c20b9f933b37deea1fa904f2954689151a4db3b41a6c427856ce5534e10473540a43ed6fd4
|
data/lib/mbt-gen.rb
CHANGED
|
@@ -182,6 +182,10 @@ def maxLength_contraint_for_expr(expr, maxLength)
|
|
|
182
182
|
"(<= (str.len #{expr}) #{maxLength})"
|
|
183
183
|
end
|
|
184
184
|
|
|
185
|
+
def minLength_contraint_for_expr(expr, minLength)
|
|
186
|
+
"(>= (str.len #{expr}) #{minLength})"
|
|
187
|
+
end
|
|
188
|
+
|
|
185
189
|
def oneOf_contraint_for_expr(expr, values)
|
|
186
190
|
list = values.map do |val|
|
|
187
191
|
"(= #{expr} \"#{val}\")"
|
|
@@ -246,7 +250,6 @@ def translate_field_def_to_SMTLIB_constraints(progress, solver, fielddef, xpath,
|
|
|
246
250
|
solver.associateAssertionIDWith(assertionID, info)
|
|
247
251
|
solver.to_solver(progress, "(assert (! (=> #{varname}-filled #{regex_constraint_for_expr("#{varname}-value", fielddef[:regex])}) :named #{assertionID}))")
|
|
248
252
|
end
|
|
249
|
-
# TODO: minLength?
|
|
250
253
|
if fielddef[:maxLength] then
|
|
251
254
|
assertionID = "maxLength-#{varname}"
|
|
252
255
|
info = {
|
|
@@ -259,6 +262,18 @@ def translate_field_def_to_SMTLIB_constraints(progress, solver, fielddef, xpath,
|
|
|
259
262
|
solver.associateAssertionIDWith(assertionID, info)
|
|
260
263
|
solver.to_solver(progress, "(assert (! (=> #{varname}-filled #{maxLength_contraint_for_expr("#{varname}-value", fielddef[:maxLength])}) :named #{assertionID}))")
|
|
261
264
|
end
|
|
265
|
+
if fielddef[:minLength] then
|
|
266
|
+
assertionID = "minLength-#{varname}"
|
|
267
|
+
info = {
|
|
268
|
+
:assertion_type => :constraint,
|
|
269
|
+
:xpath => xpath,
|
|
270
|
+
:datatype => :string,
|
|
271
|
+
:value => fielddef[:minLength],
|
|
272
|
+
:constraint_type => :minLength
|
|
273
|
+
}
|
|
274
|
+
solver.associateAssertionIDWith(assertionID, info)
|
|
275
|
+
solver.to_solver(progress, "(assert (! (=> #{varname}-filled #{minLength_contraint_for_expr("#{varname}-value", fielddef[:minLength])}) :named #{assertionID}))")
|
|
276
|
+
end
|
|
262
277
|
if fielddef[:from_list] then
|
|
263
278
|
assertionID = "oneOf-#{varname}"
|
|
264
279
|
list_filename = "#{LISTS_DIR}/#{fielddef[:from_list]}"
|
|
@@ -310,12 +325,16 @@ def translate_list_def_to_SMTLIB_constraints(progress, solver, fielddef, varname
|
|
|
310
325
|
solver.to_solver(progress, "(assert (! (=> (< #{i} #{varname}-size) #{regex_constraint_for_expr("#{varname}-index-#{i}-value", fielddef[:regex])}) :named list-regex-#{varname}-index-#{i}))")
|
|
311
326
|
end
|
|
312
327
|
end
|
|
313
|
-
# TODO: minLength?
|
|
314
328
|
if fielddef[:maxLength] then
|
|
315
329
|
fielddef[:model_maxLength].times do |i|
|
|
316
330
|
solver.to_solver(progress, "(assert (! (=> (< #{i} #{varname}-size) #{maxLength_contraint_for_expr("#{varname}-index-#{i}-value", fielddef[:maxLength])}) :named list-maxLength-#{varname}-index-#{i}))")
|
|
317
331
|
end
|
|
318
332
|
end
|
|
333
|
+
if fielddef[:minLength] then
|
|
334
|
+
fielddef[:model_maxLength].times do |i|
|
|
335
|
+
solver.to_solver(progress, "(assert (! (=> (< #{i} #{varname}-size) #{minLength_contraint_for_expr("#{varname}-index-#{i}-value", fielddef[:minLength])}) :named list-minLength-#{varname}-index-#{i}))")
|
|
336
|
+
end
|
|
337
|
+
end
|
|
319
338
|
when :enum
|
|
320
339
|
fielddef[:model_maxLength].times do |i|
|
|
321
340
|
solver.to_solver(progress, "(assert (! (=> (< #{i} #{varname}-size) #{enum_constraint_for_expr("#{varname}-index-#{i}-value", fielddef[:values])}) :named list-enum-#{varname}-index-#{i}))")
|
|
@@ -412,7 +431,7 @@ def translate_substructure_to_SMTLIB(progress, solver, struct, hash = {})
|
|
|
412
431
|
solver.to_solver(progress, "(assert (! (=> (not #{filled_var_for_field(xpath)}) (= #{size_var_for_list(xpath)} 0)) :named empty-objlist-has-zero-size-#{raw_field(xpath)}))")
|
|
413
432
|
solver.to_solver(progress, "(assert (! (=> (= #{size_var_for_list(xpath)} 0) (not #{filled_var_for_field(xpath)})) :named objlist-has-zero-size-implies-empty-objlist-#{raw_field(xpath)}))")
|
|
414
433
|
minSize = 0
|
|
415
|
-
solver.to_solver(progress, "(assert (! (=> #{filled_var_for_field(xpath)} (and (> #{size_var_for_list(xpath)} #{minSize}) (
|
|
434
|
+
solver.to_solver(progress, "(assert (! (=> #{filled_var_for_field(xpath)} (and (> #{size_var_for_list(xpath)} #{minSize}) (<= #{size_var_for_list(xpath)} #{definition[:model_maxLength]}))) :named filled-objlist-has-positive-size-#{raw_field(xpath)}))")
|
|
416
435
|
solver.to_solver(progress, "(assert (! (=> (> #{size_var_for_list(xpath)} 0) #{filled_var_for_field(xpath)}) :named objlist-has-positive-size-implies-filled-objlist-#{raw_field(xpath)}))")
|
|
417
436
|
definition[:model_maxLength].times do |i|
|
|
418
437
|
ext_xpath = "#{xpath}/#{i}"
|
|
@@ -628,7 +647,7 @@ def translate_validation_rule_to_SMTLIB(rule, context_struct, prefix, config, op
|
|
|
628
647
|
raise RuntimeError.new("could not parse LIST_VALUE_FIRST_ELEMENT[...]: #{m.inspect} in validation rule #{rule_name}")
|
|
629
648
|
end
|
|
630
649
|
xpath = $1
|
|
631
|
-
index = Integer($2)
|
|
650
|
+
index = Integer($2, 10)
|
|
632
651
|
l = resolve_field_path(xpath, context_struct, prefix)
|
|
633
652
|
value_var_for_list(l, index)
|
|
634
653
|
end
|
|
@@ -724,7 +743,7 @@ def translate_validation_rule_to_SMTLIB(rule, context_struct, prefix, config, op
|
|
|
724
743
|
end
|
|
725
744
|
elsif fdef[:datatype] == :int then
|
|
726
745
|
terms = values.filter{|l| !l.start_with?("#")}.map do |val|
|
|
727
|
-
"(= #{value_var_for_field(fpath)} #{Integer(val)})"
|
|
746
|
+
"(= #{value_var_for_field(fpath)} #{Integer(val, 10)})"
|
|
728
747
|
end
|
|
729
748
|
else
|
|
730
749
|
raise RuntimeError.new("FIELD_IN_QUERY[] was applied to a field of datatype #{fdef[:datatype].inspect}. However, it can only be applied to fields of datatype string or int.")
|
|
@@ -793,7 +812,7 @@ def parse_field_value(fielddef, value)
|
|
|
793
812
|
datatype = fielddef[:datatype]
|
|
794
813
|
case datatype
|
|
795
814
|
when :int
|
|
796
|
-
return Integer(value)
|
|
815
|
+
return Integer(value, 10)
|
|
797
816
|
when :string
|
|
798
817
|
return solver_value_to_string(value)
|
|
799
818
|
when :enum
|
|
@@ -847,7 +866,11 @@ def pick_solver_value_for_field(field_desc)
|
|
|
847
866
|
if field_desc[:maxLength] then
|
|
848
867
|
"a" * field_desc[:maxLength]
|
|
849
868
|
else
|
|
850
|
-
|
|
869
|
+
if field_desc[:minLength] then
|
|
870
|
+
"a" * field_desc[:minLength]
|
|
871
|
+
else
|
|
872
|
+
"default"
|
|
873
|
+
end
|
|
851
874
|
end
|
|
852
875
|
elsif field_desc[:datatype] == :enum then
|
|
853
876
|
field_desc[:values].first.to_s
|
|
@@ -878,8 +901,8 @@ def add_max_struct_to_doc(progress, struct, doc, prefix = nil)
|
|
|
878
901
|
node = node.first
|
|
879
902
|
end
|
|
880
903
|
xpath_element = value[:xpath_element]
|
|
881
|
-
if Integer(value[:model_maxLength]) > 0 then
|
|
882
|
-
Integer(value[:model_maxLength]).times do |i|
|
|
904
|
+
if Integer(value[:model_maxLength], 10) > 0 then
|
|
905
|
+
Integer(value[:model_maxLength], 10).times do |i|
|
|
883
906
|
node.add_child("<#{xpath_element}>#{format_solver_value(value, pick_solver_value_for_field(value))}</#{xpath_element}>")
|
|
884
907
|
end
|
|
885
908
|
end
|
|
@@ -941,8 +964,8 @@ def add_model_struct_to_doc(progress, struct, doc, model, prefix = nil)
|
|
|
941
964
|
node = node.first
|
|
942
965
|
end
|
|
943
966
|
xpath_element = value[:xpath_element]
|
|
944
|
-
if Integer(model_value[:size]) > 0 then
|
|
945
|
-
model_value[:value].slice(0, Integer(model_value[:size])).each do |mvalue|
|
|
967
|
+
if Integer(model_value[:size], 10) > 0 then
|
|
968
|
+
model_value[:value].slice(0, Integer(model_value[:size], 10)).each do |mvalue|
|
|
946
969
|
node.add_child("<#{xpath_element}>#{solver_value_to_string(mvalue)}</#{xpath_element}>")
|
|
947
970
|
end
|
|
948
971
|
end
|
|
@@ -952,7 +975,7 @@ def add_model_struct_to_doc(progress, struct, doc, model, prefix = nil)
|
|
|
952
975
|
node = node.first
|
|
953
976
|
end
|
|
954
977
|
xpath_element = value[:xpath_element]
|
|
955
|
-
if Integer(model_value[:size]) > 0 then
|
|
978
|
+
if Integer(model_value[:size], 10) > 0 then
|
|
956
979
|
model_value[:size].times do |index|
|
|
957
980
|
cnode = node.add_child("<#{xpath_element}></#{xpath_element}>")
|
|
958
981
|
if cnode.is_a?(Nokogiri::XML::NodeSet) then
|
|
@@ -1328,7 +1351,7 @@ def z3ValueToRubyValue(value)
|
|
|
1328
1351
|
if value =~ /\"(.*)\"/ then # string
|
|
1329
1352
|
return $1
|
|
1330
1353
|
elsif value =~ /\d+/ then # int
|
|
1331
|
-
return Integer(value)
|
|
1354
|
+
return Integer(value, 10)
|
|
1332
1355
|
elsif value == "true"
|
|
1333
1356
|
return true
|
|
1334
1357
|
elsif value == "false" then
|
|
@@ -1596,7 +1619,7 @@ def default_parser_for_type(value_str, datatype)
|
|
|
1596
1619
|
if datatype == :string or datatype == :enum then
|
|
1597
1620
|
value_str
|
|
1598
1621
|
elsif datatype == :int then
|
|
1599
|
-
Integer(value_str)
|
|
1622
|
+
Integer(value_str, 10)
|
|
1600
1623
|
elsif datatype == :date then
|
|
1601
1624
|
Date.parse(value_str)
|
|
1602
1625
|
elsif datatype == :timestamp then
|
|
@@ -1819,12 +1842,12 @@ class CoreEnumerationAlgo
|
|
|
1819
1842
|
|
|
1820
1843
|
def self.parse_continuation_point(line)
|
|
1821
1844
|
split = line.split(";")
|
|
1822
|
-
doc_number = Integer(split[0])
|
|
1823
|
-
num_docs = Integer(split[1])
|
|
1845
|
+
doc_number = Integer(split[0], 10)
|
|
1846
|
+
num_docs = Integer(split[1], 10)
|
|
1824
1847
|
state = CoreEnumerationAlgo.parse_state(split[2])
|
|
1825
1848
|
assignment = CoreEnumerationAlgo.parse_assignment(split[3])
|
|
1826
1849
|
new_assignment = CoreEnumerationAlgo.parse_assignment(split[4])
|
|
1827
|
-
processessing_time = Integer(split[5])
|
|
1850
|
+
processessing_time = Integer(split[5], 10)
|
|
1828
1851
|
return [doc_number, num_docs, state, assignment, new_assignment, processessing_time]
|
|
1829
1852
|
end
|
|
1830
1853
|
|
|
@@ -2523,7 +2546,7 @@ def generate(message, argv, message_config_filename = nil)
|
|
|
2523
2546
|
elsif opt == "-generate-docs-from" then
|
|
2524
2547
|
options[:combination_source] = argv.shift
|
|
2525
2548
|
elsif opt == "-skip" then
|
|
2526
|
-
options[:skip] = Integer(argv.shift)
|
|
2549
|
+
options[:skip] = Integer(argv.shift, 10)
|
|
2527
2550
|
elsif opt == "-generate-docs-for-key" then
|
|
2528
2551
|
options[:docs_for_key] = argv.shift
|
|
2529
2552
|
elsif opt == "-count-docs-for-key" then
|
|
@@ -2531,7 +2554,7 @@ def generate(message, argv, message_config_filename = nil)
|
|
|
2531
2554
|
elsif opt == "-continue" then
|
|
2532
2555
|
options[:continue] = true
|
|
2533
2556
|
elsif opt == "-max-num-docs" then
|
|
2534
|
-
options[:max_num_docs] = Integer(argv.shift)
|
|
2557
|
+
options[:max_num_docs] = Integer(argv.shift, 10)
|
|
2535
2558
|
puts "flag -max-num-docs used. Will stop after generating #{options[:max_num_docs]} documents."
|
|
2536
2559
|
elsif opt == "-validate" then
|
|
2537
2560
|
if options.has_key?(:validate_files) then
|
data/lib/regexp-to-smtlib.rb
CHANGED
|
@@ -84,8 +84,8 @@ class Regexp_to_SMTLIB
|
|
|
84
84
|
return "(re.opt #{expr})"
|
|
85
85
|
elsif multiplicator =~ /\{(\d+),(\d+)\}/ then
|
|
86
86
|
begin
|
|
87
|
-
lower = Integer($1)
|
|
88
|
-
upper = Integer($2)
|
|
87
|
+
lower = Integer($1, 10)
|
|
88
|
+
upper = Integer($2, 10)
|
|
89
89
|
rescue TypeError => e
|
|
90
90
|
raise RuntimeError.new("cannot parse regexp (#{$1} or #{$2} is no Integer)")
|
|
91
91
|
end
|
|
@@ -117,4 +117,4 @@ class Regexp_to_SMTLIB
|
|
|
117
117
|
end
|
|
118
118
|
|
|
119
119
|
|
|
120
|
-
end
|
|
120
|
+
end
|
data/lib/solver-lib.rb
CHANGED
|
@@ -337,7 +337,7 @@ class SolverFactory
|
|
|
337
337
|
unless varname =~ /-index-(\d+)-value$/
|
|
338
338
|
raise RuntimeError.new("inconsistent model: xpath #{xpath} is a list value and hence its varname should end like -index-X-value, not #{varname.inspect}.")
|
|
339
339
|
end
|
|
340
|
-
index = Integer($1)
|
|
340
|
+
index = Integer($1, 10)
|
|
341
341
|
model[xpath][:xpath_element] = info[:xpath_element]
|
|
342
342
|
if model[xpath].has_key?(:value) then
|
|
343
343
|
val = convert_solver_value(info[:type], info[:datatype], value, xpath)
|
|
@@ -354,7 +354,7 @@ class SolverFactory
|
|
|
354
354
|
if model[xpath][:type] == :field then
|
|
355
355
|
model[xpath][:type] = :list
|
|
356
356
|
end
|
|
357
|
-
model[xpath][:size] = Integer(value)
|
|
357
|
+
model[xpath][:size] = Integer(value, 10)
|
|
358
358
|
elsif varname.start_with?("struct-") && varname.end_with?("-exists") then
|
|
359
359
|
unless model[xpath][:type] == :struct then
|
|
360
360
|
raise RuntimeError.new("inconsistent model: xpath #{xpath} should be a struct, not a #{model[xpath][:type]}.")
|
|
@@ -403,9 +403,9 @@ class SolverFactory
|
|
|
403
403
|
def convert_solver_value(type, datatype, value, xpath)
|
|
404
404
|
check_type(type, value, xpath)
|
|
405
405
|
if datatype == :date then
|
|
406
|
-
return (Time.at(0).to_date + Integer(value)).to_s
|
|
406
|
+
return (Time.at(0).to_date + Integer(value, 10)).to_s
|
|
407
407
|
elsif datatype == :timestamp then
|
|
408
|
-
return Time.at(Integer(value)).to_s
|
|
408
|
+
return Time.at(Integer(value, 10)).to_s
|
|
409
409
|
else
|
|
410
410
|
return value
|
|
411
411
|
end
|
metadata
CHANGED
|
@@ -1,14 +1,14 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: mbt-gen
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 0.0.
|
|
4
|
+
version: 0.0.14
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- FM-enthusiast
|
|
8
8
|
autorequire:
|
|
9
9
|
bindir: bin
|
|
10
10
|
cert_chain: []
|
|
11
|
-
date: 2026-11-
|
|
11
|
+
date: 2026-11-05 00:00:00.000000000 Z
|
|
12
12
|
dependencies:
|
|
13
13
|
- !ruby/object:Gem::Dependency
|
|
14
14
|
name: nokogiri
|