HDLRuby 2.11.3 → 2.11.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/README.md +6 -2
- data/ext/hruby_sim/hruby_rcsim_build.c +36 -11
- data/ext/hruby_sim/hruby_sim.h +13 -1
- data/ext/hruby_sim/hruby_sim_core.c +84 -50
- data/ext/hruby_sim/hruby_sim_tree_calc.c +14 -0
- data/ext/hruby_sim/hruby_sim_vcd.c +23 -9
- data/lib/HDLRuby/hdr_samples/repeat_bench.rb +48 -0
- data/lib/HDLRuby/hruby_high.rb +11 -6
- data/lib/HDLRuby/hruby_low.rb +27 -17
- data/lib/HDLRuby/hruby_low2c.rb +31 -7
- data/lib/HDLRuby/hruby_rcsim.rb +16 -2
- data/lib/HDLRuby/hruby_rsim.rb +154 -79
- data/lib/HDLRuby/hruby_rsim_vcd.rb +181 -10
- data/lib/HDLRuby/hruby_verilog.rb +71 -58
- data/lib/HDLRuby/version.rb +1 -1
- metadata +3 -2
data/lib/HDLRuby/hruby_low2c.rb
CHANGED
@@ -843,6 +843,9 @@ module HDLRuby::Low
|
|
843
843
|
## Extends the SignalI class with generation of C text.
|
844
844
|
class SignalI
|
845
845
|
|
846
|
+
# The id of a signal in the simulator.
|
847
|
+
@@signal_id = 0
|
848
|
+
|
846
849
|
## Generates the C text for an access to the signal.
|
847
850
|
# +level+ is the hierachical level of the object.
|
848
851
|
# def to_c_signal(level = 0)
|
@@ -881,6 +884,8 @@ module HDLRuby::Low
|
|
881
884
|
res << "SignalI signalI = malloc(sizeof(SignalIS));\n"
|
882
885
|
res << " " * (level+1)*3
|
883
886
|
res << "signalI->kind = SIGNALI;\n";
|
887
|
+
res << "signalI->id = #{@@signal_id};\n"
|
888
|
+
@@signal_id = @@signal_id+1;
|
884
889
|
|
885
890
|
# Sets the global variable of the signal.
|
886
891
|
res << "\n"
|
@@ -1803,20 +1808,39 @@ module HDLRuby::Low
|
|
1803
1808
|
## Extends the TimeRepeat class with generation of C text.
|
1804
1809
|
class TimeRepeat
|
1805
1810
|
|
1811
|
+
# # Generates the C text of the equivalent HDLRuby code.
|
1812
|
+
# # +level+ is the hierachical level of the object.
|
1813
|
+
# # def to_c(level = 0)
|
1814
|
+
# def to_c(res,level = 0)
|
1815
|
+
# # The resulting string.
|
1816
|
+
# # res = " " * level*3
|
1817
|
+
# res << " " * level*3
|
1818
|
+
# # Generate an infinite loop executing the block and waiting.
|
1819
|
+
# res << "for(;;) {\n"
|
1820
|
+
# # res << "#{self.statement.to_c(level+1)}\n"
|
1821
|
+
# self.statement.to_c(res,level+1)
|
1822
|
+
# res << "\n"
|
1823
|
+
# res << " " * (level+1)*3
|
1824
|
+
# res << Low2C.wait_code(self,level)
|
1825
|
+
# # Return the resulting string.
|
1826
|
+
# return res
|
1827
|
+
# end
|
1828
|
+
|
1806
1829
|
# Generates the C text of the equivalent HDLRuby code.
|
1807
1830
|
# +level+ is the hierachical level of the object.
|
1808
1831
|
# def to_c(level = 0)
|
1809
1832
|
def to_c(res,level = 0)
|
1810
1833
|
# The resulting string.
|
1811
|
-
# res = " " * level*3
|
1812
1834
|
res << " " * level*3
|
1813
|
-
|
1814
|
-
|
1815
|
-
|
1835
|
+
if (number < 0) then
|
1836
|
+
# Generate an infinite loop executing the block and waiting.
|
1837
|
+
res << "for(;;) {\n"
|
1838
|
+
else
|
1839
|
+
# Generate a finite loop.
|
1840
|
+
res << "for(long long i = 0; i<#{self.number}; ++i) {\n"
|
1841
|
+
end
|
1816
1842
|
self.statement.to_c(res,level+1)
|
1817
|
-
res << "\n"
|
1818
|
-
res << " " * (level+1)*3
|
1819
|
-
res << Low2C.wait_code(self,level)
|
1843
|
+
res << " " * level*3 << "}\n"
|
1820
1844
|
# Return the resulting string.
|
1821
1845
|
return res
|
1822
1846
|
end
|
data/lib/HDLRuby/hruby_rcsim.rb
CHANGED
@@ -654,7 +654,21 @@ module HDLRuby::High
|
|
654
654
|
## Extends the TimeRepeat class for hybrid Ruby-C simulation.
|
655
655
|
class TimeRepeat
|
656
656
|
attr_reader :rcstatement
|
657
|
-
|
657
|
+
|
658
|
+
# Generate the C description of the hardware case.
|
659
|
+
# +owner+ is a link to the C description of the owner behavior if any.
|
660
|
+
def to_rcsim(owner = nil)
|
661
|
+
# Create the timeRepeat C object.
|
662
|
+
@rcstatement = RCSim.rcsim_make_timeRepeat(self.number,
|
663
|
+
self.statement.to_rcsim)
|
664
|
+
|
665
|
+
# Sets the owner if any.
|
666
|
+
if owner then
|
667
|
+
RCSim.rcsim_set_owner(@rcstatement,owner)
|
668
|
+
end
|
669
|
+
|
670
|
+
return @rcstatement
|
671
|
+
end
|
658
672
|
end
|
659
673
|
|
660
674
|
|
@@ -670,7 +684,7 @@ module HDLRuby::High
|
|
670
684
|
|
671
685
|
# Sets the owner if any.
|
672
686
|
if owner then
|
673
|
-
RCSim.
|
687
|
+
RCSim.rcsim_set_owner(@rcstatement,owner)
|
674
688
|
end
|
675
689
|
|
676
690
|
# Add the inner signals.
|
data/lib/HDLRuby/hruby_rsim.rb
CHANGED
@@ -16,6 +16,9 @@ module HDLRuby::High
|
|
16
16
|
# Enhance a system type with Ruby simulation.
|
17
17
|
class SystemT
|
18
18
|
|
19
|
+
# Tell if the simulation is in multithread mode or not.
|
20
|
+
attr_reader :multithread
|
21
|
+
|
19
22
|
## Add timed behavior +beh+.
|
20
23
|
# Returns the id of the timed behavior.
|
21
24
|
def add_timed_behavior(beh)
|
@@ -36,6 +39,50 @@ module HDLRuby::High
|
|
36
39
|
@sig_active << sig
|
37
40
|
end
|
38
41
|
|
42
|
+
## Advance the global simulator.
|
43
|
+
def advance
|
44
|
+
# Display the time
|
45
|
+
self.show_time
|
46
|
+
shown_values = {}
|
47
|
+
# Get the behaviors waiting on activated signals.
|
48
|
+
until @sig_active.empty? do
|
49
|
+
# # Update the signals.
|
50
|
+
# @sig_active.each { |sig| sig.c_value = sig.f_value }
|
51
|
+
# puts "sig_active.size=#{@sig_active.size}"
|
52
|
+
# Look for the behavior sensitive to the signals.
|
53
|
+
@sig_active.each do |sig|
|
54
|
+
sig.each_anyedge { |beh| @sig_exec << beh }
|
55
|
+
if (sig.c_value.zero? && !sig.f_value.zero?) then
|
56
|
+
# puts "sig.c_value=#{sig.c_value.content}"
|
57
|
+
sig.each_posedge { |beh| @sig_exec << beh }
|
58
|
+
elsif (!sig.c_value.zero? && sig.f_value.zero?) then
|
59
|
+
sig.each_negedge { |beh| @sig_exec << beh }
|
60
|
+
end
|
61
|
+
end
|
62
|
+
# Update the signals.
|
63
|
+
@sig_active.each { |sig| sig.c_value = sig.f_value }
|
64
|
+
# puts "first @sig_exec.size=#{@sig_exec.size}"
|
65
|
+
@sig_exec.uniq! {|beh| beh.object_id }
|
66
|
+
# Display the activated signals.
|
67
|
+
@sig_active.each do |sig|
|
68
|
+
if !shown_values[sig].eql?(sig.f_value) then
|
69
|
+
self.show_signal(sig)
|
70
|
+
shown_values[sig] = sig.f_value
|
71
|
+
end
|
72
|
+
end
|
73
|
+
# Clear the list of active signals.
|
74
|
+
@sig_active.clear
|
75
|
+
# puts "sig_exec.size=#{@sig_exec.size}"
|
76
|
+
# Execute the relevant behaviors and connections.
|
77
|
+
@sig_exec.each { |obj| obj.execute(:par) }
|
78
|
+
@sig_exec.clear
|
79
|
+
@sig_active.uniq! {|sig| sig.object_id }
|
80
|
+
# puts "@sig_active.size=#{@sig_active.size}"
|
81
|
+
# Advance time.
|
82
|
+
@time = (@timed_behaviors.min {|b0,b1| b0.time <=> b1.time }).time
|
83
|
+
end
|
84
|
+
end
|
85
|
+
|
39
86
|
## Run the simulation from the current systemT and outputs the resuts
|
40
87
|
# on simout.
|
41
88
|
def sim(simout)
|
@@ -43,15 +90,6 @@ module HDLRuby::High
|
|
43
90
|
HDLRuby.show "#{Time.now}#{show_mem}"
|
44
91
|
# Merge the included.
|
45
92
|
self.merge_included!
|
46
|
-
# Initializes the run mutex and the conditions.
|
47
|
-
@mutex = Mutex.new
|
48
|
-
@master = ConditionVariable.new
|
49
|
-
@master_flag = 0
|
50
|
-
@slave = ConditionVariable.new
|
51
|
-
@slave_flags_not = 0
|
52
|
-
@num_done = 0
|
53
|
-
# @lock = 0
|
54
|
-
# @runs = 0
|
55
93
|
# Initializes the time.
|
56
94
|
@time = 0
|
57
95
|
# Initializes the time and signals execution buffers.
|
@@ -68,72 +106,93 @@ module HDLRuby::High
|
|
68
106
|
self.init_sim(self)
|
69
107
|
# Initialize the displayer.
|
70
108
|
self.show_init(simout)
|
71
|
-
|
72
|
-
#
|
73
|
-
|
74
|
-
|
75
|
-
|
76
|
-
|
77
|
-
|
78
|
-
|
79
|
-
|
80
|
-
|
81
|
-
|
82
|
-
|
83
|
-
|
84
|
-
|
85
|
-
|
86
|
-
|
87
|
-
|
88
|
-
|
89
|
-
|
90
|
-
|
91
|
-
|
92
|
-
|
93
|
-
|
94
|
-
|
95
|
-
|
96
|
-
|
97
|
-
|
98
|
-
|
99
|
-
|
100
|
-
|
101
|
-
|
102
|
-
|
103
|
-
|
104
|
-
|
105
|
-
|
106
|
-
|
107
|
-
|
108
|
-
|
109
|
-
#
|
110
|
-
|
111
|
-
#
|
112
|
-
@sig_active.
|
113
|
-
|
114
|
-
|
115
|
-
|
116
|
-
|
109
|
+
|
110
|
+
# Is there more than one timed behavior.
|
111
|
+
if @total_timed_behaviors <= 1 then
|
112
|
+
# No, no need of multithreading.
|
113
|
+
@multithread = false
|
114
|
+
# Simple execute the block of the behavior.
|
115
|
+
@timed_behaviors[0].block.execute(:seq)
|
116
|
+
else
|
117
|
+
# Yes, need of multithreading.
|
118
|
+
@multithread = true
|
119
|
+
# Initializes the run mutex and the conditions.
|
120
|
+
@mutex = Mutex.new
|
121
|
+
@master = ConditionVariable.new
|
122
|
+
@master_flag = 0
|
123
|
+
@slave = ConditionVariable.new
|
124
|
+
@slave_flags_not = 0
|
125
|
+
@num_done = 0
|
126
|
+
|
127
|
+
# First all the timed behaviors are to be executed.
|
128
|
+
@timed_behaviors.each {|beh| @tim_exec << beh }
|
129
|
+
# But starts locked.
|
130
|
+
@slave_flags_not = 2**@timed_behaviors.size - 1
|
131
|
+
# Starts the threads.
|
132
|
+
@timed_behaviors.each {|beh| beh.make_thread }
|
133
|
+
|
134
|
+
HDLRuby.show "Starting Ruby-level simulator..."
|
135
|
+
HDLRuby.show "#{Time.now}#{show_mem}"
|
136
|
+
# Run the simulation.
|
137
|
+
self.run_init do
|
138
|
+
# # Wake the behaviors.
|
139
|
+
# @timed_behaviors.each {|beh| beh.run }
|
140
|
+
until @tim_exec.empty? do
|
141
|
+
# Execute the time behaviors that are ready.
|
142
|
+
self.run_ack
|
143
|
+
self.run_wait
|
144
|
+
# Advance the global simulator.
|
145
|
+
self.advance
|
146
|
+
# # Display the time
|
147
|
+
# self.show_time
|
148
|
+
# shown_values = {}
|
149
|
+
# # Get the behaviors waiting on activated signals.
|
150
|
+
# until @sig_active.empty? do
|
151
|
+
# # # Update the signals.
|
152
|
+
# # @sig_active.each { |sig| sig.c_value = sig.f_value }
|
153
|
+
# # puts "sig_active.size=#{@sig_active.size}"
|
154
|
+
# # Look for the behavior sensitive to the signals.
|
155
|
+
# @sig_active.each do |sig|
|
156
|
+
# sig.each_anyedge { |beh| @sig_exec << beh }
|
157
|
+
# if (sig.c_value.zero? && !sig.f_value.zero?) then
|
158
|
+
# # puts "sig.c_value=#{sig.c_value.content}"
|
159
|
+
# sig.each_posedge { |beh| @sig_exec << beh }
|
160
|
+
# elsif (!sig.c_value.zero? && sig.f_value.zero?) then
|
161
|
+
# sig.each_negedge { |beh| @sig_exec << beh }
|
162
|
+
# end
|
163
|
+
# end
|
164
|
+
# # Update the signals.
|
165
|
+
# @sig_active.each { |sig| sig.c_value = sig.f_value }
|
166
|
+
# # puts "first @sig_exec.size=#{@sig_exec.size}"
|
167
|
+
# @sig_exec.uniq! {|beh| beh.object_id }
|
168
|
+
# # Display the activated signals.
|
169
|
+
# @sig_active.each do |sig|
|
170
|
+
# if !shown_values[sig].eql?(sig.f_value) then
|
171
|
+
# self.show_signal(sig)
|
172
|
+
# shown_values[sig] = sig.f_value
|
173
|
+
# end
|
174
|
+
# end
|
175
|
+
# # Clear the list of active signals.
|
176
|
+
# @sig_active.clear
|
177
|
+
# # puts "sig_exec.size=#{@sig_exec.size}"
|
178
|
+
# # Execute the relevant behaviors and connections.
|
179
|
+
# @sig_exec.each { |obj| obj.execute(:par) }
|
180
|
+
# @sig_exec.clear
|
181
|
+
# @sig_active.uniq! {|sig| sig.object_id }
|
182
|
+
# # puts "@sig_active.size=#{@sig_active.size}"
|
183
|
+
# end
|
184
|
+
|
185
|
+
# # Advance time.
|
186
|
+
# @time = (@timed_behaviors.min {|b0,b1| b0.time <=> b1.time }).time
|
187
|
+
break if @timed_behaviors.empty?
|
188
|
+
# Schedule the next timed behavior to execute.
|
189
|
+
@tim_exec = []
|
190
|
+
@timed_behaviors.each do |beh|
|
191
|
+
@tim_exec << beh if beh.time == @time
|
117
192
|
end
|
118
|
-
#
|
119
|
-
@
|
120
|
-
# puts "sig_exec.size=#{@sig_exec.size}"
|
121
|
-
# Execute the relevant behaviors and connections.
|
122
|
-
@sig_exec.each { |obj| obj.execute(:par) }
|
123
|
-
@sig_exec.clear
|
124
|
-
@sig_active.uniq! {|sig| sig.object_id }
|
125
|
-
# puts "@sig_active.size=#{@sig_active.size}"
|
126
|
-
end
|
127
|
-
break if @timed_behaviors.empty?
|
128
|
-
# Advance time.
|
129
|
-
@time = (@timed_behaviors.min {|b0,b1| b0.time <=> b1.time }).time
|
130
|
-
# Schedule the next timed behavior to execute.
|
131
|
-
@tim_exec = []
|
132
|
-
@timed_behaviors.each do |beh|
|
133
|
-
@tim_exec << beh if beh.time == @time
|
193
|
+
# puts "@tim_exec.size=#{@tim_exec.size}"
|
194
|
+
# puts "@timed_bevaviors.size=#{@timed_behaviors.size}"
|
134
195
|
end
|
135
|
-
# puts "@tim_exec.size=#{@tim_exec.size}"
|
136
|
-
# puts "@timed_bevaviors.size=#{@timed_behaviors.size}"
|
137
196
|
end
|
138
197
|
end
|
139
198
|
end
|
@@ -358,7 +417,8 @@ module HDLRuby::High
|
|
358
417
|
begin
|
359
418
|
# puts "Starting thread"
|
360
419
|
systemT.run_req(@id)
|
361
|
-
self.block.execute(:par)
|
420
|
+
# self.block.execute(:par)
|
421
|
+
self.block.execute(:seq)
|
362
422
|
# puts "Ending thread"
|
363
423
|
rescue => e
|
364
424
|
puts "Got exception: #{e.full_message}"
|
@@ -690,10 +750,16 @@ module HDLRuby::High
|
|
690
750
|
def execute(mode)
|
691
751
|
@behavior ||= self.behavior
|
692
752
|
@behavior.time += self.delay.time_ps
|
693
|
-
|
694
|
-
|
695
|
-
|
696
|
-
|
753
|
+
if @sim.multithread then
|
754
|
+
# Multi thread mode: synchronize.
|
755
|
+
# puts "Stopping #{@behavior.object_id} (@behavior.time=#{@behavior.time})..."
|
756
|
+
@sim.run_done(@behavior.id)
|
757
|
+
# puts "Rerunning #{@behavior.object_id} (@behavior.time=#{@behavior.time})..."
|
758
|
+
@sim.run_req(@behavior.id)
|
759
|
+
else
|
760
|
+
# No thread mode, need to advance the global simulator.
|
761
|
+
@sim.advance
|
762
|
+
end
|
697
763
|
end
|
698
764
|
end
|
699
765
|
|
@@ -701,7 +767,16 @@ module HDLRuby::High
|
|
701
767
|
##
|
702
768
|
# Describes a timed loop statement: not synthesizable!
|
703
769
|
class TimeRepeat
|
704
|
-
##
|
770
|
+
## Initialize the simulation for system +systemT+.
|
771
|
+
def init_sim(systemT)
|
772
|
+
# Recurde on the statement.
|
773
|
+
self.statement.init_sim(systemT)
|
774
|
+
end
|
775
|
+
|
776
|
+
## Executes the statement.
|
777
|
+
def execute(mode)
|
778
|
+
self.number.times { self.statement.execute(mode) }
|
779
|
+
end
|
705
780
|
end
|
706
781
|
|
707
782
|
|
@@ -11,6 +11,35 @@ module HDLRuby::High
|
|
11
11
|
return name.to_s.gsub(/[^a-zA-Z0-9_$]/,"$")
|
12
12
|
end
|
13
13
|
|
14
|
+
## Converts a bit string to a vcd format.
|
15
|
+
def self.vcd_bitstr(str)
|
16
|
+
if str.length > 1 then
|
17
|
+
return "b" + str + " "
|
18
|
+
else
|
19
|
+
return str
|
20
|
+
end
|
21
|
+
end
|
22
|
+
|
23
|
+
## Converts a HDLRuby object to a VCD id string.
|
24
|
+
@@rsim_object_idstr = { }
|
25
|
+
@@rsim_object_idstr_count = 0
|
26
|
+
def self.vcd_idstr(obj)
|
27
|
+
idstr = @@rsim_object_idstr[obj]
|
28
|
+
unless idstr then
|
29
|
+
# Must generate a new id string.
|
30
|
+
chars = []
|
31
|
+
id = @@rsim_object_idstr_count
|
32
|
+
@@rsim_object_idstr_count += 1
|
33
|
+
loop do
|
34
|
+
chars << ((id % (127-33)) + 33).chr
|
35
|
+
break if ((id=id/(127-33)) == 0)
|
36
|
+
end
|
37
|
+
idstr = chars.join
|
38
|
+
@@rsim_object_idstr[obj] = idstr
|
39
|
+
end
|
40
|
+
return idstr
|
41
|
+
end
|
42
|
+
|
14
43
|
##
|
15
44
|
# Enhance the system type class with VCD support.
|
16
45
|
class SystemT
|
@@ -40,14 +69,24 @@ module HDLRuby::High
|
|
40
69
|
# Closes the header.
|
41
70
|
@vcdout << "$enddefinitions $end\n"
|
42
71
|
# Initializes the variables with their name.
|
43
|
-
@vars_with_fullname = self.get_vars_with_fullname
|
72
|
+
# @vars_with_fullname = self.get_vars_with_fullname
|
73
|
+
@vars_with_idstr = self.get_vars_with_idstr
|
44
74
|
@vcdout << "$dumpvars\n"
|
45
|
-
@vars_with_fullname.each_pair do |sig,fullname|
|
75
|
+
# @vars_with_fullname.each_pair do |sig,fullname|
|
76
|
+
# if sig.f_value then
|
77
|
+
# @vcdout << " b#{sig.f_value.to_vstr} #{fullname}\n"
|
78
|
+
# else
|
79
|
+
# @vcdout << " b#{"x"} #{fullname}\n"
|
80
|
+
# end
|
81
|
+
# end
|
82
|
+
@vars_with_idstr.each_pair do |sig,idstr|
|
46
83
|
if sig.f_value then
|
47
|
-
@vcdout << " b#{sig.f_value.to_vstr} #{
|
84
|
+
# @vcdout << " b#{sig.f_value.to_vstr} #{idstr}\n"
|
85
|
+
@vcdout << HDLRuby::High.vcd_bitstr(sig.f_value.to_vstr) <<
|
86
|
+
idstr << "\n"
|
48
87
|
else
|
49
|
-
# @vcdout << " b#{"x"
|
50
|
-
@vcdout << "
|
88
|
+
# @vcdout << " b#{"x"} #{idstr}\n"
|
89
|
+
@vcdout << HDLRuby::High.vcd_bitstr("x") << idstr << "\n"
|
51
90
|
end
|
52
91
|
end
|
53
92
|
@vcdout << "$end\n"
|
@@ -63,6 +102,16 @@ module HDLRuby::High
|
|
63
102
|
return self.scope.get_vars_with_fullname(vars_with_fullname)
|
64
103
|
end
|
65
104
|
|
105
|
+
## Gets the VCD variables with their id string.
|
106
|
+
def get_vars_with_idstr(vars_with_idstr = {})
|
107
|
+
# Adds the signals of the interface of the system.
|
108
|
+
self.each_signal do |sig|
|
109
|
+
vars_with_idstr[sig] = HDLRuby::High.vcd_idstr(sig)
|
110
|
+
end
|
111
|
+
# Recurse on the scope.
|
112
|
+
return self.scope.get_vars_with_idstr(vars_with_idstr)
|
113
|
+
end
|
114
|
+
|
66
115
|
## Shows the hierarchy of the variables.
|
67
116
|
def show_hierarchy(vcdout)
|
68
117
|
# puts "show_hierarchy for module #{self} (#{self.name})"
|
@@ -72,7 +121,8 @@ module HDLRuby::High
|
|
72
121
|
self.each_signal do |sig|
|
73
122
|
# puts "showing signal #{HDLRuby::High.vcd_name(sig.fullname)}"
|
74
123
|
vcdout << "$var wire #{sig.type.width} "
|
75
|
-
vcdout << "#{HDLRuby::High.vcd_name(sig.fullname)} "
|
124
|
+
# vcdout << "#{HDLRuby::High.vcd_name(sig.fullname)} "
|
125
|
+
vcdout << "#{HDLRuby::High.vcd_idstr(sig)} "
|
76
126
|
vcdout << "#{HDLRuby::High.vcd_name(sig.name)} $end\n"
|
77
127
|
end
|
78
128
|
# Recurse on the scope.
|
@@ -88,8 +138,9 @@ module HDLRuby::High
|
|
88
138
|
|
89
139
|
## Displays the value of signal +sig+.
|
90
140
|
def show_signal(sig)
|
91
|
-
@vcdout << "b#{sig.f_value.to_vstr} "
|
92
|
-
@vcdout <<
|
141
|
+
# @vcdout << "b#{sig.f_value.to_vstr} "
|
142
|
+
@vcdout << HDLRuby::High.vcd_bitstr(sig.f_value.to_vstr)
|
143
|
+
@vcdout << "#{@vars_with_idstr[sig]}\n"
|
93
144
|
end
|
94
145
|
|
95
146
|
## Displays value +val+.
|
@@ -121,7 +172,8 @@ module HDLRuby::High
|
|
121
172
|
self.each_inner do |sig|
|
122
173
|
# puts "showing inner signal #{HDLRuby::High.vcd_name(sig.fullname)}"
|
123
174
|
vcdout << "$var wire #{sig.type.width} "
|
124
|
-
vcdout << "#{HDLRuby::High.vcd_name(sig.fullname)} "
|
175
|
+
# vcdout << "#{HDLRuby::High.vcd_name(sig.fullname)} "
|
176
|
+
vcdout << "#{HDLRuby::High.vcd_idstr(sig)} "
|
125
177
|
vcdout << "#{HDLRuby::High.vcd_name(sig.name)} $end\n"
|
126
178
|
end
|
127
179
|
# Recurse on the behaviors' blocks
|
@@ -162,6 +214,27 @@ module HDLRuby::High
|
|
162
214
|
end
|
163
215
|
return vars_with_fullname
|
164
216
|
end
|
217
|
+
|
218
|
+
## Gets the VCD variables with their id string.
|
219
|
+
def get_vars_with_idstr(vars_with_idstr = {})
|
220
|
+
# Adds the inner signals.
|
221
|
+
self.each_inner do |sig|
|
222
|
+
vars_with_idstr[sig] = HDLRuby::High.vcd_idstr(sig)
|
223
|
+
end
|
224
|
+
# Recurse on the behaviors' blocks
|
225
|
+
self.each_behavior do |beh|
|
226
|
+
beh.block.get_vars_with_idstr(vars_with_idstr)
|
227
|
+
end
|
228
|
+
# Recurse on the systemI's Eigen system.
|
229
|
+
self.each_systemI do |sys|
|
230
|
+
sys.systemT.get_vars_with_idstr(vars_with_idstr)
|
231
|
+
end
|
232
|
+
# Recurse on the subscopes.
|
233
|
+
self.each_scope do |scope|
|
234
|
+
scope.get_vars_with_idstr(vars_with_idstr)
|
235
|
+
end
|
236
|
+
return vars_with_idstr
|
237
|
+
end
|
165
238
|
end
|
166
239
|
|
167
240
|
|
@@ -177,6 +250,31 @@ module HDLRuby::High
|
|
177
250
|
def get_vars_with_fullname(vars_with_fullname = {})
|
178
251
|
# By default: nothing to do
|
179
252
|
end
|
253
|
+
|
254
|
+
## Gets the VCD variables with their id string.
|
255
|
+
def get_vars_with_idstr(vars_with_idstr = {})
|
256
|
+
# By default: nothing to do
|
257
|
+
end
|
258
|
+
end
|
259
|
+
|
260
|
+
##
|
261
|
+
# Enhance the TimeRepeat class with VCD support.
|
262
|
+
class TimeRepeat
|
263
|
+
## Shows the hierarchy of the variables.
|
264
|
+
def show_hierarchy(vcdout)
|
265
|
+
# Recurse on the statement.
|
266
|
+
self.statement.show_hierarchy(vcdout)
|
267
|
+
end
|
268
|
+
|
269
|
+
## Gets the VCD variables with their long name.
|
270
|
+
def get_vars_with_fullname(vars_with_fullname = {})
|
271
|
+
# By default: nothing to do
|
272
|
+
end
|
273
|
+
|
274
|
+
## Gets the VCD variables with their idstr.
|
275
|
+
def get_vars_with_idstr(vars_with_idstr = {})
|
276
|
+
# By default: nothing to do
|
277
|
+
end
|
180
278
|
end
|
181
279
|
|
182
280
|
##
|
@@ -191,6 +289,11 @@ module HDLRuby::High
|
|
191
289
|
def get_vars_with_fullname(vars_with_fullname = {})
|
192
290
|
# By default: nothing to do
|
193
291
|
end
|
292
|
+
|
293
|
+
## Gets the VCD variables with their id string.
|
294
|
+
def get_vars_with_idstr(vars_with_idstr = {})
|
295
|
+
# By default: nothing to do
|
296
|
+
end
|
194
297
|
end
|
195
298
|
|
196
299
|
##
|
@@ -205,6 +308,11 @@ module HDLRuby::High
|
|
205
308
|
def get_vars_with_fullname(vars_with_fullname = {})
|
206
309
|
# By default: nothing to do
|
207
310
|
end
|
311
|
+
|
312
|
+
## Gets the VCD variables with their id string.
|
313
|
+
def get_vars_with_idstr(vars_with_idstr = {})
|
314
|
+
# By default: nothing to do
|
315
|
+
end
|
208
316
|
end
|
209
317
|
|
210
318
|
|
@@ -223,7 +331,8 @@ module HDLRuby::High
|
|
223
331
|
self.each_inner do |sig|
|
224
332
|
# puts "showing inner signal #{HDLRuby::High.vcd_name(sig.fullname)}"
|
225
333
|
vcdout << "$var wire #{sig.type.width} "
|
226
|
-
vcdout << "#{HDLRuby::High.vcd_name(sig.fullname)} "
|
334
|
+
# vcdout << "#{HDLRuby::High.vcd_name(sig.fullname)} "
|
335
|
+
vcdout << "#{HDLRuby::High.vcd_idstr(sig)} "
|
227
336
|
vcdout << "#{HDLRuby::High.vcd_name(sig.name)} $end\n"
|
228
337
|
end
|
229
338
|
# Recurse on the statements
|
@@ -248,6 +357,19 @@ module HDLRuby::High
|
|
248
357
|
end
|
249
358
|
return vars_with_fullname
|
250
359
|
end
|
360
|
+
|
361
|
+
## Gets the VCD variables with their id string.
|
362
|
+
def get_vars_with_idstr(vars_with_idstr = {})
|
363
|
+
# Adds the inner signals.
|
364
|
+
self.each_inner do |sig|
|
365
|
+
vars_with_idstr[sig] = HDLRuby::High.vcd_idstr(sig)
|
366
|
+
end
|
367
|
+
# Recurse on the statements.
|
368
|
+
self.each_statement do |stmnt|
|
369
|
+
stmnt.get_vars_with_idstr(vars_with_idstr)
|
370
|
+
end
|
371
|
+
return vars_with_idstr
|
372
|
+
end
|
251
373
|
end
|
252
374
|
|
253
375
|
|
@@ -292,6 +414,19 @@ module HDLRuby::High
|
|
292
414
|
self.no.get_vars_with_fullname(vars_with_fullname) if self.no
|
293
415
|
return vars_with_fullname
|
294
416
|
end
|
417
|
+
|
418
|
+
## Gets the VCD variables with their id string.
|
419
|
+
def get_vars_with_idstr(vars_with_idstr = {})
|
420
|
+
# Recurse on the yes.
|
421
|
+
self.yes.get_vars_with_idstr(vars_with_idstr)
|
422
|
+
# Recurse on the noifs.
|
423
|
+
self.each_noif do |cond,stmnt|
|
424
|
+
stmnt.get_vars_with_idstr(vars_with_idstr)
|
425
|
+
end
|
426
|
+
# Recure on the no if any.
|
427
|
+
self.no.get_vars_with_idstr(vars_with_idstr) if self.no
|
428
|
+
return vars_with_idstr
|
429
|
+
end
|
295
430
|
end
|
296
431
|
|
297
432
|
|
@@ -318,5 +453,41 @@ module HDLRuby::High
|
|
318
453
|
self.default.get_vars_with_fullname(vars_with_fullname)
|
319
454
|
return vars_with_fullname
|
320
455
|
end
|
456
|
+
|
457
|
+
## Gets the VCD variables with their id string.
|
458
|
+
def get_vars_with_idstr(vars_with_idstr = {})
|
459
|
+
# Recurse on each when.
|
460
|
+
self.each_when do |w|
|
461
|
+
w.statement.get_vars_with_idstr(vars_with_idstr)
|
462
|
+
end
|
463
|
+
# Recurse on the default if any.
|
464
|
+
self.default.get_vars_with_idstr(vars_with_idstr)
|
465
|
+
return vars_with_idstr
|
466
|
+
end
|
321
467
|
end
|
468
|
+
|
469
|
+
##
|
470
|
+
# Enhance the TimeRepeat class with VCD support.
|
471
|
+
class TimeRepeat
|
472
|
+
## Shows the hierarchy of the variables.
|
473
|
+
def show_hierarchy(vcdout)
|
474
|
+
# Recurse on the statement.
|
475
|
+
self.statement.show_hierarchy(vcdout)
|
476
|
+
end
|
477
|
+
|
478
|
+
## Gets the VCD variables with their long name.
|
479
|
+
def get_vars_with_fullname(vars_with_fullname = {})
|
480
|
+
# Recurse on the statement.
|
481
|
+
self.statement.get_vars_with_fullname(vars_with_fullname)
|
482
|
+
return vars_with_fullname
|
483
|
+
end
|
484
|
+
|
485
|
+
## Gets the VCD variables with their id string.
|
486
|
+
def get_vars_with_idstr(vars_with_idstr = {})
|
487
|
+
# Recurse on the statement.
|
488
|
+
self.statement.get_vars_with_idstr(vars_with_idstr)
|
489
|
+
return vars_with_idstr
|
490
|
+
end
|
491
|
+
end
|
492
|
+
|
322
493
|
end
|