Class: HDLRuby::Low::Expression

Inherits:
Base::Expression
  • Object
show all
Includes:
Hparent, Low2Symbol
Defined in:
lib/HDLRuby/hruby_db.rb,
lib/HDLRuby/hruby_low.rb,
lib/HDLRuby/hruby_low2c.rb,
lib/HDLRuby/hruby_low2sym.rb,
lib/HDLRuby/hruby_low2vhd.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_with_bool.rb,
lib/HDLRuby/hruby_low_without_select.rb,
lib/HDLRuby/hruby_low_without_namespace.rb

Overview

Extends the Expression class with functionality for moving the declarations to the upper namespace.

Direct Known Subclasses

Cast, Concat, Operation, Ref, Value

Constant Summary

Constants included from Low2Symbol

Low2Symbol::Low2SymbolPrefix, Low2Symbol::Low2SymbolTable, Low2Symbol::Symbol2LowTable

Instance Attribute Summary collapse

Attributes included from Hparent

#parent

Instance Method Summary collapse

Methods included from Low2Symbol

#to_sym

Constructor Details

#initialize(type = Void) ⇒ Expression

Creates a new Expression with +type+



3668
3669
3670
3671
3672
3673
3674
3675
# File 'lib/HDLRuby/hruby_low.rb', line 3668

def initialize(type = Void)
    # Check and set the type.
    if type.is_a?(Type) then
        @type = type
    else
        raise AnyError, "Invalid class for a type: #{type.class}."
    end
end

Instance Attribute Details

#typeObject (readonly)

Gets the type of the expression.

def type # By default: the void type. return Void end



3665
3666
3667
# File 'lib/HDLRuby/hruby_low.rb', line 3665

def type
  @type
end

Instance Method Details

#boolean?Boolean

Tells if the expression is boolean.

Returns:

  • (Boolean)


98
99
100
# File 'lib/HDLRuby/hruby_low_with_bool.rb', line 98

def boolean?
    return false
end

#break_types!(types) ⇒ Object

Breaks the hierarchical types into sequences of type definitions. Assumes to_upper_space! has been called before. +types+ include the resulting types.



504
505
506
507
508
509
510
511
512
# File 'lib/HDLRuby/hruby_low_without_namespace.rb', line 504

def break_types!(types)
    self.each_node do |node|
        # Need to break only in the case of a cast.
        if node.is_a?(Cast) then
            # node.type.break_types!(types)
            node.set_type!(node.type.break_types!(types))
        end
    end
end

#cloneObject

Clones the expression (deeply)

Raises:



3750
3751
3752
3753
# File 'lib/HDLRuby/hruby_low.rb', line 3750

def clone
    raise AnyError,
          "Internal error: clone not defined for class: #{self.class}"
end

#each_node(&ruby_block) ⇒ Object Also known as: each_expression

Iterates over the expression children if any.



3713
3714
3715
# File 'lib/HDLRuby/hruby_low.rb', line 3713

def each_node(&ruby_block)
    # By default: no child.
end

#each_node_deep(&ruby_block) ⇒ Object

Iterates over the nodes deeply if any.



3720
3721
3722
3723
3724
3725
3726
# File 'lib/HDLRuby/hruby_low.rb', line 3720

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 that's all.
end

#each_ref_deep(&ruby_block) ⇒ Object

Iterates over all the references encountered in the expression.

NOTE: do not iterate inside the references.



3731
3732
3733
3734
3735
3736
3737
3738
# File 'lib/HDLRuby/hruby_low.rb', line 3731

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 Expression which is:#{self}"
    # A ruby block?
    # If the expression is a reference, applies ruby_block on it.
    ruby_block.call(self) if self.is_a?(Ref)
end

#eql?(obj) ⇒ Boolean

Comparison for hash: structural comparison.

Returns:

  • (Boolean)


3678
3679
3680
3681
3682
# File 'lib/HDLRuby/hruby_low.rb', line 3678

def eql?(obj)
    return false unless obj.is_a?(Expression)
    return false unless @type.eql?(obj.type)
    return true
end

#explicit_types(type = nil) ⇒ Object

Explicit the types conversions in the expression where +type+ is the expected type of the condition if any.



181
182
183
# File 'lib/HDLRuby/hruby_low_fix_types.rb', line 181

def explicit_types(type = nil)
    raise "Should implement explicit_types for class #{self.class}."
end

#extract_selects_to!(selects) ⇒ Object

Extract the Select expressions and put them into +selects+



188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
# File 'lib/HDLRuby/hruby_low_without_select.rb', line 188

def extract_selects_to!(selects)
    # Recurse on the sub expressions.
    self.map_expressions! {|expr| expr.extract_selects_to!(selects) }
    # Treat case of select.
    if self.is_a?(Select) then
        # Create the signal replacing self.
        sig = SignalI.new(HDLRuby.uniq_name,self.type)
        # Add the self with replacing sig to the extracted selects
        selects << [self,sig]
        # Create the signal replacing self.
        blk = self.statement.block
        blk.add_inner(sig)
        # And return a reference to it.
        return RefName.new(sig.type,RefThis.new,sig.name)
    end
    return self
end

#hashObject

Hash function.



3685
3686
3687
# File 'lib/HDLRuby/hruby_low.rb', line 3685

def hash
    return [@type].hash
end

#leftvalue?Boolean

Tells if the expression is a left value of an assignment.

Returns:

  • (Boolean)


3690
3691
3692
3693
3694
3695
3696
3697
3698
3699
3700
3701
3702
3703
3704
3705
# File 'lib/HDLRuby/hruby_low.rb', line 3690

def leftvalue?
    # Maybe its the left of a left value.
    if parent.respond_to?(:leftvalue?) && parent.leftvalue? then
        # Yes so it is also a left value if it is a sub ref.
        if parent.respond_to?(:ref) then
            # It might nor be a sub ref.
            return parent.ref == self
        else
            # It is necessarily a sub ref (case of RefConcat for now).
            return true
        end
    end
    # No, therefore maybe it is directly a left value.
    return (parent.is_a?(Transmit) || parent.is_a?(Connection)) &&
            parent.left == self
end

#map_nodes!(&ruby_block) ⇒ Object Also known as: map_expressions!

Maps on the children.



1184
1185
1186
# File 'lib/HDLRuby/hruby_low_mutable.rb', line 1184

def map_nodes!(&ruby_block)
    # By default, nothing to do.
end

#replace_expressions!(node2rep) ⇒ Object

Replaces sub expressions using +node2rep+ table indicating the node to replace and the corresponding replacement. Returns the actually replaced nodes and their corresponding replacement.

NOTE: the replacement is duplicated.



1196
1197
1198
1199
# File 'lib/HDLRuby/hruby_low_mutable.rb', line 1196

def replace_expressions!(node2rep)
    # By default, nothing to do.
    return {}
end

#replace_names!(former, nname) ⇒ Object

Replaces recursively +former+ name by +nname+ until it is redeclared.



492
493
494
495
496
497
498
499
# File 'lib/HDLRuby/hruby_low_without_namespace.rb', line 492

def replace_names!(former,nname)
    # By default: try to replace the name recursively.
    self.each_node_deep do |node|
        if node.respond_to?(:name) && node.name == former then
            node.set_name!(nname)
        end
    end
end

#rightvalue?Boolean

Tells if the expression is a right value.

Returns:

  • (Boolean)


3708
3709
3710
# File 'lib/HDLRuby/hruby_low.rb', line 3708

def rightvalue?
    return !self.leftvalue?
end

#set_type!(type) ⇒ Object

Sets the type.



1174
1175
1176
1177
1178
1179
1180
1181
# File 'lib/HDLRuby/hruby_low_mutable.rb', line 1174

def set_type!(type)
    # Check and set the type.
    if type.is_a?(Type) then
        @type = type
    else
        raise AnyError, "Invalid class for a type: #{type.class}."
    end
end

#statementObject

Get the statement of the expression.



3741
3742
3743
3744
3745
3746
3747
# File 'lib/HDLRuby/hruby_low.rb', line 3741

def statement
    if self.parent.is_a?(Statement)
        return self.parent
    else
        return self.parent.statement
    end
end

#to_c(level = 0) ⇒ Object

Generates the C text of the equivalent HDLRuby::High code. +level+ is the hierachical level of the object.

Raises:



1398
1399
1400
1401
# File 'lib/HDLRuby/hruby_low2c.rb', line 1398

def to_c(level = 0)
    # Should never be here.
    raise AnyError, "Internal error: to_c should be implemented in class :#{self.class}"
end

#to_high(level = 0) ⇒ Object

Generates the text of the equivalent HDLRuby::High code. +level+ is the hierachical level of the object.

Raises:



542
543
544
545
# File 'lib/HDLRuby/hruby_low2high.rb', line 542

def to_high(level = 0)
    # Should never be here.
    raise AnyError, "Internal error: to_high should be implemented in class :#{self.class}"
end

#to_vhdl(level = 0) ⇒ Object

Generates the text of the equivalent HDLRuby::High code. +level+ is the hierachical level of the object.

Raises:



1050
1051
1052
1053
# File 'lib/HDLRuby/hruby_low2vhd.rb', line 1050

def to_vhdl(level = 0)
    # Should never be here.
    raise AnyError, "Internal error: to_vhdl should be implemented in class :#{self.class}"
end