Class: HDLRuby::Low::Cast
- Inherits:
-
Expression
- Object
- Base::Expression
- Expression
- HDLRuby::Low::Cast
- Includes:
- OneChildMutable
- Defined in:
- lib/HDLRuby/hruby_low.rb,
lib/HDLRuby/hruby_low2c.rb,
lib/HDLRuby/hruby_low2hdr.rb,
lib/HDLRuby/hruby_low2vhd.rb,
lib/HDLRuby/hruby_verilog.rb,
lib/HDLRuby/hruby_low2high.rb,
lib/HDLRuby/hruby_low_mutable.rb,
lib/HDLRuby/hruby_low_skeleton.rb,
lib/HDLRuby/hruby_low_fix_types.rb,
lib/HDLRuby/hruby_low_bool2select.rb,
lib/HDLRuby/hruby_low_casts_without_expression.rb
Overview
Extends the Cast 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
-
#child ⇒ Object
readonly
The child.
Attributes inherited from Expression
Attributes included from Hparent
Instance Method Summary collapse
-
#boolean_in_assign2select ⇒ Object
Converts booleans in assignments to select operators.
-
#casts_without_expression! ⇒ Object
Extracts the expressions from the casts.
-
#clone ⇒ Object
Clones the value (deeply).
-
#each_deep(&ruby_block) ⇒ Object
Iterates over each object deeply.
-
#each_node(&ruby_block) ⇒ Object
(also: #each_expression)
Iterates over the expression children if any.
-
#each_node_deep(&ruby_block) ⇒ Object
Iterates over the nodes deeply if any.
-
#each_ref_deep(&ruby_block) ⇒ Object
Iterates over all the references encountered in the expression.
-
#eql?(obj) ⇒ Boolean
Comparison for hash: structural comparison.
-
#explicit_types(type = nil) ⇒ Object
Explicit the types conversions in the cast where +type+ is the expected type of the condition if any.
-
#hash ⇒ Object
Hash function.
-
#immutable? ⇒ Boolean
Tells if the expression is immutable (cannot be written.).
-
#initialize(type, child) ⇒ Cast
constructor
Creates a new cast of +child+ to +type+.
-
#to_c(res, level = 0) ⇒ Object
return res end Generates the C text of the equivalent HDLRuby code.
-
#to_hdr(level = 0) ⇒ Object
Generates the text of the equivalent hdr text.
-
#to_high ⇒ Object
Creates a new high cast expression.
-
#to_verilog ⇒ Object
Converts the system to Verilog code.
-
#to_vhdl(level = 0) ⇒ Object
Generates the text of the equivalent HDLRuby::High code.
-
#use_name?(*names) ⇒ Boolean
Tell if the expression includes a signal whose name is one of +names+.
Methods included from OneChildMutable
#map_nodes!, #replace_expressions!, #set_child!
Methods inherited from Expression
#boolean?, #break_types!, #extract_selects_to!, #leftvalue?, #map_nodes!, #replace_expressions!, #replace_names!, #rightvalue?, #set_type!, #statement, #to_c_expr
Methods included from Low2Symbol
Methods included from Hparent
#hierarchy, #no_parent!, #scope
Constructor Details
#initialize(type, child) ⇒ Cast
Creates a new cast of +child+ to +type+.
4813 4814 4815 4816 4817 4818 4819 4820 4821 4822 4823 |
# File 'lib/HDLRuby/hruby_low.rb', line 4813 def initialize(type,child) # Create the expression and set the type super(type) # Check and set the child. unless child.is_a?(Expression) raise AnyError,"Invalid class for an expression: #{child.class}" end @child = child # And set its parent. child.parent = self end |
Instance Attribute Details
#child ⇒ Object (readonly)
The child
4810 4811 4812 |
# File 'lib/HDLRuby/hruby_low.rb', line 4810 def child @child end |
Instance Method Details
#boolean_in_assign2select ⇒ Object
Converts booleans in assignments to select operators.
198 199 200 201 |
# File 'lib/HDLRuby/hruby_low_bool2select.rb', line 198 def boolean_in_assign2select # Recurse on the child. return Cast.new(self.type,self.child.boolean_in_assign2select) end |
#casts_without_expression! ⇒ Object
Extracts the expressions from the casts.
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 |
# File 'lib/HDLRuby/hruby_low_casts_without_expression.rb', line 184 def casts_without_expression! # Recurse on the child. nchild = self.child.casts_without_expression! nchild.parent = nil # Process the cast. unless (nchild.is_a?(Ref)) then # Need to extract the child. # Create signal holding the child. stmnt = self.statement if (stmnt.is_a?(Connection)) then # Specific case of connections: need to build # a new block. scop = stmnt.parent scop.delete_connection!(stmnt) stmnt = Transmit.new(stmnt.left.clone, stmnt.right.clone) blk = Block.new(:seq) scop.add_behavior(Behavior.new(blk)) blk.add_statement(stmnt) else blk = stmnt.block end name = HDLRuby.uniq_name typ = nchild.type sig = blk.add_inner(SignalI.new(name,typ)) # Add a statement assigning the child to the new signal. nref = RefName.new(typ,RefThis.new,name) nstmnt = Transmit.new(nref,nchild) idx = blk.each_statement.find_index(stmnt) blk.insert_statement!(idx,nstmnt) # Replace the child by a reference to the created # signal. nchild = nref.clone end return Cast.new(self.type,nchild) end |
#clone ⇒ Object
Clones the value (deeply)
4899 4900 4901 |
# File 'lib/HDLRuby/hruby_low.rb', line 4899 def clone return Cast.new(@type,@child.clone) end |
#each_deep(&ruby_block) ⇒ Object
Iterates over each object deeply.
Returns an enumerator if no ruby block is given.
4834 4835 4836 4837 4838 4839 4840 4841 4842 4843 |
# File 'lib/HDLRuby/hruby_low.rb', line 4834 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 the type. self.type.each_deep(&ruby_block) # Then apply on the child. self.child.each_deep(&ruby_block) end |
#each_node(&ruby_block) ⇒ Object Also known as: each_expression
Iterates over the expression children if any.
4861 4862 4863 4864 4865 4866 |
# File 'lib/HDLRuby/hruby_low.rb', line 4861 def each_node(&ruby_block) # No ruby block? Return an enumerator. return to_enum(:each_node) unless ruby_block # A ruby block? Apply it on the child. ruby_block.call(@child) end |
#each_node_deep(&ruby_block) ⇒ Object
Iterates over the nodes deeply if any.
4871 4872 4873 4874 4875 4876 4877 4878 |
# File 'lib/HDLRuby/hruby_low.rb', line 4871 def each_node_deep(&ruby_block) # No ruby block? Return an enumerator. return to_enum(:each_node_deep) unless ruby_block # A ruby block? First apply it to current. ruby_block.call(self) # And recurse on the child. @child.each_node_deep(&ruby_block) end |
#each_ref_deep(&ruby_block) ⇒ Object
Iterates over all the references encountered in the expression.
NOTE: do not iterate inside the references.
4883 4884 4885 4886 4887 4888 4889 4890 |
# File 'lib/HDLRuby/hruby_low.rb', line 4883 def each_ref_deep(&ruby_block) # No ruby block? Return an enumerator. return to_enum(:each_ref_deep) unless ruby_block # puts "each_ref_deep for Unary" # A ruby block? # Recurse on the child. @child.each_ref_deep(&ruby_block) end |
#eql?(obj) ⇒ Boolean
Comparison for hash: structural comparison.
4846 4847 4848 4849 4850 4851 4852 4853 |
# File 'lib/HDLRuby/hruby_low.rb', line 4846 def eql?(obj) # General comparison. return false unless super(obj) # Specific comparison. return false unless obj.is_a?(Cast) return false unless @child.eql?(obj.child) return true end |
#explicit_types(type = nil) ⇒ Object
Explicit the types conversions in the cast where +type+ is the expected type of the condition if any.
241 242 243 244 245 246 247 248 249 250 |
# File 'lib/HDLRuby/hruby_low_fix_types.rb', line 241 def explicit_types(type = nil) # Does the type match the cast? if type && !self.type.eql?(type) then # No, Recurse on the child tomatch the type. return self.child.explicit_types(type) else # No simply recurse on the child with the cast's type. return self.child.explicit_types(self.type) end end |
#hash ⇒ Object
Hash function.
4856 4857 4858 |
# File 'lib/HDLRuby/hruby_low.rb', line 4856 def hash return [super,@child].hash end |
#immutable? ⇒ Boolean
Tells if the expression is immutable (cannot be written.)
4826 4827 4828 4829 |
# File 'lib/HDLRuby/hruby_low.rb', line 4826 def immutable? # Immutable if the child is immutable. return child.immutable? end |
#to_c(res, level = 0) ⇒ Object
return res end Generates the C text of the equivalent HDLRuby code. +level+ is the hierachical level of the object. def to_c(level = 0)
2300 2301 2302 2303 2304 2305 2306 2307 2308 2309 2310 2311 2312 2313 |
# File 'lib/HDLRuby/hruby_low2c.rb', line 2300 def to_c(res,level = 0) # Save the value pool state. res << (" " * (level*3)) << "PV;\n" # Generate the child. self.child.to_c(res,level) res << (" " * (level*3)) # res << "d=cast(d," res << "cast(" self.type.to_c(res,level+1) res << ");\n" # Restore the value pool state. res << (" " * (level*3)) << "RV;\n" return res end |
#to_hdr(level = 0) ⇒ Object
Generates the text of the equivalent hdr text. +level+ is the hierachical level of the object.
567 568 569 570 |
# File 'lib/HDLRuby/hruby_low2hdr.rb', line 567 def to_hdr(level = 0) return self.child.to_hdr(level) + ".as(" + self.type.to_hdr(level) + ")" end |
#to_high ⇒ Object
Creates a new high cast expression.
402 403 404 |
# File 'lib/HDLRuby/hruby_low2high.rb', line 402 def to_high return HDLRuby::High::Cast(self.type.to_high, self.child.to_high) end |
#to_verilog ⇒ Object
Converts the system to Verilog code. NOTE: the cast is rounded up size bit-width cast is not supported by traditional verilog.
1738 1739 1740 1741 1742 1743 1744 1745 1746 1747 1748 1749 1750 1751 1752 1753 1754 1755 1756 1757 1758 1759 1760 1761 1762 1763 1764 1765 1766 1767 1768 1769 1770 1771 1772 1773 |
# File 'lib/HDLRuby/hruby_verilog.rb', line 1738 def to_verilog if self.child.is_a?(Value) then return self.child.to_verilog end # Get the type widths, used for computing extensions or truncations. cw = self.child.type.width sw = self.type.width if self.type.signed? then if (sw>cw) then # Need to sign extend. return "$signed({{#{sw-cw}{#{self.child.to_verilog}[#{cw-1}]}}," + "#{self.child.to_verilog}})" elsif (sw<cw) then # Need to truncate # return "$signed(#{self.child.to_verilog}[#{sw-1}:0])" TruncersI.add((cw-1)..0,(sw-1)..0) return "$signed(#{TruncersI.truncer_name((cw-1)..0,(sw-1)..0)}(#{self.child.to_verilog}))" else # Only enforce signed. return "$signed(#{self.child.to_verilog})" end else if (sw>cw) then # Need to extend. return "$unsigned({{#{sw-cw}{1'b0}},#{self.child.to_verilog}})" elsif (sw<cw) then # Need to truncate # return "$unsigned(#{self.child.to_verilog}[#{sw-1}:0])" TruncersI.add((cw-1)..0,(sw-1)..0) return "$unsigned(#{TruncersI.truncer_name((cw-1)..0,(sw-1)..0)}(#{self.child.to_verilog}))" else # Only enforce signed. return "$unsigned(#{self.child.to_verilog})" end end end |
#to_vhdl(level = 0) ⇒ Object
Generates the text of the equivalent HDLRuby::High code. +level+ is the hierachical level of the object.
1216 1217 1218 1219 1220 1221 1222 1223 1224 1225 1226 1227 1228 1229 1230 1231 1232 1233 1234 1235 1236 1237 1238 1239 1240 |
# File 'lib/HDLRuby/hruby_low2vhd.rb', line 1216 def to_vhdl(level = 0) if type.class == TypeVector then case type.base.name when :bit return "std_logic_vector(resize(unsigned(" + self.child.to_vhdl(level) + ")," + (type.range.first-type.range.last+1).abs.to_s + "))" when :signed return "resize(signed(" + self.child.to_vhdl(level) + ")," + (type.range.first-type.range.last+1).abs.to_s + ")" when :unsigned return "resize(unsigned(" + self.child.to_vhdl(level) + ")," + (type.range.first-type.range.last+1).abs.to_s + ")" else raise "Intenal error: convertion to #{type.class} not supported yet for VHDL conversion." end elsif [:bit,:signed,:unsigned].include?(type.name) then # No conversion required. return self.child.to_vhdl(level) else raise "Intenal error: convertion to #{type.class} not supported yet for VHDL conversion." end end |
#use_name?(*names) ⇒ Boolean
Tell if the expression includes a signal whose name is one of +names+.
4893 4894 4895 4896 |
# File 'lib/HDLRuby/hruby_low.rb', line 4893 def use_name?(*names) # Recurse on the child. return @child.use_name?(*names) end |