Class: Origen::Pins::Pin

Inherits:
Object
  • Object
show all
Defined in:
lib/origen_sim/origen/pins/pin.rb

Overview

Override the Origen pin model so we can hook into all changes to pin states

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(id, owner, options = {}) ⇒ Pin

Returns a new instance of Pin.



10
11
12
# File 'lib/origen_sim/origen/pins/pin.rb', line 10

def initialize(id, owner, options = {})
  _orig_initialize(id, owner, options)
end

Instance Attribute Details

#simulation_indexObject

The index number that is used to refer to the pin within the simulation



7
8
9
# File 'lib/origen_sim/origen/pins/pin.rb', line 7

def simulation_index
  @simulation_index
end

Instance Method Details

#_analog_pin_?Boolean

Returns:

  • (Boolean)


88
89
90
# File 'lib/origen_sim/origen/pins/pin.rb', line 88

def _analog_pin_?
  type == :analog || is_a?(Origen::Pins::PowerPin) || is_a?(Origen::Pins::GroundPin)
end

#_orig_assertObject



69
# File 'lib/origen_sim/origen/pins/pin.rb', line 69

alias_method :_orig_assert, :assert

#_orig_driveObject



58
# File 'lib/origen_sim/origen/pins/pin.rb', line 58

alias_method :_orig_drive, :drive

#_orig_initializeObject



9
# File 'lib/origen_sim/origen/pins/pin.rb', line 9

alias_method :_orig_initialize, :initialize

#_orig_set_stateObject



21
# File 'lib/origen_sim/origen/pins/pin.rb', line 21

alias_method :_orig_set_state, :set_state

#_orig_set_valueObject



14
# File 'lib/origen_sim/origen/pins/pin.rb', line 14

alias_method :_orig_set_value, :set_value

#_orig_state=Object



28
# File 'lib/origen_sim/origen/pins/pin.rb', line 28

alias_method :_orig_state=, :state=

#apply_forceObject



92
93
94
95
96
# File 'lib/origen_sim/origen/pins/pin.rb', line 92

def apply_force
  if force
    simulator.put("2^#{simulation_index}^#{force}")
  end
end

#assert(*args) ⇒ Object Also known as: compare, expect, read, measure



70
71
72
73
74
75
76
77
78
79
80
81
82
# File 'lib/origen_sim/origen/pins/pin.rb', line 70

def assert(*args)
  if _analog_pin_? && simulation_running? && tester.simulator.wreal?
    drive_enabled = tester.peek("#{driver_net}.drive_en").to_i
    if drive_enabled == 1
      tester.poke("#{driver_net}.drive_en", 0)
      tester.cycle
    end
    measured = tester.peek("#{driver_net}.pin", true)
    # Could implement checking/limits here in future
  else
    _orig_assert(*args)
  end
end

#drive(*args) ⇒ Object Also known as: write



59
60
61
62
63
64
65
66
# File 'lib/origen_sim/origen/pins/pin.rb', line 59

def drive(*args)
  if _analog_pin_? && simulation_running? && tester.simulator.wreal?
    tester.poke("#{driver_net}.drive_en", 1)
    tester.poke("#{driver_net}.drive", args.first + 0.0)
  else
    _orig_drive(*args)
  end
end

#driver_netObject



54
55
56
# File 'lib/origen_sim/origen/pins/pin.rb', line 54

def driver_net
  @driver_net ||= "#{tester.simulator.testbench_top}.pins.#{rtl_name}"
end

#reset_simulator_stateObject



49
50
51
52
# File 'lib/origen_sim/origen/pins/pin.rb', line 49

def reset_simulator_state
  @simulator_state = nil
  @simulator_value = nil
end

#set_state(state) ⇒ Object



22
23
24
25
26
# File 'lib/origen_sim/origen/pins/pin.rb', line 22

def set_state(state)
  ret = _orig_set_state(state)
  update_simulation if simulation_running?
  ret
end

#set_value(val) ⇒ Object



15
16
17
18
19
# File 'lib/origen_sim/origen/pins/pin.rb', line 15

def set_value(val)
  ret = _orig_set_value(val)
  update_simulation if simulation_running?
  ret
end

#simulation_running?Boolean

Returns:

  • (Boolean)


35
36
37
# File 'lib/origen_sim/origen/pins/pin.rb', line 35

def simulation_running?
  tester && tester.is_a?(OrigenSim::Tester)
end

#simulatorObject



39
40
41
# File 'lib/origen_sim/origen/pins/pin.rb', line 39

def simulator
  OrigenSim.simulator
end

#simulator_needs_update?Boolean

Returns true if the current pin state is different to that last given to the simulator

Returns:

  • (Boolean)


44
45
46
47
# File 'lib/origen_sim/origen/pins/pin.rb', line 44

def simulator_needs_update?
  return false if state == :dont_care && @simulator_state == :dont_care
  state != @simulator_state || value != @simulator_value
end

#state=(val) ⇒ Object



29
30
31
32
33
# File 'lib/origen_sim/origen/pins/pin.rb', line 29

def state=(val)
  ret = _orig_state = (val)
  update_simulation if simulation_running?
  ret
end

#update_simulationObject

Applies the current pin state to the simulation, this is triggered everytime the pin state or value changes



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
# File 'lib/origen_sim/origen/pins/pin.rb', line 100

def update_simulation
  return if force || !simulation_index || !tester.timeset || !simulator_needs_update?
  case state
    when :drive
      @simulator_state = :drive
      @simulator_value = value
      simulator.put("2^#{simulation_index}^#{value}")
    when :compare
      if tester.read_reg_open?
        tester.read_reg_cycles[tester.cycle_count + 1] ||= {}
        tester.read_reg_cycles[tester.cycle_count + 1][self] = state_meta
        tester.read_reg_meta_supplied = true if state_meta[:position]
      end
      @simulator_state = :compare
      @simulator_value = value
      simulator.put("4^#{simulation_index}^#{value}")
    when :dont_care
      @simulator_state = :dont_care
      simulator.put("5^#{simulation_index}")
    when :capture
      @simulator_state = :capture
      simulator.put("e^#{simulation_index}")
    when :drive_very_high, :drive_mem, :expect_mem, :compare_midband
      fail "Simulation of pin state #{state} is not implemented yet!"
    else
      fail "Simulation of pin state #{state} is not implemented yet!"
  end
end