Class: HDLRuby::High::RefObject

Inherits:
Low::Ref show all
Includes:
HRef
Defined in:
lib/HDLRuby/hruby_high.rb,
lib/HDLRuby/hruby_rsim.rb,
lib/HDLRuby/hruby_rcsim.rb

Overview

Extends the RefObject class for hybrid Ruby-C simulation.

Constant Summary

Constants included from Low::Low2Symbol

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

Instance Attribute Summary collapse

Attributes inherited from Low::Expression

#type

Attributes included from Low::Hparent

#parent

Instance Method Summary collapse

Methods included from HRef

#each, included, #to_event

Methods inherited from Low::Ref

#each_node, #each_node_deep, #explicit_types, #hash, #map_nodes!, #path_each, #resolve, #to_c, #to_hdr, #to_vhdl

Methods inherited from Low::Expression

#boolean?, #break_types!, #each_node, #each_node_deep, #each_ref_deep, #explicit_types, #extract_selects_to!, #hash, #immutable?, #leftvalue?, #map_nodes!, #replace_expressions!, #replace_names!, #rightvalue?, #set_type!, #signal2subs!, #statement, #to_c, #to_c_expr, #to_hdr, #to_high, #to_vhdl, #use_name?

Methods included from Low::Low2Symbol

#to_sym

Methods included from Low::Hparent

#hierarchy, #no_parent!, #scope

Constructor Details

#initialize(base, object) ⇒ RefObject

Creates a new reference from a +base+ reference and named +object+.



3365
3366
3367
3368
3369
3370
3371
3372
3373
3374
3375
3376
3377
3378
3379
3380
3381
# File 'lib/HDLRuby/hruby_high.rb', line 3365

def initialize(base,object)
    # puts "New RefObjet with base=#{base}, object=#{object}"
    if object.respond_to?(:type) then
        # Typed object, so typed reference.
        super(object.type)
    else
        # Untyped object, so untyped reference.
        super(void)
    end
    # Check and set the base (it must be convertible to a reference).
    unless base.respond_to?(:to_ref)
        raise AnyError, "Invalid base for a RefObject: #{base}"
    end
    @base = base
    # Set the object
    @object = object
end

Dynamic Method Handling

This class handles dynamic methods through the method_missing method

#method_missing(m, *args, &ruby_block) ⇒ Object

Missing methods are looked for into the refered object.



3430
3431
3432
# File 'lib/HDLRuby/hruby_high.rb', line 3430

def method_missing(m, *args, &ruby_block)
    @object.send(m,*args,&ruby_block)
end

Instance Attribute Details

#baseObject (readonly)

The base of the reference



3359
3360
3361
# File 'lib/HDLRuby/hruby_high.rb', line 3359

def base
  @base
end

#objectObject (readonly)

The refered object.



3362
3363
3364
# File 'lib/HDLRuby/hruby_high.rb', line 3362

def object
  @object
end

Instance Method Details

#assign(mode, value) ⇒ Object

Assigns +value+ the the reference.



1355
1356
1357
1358
1359
1360
1361
1362
1363
# File 'lib/HDLRuby/hruby_rsim.rb', line 1355

def assign(mode,value)
    self.object.assign(mode,value)
    # puts "name=#{self.object.name} value=#{value.to_vstr}"
    # puts "c_value=#{self.object.c_value.content}" if self.object.c_value
    # puts "f_value=#{self.object.f_value.content}" if self.object.f_value
    if !(self.object.c_value.eql?(self.object.f_value)) then
        @sim.add_sig_active(self.object)
    end
end

#assign_at(mode, value, index) ⇒ Object

Assigns +value+ at +index+ (integer or range).



1366
1367
1368
1369
1370
1371
1372
1373
1374
# File 'lib/HDLRuby/hruby_rsim.rb', line 1366

def assign_at(mode,value,index)
    # puts "name=#{self.object.name} value=#{value.to_vstr}"
    self.object.assign_at(mode,value,index)
    # puts "c_value=#{self.object.c_value.content}" if self.object.c_value
    # puts "f_value=#{self.object.f_value.content}" if self.object.f_value
    if !(self.object.c_value.eql?(self.object.f_value)) then
        @sim.add_sig_active(self.object)
    end
end

#cloneObject

Clones.



3384
3385
3386
# File 'lib/HDLRuby/hruby_high.rb', line 3384

def clone
    return RefObject.new(self.base.clone,self.object)
end

#constant?Boolean

Tell if the expression is constant.

Returns:

  • (Boolean)


3389
3390
3391
# File 'lib/HDLRuby/hruby_high.rb', line 3389

def constant?
    return self.base.constant?
end

#eql?(obj) ⇒ Boolean

Comparison for hash: structural comparison.

Returns:

  • (Boolean)


3399
3400
3401
3402
3403
3404
# File 'lib/HDLRuby/hruby_high.rb', line 3399

def eql?(obj)
    return false unless obj.is_a?(RefObject)
    return false unless @base.eql?(obj.base)
    return false unless @object.eql?(obj.object)
    return true
end

#execute(mode) ⇒ Object

Execute the expression.



1350
1351
1352
# File 'lib/HDLRuby/hruby_rsim.rb', line 1350

def execute(mode)
    return self.object.execute(mode)
end

#init_sim(systemT) ⇒ Object

Initialize the simulation for system +systemT+.



1308
1309
1310
1311
1312
1313
1314
1315
1316
1317
1318
1319
1320
1321
1322
1323
1324
1325
1326
1327
1328
1329
1330
1331
1332
1333
1334
1335
1336
1337
1338
1339
1340
1341
1342
1343
1344
1345
1346
1347
# File 'lib/HDLRuby/hruby_rsim.rb', line 1308

def init_sim(systemT)
    # puts "init_sim for RefObject=#{self}"
    @sim = systemT

    # Modify the exectute and assign methods if the object has
    # sub signals (for faster execution).
    if self.object.each_signal.any? then
        ## Execute the expression.
        self.define_singleton_method(:execute) do |mode|
            # Recurse on the children.
            iter = self.object.each_signal
            iter = iter.reverse_each unless self.object.type.direction == :big
            tmpe = iter.map {|sig| sig.execute(mode) }
            # Concatenate the result.
            # return tmpe.reduce(:concat)
            return Vprocess.concat(*tmpe)
        end
        ## Assigns +value+ the the reference.
        self.define_singleton_method(:assign) do |mode,value|
            # puts "RefObject #{self} assign with object=#{self.object}"
            # Flatten the value type.
            value.type = [value.type.width].to_type
            pos = 0
            width = 0
            # Recurse on the children.
            iter = self.object.each_signal
            iter = iter.reverse_each unless self.object.type.direction == :big
            iter.each do |sig|
                width = sig.type.width
                sig.assign(mode,value[(pos+width-1).to_expr..pos.to_expr])
                # Tell the signal changed.
                if !(sig.c_value.eql?(sig.f_value)) then
                    @sim.add_sig_active(sig)
                end
                # Prepare for the next reference.
                pos += width
            end
        end
    end
end

#to_lowObject

Converts the name reference to a HDLRuby::Low::RefName.



3407
3408
3409
3410
3411
3412
3413
3414
3415
3416
3417
3418
3419
3420
3421
3422
3423
3424
3425
3426
3427
# File 'lib/HDLRuby/hruby_high.rb', line 3407

def to_low
    # puts "to_low with base=#{@base} @object=#{@object}"
    # puts "@object.name=#{@object.name}"
    if @base.is_a?(RefThis) && 
            (@object.parent != High.top_user) &&
            (@object.parent != High.cur_system) &&
            (!@object.parent.name.empty?) then
        # Need to have a hierachical access.
        # puts "Indirect access for #{self.object.name}: #{self.object.parent.name}(#{self.object.parent.class}) != #{High.cur_system.name}(#{High.top_user.class})"
        refNameL = HDLRuby::Low::RefName.new(self.type.to_low,
                                             @object.parent.to_ref.to_low,@object.name)
    else
        # Direct access is enough.
        refNameL = HDLRuby::Low::RefName.new(self.type.to_low,
                                     @base.to_ref.to_low,@object.name)
    end
    # # For debugging: set the source high object 
    # refNameL.properties[:low2high] = self.hdr_id
    # self.properties[:high2low] = refNameL
    return refNameL
end

#to_rcsimObject

Generate the C description of the reference object.



1030
1031
1032
1033
1034
1035
1036
1037
1038
1039
1040
1041
# File 'lib/HDLRuby/hruby_rcsim.rb', line 1030

def to_rcsim
    # puts "object=#{self.object.name}(#{self.object})"
    if self.object.is_a?(SignalI)
        return self.object.each_signal.any? ? self.to_rcsim_subs :
            self.object.rcsignalI
    elsif self.object.is_a?(SignalC)
        return self.object.each_signal.any? ? self.to_rcsim_subs :
            self.object.rcsignalC
    else
        raise "Invalid object: #{self.object}"
    end
end

#to_rcsim_subsObject

Generate the C description of the reference object with sub signals.



1010
1011
1012
1013
1014
1015
1016
1017
1018
1019
1020
1021
1022
1023
1024
1025
1026
1027
# File 'lib/HDLRuby/hruby_rcsim.rb', line 1010

def to_rcsim_subs
    # Create the reference concat C object.
    # The reference is always big endian, it is the sequence
    # of element which is reversed if necessary.
    rcref = RCSim.rcsim_make_refConcat(self.type.to_rcsim,:big)
                                 # self.type.direction)

    # Add the concatenated expressions. */
    if self.object.each_signal.any? then
        iter = self.object.each_signal
        iter = iter.reverse_each if self.type.direction == :big
        RCSim.rcsim_add_refConcat_refs(rcref, iter.map do|sig|
            sig.is_a?(SignalI) ? sig.rcsignalI : sig.rcsignalC
        end)
    end
    
    return rcref
end

#to_refObject

Converts to a new reference.



3394
3395
3396
# File 'lib/HDLRuby/hruby_high.rb', line 3394

def to_ref
    return RefObject.new(@base,@object)
end