Class: HDLRuby::Low::SystemT
- Inherits:
-
Base::SystemT
- Object
- Base::SystemT
- HDLRuby::Low::SystemT
- Includes:
- ForceName, Hparent, Low2Symbol
- Defined in:
- lib/HDLRuby/hruby_db.rb,
lib/HDLRuby/hruby_low.rb,
lib/HDLRuby/hruby_low2c.rb,
lib/HDLRuby/hruby_low2hdr.rb,
lib/HDLRuby/hruby_low2seq.rb,
lib/HDLRuby/hruby_low2sym.rb,
lib/HDLRuby/hruby_low2vhd.rb,
lib/HDLRuby/hruby_verilog.rb,
lib/HDLRuby/hruby_low2high.rb,
lib/HDLRuby/hruby_low_cleanup.rb,
lib/HDLRuby/hruby_low_mutable.rb,
lib/HDLRuby/hruby_low_resolve.rb,
lib/HDLRuby/hruby_low_skeleton.rb,
lib/HDLRuby/hruby_low_with_var.rb,
lib/HDLRuby/hruby_low_fix_types.rb,
lib/HDLRuby/hruby_low_with_bool.rb,
lib/HDLRuby/hruby_low_with_port.rb,
lib/HDLRuby/hruby_low_bool2select.rb,
lib/HDLRuby/hruby_low_without_concat.rb,
lib/HDLRuby/hruby_low_without_select.rb,
lib/HDLRuby/backend/hruby_c_allocator.rb,
lib/HDLRuby/hruby_low_without_outread.rb,
lib/HDLRuby/hruby_low_without_parinseq.rb,
lib/HDLRuby/hruby_low_without_namespace.rb,
lib/HDLRuby/hruby_low_without_bit2vector.rb,
lib/HDLRuby/hruby_low_without_connection.rb,
lib/HDLRuby/hruby_low_casts_without_expression.rb
Overview
Extends the SystemT class with functionality for extracting expressions from cast.
Direct Known Subclasses
Constant Summary
Constants included from Low2Symbol
Low2Symbol::Low2SymbolPrefix, Low2Symbol::Low2SymbolTable, Low2Symbol::Symbol2LowTable
Instance Attribute Summary collapse
-
#name ⇒ Object
readonly
The name of the system.
-
#scope ⇒ Object
readonly
The scope of the system type.
Attributes included from Hparent
Class Method Summary collapse
-
.get(name) ⇒ Object
Get an existing system type by +name+.
Instance Method Summary collapse
-
#add_inout(signal) ⇒ Object
Adds inout +signal+.
-
#add_input(signal) ⇒ Object
Adds input +signal+.
-
#add_output(signal) ⇒ Object
Adds output +signal+.
-
#bit2vector2inner! ⇒ Object
Replace bit to vector conversions by assignment to on bit of an intermediate inner vector.
-
#blocks2seq! ⇒ Object
Converts the par sub blocks to seq.
-
#boolean_in_assign2select! ⇒ Object
Converts booleans in assignments to select operators.
-
#break_concat_assigns! ⇒ Object
Breaks the assignments to concats.
-
#break_types! ⇒ Object
Breaks the hierarchical types into sequences of type definitions.
-
#c_code_allocate(allocator) ⇒ Object
Allocates signals within C code using +allocator+.
-
#casts_without_expression! ⇒ Object
Extracts the expressions from the casts.
-
#cleanup! ⇒ Object
Cleans up.
-
#connections_to_behaviors! ⇒ Object
Remove the connections and replace them by behaviors.
-
#delete_inout!(signal) ⇒ Object
Deletes an inout.
-
#delete_input!(signal) ⇒ Object
Deletes an input.
-
#delete_output!(signal) ⇒ Object
Deletes an output.
-
#each_deep(&ruby_block) ⇒ Object
Iterates over each object deeply.
-
#each_inout(&ruby_block) ⇒ Object
Iterates over the inout signals.
-
#each_input(&ruby_block) ⇒ Object
Iterates over the input signals.
-
#each_output(&ruby_block) ⇒ Object
Iterates over the output signals.
-
#each_signal(&ruby_block) ⇒ Object
Iterates over all the signals of the interface of the system.
-
#each_signal_all(&ruby_block) ⇒ Object
Iterates over all the signals of the system including its scope (input, output, inout, inner).
-
#each_signal_deep(&ruby_block) ⇒ Object
Iterates over all the signals of the system type and its scope.
-
#each_systemT_deep(&ruby_block) ⇒ Object
Iterates over the systemT deeply if any.
-
#each_systemT_deep_ref(&ruby_block) ⇒ Object
Iterates over the systemT deeply if any in order of reference to ensure the refered elements are processed first.
-
#eql?(obj) ⇒ Boolean
Comparison for hash: structural comparison.
-
#explicit_types! ⇒ Object
Explicit the types conversions in the system.
-
#extract_port_assign!(systemI, signal) ⇒ Object
Extracts the assignments to port +systemI.signal+ and returns the resulting reference to a port wire.
-
#get_all_inouts ⇒ Object
Gets an array containing all the inout signals.
-
#get_all_inputs ⇒ Object
Gets an array containing all the input signals.
-
#get_all_outputs ⇒ Object
Gets an array containing all the output signals.
-
#get_all_signals ⇒ Object
Gets an array containing all the signals.
-
#get_by_name(name) ⇒ Object
Find an inner object by +name+.
-
#get_inout(name) ⇒ Object
Gets an inout signal by +name+.
-
#get_input(name) ⇒ Object
Gets an input signal by +name+.
-
#get_interface(i) ⇒ Object
Gets an interface signal by order of declaration +i+.
-
#get_output(name) ⇒ Object
Gets an output signal by +name+.
-
#get_signal(name) ⇒ Object
Gets a signal by +name+.
-
#has_inout? ⇒ Boolean
Tells if there is any output signal.
-
#has_input? ⇒ Boolean
Tells if there is any input signal.
-
#has_output? ⇒ Boolean
Tells if there is any output signal.
-
#has_signal? ⇒ Boolean
Tells if there is any signal (including in the scope of the system).
-
#hash ⇒ Object
Hash function.
-
#initial_concat_to_timed! ⇒ Object
Converts initial concat of values of signals to assignment in timed blocks (for making the code compatible with verilog translation).
-
#initialize(name, scope) ⇒ SystemT
constructor
Creates a new system type named +name+ with +scope+.
-
#map_inouts!(&ruby_block) ⇒ Object
Maps on the inouts.
-
#map_inputs!(&ruby_block) ⇒ Object
Maps on the inputs.
-
#map_outputs!(&ruby_block) ⇒ Object
Maps on the outputs.
-
#mixblocks2seq! ⇒ Object
Converts the par sub blocks to seq if they are not full par.
-
#outread2inner! ⇒ Object
Replace read of output signal to read of intermediate inner signal.
-
#par_in_seq2seq! ⇒ Object
Converts par blocks within seq blocks to seq blocks.
-
#port_assign?(expr, systemI, signal) ⇒ Boolean
Tells if an expression is a reference to port +systemI.signal+.
-
#port_output_connection?(connection) ⇒ Boolean
Tells if a connection is actually a port connection.
-
#replace_names!(former, nname) ⇒ Object
Replaces recursively +former+ name by +nname+ until it is redeclared.
-
#select2case! ⇒ Object
Converts the Select expressions to Case statements.
-
#set_name!(name) ⇒ Object
Sets the +name+.
-
#set_scope!(scope) ⇒ Object
Sets the +scope+.
-
#to_c(res, level = 0, *hnames) ⇒ Object
Generates the text of the equivalent HDLRuby code.
-
#to_c_code(res, level) ⇒ Object
Generates the code for an execution starting from the system.
-
#to_ch(res) ⇒ Object
Generates the content of the h file.
-
#to_global_systemTs! ⇒ Object
Moves local systemTs to global.
-
#to_hdr(level = 0) ⇒ Object
Generates the text of the equivalent hdr text.
-
#to_high ⇒ Object
Creates a new high system type named +name+ with +scope+.
-
#to_upper_space! ⇒ Object
Moves the declarations to the upper namespace.
-
#to_verilog(vcd = false) ⇒ Object
Converts the system to Verilog code.
-
#to_vhdl(level = 0) ⇒ Object
Generates the text of the equivalent HDLRuby::High code.
-
#with_boolean! ⇒ Object
Converts to a variable-compatible system.
-
#with_port! ⇒ Object
Converts to a port-compatible system.
-
#with_var! ⇒ Object
Converts to a variable-compatible system.
-
#wrapper ⇒ Object
Gets the configuration wrapper if any.
-
#wrapper=(systemT) ⇒ Object
Sets the configuration wrapper to +systemT+.
Methods included from ForceName
Methods included from Low2Symbol
Methods included from Hparent
Constructor Details
#initialize(name, scope) ⇒ SystemT
Creates a new system type named +name+ with +scope+.
31 32 33 34 35 36 37 38 |
# File 'lib/HDLRuby/hruby_db.rb', line 31 def initialize(name) # Initialize the system type structure. super(name) # Update the library of existing system types. # Note: no check is made so an exisiting system type with a same # name is overwritten. SystemTs[@name] = self end |
Instance Attribute Details
#name ⇒ Object (readonly)
The name of the system.
95 96 97 |
# File 'lib/HDLRuby/hruby_low.rb', line 95 def name @name end |
#scope ⇒ Object (readonly)
The scope of the system type.
98 99 100 |
# File 'lib/HDLRuby/hruby_low.rb', line 98 def scope @scope end |
Class Method Details
.get(name) ⇒ Object
Get an existing system type by +name+.
25 26 27 28 |
# File 'lib/HDLRuby/hruby_db.rb', line 25 def self.get(name) return name if name.is_a?(SystemT) return SystemTs[name.to_sym] end |
Instance Method Details
#add_inout(signal) ⇒ Object
Adds inout +signal+.
244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 |
# File 'lib/HDLRuby/hruby_low.rb', line 244 def add_inout(signal) # Check and add the signal. unless signal.is_a?(SignalI) raise AnyError, "Invalid class for a signal instance: #{signal.class}" end # if @inouts.include?(signal) then # raise AnyError, "SignalI #{signal.name} already present." # end if @inouts.include?(signal) then signal.parent = self # Replace the signal. old_signal = @inouts[signal.name] @inouts.add(signal) @interface[@interface.index(old_signal)] = signal else # Set the parent of the signal. signal.parent = self # And add the signal. @inouts.add(signal) @interface << signal end return signal end |
#add_input(signal) ⇒ Object
Adds input +signal+.
191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 |
# File 'lib/HDLRuby/hruby_low.rb', line 191 def add_input(signal) # print "In #{self} add_input with signal: #{signal.name}\n" # Check and add the signal. unless signal.is_a?(SignalI) raise AnyError, "Invalid class for a signal instance: #{signal.class}" end # if @inputs.include?(signal) then # raise AnyError, "SignalI #{signal.name} already present." # end if @inputs.include?(signal) then signal.parent = self # Replace the signal. old_signal = @inputs[signal.name] @inputs.add(signal) @interface[@interface.index(old_signal)] = signal else # Set the parent of the signal. signal.parent = self # And add the signal. @inputs.add(signal) @interface << signal end return signal end |
#add_output(signal) ⇒ Object
Adds output +signal+.
218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 |
# File 'lib/HDLRuby/hruby_low.rb', line 218 def add_output(signal) # Check and add the signal. unless signal.is_a?(SignalI) raise AnyError, "Invalid class for a signal instance: #{signal.class}" end # if @outputs.include?(signal) then # raise AnyError, "SignalI #{signal.name} already present." # end if @outputs.include?(signal) then signal.parent = self # Replace the signal. old_signal = @outputs[signal.name] @outputs.add(signal) @interface[@interface.index(old_signal)] = signal else # Set the parent of the signal. signal.parent = self # And add the signal. @outputs.add(signal) @interface << signal end return signal end |
#bit2vector2inner! ⇒ Object
Replace bit to vector conversions by assignment to on bit of an intermediate inner vector.
NOTE: the result is the same systemT.
23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 |
# File 'lib/HDLRuby/hruby_low_without_bit2vector.rb', line 23 def bit2vector2inner! # puts "For system: #{self.name}" # First gather the bit conversions to vector. bits2vectors = Set.new gather_bits2vectors = proc do |node| if node.is_a?(Expression) && node.type == Bit && node.parent.is_a?(Expression) && # References are not relevant parents !node.parent.is_a?(Ref) && # Neither do concat that are processed separatly !node.parent.is_a?(Concat) && node.parent.type != Bit then # puts "node=#{node.to_high}, node.parent=#{node.parent}" bits2vectors.add(node) end end # Apply the procedure for gathering the read on outputs signals. self.scope.each_scope_deep do |scope| scope.each_connection do |connection| # Recurse on the connection. connection.each_node_deep(&gather_bits2vectors) end scope.each_behavior do |behavior| behavior.each_event do |event| gather_bits2vectors.(event.ref) end behavior.each_statement do |statement| # puts "statement=#{statement.class}" statement.each_node_deep(&gather_bits2vectors) end end end # puts "bits2vectors=#{bits2vectors.size}" # Create the 1-bit-vector type. vec1T = TypeVector.new(:"bit1",Bit,0..0) # Generate one inner 1-bit-vector signal per read output. bit2inner = {} bits2vectors.each do |node| # Generate the inner variable. sig = self.scope.add_inner(SignalI.new(HDLRuby::uniq_name,vec1T)) ref = RefName.new(vec1T,RefThis.new,sig.name) bit2inner[node] = [ ref, RefIndex.new(Bit,ref,Value.new(Integer,0)) ] # puts "new inner=#{out2inner[name].name}" end # Apply the replacement procedure on the code self.scope.each_scope_deep do |scope| scope.each_connection.to_a.each do |connection| connection.reassign_expressions!(bit2inner) end scope.each_behavior do |behavior| behavior.each_event do |event| event.reassign_expressions!(bit2inner) end behavior.block.reassign_expressions!(bit2inner) end end return self end |
#blocks2seq! ⇒ Object
Converts the par sub blocks to seq.
21 22 23 24 25 |
# File 'lib/HDLRuby/hruby_low2seq.rb', line 21 def blocks2seq! # Recurse on the scope. self.scope.to_seq! return self end |
#boolean_in_assign2select! ⇒ Object
Converts booleans in assignments to select operators.
22 23 24 25 |
# File 'lib/HDLRuby/hruby_low_bool2select.rb', line 22 def boolean_in_assign2select! self.scope.boolean_in_assign2select! return self end |
#break_concat_assigns! ⇒ Object
Breaks the assignments to concats.
21 22 23 |
# File 'lib/HDLRuby/hruby_low_without_concat.rb', line 21 def break_concat_assigns! self.scope.break_concat_assigns! end |
#break_types! ⇒ Object
Breaks the hierarchical types into sequences of type definitions.
76 77 78 |
# File 'lib/HDLRuby/hruby_low_without_namespace.rb', line 76 def break_types! self.scope.break_types! end |
#c_code_allocate(allocator) ⇒ Object
Allocates signals within C code using +allocator+.
18 19 20 |
# File 'lib/HDLRuby/backend/hruby_c_allocator.rb', line 18 def c_code_allocate(allocator) self.scope.c_code_allocate(allocator) end |
#casts_without_expression! ⇒ Object
Extracts the expressions from the casts.
23 24 25 26 |
# File 'lib/HDLRuby/hruby_low_casts_without_expression.rb', line 23 def casts_without_expression! self.scope.casts_without_expression! return self end |
#cleanup! ⇒ Object
Cleans up.
22 23 24 25 26 27 28 |
# File 'lib/HDLRuby/hruby_low_cleanup.rb', line 22 def cleanup! # Gather the output and inout signals' names, they are used to # identify the signals that can be removed. keep = self.each_output.map {|sig| sig.name } + self.each_inout.map {|sig| sig.name } self.scope.cleanup!(keep) end |
#connections_to_behaviors! ⇒ Object
Remove the connections and replace them by behaviors. NOTE: one behavior is created for input connections and one for output ones while inout/inner-only connections are copied in both behaviors.
25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 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 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 |
# File 'lib/HDLRuby/hruby_low_without_connection.rb', line 25 def connections_to_behaviors! # Process the connections: create a behavior containing # them all within a par block. self.scope.each_scope_deep do |scope| if scope.each_connection.to_a.any? then inputs_blk = Block.new(:par) outputs_blk = Block.new(:par) timed_blk = TimeBlock.new(:seq) scope.each_connection do |connection| # puts "For connection: #{connection}" # Check the left and right of the connection # for input or output port. left = connection.left left_r = left.resolve # puts "left_r=#{left_r.name}" if left_r # puts "left_r.parent=#{left_r.parent.name}" if left_r && left_r.parent right = connection.right right_r = right.resolve if right.respond_to?(:resolve) # puts "right_r=#{right_r.name}" if right_r # puts "right_r.parent=#{right_r.parent.name}" if right_r && right_r.parent # if right.is_a?(Value) then if right.immutable? then # Right is value, the new transmit is to add # to the timed block. timed_blk.add_statement( Transmit.new(left.clone,right.clone)) # No more process for this connection. next end # Check if left is an input or an output. left_is_i = left_is_o = false if left_r && left_r.parent.is_a?(SystemT) then if left_r.parent.each_input.include?(left_r) then # puts "Left is input." # puts "Left is from systemI: #{left.from_systemI?}" left_is_i = left.from_systemI? left_is_o = !left_is_i elsif left_r.parent.each_output.include?(left_r) then # puts "Left is output." # puts "Left is from systemI: #{left.from_systemI?}" left_is_o = left.from_systemI? left_is_i = !left_is_o end end # Check if right is an input or an output. right_is_i = right_is_o = false if right_r && right_r.parent.is_a?(SystemT) then if right_r.parent.each_input.include?(right_r) then # puts "Right is input." # puts "Right is from systemI: #{right.from_systemI?}" right_is_i = right.from_systemI? right_is_o = !right_is_i elsif right_r.parent.each_output.include?(right_r) then # puts "Right is output." # puts "Right is from systemI: #{right.from_systemI?}" right_is_o = right.from_systemI? right_is_i = !right_is_o end end # puts "left_is_i=#{left_is_i} left_is_o=#{left_is_o}" # puts "right_is_i=#{right_is_i} right_is_o=#{right_is_o}" # Fills the relevant block. if (left_is_i) then inputs_blk.add_statement( Transmit.new(left.clone,right.clone)) elsif (right_is_i) then inputs_blk.add_statement( Transmit.new(right.clone,left.clone)) elsif (left_is_o) then # puts "left=#{left} right=#{right}" outputs_blk.add_statement( Transmit.new(right.clone,left.clone)) elsif (right_is_o) then outputs_blk.add_statement( Transmit.new(left.clone,right.clone)) else # # puts "left/right is inout" # if (left.is_a?(Ref)) then # inputs_blk.add_statement( # Transmit.new(left.clone,right.clone)) # end # if (right.is_a?(Ref)) then # outputs_blk.add_statement( # Transmit.new(right.clone,left.clone)) # end # Both or neither input/output, make a behavior # for each. if (left.is_a?(Ref) && !(left_r && left_r.immutable?)) then blk = Block.new(:par) blk.add_statement( Transmit.new(left.clone,right.clone)) scope.add_behavior(Behavior.new(blk)) end if (right.is_a?(Ref) && !(right_r && right_r.immutable?)) then blk = Block.new(:par) blk.add_statement( Transmit.new(right.clone,left.clone)) scope.add_behavior(Behavior.new(blk)) end end end # Adds the behaviors. if inputs_blk.each_statement.any? then scope.add_behavior(Behavior.new(inputs_blk)) end if outputs_blk.each_statement.any? then scope.add_behavior(Behavior.new(outputs_blk)) end if timed_blk.each_statement.any? then scope.add_behavior(TimeBehavior.new(timed_blk)) end end end end |
#delete_inout!(signal) ⇒ Object
Deletes an inout.
87 88 89 90 91 92 93 94 95 96 |
# File 'lib/HDLRuby/hruby_low_mutable.rb', line 87 def delete_inout!(signal) if @inouts.key?(signal.name) then # The signal is present, delete it. @inouts.delete(signal.name) @interface.delete(signal) # And remove its parent. signal.parent = nil end signal end |
#delete_input!(signal) ⇒ Object
Deletes an input.
63 64 65 66 67 68 69 70 71 72 |
# File 'lib/HDLRuby/hruby_low_mutable.rb', line 63 def delete_input!(signal) if @inputs.key?(signal.name) then # The signal is present, delete it. @inputs.delete(signal.name) @interface.delete(signal) # And remove its parent. signal.parent = nil end signal end |
#delete_output!(signal) ⇒ Object
Deletes an output.
75 76 77 78 79 80 81 82 83 84 |
# File 'lib/HDLRuby/hruby_low_mutable.rb', line 75 def delete_output!(signal) if @outputs.key?(signal.name) then # The signal is present, delete it. @outputs.delete(signal.name) @interface.delete(signal) # And remove its parent. signal.parent = nil end signal end |
#each_deep(&ruby_block) ⇒ Object
Iterates over each object deeply.
Returns an enumerator if no ruby block is given.
449 450 451 452 453 454 455 456 457 458 459 460 461 462 |
# File 'lib/HDLRuby/hruby_low.rb', line 449 def each_deep(&ruby_block) # No ruby block? Return an enumerator. return to_enum(:each_deep) unless ruby_block # A ruby block? First apply it to current. ruby_block.call(self) # Then apply on each signal. self.each_signal do |signal| signal.each_deep(&ruby_block) end # Then apply on each scope. self.each_scope do |scope| scope.each_deep(&ruby_block) end end |
#each_inout(&ruby_block) ⇒ Object
Iterates over the inout signals.
Returns an enumerator if no ruby block is given.
292 293 294 295 296 297 |
# File 'lib/HDLRuby/hruby_low.rb', line 292 def each_inout(&ruby_block) # No ruby block? Return an enumerator. return to_enum(:each_inout) unless ruby_block # A ruby block? Apply it on each inout signal instance. @inouts.each(&ruby_block) end |
#each_input(&ruby_block) ⇒ Object
Iterates over the input signals.
Returns an enumerator if no ruby block is given.
272 273 274 275 276 277 |
# File 'lib/HDLRuby/hruby_low.rb', line 272 def each_input(&ruby_block) # No ruby block? Return an enumerator. return to_enum(:each_input) unless ruby_block # A ruby block? Apply it on each input signal instance. @inputs.each(&ruby_block) end |
#each_output(&ruby_block) ⇒ Object
Iterates over the output signals.
Returns an enumerator if no ruby block is given.
282 283 284 285 286 287 |
# File 'lib/HDLRuby/hruby_low.rb', line 282 def each_output(&ruby_block) # No ruby block? Return an enumerator. return to_enum(:each_output) unless ruby_block # A ruby block? Apply it on each output signal instance. @outputs.each(&ruby_block) end |
#each_signal(&ruby_block) ⇒ Object
Iterates over all the signals of the interface of the system.
Returns an enumerator if no ruby block is given.
303 304 305 306 307 308 |
# File 'lib/HDLRuby/hruby_low.rb', line 303 def each_signal(&ruby_block) # No ruby block? Return an enumerator. return to_enum(:each_signal) unless ruby_block # A ruby block? Apply it on each signal instance. @interface.each(&ruby_block) end |
#each_signal_all(&ruby_block) ⇒ Object
Iterates over all the signals of the system including its scope (input, output, inout, inner).
Returns an enumerator if no ruby block is given.
314 315 316 317 318 319 320 321 322 323 |
# File 'lib/HDLRuby/hruby_low.rb', line 314 def each_signal_all(&ruby_block) # No ruby block? Return an enumerator. return to_enum(:each_signal) unless ruby_block # A ruby block? Apply it on each signal instance. @inputs.each(&ruby_block) @outputs.each(&ruby_block) @inouts.each(&ruby_block) # And each signal of the direct scope. @scope.each_signal(&ruby_block) end |
#each_signal_deep(&ruby_block) ⇒ Object
Iterates over all the signals of the system type and its scope.
326 327 328 329 330 331 332 333 334 335 336 |
# File 'lib/HDLRuby/hruby_low.rb', line 326 def each_signal_deep(&ruby_block) # No ruby block? Return an enumerator. return to_enum(:each_signal_deep) unless ruby_block # A ruby block? # First iterate over the current system type's signals. # self.each_signal_all(&ruby_block) self.each_signal(&ruby_block) # Then apply on the behaviors (since in HDLRuby:High, blocks can # include signals). @scope.each_signal_deep(&ruby_block) end |
#each_systemT_deep(&ruby_block) ⇒ Object
Iterates over the systemT deeply if any.
Returns an enumerator if no ruby block is given.
467 468 469 470 471 472 473 474 475 476 477 478 479 480 481 |
# File 'lib/HDLRuby/hruby_low.rb', line 467 def each_systemT_deep(&ruby_block) # No ruby block? Return an enumerator. return to_enum(:each_systemT_deep) unless ruby_block # A ruby block? First apply it to current. ruby_block.call(self) # And recurse on the systemT accessible through the instances. self.scope.each_scope_deep do |scope| scope.each_systemI do |systemI| # systemI.systemT.each_systemT_deep(&ruby_block) systemI.each_systemT do |systemT| systemT.each_systemT_deep(&ruby_block) end end end end |
#each_systemT_deep_ref(&ruby_block) ⇒ Object
Iterates over the systemT deeply if any in order of reference to ensure the refered elements are processed first.
Returns an enumerator if no ruby block is given.
487 488 489 490 491 492 493 494 495 496 497 498 499 500 501 502 |
# File 'lib/HDLRuby/hruby_low.rb', line 487 def each_systemT_deep_ref(&ruby_block) # No ruby block? Return an enumerator. return to_enum(:each_systemT_deep_ref) unless ruby_block # A ruby block? # Recurse on the systemT accessible through the instances. self.scope.each_scope_deep do |scope| scope.each_systemI do |systemI| # systemI.systemT.each_systemT_deep(&ruby_block) systemI.each_systemT do |systemT| systemT.each_systemT_deep_ref(&ruby_block) end end end # Finally apply it to current. ruby_block.call(self) end |
#eql?(obj) ⇒ Boolean
Comparison for hash: structural comparison.
141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 |
# File 'lib/HDLRuby/hruby_low.rb', line 141 def eql?(obj) return false unless obj.is_a?(SystemT) return false unless @name.eql?(obj.name) return false unless @scope.eql?(obj.scope) idx = 0 obj.each_input do |input| return false unless @inputs[input.name].eql?(input) idx += 1 end return false unless idx == @inputs.size idx = 0 obj.each_output do |output| return false unless @outputs[output.name].eql?(output) idx += 1 end return false unless idx == @outputs.size idx = 0 obj.each_inout do |inout| return false unless @inouts[inout.name].eql?(inout) idx += 1 end return false unless idx == @inouts.size return true end |
#explicit_types! ⇒ Object
Explicit the types conversions in the system.
18 19 20 21 22 |
# File 'lib/HDLRuby/hruby_low_fix_types.rb', line 18 def explicit_types! # No direct fix required in the system, recurse on the scope. self.scope.explicit_types! return self end |
#extract_port_assign!(systemI, signal) ⇒ Object
Extracts the assignments to port +systemI.signal+ and returns the resulting reference to a port wire.
NOTE: assumes to_upper_space! and with_port! has been called.
1849 1850 1851 1852 1853 1854 1855 1856 1857 1858 1859 1860 1861 1862 1863 1864 1865 1866 1867 1868 1869 |
# File 'lib/HDLRuby/hruby_verilog.rb', line 1849 def extract_port_assign!(systemI,signal) # Extract the assignment. assign = nil self.each_connection.to_a.each do |connection| if self.port_assign?(connection.left,systemI,signal) then # The left is the port. # Delete the connection. self.scope.delete_connection!(connection) # And return a copy of the right. return connection.right.clone elsif self.port_assign?(connection.right,systemI,signal) then # The right is the port. # Delete the connection. self.scope.delete_connection!(connection) # And return a copy of the left. return connection.left.clone end end # No port found, nothing to do return nil end |
#get_all_inouts ⇒ Object
Gets an array containing all the inout signals.
370 371 372 |
# File 'lib/HDLRuby/hruby_low.rb', line 370 def get_all_inouts return each_inout.to_a end |
#get_all_inputs ⇒ Object
Gets an array containing all the input signals.
360 361 362 |
# File 'lib/HDLRuby/hruby_low.rb', line 360 def get_all_inputs return each_input.to_a end |
#get_all_outputs ⇒ Object
Gets an array containing all the output signals.
365 366 367 |
# File 'lib/HDLRuby/hruby_low.rb', line 365 def get_all_outputs return each_output.to_a end |
#get_all_signals ⇒ Object
Gets an array containing all the signals.
375 376 377 |
# File 'lib/HDLRuby/hruby_low.rb', line 375 def get_all_signals return each_signal.to_a end |
#get_by_name(name) ⇒ Object
Find an inner object by +name+. NOTE: return nil if not found.
20 21 22 23 24 25 26 27 28 29 30 |
# File 'lib/HDLRuby/hruby_low_resolve.rb', line 20 def get_by_name(name) # Ensure the name is a symbol. name = name.to_sym # Look in the interface. found = self.get_signal(name) return found if found # Maybe it is the scope. return self.scope if self.scope.name == name # Look in the scope. return self.scope.get_by_name(name) end |
#get_inout(name) ⇒ Object
Gets an inout signal by +name+.
390 391 392 |
# File 'lib/HDLRuby/hruby_low.rb', line 390 def get_inout(name) return @inouts[name.to_sym] end |
#get_input(name) ⇒ Object
Gets an input signal by +name+.
380 381 382 |
# File 'lib/HDLRuby/hruby_low.rb', line 380 def get_input(name) return @inputs[name.to_sym] end |
#get_interface(i) ⇒ Object
Gets an interface signal by order of declaration +i+.
406 407 408 |
# File 'lib/HDLRuby/hruby_low.rb', line 406 def get_interface(i) return @interface[i] end |
#get_output(name) ⇒ Object
Gets an output signal by +name+.
385 386 387 |
# File 'lib/HDLRuby/hruby_low.rb', line 385 def get_output(name) return @outputs[name.to_sym] end |
#get_signal(name) ⇒ Object
Gets a signal by +name+.
400 401 402 403 |
# File 'lib/HDLRuby/hruby_low.rb', line 400 def get_signal(name) return get_input(name) || get_output(name) || get_inout(name) # || # get_inner(name) end |
#has_inout? ⇒ Boolean
Tells if there is any output signal.
349 350 351 |
# File 'lib/HDLRuby/hruby_low.rb', line 349 def has_inout? return !@inouts.empty? end |
#has_input? ⇒ Boolean
Tells if there is any input signal.
339 340 341 |
# File 'lib/HDLRuby/hruby_low.rb', line 339 def has_input? return !@inputs.empty? end |
#has_output? ⇒ Boolean
Tells if there is any output signal.
344 345 346 |
# File 'lib/HDLRuby/hruby_low.rb', line 344 def has_output? return !@outputs.empty? end |
#has_signal? ⇒ Boolean
Tells if there is any signal (including in the scope of the system).
354 355 356 357 |
# File 'lib/HDLRuby/hruby_low.rb', line 354 def has_signal? return ( self.has_input? or self.has_output? or self.has_inout? or self.has_inner? ) end |
#hash ⇒ Object
Hash function.
167 168 169 |
# File 'lib/HDLRuby/hruby_low.rb', line 167 def hash return [@name,@scope,@inputs,@outputs,@inouts].hash end |
#initial_concat_to_timed! ⇒ Object
Converts initial concat of values of signals to assignment in timed blocks (for making the code compatible with verilog translation).
NOTE: Assumes such array as at the top level.
30 31 32 |
# File 'lib/HDLRuby/hruby_low_without_concat.rb', line 30 def initial_concat_to_timed! self.scope.initial_concat_to_timed! end |
#map_inouts!(&ruby_block) ⇒ Object
Maps on the inouts.
54 55 56 57 58 59 60 |
# File 'lib/HDLRuby/hruby_low_mutable.rb', line 54 def map_inouts!(&ruby_block) @inouts.map! do |inout| inout = ruby_block.call(inout) inout.parent = self unless inout.parent inout end end |
#map_inputs!(&ruby_block) ⇒ Object
Maps on the inputs.
36 37 38 39 40 41 42 |
# File 'lib/HDLRuby/hruby_low_mutable.rb', line 36 def map_inputs!(&ruby_block) @inputs.map! do |input| input = ruby_block.call(input) input.parent = self unless input.parent input end end |
#map_outputs!(&ruby_block) ⇒ Object
Maps on the outputs.
45 46 47 48 49 50 51 |
# File 'lib/HDLRuby/hruby_low_mutable.rb', line 45 def map_outputs!(&ruby_block) @outputs.map! do |output| output = ruby_block.call(output) output.parent = self unless output.parent output end end |
#mixblocks2seq! ⇒ Object
Converts the par sub blocks to seq if they are not full par.
28 29 30 31 |
# File 'lib/HDLRuby/hruby_low2seq.rb', line 28 def mixblocks2seq! # Recurse on the scope. self.scope.mixblocks2seq! end |
#outread2inner! ⇒ Object
Replace read of output signal to read of intermediate inner signal.
NOTE: the result is the same systemT.
23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 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 |
# File 'lib/HDLRuby/hruby_low_without_outread.rb', line 23 def outread2inner! # puts "For system: #{self.name}" # First gather the read on output signals. outreads = {} gather_outreads = proc do |node| # puts "node=#{node.name}" if node.is_a?(RefName) if node.is_a?(RefName) && !node.leftvalue? then name = node.name # puts "name=#{name}" sig = self.get_output(name) outreads[node.name] = node if sig end end # Apply the procedure for gathering the read on outputs signals. self.scope.each_scope_deep do |scope| scope.each_connection do |connection| connection.each_node_deep(&gather_outreads) end scope.each_behavior do |behavior| behavior.each_event do |event| gather_outreads.(event.ref) end behavior.each_statement do |statement| # puts "statement=#{statement.class}" statement.each_node_deep(&gather_outreads) end end end # puts "outreads=#{outreads.keys}" # Generate one inner signal per read output. out2inner = {} outreads.each do |name,node| # Generate the inner variable. out2inner[name] = self.scope.add_inner(SignalI.new(HDLRuby::uniq_name,node.type)) # puts "new inner=#{out2inner[name].name}" end # Replace the output by the corresponding inner in the # expressions. replace_name = proc do |node| # The replacement procedure. # Only single name reference are to be replaced, the others # cannot correspond to output signal. if node.is_a?(RefName) && node.ref.is_a?(RefThis) && !node.parent.is_a?(RefName) then inner = out2inner[node.name] # puts "node=#{node.name} inner=#{inner}" # puts "Replace name: #{node.name} by #{inner.name}" if inner node.set_name!(inner.name) if inner end end # Apply the replacement procedure on the code self.scope.each_scope_deep do |scope| scope.each_connection do |connection| connection.each_node_deep do |node| replace_name.(node) end end scope.each_behavior do |behavior| behavior.each_event do |event| event.ref.each_node_deep do |node| replace_name.(node) end end behavior.each_statement do |statement| statement.each_node_deep do |node| replace_name.(node) end end end end # Finally connect the inner to the output. out2inner.each do |out,inner| self.scope.add_connection( Connection.new(RefName.new(inner.type,RefThis.new,out), RefName.new(inner.type,RefThis.new,inner.name))) end return self end |
#par_in_seq2seq! ⇒ Object
Converts par blocks within seq blocks to seq blocks.
21 22 23 |
# File 'lib/HDLRuby/hruby_low_without_parinseq.rb', line 21 def par_in_seq2seq! self.scope.par_in_seq2seq! end |
#port_assign?(expr, systemI, signal) ⇒ Boolean
Tells if an expression is a reference to port +systemI.signal+.
1840 1841 1842 1843 |
# File 'lib/HDLRuby/hruby_verilog.rb', line 1840 def port_assign?(expr, systemI, signal) return expr.is_a?(RefName) && expr.name == signal.name && expr.ref.is_a?(RefName) && expr.ref.name == systemI.name end |
#port_output_connection?(connection) ⇒ Boolean
Tells if a connection is actually a port connection.
1826 1827 1828 1829 1830 1831 1832 1833 1834 1835 1836 1837 |
# File 'lib/HDLRuby/hruby_verilog.rb', line 1826 def port_output_connection?(connection) return self.each_systemI.find do |systemI| if connection.right.is_a?(RefName) && connection.right.ref.is_a?(RefName) && systemI.name == connection.right.ref.name puts "port_connection for right=#{connection.right.name} and systemI=#{systemI.name}" true else false end end end |
#replace_names!(former, nname) ⇒ Object
Replaces recursively +former+ name by +nname+ until it is redeclared.
62 63 64 65 66 67 68 69 70 71 72 73 |
# File 'lib/HDLRuby/hruby_low_without_namespace.rb', line 62 def replace_names!(former,nname) # Replace owns name if required. if self.name == former then self.set_name!(nname) end # Recurse on the interface. self.each_input {|input| input.replace_names!(former,nname) } self.each_output {|output| output.replace_names!(former,nname) } self.each_inout {|inout| inout.replace_names!(former,nname) } # Recurse on the scope. self.scope.replace_names!(former,nname) end |
#select2case! ⇒ Object
Converts the Select expressions to Case statements.
60 61 62 |
# File 'lib/HDLRuby/hruby_low_without_select.rb', line 60 def select2case! self.scope.select2case! end |
#set_name!(name) ⇒ Object
Sets the +name+.
22 23 24 |
# File 'lib/HDLRuby/hruby_low_mutable.rb', line 22 def set_name!(name) @name = name.to_sym end |
#set_scope!(scope) ⇒ Object
Sets the +scope+.
27 28 29 30 31 32 33 |
# File 'lib/HDLRuby/hruby_low_mutable.rb', line 27 def set_scope!(scope) unless scope.is_a?(Scope) then raise AnyError, "Invalid class for a scope: #{scope.class}" end scope.parent = self @scope = scope end |
#to_c(res, level = 0, *hnames) ⇒ Object
Generates the text of the equivalent HDLRuby code. +level+ is the hierachical level of the object and +hnames+ is the list of extra h files to include. def to_c(level = 0, *hnames)
174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 |
# File 'lib/HDLRuby/hruby_low2c.rb', line 174 def to_c(res, level = 0, *hnames) # puts "SystemT.to_c with name=#{Low2C.obj_name(self)}#{@wrapper ? " and wrapper=#{Low2C.obj_name(@wrapper)}" : ""}" # The header # res = Low2C.includes(*hnames) res << Low2C.includes(*hnames) # Declare the global variable holding the system. res << "SystemT " << Low2C.obj_name(self) << ";\n\n" # Generate the signals of the system. # self.each_signal { |signal| signal.to_c(level) } if ((defined? @wrapper) && @wrapper) then # It is a reconfiguring system, alias the signals. wrap_signals = @wrapper.each_signal.to_a self.each_signal.with_index do |signal,i| signal.to_c_alias(res,wrap_signals[i],level) end else # It is a single system, default generation. self.each_signal { |signal| signal.to_c(res,level) } end # Generate the code for all the blocks included in the system. self.scope.each_scope_deep do |scope| scope.each_behavior do |behavior| # res << behavior.block.to_c_code(level) behavior.block.to_c_code(res,level) end end # Generate the code for all the values included in the system. self.each_signal do |signal| # res << signal.value.to_c_make(level) if signal.value signal.value.each_node_deep do |node| # res << node.to_c_make(level) if node.respond_to?(:to_c_make) node.to_c_make(res,level) if node.respond_to?(:to_c_make) end if signal.value end self.scope.each_scope_deep do |scope| scope.each_inner do |signal| signal.value.each_node_deep do |node| # res << node.to_c_make(level) if node.respond_to?(:to_c_make) node.to_c_make(res,level) if node.respond_to?(:to_c_make) end if signal.value end end self.scope.each_block_deep do |block| # puts "treating for block=#{Low2C.obj_name(block)} with=#{block.each_inner.count} inners" block.each_inner do |signal| signal.value.each_node_deep do |node| # res << node.to_c_make(level) if node.respond_to?(:to_c_make) node.to_c_make(res,level) if node.respond_to?(:to_c_make) end if signal.value end end self.scope.each_node_deep do |node| # res << node.to_c_make(level) if node.is_a?(Value) node.to_c_make(res,level) if node.is_a?(Value) end # Generate the scope. # res << self.scope.to_c(level) self.scope.to_c(res,level) # Generate the entity res << "SystemT " << Low2C.make_name(self) << "() {\n" # Creates the structure. res << " " * (level+1)*3 res << "SystemT systemT = malloc(sizeof(SystemTS));\n" res << " " * (level+1)*3 res << "systemT->kind = SYSTEMT;\n"; # Sets the global variable of the system. res << "\n" res << " " * (level+1)*3 res << Low2C.obj_name(self) << " = systemT;\n" # Set the owner if any. if @owner then res << " " * (level+1)*3 res << "systemT->owner = (Object)" res << Low2C.obj_name(@owner) << ";\n" else res << "systemT->owner = NULL;\n" end # The name res << " " * (level+1)*3 res << "systemT->name = \"#{self.name}\";\n" # The ports # Inputs res << " " * (level+1)*3 res << "systemT->num_inputs = #{self.each_input.to_a.size};\n" res << " " * (level+1)*3 res << "systemT->inputs = calloc(sizeof(SignalI)," res << "systemT->num_inputs);\n" self.each_input.with_index do |input,i| res << " " * (level+1)*3 res << "systemT->inputs[#{i}] = " res << Low2C.make_name(input) << "();\n" end # Outputs res << " " * (level+1)*3 res << "systemT->num_outputs = #{self.each_output.to_a.size};\n" res << " " * (level+1)*3 res << "systemT->outputs = calloc(sizeof(SignalI)," res << "systemT->num_outputs);\n" self.each_output.with_index do |output,i| res << " " * (level+1)*3 res << "systemT->outputs[#{i}] = " res << Low2C.make_name(output) << "();\n" end # Inouts res << " " * (level+1)*3 res << "systemT->num_inouts = #{self.each_inout.to_a.size};\n" res << " " * (level+1)*3 res << "systemT->inouts = calloc(sizeof(SignalI)," + "systemT->num_inouts);\n" self.each_inout.with_index do |inout,i| res << " " * (level+1)*3 res << "systemT->inouts[#{i}] = " res << Low2C.make_name(inout) << "();\n" end # Adds the scope. res << "\n" res << " " * (level+1)*3 res << "systemT->scope = " << Low2C.make_name(self.scope) << "();\n" # Generate the Returns of the result. res << "\n" res << " " * (level+1)*3 res << "return systemT;\n" # End of the system. res << " " * level*3 res << "}" # Return the result. return res end |
#to_c_code(res, level) ⇒ Object
Generates the code for an execution starting from the system. +level+ is the hierachical level of the object. def to_c_code(level)
319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 |
# File 'lib/HDLRuby/hruby_low2c.rb', line 319 def to_c_code(res,level) res << " " * (level*3) res << Low2C.code_name(self) << "() {\n" # res << "printf(\"Executing #{Low2C.code_name(self)}...\\n\");" # Launch the execution of all the time behaviors of the # system. self.each_behavior_deep do |behavior| if behavior.is_a?(HDLRuby::Low::TimeBehavior) then res << " " * (level+1)*3 res << Low2C.code_name(behavior.block) << "();\n" end end # Close the execution procedure. res << " " * level*3 res << "}\n" # Return the result. return res end |
#to_ch(res) ⇒ Object
Generates the content of the h file. def to_ch
341 342 343 344 345 346 347 348 349 350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 368 369 370 371 372 373 374 375 376 377 378 379 380 381 382 383 384 385 386 387 388 389 390 391 392 393 394 395 396 397 398 399 |
# File 'lib/HDLRuby/hruby_low2c.rb', line 341 def to_ch(res) # res = "" # Declare the global variable holding the signal. res << "extern SystemT " << Low2C.obj_name(self) << ";\n\n" # Generate the access to the function making the systemT. */ res << "extern SystemT " << Low2C.make_name(self) << "();\n\n" # Generate the accesses to the values. self.each_signal do |signal| # res << signal.value.to_ch if signal.value if signal.value then signal.value.each_node_deep do |node| # res << node.to_ch if node.is_a?(Value) node.to_ch(res) if node.is_a?(Value) end end end self.scope.each_scope_deep do |scope| scope.each_inner do |signal| if signal.value then signal.value.each_node_deep do |node| # res << node.to_ch if node.is_a?(Value) node.to_ch(res) if node.is_a?(Value) end end end end self.scope.each_block_deep do |block| block.each_inner do |signal| # signal.value.to_ch(res) if signal.value if signal.value then signal.value.each_node_deep do |node| # res << node.to_ch if node.is_a?(Value) node.to_ch(res) if node.is_a?(Value) end end end block.each_node_deep do |node| # res << node.to_ch if node.is_a?(Value) node.to_ch(res) if node.is_a?(Value) end end # Generate the accesses to the ports. # self.each_input { |input| res << input.to_ch } self.each_input { |input| input.to_ch(res) } # self.each_output { |output| res << output.to_ch } self.each_output { |output| output.to_ch(res) } # self.each_inout { |inout| res << inout.to_ch } self.each_inout { |inout| inout.to_ch(res) } # Generate the accesses to the scope. # res << self.scope.to_ch << "\n" self.scope.to_ch(res) res << "\n" return res; end |
#to_global_systemTs! ⇒ Object
Moves local systemTs to global.
NOTE: assumes to_upper_space! has been called.
44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 |
# File 'lib/HDLRuby/hruby_low_without_namespace.rb', line 44 def to_global_systemTs! # Force a name if not. self.force_name! # puts "to_global_systemTs! for #{self.name}" # For each local systemT self.scope.each_systemT.to_a.each do |systemT| # puts "Processing system: #{systemT}" # Rename it for globalization. former = systemT.name self.extend_name!(systemT) # Apply the renaming to all the inner objects. self.scope.replace_names_subs!(former,systemT.name) # Remove it. self.scope.delete_systemT!(systemT) end end |
#to_hdr(level = 0) ⇒ Object
Generates the text of the equivalent hdr text. +level+ is the hierachical level of the object.
64 65 66 67 68 69 70 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 |
# File 'lib/HDLRuby/hruby_low2hdr.rb', line 64 def to_hdr(level = 0) # The resulting string. res = "" # Generate the header. res << " " * (level*3) res << "system :#{Low2HDR.hdr_decl_name(self.name)} do\n" # Generate the interface. # Inputs. self.each_input do |input| res << " " * ((level+1)*3) res << input.type.to_hdr(level+1) res << ".input :" << Low2HDR.hdr_decl_name(input.name) res << "\n" end # Outputs. self.each_output do |output| res << " " * ((level+1)*3) res << output.type.to_hdr(level+1) res << ".output :" << Low2HDR.hdr_decl_name(output.name) res << "\n" end # Inouts. self.each_inout do |inout| res << " " * ((level+1)*3) res << inout.type.to_hdr(level+1) res << ".inout :" << Low2HDR.hdr_decl_name(inout.name) res << "\n" end # Generate the scope. res << " " * (level*3) res << "\n" res << self.scope.to_hdr(level+1,false) # End of the system. res << " " * (level*3) res << "end\n\n" # Return the result. return res end |
#to_high ⇒ Object
Creates a new high system type named +name+ with +scope+.
17 18 19 20 21 22 23 24 25 26 27 |
# File 'lib/HDLRuby/hruby_low2high.rb', line 17 def to_high # Create the high system type. res = HDLRuby::High::SystemT.new(self.name,self.scope.to_high) # Add the inputs. self.each_input { |i| res.add_input(i.to_high) } # Add the outputs. self.each_output { |o| res.add_output(o.to_high) } # Add the inouts. self.each_inout { |io| res.add_inout(io.to_high) } return res end |
#to_upper_space! ⇒ Object
Moves the declarations to the upper namespace.
37 38 39 |
# File 'lib/HDLRuby/hruby_low_without_namespace.rb', line 37 def to_upper_space! self.scope.to_upper_space! end |
#to_verilog(vcd = false) ⇒ Object
Converts the system to Verilog code. NOTE: if +vcd+ is true, generate verilog code whose simulation produces a vcd file.
1876 1877 1878 1879 1880 1881 1882 1883 1884 1885 1886 1887 1888 1889 1890 1891 1892 1893 1894 1895 1896 1897 1898 1899 1900 1901 1902 1903 1904 1905 1906 1907 1908 1909 1910 1911 1912 1913 1914 1915 1916 1917 1918 1919 1920 1921 1922 1923 1924 1925 1926 1927 1928 1929 1930 1931 1932 1933 1934 1935 1936 1937 1938 1939 1940 1941 1942 1943 1944 1945 1946 1947 1948 1949 1950 1951 1952 1953 1954 1955 1956 1957 1958 1959 1960 1961 1962 1963 1964 1965 1966 1967 1968 1969 1970 1971 1972 1973 1974 1975 1976 1977 1978 1979 1980 1981 1982 1983 1984 1985 1986 1987 1988 1989 1990 1991 1992 1993 1994 1995 1996 1997 1998 1999 2000 2001 2002 2003 2004 2005 2006 2007 2008 2009 2010 2011 2012 2013 2014 2015 2016 2017 2018 2019 2020 2021 2022 2023 2024 2025 2026 2027 2028 2029 2030 2031 2032 2033 2034 2035 2036 2037 2038 2039 2040 2041 2042 2043 2044 2045 2046 2047 2048 2049 2050 2051 2052 2053 2054 2055 2056 2057 2058 2059 2060 2061 2062 2063 2064 2065 2066 2067 2068 2069 2070 2071 2072 2073 2074 2075 2076 2077 2078 2079 2080 2081 2082 2083 2084 2085 2086 2087 2088 2089 2090 2091 2092 2093 2094 2095 2096 2097 2098 2099 2100 2101 2102 2103 2104 2105 2106 2107 2108 2109 2110 2111 2112 2113 2114 2115 2116 2117 2118 2119 2120 2121 2122 2123 2124 2125 2126 2127 2128 2129 2130 2131 2132 2133 2134 2135 2136 2137 2138 2139 2140 2141 2142 2143 2144 2145 2146 2147 2148 2149 2150 2151 2152 2153 2154 2155 2156 2157 2158 2159 2160 2161 2162 2163 2164 2165 2166 2167 2168 2169 2170 2171 2172 2173 2174 2175 2176 2177 2178 2179 2180 2181 2182 2183 2184 2185 2186 2187 2188 2189 2190 |
# File 'lib/HDLRuby/hruby_verilog.rb', line 1876 def to_verilog(vcd = false) # Detect the registers HDLRuby::Low::VERILOG_REGS.clear # The left values. self.each_behavior do |behavior| behavior.each_block_deep do |block| block.each_statement do |statement| if statement.is_a?(Transmit) HDLRuby::Low::VERILOG_REGS << statement.left.to_verilog end end end end # And the initialized signals. self.each_output do |output| # regs << output.to_verilog if output.value HDLRuby::Low::VERILOG_REGS << output.to_verilog if output.value end self.each_inner do |inner| # regs << inner.to_verilog if inner.value HDLRuby::Low::VERILOG_REGS << inner.to_verilog if inner.value end # And the array types signals. self.each_signal do |sig| if sig.type.vector? && sig.type.base.vector? then HDLRuby::Low::VERILOG_REGS << sig.to_verilog end end self.each_inner do |sig| if sig.type.vector? && sig.type.base.vector? then HDLRuby::Low::VERILOG_REGS << sig.to_verilog end end # Code generation inputs = 0 outputs = 0 inout = 0 inputs = self.each_input.to_a outputs = self.each_output.to_a inout = self.each_inout.to_a # Spelling necessary for simulation. code = "`timescale 1ps/1ps\n\n" vname = name_to_verilog(self.name) # self.properties[:verilog_name] = vname # Output the module name. code << "module #{vname}(" # Output the last two to the input. inputs[0..-2].each do |input| code << " #{input.to_verilog}," end # When only input is used, it is necessary to close (), so it branches with if. if outputs.empty? && inout.empty? then if (inputs.empty?) code << " ); \n" end else code << " #{inputs.last.to_verilog}," unless inputs.empty? end # Output the last two to the output. outputs[0..-2].each do |output| code << " #{output.to_verilog}," end # When only input and output are used, it is necessary to close (), so it branches with if. if inout.empty? then code << " #{outputs.last.to_verilog} ); \n" unless outputs.empty? else code << " #{outputs.last.to_verilog}," unless outputs.empty? end # Output the last two to the inout. inout[0..-2].each do |inout| code << " #{inout.to_verilog}," end # There is no comma as it is the last one code << " #{inout.last.to_verilog} ); \n" unless inout.empty? # Declare "input" self.each_input do |input| if input.type.respond_to? (:each_type) then $vector_reg = "#{input.to_verilog}" $vector_cnt = 0 input.type.each_type do |type| code << "input #{type.to_verilog} #{$vector_reg}:#{$vector_cnt};\n" $vector_cnt += 1 end else code << " input#{input.type.to_verilog} #{input.to_verilog};\n" end end # Declare "output" self.each_output do |output| if output.type.respond_to? (:each_type) then $vector_reg = "#{output.to_verilog}" $vector_cnt = 0 output.type.each_type do |type| # if regs.include?(type.name) then if HDLRuby::Low::VERILOG_REGS.include?(type.name) then code << " output reg" else code << " output" end code << "#{type.to_verilog} #{$vector_reg}:#{$vector_cnt}" if output.value then # There is an initial value. code << " = #{output.value.to_verilog}" end code << ";\n" $vector_cnt += 1 end else if HDLRuby::Low::VERILOG_REGS.include?(output.to_verilog) then code << " output reg" else code << " output" end code << "#{output.type.to_verilog} #{output.to_verilog}" if output.value then # There is an initial value. code << " = #{output.value.to_verilog}" end code << ";\n" end end # Declare "inout" self.each_inout do |inout| if inout.type.respond_to? (:each_type) then $vector_reg = "#{inout.to_verilog}" $vector_cnt = 0 inout.type.each_type do |type| code << "inout #{type.to_verilog} #{$vector_reg}:#{$vector_cnt};\n" $vector_cnt += 1 end else code << " inout#{inout.type.to_verilog} #{inout.to_verilog};\n" end end # Generate content code. codeC = "" # Declare "inner". self.each_inner do |inner| if HDLRuby::Low::VERILOG_REGS.include?(inner.to_verilog) then codeC << " reg" else codeC << " wire" end if inner.type.base? if inner.type.base.base? codeC << "#{inner.type.base.to_verilog} #{inner.to_verilog} #{inner.type.to_verilog}" else codeC << "#{inner.type.to_verilog} #{inner.to_verilog}" end else codeC << " #{inner.type.to_verilog}#{inner.to_verilog}" end if inner.value then # There is an initial value. codeC << " = #{inner.value.to_verilog}" end codeC << ";\n" end # If there is scope in scope, translate it. self.each_scope do |scope| scope.each_inner do |inner| if HDLRuby::Low::VERILOG_REGS.include?(inner.to_verilog) then codeC << " reg " else codeC << " wire " end if inner.type.respond_to? (:base) if inner.type.base.base? codeC << "#{inner.type.base.to_verilog} #{inner.to_verilog} #{inner.type.to_verilog}" else codeC << "#{inner.type.to_verilog} #{inner.to_verilog}" end else codeC << "inner #{inner.type.to_verilog} #{inner.to_verilog}" end if inner.value then # There is an initial value. codeC << " = #{inner.value.to_verilog}" end codeC << ";\n" end scope.each_connection do |connection| codeC << "\n" codeC << "#{connection.to_verilog}" end end codeC << "\n" # puts "For system=#{self.name}" # transliation of the instantiation part. # Generate the instances connections. self.each_systemI do |systemI| # puts "Processing systemI = #{systemI.name}" # Its Declaration. codeC << " " * 3 systemT = systemI.systemT codeC << name_to_verilog(systemT.name) << " " vname = name_to_verilog(systemI.name) # systemI.properties[:verilog_name] = vname codeC << vname << "(" # Its ports connections # Inputs systemT.each_input do |input| ref = self.extract_port_assign!(systemI,input) if ref then codeC << "." << name_to_verilog(input.name) << "(" codeC << ref.to_verilog codeC << ")," end end # Outputs systemT.each_output do |output| ref = self.extract_port_assign!(systemI,output) if ref then codeC << "." << name_to_verilog(output.name) << "(" codeC << ref.to_verilog codeC << ")," end end # Inouts systemT.each_inout do |inout| ref = self.extract_port_assign!(systemI,inout) if ref then codeC << "." << name_to_verilog(inout.name) << "(" codeC << ref.to_verilog codeC << ")," end end # Remove the last "," for conforming with Verilog syntax. # and close the port connection. codeC[-1] = ");\n" end # translation of the connection part (assigen). self.each_connection do |connection| codeC << "#{connection.to_verilog}\n" end # Translation of behavior part (always). $timebeh_shown = false self.each_behavior do |behavior| timebeh = false if behavior.block.is_a?(TimeBlock) then # Tell it is a time behavior for further processing. timebeh = true # Extract and translate the TimeRepeat separately. behavior.each_block_deep do |blk| codeC << blk.repeat_to_verilog! end # And generate an initial block. codeC << " initial " else # Generate a standard process. codeC << " always @( " # If there is no "always" condition, it is always @("*"). if behavior.each_event.to_a.empty? then codeC << "*" else event = behavior.each_event.to_a event[0..-2].each do |event| # If "posedge" or "negedge" does not exist, the variable is set to condition. if (event.type.to_s != "posedge" && event.type.to_s != "negedge") then codeC << "#{event.ref.to_verilog}, " else # Otherwise, it outputs "psoedge" or "negedge" as a condition. codeC << "#{event.type.to_s} #{event.ref.to_verilog}, " end end # Since no comma is necessary at the end, we try not to separate commas separately at the end. if (event.last.type.to_s != "posedge" && event.last.type.to_s != "negedge") then codeC << "#{event.last.ref.to_verilog}" else codeC << "#{event.last.type.to_s} #{event.last.ref.to_verilog}" end end codeC << " ) " end if vcd && timebeh && !$timebeh_shown then codeC << behavior.block.to_verilog(3,name_to_verilog(self.name)) $timebeh_shown = true else codeC << behavior.block.to_verilog end end # Conclusion. codeC << "\nendmodule" # Adds the truncing functions. code << TruncersI.dump # Adds the content code. code << codeC return code end |
#to_vhdl(level = 0) ⇒ Object
Generates the text of the equivalent HDLRuby::High code. +level+ is the hierachical level of the object.
348 349 350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 368 369 370 371 372 373 374 375 376 377 378 379 380 381 382 383 384 385 386 387 388 389 390 391 392 393 394 395 396 397 398 399 400 401 402 |
# File 'lib/HDLRuby/hruby_low2vhd.rb', line 348 def to_vhdl(level = 0) # The resulting string. res = "" # Generate the entity # The header res << Low2VHDL.packages(" " * (level*3)) res << " " * (level*3) res << "entity #{Low2VHDL.entity_name(self.name)} is\n" # The ports if self.each_input.any? || self.each_output.any? || self.each_inout.any? then res << " " * ((level+1)*3) res << "port (\n" # Inputs self.each_input do |input| res << " " * ((level+2)*3) res << Low2VHDL.vhdl_name(input.name) << ": in " res << input.type.to_vhdl << ";\n" end # Outputs self.each_output do |output| res << " " * ((level+2)*3) res << Low2VHDL.vhdl_name(output.name) << ": out " res << output.type.to_vhdl << ";\n" end # Inouts self.each_inout do |inout| res << " " * ((level+2)*3) res << Low2VHDL.vhdl_name(inout.name) << ": inout " res << inout.type.to_vhdl << ";\n" end # Remove the last ";" for conforming with VHDL syntax. res[-2..-1] = "\n" if res[-2] == ";" res << " " * ((level+1)*3) # Close the port declaration. res << ");\n" end # Close the entity res << " " * (level*3) res << "end #{Low2VHDL.entity_name(self.name)};\n\n" # Generate the architecture. res << " " * (level*3) res << "architecture #{Low2VHDL.architecture_name(self.name)} " res << "of #{Low2VHDL.entity_name(self.name)} is\n" # Generate the scope. res << "\n" res << self.scope.to_vhdl(level+1) # End of the system. res << " " * (level*3) res << "end #{Low2VHDL.architecture_name(self.name)};\n\n" # Return the result. return res end |
#with_boolean! ⇒ Object
Converts to a variable-compatible system.
NOTE: the result is the same systemT.
59 60 61 62 63 64 65 |
# File 'lib/HDLRuby/hruby_low_with_bool.rb', line 59 def with_boolean! self.scope.each_scope_deep do |scope| scope.each_connection { |connection| connection.with_boolean! } scope.each_behavior { |behavior| behavior.with_boolean! } end return self end |
#with_port! ⇒ Object
Converts to a port-compatible system.
NOTE: the result is the same systemT.
29 30 31 32 |
# File 'lib/HDLRuby/hruby_low_with_port.rb', line 29 def with_port! self.scope.with_port! return self end |
#with_var! ⇒ Object
Converts to a variable-compatible system.
NOTE: the result is the same systemT.
21 22 23 24 |
# File 'lib/HDLRuby/hruby_low_with_var.rb', line 21 def with_var! self.each_behavior { |behavior| behavior.with_var! } return self end |
#wrapper ⇒ Object
Gets the configuration wrapper if any.
175 176 177 |
# File 'lib/HDLRuby/hruby_low.rb', line 175 def wrapper return defined? @wrapper ? @wrapper : nil end |
#wrapper=(systemT) ⇒ Object
Sets the configuration wrapper to +systemT+.
180 181 182 183 184 185 |
# File 'lib/HDLRuby/hruby_low.rb', line 180 def wrapper=(systemT) unless systemT.is_a?(SystemT) then raise "Invalid class for a wrapper system type: #{systemT}." end @wrapper = systemT end |