sfp 0.3.5 → 0.3.6

Sign up to get free protection for your applications and to get access to all the features.
data/lib/sfp/Sfplib.rb CHANGED
@@ -1,12 +1,11 @@
1
1
  module Sfp
2
2
  module SfpLangHelper
3
- attr_accessor :root_dir, :home_dir
3
+ attr_accessor :root_dir, :home_dir, :constraint_next_id
4
4
  attr_reader :root, :used_classes, :arrays, :conformant
5
5
 
6
6
  def init
7
7
  @root = Hash.new
8
8
  @now = @root
9
- @id = 0
10
9
  @root['Object'] = { '_self' => 'Object', '_context' => 'class', '_parent' => @root }
11
10
  @unexpanded_classes = Array.new
12
11
  @used_classes = Array.new
@@ -15,8 +14,8 @@ module Sfp
15
14
  end
16
15
 
17
16
  def next_id
18
- nid = "c" + @id.to_s
19
- @id += 1
17
+ nid = "c#{@constraint_next_id}"
18
+ @constraint_next_id += 1
20
19
  return nid
21
20
  end
22
21
 
@@ -48,25 +47,25 @@ module Sfp
48
47
 
49
48
  raise Exception, 'File not found: ' + file if not File.exist?(filepath)
50
49
 
51
- new_home_dir = File.expand_path(File.dirname(filepath))
52
- parser = Sfp::Parser.new({:root_dir => @root_dir, :home_dir => new_home_dir})
50
+ parser = Sfp::Parser.new({ :root_dir => @root_dir,
51
+ :home_dir => File.expand_path(File.dirname(filepath)),
52
+ :constraint_next_id => @constraint_next_id })
53
53
  parser.parse(File.read(filepath))
54
-
55
- parser.root.each_pair { |key,val|
56
- if val['_context'] == 'class' or val['_context'] == 'composite'
57
- @root[key] = val
58
- elsif val['_context'] == 'state' or val['_context'] == 'constraint'
59
- if @root.has_key?(key)
60
- if @root[key]['_context'] != val['_context']
61
- @root[key] = val
62
- else
63
- val['_context'].each_pair { |k2,v2| @root[key][k2] = v2 }
64
- end
54
+ parser.root.each_pair do |key,val|
55
+ if val.is_a?(Hash)
56
+ if val['_context'] == 'state' and @root.has_key?(key) and @root[key]['_context'] == 'state'
57
+ val.each_pair { |k2,v2| @root[key][k2] = v2 if k2[0,1] != '_' }
58
+ elsif val['_context'] == 'constraint' and @root.has_key?(key) and @root[key]['_context'] == 'constraint'
59
+ val.each_pair { |k2,v2| @root[key][k2] = v2 if k2[0,1] != '_' }
65
60
  else
66
61
  @root[key] = val
62
+ val['_parent'] = @root if val['_context'] != 'state'
67
63
  end
64
+ else
65
+ @root[key] = val
68
66
  end
69
- }
67
+ end
68
+ @constraint_next_id = parser.constraint_next_id
70
69
  end
71
70
 
72
71
  def goto_parent(remove_parent=false)
@@ -76,20 +75,22 @@ module Sfp
76
75
  return n
77
76
  end
78
77
 
79
- def expand_classes
80
- @unexpanded_classes.each { |c|
81
- sclass = @root.at?(c['_extends'])
82
- c.inherits( sclass )
83
- c['_super'] = (sclass.has_key?('_super') ? sclass['_super'].clone : Array.new)
84
- c['_super'] << c['_extends']
85
- if sclass['_finals'].is_a?(Array)
86
- if c['_finals'].is_a?(Array)
87
- c['_finals'].concat(sclass['_finals'])
88
- else
89
- c['_finals'] = sclass['_finals']
90
- end
78
+ def expand_class(c)
79
+ sclass = @root.at?(c['_extends'])
80
+ c.inherits( sclass )
81
+ c['_super'] = (sclass.has_key?('_super') ? sclass['_super'].clone : Array.new)
82
+ c['_super'] << c['_extends']
83
+ if sclass['_finals'].is_a?(Array)
84
+ if c['_finals'].is_a?(Array)
85
+ c['_finals'].concat(sclass['_finals'])
86
+ else
87
+ c['_finals'] = sclass['_finals']
91
88
  end
92
- }
89
+ end
90
+ end
91
+
92
+ def expand_classes
93
+ @unexpanded_classes.each { |c| expand_class(c) }
93
94
  end
94
95
 
95
96
  def expand_object(obj)
data/lib/sfp/parser.rb CHANGED
@@ -1,136 +1,50 @@
1
- module Sfp
2
- # main class which processes configuration description in SFP language either
3
- # in file or as a string
4
- class Parser
5
- # enable this class to process SFP into FDR (SAS+)
6
- include Sfp::SasTranslator
7
-
8
- attr_accessor :root_dir, :home_dir, :conformant
9
- attr_reader :root
10
-
11
- def initialize(params={})
12
- @root_dir = (params[:root_dir].is_a?(String) ?
13
- params[:root_dir].strip :
14
- nil)
15
- @home_dir = (params[:home_dir].is_a?(String) ?
16
- params[:home_dir].strip :
17
- nil)
18
- @root = params[:root]
19
- @conformant = !!params[:conformant]
20
- end
21
-
22
- # @param string : a string in SFP language
23
- def parse(string)
24
- lexer = SfpLang::Lexer.new(string)
25
- tokens = ANTLR3::CommonTokenStream.new(lexer)
26
- parser = SfpLang::Parser.new(tokens)
27
- parser.root_dir = @root_dir
28
- parser.home_dir = @home_dir
29
- parser.sfp
30
- @root = parser.root
31
- @conformant = parser.conformant
32
- @parser_arrays = parser.arrays
33
- end
34
-
35
- def to_json(params={})
36
- return 'null' if @root.nil?
37
- return Sfp::Helper.to_pretty_json(@root) if params[:pretty]
38
- return Sfp::Helper.to_json(@root)
39
- end
40
-
41
- def self.parse_file(filepath)
42
- homedir = File.expand_path(File.dirname(filepath))
43
- parser = Sfp::Parser.new({:home_dir => homedir})
44
- parser.parse(File.read(filepath))
45
- parser.root
46
- end
47
-
48
- =begin
49
- # Parse SFP file and return its JSON representation
50
- def self.parse_file(file)
51
- return file_to_sfp(file)
52
- end
53
-
54
- def self.file_to_sfp(file)
55
- parser = Parser.new
56
- parser.parse_file(file)
57
- return parser.to_sfp
58
- end
59
-
60
- def self.to_sfp(string)
61
- parser = Parser.new
62
- parser.parse(string)
63
- return parser.to_sfp
64
- end
65
-
66
- # parse SFP file
67
- def parse_file(file)
68
- f = File.open(file, 'rb')
69
- lexer = SFP::Lexer.new(f)
70
- tokens = ANTLR3::CommonTokenStream.new(lexer)
71
- parser = SFP::Parser.new(tokens)
72
- parser.root_dir = (@root_dir == nil or @root_dir == '' ?
73
- File.expand_path('.') : @root_dir)
74
- parser.home_dir = File.dirname(f.path)
75
- parser.sfp
76
- @conformant = parser.conformant
77
- @root = parser.root
78
- @parser_arrays = parser.arrays
79
- end
80
-
81
- # parse SFP in a string
82
- def parse(text)
83
- lexer = SFP::Lexer.new(text)
84
- tokens = ANTLR3::CommonTokenStream.new(lexer)
85
- parser = SFP::Parser.new(tokens)
86
- parser.root_dir = (@root_dir == nil or @root_dir == '' ?
87
- File.expand_path(File.dirname('.')) : @root_dir)
88
- parser.home_dir = parser.root_dir
89
- parser.sfp
90
- @root = parser.root
91
- @parser_arrays = parser.arrays
92
- end
93
-
94
- # dump the parsed specification into standard output
95
- def dump(root=nil)
96
- return if root == nil
97
- root = Nuri::Sfp.deep_clone(@root)
98
- root.accept(ParentEliminator.new)
99
- puts JSON.pretty_generate(root)
100
- end
101
-
102
- def self.dump(root)
103
- return if root == nil
104
- root = Nuri::Sfp.deep_clone(root)
105
- root.accept(ParentEliminator.new)
106
- puts JSON.pretty_generate(root)
107
- end
108
-
109
- def to_sfp
110
- @root
111
- end
112
-
113
- def to_json
114
- root = self.to_sfp
115
- return if root == nil
116
- root = Nuri::Sfp.deep_clone(root)
117
- return Nuri::Sfp.to_json(root)
118
- end
119
- =end
1
+ # main class which processes configuration description in SFP language either
2
+ # in file or as a string
3
+ class Sfp::Parser
4
+ # enable this class to process SFP into FDR (SAS+)
5
+ include Sfp::SasTranslator
6
+
7
+ attr_accessor :root_dir, :home_dir, :conformant
8
+ attr_reader :root, :constraint_next_id
9
+
10
+ def initialize(params={})
11
+ @root_dir = (params[:root_dir].is_a?(String) ?
12
+ params[:root_dir].strip :
13
+ nil)
14
+ @home_dir = (params[:home_dir].is_a?(String) ?
15
+ params[:home_dir].strip :
16
+ nil)
17
+ @root = params[:root]
18
+ @conformant = !!params[:conformant]
19
+ @constraint_next_id = (params[:constraint_next_id] ? params[:constraint_next_id] : 0)
120
20
  end
121
21
 
122
- =begin
123
- def self.to_json(sfp)
124
- root = Sfp::Helper.deep_clone(sfp)
125
- root.accept(Nuri::Sfp::ParentEliminator.new)
126
- return JSON.generate(root)
22
+ # @param string : a string in SFP language
23
+ def parse(string, options={})
24
+ lexer = SfpLang::Lexer.new(string)
25
+ tokens = ANTLR3::CommonTokenStream.new(lexer)
26
+ parser = SfpLang::Parser.new(tokens)
27
+ parser.root_dir = @root_dir
28
+ parser.home_dir = @home_dir
29
+ parser.constraint_next_id = @constraint_next_id
30
+ parser.sfp
31
+ @constraint_next_id = parser.constraint_next_id
32
+ @root = parser.root
33
+ @conformant = parser.conformant
34
+ @parser_arrays = parser.arrays
127
35
  end
128
36
 
129
- def self.to_pretty_json(sfp)
130
- root = Nuri::Sfp.deep_clone(sfp)
131
- root.accept(Nuri::Sfp::ParentEliminator.new)
132
- return JSON.pretty_generate(root)
37
+ def to_json(params={})
38
+ return 'null' if @root.nil?
39
+ return Sfp::Helper.to_pretty_json(@root) if params[:pretty]
40
+ return Sfp::Helper.to_json(@root)
133
41
  end
134
- =end
135
42
 
43
+ def self.parse_file(filepath, options={})
44
+ #homedir = File.expand_path(File.dirname(filepath))
45
+ options[:home_dir] = File.expand_path(File.dirname(filepath)) if !options[:home_dir]
46
+ parser = Sfp::Parser.new(options) #{:home_dir => homedir})
47
+ parser.parse(File.read(filepath))
48
+ parser.root
49
+ end
136
50
  end
@@ -162,15 +162,11 @@ module Sfp
162
162
  end
163
163
 
164
164
  ### process all procedures
165
- @variables.each_value { |var|
165
+ @variables.each_value do |var|
166
166
  if var.is_final
167
- var.init.each { |k,v|
168
- if v.is_a?(Hash) and v.isprocedure
169
- process_procedure(v, var.init)
170
- end
171
- }
167
+ var.init.each { |k,v| process_procedure(v, var.init) if v.is_a?(Hash) and v.isprocedure }
172
168
  end
173
- }
169
+ end
174
170
  self.reset_operators_name
175
171
 
176
172
  ### process sometime modalities ###
@@ -304,7 +300,7 @@ module Sfp
304
300
  postprocess_simple_global_constraint_to_operator(operator).each { |op|
305
301
  @operators[op.name] = op
306
302
  }
307
- end
303
+ end if @operators.is_a?(Hash)
308
304
  end
309
305
 
310
306
  def postprocess_simple_global_constraint_to_operator(operator)
@@ -701,12 +697,10 @@ module Sfp
701
697
  return map
702
698
  end
703
699
 
704
- def and_equals_constraint_to_map(constraint)
705
- map = Hash.new
706
- constraint.each { |k,v|
707
- next if k[0,1] == '_'
708
- map[k] = v['_value'] if v['_type'] == 'equals'
709
- }
700
+ def and_equals_constraint_to_map(c)
701
+ return { c['_self'] => c['_value'] } if c['_type'] == 'equals'
702
+ map = {}
703
+ c.each { |k,v| map[k] = v['_value'] if k[0,1] != '_' and v['_type'] == 'equals' }
710
704
  return map
711
705
  end
712
706
 
@@ -790,18 +784,7 @@ module Sfp
790
784
 
791
785
  operators = ground_procedure_parameters(procedure)
792
786
  if operators != nil
793
- invalid_operators = []
794
- operators.each do |op|
795
- #begin
796
- process_operator(op)
797
- #rescue UndefinedValueException
798
- # invalid_operators << op
799
- # puts "TODO -- invalid operator: " + op['_self'].to_s
800
- #end
801
- end
802
- #operators.delete_if { |op| not invalid_operators.index(op).nil? }
803
- else
804
- #puts 'proc: ' + procedure.ref + ' cannot be grounded'
787
+ operators.each { |op| process_operator(op) }
805
788
  end
806
789
  # remove the procedure because we don't need it anymore
807
790
  object.delete(procedure['_self'])
@@ -819,7 +802,14 @@ module Sfp
819
802
  return nil
820
803
  end
821
804
  params[k] = Array.new
822
- type = (v.isnull ? v['_isa'] : (v.isset ? "(#{v['_isa']})" : nil))
805
+ type = case v['_context']
806
+ when 'null', 'any_value'
807
+ v['_isa']
808
+ when 'set'
809
+ "(#{v['_isa']})"
810
+ else
811
+ nil
812
+ end
823
813
  next if type == nil
824
814
  raise TypeNotFoundException, type if not @types.has_key?(type)
825
815
  @types[ type ].each { |val| params[k] << val if not (val.is_a?(Hash) and val.isnull) }
@@ -1664,9 +1654,12 @@ module Sfp
1664
1654
 
1665
1655
  def visit(name, value, obj)
1666
1656
  return if name[0,1] == '_' and name != '_value' and name != '_template'
1657
+ # substituting left side
1667
1658
  if name[0,1] != '_'
1668
1659
  modified = false
1669
1660
  map.each { |k,v|
1661
+ #puts k + ',' + name if v.is_a?(Sfp::Undefined) or v.is_a?(Sfp::Unknown)
1662
+ next if v.is_a?(Sfp::Undefined) or v.is_a?(Sfp::Unknown)
1670
1663
  if name == k
1671
1664
  obj[v] = value
1672
1665
  obj.delete(name)
@@ -1675,6 +1668,7 @@ module Sfp
1675
1668
  modified = true
1676
1669
  break
1677
1670
  elsif name.length > k.length and name[k.length,1] == '.' and name[0, k.length] == k
1671
+ #next if v.is_a?(Sfp::Undefined) or v.is_a?(Sfp::Unknown)
1678
1672
  grounded = v + name[k.length, (name.length-k.length)]
1679
1673
  obj[grounded] = value
1680
1674
  obj.delete(name)
@@ -1705,12 +1699,15 @@ module Sfp
1705
1699
  #puts "==>> " + obj.ref.push(name)
1706
1700
  end
1707
1701
  # ------ END of HACK! ----
1702
+
1703
+ # substituting right side
1708
1704
  if value.is_a?(String) and value.isref
1709
1705
  map.each { |k,v|
1710
1706
  if value == k
1711
1707
  obj[name] = v
1712
1708
  break
1713
- elsif value.length > k.length and value[k.length,1] == '.' and value[0,k.length] == k
1709
+ elsif value.length > k.length and value[k.length,1] == '.' and value[0,k.length] == k and
1710
+ not(v.is_a?(Sfp::Undefined) or v.is_a?(Sfp::Unknown))
1714
1711
  obj[name] = v + value[k.length, (value.length-k.length)]
1715
1712
  break
1716
1713
  end
data/sfp.gemspec CHANGED
@@ -1,7 +1,7 @@
1
1
  Gem::Specification.new do |s|
2
2
  s.name = 'sfp'
3
- s.version = '0.3.5'
4
- s.date = '2013-07-15'
3
+ s.version = '0.3.6'
4
+ s.date = '2013-08-05'
5
5
  s.summary = 'SFP Parser'
6
6
  s.description = 'A Ruby API and script for SFP language parser'
7
7
  s.authors = ['Herry']
@@ -17,5 +17,5 @@ Gem::Specification.new do |s|
17
17
  s.rubyforge_project = 'sfp'
18
18
 
19
19
  s.add_dependency 'json', '~> 1.7.5'
20
- s.add_dependency 'antlr3', '~> 1.8.12'
20
+ s.add_dependency 'antlr3', '~> 1.9.0'
21
21
  end
data/src/SfpLang.g CHANGED
@@ -38,11 +38,17 @@ TODO:
38
38
 
39
39
  sfp
40
40
  : { self.init }
41
- NL* include* header*
42
- { self.expand_classes }
43
- (object_def NL* | state | constraint | goal_constraint | composite)*
41
+ NL*
42
+ //{ self.expand_classes }
43
+ ( (object_def | state | constraints) NL* | include | class_def | procedure )*
44
+ // | goal_constraint | composite)*
44
45
  ;
45
46
 
47
+ constraints
48
+ : goal_constraint
49
+ | global_constraint
50
+ | sometime_constraint
51
+ ;
46
52
 
47
53
  /*mmutation
48
54
  : reference equals_op value NL+
@@ -72,12 +78,12 @@ include_file
72
78
  ;
73
79
 
74
80
  header
75
- : class_definition
81
+ : class_def
76
82
  | procedure
77
83
  ;
78
84
 
79
85
  state
80
- : ID 'state'
86
+ : ID 'state' NL*
81
87
  {
82
88
  @now[$ID.text] = { '_self' => $ID.text,
83
89
  '_context' => 'state',
@@ -87,7 +93,7 @@ state
87
93
  }
88
94
  '{' NL*
89
95
  attribute*
90
- '}' NL*
96
+ '}'
91
97
  { self.goto_parent(true) }
92
98
  ;
93
99
 
@@ -104,7 +110,7 @@ composite
104
110
  { self.goto_parent(true) }
105
111
  ;
106
112
 
107
- class_definition
113
+ class_def
108
114
  : ('class'|'schema') ID
109
115
  {
110
116
  @now[$ID.text] = { '_self' => $ID.text,
@@ -124,6 +130,7 @@ class_definition
124
130
  @now['_extends'] = '$.Object'
125
131
  @now['_super'] = ['$.Object']
126
132
  end
133
+ expand_class(@now)
127
134
  self.goto_parent()
128
135
  }
129
136
  ;
@@ -263,7 +270,7 @@ object_def
263
270
  ;
264
271
 
265
272
  object_body
266
- : '{' NL* ( object_attribute | state_dependency | operator )* '}'
273
+ : '{' NL* ( object_attribute | procedure )* '}'
267
274
  ;
268
275
 
269
276
  object_attribute
@@ -290,27 +297,6 @@ dep_effect
290
297
  )
291
298
  ;
292
299
 
293
- operator
294
- : 'operator' ID '{' NL*
295
- {
296
- @now[$ID.text] = { '_self' => $ID.text,
297
- '_context' => 'operator',
298
- '_parent' => @now,
299
- '_cost' => 1,
300
- '_condition' => { '_context' => 'constraint' },
301
- '_effect' => { '_context' => 'effect' }
302
- }
303
- @now = @now[$ID.text]
304
- }
305
- ( 'cost' equals_op NUMBER NL+
306
- { @now['_cost'] = $NUMBER.text.to_i }
307
- )?
308
- /*op_param**/
309
- op_conditions? op_effects
310
- '}' NL+
311
- { self.goto_parent() }
312
- ;
313
-
314
300
  op_param
315
301
  : ID equals_op reference NL+
316
302
  { @now[$ID.text] = $reference.val }
@@ -369,7 +355,13 @@ parameters
369
355
  ;
370
356
 
371
357
  parameter
372
- : ID reference_type
358
+ : ID ':' path
359
+ {
360
+ @now[$ID.text] = { '_context' => 'any_value',
361
+ '_isa' => self.to_ref($path.text)
362
+ }
363
+ }
364
+ | ID reference_type
373
365
  { @now[$ID.text] = $reference_type.val }
374
366
  | ID 'areall' path
375
367
  {
@@ -424,10 +416,31 @@ goal_constraint
424
416
  }
425
417
  @now = @now['goal']
426
418
  }
427
- '{' NL* goal_body* '}' NL+
419
+ '{' NL* goal_body* '}'
420
+ { self.goto_parent() }
421
+ ;
422
+
423
+ global_constraint
424
+ : ('global'|'always') 'constraint'? NL*
425
+ {
426
+ @now['global'] = self.create_constraint('global', 'and') if !@now.has_key?('global')
427
+ @now = @now['global']
428
+ }
429
+ '{' NL* constraint_body '}'
428
430
  { self.goto_parent() }
429
431
  ;
430
432
 
433
+ sometime_constraint
434
+ : 'sometime' 'constraint'? NL*
435
+ {
436
+ @now['sometime'] = self.create_constraint('sometime', 'or') if !@now.has_key?('sometime')
437
+ @now = @now['sometime']
438
+ }
439
+ '{' NL* constraint_body '}'
440
+ { self.goto_parent() }
441
+ ;
442
+
443
+
431
444
  goal_body
432
445
  : (
433
446
  ( constraint_statement
@@ -439,11 +452,11 @@ goal_body
439
452
  | constraint_class_quantification
440
453
  )
441
454
  NL+)
442
- | 'always' NL*
455
+ | ('always'|'global') NL*
443
456
  {
444
- @now['always'] = self.create_constraint('always', 'and') if
445
- not @now.has_key?('always')
446
- @now = @now['always']
457
+ @now['global'] = self.create_constraint('global', 'and') if
458
+ not @now.has_key?('global')
459
+ @now = @now['global']
447
460
  }
448
461
  '{' NL* constraint_body '}' NL+
449
462
  { self.goto_parent() }
@@ -520,12 +533,12 @@ nested_constraint
520
533
  ;
521
534
 
522
535
  constraint
523
- : ID 'constraint'
536
+ : 'constraint' ID
524
537
  {
525
538
  @now[$ID.text] = self.create_constraint($ID.text, 'and')
526
539
  @now = @now[$ID.text]
527
540
  }
528
- '{' NL* constraint_body '}' NL+
541
+ '{' NL* constraint_body '}'
529
542
  { self.goto_parent() }
530
543
  ;
531
544
 
@@ -1015,7 +1028,7 @@ BOOLEAN
1015
1028
  | 'no'
1016
1029
  ;
1017
1030
 
1018
- ID : ('a'..'z'|'A'..'Z') ('a'..'z'|'A'..'Z'|'0'..'9'|'_'|'-')*
1031
+ ID : ('a'..'z'|'A'..'Z')('a'..'z'|'A'..'Z'|'0'..'9'|'_')*
1019
1032
  ;
1020
1033
 
1021
1034
  NUMBER
@@ -1039,7 +1052,7 @@ MULTILINE_STRING
1039
1052
  : 'r"' ( options {greedy=false;} : .)* '"'
1040
1053
  ;
1041
1054
 
1042
- NL : '\r'? '\n'
1055
+ NL : ('\r'? '\n'|';')
1043
1056
  ;
1044
1057
 
1045
1058
  WS : ( ' ' | '\t' ) {$channel=HIDDEN;}
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: sfp
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.3.5
4
+ version: 0.3.6
5
5
  prerelease:
6
6
  platform: ruby
7
7
  authors:
@@ -9,11 +9,11 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2013-07-15 00:00:00.000000000 Z
12
+ date: 2013-08-05 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: json
16
- requirement: &20938540 !ruby/object:Gem::Requirement
16
+ requirement: !ruby/object:Gem::Requirement
17
17
  none: false
18
18
  requirements:
19
19
  - - ~>
@@ -21,18 +21,28 @@ dependencies:
21
21
  version: 1.7.5
22
22
  type: :runtime
23
23
  prerelease: false
24
- version_requirements: *20938540
24
+ version_requirements: !ruby/object:Gem::Requirement
25
+ none: false
26
+ requirements:
27
+ - - ~>
28
+ - !ruby/object:Gem::Version
29
+ version: 1.7.5
25
30
  - !ruby/object:Gem::Dependency
26
31
  name: antlr3
27
- requirement: &20938040 !ruby/object:Gem::Requirement
32
+ requirement: !ruby/object:Gem::Requirement
28
33
  none: false
29
34
  requirements:
30
35
  - - ~>
31
36
  - !ruby/object:Gem::Version
32
- version: 1.8.12
37
+ version: 1.9.0
33
38
  type: :runtime
34
39
  prerelease: false
35
- version_requirements: *20938040
40
+ version_requirements: !ruby/object:Gem::Requirement
41
+ none: false
42
+ requirements:
43
+ - - ~>
44
+ - !ruby/object:Gem::Version
45
+ version: 1.9.0
36
46
  description: A Ruby API and script for SFP language parser
37
47
  email: herry13@gmail.com
38
48
  executables:
@@ -79,7 +89,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
79
89
  version: '0'
80
90
  requirements: []
81
91
  rubyforge_project: sfp
82
- rubygems_version: 1.8.11
92
+ rubygems_version: 1.8.23
83
93
  signing_key:
84
94
  specification_version: 3
85
95
  summary: SFP Parser