HDLRuby 2.5.1 → 2.6.8

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 (46) hide show
  1. checksums.yaml +4 -4
  2. data/lib/HDLRuby/hdr_samples/adder.rb +1 -1
  3. data/lib/HDLRuby/hdr_samples/adder_bench.rb +1 -1
  4. data/lib/HDLRuby/hdr_samples/adder_gen.rb +1 -1
  5. data/lib/HDLRuby/hdr_samples/comparison_bench.rb +40 -0
  6. data/lib/HDLRuby/hdr_samples/constant_in_function.rb +27 -0
  7. data/lib/HDLRuby/hdr_samples/dff_unit.rb +3 -3
  8. data/lib/HDLRuby/hdr_samples/huge_rom.rb +25 -0
  9. data/lib/HDLRuby/hdr_samples/logic_bench.rb +21 -0
  10. data/lib/HDLRuby/hdr_samples/mei8_bench.rb +1 -1
  11. data/lib/HDLRuby/hdr_samples/multi_timed_bench.rb +54 -0
  12. data/lib/HDLRuby/hdr_samples/music.rb +79 -0
  13. data/lib/HDLRuby/hdr_samples/named_sub.rb +42 -0
  14. data/lib/HDLRuby/hdr_samples/rom.rb +16 -0
  15. data/lib/HDLRuby/hdr_samples/type_minmax_bench.rb +37 -0
  16. data/lib/HDLRuby/hdr_samples/with_function_generator.rb +25 -0
  17. data/lib/HDLRuby/hdr_samples/with_to_array.rb +29 -0
  18. data/lib/HDLRuby/hdrcc.rb +69 -9
  19. data/lib/HDLRuby/hruby_decorator.rb +3 -1
  20. data/lib/HDLRuby/hruby_high.rb +220 -29
  21. data/lib/HDLRuby/hruby_low.rb +433 -45
  22. data/lib/HDLRuby/hruby_low2c.rb +122 -168
  23. data/lib/HDLRuby/hruby_low2hdr.rb +738 -0
  24. data/lib/HDLRuby/hruby_low2high.rb +331 -549
  25. data/lib/HDLRuby/hruby_low2vhd.rb +39 -2
  26. data/lib/HDLRuby/hruby_low_bool2select.rb +29 -0
  27. data/lib/HDLRuby/hruby_low_casts_without_expression.rb +27 -0
  28. data/lib/HDLRuby/hruby_low_fix_types.rb +25 -0
  29. data/lib/HDLRuby/hruby_low_mutable.rb +70 -0
  30. data/lib/HDLRuby/hruby_low_resolve.rb +28 -0
  31. data/lib/HDLRuby/hruby_low_without_connection.rb +6 -3
  32. data/lib/HDLRuby/hruby_low_without_namespace.rb +7 -4
  33. data/lib/HDLRuby/hruby_low_without_select.rb +13 -0
  34. data/lib/HDLRuby/hruby_tools.rb +11 -1
  35. data/lib/HDLRuby/hruby_verilog.rb +1572 -1723
  36. data/lib/HDLRuby/sim/hruby_sim.h +45 -5
  37. data/lib/HDLRuby/sim/hruby_sim_calc.c +192 -20
  38. data/lib/HDLRuby/sim/hruby_sim_core.c +24 -9
  39. data/lib/HDLRuby/sim/hruby_sim_vcd.c +7 -3
  40. data/lib/HDLRuby/sim/hruby_sim_vizualize.c +22 -6
  41. data/lib/HDLRuby/std/fixpoint.rb +9 -0
  42. data/lib/HDLRuby/std/function_generator.rb +139 -0
  43. data/lib/HDLRuby/std/hruby_unit.rb +75 -0
  44. data/lib/HDLRuby/version.rb +1 -1
  45. metadata +18 -6
  46. data/lib/HDLRuby/hruby_unit.rb +0 -43
@@ -50,6 +50,15 @@ module HDLRuby::Low
50
50
  @@alliance = mode ? true : false
51
51
  end
52
52
 
53
+
54
+ ## Converts string +str+ to a VHDL-compatible string.
55
+ def self.vhdl_string(str)
56
+ str = str.gsub(/\n/,"\\n")
57
+ str.gsub!(/\t/,"\\t")
58
+ return str
59
+ end
60
+
61
+
53
62
  ## Generates the pakage requirement for an entity.
54
63
  # +spaces+ are the spaces to put before each line.
55
64
  def self.packages(spaces)
@@ -523,7 +532,8 @@ module HDLRuby::Low
523
532
  if inner.value.is_a?(Concat) then
524
533
  # Concat are to be given the expected type of the
525
534
  # elements for casting them equally.
526
- res << " := " << inner.value.to_vhdl(inner.type.base,level)
535
+ # res << " := " << inner.value.to_vhdl(inner.type.base,level)
536
+ res << " := " << inner.value.to_vhdl(level,inner.type.base)
527
537
  else
528
538
  res << " := " << inner.value.to_vhdl(level)
529
539
  end
@@ -901,6 +911,20 @@ module HDLRuby::Low
901
911
  Low2VHDL.to_type(self.left.type,self.right) + ";\n"
902
912
  end
903
913
  end
914
+
915
+ ## Extends the Print class with generation of HDLRuby::High text.
916
+ class Print
917
+
918
+ # Generates the text of the equivalent HDLRuby::High code.
919
+ # +vars+ is the list of the variables and
920
+ # +level+ is the hierachical level of the object.
921
+ def to_vhdl(vars,level = 0)
922
+ # Generate a report statement.
923
+ return " " * (level*3) + "report " + self.each_arg.map do |arg|
924
+ arg.to_vhdl
925
+ end.join(" & ") + ";\n"
926
+ end
927
+ end
904
928
 
905
929
  ## Extends the If class with generation of HDLRuby::High text.
906
930
  class If
@@ -1347,7 +1371,8 @@ module HDLRuby::Low
1347
1371
  # Generates the text of the equivalent HDLRuby::High code.
1348
1372
  # +type+ is the expected type of the content.
1349
1373
  # +level+ is the hierachical level of the object.
1350
- def to_vhdl(type,level = 0)
1374
+ # def to_vhdl(type,level = 0)
1375
+ def to_vhdl(level = 0, type = self.type)
1351
1376
  raise "Invalid class for a type: #{type.class}" unless type.is_a?(Type)
1352
1377
  # The resulting string.
1353
1378
  res = ""
@@ -1487,6 +1512,18 @@ module HDLRuby::Low
1487
1512
  # Nothing to generate.
1488
1513
  end
1489
1514
 
1515
+ ## Extends the StringE class with generation of HDLRuby::High text.
1516
+ class StringE
1517
+
1518
+ # Generates the text of the equivalent HDLRuby::High code.
1519
+ # +level+ is the hierachical level of the object.
1520
+ def to_vhdl(level = 0, std_logic = false)
1521
+ # Generate a report statement.
1522
+ return "\"#{Low2VHDL.vhdl_string(self.content)}\"" +
1523
+ self.each_arg.map { |arg| arg.to_vhdl }.join(" & ")
1524
+ end
1525
+ end
1526
+
1490
1527
  ## Extends the Numeric class with generation of HDLRuby::High text.
1491
1528
  class ::Numeric
1492
1529
 
@@ -61,6 +61,20 @@ module HDLRuby::Low
61
61
  return self
62
62
  end
63
63
  end
64
+
65
+
66
+ ## Extends the Print class with functionality for converting booleans
67
+ # in assignments to select operators.
68
+ class Print
69
+
70
+ # Converts booleans in assignments to select operators.
71
+ def boolean_in_assign2select!
72
+ # Apply on the arguments.
73
+ self.map_args! { |arg| arg.boolean_in_assign2select }
74
+ return self
75
+ end
76
+ end
77
+
64
78
 
65
79
  ## Extends the If class with functionality for converting booleans
66
80
  # in assignments to select operators.
@@ -315,4 +329,19 @@ module HDLRuby::Low
315
329
  return self.clone
316
330
  end
317
331
  end
332
+
333
+
334
+ ## Extends the StringE class with functionality for converting booleans
335
+ # in assignments to select operators.
336
+ class StringE
337
+
338
+ # Converts booleans in assignments to select operators.
339
+ def boolean_in_assign2select
340
+ # Apply on the content.
341
+ # Apply on the arguments.
342
+ return StringE.new(self.content.clone,*self.each_arg.map do |arg|
343
+ arg.boolean_in_assign2select
344
+ end)
345
+ end
346
+ end
318
347
  end
@@ -62,6 +62,20 @@ module HDLRuby::Low
62
62
  return self
63
63
  end
64
64
  end
65
+
66
+
67
+ ## Extends the Print class with functionality for extracting
68
+ # expressions from cast.
69
+ class Print
70
+
71
+ # Extracts the expressions from the casts.
72
+ def casts_without_expression!
73
+ # Apply on the arguments.
74
+ self.map_args!(&:casts_without_expression)
75
+ return self
76
+ end
77
+ end
78
+
65
79
 
66
80
  ## Extends the If class with functionality for extracting
67
81
  # expressions from cast.
@@ -323,4 +337,17 @@ module HDLRuby::Low
323
337
  return self.clone
324
338
  end
325
339
  end
340
+
341
+
342
+ ## Extends the StringE class with functionality for extracting
343
+ # expressions from cast.
344
+ class StringE
345
+
346
+ # Extracts the expressions from the casts.
347
+ def casts_without_expression
348
+ return StringE.new(self.content,
349
+ *self.each_arg.map(&:cast_without_expression))
350
+ return self
351
+ end
352
+ end
326
353
  end
@@ -89,6 +89,20 @@ module HDLRuby::Low
89
89
 
90
90
  end
91
91
 
92
+
93
+ ## Extends the Print class with fixing of types and constants.
94
+ class Print
95
+ # Explicit the types conversions in the statement.
96
+ def explicit_types!
97
+ # Recurse on the arguments.
98
+ self.map_args!(&:explicit_types)
99
+ return self
100
+ end
101
+
102
+ end
103
+
104
+
105
+
92
106
 
93
107
  ## Extends the If class with fixing of types and constants.
94
108
  class If
@@ -438,4 +452,15 @@ module HDLRuby::Low
438
452
  end
439
453
 
440
454
 
455
+ ## Extends the stringE class with fixing of types and constants.
456
+ class StringE
457
+ # Explicit the types conversions in the concat where
458
+ # +type+ is the expected type of the condition if any.
459
+ def explicit_types(type = nil)
460
+ return StringE.new(self.content,
461
+ *self.each_arg.map(&:explicit_types))
462
+ end
463
+ end
464
+
465
+
441
466
  end
@@ -626,6 +626,64 @@ module HDLRuby::Low
626
626
  end
627
627
 
628
628
 
629
+ ##
630
+ # Decribes a print statement.
631
+ class Print
632
+
633
+ # Maps on the arguments.
634
+ def map_args!(&ruby_block)
635
+ @args.map! do |arg|
636
+ arg = ruby_block.call(arg)
637
+ arg.parent = self unless arg.parent
638
+ arg
639
+ end
640
+ end
641
+
642
+ alias_method :map_nodes!, :map_args!
643
+
644
+ # Delete an arg.
645
+ def delete_arg!(arg)
646
+ if @args.include?(arg) then
647
+ # The arg is present, delete it.
648
+ @args.delete(arg)
649
+ # And remove its parent.
650
+ arg.parent = nil
651
+ end
652
+ arg
653
+ end
654
+
655
+ # Replaces sub arguments using +node2rep+ table indicating the
656
+ # node to replace and the corresponding replacement.
657
+ # Returns the actually replaced nodes and their corresponding
658
+ # replacement.
659
+ #
660
+ # NOTE: the replacement is duplicated.
661
+ def replace_args!(node2rep)
662
+ # First recurse on the children.
663
+ res = {}
664
+ self.each_node do |node|
665
+ res.merge!(node.replace_args!(node2rep))
666
+ end
667
+ # Is there a replacement of on a sub node?
668
+ self.map_nodes! do |sub|
669
+ rep = node2rep[sub]
670
+ if rep then
671
+ # Yes, do it.
672
+ rep = rep.clone
673
+ node = sub
674
+ # node.set_parent!(nil)
675
+ # And register the replacement.
676
+ res[node] = rep
677
+ rep
678
+ else
679
+ sub
680
+ end
681
+ end
682
+ return res
683
+ end
684
+ end
685
+
686
+
629
687
  ##
630
688
  # Describes an if statement.
631
689
  class If
@@ -1093,6 +1151,18 @@ module HDLRuby::Low
1093
1151
  stmnt.parent = self
1094
1152
  end
1095
1153
 
1154
+ # Replaces statement +org+ by statement +stmnt+.
1155
+ #
1156
+ # NOTE: does nothing if +org+ is not present.
1157
+ def replace_statement!(org,stmnt)
1158
+ # Checks the statement.
1159
+ unless stmnt.is_a?(Statement)
1160
+ raise AnyError, "Invalid type for a statement: #{stmnt.class}"
1161
+ end
1162
+ idx = @statements.index(org)
1163
+ @statements[idx] = stmnt if idx
1164
+ end
1165
+
1096
1166
  # Maps on the statements.
1097
1167
  def map_statements!(&ruby_block)
1098
1168
  @statements.map! do |stmnt|
@@ -84,6 +84,20 @@ module HDLRuby::Low
84
84
  end
85
85
 
86
86
 
87
+ ##
88
+ # Extends RefIndex with the capability of finding the object it
89
+ # refered to.
90
+ class Ref
91
+ ## Resolves the name of the reference (if any) and return the
92
+ # corresponding object.
93
+ # NOTE: return nil if could not resolve.
94
+ def resolve
95
+ # By default cannot resolve.
96
+ return nil
97
+ end
98
+ end
99
+
100
+
87
101
  ##
88
102
  # Extends RefIndex with the capability of finding the object it
89
103
  # refered to.
@@ -93,6 +107,13 @@ module HDLRuby::Low
93
107
  def from_systemI?
94
108
  return self.ref.from_systemI?
95
109
  end
110
+
111
+ ## Resolves the name of the reference (if any) and return the
112
+ # corresponding object.
113
+ # NOTE: return nil if could not resolve.
114
+ def resolve
115
+ return self.ref.resolve
116
+ end
96
117
  end
97
118
 
98
119
 
@@ -105,6 +126,13 @@ module HDLRuby::Low
105
126
  def from_systemI?
106
127
  return self.ref.from_systemI?
107
128
  end
129
+
130
+ ## Resolves the name of the reference (if any) and return the
131
+ # corresponding object.
132
+ # NOTE: return nil if could not resolve.
133
+ def resolve
134
+ return self.ref.resolve
135
+ end
108
136
  end
109
137
 
110
138
 
@@ -42,7 +42,8 @@ module HDLRuby::Low
42
42
  right_r = right.resolve if right.respond_to?(:resolve)
43
43
  # puts "right_r=#{right_r.name}" if right_r
44
44
  # puts "right_r.parent=#{right_r.parent.name}" if right_r && right_r.parent
45
- if right.is_a?(Value) then
45
+ # if right.is_a?(Value) then
46
+ if right.immutable? then
46
47
  # Right is value, the new transmit is to add
47
48
  # to the timed block.
48
49
  timed_blk.add_statement(
@@ -108,13 +109,15 @@ module HDLRuby::Low
108
109
  # end
109
110
  # Both or neither input/output, make a behavior
110
111
  # for each.
111
- if (left.is_a?(Ref)) then
112
+ if (left.is_a?(Ref) &&
113
+ !(left_r && left_r.immutable?)) then
112
114
  blk = Block.new(:par)
113
115
  blk.add_statement(
114
116
  Transmit.new(left.clone,right.clone))
115
117
  scope.add_behavior(Behavior.new(blk))
116
118
  end
117
- if (right.is_a?(Ref)) then
119
+ if (right.is_a?(Ref) &&
120
+ !(right_r && right_r.immutable?)) then
118
121
  blk = Block.new(:par)
119
122
  blk.add_statement(
120
123
  Transmit.new(right.clone,left.clone))
@@ -617,10 +617,13 @@ module HDLRuby::Low
617
617
  #
618
618
  # NOTE: do not recurse into the sub scopes or behaviors!
619
619
  def extract_declares!
620
- # Recurse on the whens.
621
- return self.each_when.map(&:extract_declares!)
622
- # Recurse on the default if any.
623
- self.default.extract_declares! if self.default
620
+ # # Recurse on the whens.
621
+ # return self.each_when.map(&:extract_declares!)
622
+ # # Recurse on the default if any.
623
+ # self.default.extract_declares! if self.default
624
+ res = self.each_when.map(&:extract_declares!)
625
+ res += self.default.extract_declares! if self.default
626
+ return res
624
627
  end
625
628
 
626
629
  # Replaces recursively +former+ name by +nname+ until it is redeclared.
@@ -162,6 +162,19 @@ module HDLRuby::Low
162
162
  return selects
163
163
  end
164
164
  end
165
+
166
+ ## Extends the String class with functionality for converting select
167
+ # expressions to case statements.
168
+ class Print
169
+ # Extract the Select expressions.
170
+ def extract_selects!
171
+ selects = []
172
+ self.map_args! do |arg|
173
+ arg.extract_selects_to!(selects)
174
+ end
175
+ return selects
176
+ end
177
+ end
165
178
 
166
179
  ## Extends the If class with functionality for converting select
167
180
  # expressions to case statements.
@@ -1,4 +1,3 @@
1
-
2
1
  module HDLRuby
3
2
 
4
3
  ##
@@ -40,4 +39,15 @@ module HDLRuby
40
39
  end
41
40
  end
42
41
 
42
+
43
+ # Module for adding prefixes to names.
44
+ module HDLRuby::Prefix
45
+
46
+ # Get the prefix
47
+ def prefix
48
+ return self.name + "#"
49
+ end
50
+
51
+ end
52
+
43
53
  end
@@ -17,116 +17,120 @@ module HDLRuby::Low
17
17
  # The list of signals that are actually verilog regs.
18
18
  VERILOG_REGS = []
19
19
 
20
+ ## Converts string +str+ to a Verilog-compatible string.
21
+ def self.v_string(str)
22
+ str = str.gsub(/\n/,"\\n")
23
+ str.gsub!(/\t/,"\\t")
24
+ return str
25
+ end
26
+
27
+
28
+ # Sample of very handy for programming.
29
+ # puts "class=#{self.yes.class}" # Confirm class of self.yes.
30
+ # puts "methods=#{self.right.methods}" # Confirm method of self.right.
31
+ # puts "outputs=#{outputs}" # Confirm outputs
32
+
33
+ # each. do |*arg| # I forgot this.
34
+ # puts args
35
+ # end
36
+
37
+ # Global variable used for indentation and structure (temporary).
38
+ $vector_reg = "" # For storing signal type at structure declaration. (temporary)
39
+ $vector_cnt = 0 # For allocating numbers at structure declaration. (temporary)
20
40
 
21
- # Sample of very handy for programming.
22
- # puts "class=#{self.yes.class}" # Confirm class of self.yes.
23
- # puts "methods=#{self.right.methods}" # Confirm method of self.right.
24
- # puts "outputs=#{outputs}" # Confirm outputs
25
-
26
- # each. do |*arg| # I forgot this.
27
- # puts args
28
- # end
29
-
30
- # Global variable used for indentation and structure (temporary).
31
- # $space_count = 0 # Count used for increasing indent by if statement. (temporary)
32
- $vector_reg = "" # For storing signal type at structure declaration. (temporary)
33
- $vector_cnt = 0 # For allocating numbers at structure declaration. (temporary)
34
-
35
- # class Fixnum
36
- # def to_verilog
37
- # to_s
38
- # end
39
- # end
40
- class ::Integer
41
- def to_verilog
42
- to_s
41
+ class ::Integer
42
+ def to_verilog
43
+ to_s
44
+ end
43
45
  end
44
- end
45
46
 
46
- # Class summarizing "hash" used for "par" or "seq" conversion.
47
- class Fm
48
- attr_reader :fm_seq, :fm_par, :rep, :rep_sharp
49
- def initialize
50
- @fm_seq = {} # Used to seq -> par.
51
- @fm_par = {} # Used to par -> seq.
52
- @rep = {} # Used to give ' to variables
53
- @rep_sharp = {} # Used to give # to variables
47
+ # Class summarizing "hash" used for "par" or "seq" conversion.
48
+ class Fm
49
+ attr_reader :fm_seq, :fm_par, :rep, :rep_sharp
50
+ def initialize
51
+ @fm_seq = {} # Used to seq -> par.
52
+ @fm_par = {} # Used to par -> seq.
53
+ @rep = {} # Used to give ' to variables
54
+ @rep_sharp = {} # Used to give # to variables
55
+ end
54
56
  end
55
- end
56
57
 
57
- # Declaration of fm to manage each hash.
58
- $fm = Fm.new
58
+ # Declaration of fm to manage each hash.
59
+ $fm = Fm.new
59
60
 
60
- # A class that translates the left-hand side, operator, and right-hand side into form of expression.
61
- class Binary
62
- # Converts the system to Verilog code.
63
- def to_verilog
64
- return "(#{self.left.to_verilog} #{self.operator} #{self.right.to_verilog})"
65
- end
61
+ # A class that translates the left-hand side, operator, and right-hand side into form of expression.
62
+ class Binary
63
+ # Converts the system to Verilog code.
64
+ def to_verilog
65
+ return "(#{self.left.to_verilog} #{self.operator} #{self.right.to_verilog})"
66
+ end
66
67
 
67
- # Method called when two or more expression terms are present.
68
- # When translating par into seq mode = seq, when translating seq to par mode = par.
69
- # Search recursively and replace if hash matches identifier.
70
- def to_change(mode)
71
- # Recursively search the left side and the right side, check the identifier and replace it.
72
- if self.left.is_a? (Binary) then
73
- # If there is an expression on the left side of the right side, to_chang is executed again.
74
- left = self.left.to_change(mode)
75
- else
76
- # If you need to replace the variable, replace it. Otherwise we will get a clone.
77
- if $fm.fm_par.has_key?(self.left.to_verilog) && mode == :par then
78
- left = $fm.fm_par["#{self.left.to_verilog}"]
79
- elsif $fm.fm_seq.has_key?(self.left.to_verilog) && mode == :seq then
80
- left = $fm.fm_seq["#{self.left.to_verilog}"]
68
+ # Method called when two or more expression terms are present.
69
+ # When translating par into seq mode = seq, when translating seq to par mode = par.
70
+ # Search recursively and replace if hash matches identifier.
71
+ def to_change(mode)
72
+ # Recursively search the left side and the right side, check the identifier and replace it.
73
+ if self.left.is_a? (Binary) then
74
+ # If there is an expression on the left side of the right side, to_chang is executed again.
75
+ left = self.left.to_change(mode)
81
76
  else
82
- left = self.left.clone
77
+ # If you need to replace the variable, replace it. Otherwise we will get a clone.
78
+ if $fm.fm_par.has_key?(self.left.to_verilog) && mode == :par then
79
+ left = $fm.fm_par["#{self.left.to_verilog}"]
80
+ elsif $fm.fm_seq.has_key?(self.left.to_verilog) && mode == :seq then
81
+ left = $fm.fm_seq["#{self.left.to_verilog}"]
82
+ else
83
+ left = self.left.clone
84
+ end
83
85
  end
84
- end
85
- if self.right.is_a? (Binary) then
86
- # Recursively search the right side and the right side, check the identifier and replace it.
87
- right = self.right.to_change(mode)
88
- else
89
- # If you need to replace the variable, replace it. Otherwise we will get a clone.
90
- if $fm.fm_par.has_key?(self.right.to_verilog) && mode == :par then
91
- right = $fm.fm_par["#{self.right.to_verilog}"]
92
- elsif $fm.fm_seq.has_key?(self.right.to_verilog) && mode == :seq then
93
- right = $fm.fm_seq["#{self.right.to_verilog}"]
86
+ if self.right.is_a? (Binary) then
87
+ # Recursively search the right side and the right side, check the identifier and replace it.
88
+ right = self.right.to_change(mode)
94
89
  else
95
- right = self.right.clone
90
+ # If you need to replace the variable, replace it. Otherwise we will get a clone.
91
+ if $fm.fm_par.has_key?(self.right.to_verilog) && mode == :par then
92
+ right = $fm.fm_par["#{self.right.to_verilog}"]
93
+ elsif $fm.fm_seq.has_key?(self.right.to_verilog) && mode == :seq then
94
+ right = $fm.fm_seq["#{self.right.to_verilog}"]
95
+ else
96
+ right = self.right.clone
97
+ end
96
98
  end
99
+ # After confirmation, we create and return an expression.
100
+ return Binary.new(self.type,self.operator,left.clone,right.clone)
97
101
  end
98
- # After confirmation, we create and return an expression.
99
- return Binary.new(self.type,self.operator,left.clone,right.clone)
100
102
  end
101
- end
102
103
 
103
- # class of Represent blocking substitution or nonblocking assignment.
104
- # Enhance Transmit with generation of verilog code.
105
- class Transmit
106
- # Converts the system to Verilog code.
107
- # def to_verilog(mode = nil)
108
- def to_verilog(spc = 3)
109
- # Determine blocking assignment or nonblocking substitution from mode and return it.
110
- # code = "#{self.left.to_verilog} #{mode == "seq" ? "=" : "<="} #{self.right.to_verilog};\n"
111
- code = "#{" " * spc}#{self.left.to_verilog} #{self.block.mode == :seq ? "=" : "<="} #{self.right.to_verilog};"
112
- return code
104
+ # class of Represent blocking substitution or nonblocking assignment.
105
+ # Enhance Transmit with generation of verilog code.
106
+ class Transmit
107
+ # Converts the system to Verilog code.
108
+ def to_verilog(spc = 3)
109
+ # Determine blocking assignment or nonblocking substitution from mode and return it.
110
+ code = "#{" " * spc}#{self.left.to_verilog} #{self.block.mode == :seq ? "=" : "<="} #{self.right.to_verilog};"
111
+ return code
112
+ end
113
113
  end
114
- end
115
114
 
116
- # To scheduling to the Block.
117
- # Enhance Block with generation of verilog code.
118
- class Block
119
- # # Converts the system to Verilog code.
120
- # def to_verilog(mode = nil)
121
- # # No translation is done in this class.
122
- # puts "Block to_verilog not found" # For debugging
123
- # end
115
+ # Enhance Print with generation of verilog code.
116
+ class Print
117
+ # Converts the system to Verilog code.
118
+ def to_verilog(spc = 3)
119
+ code = "#{" " * spc}$write(#{self.each_arg.map do |arg|
120
+ arg.to_verilog
121
+ end.join(",") });"
122
+ return code
123
+ end
124
+ end
125
+
126
+ # To scheduling to the Block.
127
+ # Enhance Block with generation of verilog code.
128
+ class Block
124
129
 
125
- # Converts the system to Verilog code adding 'spc' spaces at the begining
126
- # of each line.
127
- def to_verilog(spc = 3)
130
+ # Converts the system to Verilog code adding 'spc' spaces at the begining
131
+ # of each line.
132
+ def to_verilog(spc = 3)
128
133
  code = "begin"
129
- # code << " : #{name_to_verilog(self.name)}" if self.name && !self.name.empty?
130
134
  if self.name && !self.name.empty? then
131
135
  vname = name_to_verilog(self.name)
132
136
  code << " : #{vname}"
@@ -135,7 +139,6 @@ class Block
135
139
  code << "\n" if block.each_inner.any?
136
140
  # Declaration of "inner" part within "always".
137
141
  block.each_inner do |inner|
138
- # if regs.include?(inner.name) then
139
142
  if HDLRuby::Low::VERILOG_REGS.include?(inner.to_verilog) then
140
143
  # code << " reg"
141
144
  code << "#{" " * (spc+3)}reg"
@@ -147,14 +150,11 @@ class Block
147
150
  # It is determined by an if.
148
151
  if inner.type.base?
149
152
  if inner.type.base.base?
150
- # code << "#{inner.type.base.to_verilog} #{inner.to_verilog} #{inner.type.to_verilog};\n"
151
153
  code << "#{inner.type.base.to_verilog} #{inner.to_verilog} #{inner.type.to_verilog}"
152
154
  else
153
- # code << "#{inner.type.to_verilog} #{inner.to_verilog};\n"
154
155
  code << "#{inner.type.to_verilog} #{inner.to_verilog}"
155
156
  end
156
157
  else
157
- # code << " #{inner.type.to_verilog}#{inner.to_verilog};\n"
158
158
  code << " #{inner.type.to_verilog}#{inner.to_verilog}"
159
159
  end
160
160
  if inner.value then
@@ -166,8 +166,7 @@ class Block
166
166
 
167
167
  # Translate the block that finished scheduling.
168
168
  block.each_statement do |statement|
169
- #code << "\n #{statement.to_verilog(behavior.block.mode.to_s)}"
170
- # code << "\n#{" "*spc}#{statement.to_verilog(behavior.block.mode.to_s)}"
169
+ # puts "#{statement.to_verilog(spc+3)}"
171
170
  if statement.is_a?(Block) then
172
171
  code << "\n#{" " * (spc+3)}#{statement.to_verilog(spc+3)}"
173
172
  else
@@ -177,94 +176,177 @@ class Block
177
176
  # Close the block."
178
177
  code << "\n#{" "*spc}end"
179
178
  return code
180
- end
179
+ end
181
180
 
182
181
 
183
182
 
184
183
 
185
184
 
186
- # Extract and convert to verilog the TimeRepeat statements.
187
- # NOTE: work only on the current level of the block (should be called
188
- # through each_block_deep).
189
- def repeat_to_verilog!
190
- code = ""
191
- # Gather the TimeRepeat statements.
192
- repeats = self.each_statement.find_all { |st| st.is_a?(TimeRepeat) }
193
- # Remove them from the block.
194
- repeats.each { |st| self.delete_statement!(st) }
195
- # Generate them separately in timed always processes.
196
- repeats.each do |st|
197
- code << " always #{st.delay.to_verilog} begin\n"
185
+ # Extract and convert to verilog the TimeRepeat statements.
186
+ # NOTE: work only on the current level of the block (should be called
187
+ # through each_block_deep).
188
+ def repeat_to_verilog!
189
+ code = ""
190
+ # Gather the TimeRepeat statements.
191
+ repeats = self.each_statement.find_all { |st| st.is_a?(TimeRepeat) }
192
+ # Remove them from the block.
193
+ repeats.each { |st| self.delete_statement!(st) }
194
+ # Generate them separately in timed always processes.
195
+ repeats.each do |st|
196
+ code << " always #{st.delay.to_verilog} begin\n"
198
197
 
199
- # Perform "scheduling" using the method "flatten".
200
- block = st.statement.flatten(st.statement.mode.to_s)
198
+ # Perform "scheduling" using the method "flatten".
199
+ block = st.statement.flatten(st.statement.mode.to_s)
201
200
 
202
- # Declaration of "inner" part within "always".
203
- block.each_inner do |inner|
204
- # if regs.include?(inner.name) then
205
- if HDLRuby::Low::VERILOG_REGS.include?(inner.to_verilog) then
206
- code << " reg"
207
- else
208
- code << " wire"
209
- end
201
+ # Declaration of "inner" part within "always".
202
+ block.each_inner do |inner|
203
+ # if regs.include?(inner.name) then
204
+ if HDLRuby::Low::VERILOG_REGS.include?(inner.to_verilog) then
205
+ code << " reg"
206
+ else
207
+ code << " wire"
208
+ end
210
209
 
211
- # Variable has "base", but if there is width etc, it is not in "base".
212
- # It is determined by an if.
213
- if inner.type.base?
214
- if inner.type.base.base?
215
- # code << "#{inner.type.base.to_verilog} #{inner.to_verilog} #{inner.type.to_verilog};\n"
216
- code << "#{inner.type.base.to_verilog} #{inner.to_verilog} #{inner.type.to_verilog}"
210
+ # Variable has "base", but if there is width etc, it is not in "base".
211
+ # It is determined by an if.
212
+ if inner.type.base?
213
+ if inner.type.base.base?
214
+ code << "#{inner.type.base.to_verilog} #{inner.to_verilog} #{inner.type.to_verilog}"
215
+ else
216
+ code << "#{inner.type.to_verilog} #{inner.to_verilog}"
217
+ end
217
218
  else
218
- # code << "#{inner.type.to_verilog} #{inner.to_verilog};\n"
219
- code << "#{inner.type.to_verilog} #{inner.to_verilog}"
219
+ code << " #{inner.type.to_verilog}#{inner.to_verilog}"
220
220
  end
221
- else
222
- # code << " #{inner.type.to_verilog}#{inner.to_verilog};\n"
223
- code << " #{inner.type.to_verilog}#{inner.to_verilog}"
221
+ if inner.value then
222
+ # There is an initial value.
223
+ code << " = #{inner.value.to_verilog}"
224
+ end
225
+ code << ";\n"
224
226
  end
225
- if inner.value then
226
- # There is an initial value.
227
- code << " = #{inner.value.to_verilog}"
227
+
228
+ # Translate the block that finished scheduling.
229
+ block.each_statement do |statement|
230
+ code << "\n #{statement.to_verilog(block.mode.to_s)}"
228
231
  end
229
- code << ";\n"
230
- end
231
232
 
232
- # Translate the block that finished scheduling.
233
- block.each_statement do |statement|
234
- code << "\n #{statement.to_verilog(block.mode.to_s)}"
233
+ $fm.fm_par.clear()
234
+
235
+ code << "\n end\n\n"
235
236
  end
237
+ return code
238
+ end
236
239
 
237
- $fm.fm_par.clear()
238
240
 
239
- code << "\n end\n\n"
240
- end
241
- return code
242
- end
241
+ # Process top layer of Block.
242
+ # Determine whether there is a block under block and convert it.
243
+ def flatten(mode = nil)
244
+ if self.is_a?(TimeBlock) then
245
+ new_block = TimeBlock.new(self.mode,"")
246
+ else
247
+ new_block = Block.new(self.mode,"") # A new block to store the converted statement.
248
+ end
249
+ list = [] # A list for confirming that variable declarations do not overlap.
250
+
251
+ # Is block in the statement?
252
+ if (self.each_statement.find {|stmnt| stmnt.is_a?(Block)}) then
253
+ # Process for each type of statement in block.
254
+ self.each_statement do |statement|
255
+ # If statement is case, there is a block for each default and when, so translate each.
256
+ if statement.is_a?(Case) then
257
+ if statement.default.is_a?(Block)
258
+ default = statement.default.flatten
259
+ new_default = Block.new(default.mode,"")
260
+
261
+ default.each_inner do |inner|
262
+ # I read inner, but when I am par, I delete all '.
263
+ unless (list.include?(inner.name.to_s)) then
264
+ if (self.mode == :seq) || (inner.name.to_s.include? "#") then
265
+ list << inner.name.to_s
266
+ new_block.add_inner(inner.clone)
267
+ end
268
+ end
269
+ end
243
270
 
271
+ default.each_statement do |statement|
272
+ # If statement is Transmit, it is an expression and should be processed.
273
+ if statement.is_a?(Transmit) then
274
+ # If you add a # to the one with 'on the left side, the shape of the formula will collapse and it will be removed.
275
+ unless (res_name(statement.left).name.to_s.include? "'") || default.mode == :par then
276
+ # Prepare a new signal with the # on the variable on the left side using the att_signal method.
277
+ new_signal = att_signal(statement.left, "#")
278
+ # Check list and add new variables to inner if they do not duplicate.
279
+ unless (list.include?(new_signal.name.to_s)) then
280
+ list << new_signal.name.to_s
281
+ new_block.add_inner(new_signal)
282
+ end
283
+
284
+ new_statement = Transmit.new(search_refname(statement.left,"#"),statement.right.clone)
285
+
286
+ $fm.rep_sharp[statement.left] = search_refname(statement.left,"#")
287
+
288
+ $fm.fm_par["#{statement.left.to_verilog}"] = new_statement.left
289
+ new_default.add_statement(new_statement.clone)
290
+ else
291
+ new_default.add_statement(statement.clone)
292
+ end
293
+ else
294
+ new_default.add_statement(statement.clone)
295
+ end
296
+ end
297
+ end
244
298
 
245
- # Process top layer of Block.
246
- # Determine whether there is a block under block and convert it.
247
- def flatten(mode = nil)
248
- if self.is_a?(TimeBlock) then
249
- new_block = TimeBlock.new(self.mode,"")
250
- else
251
- new_block = Block.new(self.mode,"") # A new block to store the converted statement.
252
- end
253
- list = [] # A list for confirming that variable declarations do not overlap.
299
+ new_statement = Case.new(statement.value.clone,statement.default ? new_default.clone : nil,[])
300
+
301
+ statement.each_when do |whens|
302
+ when_smt = whens.statement.flatten
303
+ new_when_smt = Block.new(when_smt.mode,"")
304
+
305
+ when_smt.each_statement do |statement|
306
+ # If statement is Transmit, it is an expression and should be processed.
307
+ if statement.is_a?(Transmit) then
308
+ # # If you add a # to the one with 'on the left side, the shape of the formula will collapse and it will be removed.
309
+ unless (res_name(statement.left).name.to_s.include? "'") || when_smt.mode == :par then
310
+ # # Prepare a new signal with the # on the variable on the left side using the att_signal method.
311
+ new_signal = att_signal(statement.left, "#")
312
+ # Check list and add new variables to inner if they do not duplicate.
313
+ unless (list.include?(new_signal.name.to_s)) then
314
+ list << new_signal.name.to_s
315
+ new_block.add_inner(new_signal)
316
+ end
317
+
318
+ new_smt = Transmit.new(search_refname(statement.left,"#"),statement.right.clone)
319
+
320
+ $fm.rep_sharp[statement.left] = search_refname(statement.left,"#")
321
+
322
+ $fm.fm_par["#{statement.left.to_verilog}"] = new_smt.left
323
+ new_when_smt.add_statement(new_smt.clone)
324
+ else
325
+ new_when_smt.add_statement(statement.clone)
326
+ end
327
+ else
328
+ new_when_smt.add_statement(statement.clone)
329
+ end
330
+ end
254
331
 
255
- # Is block in the statement?
256
- if (self.each_statement.find {|stmnt| stmnt.is_a?(Block)}) then
257
- # Process for each type of statement in block.
258
- self.each_statement do |statement|
332
+ new_when = When.new(whens.match.clone,new_when_smt.clone)
333
+ new_statement.add_when(new_when.clone)
334
+ end
259
335
 
336
+ new_block.add_statement(new_statement)
260
337
 
261
- # If statement is case, there is a block for each default and when, so translate each.
262
- if statement.is_a?(Case) then
263
- if statement.default.is_a?(Block)
264
- default = statement.default.flatten
265
- new_default = Block.new(default.mode,"")
338
+ $fm.rep_sharp.each_key do |key|
339
+ new_smt = Transmit.new(key.clone,$fm.rep_sharp[key].clone)
340
+ new_block.add_statement(new_smt.clone)
341
+ end
342
+ $fm.rep_sharp.clear() # Deactivate rep that has become obsolete.
266
343
 
267
- default.each_inner do |inner|
344
+ # If the statement is if, there is a block for each of yes, no, noifs, so translate each.
345
+ elsif statement.is_a?(If) then
346
+ yes = statement.yes.flatten # Smooth yes of if statement.
347
+ new_yes = Block.new(yes.mode,"") # New yes storage block
348
+
349
+ yes.each_inner do |inner|
268
350
  # I read inner, but when I am par, I delete all '.
269
351
  unless (list.include?(inner.name.to_s)) then
270
352
  if (self.mode == :seq) || (inner.name.to_s.include? "#") then
@@ -274,11 +356,12 @@ class Block
274
356
  end
275
357
  end
276
358
 
277
- default.each_statement do |statement|
359
+ # Check the statements in "yes" in order.
360
+ yes.each_statement do |statement|
278
361
  # If statement is Transmit, it is an expression and should be processed.
279
362
  if statement.is_a?(Transmit) then
280
363
  # If you add a # to the one with 'on the left side, the shape of the formula will collapse and it will be removed.
281
- unless (res_name(statement.left).name.to_s.include? "'") || default.mode == :par then
364
+ unless (res_name(statement.left).name.to_s.include? "'") || yes.mode == :par then
282
365
  # Prepare a new signal with the # on the variable on the left side using the att_signal method.
283
366
  new_signal = att_signal(statement.left, "#")
284
367
  # Check list and add new variables to inner if they do not duplicate.
@@ -291,130 +374,188 @@ class Block
291
374
 
292
375
  $fm.rep_sharp[statement.left] = search_refname(statement.left,"#")
293
376
 
377
+ new_yes.add_statement(new_statement.clone)
378
+
379
+
294
380
  $fm.fm_par["#{statement.left.to_verilog}"] = new_statement.left
295
- new_default.add_statement(new_statement.clone)
381
+
296
382
  else
297
- new_default.add_statement(statement.clone)
383
+ new_yes.add_statement(statement.clone)
298
384
  end
299
385
  else
300
- new_default.add_statement(statement.clone)
386
+ new_yes.add_statement(statement.clone)
301
387
  end
302
- end
303
- end
388
+ end
304
389
 
305
- new_statement = Case.new(statement.value.clone,statement.default ? new_default.clone : nil,[])
390
+ # Confirm that "else" exists and convert it if it exists.
391
+ # Because error occurs when trying to convert when "else" does not exist.
392
+ if statement.no.is_a? (Block) then
393
+ no = statement.no.flatten
394
+ new_no = Block.new(no.mode,"")
395
+
396
+ no.each_inner do |inner|
397
+ # I read inner, but when I am par, I delete all '.
398
+ unless (list.include?(inner.name.to_s)) then
399
+ if (self.mode == :seq) || (inner.name.to_s.include? "#") then
400
+ list << inner.name.to_s
401
+ new_block.add_inner(inner.clone)
402
+ end
403
+ end
404
+ end
306
405
 
307
- statement.each_when do |whens|
308
- when_smt = whens.statement.flatten
309
- new_when_smt = Block.new(when_smt.mode,"")
406
+ no.each_statement do |statement|
407
+ # If statement is Transmit, it is an expression and should be processed.
408
+ if statement.is_a?(Transmit) then
409
+ # If you add a # to the one with 'on the left side, the shape of the formula will collapse and it will be removed.
410
+ unless (res_name(statement.left).name.to_s.include? "'") || yes.mode == :par then
310
411
 
311
- when_smt.each_statement do |statement|
312
- # If statement is Transmit, it is an expression and should be processed.
313
- if statement.is_a?(Transmit) then
314
- # # If you add a # to the one with 'on the left side, the shape of the formula will collapse and it will be removed.
315
- unless (res_name(statement.left).name.to_s.include? "'") || when_smt.mode == :par then
316
- # # Prepare a new signal with the # on the variable on the left side using the att_signal method.
317
- new_signal = att_signal(statement.left, "#")
318
- # Check list and add new variables to inner if they do not duplicate.
319
- unless (list.include?(new_signal.name.to_s)) then
320
- list << new_signal.name.to_s
321
- new_block.add_inner(new_signal)
322
- end
412
+ new_signal = att_signal(statement.left, "#")
323
413
 
324
- new_smt = Transmit.new(search_refname(statement.left,"#"),statement.right.clone)
414
+ # Double declaration of existing variable can not be done, so it is excluded.
415
+ unless (list.include?(new_signal.name.to_s)) then
416
+ list << new_signal.name.to_s
417
+ new_block.add_inner(new_signal)
418
+ end
325
419
 
326
- $fm.rep_sharp[statement.left] = search_refname(statement.left,"#")
420
+ new_statement = Transmit.new(search_refname(statement.left,"#"),statement.right.clone)
327
421
 
328
- $fm.fm_par["#{statement.left.to_verilog}"] = new_smt.left
329
- new_when_smt.add_statement(new_smt.clone)
422
+ $fm.rep_sharp[statement.left] = search_refname(statement.left,"#")
423
+
424
+ $fm.fm_par["#{statement.left.to_verilog}"] = new_statement.left
425
+ new_no.add_statement(new_statement.clone)
426
+ else
427
+ new_no.add_statement(statement.clone)
428
+ end
330
429
  else
331
- new_when_smt.add_statement(statement.clone)
332
- end
333
- else
334
- new_when_smt.add_statement(statement.clone)
430
+ new_no.add_statement(statement.clone)
431
+ end
335
432
  end
336
433
  end
337
434
 
338
- new_when = When.new(whens.match.clone,new_when_smt.clone)
339
- new_statement.add_when(new_when.clone)
340
- end
435
+ # Rebuild the converted "if" as a new" statement (If)".
436
+ new_statement = If.new(statement.condition.clone,new_yes.clone,statement.no ? new_no.clone : nil)
437
+
438
+ # Just like "no", check if "noifs (elsif)" exists and if there is, take one by one and convert.
439
+ # After that, add the converted "noif" to "If".
440
+ statement.each_noif do |condition, block|
441
+ noif = block.flatten
442
+ new_noif = Block.new(noif.mode,"")
443
+
444
+ noif.each_inner do |inner|
445
+ # I read inner, but when I am par, I delete all '.
446
+ unless (list.include?(inner.name.to_s)) then
447
+ if (self.mode == :seq) || (inner.name.to_s.include? "#") then
448
+ list << inner.name.to_s
449
+ new_block.add_inner(inner.clone)
450
+ end
451
+ end
452
+ end
341
453
 
342
- new_block.add_statement(new_statement)
343
454
 
344
- $fm.rep_sharp.each_key do |key|
345
- new_smt = Transmit.new(key.clone,$fm.rep_sharp[key].clone)
346
- new_block.add_statement(new_smt.clone)
347
- end
348
- $fm.rep_sharp.clear() # Deactivate rep that has become obsolete.
455
+ noif.each_statement do |statement|
456
+ # If statement is Transmit, it is an expression and should be processed.
457
+ if statement.is_a?(Transmit) then
458
+ # If you add a # to the one with 'on the left side, the shape of the formula will collapse and it will be removed.
459
+ unless (res_name(statement.left).name.to_s.include? "'") || yes.mode == :par then
349
460
 
350
- # If the statement is if, there is a block for each of yes, no, noifs, so translate each.
351
- elsif statement.is_a?(If) then
352
- yes = statement.yes.flatten # Smooth yes of if statement.
353
- new_yes = Block.new(yes.mode,"") # New yes storage block
461
+ new_signal = att_signal(statement.left, "#")
354
462
 
355
- yes.each_inner do |inner|
356
- # I read inner, but when I am par, I delete all '.
357
- unless (list.include?(inner.name.to_s)) then
358
- if (self.mode == :seq) || (inner.name.to_s.include? "#") then
359
- list << inner.name.to_s
360
- new_block.add_inner(inner.clone)
361
- end
362
- end
363
- end
463
+ # Double declaration of existing variable can not be done, so it is excluded.
464
+ unless (list.include?(new_signal.name.to_s)) then
465
+ list << new_signal.name.to_s
466
+ new_block.add_inner(new_signal)
467
+ end
364
468
 
365
- # Check the statements in "yes" in order.
366
- yes.each_statement do |statement|
367
- # If statement is Transmit, it is an expression and should be processed.
368
- if statement.is_a?(Transmit) then
369
- # If you add a # to the one with 'on the left side, the shape of the formula will collapse and it will be removed.
370
- unless (res_name(statement.left).name.to_s.include? "'") || yes.mode == :par then
371
- # Prepare a new signal with the # on the variable on the left side using the att_signal method.
372
- new_signal = att_signal(statement.left, "#")
373
- # Check list and add new variables to inner if they do not duplicate.
374
- unless (list.include?(new_signal.name.to_s)) then
375
- list << new_signal.name.to_s
376
- new_block.add_inner(new_signal)
469
+ new_statement = Transmit.new(search_refname(statement.left,"#"),statement.right.clone)
470
+
471
+ $fm.rep_sharp[statement.left] = search_refname(statement.left,"#")
472
+
473
+ $fm.fm_par["#{statement.left.to_verilog}"] = new_statement.left
474
+ new_noif.add_statement(new_statement.clone)
475
+ else
476
+ new_noif.add_statement(statement.clone)
477
+ end
478
+ else
479
+ new_noif.add_statement(statement.clone)
377
480
  end
481
+ end
378
482
 
379
- new_statement = Transmit.new(search_refname(statement.left,"#"),statement.right.clone)
483
+ new_statement.add_noif(condition.clone,new_noif.clone)
484
+ end
380
485
 
381
- $fm.rep_sharp[statement.left] = search_refname(statement.left,"#")
486
+ new_block.add_statement(new_statement.clone)
382
487
 
383
- new_yes.add_statement(new_statement.clone)
488
+ $fm.rep_sharp.each_key do |key|
489
+ new_smt = Transmit.new(key.clone,$fm.rep_sharp[key].clone)
490
+ new_block.add_statement(new_smt.clone)
491
+ end
492
+ $fm.rep_sharp.clear() # Deactivate rep that has become obsolete.
384
493
 
494
+ # Process when "statement" is "Transmit" (just expression).
495
+ # Record the expression in fm_par used for par-> seq and add the expression to new_block which is the "new block".
496
+ elsif statement.is_a?(Transmit) then
497
+ if self.mode == :seq then
498
+ $fm.fm_par["#{statement.left.to_verilog}"] = statement.right
499
+ end
500
+ new_block.add_statement(statement.clone)
385
501
 
386
- $fm.fm_par["#{statement.left.to_verilog}"] = new_statement.left
502
+ # When statement is Block (lower layer exists).
503
+ # Smooth the lower layer with do_flat.
504
+ # Add the added variables (inner) and expressions (statement) to new_block, respectively.
505
+ elsif statement.is_a?(Block) then
506
+ smt = statement.do_flat(self.mode)
387
507
 
388
- else
389
- new_yes.add_statement(statement.clone)
390
- end
391
- else
392
- new_yes.add_statement(statement.clone)
508
+ smt.each_inner do |inner|
509
+ # I read inner, but when I am par, I delete all '.
510
+ unless (list.include?(inner.name.to_s)) then
511
+ if (self.mode == :seq) || (inner.name.to_s.include? "#") then
512
+ list << inner.name.to_s
513
+ new_block.add_inner(inner.clone)
514
+ end
515
+ end
516
+ end
517
+ smt.each_statement do |tmt|
518
+ # Retrieve the RefName of the variable on the left side and store it in this_name.
519
+ if ((tmt.is_a? (Transmit)) && (self.mode == :seq)) then
520
+ $fm.fm_par["#{tmt.left.to_verilog}"] = tmt.right
521
+ end
522
+ new_block.add_statement(tmt.clone)
393
523
  end
524
+ else
525
+ # Other statements are simply added as is.
526
+ new_block.add_statement(statement.clone)
394
527
  end
528
+ end
395
529
 
396
- # Confirm that "else" exists and convert it if it exists.
397
- # Because error occurs when trying to convert when "else" does not exist.
398
- if statement.no.is_a? (Block) then
399
- no = statement.no.flatten
400
- new_no = Block.new(no.mode,"")
530
+ return new_block # Return the new_block that completed the smoothing.
401
531
 
402
- no.each_inner do |inner|
532
+ # Processing when there is no block beneath.
533
+ # Unlike ordinary "if" and "case" blocks come down, we check individually block under block.
534
+ else
535
+ self.each_statement do |statement|
536
+ # If the if statement, convert it, otherwise add it as is
537
+ if statement.is_a?(If) then
538
+ # Since yes always exists, it is no problem even if it is converted as it is.
539
+ yes = statement.yes.flatten
540
+ new_yes = Block.new(yes.mode,"")
541
+
542
+ yes.each_inner do |inner|
403
543
  # I read inner, but when I am par, I delete all '.
404
544
  unless (list.include?(inner.name.to_s)) then
405
- if (self.mode == :seq) || (inner.name.to_s.include? "#") then
545
+ if (yes.mode == :seq) || (inner.name.to_s.include? "#") then
406
546
  list << inner.name.to_s
407
547
  new_block.add_inner(inner.clone)
408
548
  end
409
549
  end
410
550
  end
411
551
 
412
- no.each_statement do |statement|
552
+ # Check the statements in "yes" in order.
553
+ yes.each_statement do |statement|
413
554
  # If statement is Transmit, it is an expression and should be processed.
414
555
  if statement.is_a?(Transmit) then
415
556
  # If you add a # to the one with 'on the left side, the shape of the formula will collapse and it will be removed.
416
557
  unless (res_name(statement.left).name.to_s.include? "'") || yes.mode == :par then
417
-
558
+ # Generate a new signal to return #.
418
559
  new_signal = att_signal(statement.left, "#")
419
560
 
420
561
  # Double declaration of existing variable can not be done, so it is excluded.
@@ -428,1836 +569,1544 @@ class Block
428
569
  $fm.rep_sharp[statement.left] = search_refname(statement.left,"#")
429
570
 
430
571
  $fm.fm_par["#{statement.left.to_verilog}"] = new_statement.left
431
- new_no.add_statement(new_statement.clone)
572
+ new_yes.add_statement(new_statement.clone)
432
573
  else
433
- new_no.add_statement(statement.clone)
574
+ new_yes.add_statement(statement.clone)
434
575
  end
435
576
  else
436
- new_no.add_statement(statement.clone)
577
+ new_yes.add_statement(statement.clone)
437
578
  end
438
579
  end
439
- end
440
580
 
441
- # Rebuild the converted "if" as a new" statement (If)".
442
- new_statement = If.new(statement.condition.clone,new_yes.clone,statement.no ? new_no.clone : nil)
581
+ # Confirm that "else" exists and convert it if it exists.
582
+ # Because error occurs when trying to convert when "else" does not exist.
583
+ if statement.no.is_a? (Block) then
584
+ no = statement.no.flatten
585
+ new_no = Block.new(no.mode,"")
586
+
587
+ no.each_inner do |inner|
588
+ # I read inner, but when I am par, I delete all '.
589
+ unless (list.include?(inner.name.to_s)) then
590
+ if (no.mode == :seq) || (inner.name.to_s.include? "#") then
591
+ list << inner.name.to_s
592
+ new_block.add_inner(inner.clone)
593
+ end
594
+ end
595
+ end
443
596
 
444
- # Just like "no", check if "noifs (elsif)" exists and if there is, take one by one and convert.
445
- # After that, add the converted "noif" to "If".
446
- statement.each_noif do |condition, block|
447
- noif = block.flatten
448
- new_noif = Block.new(noif.mode,"")
597
+ no.each_statement do |statement|
598
+ # If statement is Transmit, it is an expression and should be processed.
599
+ if statement.is_a?(Transmit) then
600
+ # If you add a # to the one with 'on the left side, the shape of the formula will collapse and it will be removed.
601
+ unless (res_name(statement.left).name.to_s.include? "'") || no.mode == :par then
449
602
 
450
- noif.each_inner do |inner|
451
- # I read inner, but when I am par, I delete all '.
452
- unless (list.include?(inner.name.to_s)) then
453
- if (self.mode == :seq) || (inner.name.to_s.include? "#") then
454
- list << inner.name.to_s
455
- new_block.add_inner(inner.clone)
456
- end
603
+ new_signal = att_signal(statement.left, "#")
604
+
605
+ # Double declaration of existing variable can not be done, so it is excluded.
606
+ unless (list.include?(new_signal.name.to_s)) then
607
+ list << new_signal.name.to_s
608
+ new_block.add_inner(new_signal)
609
+ end
610
+
611
+ new_statement = Transmit.new(search_refname(statement.left,"#"),statement.right.clone)
612
+
613
+ $fm.rep_sharp[statement.left] = search_refname(statement.left,"#")
614
+
615
+ $fm.fm_par["#{statement.left.to_verilog}"] = new_statement.left
616
+ new_no.add_statement(new_statement.clone)
617
+ else
618
+ new_no.add_statement(statement.clone)
619
+ end
620
+ else
621
+ new_no.add_statement(statement.clone)
622
+ end
457
623
  end
458
624
  end
625
+ # Rebuild the converted "if" as a new" statement (If)".
626
+ new_statement = If.new(statement.condition.clone,new_yes.clone,statement.no ? new_no.clone : nil)
627
+ # Just like "no", check if "noifs (elsif)" exists and if there is, take one by one and convert.
628
+ # After that, add the converted "noif" to "If".
629
+ statement.each_noif do |condition, block|
630
+
631
+ noif = block.flatten
632
+ new_noif = Block.new(noif.mode,"")
633
+
634
+ noif.each_inner do |inner|
635
+ # I read inner, but when I am par, I delete all '.
636
+ unless (list.include?(inner.name.to_s)) then
637
+ if (noif.mode == :seq) || (inner.name.to_s.include? "#") then
638
+ list << inner.name.to_s
639
+ new_block.add_inner(inner.clone)
640
+ end
641
+ end
642
+ end
459
643
 
460
644
 
461
- noif.each_statement do |statement|
462
- # If statement is Transmit, it is an expression and should be processed.
463
- if statement.is_a?(Transmit) then
464
- # If you add a # to the one with 'on the left side, the shape of the formula will collapse and it will be removed.
465
- unless (res_name(statement.left).name.to_s.include? "'") || yes.mode == :par then
645
+ noif.each_statement do |statement|
646
+ # If statement is Transmit, it is an expression and should be processed.
647
+ if statement.is_a?(Transmit) then
648
+ # If you add a # to the one with 'on the left side, the shape of the formula will collapse and it will be removed.
649
+ unless (res_name(statement.left).name.to_s.include? "'") || noif.mode == :par then
466
650
 
467
- new_signal = att_signal(statement.left, "#")
651
+ new_signal = att_signal(statement.left, "#")
468
652
 
469
- # Double declaration of existing variable can not be done, so it is excluded.
470
- unless (list.include?(new_signal.name.to_s)) then
471
- list << new_signal.name.to_s
472
- new_block.add_inner(new_signal)
473
- end
653
+ # Double declaration of existing variable can not be done, so it is excluded.
654
+ unless (list.include?(new_signal.name.to_s)) then
655
+ list << new_signal.name.to_s
656
+ new_block.add_inner(new_signal)
657
+ end
474
658
 
475
- new_statement = Transmit.new(search_refname(statement.left,"#"),statement.right.clone)
659
+ new_statement = Transmit.new(search_refname(statement.left,"#"),statement.right.clone)
476
660
 
477
- $fm.rep_sharp[statement.left] = search_refname(statement.left,"#")
661
+ $fm.rep_sharp[statement.left] = search_refname(statement.left,"#")
478
662
 
479
- $fm.fm_par["#{statement.left.to_verilog}"] = new_statement.left
480
- new_noif.add_statement(new_statement.clone)
663
+ $fm.fm_par["#{statement.left.to_verilog}"] = new_statement.left
664
+ new_noif.add_statement(new_statement.clone)
665
+ else
666
+ new_noif.add_statement(statement.clone)
667
+ end
481
668
  else
482
669
  new_noif.add_statement(statement.clone)
483
- end
484
- else
485
- new_noif.add_statement(statement.clone)
670
+ end
486
671
  end
487
- end
488
672
 
489
- new_statement.add_noif(condition.clone,new_noif.clone)
490
- end
673
+ new_statement.add_noif(condition.clone,new_noif.clone)
674
+ end
491
675
 
492
- new_block.add_statement(new_statement.clone)
676
+ new_block.add_statement(new_statement.clone)
493
677
 
494
- $fm.rep_sharp.each_key do |key|
495
- new_smt = Transmit.new(key.clone,$fm.rep_sharp[key].clone)
496
- new_block.add_statement(new_smt.clone)
497
- end
498
- $fm.rep_sharp.clear() # Deactivate rep that has become obsolete.
678
+ $fm.rep_sharp.each_key do |key|
679
+ new_smt = Transmit.new(key.clone,$fm.rep_sharp[key].clone)
680
+ new_block.add_statement(new_smt.clone)
681
+ end
682
+ $fm.rep_sharp.clear() # Deactivate rep that has become obsolete.
499
683
 
500
- # Process when "statement" is "Transmit" (just expression).
501
- # Record the expression in fm_par used for par-> seq and add the expression to new_block which is the "new block".
502
- elsif statement.is_a?(Transmit) then
503
- if self.mode == :seq then
504
- $fm.fm_par["#{statement.left.to_verilog}"] = statement.right
505
- end
506
- new_block.add_statement(statement.clone)
684
+ elsif statement.is_a?(Case) then
685
+ if statement.default.is_a?(Block)
686
+ new_default = statement.default.flatten
687
+ end
507
688
 
508
- # When statement is Block (lower layer exists).
509
- # Smooth the lower layer with do_flat.
510
- # Add the added variables (inner) and expressions (statement) to new_block, respectively.
511
- elsif statement.is_a?(Block) then
512
- smt = statement.do_flat(self.mode)
689
+ new_statement = Case.new(statement.value.clone,statement.default ? new_default.clone : nil,[])
690
+ statement.each_when do |whens|
691
+ new_when_statement = whens.statement.flatten
692
+ new_when = When.new(whens.match.clone,new_when_statement.clone)
513
693
 
514
- smt.each_inner do |inner|
515
- # I read inner, but when I am par, I delete all '.
516
- unless (list.include?(inner.name.to_s)) then
517
- if (self.mode == :seq) || (inner.name.to_s.include? "#") then
518
- list << inner.name.to_s
519
- new_block.add_inner(inner.clone)
520
- end
521
- end
522
- end
523
- smt.each_statement do |tmt|
524
- # Retrieve the RefName of the variable on the left side and store it in this_name.
525
- if ((tmt.is_a? (Transmit)) && (self.mode == :seq)) then
526
- $fm.fm_par["#{tmt.left.to_verilog}"] = tmt.right
694
+ new_statement.add_when(new_when.clone)
527
695
  end
528
- new_block.add_statement(tmt.clone)
696
+
697
+ new_block.add_statement(new_statement)
698
+ else
699
+ new_block.add_statement(statement.clone)
529
700
  end
701
+ end
702
+ return new_block
703
+ end
704
+ end
705
+
706
+ def do_flat(mode = nil)
707
+ flat = Block.new(self.mode,"") # Block between lower layers when converting.
708
+ trans = Block.new(self.mode,"") # The block used for converting itself.
709
+ replase = Block.new(self.mode,"") # block to be used for further conversion in case of if statement.
710
+ list = []
711
+ rep_list = []
712
+
713
+ # If there is a block inside the statement it is not the lowest layer. If there is, it is the lowest layer.
714
+ if (self.each_statement.find {|stmnt| stmnt.is_a?(Block)} || (self.each_statement.find {|stmnt| stmnt.is_a?(If)}) || (self.each_statement.find {|stmnt| stmnt.is_a?(Case)}))then
715
+ # In the case of seq, the lower layer is par. Isolate fm_par so that it is not crosstalked.
716
+ if(self.mode == :seq) then
717
+ fm_buckup = $fm.fm_par.clone
718
+ $fm.fm_par.clear()
719
+
720
+ new_block = change_branch(self)
530
721
  else
531
- # Other statements are simply added as is.
532
- new_block.add_statement(statement.clone)
722
+ new_block = self.clone
533
723
  end
534
- end
535
724
 
536
- return new_block # Return the new_block that completed the smoothing.
725
+ # Process for each statement.
726
+ new_block.each_statement do |statement|
727
+ # If statement is If, convert yes, no, noif and add them to flat.
728
+ if statement.is_a?(Case) then
729
+ if(self.mode == :seq) then
730
+ fm_buckup_if = $fm.fm_par.clone
731
+ end
537
732
 
538
- # Processing when there is no block beneath.
539
- # Unlike ordinary "if" and "case" blocks come down, we check individually block under block.
540
- else
541
- self.each_statement do |statement|
542
- # If the if statement, convert it, otherwise add it as is
543
- if statement.is_a?(If) then
544
- # Since yes always exists, it is no problem even if it is converted as it is.
545
- yes = statement.yes.flatten
546
- new_yes = Block.new(yes.mode,"")
547
-
548
- yes.each_inner do |inner|
549
- # I read inner, but when I am par, I delete all '.
550
- unless (list.include?(inner.name.to_s)) then
551
- if (yes.mode == :seq) || (inner.name.to_s.include? "#") then
552
- list << inner.name.to_s
553
- new_block.add_inner(inner.clone)
554
- end
733
+ if statement.default.is_a?(Block)
734
+ default = statement.default.flatten
735
+ new_default = Block.new(default.mode,"")
736
+
737
+ default.each_statement do |statement|
738
+ new_default.add_statement(statement.clone)
739
+ end
555
740
  end
556
- end
557
741
 
558
- # Check the statements in "yes" in order.
559
- yes.each_statement do |statement|
560
- # If statement is Transmit, it is an expression and should be processed.
561
- if statement.is_a?(Transmit) then
562
- # If you add a # to the one with 'on the left side, the shape of the formula will collapse and it will be removed.
563
- unless (res_name(statement.left).name.to_s.include? "'") || yes.mode == :par then
564
- # Generate a new signal to return #.
565
- new_signal = att_signal(statement.left, "#")
566
742
 
567
- # Double declaration of existing variable can not be done, so it is excluded.
568
- unless (list.include?(new_signal.name.to_s)) then
569
- list << new_signal.name.to_s
570
- new_block.add_inner(new_signal)
571
- end
743
+ new_statement = Case.new(statement.value.clone,statement.default ? new_default.clone : nil,[])
572
744
 
573
- new_statement = Transmit.new(search_refname(statement.left,"#"),statement.right.clone)
745
+ statement.each_when do |whens|
746
+ if(self.mode == :seq) then
747
+ fm_buckup_if.each_key do |key|
748
+ $fm.fm_par[key] = fm_buckup_if[key]
749
+ end
750
+ end
574
751
 
575
- $fm.rep_sharp[statement.left] = search_refname(statement.left,"#")
752
+ when_smt = whens.statement.flatten
753
+ new_when = When.new(whens.match.clone,when_smt.clone)
754
+ new_statement.add_when(new_when.clone)
755
+ end
756
+ flat.add_statement(new_statement)
576
757
 
577
- $fm.fm_par["#{statement.left.to_verilog}"] = new_statement.left
578
- new_yes.add_statement(new_statement.clone)
579
- else
580
- new_yes.add_statement(statement.clone)
581
- end
582
- else
583
- new_yes.add_statement(statement.clone)
758
+ elsif statement.is_a?(If) then
759
+ if(self.mode == :seq) then
760
+ fm_buckup_if = $fm.fm_par.clone
584
761
  end
585
- end
586
762
 
587
- # Confirm that "else" exists and convert it if it exists.
588
- # Because error occurs when trying to convert when "else" does not exist.
589
- if statement.no.is_a? (Block) then
590
- no = statement.no.flatten
591
- new_no = Block.new(no.mode,"")
763
+ # Since yes always exist, convert without confirming.
764
+ new_yes = statement.yes.flatten
592
765
 
593
- no.each_inner do |inner|
594
- # I read inner, but when I am par, I delete all '.
595
- unless (list.include?(inner.name.to_s)) then
596
- if (no.mode == :seq) || (inner.name.to_s.include? "#") then
597
- list << inner.name.to_s
598
- new_block.add_inner(inner.clone)
599
- end
600
- end
601
- end
602
-
603
- no.each_statement do |statement|
604
- # If statement is Transmit, it is an expression and should be processed.
605
- if statement.is_a?(Transmit) then
606
- # If you add a # to the one with 'on the left side, the shape of the formula will collapse and it will be removed.
607
- unless (res_name(statement.left).name.to_s.include? "'") || no.mode == :par then
608
-
609
- new_signal = att_signal(statement.left, "#")
766
+ # I do not know whether no (else) exists, so convert it if it is confirmed.
767
+ if statement.no.is_a? (Block) then
610
768
 
611
- # Double declaration of existing variable can not be done, so it is excluded.
612
- unless (list.include?(new_signal.name.to_s)) then
613
- list << new_signal.name.to_s
614
- new_block.add_inner(new_signal)
615
- end
769
+ if(self.mode == :seq) then
770
+ fm_buckup_if.each_key do |key|
771
+ $fm.fm_par[key] = fm_buckup_if[key]
772
+ end
773
+ end
616
774
 
617
- new_statement = Transmit.new(search_refname(statement.left,"#"),statement.right.clone)
775
+ new_no = statement.no.flatten
776
+ end
777
+ # Create a new if statement with converted yes and no.
778
+ new_statement = If.new(statement.condition.clone,new_yes.clone,statement.no ? new_no.clone : nil)
779
+
780
+ # Since I do not know whether there is noifs (elsif), I convert it and add it if it is confirmed.
781
+ statement.each_noif do |condition, block|
782
+ if(self.mode == :seq) then
783
+ fm_buckup_if.each_key do |key|
784
+ $fm.fm_par[key] = fm_buckup_if[key]
785
+ end
786
+ end
618
787
 
619
- $fm.rep_sharp[statement.left] = search_refname(statement.left,"#")
788
+ new_noif = block.flatten
789
+ new_statement.add_noif(condition.clone,new_noif.clone)
790
+ end
791
+ # Add the new statement (if statement) created to flat.
792
+ flat.add_statement(new_statement.clone)
620
793
 
621
- $fm.fm_par["#{statement.left.to_verilog}"] = new_statement.left
622
- new_no.add_statement(new_statement.clone)
623
- else
624
- new_no.add_statement(statement.clone)
625
- end
626
- else
627
- new_no.add_statement(statement.clone)
628
- end
794
+ # If statement is Transmit, record the expression in fm_par and add the expression to flat as it is.
795
+ elsif statement.is_a?(Transmit) then
796
+ if(self.mode == :seq) then
797
+ $fm.fm_par["#{statement.left.to_verilog}"] = statement.right.clone
629
798
  end
630
- end
631
- # Rebuild the converted "if" as a new" statement (If)".
632
- new_statement = If.new(statement.condition.clone,new_yes.clone,statement.no ? new_no.clone : nil)
633
- # Just like "no", check if "noifs (elsif)" exists and if there is, take one by one and convert.
634
- # After that, add the converted "noif" to "If".
635
- statement.each_noif do |condition, block|
636
799
 
637
- noif = block.flatten
638
- new_noif = Block.new(noif.mode,"")
800
+ flat.add_statement(statement.clone)
801
+ # If statement is Block, convert it with do_flat and add the returned expression and variable to flat respectively.
639
802
 
640
- noif.each_inner do |inner|
641
- # I read inner, but when I am par, I delete all '.
642
- unless (list.include?(inner.name.to_s)) then
643
- if (noif.mode == :seq) || (inner.name.to_s.include? "#") then
803
+ elsif statement.is_a?(Block) then
804
+ smt = statement.do_flat(self.mode)
805
+ # If smt has inner, check it separately and add it if it's convenient.
806
+ smt.each_inner do |inner|
807
+ if self.mode == :seq then
808
+ unless (list.include?(inner.name.to_s)) then
644
809
  list << inner.name.to_s
645
- new_block.add_inner(inner.clone)
810
+ flat.add_inner(inner.clone)
811
+ end
812
+ else
813
+ unless (list.include?(inner.name.to_s)) then
814
+ if(inner.name.to_s.include? "#") then
815
+ list << inner.name.to_s
816
+ flat.add_inner(inner.clone) # It was new_block. why?
817
+ end
646
818
  end
647
819
  end
648
820
  end
649
-
650
-
651
- noif.each_statement do |statement|
652
- # If statement is Transmit, it is an expression and should be processed.
653
- if statement.is_a?(Transmit) then
654
- # If you add a # to the one with 'on the left side, the shape of the formula will collapse and it will be removed.
655
- unless (res_name(statement.left).name.to_s.include? "'") || noif.mode == :par then
656
-
657
- new_signal = att_signal(statement.left, "#")
658
-
659
- # Double declaration of existing variable can not be done, so it is excluded.
660
- unless (list.include?(new_signal.name.to_s)) then
661
- list << new_signal.name.to_s
662
- new_block.add_inner(new_signal)
663
- end
664
-
665
- new_statement = Transmit.new(search_refname(statement.left,"#"),statement.right.clone)
666
-
667
- $fm.rep_sharp[statement.left] = search_refname(statement.left,"#")
668
-
669
- $fm.fm_par["#{statement.left.to_verilog}"] = new_statement.left
670
- new_noif.add_statement(new_statement.clone)
671
- else
672
- new_noif.add_statement(statement.clone)
673
- end
674
- else
675
- new_noif.add_statement(statement.clone)
821
+ # If it is seq, the expression after conversion is also likely to be used, so record the expression.
822
+ smt.each_statement do |tmt|
823
+ if self.mode == :seq then
824
+ $fm.fm_par["#{tmt.left.to_verilog}"] = tmt.right.clone
676
825
  end
677
- end
826
+ flat.add_statement(tmt.clone)
827
+ end
828
+ end
829
+ end
678
830
 
679
- new_statement.add_noif(condition.clone,new_noif.clone)
831
+ # Overwrite to restore fm_par which was quarantined.
832
+ if(self.mode == :seq) then
833
+ $fm.fm_par.clear()
834
+ fm_buckup.each_key do |key|
835
+ $fm.fm_par[key] = fm_buckup[key]
680
836
  end
837
+ end
681
838
 
682
- new_block.add_statement(new_statement.clone)
683
839
 
684
- $fm.rep_sharp.each_key do |key|
685
- new_smt = Transmit.new(key.clone,$fm.rep_sharp[key].clone)
686
- new_block.add_statement(new_smt.clone)
687
- end
688
- $fm.rep_sharp.clear() # Deactivate rep that has become obsolete.
689
840
 
690
- elsif statement.is_a?(Case) then
691
- if statement.default.is_a?(Block)
692
- new_default = statement.default.flatten
693
- end
841
+ # Since it is a middle tier itself, it performs flat transformation, shifts inner, and returns the result.
842
+ trans = flat.to_conversion(mode)
694
843
 
695
- new_statement = Case.new(statement.value.clone,statement.default ? new_default.clone : nil,[])
696
- statement.each_when do |whens|
697
- new_when_statement = whens.statement.flatten
698
- new_when = When.new(whens.match.clone,new_when_statement.clone)
699
844
 
700
- new_statement.add_when(new_when.clone)
845
+ # Write an expression that assigns an identifier that added # to an identifier that has not added.
846
+ trans.each_statement do |statement|
847
+ replase.add_statement(statement.clone)
848
+ if statement.is_a?(If)
849
+ $fm.rep_sharp.each_key do |key|
850
+ new_statement = Transmit.new(key.clone,$fm.rep_sharp[key].clone)
851
+ replase.add_statement(new_statement.clone)
852
+ end
853
+ $fm.rep_sharp.clear() # Deactivate rep that has become obsolete.
701
854
  end
855
+ end
702
856
 
703
- new_block.add_statement(new_statement)
704
- else
705
- new_block.add_statement(statement.clone)
857
+ # Extract the inner left in flat and add it to replase.
858
+ flat.each_inner do |inner|
859
+ replase.add_inner(inner.clone)
706
860
  end
707
- end
708
- return new_block
709
- end
710
- end
711
861
 
712
- def do_flat(mode = nil)
713
- flat = Block.new(self.mode,"") # Block between lower layers when converting.
714
- trans = Block.new(self.mode,"") # The block used for converting itself.
715
- replase = Block.new(self.mode,"") # block to be used for further conversion in case of if statement.
716
- list = []
717
- rep_list = []
718
-
719
- # If there is a block inside the statement it is not the lowest layer. If there is, it is the lowest layer.
720
- if (self.each_statement.find {|stmnt| stmnt.is_a?(Block)} || (self.each_statement.find {|stmnt| stmnt.is_a?(If)}) || (self.each_statement.find {|stmnt| stmnt.is_a?(Case)}))then
721
- # In the case of seq, the lower layer is par. Isolate fm_par so that it is not crosstalked.
722
- if(self.mode == :seq) then
723
- fm_buckup = $fm.fm_par.clone
724
- $fm.fm_par.clear()
862
+ # Extract the inner left in trans and add it to replase.
863
+ trans.each_inner do |inner|
864
+ replase.add_inner(inner.clone)
865
+ end
725
866
 
726
- new_block = change_branch(self)
867
+ return replase
868
+
869
+ # Processing when there is no block (reaching the bottom layer).
727
870
  else
728
- new_block = self.clone
871
+ # Since it is the lowest layer, it does not smooth but converts itself and returns it.
872
+ flat = self.to_conversion(mode)
873
+ return flat
729
874
  end
875
+ end
730
876
 
731
- # Process for each statement.
732
- new_block.each_statement do |statement|
733
- # If statement is If, convert yes, no, noif and add them to flat.
734
- if statement.is_a?(Case) then
735
- if(self.mode == :seq) then
736
- fm_buckup_if = $fm.fm_par.clone
737
- end
738
-
739
- if statement.default.is_a?(Block)
740
- default = statement.default.flatten
741
- new_default = Block.new(default.mode,"")
742
-
743
- default.each_statement do |statement|
744
- new_default.add_statement(statement.clone)
745
- end
746
- end
747
-
748
-
749
- new_statement = Case.new(statement.value.clone,statement.default ? new_default.clone : nil,[])
750
-
751
- statement.each_when do |whens|
752
- if(self.mode == :seq) then
753
- fm_buckup_if.each_key do |key|
754
- $fm.fm_par[key] = fm_buckup_if[key]
755
- end
756
- end
877
+ def to_conversion(mode = nil, rst = true, rep = true)
878
+ flat = Block.new(mode,"") # Block that stores results.
879
+ new_yes = Block.new(mode,"") # Block containing the new yes.
880
+ new_no = Block.new(mode,"") # Block containing the new no.
881
+ new_noif = Block.new(mode,"") # Block containing the new noif.
882
+ list = []
757
883
 
758
- when_smt = whens.statement.flatten
759
- new_when = When.new(whens.match.clone,when_smt.clone)
760
- new_statement.add_when(new_when.clone)
761
- end
762
- flat.add_statement(new_statement)
763
-
764
- elsif statement.is_a?(If) then
765
- if(self.mode == :seq) then
766
- fm_buckup_if = $fm.fm_par.clone
767
- end
884
+ if rst == false then
885
+ fm_seq_backup = $fm.fm_seq.dup
886
+ end
768
887
 
769
- # Since yes always exist, convert without confirming.
770
- new_yes = statement.yes.flatten
888
+ # The statement is divided (since it is the lowest layer, there is only Transmit).
889
+ self.each_statement do |statement|
890
+ # Various processing is performed depending on the type of Transmit.
891
+ # If the mode of the upper layer = its own mode, it compresses as it is.
771
892
 
772
- # I do not know whether no (else) exists, so convert it if it is confirmed.
773
- if statement.no.is_a? (Block) then
893
+ if(mode == self.mode) then
894
+ new_statement = statement.clone
895
+ # In the case of an If statement, processing of if, else, elsif is performed.
896
+ elsif statement.is_a?(Case) then
774
897
 
775
- if(self.mode == :seq) then
776
- fm_buckup_if.each_key do |key|
777
- $fm.fm_par[key] = fm_buckup_if[key]
778
- end
898
+ if statement.default.is_a?(Block)
899
+ rep_buckup = $fm.rep.dup
900
+ $fm.rep.clear()
901
+ default = statement.default.to_conversion(mode,false,false)
902
+ $fm.rep.clear()
903
+ rep_buckup.each_key do |key|
904
+ $fm.rep[key] = rep_buckup[key]
779
905
  end
780
906
 
781
- new_no = statement.no.flatten
782
- end
783
- # Create a new if statement with converted yes and no.
784
- new_statement = If.new(statement.condition.clone,new_yes.clone,statement.no ? new_no.clone : nil)
907
+ new_default = Block.new(default.mode,"")
785
908
 
786
- # Since I do not know whether there is noifs (elsif), I convert it and add it if it is confirmed.
787
- statement.each_noif do |condition, block|
788
- if(self.mode == :seq) then
789
- fm_buckup_if.each_key do |key|
790
- $fm.fm_par[key] = fm_buckup_if[key]
909
+ default.each_inner do |inner|
910
+ # I read inner, but when I am par, I delete all '.
911
+ unless (list.include?(inner.name.to_s)) then
912
+ if (self.mode == :seq) || (inner.name.to_s.include? "#") then
913
+ list << inner.name.to_s
914
+ flat.add_inner(inner.clone)
915
+ end
791
916
  end
792
917
  end
793
918
 
794
- new_noif = block.flatten
795
- new_statement.add_noif(condition.clone,new_noif.clone)
796
- end
797
- # Add the new statement (if statement) created to flat.
798
- flat.add_statement(new_statement.clone)
919
+ default.each_statement do |statement|
920
+ # If statement is Transmit, it is an expression and should be processed.
921
+ if statement.is_a?(Transmit) then
922
+ # If you add a # to the one with 'on the left side, the shape of the formula will collapse and it will be removed.
923
+ unless (res_name(statement.left).name.to_s.include? "'") || default.mode == :par then
924
+ # Prepare a new signal with the # on the variable on the left side using the att_signal method.
925
+ new_signal = att_signal(statement.left, "#")
926
+ # Check list and add new variables to inner if they do not duplicate.
927
+ unless (list.include?(new_signal.name.to_s)) then
928
+ list << new_signal.name.to_s
929
+ flat.add_inner(new_signal)
930
+ end
799
931
 
800
- # If statement is Transmit, record the expression in fm_par and add the expression to flat as it is.
801
- elsif statement.is_a?(Transmit) then
802
- if(self.mode == :seq) then
803
- $fm.fm_par["#{statement.left.to_verilog}"] = statement.right.clone
804
- end
932
+ new_smt = Transmit.new(search_refname(statement.left,"#"),statement.right.clone)
805
933
 
806
- flat.add_statement(statement.clone)
807
- # If statement is Block, convert it with do_flat and add the returned expression and variable to flat respectively.
934
+ $fm.rep_sharp[statement.left] = search_refname(statement.left,"#")
808
935
 
809
- elsif statement.is_a?(Block) then
810
- smt = statement.do_flat(self.mode)
811
- # If smt has inner, check it separately and add it if it's convenient.
812
- smt.each_inner do |inner|
813
- if self.mode == :seq then
814
- unless (list.include?(inner.name.to_s)) then
815
- list << inner.name.to_s
816
- flat.add_inner(inner.clone)
936
+ $fm.fm_par["#{statement.left.to_verilog}"] = new_smt.left
937
+ new_default.add_statement(new_smt.clone)
938
+ else
939
+ new_default.add_statement(statement.clone)
940
+ end
941
+ else
942
+ new_default.add_statement(statement.clone)
817
943
  end
818
- else
819
- unless (list.include?(inner.name.to_s)) then
820
- if(inner.name.to_s.include? "#") then
821
- list << inner.name.to_s
822
- flat.add_inner(inner.clone) # It was new_block. why?
823
- end
824
- end
825
- end
944
+ end
826
945
  end
827
- # If it is seq, the expression after conversion is also likely to be used, so record the expression.
828
- smt.each_statement do |tmt|
829
- if self.mode == :seq then
830
- $fm.fm_par["#{tmt.left.to_verilog}"] = tmt.right.clone
831
- end
832
- flat.add_statement(tmt.clone)
833
- end
834
- end
835
- end
836
-
837
- # Overwrite to restore fm_par which was quarantined.
838
- if(self.mode == :seq) then
839
- $fm.fm_par.clear()
840
- fm_buckup.each_key do |key|
841
- $fm.fm_par[key] = fm_buckup[key]
842
- end
843
- end
844
-
845
946
 
846
947
 
847
- # Since it is a middle tier itself, it performs flat transformation, shifts inner, and returns the result.
848
- trans = flat.to_conversion(mode)
849
-
948
+ new_statement = Case.new(statement.value.clone,statement.default ? new_default.clone : nil,[])
850
949
 
851
- # Write an expression that assigns an identifier that added # to an identifier that has not added.
852
- trans.each_statement do |statement|
853
- replase.add_statement(statement.clone)
854
- if statement.is_a?(If)
855
- $fm.rep_sharp.each_key do |key|
856
- new_statement = Transmit.new(key.clone,$fm.rep_sharp[key].clone)
857
- replase.add_statement(new_statement.clone)
858
- end
859
- $fm.rep_sharp.clear() # Deactivate rep that has become obsolete.
860
- end
861
- end
950
+ statement.each_when do |whens|
862
951
 
863
- # Extract the inner left in flat and add it to replase.
864
- flat.each_inner do |inner|
865
- replase.add_inner(inner.clone)
866
- end
952
+ rep_buckup = $fm.rep.dup
953
+ $fm.rep.clear()
954
+ when_smt = whens.statement.to_conversion(mode,false,false)
955
+ $fm.rep.clear()
956
+ rep_buckup.each_key do |key|
957
+ $fm.rep[key] = rep_buckup[key]
958
+ end
867
959
 
868
- # Extract the inner left in trans and add it to replase.
869
- trans.each_inner do |inner|
870
- replase.add_inner(inner.clone)
871
- end
960
+ new_when_smt = Block.new(when_smt.mode,"")
872
961
 
873
- return replase
962
+ when_smt.each_statement do |statement|
963
+ # If statement is Transmit, it is an expression and should be processed.
964
+ if statement.is_a?(Transmit) then
965
+ # If you add a # to the one with 'on the left side, the shape of the formula will collapse and it will be removed.
966
+ unless (res_name(statement.left).name.to_s.include? "'") || when_smt.mode == :par then
967
+ # Prepare a new signal with the # on the variable on the left side using the att_signal method.
968
+ new_signal = att_signal(statement.left, "#")
969
+ # Check list and add new variables to inner if they do not duplicate.
970
+ unless (list.include?(new_signal.name.to_s)) then
971
+ list << new_signal.name.to_s
972
+ flat.add_inner(new_signal)
973
+ end
874
974
 
875
- # Processing when there is no block (reaching the bottom layer).
876
- else
877
- # Since it is the lowest layer, it does not smooth but converts itself and returns it.
878
- flat = self.to_conversion(mode)
879
- return flat
880
- end
881
- end
975
+ new_smt = Transmit.new(search_refname(statement.left,"#"),statement.right.clone)
882
976
 
883
- def to_conversion(mode = nil, rst = true, rep = true)
884
- flat = Block.new(mode,"") # Block that stores results.
885
- new_yes = Block.new(mode,"") # Block containing the new yes.
886
- new_no = Block.new(mode,"") # Block containing the new no.
887
- new_noif = Block.new(mode,"") # Block containing the new noif.
888
- list = []
977
+ $fm.rep_sharp[statement.left] = search_refname(statement.left,"#")
889
978
 
890
- if rst == false then
891
- fm_seq_backup = $fm.fm_seq.dup
892
- end
979
+ $fm.fm_par["#{statement.left.to_verilog}"] = new_smt.left
980
+ new_when_smt.add_statement(new_smt.clone)
981
+ else
982
+ new_when_smt.add_statement(statement.clone)
983
+ end
984
+ else
985
+ new_when_smt.add_statement(statement.clone)
986
+ end
987
+ end
893
988
 
894
- # The statement is divided (since it is the lowest layer, there is only Transmit).
895
- self.each_statement do |statement|
896
- # Various processing is performed depending on the type of Transmit.
897
- # If the mode of the upper layer = its own mode, it compresses as it is.
989
+ new_when = When.new(whens.match.clone,new_when_smt.clone)
990
+ new_statement.add_when(new_when.clone)
991
+ end
898
992
 
899
- if(mode == self.mode) then
900
- new_statement = statement.clone
901
- # In the case of an If statement, processing of if, else, elsif is performed.
902
- elsif statement.is_a?(Case) then
993
+ elsif statement.is_a?(If) then
903
994
 
904
- if statement.default.is_a?(Block)
905
995
  rep_buckup = $fm.rep.dup
906
996
  $fm.rep.clear()
907
- default = statement.default.to_conversion(mode,false,false)
997
+ yes = statement.yes.to_conversion(mode, false,false)
908
998
  $fm.rep.clear()
909
999
  rep_buckup.each_key do |key|
910
1000
  $fm.rep[key] = rep_buckup[key]
911
1001
  end
912
1002
 
913
- new_default = Block.new(default.mode,"")
914
-
915
- default.each_inner do |inner|
916
- # I read inner, but when I am par, I delete all '.
1003
+ yes.each_inner do |inner|
917
1004
  unless (list.include?(inner.name.to_s)) then
918
- if (self.mode == :seq) || (inner.name.to_s.include? "#") then
1005
+ if (yes.mode == :seq) || (inner.name.to_s.include? "#") then
919
1006
  list << inner.name.to_s
920
- flat.add_inner(inner.clone)
1007
+ flat.add_inner(inner.clone) # It was new_block. why?
921
1008
  end
922
1009
  end
923
1010
  end
924
1011
 
925
- default.each_statement do |statement|
926
- # If statement is Transmit, it is an expression and should be processed.
927
- if statement.is_a?(Transmit) then
928
- # If you add a # to the one with 'on the left side, the shape of the formula will collapse and it will be removed.
929
- unless (res_name(statement.left).name.to_s.include? "'") || default.mode == :par then
930
- # Prepare a new signal with the # on the variable on the left side using the att_signal method.
931
- new_signal = att_signal(statement.left, "#")
932
- # Check list and add new variables to inner if they do not duplicate.
933
- unless (list.include?(new_signal.name.to_s)) then
934
- list << new_signal.name.to_s
935
- flat.add_inner(new_signal)
936
- end
1012
+ yes.each_statement do |smt|
1013
+ if(yes.mode == :seq) then
1014
+ new_signal = att_signal(smt.left, "#")
937
1015
 
938
- new_smt = Transmit.new(search_refname(statement.left,"#"),statement.right.clone)
1016
+ unless (list.include?(new_signal.name.to_s)) then
1017
+ list << new_signal.name.to_s
1018
+ flat.add_inner(new_signal)
1019
+ end
939
1020
 
940
- $fm.rep_sharp[statement.left] = search_refname(statement.left,"#")
1021
+ yes_statement = Transmit.new(search_refname(smt.left,"#"),smt.right.clone)
941
1022
 
942
- $fm.fm_par["#{statement.left.to_verilog}"] = new_smt.left
943
- new_default.add_statement(new_smt.clone)
944
- else
945
- new_default.add_statement(statement.clone)
946
- end
1023
+ $fm.rep_sharp[statement.left] = search_refname(statement.left,"#")
1024
+
1025
+ $fm.fm_par["#{smt.left.to_verilog}"] = yes_statement.left
1026
+ new_yes.add_statement(yes_statement)
947
1027
  else
948
- new_default.add_statement(statement.clone)
1028
+ new_yes.add_statement(smt.clone)
949
1029
  end
950
- end
951
- end
952
-
953
-
954
- new_statement = Case.new(statement.value.clone,statement.default ? new_default.clone : nil,[])
1030
+ end
955
1031
 
956
- statement.each_when do |whens|
1032
+ if statement.no.is_a? (Block) then
1033
+ rep_buckup = $fm.rep.dup
1034
+ $fm.rep.clear()
1035
+ no = statement.no.to_conversion(mode,false,false)
1036
+ $fm.rep.clear()
1037
+ rep_buckup.each_key do |key|
1038
+ $fm.rep[key] = rep_buckup[key]
1039
+ end
957
1040
 
958
- rep_buckup = $fm.rep.dup
959
- $fm.rep.clear()
960
- when_smt = whens.statement.to_conversion(mode,false,false)
961
- $fm.rep.clear()
962
- rep_buckup.each_key do |key|
963
- $fm.rep[key] = rep_buckup[key]
964
- end
1041
+ no.each_inner do |inner|
1042
+ unless (list.include?(inner.name.to_s)) then
1043
+ if (no.mode == :seq) || (inner.name.to_s.include? "#") then
1044
+ list << inner.name.to_s
1045
+ flat.add_inner(inner.clone) # It was new_block. why?
1046
+ end
1047
+ end
1048
+ end
965
1049
 
966
- new_when_smt = Block.new(when_smt.mode,"")
1050
+ no.each_statement do |smt|
1051
+ if(no.mode == :seq) then
1052
+ new_signal = att_signal(smt.left, "#")
967
1053
 
968
- when_smt.each_statement do |statement|
969
- # If statement is Transmit, it is an expression and should be processed.
970
- if statement.is_a?(Transmit) then
971
- # If you add a # to the one with 'on the left side, the shape of the formula will collapse and it will be removed.
972
- unless (res_name(statement.left).name.to_s.include? "'") || when_smt.mode == :par then
973
- # Prepare a new signal with the # on the variable on the left side using the att_signal method.
974
- new_signal = att_signal(statement.left, "#")
975
- # Check list and add new variables to inner if they do not duplicate.
976
1054
  unless (list.include?(new_signal.name.to_s)) then
977
1055
  list << new_signal.name.to_s
978
1056
  flat.add_inner(new_signal)
979
1057
  end
980
1058
 
981
- new_smt = Transmit.new(search_refname(statement.left,"#"),statement.right.clone)
1059
+ no_statement = Transmit.new(search_refname(smt.left,"#"),smt.right.clone)
982
1060
 
983
1061
  $fm.rep_sharp[statement.left] = search_refname(statement.left,"#")
984
1062
 
985
- $fm.fm_par["#{statement.left.to_verilog}"] = new_smt.left
986
- new_when_smt.add_statement(new_smt.clone)
1063
+ $fm.fm_par["#{smt.left.to_verilog}"] = no_statement.left
1064
+ new_no.add_statement(no_statement)
987
1065
  else
988
- new_when_smt.add_statement(statement.clone)
989
- end
990
- else
991
- new_when_smt.add_statement(statement.clone)
1066
+ new_no.add_statement(smt.clone)
1067
+ end
992
1068
  end
993
1069
  end
994
1070
 
995
- new_when = When.new(whens.match.clone,new_when_smt.clone)
996
- new_statement.add_when(new_when.clone)
997
- end
998
-
999
- elsif statement.is_a?(If) then
1000
-
1001
- rep_buckup = $fm.rep.dup
1002
- $fm.rep.clear()
1003
- yes = statement.yes.to_conversion(mode, false,false)
1004
- $fm.rep.clear()
1005
- rep_buckup.each_key do |key|
1006
- $fm.rep[key] = rep_buckup[key]
1007
- end
1008
-
1009
- yes.each_inner do |inner|
1010
- unless (list.include?(inner.name.to_s)) then
1011
- if (yes.mode == :seq) || (inner.name.to_s.include? "#") then
1012
- list << inner.name.to_s
1013
- flat.add_inner(inner.clone) # It was new_block. why?
1014
- end
1015
- end
1016
- end
1071
+ new_statement = If.new(statement.condition.clone,new_yes.clone,statement.no ? new_no.clone : nil)
1017
1072
 
1018
- yes.each_statement do |smt|
1019
- if(yes.mode == :seq) then
1020
- new_signal = att_signal(smt.left, "#")
1073
+ statement.each_noif do |condition, block|
1074
+ rep_buckup = $fm.rep.dup
1075
+ $fm.rep.clear()
1076
+ noif = block.to_conversion(mode,false,false)
1077
+ $fm.rep.clear()
1078
+ rep_buckup.each_key do |key|
1079
+ $fm.rep[key] = rep_buckup[key]
1080
+ end
1021
1081
 
1022
- unless (list.include?(new_signal.name.to_s)) then
1023
- list << new_signal.name.to_s
1024
- flat.add_inner(new_signal)
1082
+ noif.each_inner do |inner|
1083
+ unless (list.include?(inner.name.to_s)) then
1084
+ if (noif.mode == :seq) || (inner.name.to_s.include? "#") then
1085
+ list << inner.name.to_s
1086
+ flat.add_inner(inner.clone) # It was new_block. why?
1087
+ end
1088
+ end
1025
1089
  end
1026
1090
 
1027
- yes_statement = Transmit.new(search_refname(smt.left,"#"),smt.right.clone)
1091
+ noif.each_statement do |smt|
1092
+ if(noif.mode == :seq) then
1093
+ new_signal = att_signal(smt.left, "#")
1028
1094
 
1029
- $fm.rep_sharp[statement.left] = search_refname(statement.left,"#")
1095
+ unless (list.include?(new_signal.name.to_s)) then
1096
+ list << new_signal.name.to_s
1097
+ flat.add_inner(new_signal)
1098
+ end
1030
1099
 
1031
- $fm.fm_par["#{smt.left.to_verilog}"] = yes_statement.left
1032
- new_yes.add_statement(yes_statement)
1033
- else
1034
- new_yes.add_statement(smt.clone)
1035
- end
1036
- end
1100
+ noif_statement = Transmit.new(search_refname(smt.left,"#"),smt.right.clone)
1037
1101
 
1038
- if statement.no.is_a? (Block) then
1039
- rep_buckup = $fm.rep.dup
1040
- $fm.rep.clear()
1041
- no = statement.no.to_conversion(mode,false,false)
1042
- $fm.rep.clear()
1043
- rep_buckup.each_key do |key|
1044
- $fm.rep[key] = rep_buckup[key]
1045
- end
1102
+ $fm.rep_sharp[statement.left] = search_refname(statement.left,"#")
1046
1103
 
1047
- no.each_inner do |inner|
1048
- unless (list.include?(inner.name.to_s)) then
1049
- if (no.mode == :seq) || (inner.name.to_s.include? "#") then
1050
- list << inner.name.to_s
1051
- flat.add_inner(inner.clone) # It was new_block. why?
1052
- end
1104
+ $fm.fm_par["#{smt.left.to_verilog}"] = noif_statement.left
1105
+ new_noif.add_statement(no_statement)
1106
+ else
1107
+ new_noif.add_statement(smt.clone)
1108
+ end
1053
1109
  end
1054
- end
1055
1110
 
1056
- no.each_statement do |smt|
1057
- if(no.mode == :seq) then
1058
- new_signal = att_signal(smt.left, "#")
1111
+ new_statement.add_noif(condition.clone,new_noif.clone)
1112
+ end
1059
1113
 
1060
- unless (list.include?(new_signal.name.to_s)) then
1061
- list << new_signal.name.to_s
1062
- flat.add_inner(new_signal)
1114
+ # Otherwise, it is necessary to process par-> seq or seq-> par.
1115
+ else
1116
+ # Make sure the right side is a formula (Binary).
1117
+ if statement.right.is_a?(Binary) then
1118
+ # Check the right side and the left side, and if they are variables, check the corresponding expressions and replace them.
1119
+ # If it is not a variable, it calls the method to be searched.
1120
+ if statement.right.left.is_a? (Ref) then
1121
+ if (mode == :par && self.mode == :seq) && $fm.fm_seq.has_key?(statement.right.left.to_verilog) then
1122
+ statement_left = $fm.fm_seq["#{statement.right.left.to_verilog}"]
1123
+ elsif (mode == :seq && self.mode == :par) && $fm.fm_par.has_key?(statement.right.left.to_verilog) then
1124
+ statement_left = $fm.fm_par["#{statement.right.left.to_verilog}"]
1125
+ else
1126
+ statement_left = statement.right.left.clone
1063
1127
  end
1064
-
1065
- no_statement = Transmit.new(search_refname(smt.left,"#"),smt.right.clone)
1066
-
1067
- $fm.rep_sharp[statement.left] = search_refname(statement.left,"#")
1068
-
1069
- $fm.fm_par["#{smt.left.to_verilog}"] = no_statement.left
1070
- new_no.add_statement(no_statement)
1128
+ elsif statement.right.left.is_a? (Binary) then
1129
+ statement_left = statement.right.left.to_change(self.mode)
1071
1130
  else
1072
- new_no.add_statement(smt.clone)
1131
+ statement_left = statement.right.left.clone
1073
1132
  end
1074
- end
1075
- end
1076
-
1077
- new_statement = If.new(statement.condition.clone,new_yes.clone,statement.no ? new_no.clone : nil)
1078
-
1079
- statement.each_noif do |condition, block|
1080
- rep_buckup = $fm.rep.dup
1081
- $fm.rep.clear()
1082
- noif = block.to_conversion(mode,false,false)
1083
- $fm.rep.clear()
1084
- rep_buckup.each_key do |key|
1085
- $fm.rep[key] = rep_buckup[key]
1086
- end
1087
1133
 
1088
- noif.each_inner do |inner|
1089
- unless (list.include?(inner.name.to_s)) then
1090
- if (noif.mode == :seq) || (inner.name.to_s.include? "#") then
1091
- list << inner.name.to_s
1092
- flat.add_inner(inner.clone) # It was new_block. why?
1093
- end
1134
+ if statement.right.right.is_a? (Ref) then
1135
+ if (mode == :par && self.mode == :seq) && $fm.fm_seq.has_key?(statement.right.right.to_verilog) then
1136
+ statement_right = $fm.fm_seq["#{statement.right.right.to_verilog}"]
1137
+ elsif (mode == :seq && self.mode == :par) && $fm.fm_par.has_key?(statement.right.right.to_verilog) then
1138
+ statement_right = $fm.fm_par["#{statement.right.right.to_verilog}"]
1139
+ else
1140
+ statement_right = statement.right.right.clone
1141
+ end
1142
+ elsif statement.right.right.is_a? (Binary) then
1143
+ statement_right = statement.right.right.to_change(self.mode)
1144
+ else
1145
+ statement_right = statement.right.right.clone
1146
+ end
1147
+ new_right = Binary.new(statement.right.type,statement.right.operator,statement_left.clone,statement_right.clone)
1148
+ # Confirm whether it is a variable.
1149
+ elsif statement.right.is_a?(Ref) then
1150
+ if (mode == :par && self.mode == :seq) && $fm.fm_seq.has_key?(statement.right.to_verilog) then
1151
+ new_right = $fm.fm_seq["#{statement.right.to_verilog}"].clone
1152
+ elsif (mode == :seq && self.mode == :par) && $fm.fm_par.has_key?(statement.right.to_verilog) then
1153
+ new_right = $fm.fm_par["#{statement.right.to_verilog}"].clone
1154
+ else
1155
+ new_right = statement.right.clone
1094
1156
  end
1157
+ # Because it is not a number. Put it in as it is.
1158
+ else
1159
+ new_right = statement.right.clone
1095
1160
  end
1096
1161
 
1097
- noif.each_statement do |smt|
1098
- if(noif.mode == :seq) then
1099
- new_signal = att_signal(smt.left, "#")
1162
+ if (mode == :par && self.mode == :seq) then
1163
+ # Dock the existing left hand side and the replaced right hand side to create a new expression.
1164
+ # Record the expression after conversion to hash to continue seq-> par.
1165
+ new_statement = Transmit.new(statement.left.clone,new_right)
1166
+ $fm.fm_seq["#{statement.left.to_verilog}"] = new_right
1167
+ elsif (mode == :seq && self.mode == :par) && (rep) then
1168
+ unless (res_name(statement.left).name.to_s.include? "#")
1169
+ # Search the variable on the left side and give 'to the name.
1170
+ new_signal = att_signal(statement.left,"'")
1100
1171
 
1101
1172
  unless (list.include?(new_signal.name.to_s)) then
1102
1173
  list << new_signal.name.to_s
1103
1174
  flat.add_inner(new_signal)
1104
1175
  end
1105
1176
 
1106
- noif_statement = Transmit.new(search_refname(smt.left,"#"),smt.right.clone)
1107
-
1108
- $fm.rep_sharp[statement.left] = search_refname(statement.left,"#")
1177
+ new_statement = Transmit.new(search_refname(statement.left,"'"),new_right)
1109
1178
 
1110
- $fm.fm_par["#{smt.left.to_verilog}"] = noif_statement.left
1111
- new_noif.add_statement(no_statement)
1112
- else
1113
- new_noif.add_statement(smt.clone)
1179
+ $fm.rep[statement.left] = new_statement
1114
1180
  end
1115
- end
1116
-
1117
- new_statement.add_noif(condition.clone,new_noif.clone)
1118
- end
1119
-
1120
- # Otherwise, it is necessary to process par-> seq or seq-> par.
1121
- else
1122
- # Make sure the right side is a formula (Binary).
1123
- if statement.right.is_a?(Binary) then
1124
- # Check the right side and the left side, and if they are variables, check the corresponding expressions and replace them.
1125
- # If it is not a variable, it calls the method to be searched.
1126
- if statement.right.left.is_a? (Ref) then
1127
- if (mode == :par && self.mode == :seq) && $fm.fm_seq.has_key?(statement.right.left.to_verilog) then
1128
- statement_left = $fm.fm_seq["#{statement.right.left.to_verilog}"]
1129
- elsif (mode == :seq && self.mode == :par) && $fm.fm_par.has_key?(statement.right.left.to_verilog) then
1130
- statement_left = $fm.fm_par["#{statement.right.left.to_verilog}"]
1131
- else
1132
- statement_left = statement.right.left.clone
1133
- end
1134
- elsif statement.right.left.is_a? (Binary) then
1135
- statement_left = statement.right.left.to_change(self.mode)
1136
- else
1137
- statement_left = statement.right.left.clone
1138
- end
1139
-
1140
- if statement.right.right.is_a? (Ref) then
1141
- if (mode == :par && self.mode == :seq) && $fm.fm_seq.has_key?(statement.right.right.to_verilog) then
1142
- statement_right = $fm.fm_seq["#{statement.right.right.to_verilog}"]
1143
- elsif (mode == :seq && self.mode == :par) && $fm.fm_par.has_key?(statement.right.right.to_verilog) then
1144
- statement_right = $fm.fm_par["#{statement.right.right.to_verilog}"]
1145
- else
1146
- statement_right = statement.right.right.clone
1147
- end
1148
- elsif statement.right.right.is_a? (Binary) then
1149
- statement_right = statement.right.right.to_change(self.mode)
1150
- else
1151
- statement_right = statement.right.right.clone
1152
- end
1153
- new_right = Binary.new(statement.right.type,statement.right.operator,statement_left.clone,statement_right.clone)
1154
- # Confirm whether it is a variable.
1155
- elsif statement.right.is_a?(Ref) then
1156
- if (mode == :par && self.mode == :seq) && $fm.fm_seq.has_key?(statement.right.to_verilog) then
1157
- new_right = $fm.fm_seq["#{statement.right.to_verilog}"].clone
1158
- elsif (mode == :seq && self.mode == :par) && $fm.fm_par.has_key?(statement.right.to_verilog) then
1159
- new_right = $fm.fm_par["#{statement.right.to_verilog}"].clone
1160
1181
  else
1161
- new_right = statement.right.clone
1162
- end
1163
- # Because it is not a number. Put it in as it is.
1164
- else
1165
- new_right = statement.right.clone
1182
+ new_statement = Transmit.new(statement.left.clone,new_right)
1183
+ end
1166
1184
  end
1185
+ # Add the converted statement to flat (because par -> par or seq -> seq will be added until then).
1167
1186
 
1168
- if (mode == :par && self.mode == :seq) then
1169
- # Dock the existing left hand side and the replaced right hand side to create a new expression.
1170
- # Record the expression after conversion to hash to continue seq-> par.
1171
- new_statement = Transmit.new(statement.left.clone,new_right)
1172
- $fm.fm_seq["#{statement.left.to_verilog}"] = new_right
1173
- elsif (mode == :seq && self.mode == :par) && (rep) then
1174
- unless (res_name(statement.left).name.to_s.include? "#")
1175
- # Search the variable on the left side and give 'to the name.
1176
- new_signal = att_signal(statement.left,"'")
1177
-
1178
- unless (list.include?(new_signal.name.to_s)) then
1179
- list << new_signal.name.to_s
1180
- flat.add_inner(new_signal)
1181
- end
1182
-
1183
- new_statement = Transmit.new(search_refname(statement.left,"'"),new_right)
1184
-
1185
- $fm.rep[statement.left] = new_statement
1187
+ if new_statement.is_a?(Transmit) then
1188
+ unless (mode == :par && self.mode == :seq) && (res_name(new_statement.left).name.to_s.include? "'") then
1189
+ flat.add_statement(new_statement.clone)
1186
1190
  end
1187
1191
  else
1188
- new_statement = Transmit.new(statement.left.clone,new_right)
1189
- end
1190
- end
1191
- # Add the converted statement to flat (because par -> par or seq -> seq will be added until then).
1192
-
1193
- if new_statement.is_a?(Transmit) then
1194
- unless (mode == :par && self.mode == :seq) && (res_name(new_statement.left).name.to_s.include? "'") then
1195
1192
  flat.add_statement(new_statement.clone)
1196
1193
  end
1197
- else
1198
- flat.add_statement(new_statement.clone)
1199
- end
1200
1194
 
1201
- if (rep)
1202
- $fm.rep_sharp.each_key do |key|
1203
- new_smt = Transmit.new(key.clone,$fm.rep_sharp[key].clone)
1204
- flat.add_statement(new_smt.clone)
1195
+ if (rep)
1196
+ $fm.rep_sharp.each_key do |key|
1197
+ new_smt = Transmit.new(key.clone,$fm.rep_sharp[key].clone)
1198
+ flat.add_statement(new_smt.clone)
1199
+ end
1200
+ $fm.rep_sharp.clear() # Deactivate rep that has become obsolete.
1205
1201
  end
1206
- $fm.rep_sharp.clear() # Deactivate rep that has become obsolete.
1207
1202
  end
1208
- end
1209
- # Add an expression after paragraph based on rep.
1210
- # A complement expression like x = x '.
1211
- $fm.rep.each_key do |key|
1212
- new_statement = Transmit.new(key.clone,$fm.rep[key].left.clone)
1213
- flat.add_statement(new_statement.clone)
1214
- end
1215
- $fm.rep.clear() # Deactivate rep that has become obsolete.
1203
+ # Add an expression after paragraph based on rep.
1204
+ # A complement expression like x = x '.
1205
+ $fm.rep.each_key do |key|
1206
+ new_statement = Transmit.new(key.clone,$fm.rep[key].left.clone)
1207
+ flat.add_statement(new_statement.clone)
1208
+ end
1209
+ $fm.rep.clear() # Deactivate rep that has become obsolete.
1216
1210
 
1217
1211
 
1218
- # Since seq -> par is the end, fm_par is deleted.
1219
- if (mode == :par && self.mode == :seq) then
1220
- $fm.fm_seq.clear()
1221
- end
1212
+ # Since seq -> par is the end, fm_par is deleted.
1213
+ if (mode == :par && self.mode == :seq) then
1214
+ $fm.fm_seq.clear()
1215
+ end
1222
1216
 
1223
- # In case of if statement (when rst == false) you can not convert no or else if you delete the contents of fm_seq.
1224
- # Therefore, in this case restore the backup to restore.
1225
- # This means that it is necessary to erase fm_seq once obtained in the if statement once.
1226
- if(rst == false) then
1227
- $fm.fm_seq.clear()
1228
- fm_seq_backup.each_key do |key|
1229
- $fm.fm_seq[key] = fm_seq_backup[key]
1217
+ # In case of if statement (when rst == false) you can not convert no or else if you delete the contents of fm_seq.
1218
+ # Therefore, in this case restore the backup to restore.
1219
+ # This means that it is necessary to erase fm_seq once obtained in the if statement once.
1220
+ if(rst == false) then
1221
+ $fm.fm_seq.clear()
1222
+ fm_seq_backup.each_key do |key|
1223
+ $fm.fm_seq[key] = fm_seq_backup[key]
1224
+ end
1230
1225
  end
1231
- end
1232
1226
 
1233
- return flat # Return flat finished checking.
1234
- end
1227
+ return flat # Return flat finished checking.
1228
+ end
1235
1229
 
1236
1230
 
1237
- def change_branch(block)
1238
- flat = Block.new(self.mode,"") # Store the expression until if is found.
1239
- trans = Block.new(self.mode,"") # A block that stores the expression after if is found.
1240
- new_block = Block.new(self.mode,"") # Block storing each converted expression.
1231
+ def change_branch(block)
1232
+ flat = Block.new(self.mode,"") # Store the expression until if is found.
1233
+ trans = Block.new(self.mode,"") # A block that stores the expression after if is found.
1234
+ new_block = Block.new(self.mode,"") # Block storing each converted expression.
1241
1235
 
1242
- has_branch = false # It is true if there is an if in the block.
1243
- more_has_branch = false # It is true if there are two or more if in the block.
1236
+ has_branch = false # It is true if there is an if in the block.
1237
+ more_has_branch = false # It is true if there are two or more if in the block.
1244
1238
 
1245
- # Search each expression for if.
1246
- block.each_statement do |statement|
1247
- if (has_branch)
1248
- trans.add_statement(statement.clone)
1249
- if statement.is_a?(If) || statement.is_a?(Case) then
1250
- more_has_branch = true
1251
- end
1252
- else
1253
- if statement.is_a?(If) || statement.is_a?(Case) then
1254
- flat.add_statement(statement.clone)
1255
- has_branch = true
1239
+ # Search each expression for if.
1240
+ block.each_statement do |statement|
1241
+ if (has_branch)
1242
+ trans.add_statement(statement.clone)
1243
+ if statement.is_a?(If) || statement.is_a?(Case) then
1244
+ more_has_branch = true
1245
+ end
1256
1246
  else
1257
- flat.add_statement(statement.clone)
1247
+ if statement.is_a?(If) || statement.is_a?(Case) then
1248
+ flat.add_statement(statement.clone)
1249
+ has_branch = true
1250
+ else
1251
+ flat.add_statement(statement.clone)
1252
+ end
1258
1253
  end
1259
1254
  end
1260
- end
1261
1255
 
1262
- # If there are two or more if, recursively process if.
1263
- if(more_has_branch) then
1264
- conversion_block = change_branch(trans)
1265
- else
1266
- conversion_block = trans.clone
1267
- end
1268
-
1269
- # Store "trans" contents for "if" and "case" in "flat".
1270
- flat.each_statement do |statement|
1271
- # Since case statements include defaulu and when, we store the expressions saved in each case.
1272
- if statement.is_a?(Case) then
1273
- if statement.default.is_a?(Block)
1274
- new_default = statement.default.clone
1275
- conversion_block.each_statement do |smt|
1276
- new_default.add_statement(smt.clone)
1277
- end
1278
- end
1256
+ # If there are two or more if, recursively process if.
1257
+ if(more_has_branch) then
1258
+ conversion_block = change_branch(trans)
1259
+ else
1260
+ conversion_block = trans.clone
1261
+ end
1279
1262
 
1280
- new_statement = Case.new(statement.value.clone,statement.default ? new_default.clone : nil,[])
1263
+ # Store "trans" contents for "if" and "case" in "flat".
1264
+ flat.each_statement do |statement|
1265
+ # Since case statements include defaulu and when, we store the expressions saved in each case.
1266
+ if statement.is_a?(Case) then
1267
+ if statement.default.is_a?(Block)
1268
+ new_default = statement.default.clone
1269
+ conversion_block.each_statement do |smt|
1270
+ new_default.add_statement(smt.clone)
1271
+ end
1272
+ end
1281
1273
 
1282
- statement.each_when do |whens|
1283
- new_when = whens.clone
1274
+ new_statement = Case.new(statement.value.clone,statement.default ? new_default.clone : nil,[])
1284
1275
 
1285
- conversion_block.each_statement do |smt|
1286
- new_when.statement.add_statement(smt.clone)
1287
- end
1288
- new_statement.add_when(new_when.clone)
1289
- end
1276
+ statement.each_when do |whens|
1277
+ new_when = whens.clone
1290
1278
 
1291
- new_block.add_statement(new_statement.clone)
1292
- # Because there are yes, no and noifs in the if statement, store the expression saved in each.
1293
- elsif statement.is_a?(If) then
1294
- new_yes = statement.yes.clone
1295
- conversion_block.each_statement do |smt|
1296
- new_yes.add_statement(smt.clone)
1297
- end
1279
+ conversion_block.each_statement do |smt|
1280
+ new_when.statement.add_statement(smt.clone)
1281
+ end
1282
+ new_statement.add_when(new_when.clone)
1283
+ end
1298
1284
 
1299
- if statement.no.is_a? (Block) then
1300
- new_no = statement.no.clone
1285
+ new_block.add_statement(new_statement.clone)
1286
+ # Because there are yes, no and noifs in the if statement, store the expression saved in each.
1287
+ elsif statement.is_a?(If) then
1288
+ new_yes = statement.yes.clone
1301
1289
  conversion_block.each_statement do |smt|
1302
- new_no.add_statement(smt.clone)
1290
+ new_yes.add_statement(smt.clone)
1291
+ end
1292
+
1293
+ if statement.no.is_a? (Block) then
1294
+ new_no = statement.no.clone
1295
+ conversion_block.each_statement do |smt|
1296
+ new_no.add_statement(smt.clone)
1297
+ end
1303
1298
  end
1304
- end
1305
1299
 
1306
- # Make new if with converted yes and no.
1307
- new_statement = If.new(statement.condition.clone,new_yes.clone,statement.no ? new_no.clone : nil)
1300
+ # Make new if with converted yes and no.
1301
+ new_statement = If.new(statement.condition.clone,new_yes.clone,statement.no ? new_no.clone : nil)
1308
1302
 
1309
1303
 
1310
- statement.each_noif do |condition, block|
1311
- new_noif = block.clone
1312
- conversion_block.each_statement do |smt|
1313
- new_noif.add_statement(smt.clone)
1304
+ statement.each_noif do |condition, block|
1305
+ new_noif = block.clone
1306
+ conversion_block.each_statement do |smt|
1307
+ new_noif.add_statement(smt.clone)
1308
+ end
1309
+ new_statement.add_noif(condition.clone,new_noif.clone)
1314
1310
  end
1315
- new_statement.add_noif(condition.clone,new_noif.clone)
1311
+ # Add the new statement (if) created to flat.
1312
+ new_block.add_statement(new_statement.clone)
1313
+ else
1314
+ new_block.add_statement(statement.clone)
1316
1315
  end
1317
- # Add the new statement (if) created to flat.
1318
- new_block.add_statement(new_statement.clone)
1319
- else
1320
- new_block.add_statement(statement.clone)
1321
1316
  end
1322
- end
1323
1317
 
1324
- return new_block # Return block after conversion.
1325
- end
1326
-
1327
- # Generate a signal for the variable to which "'" or "#" is added.
1328
- def att_signal(left,att = "'")
1329
- this_name = res_name(left)
1330
- new_name = RefName.new(this_name.type, this_name.ref.clone, this_name.name.to_s + att)
1331
- new_signal = SignalI.new(new_name.name,new_name.type)
1318
+ return new_block # Return block after conversion.
1319
+ end
1332
1320
 
1333
- return new_signal
1334
- end
1321
+ # Generate a signal for the variable to which "'" or "#" is added.
1322
+ def att_signal(left,att = "'")
1323
+ this_name = res_name(left)
1324
+ new_name = RefName.new(this_name.type, this_name.ref.clone, this_name.name.to_s + att)
1325
+ new_signal = SignalI.new(new_name.name,new_name.type)
1335
1326
 
1336
- # A method that takes a variable from the sent left side and adds "att".
1337
- def att_sharp(left,att = "'")
1338
- #if left.is_a?(RefName) then
1339
- new_left = search_refname(left, att)
1340
- #elsif left.is_a?(RefIndex) then
1341
- # new_ref = search_refname(left, att)
1342
- # new_left = RefIndex.new(left.type, new_ref, left.index.clone)
1343
- #elsif left.is_a?(RefRange) then
1344
- # new_ref = search_refname(left, att)
1345
- # my_range = left.range
1346
- # new_left = RefRange.new(left.type, new_ref, my_range.first.clone..my_range.last.clone)
1347
- #end
1348
-
1349
- # Add new signal to hash.
1350
- # if(att == "#") then
1351
- # $fm.rep_sharp[left] = new_left
1352
- # end
1353
- return new_left
1354
- end
1327
+ return new_signal
1328
+ end
1355
1329
 
1330
+ # A method that takes a variable from the sent left side and adds "att".
1331
+ def att_sharp(left,att = "'")
1332
+ new_left = search_refname(left, att)
1356
1333
 
1357
- # Recursively search, add "att" to RefName and return.
1358
- def search_refname(me,att = "'")
1359
- if me.is_a? (RefName) then
1360
- return RefName.new(me.type, me.ref.clone, me.name.to_s + att)
1361
- elsif me.ref.is_a? (RefName) then
1362
- return RefName.new(me.ref.type, me.ref.ref.clone, me.ref.name.to_s + att)
1363
- elsif me.ref.is_a? (RefIndex) then
1364
- return RefIndex.new(me.ref.type, search_refname(me.ref), me.ref.index.clone)
1365
- elsif me.ref.is_a? (RefRange) then
1366
- my_range = me.ref.range
1367
- return RefRange.new(me.ref.type, search_refname(me.ref), my_range.first.clone..my_range.last.clone)
1334
+ return new_left
1368
1335
  end
1369
- end
1370
1336
 
1371
- # Recursively search, return Refname.
1372
- def res_name(me)
1373
- if me.is_a? (RefName) then
1374
- return me
1375
- else
1376
- if me.ref.is_a? (RefName) then
1377
- return RefName.new(me.ref.type, me.ref.ref.clone, me.ref.name.to_s)
1337
+
1338
+ # Recursively search, add "att" to RefName and return.
1339
+ def search_refname(me,att = "'")
1340
+ if me.is_a? (RefName) then
1341
+ return RefName.new(me.type, me.ref.clone, me.name.to_s + att)
1342
+ elsif me.ref.is_a? (RefName) then
1343
+ return RefName.new(me.ref.type, me.ref.ref.clone, me.ref.name.to_s + att)
1378
1344
  elsif me.ref.is_a? (RefIndex) then
1379
- return res_name(me.ref)
1345
+ return RefIndex.new(me.ref.type, search_refname(me.ref), me.ref.index.clone)
1380
1346
  elsif me.ref.is_a? (RefRange) then
1381
- return res_name(me.ref)
1347
+ my_range = me.ref.range
1348
+ return RefRange.new(me.ref.type, search_refname(me.ref), my_range.first.clone..my_range.last.clone)
1382
1349
  end
1383
1350
  end
1384
- end
1385
- end
1386
1351
 
1387
- # Used to display variable names.
1388
- # Enhance RefName with generation of verilog code.
1389
- class RefName
1390
- # Converts the system to Verilog code using +renamer+ for producing Verilog-compatible names.
1391
- def to_verilog
1392
- # return "#{name_to_verilog(self.name)}"
1393
- vname = name_to_verilog(self.name)
1394
- self.properties[:verilog_name] = vname
1395
- return "#{vname}"
1352
+ # Recursively search, return Refname.
1353
+ def res_name(me)
1354
+ if me.is_a? (RefName) then
1355
+ return me
1356
+ else
1357
+ if me.ref.is_a? (RefName) then
1358
+ return RefName.new(me.ref.type, me.ref.ref.clone, me.ref.name.to_s)
1359
+ elsif me.ref.is_a? (RefIndex) then
1360
+ return res_name(me.ref)
1361
+ elsif me.ref.is_a? (RefRange) then
1362
+ return res_name(me.ref)
1363
+ end
1364
+ end
1365
+ end
1396
1366
  end
1397
1367
 
1398
- # Used for instantiation (emergency procedure).
1399
- def to_another_verilog
1400
- return "_#{self.name.to_s}"
1401
- end
1368
+ # Used to display variable names.
1369
+ # Enhance RefName with generation of verilog code.
1370
+ class RefName
1371
+ # Converts the system to Verilog code using +renamer+ for producing Verilog-compatible names.
1372
+ def to_verilog
1373
+ vname = name_to_verilog(self.name)
1374
+ self.properties[:verilog_name] = vname
1375
+ return "#{vname}"
1376
+ end
1402
1377
 
1403
- def ancestor(my)
1404
- if my.parent.parent.respond_to? (:mode) then
1405
- return ancestor(my.parent)
1406
- else
1407
- return "#{my.parent.mode.to_s}#{my.mode.to_s}"
1378
+ # Used for instantiation (emergency procedure).
1379
+ def to_another_verilog
1380
+ return "_#{self.name.to_s}"
1381
+ end
1382
+
1383
+ def ancestor(my)
1384
+ if my.parent.parent.respond_to? (:mode) then
1385
+ return ancestor(my.parent)
1386
+ else
1387
+ return "#{my.parent.mode.to_s}#{my.mode.to_s}"
1388
+ end
1408
1389
  end
1409
1390
  end
1410
- end
1411
1391
 
1412
- # Used to convert an array.
1413
- # Enhance RefIndex with generation of verilog code.
1414
- class RefIndex
1415
- # Converts the system to Verilog code.
1416
- def to_verilog
1417
- return "#{self.ref.to_verilog}[#{self.index.to_verilog}]"
1392
+ # Used to convert an array.
1393
+ # Enhance RefIndex with generation of verilog code.
1394
+ class RefIndex
1395
+ # Converts the system to Verilog code.
1396
+ def to_verilog
1397
+ return "#{self.ref.to_verilog}[#{self.index.to_verilog}]"
1398
+ end
1418
1399
  end
1419
- end
1420
1400
 
1421
1401
 
1422
- # Used to indicate the number of bits.
1423
- # Enhance TypeVector with generation of verilog code.
1424
- class TypeVector
1425
- # Converts the system to Verilog code.
1426
- def to_verilog
1427
- # if self.base.name.to_s != "bit"
1428
- if VERILOG_BASE_TYPES.include?(self.base.name.to_s)
1429
- return " #{self.base.name.to_s}[#{self.range.first}:#{self.range.last}]"
1402
+ # Used to indicate the number of bits.
1403
+ # Enhance TypeVector with generation of verilog code.
1404
+ class TypeVector
1405
+ # Converts the system to Verilog code.
1406
+ def to_verilog
1407
+ # if self.base.name.to_s != "bit"
1408
+ if VERILOG_BASE_TYPES.include?(self.base.name.to_s)
1409
+ return " #{self.base.name.to_s}[#{self.range.first}:#{self.range.last}]"
1410
+ end
1411
+ return " [#{self.range.first}:#{self.range.last}]"
1430
1412
  end
1431
- return " [#{self.range.first}:#{self.range.last}]"
1432
1413
  end
1433
- end
1434
1414
 
1435
- # Necessary for displaying bit width (eg, specify and assign).
1436
- class RefRange
1437
- # Converts the system to Verilog code.
1438
- def to_verilog(unknown = false)
1439
- return "#{self.ref.to_verilog}[#{self.range.first.to_getrange}:#{self.range.last.to_getrange}]"
1415
+ # Necessary for displaying bit width (eg, specify and assign).
1416
+ class RefRange
1417
+ # Converts the system to Verilog code.
1418
+ def to_verilog(unknown = false)
1419
+ return "#{self.ref.to_verilog}[#{self.range.first.to_getrange}:#{self.range.last.to_getrange}]"
1420
+ end
1440
1421
  end
1441
- end
1442
1422
 
1443
- # Use it when collecting references.
1444
- class RefConcat
1445
- def to_verilog
1446
- ref = self.each_ref.to_a
1423
+ # Use it when collecting references.
1424
+ class RefConcat
1425
+ def to_verilog
1426
+ ref = self.each_ref.to_a
1447
1427
 
1448
- result = "{"
1449
- ref[0..-2].each do |ref|
1450
- result << "#{ref.to_verilog},"
1451
- end
1452
- result << "#{ref.last.to_verilog}}"
1428
+ result = "{"
1429
+ ref[0..-2].each do |ref|
1430
+ result << "#{ref.to_verilog},"
1431
+ end
1432
+ result << "#{ref.last.to_verilog}}"
1453
1433
 
1454
- return result
1434
+ return result
1435
+ end
1455
1436
  end
1456
- end
1457
1437
 
1458
- # Used to output bitstring.
1459
- # Enhance HDLRuby with generation of verilog code.
1460
- class HDLRuby::BitString
1461
- # Converts the system to Verilog code.
1462
- def to_verilog
1463
- return "#{self.to_s}"
1438
+ # Used to output bitstring.
1439
+ # Enhance HDLRuby with generation of verilog code.
1440
+ class HDLRuby::BitString
1441
+ # Converts the system to Verilog code.
1442
+ def to_verilog
1443
+ return "#{self.to_s}"
1444
+ end
1464
1445
  end
1465
- end
1466
1446
 
1467
- # Used for connection using choice.
1468
- # Enhance Select with generation of verilog code.
1469
- class Select
1470
- # Converts the system to Verilog code.
1471
- def to_verilog
1472
- # Outputs the first and second choices (choice (0) and choice (1)).
1473
- return "#{self.select.to_verilog} == 1 #{self.operator} #{self.get_choice(0).to_verilog} : #{self.get_choice(1).to_verilog}"
1447
+ # Used for connection using choice.
1448
+ # Enhance Select with generation of verilog code.
1449
+ class Select
1450
+ # Converts the system to Verilog code.
1451
+ def to_verilog
1452
+ # Outputs the first and second choices (choice (0) and choice (1)).
1453
+ return "#{self.select.to_verilog} == 1 #{self.operator} #{self.get_choice(0).to_verilog} : #{self.get_choice(1).to_verilog}"
1454
+ end
1474
1455
  end
1475
- end
1476
1456
 
1477
- # Used to output numbers.
1478
- # Enhance Value with generation of verilog code.
1479
- class Value
1480
- # Converts the system to Verilog code.
1481
- # If it is bit, it is b, and if it is int, it is represented by d. (Example: 4'b0000, 32'd1)
1482
- def to_verilog(unknown = nil)
1483
- if self.type.base.name.to_s == "bit"
1484
- return "#{self.type.range.first + 1}'b#{self.content.to_verilog}"
1485
- elsif self.type.name.to_s == "integer"
1486
- str = self.content.to_verilog
1487
- if str[0] == "-" then
1488
- # Negative value.
1489
- return "-#{self.type.range.first + 1}'d#{str[1..-1]}"
1490
- else
1491
- return "#{self.type.range.first + 1}'d#{str}"
1457
+ # Used to output numbers.
1458
+ # Enhance Value with generation of verilog code.
1459
+ class Value
1460
+ # Converts the system to Verilog code.
1461
+ # If it is bit, it is b, and if it is int, it is represented by d. (Example: 4'b0000, 32'd1)
1462
+ def to_verilog(unknown = nil)
1463
+ if self.type.base.name.to_s == "bit"
1464
+ return "#{self.type.range.first + 1}'b#{self.content.to_verilog}"
1465
+ elsif self.type.name.to_s == "integer"
1466
+ str = self.content.to_verilog
1467
+ if str[0] == "-" then
1468
+ # Negative value.
1469
+ return "-#{self.type.range.first + 1}'d#{str[1..-1]}"
1470
+ else
1471
+ return "#{self.type.range.first + 1}'d#{str}"
1472
+ end
1492
1473
  end
1474
+ return "#{self.type.range.first + 1}'b#{self.content.to_verilog}"
1475
+ end
1476
+ # How to use when simply obtaining the width
1477
+ def to_getrange
1478
+ return "#{self.content.to_verilog}"
1493
1479
  end
1494
- return "#{self.type.range.first + 1}'b#{self.content.to_verilog}"
1495
- end
1496
- # How to use when simply obtaining the width
1497
- def to_getrange
1498
- return "#{self.content.to_verilog}"
1499
1480
  end
1500
- end
1501
1481
 
1502
1482
 
1503
- # Used to transrate if.
1504
- # Enhance If with generation of verilog code.
1505
- class If
1506
- # # Converts the system to Verilog code.
1507
- # def to_verilog(mode = nil)
1508
- # Converts to Verilog code, checking adding 'spc' spaces at the begining
1509
- # of each line.
1510
- def to_verilog(spc = 3)
1483
+ # Used to transrate if.
1484
+ # Enhance If with generation of verilog code.
1485
+ class If
1486
+ # # Converts the system to Verilog code.
1487
+ # def to_verilog(mode = nil)
1488
+ # Converts to Verilog code, checking adding 'spc' spaces at the begining
1489
+ # of each line.
1490
+ def to_verilog(spc = 3)
1511
1491
 
1512
- $blocking = false
1492
+ $blocking = false
1513
1493
 
1514
- # if ($space_count == 0) then
1515
- # result = " " * ($space_count) # Indented based on space_count.
1516
- # else
1517
- # result = ""
1518
- # end
1519
- # $space_count += 1 # Add count to be used for indentation.
1520
- result = " " * spc # Indented based on space_count.
1494
+ result = " " * spc # Indented based on space_count.
1521
1495
 
1522
- # result << "if (#{self.condition.to_verilog}) begin\n"
1523
- result << "if (#{self.condition.to_verilog}) "
1496
+ result << "if (#{self.condition.to_verilog}) "
1524
1497
 
1525
1498
 
1526
- # Check if there is yes (if) and output yes or less.
1527
- if self.respond_to? (:yes)
1528
- # self.yes.each_statement do |statement|
1529
- # result << "#{" " * $space_count} #{statement.to_verilog(mode)}"
1530
- # end
1531
- # result << "#{" " * $space_count} end\n"
1532
- result << self.yes.to_verilog(spc)
1533
- end
1499
+ # Check if there is yes (if) and output yes or less.
1500
+ if self.respond_to? (:yes)
1501
+ result << self.yes.to_verilog(spc)
1502
+ end
1534
1503
 
1535
- # If noif (else if) exists, it outputs it.
1536
- # Since noif is directly under, respond_to is unnecessary.
1537
- self.each_noif do |condition, block|
1538
- # result << "#{" " * $space_count} else if (#{condition.to_verilog}) begin\n"
1539
- result << "\n#{" "*spc}else if (#{condition.to_verilog}) "
1540
- # block.each_statement do |statement|
1541
- # result << "#{" " * $space_count} #{statement.to_verilog(mode)}"
1542
- # end
1543
- # result << "#{" "* $space_count} end\n"
1544
- result << block.to_verilog(spc)
1545
- end
1504
+ # If noif (else if) exists, it outputs it.
1505
+ # Since noif is directly under, respond_to is unnecessary.
1506
+ self.each_noif do |condition, block|
1507
+ result << "\n#{" "*spc}else if (#{condition.to_verilog}) "
1508
+ result << block.to_verilog(spc)
1509
+ end
1546
1510
 
1547
- # Check if there is no (else) and output no or less.
1548
- if self.no.respond_to?(:mode)
1549
- # result << "#{" " * $space_count} else begin\n"
1550
- result << "\n#{" " * spc}else "
1551
- # self.no.each_statement do |statement|
1552
- # result << "#{" " * $space_count} #{statement.to_verilog(mode)}"
1553
- # end
1554
- # result << "#{" " * $space_count} end\n"
1555
- result << self.no.to_verilog(spc)
1556
- end
1511
+ # Check if there is no (else) and output no or less.
1512
+ if self.no.respond_to?(:mode)
1513
+ result << "\n#{" " * spc}else "
1514
+ result << self.no.to_verilog(spc)
1515
+ end
1557
1516
 
1558
- # $space_count -= 1 # Since the output ends, reduce the count.
1559
- return result
1517
+ return result
1518
+ end
1560
1519
  end
1561
- end
1562
1520
 
1563
- # Used to translate case
1564
- class Case
1565
- # def to_verilog(mode = nil)
1566
- #
1567
- # Converts to Verilog code, checking if variables are register
1568
- # or wire adding 'spc' spaces at the begining of each line.
1569
- def to_verilog(spc = 3)
1570
-
1571
- # if ($space_count == 0) then
1572
- # result = " " * ($space_count) # Indented based on space_count.
1573
- # else
1574
- # result = ""
1575
- # end
1576
- # $space_count += 1 # Add count to be used for indentation.
1577
- result = " " * spc # Indented based on space_count.
1578
-
1579
- result = ""
1580
- result << "case(#{self.value.to_verilog})\n"
1581
-
1582
- # n the case statement, each branch is partitioned by when. Process each time when.
1583
- self.each_when do |whens|
1584
- # Reads and stores the numbers and expressions stored in when.
1585
- # result << " " + " " *$space_count + "#{whens.match.to_verilog}: "
1586
- result << " " * (spc+3) + "#{whens.match.to_verilog}: "
1587
-
1588
- # if whens.statement.each_statement.count > 1 then
1589
- # result << "begin\n"
1590
- # whens.statement.each_statement do |statement|
1591
- # result << " "+ " " *$space_count +"#{statement.to_verilog}"
1592
- # end
1593
- # result << " " + " " *$space_count + "end\n"
1594
- # elsif whens.statement.each_statement.count == 1 then
1595
- # whens.statement.each_statement do |statement|
1596
- # result << "#{statement.to_verilog}"
1597
- # end
1598
- # else
1599
- # # Empty statement case.
1600
- # result << "\n"
1601
- # end
1602
- if whens.statement.each_statement.count >= 1 then
1603
- result << whens.statement.to_verilog(spc+3)
1604
- else
1605
- result << "\n"
1521
+ # Used to translate case
1522
+ class Case
1523
+ # def to_verilog(mode = nil)
1524
+ #
1525
+ # Converts to Verilog code, checking if variables are register
1526
+ # or wire adding 'spc' spaces at the begining of each line.
1527
+ def to_verilog(spc = 3)
1528
+
1529
+ result = " " * spc # Indented based on space_count.
1530
+
1531
+ result = ""
1532
+ result << "case(#{self.value.to_verilog})\n"
1533
+
1534
+ # n the case statement, each branch is partitioned by when. Process each time when.
1535
+ self.each_when do |whens|
1536
+ # Reads and stores the numbers and expressions stored in when.
1537
+ result << " " * (spc+3) + "#{whens.match.to_verilog}: "
1538
+
1539
+ if whens.statement.each_statement.count >= 1 then
1540
+ result << whens.statement.to_verilog(spc+3)
1541
+ else
1542
+ result << "\n"
1543
+ end
1606
1544
  end
1607
- end
1608
- # # The default part is stored in default instead of when. Reads and processes in the same way as when.
1609
- # if self.default then
1610
- # if self.default.each_statement.count > 1 then
1611
- # result << " " + " " *$space_count + "default: begin\n"
1612
- # self.default.each_statement do |statement|
1613
- # result << " " + " " *$space_count + "#{statement.to_verilog}"
1614
- # end
1615
- # result << " end\n"
1616
- # elsif self.default.each_statement.count == 1 then
1617
- # result << " " + " " *$space_count + "default: "
1618
- # self.default.each_statement do |statement|
1619
- # result << "#{statement.to_verilog}"
1620
- # end
1621
- # end
1622
- # end
1623
- if self.default then
1624
- if self.default.each_statement.count >= 1 then
1625
- result << self.default.each_statement.to_verilog(spc+3)
1626
- else
1627
- result << "\n"
1545
+ if self.default then
1546
+ if self.default.each_statement.count >= 1 then
1547
+ result << self.default.each_statement.map do |stmnt|
1548
+ stmnt.to_verilog(spc+3)
1549
+ end.join("\n")
1550
+ else
1551
+ result << "\n"
1552
+ end
1628
1553
  end
1629
- end
1630
- # result << " " + " " *$space_count + "endcase\n" # Conclusion.
1631
- result << " " * spc + "endcase\n" # Conclusion.
1632
-
1633
- # $space_count -= 1 # Since the output ends, reduce the count.
1634
- return result # Return case after translation.
1635
- end
1636
- end
1554
+ result << " " * spc + "endcase\n" # Conclusion.
1637
1555
 
1638
- # Translate expression of combination circuit.
1639
- # Enhance Connection with generation of verilog code.
1640
- class Connection
1641
- # Converts the system to Verilog code.
1642
-
1643
- # Method used for array.
1644
- def array_connection(left,right)
1645
- expression = right.each_expression.to_a
1646
- result = ""
1647
- expression[0..-2].each do |expression|
1648
- result << " assign #{left.to_verilog}[#{expression.content.to_s}] = #{expression.to_verilog};\n"
1556
+ return result # Return case after translation.
1649
1557
  end
1650
- result << " assign #{left.to_verilog}[#{expression.last.content.to_s}] = #{expression.last.to_verilog};\n"
1651
- return result
1652
1558
  end
1653
1559
 
1654
- def to_verilog
1655
- # Decide whether to assign to array by if.
1656
- # NOTICE: Now array assignment is done trough constant initialization, will be treated later.
1657
- # if self.right.respond_to? (:each_expression)
1658
- # array_connection(self.left,self.right);
1659
- # else
1660
- cnt = 0 # Use count.
1661
- bit = -2 # Used to determine the bit width. Since there are 0 and default, -2.
1662
-
1663
- # Measure the number of choices on the right side (case statement if it is 3 or more).
1664
- if self.right.respond_to? (:each_choice)
1665
- choice = self.right.each_choice.to_a
1666
- choice.each do |choice|
1667
- bit += 1
1560
+ # Translate expression of combination circuit.
1561
+ # Enhance Connection with generation of verilog code.
1562
+ class Connection
1563
+ # Converts the system to Verilog code.
1564
+
1565
+ # Method used for array.
1566
+ def array_connection(left,right)
1567
+ expression = right.each_expression.to_a
1568
+ result = ""
1569
+ expression[0..-2].each do |expression|
1570
+ result << " assign #{left.to_verilog}[#{expression.content.to_s}] = #{expression.to_verilog};\n"
1668
1571
  end
1572
+ result << " assign #{left.to_verilog}[#{expression.last.content.to_s}] = #{expression.last.to_verilog};\n"
1573
+ return result
1669
1574
  end
1670
1575
 
1671
- # Three or more choices.
1672
- if (bit > 2)
1673
- # The bit width is obtained by converting the bit into a binary number and obtaining the size.
1674
- bit = bit.to_s(2).size
1675
-
1676
- # Create a case statement.
1677
- result = " begin\n"
1678
- result << " case(#{self.right.select.to_verilog})\n"
1679
- # Output other than the last one in order.
1680
- choice[0..-2].each do |choice|
1681
- result << " #{bit}'#{cnt}: #{self.left.to_verilog} = #{choice.to_verilog}\n"
1682
- cnt += 1
1576
+ def to_verilog
1577
+ # Decide whether to assign to array by if.
1578
+ # NOTICE: Now array assignment is done trough constant initialization, will be treated later.
1579
+ # if self.right.respond_to? (:each_expression)
1580
+ # array_connection(self.left,self.right);
1581
+ # else
1582
+ cnt = 0 # Use count.
1583
+ bit = -2 # Used to determine the bit width. Since there are 0 and default, -2.
1584
+
1585
+ # Measure the number of choices on the right side (case statement if it is 3 or more).
1586
+ if self.right.respond_to? (:each_choice)
1587
+ choice = self.right.each_choice.to_a
1588
+ choice.each do |choice|
1589
+ bit += 1
1590
+ end
1683
1591
  end
1684
- # At the end, it becomes default because it needs default.
1685
- result << " default: #{self.left.to_verilog} = #{choice.last.to_verilog}\n"
1686
- result << " endcase\n"
1687
- result << " end\n"
1688
- return result
1689
- end
1690
1592
 
1691
- # It is not a case so call it normally.
1692
- return " assign #{self.left.to_verilog} = #{self.right.to_verilog};\n"
1693
- # end
1694
- end
1695
- end
1593
+ # Three or more choices.
1594
+ if (bit > 2)
1595
+ # The bit width is obtained by converting the bit into a binary number and obtaining the size.
1596
+ bit = bit.to_s(2).size
1597
+
1598
+ # Create a case statement.
1599
+ result = " begin\n"
1600
+ result << " case(#{self.right.select.to_verilog})\n"
1601
+ # Output other than the last one in order.
1602
+ choice[0..-2].each do |choice|
1603
+ result << " #{bit}'#{cnt}: #{self.left.to_verilog} = #{choice.to_verilog}\n"
1604
+ cnt += 1
1605
+ end
1606
+ # At the end, it becomes default because it needs default.
1607
+ result << " default: #{self.left.to_verilog} = #{choice.last.to_verilog}\n"
1608
+ result << " endcase\n"
1609
+ result << " end\n"
1610
+ return result
1611
+ end
1696
1612
 
1697
- # It could be used for instantiation.
1698
- class RefThis
1699
- def to_another_verilog
1700
- return ""
1613
+ # It is not a case so call it normally.
1614
+ return " assign #{self.left.to_verilog} = #{self.right.to_verilog};\n"
1615
+ # end
1616
+ end
1701
1617
  end
1702
- end
1703
1618
 
1704
- # Used when using "~" for expressions.
1705
- class Unary
1706
- # Converts the system to Verilog code.
1707
- def to_verilog
1708
- return "#{self.operator[0]}#{self.child.to_verilog}"
1619
+ # It could be used for instantiation.
1620
+ class RefThis
1621
+ def to_another_verilog
1622
+ return ""
1623
+ end
1709
1624
  end
1710
- end
1711
1625
 
1712
- # Used when casting expressions.
1713
- class Cast
1714
- # Converts the system to Verilog code.
1715
- # NOTE: the cast is rounded up size bit-width cast is not supported
1716
- # by traditional verilog.
1717
- def to_verilog
1718
- # return "#{self.type.to_verilog}'(#{self.child.to_verilog})"
1719
- if self.child.is_a?(Value) then
1720
- return self.child.to_verilog
1626
+ # Used when using "~" for expressions.
1627
+ class Unary
1628
+ # Converts the system to Verilog code.
1629
+ def to_verilog
1630
+ return "#{self.operator[0]}#{self.child.to_verilog}"
1721
1631
  end
1722
- # Get the type widths, used for computing extensions or truncations.
1723
- cw = self.child.type.width
1724
- sw = self.type.width
1725
- if self.type.signed? then
1726
- # return "$signed(#{self.child.to_verilog})"
1727
- if (sw>cw) then
1728
- # Need to sign extend.
1729
- return "$signed({{#{sw-cw}{#{self.child.to_verilog}[#{cw-1}]}}," +
1730
- "#{self.child.to_verilog}})"
1731
- elsif (sw<cw) then
1732
- # Need to truncate
1733
- return "$signed(#{self.child.to_verilog}[#{sw-1}:0])"
1734
- else
1735
- # Only enforce signed.
1736
- return "$signed(#{self.child.to_verilog})"
1632
+ end
1633
+
1634
+ # Used when casting expressions.
1635
+ class Cast
1636
+ # Converts the system to Verilog code.
1637
+ # NOTE: the cast is rounded up size bit-width cast is not supported
1638
+ # by traditional verilog.
1639
+ def to_verilog
1640
+ if self.child.is_a?(Value) then
1641
+ return self.child.to_verilog
1737
1642
  end
1738
- else
1739
- # return "$unsigned(#{self.child.to_verilog})"
1740
- if (sw>cw) then
1741
- # Need to extend.
1742
- return "$unsigned({{#{sw-cw}{1'b0}},#{self.child.to_verilog}})"
1743
- elsif (sw<cw) then
1744
- # Need to truncate
1745
- return "$unsigned(#{self.child.to_verilog}[#{sw-1}:0])"
1643
+ # Get the type widths, used for computing extensions or truncations.
1644
+ cw = self.child.type.width
1645
+ sw = self.type.width
1646
+ if self.type.signed? then
1647
+ if (sw>cw) then
1648
+ # Need to sign extend.
1649
+ return "$signed({{#{sw-cw}{#{self.child.to_verilog}[#{cw-1}]}}," +
1650
+ "#{self.child.to_verilog}})"
1651
+ elsif (sw<cw) then
1652
+ # Need to truncate
1653
+ return "$signed(#{self.child.to_verilog}[#{sw-1}:0])"
1654
+ else
1655
+ # Only enforce signed.
1656
+ return "$signed(#{self.child.to_verilog})"
1657
+ end
1746
1658
  else
1747
- # Only enforce signed.
1748
- return "$unsigned(#{self.child.to_verilog})"
1659
+ if (sw>cw) then
1660
+ # Need to extend.
1661
+ return "$unsigned({{#{sw-cw}{1'b0}},#{self.child.to_verilog}})"
1662
+ elsif (sw<cw) then
1663
+ # Need to truncate
1664
+ return "$unsigned(#{self.child.to_verilog}[#{sw-1}:0])"
1665
+ else
1666
+ # Only enforce signed.
1667
+ return "$unsigned(#{self.child.to_verilog})"
1668
+ end
1749
1669
  end
1750
1670
  end
1751
1671
  end
1752
- end
1753
1672
 
1754
- # For declaring variables.
1755
- # Enhance SignalI with generation of verilog code.
1756
- class SignalI
1757
- # Converts the system to Verilog code.
1758
- def to_verilog
1759
- # Convert unusable characters and return them.
1760
- # return "#{name_to_verilog(self.name)}"
1761
- vname = name_to_verilog(self.name)
1762
- self.properties[:verilog_name] = vname
1763
- return "#{vname}"
1673
+ # For declaring variables.
1674
+ # Enhance SignalI with generation of verilog code.
1675
+ class SignalI
1676
+ # Converts the system to Verilog code.
1677
+ def to_verilog
1678
+ # Convert unusable characters and return them.
1679
+ vname = name_to_verilog(self.name)
1680
+ self.properties[:verilog_name] = vname
1681
+ return "#{vname}"
1682
+ end
1764
1683
  end
1765
- end
1766
1684
 
1767
- # If it is signed, it outputs signed.
1768
- # Enhance Type with generation of verilog code.
1769
- class Type
1770
- # Converts the type to Verilog code.
1771
- def to_verilog
1772
- return self.name == :signed ? "#{self.name.to_s} " : ""
1685
+ # If it is signed, it outputs signed.
1686
+ # Enhance Type with generation of verilog code.
1687
+ class Type
1688
+ # Converts the type to Verilog code.
1689
+ def to_verilog
1690
+ return self.name == :signed ? "#{self.name.to_s} " : ""
1691
+ end
1773
1692
  end
1774
- end
1775
1693
 
1776
- # Replace type by refered type.
1777
- class TypeDef
1778
- # Converts the type to verilog code.
1779
- def to_verilog
1780
- return self.def.to_verilog
1694
+ # Replace type by refered type.
1695
+ class TypeDef
1696
+ # Converts the type to verilog code.
1697
+ def to_verilog
1698
+ return self.def.to_verilog
1699
+ end
1781
1700
  end
1782
- end
1783
1701
 
1784
- # Use it when collecting.
1785
- class Concat
1786
- def to_verilog
1787
- expression = self.each_expression.to_a
1702
+ # Use it when collecting.
1703
+ class Concat
1704
+ def to_verilog
1705
+ expression = self.each_expression.to_a
1788
1706
 
1789
- result = "{"
1790
- expression[0..-2].each do |expression|
1791
- result << "#{expression.to_verilog},"
1792
- end
1793
- result << "#{expression.last.to_verilog}}"
1707
+ result = "{"
1708
+ expression[0..-2].each do |expression|
1709
+ result << "#{expression.to_verilog},"
1710
+ end
1711
+ result << "#{expression.last.to_verilog}}"
1794
1712
 
1795
- return result
1713
+ return result
1714
+ end
1796
1715
  end
1797
- end
1798
1716
 
1799
- # Look at the unit of time, convert the time to ps and output it.
1800
- # One of two people, TimeWait and Delay.
1801
- class TimeWait
1802
- # def to_verilog(mode=nil)
1803
- def to_verilog(spc = 3)
1804
- return (" " * spc) + self.delay.to_verilog + "\n"
1717
+ # Look at the unit of time, convert the time to ps and output it.
1718
+ # One of two people, TimeWait and Delay.
1719
+ class TimeWait
1720
+ def to_verilog(spc = 3)
1721
+ return (" " * spc) + self.delay.to_verilog + "\n"
1722
+ end
1805
1723
  end
1806
- end
1807
- class Delay
1808
- def to_verilog
1809
- time = self.value.to_s
1810
- if(self.unit.to_s == "ps") then
1811
- return "##{time};"
1812
- elsif(self.unit.to_s == "ns")
1813
- return "##{time}000;"
1814
- elsif(self.unit.to_s == "us")
1815
- return "##{time}000000;"
1816
- elsif(self.unit.to_s == "ms")
1817
- return "##{time}000000000;"
1818
- elsif(self.unit.to_s == "s")
1819
- return "##{time}000000000000;"
1724
+ class Delay
1725
+ def to_verilog
1726
+ time = self.value.to_s
1727
+ if(self.unit.to_s == "ps") then
1728
+ return "##{time};"
1729
+ elsif(self.unit.to_s == "ns")
1730
+ return "##{time}000;"
1731
+ elsif(self.unit.to_s == "us")
1732
+ return "##{time}000000;"
1733
+ elsif(self.unit.to_s == "ms")
1734
+ return "##{time}000000000;"
1735
+ elsif(self.unit.to_s == "s")
1736
+ return "##{time}000000000000;"
1737
+ end
1820
1738
  end
1821
1739
  end
1822
- end
1823
1740
 
1824
- # Those who disappeared.
1825
- #class SystemI
1826
- #class TypeTuple
1827
- #class Event
1828
-
1829
- # Enhance SystemT with generation of verilog code.
1830
- class SystemT
1831
-
1832
- ## Tells if a connection is actually a port connection.
1833
- def port_output_connection?(connection)
1834
- return self.each_systemI.find do |systemI|
1835
- if connection.right.is_a?(RefName) &&
1836
- connection.right.ref.is_a?(RefName) &&
1837
- systemI.name == connection.right.ref.name
1838
- puts "port_connection for right=#{connection.right.name} and systemI=#{systemI.name}"
1839
- true
1840
- else
1841
- false
1741
+ # Those who disappeared.
1742
+ #class SystemI
1743
+ #class TypeTuple
1744
+ #class Event
1745
+
1746
+ # Enhance SystemT with generation of verilog code.
1747
+ class SystemT
1748
+
1749
+ ## Tells if a connection is actually a port connection.
1750
+ def port_output_connection?(connection)
1751
+ return self.each_systemI.find do |systemI|
1752
+ if connection.right.is_a?(RefName) &&
1753
+ connection.right.ref.is_a?(RefName) &&
1754
+ systemI.name == connection.right.ref.name
1755
+ puts "port_connection for right=#{connection.right.name} and systemI=#{systemI.name}"
1756
+ true
1757
+ else
1758
+ false
1759
+ end
1842
1760
  end
1843
1761
  end
1844
- end
1845
1762
 
1846
- ## Tells if an expression is a reference to port +systemI.signal+.
1847
- def port_assign?(expr, systemI, signal)
1848
- return expr.is_a?(RefName) && expr.name == signal.name &&
1849
- expr.ref.is_a?(RefName) && expr.ref.name == systemI.name
1850
- end
1763
+ ## Tells if an expression is a reference to port +systemI.signal+.
1764
+ def port_assign?(expr, systemI, signal)
1765
+ return expr.is_a?(RefName) && expr.name == signal.name &&
1766
+ expr.ref.is_a?(RefName) && expr.ref.name == systemI.name
1767
+ end
1851
1768
 
1852
- ## Extracts the assignments to port +systemI.signal+ and returns
1853
- # the resulting reference to a port wire.
1854
- #
1855
- # NOTE: assumes to_upper_space! and with_port! has been called.
1856
- def extract_port_assign!(systemI,signal)
1857
- # Extract the assignment.
1858
- assign = nil
1859
- self.each_connection.to_a.each do |connection|
1860
- if self.port_assign?(connection.left,systemI,signal) then
1861
- # The left is the port.
1862
- # Delete the connection.
1863
- self.scope.delete_connection!(connection)
1864
- # And return a copy of the right.
1865
- return connection.right.clone
1866
- elsif self.port_assign?(connection.right,systemI,signal) then
1867
- # The right is the port.
1868
- # Delete the connection.
1869
- self.scope.delete_connection!(connection)
1870
- # And return a copy of the left.
1871
- return connection.left.clone
1769
+ ## Extracts the assignments to port +systemI.signal+ and returns
1770
+ # the resulting reference to a port wire.
1771
+ #
1772
+ # NOTE: assumes to_upper_space! and with_port! has been called.
1773
+ def extract_port_assign!(systemI,signal)
1774
+ # Extract the assignment.
1775
+ assign = nil
1776
+ self.each_connection.to_a.each do |connection|
1777
+ if self.port_assign?(connection.left,systemI,signal) then
1778
+ # The left is the port.
1779
+ # Delete the connection.
1780
+ self.scope.delete_connection!(connection)
1781
+ # And return a copy of the right.
1782
+ return connection.right.clone
1783
+ elsif self.port_assign?(connection.right,systemI,signal) then
1784
+ # The right is the port.
1785
+ # Delete the connection.
1786
+ self.scope.delete_connection!(connection)
1787
+ # And return a copy of the left.
1788
+ return connection.left.clone
1789
+ end
1872
1790
  end
1791
+ # No port found, nothing to do
1792
+ return nil
1873
1793
  end
1874
- # No port found, nothing to do
1875
- return nil
1876
- end
1877
1794
 
1878
1795
 
1879
1796
 
1880
- # Converts the system to Verilog code.
1881
- def to_verilog
1882
- # Detect the registers
1883
- # regs = []
1884
- HDLRuby::Low::VERILOG_REGS.clear
1885
- # The left values.
1886
- self.each_behavior do |behavior|
1887
- # behavior.block.each_statement do |statement|
1888
- # regs << statement.left.to_verilog if statement.is_a?(Transmit)
1889
- # end
1890
- behavior.each_block_deep do |block|
1891
- block.each_statement do |statement|
1892
- if statement.is_a?(Transmit)
1893
- HDLRuby::Low::VERILOG_REGS << statement.left.to_verilog
1797
+ # Converts the system to Verilog code.
1798
+ def to_verilog
1799
+ # Detect the registers
1800
+ HDLRuby::Low::VERILOG_REGS.clear
1801
+ # The left values.
1802
+ self.each_behavior do |behavior|
1803
+ behavior.each_block_deep do |block|
1804
+ block.each_statement do |statement|
1805
+ if statement.is_a?(Transmit)
1806
+ HDLRuby::Low::VERILOG_REGS << statement.left.to_verilog
1807
+ end
1894
1808
  end
1895
1809
  end
1896
1810
  end
1897
- end
1898
- # # puts "regs has clk?: #{regs.include?("clk")}"
1899
- # # puts "for system #{self.name}"
1900
- # # Remove the left values of connection, they do not count.
1901
- # self.scope.each_connection do |connection|
1902
- # # Skip port connections.
1903
- # next if !self.port_output_connection?(connection)
1904
- # # puts "Not counting left in connection: #{connection.to_verilog}"
1905
- # # puts "i.e.: #{connection.left.to_verilog}"
1906
- # regs.delete(connection.left.to_verilog)
1907
- # end
1908
- # # puts "Now regs has clk?: #{regs.include?("clk")}"
1909
- # And the initialized signals.
1910
- self.each_output do |output|
1911
- # regs << output.to_verilog if output.value
1912
- HDLRuby::Low::VERILOG_REGS << output.to_verilog if output.value
1913
- end
1914
- self.each_inner do |inner|
1915
- # regs << inner.to_verilog if inner.value
1916
- HDLRuby::Low::VERILOG_REGS << inner.to_verilog if inner.value
1917
- end
1918
- # And the array types signals.
1919
- self.each_signal do |sig|
1920
- # # regs << sig.to_verilog if sig.type.is_a?(TypeVector) && sig.type.base.is_a?(TypeVector)
1921
- # regs << sig.to_verilog if sig.type.vector? && sig.type.base.vector?
1922
- if sig.type.vector? && sig.type.base.vector? then
1923
- HDLRuby::Low::VERILOG_REGS << sig.to_verilog
1811
+ # And the initialized signals.
1812
+ self.each_output do |output|
1813
+ # regs << output.to_verilog if output.value
1814
+ HDLRuby::Low::VERILOG_REGS << output.to_verilog if output.value
1924
1815
  end
1925
- end
1926
- self.each_inner do |sig|
1927
- # # regs << sig.to_verilog if sig.type.is_a?(TypeVector) && sig.type.base.is_a?(TypeVector)
1928
- # regs << sig.to_verilog if sig.type.vector? && sig.type.base.vector?
1929
- if sig.type.vector? && sig.type.base.vector? then
1930
- HDLRuby::Low::VERILOG_REGS << sig.to_verilog
1816
+ self.each_inner do |inner|
1817
+ # regs << inner.to_verilog if inner.value
1818
+ HDLRuby::Low::VERILOG_REGS << inner.to_verilog if inner.value
1819
+ end
1820
+ # And the array types signals.
1821
+ self.each_signal do |sig|
1822
+ if sig.type.vector? && sig.type.base.vector? then
1823
+ HDLRuby::Low::VERILOG_REGS << sig.to_verilog
1824
+ end
1825
+ end
1826
+ self.each_inner do |sig|
1827
+ if sig.type.vector? && sig.type.base.vector? then
1828
+ HDLRuby::Low::VERILOG_REGS << sig.to_verilog
1829
+ end
1931
1830
  end
1932
- end
1933
-
1934
- # Code generation
1935
- inputs = 0
1936
- outputs = 0
1937
- inout = 0
1938
1831
 
1939
- inputs = self.each_input.to_a
1940
- outputs = self.each_output.to_a
1941
- inout = self.each_inout.to_a
1832
+ # Code generation
1833
+ inputs = 0
1834
+ outputs = 0
1835
+ inout = 0
1942
1836
 
1943
- # Spelling necessary for simulation.
1944
- code = "`timescale 1ps/1ps\n\n"
1837
+ inputs = self.each_input.to_a
1838
+ outputs = self.each_output.to_a
1839
+ inout = self.each_inout.to_a
1945
1840
 
1946
- # # Output the module name.
1947
- # code << "module #{name_to_verilog(self.name)}("
1841
+ # Spelling necessary for simulation.
1842
+ code = "`timescale 1ps/1ps\n\n"
1948
1843
 
1949
- vname = name_to_verilog(self.name)
1950
- self.properties[:verilog_name] = vname
1951
- # Output the module name.
1952
- code << "module #{vname}("
1844
+ vname = name_to_verilog(self.name)
1845
+ self.properties[:verilog_name] = vname
1846
+ # Output the module name.
1847
+ code << "module #{vname}("
1953
1848
 
1954
- # Output the last two to the input.
1955
- inputs[0..-2].each do |input|
1956
- code << " #{input.to_verilog},"
1957
- end
1958
- # When only input is used, it is necessary to close (), so it branches with if.
1959
- if outputs.empty? && inout.empty? then
1960
- # code << " #{inputs.last.to_verilog} ); \n" unless inputs.empty?
1961
- if (inputs.empty?)
1962
- code << " ); \n"
1849
+ # Output the last two to the input.
1850
+ inputs[0..-2].each do |input|
1851
+ code << " #{input.to_verilog},"
1852
+ end
1853
+ # When only input is used, it is necessary to close (), so it branches with if.
1854
+ if outputs.empty? && inout.empty? then
1855
+ if (inputs.empty?)
1856
+ code << " ); \n"
1857
+ end
1858
+ else
1859
+ code << " #{inputs.last.to_verilog}," unless inputs.empty?
1963
1860
  end
1964
- else
1965
- code << " #{inputs.last.to_verilog}," unless inputs.empty?
1966
- end
1967
-
1968
- # Output the last two to the output.
1969
- outputs[0..-2].each do |output|
1970
- code << " #{output.to_verilog},"
1971
- end
1972
- # When only input and output are used, it is necessary to close (), so it branches with if.
1973
- if inout.empty? then
1974
- code << " #{outputs.last.to_verilog} ); \n" unless outputs.empty?
1975
- else
1976
- code << " #{outputs.last.to_verilog}," unless outputs.empty?
1977
- end
1978
1861
 
1979
- # Output the last two to the inout.
1980
- inout[0..-2].each do |inout|
1981
- code << " #{inout.to_verilog},"
1982
- end
1983
- # There is no comma as it is the last one
1984
- code << " #{inout.last.to_verilog} ); \n" unless inout.empty?
1985
-
1986
- # Declare "input"
1987
- self.each_input do |input|
1988
- if input.type.respond_to? (:each_type) then
1989
- $vector_reg = "#{input.to_verilog}"
1990
- $vector_cnt = 0
1991
- input.type.each_type do |type|
1992
- code << "input #{type.to_verilog} #{$vector_reg}:#{$vector_cnt};\n"
1993
- $vector_cnt += 1
1994
- end
1862
+ # Output the last two to the output.
1863
+ outputs[0..-2].each do |output|
1864
+ code << " #{output.to_verilog},"
1865
+ end
1866
+ # When only input and output are used, it is necessary to close (), so it branches with if.
1867
+ if inout.empty? then
1868
+ code << " #{outputs.last.to_verilog} ); \n" unless outputs.empty?
1995
1869
  else
1996
- code << " input#{input.type.to_verilog} #{input.to_verilog};\n"
1870
+ code << " #{outputs.last.to_verilog}," unless outputs.empty?
1871
+ end
1872
+
1873
+ # Output the last two to the inout.
1874
+ inout[0..-2].each do |inout|
1875
+ code << " #{inout.to_verilog},"
1876
+ end
1877
+ # There is no comma as it is the last one
1878
+ code << " #{inout.last.to_verilog} ); \n" unless inout.empty?
1879
+
1880
+ # Declare "input"
1881
+ self.each_input do |input|
1882
+ if input.type.respond_to? (:each_type) then
1883
+ $vector_reg = "#{input.to_verilog}"
1884
+ $vector_cnt = 0
1885
+ input.type.each_type do |type|
1886
+ code << "input #{type.to_verilog} #{$vector_reg}:#{$vector_cnt};\n"
1887
+ $vector_cnt += 1
1888
+ end
1889
+ else
1890
+ code << " input#{input.type.to_verilog} #{input.to_verilog};\n"
1891
+ end
1997
1892
  end
1998
- end
1999
1893
 
2000
- # Declare "output"
2001
- self.each_output do |output|
2002
- if output.type.respond_to? (:each_type) then
2003
- $vector_reg = "#{output.to_verilog}"
2004
- $vector_cnt = 0
2005
- output.type.each_type do |type|
2006
- # if regs.include?(type.name) then
2007
- if HDLRuby::Low::VERILOG_REGS.include?(type.name) then
1894
+ # Declare "output"
1895
+ self.each_output do |output|
1896
+ if output.type.respond_to? (:each_type) then
1897
+ $vector_reg = "#{output.to_verilog}"
1898
+ $vector_cnt = 0
1899
+ output.type.each_type do |type|
1900
+ # if regs.include?(type.name) then
1901
+ if HDLRuby::Low::VERILOG_REGS.include?(type.name) then
1902
+ code << " output reg"
1903
+ else
1904
+ code << " output"
1905
+ end
1906
+ code << "#{type.to_verilog} #{$vector_reg}:#{$vector_cnt}"
1907
+ if output.value then
1908
+ # There is an initial value.
1909
+ code << " = #{output.value.to_verilog}"
1910
+ end
1911
+ code << ";\n"
1912
+ $vector_cnt += 1
1913
+ end
1914
+ else
1915
+ if HDLRuby::Low::VERILOG_REGS.include?(output.to_verilog) then
2008
1916
  code << " output reg"
2009
1917
  else
2010
1918
  code << " output"
2011
1919
  end
2012
- # code << "#{type.to_verilog} #{$vector_reg}:#{$vector_cnt};\n"
2013
- code << "#{type.to_verilog} #{$vector_reg}:#{$vector_cnt}"
1920
+ code << "#{output.type.to_verilog} #{output.to_verilog}"
2014
1921
  if output.value then
2015
1922
  # There is an initial value.
2016
1923
  code << " = #{output.value.to_verilog}"
2017
1924
  end
2018
1925
  code << ";\n"
2019
- $vector_cnt += 1
2020
- end
2021
- else
2022
- # if regs.include?(output.name) then
2023
- # if regs.include?(output.to_verilog) then
2024
- if HDLRuby::Low::VERILOG_REGS.include?(output.to_verilog) then
2025
- code << " output reg"
2026
- else
2027
- code << " output"
2028
- end
2029
- # code << "#{output.type.to_verilog} #{output.to_verilog};\n"
2030
- code << "#{output.type.to_verilog} #{output.to_verilog}"
2031
- if output.value then
2032
- # There is an initial value.
2033
- code << " = #{output.value.to_verilog}"
2034
1926
  end
2035
- code << ";\n"
2036
- end
2037
- end
2038
-
2039
- # Declare "inout"
2040
- self.each_inout do |inout|
2041
- if inout.type.respond_to? (:each_type) then
2042
- $vector_reg = "#{inout.to_verilog}"
2043
- $vector_cnt = 0
2044
- inout.type.each_type do |type|
2045
- code << "inout #{type.to_verilog} #{$vector_reg}:#{$vector_cnt};\n"
2046
- $vector_cnt += 1
2047
- end
2048
- else
2049
- code << " inout#{inout.type.to_verilog} #{inout.to_verilog};\n"
2050
- end
2051
- end
2052
-
2053
- # Declare "inner".
2054
- self.each_inner do |inner|
2055
- # # if regs.include?(inner.name) then
2056
- # if regs.include?(inner.to_verilog) then
2057
- if HDLRuby::Low::VERILOG_REGS.include?(inner.to_verilog) then
2058
- code << " reg"
2059
- else
2060
- code << " wire"
2061
1927
  end
2062
1928
 
2063
- if inner.type.base?
2064
- if inner.type.base.base?
2065
- # code << "#{inner.type.base.to_verilog} #{inner.to_verilog} #{inner.type.to_verilog};\n"
2066
- code << "#{inner.type.base.to_verilog} #{inner.to_verilog} #{inner.type.to_verilog}"
1929
+ # Declare "inout"
1930
+ self.each_inout do |inout|
1931
+ if inout.type.respond_to? (:each_type) then
1932
+ $vector_reg = "#{inout.to_verilog}"
1933
+ $vector_cnt = 0
1934
+ inout.type.each_type do |type|
1935
+ code << "inout #{type.to_verilog} #{$vector_reg}:#{$vector_cnt};\n"
1936
+ $vector_cnt += 1
1937
+ end
2067
1938
  else
2068
- # code << "#{inner.type.to_verilog} #{inner.to_verilog};\n"
2069
- code << "#{inner.type.to_verilog} #{inner.to_verilog}"
1939
+ code << " inout#{inout.type.to_verilog} #{inout.to_verilog};\n"
2070
1940
  end
2071
- else
2072
- # code << " #{inner.type.to_verilog}#{inner.to_verilog};\n"
2073
- code << " #{inner.type.to_verilog}#{inner.to_verilog}"
2074
- end
2075
- if inner.value then
2076
- # There is an initial value.
2077
- code << " = #{inner.value.to_verilog}"
2078
1941
  end
2079
- code << ";\n"
2080
- end
2081
1942
 
2082
- # If there is scope in scope, translate it.
2083
- self.each_scope do |scope|
2084
- scope.each_inner do |inner|
2085
- # # if regs.include?(inner.name) then
2086
- # if regs.include?(inner.to_verilog) then
1943
+ # Declare "inner".
1944
+ self.each_inner do |inner|
2087
1945
  if HDLRuby::Low::VERILOG_REGS.include?(inner.to_verilog) then
2088
- code << " reg "
1946
+ code << " reg"
2089
1947
  else
2090
- code << " wire "
1948
+ code << " wire"
2091
1949
  end
2092
1950
 
2093
- if inner.type.respond_to? (:base)
2094
- if inner.type.base.base?
2095
- # code << "#{inner.type.base.to_verilog} #{inner.to_verilog} #{inner.type.to_verilog};\n"
1951
+ if inner.type.base?
1952
+ if inner.type.base.base?
2096
1953
  code << "#{inner.type.base.to_verilog} #{inner.to_verilog} #{inner.type.to_verilog}"
2097
1954
  else
2098
- # code << "#{inner.type.to_verilog} #{inner.to_verilog};\n"
2099
1955
  code << "#{inner.type.to_verilog} #{inner.to_verilog}"
2100
1956
  end
2101
1957
  else
2102
- # code << "inner #{inner.type.to_verilog} #{inner.to_verilog};\n"
2103
- code << "inner #{inner.type.to_verilog} #{inner.to_verilog}"
1958
+ code << " #{inner.type.to_verilog}#{inner.to_verilog}"
2104
1959
  end
2105
1960
  if inner.value then
2106
1961
  # There is an initial value.
2107
1962
  code << " = #{inner.value.to_verilog}"
2108
1963
  end
2109
1964
  code << ";\n"
2110
- end
2111
-
2112
- scope.each_connection do |connection|
2113
- code << "\n"
2114
- code << "#{connection.to_verilog}"
2115
1965
  end
2116
- end
2117
1966
 
2118
- code << "\n"
2119
-
2120
- # puts "For system=#{self.name}"
2121
- # transliation of the instantiation part.
2122
- # Generate the instances connections.
2123
- self.each_systemI do |systemI|
2124
- # puts "Processing systemI = #{systemI.name}"
2125
- # Its Declaration.
2126
- code << " " * 3
2127
- systemT = systemI.systemT
2128
- code << name_to_verilog(systemT.name) << " "
2129
- # code << name_to_verilog(systemI.name) << "("
2130
- vname = name_to_verilog(systemI.name)
2131
- systemI.properties[:verilog_name] = vname
2132
- code << vname << "("
2133
- # Its ports connections
2134
- # Inputs
2135
- systemT.each_input do |input|
2136
- ref = self.extract_port_assign!(systemI,input)
2137
- if ref then
2138
- code << "." << name_to_verilog(input.name) << "("
2139
- code << ref.to_verilog
2140
- code << "),"
1967
+ # If there is scope in scope, translate it.
1968
+ self.each_scope do |scope|
1969
+ scope.each_inner do |inner|
1970
+ if HDLRuby::Low::VERILOG_REGS.include?(inner.to_verilog) then
1971
+ code << " reg "
1972
+ else
1973
+ code << " wire "
1974
+ end
1975
+
1976
+ if inner.type.respond_to? (:base)
1977
+ if inner.type.base.base?
1978
+ code << "#{inner.type.base.to_verilog} #{inner.to_verilog} #{inner.type.to_verilog}"
1979
+ else
1980
+ code << "#{inner.type.to_verilog} #{inner.to_verilog}"
1981
+ end
1982
+ else
1983
+ code << "inner #{inner.type.to_verilog} #{inner.to_verilog}"
1984
+ end
1985
+ if inner.value then
1986
+ # There is an initial value.
1987
+ code << " = #{inner.value.to_verilog}"
1988
+ end
1989
+ code << ";\n"
1990
+ end
1991
+
1992
+ scope.each_connection do |connection|
1993
+ code << "\n"
1994
+ code << "#{connection.to_verilog}"
2141
1995
  end
2142
1996
  end
2143
- # Outputs
2144
- systemT.each_output do |output|
2145
- ref = self.extract_port_assign!(systemI,output)
2146
- if ref then
2147
- code << "." << name_to_verilog(output.name) << "("
2148
- code << ref.to_verilog
2149
- code << "),"
1997
+
1998
+ code << "\n"
1999
+
2000
+ # puts "For system=#{self.name}"
2001
+ # transliation of the instantiation part.
2002
+ # Generate the instances connections.
2003
+ self.each_systemI do |systemI|
2004
+ # puts "Processing systemI = #{systemI.name}"
2005
+ # Its Declaration.
2006
+ code << " " * 3
2007
+ systemT = systemI.systemT
2008
+ code << name_to_verilog(systemT.name) << " "
2009
+ vname = name_to_verilog(systemI.name)
2010
+ systemI.properties[:verilog_name] = vname
2011
+ code << vname << "("
2012
+ # Its ports connections
2013
+ # Inputs
2014
+ systemT.each_input do |input|
2015
+ ref = self.extract_port_assign!(systemI,input)
2016
+ if ref then
2017
+ code << "." << name_to_verilog(input.name) << "("
2018
+ code << ref.to_verilog
2019
+ code << "),"
2020
+ end
2150
2021
  end
2151
- end
2152
- # Inouts
2153
- systemT.each_inout do |inout|
2154
- ref = self.extract_port_assign!(systemI,inout)
2155
- if ref then
2156
- code << "." << name_to_verilog(inout.name) << "("
2157
- code << ref.to_verilog
2158
- code << "),"
2022
+ # Outputs
2023
+ systemT.each_output do |output|
2024
+ ref = self.extract_port_assign!(systemI,output)
2025
+ if ref then
2026
+ code << "." << name_to_verilog(output.name) << "("
2027
+ code << ref.to_verilog
2028
+ code << "),"
2029
+ end
2030
+ end
2031
+ # Inouts
2032
+ systemT.each_inout do |inout|
2033
+ ref = self.extract_port_assign!(systemI,inout)
2034
+ if ref then
2035
+ code << "." << name_to_verilog(inout.name) << "("
2036
+ code << ref.to_verilog
2037
+ code << "),"
2038
+ end
2159
2039
  end
2040
+ # Remove the last "," for conforming with Verilog syntax.
2041
+ # and close the port connection.
2042
+ code[-1] = ");\n"
2160
2043
  end
2161
- # Remove the last "," for conforming with Verilog syntax.
2162
- # and close the port connection.
2163
- code[-1] = ");\n"
2164
- end
2165
2044
 
2166
2045
 
2167
2046
 
2168
- # translation of the connection part (assigen).
2169
- self.each_connection do |connection|
2170
- code << "#{connection.to_verilog}\n"
2171
- end
2047
+ # translation of the connection part (assigen).
2048
+ self.each_connection do |connection|
2049
+ code << "#{connection.to_verilog}\n"
2050
+ end
2172
2051
 
2173
- # Translation of behavior part (always).
2174
- self.each_behavior do |behavior|
2175
- if behavior.block.is_a?(TimeBlock) then
2176
- # Extract and translate the TimeRepeat separately.
2177
- behavior.each_block_deep do |blk|
2178
- code << blk.repeat_to_verilog!
2179
- end
2180
- # And generate an initial block.
2181
- # code << " initial begin\n"
2182
- code << " initial "
2183
- else
2184
- # Generate a standard process.
2185
- code << " always @( "
2186
- # If there is no "always" condition, it is always @("*").
2187
- if behavior.each_event.to_a.empty? then
2188
- code << "*"
2052
+ # Translation of behavior part (always).
2053
+ self.each_behavior do |behavior|
2054
+ if behavior.block.is_a?(TimeBlock) then
2055
+ # Extract and translate the TimeRepeat separately.
2056
+ behavior.each_block_deep do |blk|
2057
+ code << blk.repeat_to_verilog!
2058
+ end
2059
+ # And generate an initial block.
2060
+ code << " initial "
2189
2061
  else
2190
- event = behavior.each_event.to_a
2191
- event[0..-2].each do |event|
2192
- # If "posedge" or "negedge" does not exist, the variable is set to condition.
2193
- if (event.type.to_s != "posedge" && event.type.to_s != "negedge") then
2194
- code << "#{event.ref.to_verilog}, "
2062
+ # Generate a standard process.
2063
+ code << " always @( "
2064
+ # If there is no "always" condition, it is always @("*").
2065
+ if behavior.each_event.to_a.empty? then
2066
+ code << "*"
2067
+ else
2068
+ event = behavior.each_event.to_a
2069
+ event[0..-2].each do |event|
2070
+ # If "posedge" or "negedge" does not exist, the variable is set to condition.
2071
+ if (event.type.to_s != "posedge" && event.type.to_s != "negedge") then
2072
+ code << "#{event.ref.to_verilog}, "
2073
+ else
2074
+ # Otherwise, it outputs "psoedge" or "negedge" as a condition.
2075
+ code << "#{event.type.to_s} #{event.ref.to_verilog}, "
2076
+ end
2077
+ end
2078
+ # Since no comma is necessary at the end, we try not to separate commas separately at the end.
2079
+ if (event.last.type.to_s != "posedge" && event.last.type.to_s != "negedge") then
2080
+ code << "#{event.last.ref.to_verilog}"
2195
2081
  else
2196
- # Otherwise, it outputs "psoedge" or "negedge" as a condition.
2197
- code << "#{event.type.to_s} #{event.ref.to_verilog}, "
2082
+ code << "#{event.last.type.to_s} #{event.last.ref.to_verilog}"
2198
2083
  end
2199
2084
  end
2200
- # Since no comma is necessary at the end, we try not to separate commas separately at the end.
2201
- if (event.last.type.to_s != "posedge" && event.last.type.to_s != "negedge") then
2202
- code << "#{event.last.ref.to_verilog}"
2203
- else
2204
- code << "#{event.last.type.to_s} #{event.last.ref.to_verilog}"
2205
- end
2085
+ code << " ) "
2206
2086
  end
2207
- # code << " ) begin\n"
2208
- code << " ) "
2209
- end
2210
-
2211
- # # Perform "scheduling" using the method "flatten".
2212
- # block = behavior.block.flatten(behavior.block.mode.to_s)
2213
- # code << block.to_verilog(regs)
2214
- code << behavior.block.to_verilog
2215
-
2216
- # # Declaration of "inner" part within "always".
2217
- # block.each_inner do |inner|
2218
- # # if regs.include?(inner.name) then
2219
- # if regs.include?(inner.to_verilog) then
2220
- # code << " reg"
2221
- # else
2222
- # code << " wire"
2223
- # end
2224
-
2225
- # # Variable has "base", but if there is width etc, it is not in "base".
2226
- # # It is determined by an if.
2227
- # if inner.type.base?
2228
- # if inner.type.base.base?
2229
- # # code << "#{inner.type.base.to_verilog} #{inner.to_verilog} #{inner.type.to_verilog};\n"
2230
- # code << "#{inner.type.base.to_verilog} #{inner.to_verilog} #{inner.type.to_verilog}"
2231
- # else
2232
- # # code << "#{inner.type.to_verilog} #{inner.to_verilog};\n"
2233
- # code << "#{inner.type.to_verilog} #{inner.to_verilog}"
2234
- # end
2235
- # else
2236
- # # code << " #{inner.type.to_verilog}#{inner.to_verilog};\n"
2237
- # code << " #{inner.type.to_verilog}#{inner.to_verilog}"
2238
- # end
2239
- # if inner.value then
2240
- # # There is an initial value.
2241
- # code << " = #{inner.value.to_verilog}"
2242
- # end
2243
- # code << ";\n"
2244
- # end
2245
2087
 
2246
- # # Translate the block that finished scheduling.
2247
- # block.each_statement do |statement|
2248
- # code << "\n #{statement.to_verilog(behavior.block.mode.to_s)}"
2249
- # end
2088
+ code << behavior.block.to_verilog
2250
2089
 
2251
- # $fm.fm_par.clear()
2090
+ end
2252
2091
 
2253
- # code << "\n end\n\n"
2092
+ # Conclusion.
2093
+ code << "\nendmodule"
2094
+ return code
2254
2095
  end
2096
+ end
2255
2097
 
2256
- # Conclusion.
2257
- code << "\nendmodule"
2258
- return code
2098
+
2099
+ # Enhance StringE with generation of verilog code.
2100
+ class StringE
2101
+ # Converts the system to Verilog code.
2102
+ def to_verilog(spc = 3)
2103
+ code = "\"#{Low.v_string(self.content)}" +
2104
+ "#{self.each_arg.map do |arg|
2105
+ to.to_verilog
2106
+ end.join(",")}\""
2107
+ return code
2108
+ end
2259
2109
  end
2260
- end
2261
2110
 
2262
2111
  end
2263
2112