Class: HDLRuby::Low::Value
- Inherits:
-
Expression
- Object
- Base::Expression
- Expression
- HDLRuby::Low::Value
- 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_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 Value class with functionality for extracting expressions from cast.
Direct Known Subclasses
Constant Summary collapse
- @@made_values =
Set.new
Constants included from Low2Symbol
Low2Symbol::Low2SymbolPrefix, Low2Symbol::Low2SymbolTable, Low2Symbol::Symbol2LowTable
Instance Attribute Summary collapse
-
#content ⇒ Object
readonly
The content of the value.
Attributes inherited from Expression
Attributes included from Hparent
Instance Method Summary collapse
-
#<=>(value) ⇒ Object
Compare values.
-
#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.
-
#eql?(obj) ⇒ Boolean
Comparison for hash: structural comparison.
-
#even? ⇒ Boolean
Tells if the value is even.
-
#explicit_types(type = nil) ⇒ Object
Explicit the types conversions in the value 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, content) ⇒ Value
constructor
Creates a new value typed +type+ and containing +content+.
-
#odd? ⇒ Boolean
Tells if the value is odd.
-
#set_content!(content) ⇒ Object
Sets the content.
-
#to_arith ⇒ Object
Generate the text of the equivalent VHDL is case of arithmetic expression.
-
#to_c(res, level = 0) ⇒ Object
Generates the C text for an access to the value.
-
#to_c_expr(res, level = 0) ⇒ Object
Generates the C text for an expression access to the value.
-
#to_c_make(res, level = 0) ⇒ Object
Generates the text of the equivalent c.
-
#to_ch(res) ⇒ Object
Generates the content of the h file.
-
#to_getrange ⇒ Object
How to use when simply obtaining the width.
-
#to_hdr(level = 0) ⇒ Object
Generates the text of the equivalent hdr text.
-
#to_high ⇒ Object
Creates a new high value expression.
-
#to_i ⇒ Object
Converts to integer.
-
#to_verilog(unknown = nil) ⇒ Object
Converts the system to Verilog code.
-
#to_vhdl(level = 0, std_logic = false, width = nil) ⇒ Object
Generates the text of the equivalent VHDL with +width+ bits.
-
#width ⇒ Object
Gets the bit width of the value.
Methods inherited from Expression
#boolean?, #break_types!, #each_node, #each_node_deep, #each_ref_deep, #extract_selects_to!, #leftvalue?, #map_nodes!, #replace_expressions!, #replace_names!, #rightvalue?, #set_type!, #statement, #use_name?
Methods included from Low2Symbol
Methods included from Hparent
Constructor Details
#initialize(type, content) ⇒ Value
Creates a new value typed +type+ and containing +content+.
329 330 331 332 333 334 335 336 337 338 339 |
# File 'lib/HDLRuby/hruby_db.rb', line 329 def initialize(type,content) # Ensures type is from Low::Type type = Type.get(type) # # Ensures the content is valid for low-level hardware. # unless content.is_a?(Numeric) or # content.is_a?(HDLRuby::BitString) then # raise "Invalid type for a value content: #{content.class}." # end # NOW CHECKED BY BASE # Initialize the value structure. super(type,content) end |
Instance Attribute Details
#content ⇒ Object (readonly)
The content of the value.
4448 4449 4450 |
# File 'lib/HDLRuby/hruby_low.rb', line 4448 def content @content end |
Instance Method Details
#<=>(value) ⇒ Object
Compare values.
NOTE: mainly used for being supported by ranges.
4512 4513 4514 4515 |
# File 'lib/HDLRuby/hruby_low.rb', line 4512 def <=>(value) value = value.content if value.respond_to?(:content) return self.content <=> value end |
#boolean_in_assign2select ⇒ Object
Converts booleans in assignments to select operators.
175 176 177 178 |
# File 'lib/HDLRuby/hruby_low_bool2select.rb', line 175 def boolean_in_assign2select # Simple clones. return self.clone end |
#casts_without_expression! ⇒ Object
Extracts the expressions from the casts.
172 173 174 175 176 |
# File 'lib/HDLRuby/hruby_low_casts_without_expression.rb', line 172 def casts_without_expression! # # Simple clones. # return self.clone return self end |
#clone ⇒ Object
Clones the value (deeply)
4538 4539 4540 |
# File 'lib/HDLRuby/hruby_low.rb', line 4538 def clone return Value.new(@type,@content) end |
#each_deep(&ruby_block) ⇒ Object
Iterates over each object deeply.
Returns an enumerator if no ruby block is given.
4480 4481 4482 4483 4484 4485 4486 4487 4488 4489 4490 4491 |
# File 'lib/HDLRuby/hruby_low.rb', line 4480 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 content if possible. if self.content.respond_to?(:each_deep) then self.content.each_deep(&ruby_block) end end |
#eql?(obj) ⇒ Boolean
Comparison for hash: structural comparison.
4494 4495 4496 4497 4498 4499 4500 4501 |
# File 'lib/HDLRuby/hruby_low.rb', line 4494 def eql?(obj) # General comparison. return false unless super(obj) # Specific comparison. return false unless obj.is_a?(Value) return false unless @content.eql?(obj.content) return true end |
#even? ⇒ Boolean
Tells if the value is even.
4523 4524 4525 |
# File 'lib/HDLRuby/hruby_low.rb', line 4523 def even? return @content.even? end |
#explicit_types(type = nil) ⇒ Object
Explicit the types conversions in the value where +type+ is the expected type of the condition if any.
205 206 207 208 209 210 211 212 213 214 |
# File 'lib/HDLRuby/hruby_low_fix_types.rb', line 205 def explicit_types(type = nil) # Does the type match the value? if type && !self.type.eql?(type) then # No, update the type of the value. return Value.new(type,self.content) else # yes, return the value as is. return self.clone end end |
#hash ⇒ Object
Hash function.
4504 4505 4506 |
# File 'lib/HDLRuby/hruby_low.rb', line 4504 def hash return [super,@content].hash end |
#immutable? ⇒ Boolean
Tells if the expression is immutable (cannot be written.)
4472 4473 4474 4475 |
# File 'lib/HDLRuby/hruby_low.rb', line 4472 def immutable? # Values are always immutable. true end |
#odd? ⇒ Boolean
Tells if the value is odd.
4528 4529 4530 |
# File 'lib/HDLRuby/hruby_low.rb', line 4528 def odd? return @content.odd? end |
#set_content!(content) ⇒ Object
Sets the content.
1379 1380 1381 1382 1383 1384 |
# File 'lib/HDLRuby/hruby_low_mutable.rb', line 1379 def set_content!(content) unless content.is_a?(Numeric) or content.is_a?(HDLRuby::BitString) content = HDLRuby::BitString.new(content.to_s) end @content = content end |
#to_arith ⇒ Object
Generate the text of the equivalent VHDL is case of arithmetic expression.
1143 1144 1145 1146 1147 1148 1149 1150 1151 1152 1153 1154 1155 1156 1157 |
# File 'lib/HDLRuby/hruby_low2vhd.rb', line 1143 def to_arith case self.content when HDLRuby::BitString if self.content.specified? then sign = self.type.signed? && self.content.to_s[-1] == "0" ? -1 : 1 return (sign * self.content.to_s.to_i(2)).to_s else return self.content.to_s.upcase end else # NOTE: in VHDL, "z" and "x" must be upcase. return self.content.to_s.upcase end end |
#to_c(res, level = 0) ⇒ Object
Generates the C text for an access to the value. +level+ is the hierachical level of the object.
1924 1925 1926 1927 1928 1929 1930 1931 |
# File 'lib/HDLRuby/hruby_low2c.rb', line 1924 def to_c(res,level = 0) # res << Low2C.make_name(self) << "()" # return res res << (" " * (level*3)) # res << "d=" << Low2C.make_name(self) << "();\n" res << "push(" << Low2C.make_name(self) << "());\n" return res end |
#to_c_expr(res, level = 0) ⇒ Object
Generates the C text for an expression access to the value. +level+ is the hierachical level of the object.
1935 1936 1937 1938 |
# File 'lib/HDLRuby/hruby_low2c.rb', line 1935 def to_c_expr(res,level = 0) res << Low2C.make_name(self) << "()" return res end |
#to_c_make(res, level = 0) ⇒ Object
Generates the text of the equivalent c. +level+ is the hierachical level of the object. def to_c_make(level = 0)
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 |
# File 'lib/HDLRuby/hruby_low2c.rb', line 1954 def to_c_make(res,level = 0) # Check is the value maker is already present. maker = Low2C.make_name(self); # return "" if @@made_values.include?(maker) return res if @@made_values.include?(maker) @@made_values.add(maker) # The resulting string. # res = "" # The header of the value generation. res << " " * level*3 # res << "Value " << Low2C.make_name(self) << "() {\n" res << "Value " << maker << "() {\n" # Declares the data. # Create the bit string. # str = self.content.is_a?(BitString) ? # self.content.to_s : self.content.to_s(2).rjust(32,"0") if self.content.is_a?(BitString) then str = self.content.is_a?(BitString) ? self.content.to_s : self.content.to_s(2).rjust(32,"0") else # sign = self.content>=0 ? "0" : "1" # str = self.content.abs.to_s(2).rjust(width,sign).upcase if self.content >= 0 then str = self.content.to_s(2).rjust(width,"0").upcase else # Compute the extension to the next multiple # of int_width ext_width = (((width-1) / Low2C.int_width)+1)*Low2C.int_width # Convert the string. str = (2**ext_width+self.content).to_s(2).upcase end # puts "content=#{self.content} str=#{str}" end # Is it a fully defined number? # NOTE: bignum values are not supported by the simulation engine # yet, therefore numeric values are limited to 64 max. if str =~ /^[01]+$/ && str.length <= 64 then # Yes, generate a numeral value. res << " " * (level+1)*3 # res << "static unsigned long long data[] = { " res << "static unsigned int data[] = { " res << str.scan(/.{1,#{Low2C.int_width}}/m).reverse.map do |sub| sub.to_i(2).to_s # + "ULL" end.join(",") res << " };\n" # Create the value. res << " " * (level+1)*3 # puts "str=#{str} type width=#{self.type.width} signed? #{type.signed?}" # res << "return make_set_value(#{self.type.to_c(level+1)},1," + # "data);\n" res << "return make_set_value(" self.type.to_c(res,level+1) res << ",1,data);\n" else # No, generate a bit string value. res << " " * (level+1)*3 # res << "static unsigned char data[] = \"#{str}\";\n" res << "static unsigned char data[] = \"#{str.reverse}\";\n" # Create the value. res << " " * (level+1)*3 # res << "return make_set_value(#{self.type.to_c(level+1)},0," + # "data);\n" res << "return make_set_value(" self.type.to_c(res,level+1) res << ",0,data);\n" end # Close the value. res << " " * level*3 res << "}\n\n" # Return the result. return res end |
#to_ch(res) ⇒ Object
Generates the content of the h file. def to_ch
1942 1943 1944 1945 1946 1947 |
# File 'lib/HDLRuby/hruby_low2c.rb', line 1942 def to_ch(res) # res = "" # return "extern Value #{Low2C.make_name(self)}();" res << "extern Value " << Low2C.make_name(self) << "();" return res end |
#to_getrange ⇒ Object
How to use when simply obtaining the width
1534 1535 1536 |
# File 'lib/HDLRuby/hruby_verilog.rb', line 1534 def to_getrange return "#{self.content.to_verilog}" end |
#to_hdr(level = 0) ⇒ Object
Generates the text of the equivalent hdr text. +level+ is the hierachical level of the object.
553 554 555 556 557 558 559 |
# File 'lib/HDLRuby/hruby_low2hdr.rb', line 553 def to_hdr(level = 0) if self.content.is_a?(HDLRuby::BitString) then return "_#{self.content}" else return self.content.to_s end end |
#to_high ⇒ Object
Creates a new high value expression.
384 385 386 387 388 389 390 391 392 393 394 395 |
# File 'lib/HDLRuby/hruby_low2high.rb', line 384 def to_high # Is there a content? if (self.content) then # Yes, use it for creating the new value. return HDLRuby::High::Value.new(self.type.to_high, self.content.to_high) else # puts "Self.type.name=#{self.type.name}" # No (this should be a void value). return HDLRuby::High::Value.new(self.type.to_high,nil) end end |
#to_i ⇒ Object
Converts to integer.
4533 4534 4535 |
# File 'lib/HDLRuby/hruby_low.rb', line 4533 def to_i return @content.to_i end |
#to_verilog(unknown = nil) ⇒ Object
Converts the system to Verilog code. If it is bit, it is b, and if it is int, it is represented by d. (Example: 4'b0000, 32'd1)
1519 1520 1521 1522 1523 1524 1525 1526 1527 1528 1529 1530 1531 1532 |
# File 'lib/HDLRuby/hruby_verilog.rb', line 1519 def to_verilog(unknown = nil) if self.type.base.name.to_s == "bit" return "#{self.type.range.first + 1}'b#{self.content.to_verilog}" elsif self.type.name.to_s == "integer" str = self.content.to_verilog if str[0] == "-" then # Negative value. return "-#{self.type.range.first + 1}'d#{str[1..-1]}" else return "#{self.type.range.first + 1}'d#{str}" end end return "#{self.type.range.first + 1}'b#{self.content.to_verilog}" end |
#to_vhdl(level = 0, std_logic = false, width = nil) ⇒ Object
Generates the text of the equivalent VHDL with +width+ bits. +level+ is the hierachical level of the object.
1162 1163 1164 1165 1166 1167 1168 1169 1170 1171 1172 1173 1174 1175 1176 1177 1178 1179 1180 1181 1182 1183 1184 1185 1186 1187 1188 1189 1190 1191 1192 1193 1194 1195 1196 |
# File 'lib/HDLRuby/hruby_low2vhd.rb', line 1162 def to_vhdl(level = 0, std_logic = false, width = nil) raise "Invalid std_logic argument: #{std_logic}." unless std_logic == true || std_logic == false if self.type.boolean? then # Boolean case if self.content.is_a?(HDLRuby::BitString) return self.zero? ? "false" : "true" else return self.to_i == 0 ? "false" : "true" end end # Other cases # Maybe the value is used as a range or an index. if self.parent.is_a?(RefIndex) or self.parent.is_a?(RefRange) then # Yes, convert to a simple integer. return self.to_i.to_s.upcase end # No, generates as a bit string. width = self.type.width unless width # puts "self.type=#{self.type} width=#{width}" case self.content # when Numeric # return self.content.to_s when HDLRuby::BitString # Compute the extension: in case of signed type, the extension # is the last bit. Otherwise it is 0 unless the last bit # is not defined (Z or X). sign = self.type.signed? ? self.content.to_s[-1] : /[01]/ =~ self.content[-1] ? "0" : self.content[-1] return '"' + self.content.to_s.rjust(width,sign).upcase + '"' else # sign = self.type.signed? ? (self.content>=0 ? "0" : "1") : "0" sign = self.content>=0 ? "0" : "1" return '"' + self.content.abs.to_s(2).rjust(width,sign).upcase + '"' end end |
#width ⇒ Object
Gets the bit width of the value.
4518 4519 4520 |
# File 'lib/HDLRuby/hruby_low.rb', line 4518 def width return @type.width end |