origen_sim 0.16.1 → 0.20.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/config/application.rb +2 -0
- data/config/commands.rb +29 -20
- data/config/version.rb +2 -2
- data/ext/bridge.c +72 -14
- data/ext/origen.c +29 -17
- data/ext/origen.h +6 -0
- data/ext/origen_tasks.tab +2 -0
- data/lib/origen_sim/commands/build.rb +90 -59
- data/lib/origen_sim/origen/pins/pin.rb +38 -0
- data/lib/origen_sim/origen/top_level.rb +8 -3
- data/lib/origen_sim/simulation.rb +1 -1
- data/lib/origen_sim/simulator/user_details.rb +0 -1
- data/lib/origen_sim/simulator.rb +70 -70
- data/lib/origen_sim/tester.rb +53 -10
- data/lib/origen_sim_dev/dut.rb +66 -46
- data/lib/origen_sim_dev/ip.rb +15 -8
- data/pattern/concurrent_ip.rb +17 -0
- data/pattern/test.rb +122 -10
- data/templates/empty.rc +16 -26
- data/templates/origen_guides/simulation/ams.md.erb +141 -0
- data/templates/origen_guides/simulation/compiling.md.erb +52 -7
- data/templates/origen_guides/simulation/debugging.md.erb +1 -1
- data/templates/origen_guides/simulation/direct.md.erb +112 -0
- data/templates/origen_guides/simulation/environment.md.erb +6 -3
- data/templates/origen_guides/simulation/patterns.md.erb +2 -7
- data/templates/rtl_v/origen.v.erb +114 -12
- metadata +13 -9
data/lib/origen_sim/simulator.rb
CHANGED
@@ -428,8 +428,8 @@ module OrigenSim
|
|
428
428
|
edir = Pathname.new(wave_config_dir).relative_path_from(Pathname.pwd)
|
429
429
|
cmd = "cd #{edir} && "
|
430
430
|
if configuration[:verdi]
|
431
|
-
unless ENV['VCS_HOME']
|
432
|
-
|
431
|
+
unless ENV['VCS_HOME']
|
432
|
+
Origen.log.warning "Your environment doesn't define VCS_HOME, you will probably need that to run Verdi"
|
433
433
|
end
|
434
434
|
edir = Pathname.new(wave_config_dir).relative_path_from(Pathname.pwd)
|
435
435
|
cmd = "cd #{edir} && "
|
@@ -778,7 +778,7 @@ module OrigenSim
|
|
778
778
|
# set up internal handles to efficiently access them
|
779
779
|
def define_pins
|
780
780
|
@pins_by_rtl_name = {}
|
781
|
-
dut.rtl_pins.each_with_index do |(name, pin), i|
|
781
|
+
dut.rtl_pins(type: :digital).each_with_index do |(name, pin), i|
|
782
782
|
@pins_by_rtl_name[pin.rtl_name] = pin
|
783
783
|
pin.simulation_index = i
|
784
784
|
put("0^#{pin.rtl_name}^#{i}^#{pin.drive_wave.index}^#{pin.compare_wave.index}")
|
@@ -865,6 +865,7 @@ module OrigenSim
|
|
865
865
|
|
866
866
|
def error(message)
|
867
867
|
simulation.logged_errors = true
|
868
|
+
poke "#{testbench_top}.debug.errors", error_count + 1
|
868
869
|
log message, :error
|
869
870
|
end
|
870
871
|
|
@@ -877,87 +878,82 @@ module OrigenSim
|
|
877
878
|
# resolve to a valid node
|
878
879
|
#
|
879
880
|
# The value is returned as an instance of Origen::Value
|
880
|
-
def peek(net)
|
881
|
-
# The Verilog spec does not specify that underlying VPI put method should
|
882
|
-
# handle a part select, so some simulators do not handle it. Therefore we
|
883
|
-
# deal with it here to ensure cross simulator compatibility.
|
884
|
-
|
885
|
-
# http://rubular.com/r/eTVGzrYmXQ
|
886
|
-
if net =~ /(.*)\[(\d+):?(\.\.)?(\d*)\]$/
|
887
|
-
net = Regexp.last_match(1)
|
888
|
-
msb = Regexp.last_match(2).to_i
|
889
|
-
lsb = Regexp.last_match(4)
|
890
|
-
lsb = lsb.empty? ? nil : lsb.to_i
|
891
|
-
end
|
892
|
-
|
881
|
+
def peek(net, real = false)
|
893
882
|
sync_up
|
894
|
-
|
895
|
-
|
883
|
+
if dut_version > '0.19.0'
|
884
|
+
if real
|
885
|
+
put("9^#{clean(net)}^f")
|
886
|
+
m = get.strip
|
887
|
+
if m == 'FAIL'
|
888
|
+
return nil
|
889
|
+
else
|
890
|
+
m.to_f
|
891
|
+
end
|
892
|
+
else
|
893
|
+
put("9^#{clean(net)}^i")
|
894
|
+
m = get.strip
|
896
895
|
|
897
|
-
|
898
|
-
|
899
|
-
|
900
|
-
if msb
|
901
|
-
# Setting a range of bits
|
902
|
-
if lsb
|
903
|
-
Origen::Value.new('b' + m[(m.size - 1 - msb)..(m.size - 1 - lsb)])
|
896
|
+
if m == 'FAIL'
|
897
|
+
Origen.log.warning "Peek of net #{net} failed to return any data!"
|
898
|
+
return nil
|
904
899
|
else
|
905
|
-
Origen::Value.new('b' + m
|
900
|
+
Origen::Value.new('b' + m)
|
906
901
|
end
|
902
|
+
end
|
903
|
+
else
|
904
|
+
put("9^#{clean(net)}")
|
905
|
+
m = get.strip
|
906
|
+
|
907
|
+
if m == 'FAIL'
|
908
|
+
Origen.log.warning "Peek of net #{net} failed to return any data!"
|
909
|
+
return nil
|
907
910
|
else
|
908
911
|
Origen::Value.new('b' + m)
|
909
912
|
end
|
910
913
|
end
|
911
914
|
end
|
912
915
|
|
916
|
+
def peek_real(net)
|
917
|
+
peek(net, true)
|
918
|
+
end
|
919
|
+
|
913
920
|
# Forces the given value to the given net.
|
914
921
|
# Note that no error checking is done and no error will be communicated if an illegal
|
915
922
|
# net is supplied. The user should follow up with a peek if they want to verify that
|
916
923
|
# the poke was applied.
|
917
924
|
def poke(net, value)
|
918
|
-
|
919
|
-
|
920
|
-
|
921
|
-
|
922
|
-
|
923
|
-
|
924
|
-
|
925
|
-
|
926
|
-
|
927
|
-
|
928
|
-
|
929
|
-
v = peek(path)
|
930
|
-
return nil unless v
|
931
|
-
# Setting a range of bits
|
932
|
-
if lsb
|
933
|
-
upper = v >> (msb + 1)
|
934
|
-
# Make sure value does not overflow
|
935
|
-
value = value[(msb - lsb)..0]
|
936
|
-
if lsb == 0
|
937
|
-
value = (upper << (msb + 1)) | value
|
938
|
-
else
|
939
|
-
lower = v[(lsb - 1)..0]
|
940
|
-
value = (upper << (msb + 1)) |
|
941
|
-
(value << lsb) | lower
|
942
|
-
end
|
925
|
+
sync_up
|
926
|
+
if dut_version > '0.19.0'
|
927
|
+
if value.is_a?(Integer)
|
928
|
+
put("b^#{clean(net)}^i^#{value}")
|
929
|
+
else
|
930
|
+
put("b^#{clean(net)}^f^#{value}")
|
931
|
+
end
|
932
|
+
else
|
933
|
+
put("b^#{clean(net)}^#{value}")
|
934
|
+
end
|
935
|
+
end
|
943
936
|
|
944
|
-
|
937
|
+
def force(net, value)
|
938
|
+
sync_up
|
939
|
+
if dut_version > '0.19.0'
|
940
|
+
if value.is_a?(Integer)
|
941
|
+
put("r^#{clean(net)}^i^#{value}")
|
945
942
|
else
|
946
|
-
|
947
|
-
upper = v >> 1
|
948
|
-
value = (upper << 1) | value[0]
|
949
|
-
else
|
950
|
-
lower = v[(msb - 1)..0]
|
951
|
-
upper = v >> (msb + 1)
|
952
|
-
value = (upper << (msb + 1)) |
|
953
|
-
(value[0] << msb) | lower
|
954
|
-
end
|
943
|
+
put("r^#{clean(net)}^f^#{value}")
|
955
944
|
end
|
956
|
-
|
945
|
+
else
|
946
|
+
OrigenSim.error 'Your DUT needs to be recompiled with OrigenSim >= 0.20.0 to support forcing, force not applied!'
|
957
947
|
end
|
948
|
+
end
|
958
949
|
|
950
|
+
def release(net)
|
959
951
|
sync_up
|
960
|
-
|
952
|
+
if dut_version > '0.19.0'
|
953
|
+
put("s^#{clean(net)}")
|
954
|
+
else
|
955
|
+
OrigenSim.error 'Your DUT needs to be recompiled with OrigenSim >= 0.20.0 to support releasing, force not released!'
|
956
|
+
end
|
961
957
|
end
|
962
958
|
|
963
959
|
def interactive_shutdown
|
@@ -1124,17 +1120,13 @@ module OrigenSim
|
|
1124
1120
|
end
|
1125
1121
|
|
1126
1122
|
def peek_str(signal)
|
1127
|
-
val =
|
1123
|
+
val = peek(signal)
|
1128
1124
|
unless val.nil?
|
1129
|
-
puts val
|
1130
|
-
puts val.class
|
1131
1125
|
# All zeros seems to be what an empty string is returned from the VPI,
|
1132
1126
|
# Otherwise, break the string up into 8-bit chunks and decode the ASCII>
|
1133
1127
|
val = (val.to_s == 'b00000000' ? '' : val.to_s[1..-1].scan(/.{1,8}/).collect { |char| char.to_i(2).chr }.join)
|
1134
1128
|
end
|
1135
1129
|
val
|
1136
|
-
# puts "Peaking #{signal}: #{a}: #{a.class}"
|
1137
|
-
# tester.simulator.peek(signal).to_s[1..-1].scan(/.{1,8}/).collect { |char| char.to_i(2).chr }.join
|
1138
1130
|
end
|
1139
1131
|
alias_method :str_peek, :peek_str
|
1140
1132
|
alias_method :peek_string, :peek_str
|
@@ -1161,8 +1153,8 @@ module OrigenSim
|
|
1161
1153
|
errors = []
|
1162
1154
|
error_count.times do |i|
|
1163
1155
|
data = get # => "tdo,648,1,0\n"
|
1164
|
-
pin_name, cycle, expected,
|
1165
|
-
errors << { pin_name: pin_name, cycle: cycle.to_i, expected: expected.to_i,
|
1156
|
+
pin_name, cycle, expected, received = *(data.strip.split(','))
|
1157
|
+
errors << { pin_name: pin_name, cycle: cycle.to_i, expected: expected.to_i, received: received.to_i }
|
1166
1158
|
end
|
1167
1159
|
[true, error_count > max_errors, errors]
|
1168
1160
|
end
|
@@ -1175,6 +1167,14 @@ module OrigenSim
|
|
1175
1167
|
get.strip.to_i
|
1176
1168
|
end
|
1177
1169
|
|
1170
|
+
# Returns true if the snapshot has been compiled with WREAL support
|
1171
|
+
def wreal?
|
1172
|
+
return @wreal if defined?(@wreal)
|
1173
|
+
@wreal = (dut_version > '0.19.0' &&
|
1174
|
+
peek("#{testbench_top}.debug.wreal_enabled").to_i == 1)
|
1175
|
+
end
|
1176
|
+
alias_method :wreal_enabled?, :wreal?
|
1177
|
+
|
1178
1178
|
private
|
1179
1179
|
|
1180
1180
|
# Will be called when the simulator has aborted due to the max error count being exceeded
|
data/lib/origen_sim/tester.rb
CHANGED
@@ -16,6 +16,7 @@ module OrigenSim
|
|
16
16
|
simulator.configure(opts, &block)
|
17
17
|
@comment_buffer = []
|
18
18
|
@last_comment_size = 0
|
19
|
+
@execution_time_in_ns = 0
|
19
20
|
super()
|
20
21
|
end
|
21
22
|
|
@@ -38,9 +39,9 @@ module OrigenSim
|
|
38
39
|
end
|
39
40
|
@sync_pins.map do |pin|
|
40
41
|
if @sync_cycles.size == 1
|
41
|
-
simulator.peek("#{simulator.testbench_top}.pins.#{pin.id}.sync_memory[0]
|
42
|
+
simulator.peek("#{simulator.testbench_top}.pins.#{pin.id}.sync_memory")[0]
|
42
43
|
else
|
43
|
-
simulator.peek("#{simulator.testbench_top}.pins.#{pin.id}.sync_memory[
|
44
|
+
simulator.peek("#{simulator.testbench_top}.pins.#{pin.id}.sync_memory").to_i[(@sync_cycles - 1)..0]
|
44
45
|
end
|
45
46
|
end
|
46
47
|
end
|
@@ -80,11 +81,13 @@ module OrigenSim
|
|
80
81
|
unless options[:timeset]
|
81
82
|
puts 'No timeset defined!'
|
82
83
|
puts 'Add one to your top level startup method or target like this:'
|
83
|
-
puts '
|
84
|
+
puts 'tester.set_timeset("nvmbist", 40) # Where 40 is the period in ns'
|
84
85
|
exit 1
|
85
86
|
end
|
86
87
|
flush_comments unless @comment_buffer.empty?
|
87
|
-
|
88
|
+
repeat = options[:repeat] || 1
|
89
|
+
simulator.cycle(repeat)
|
90
|
+
@execution_time_in_ns += repeat * tester.timeset.period_in_ns
|
88
91
|
if @after_next_vector
|
89
92
|
@after_next_vector.call(@after_next_vector_args)
|
90
93
|
@after_next_vector = nil
|
@@ -94,6 +97,7 @@ module OrigenSim
|
|
94
97
|
|
95
98
|
def c1(msg, options = {})
|
96
99
|
if @step_comment_on
|
100
|
+
PatSeq.add_thread(msg) unless options[:no_thread_id]
|
97
101
|
simulator.log msg
|
98
102
|
@comment_buffer << msg
|
99
103
|
end
|
@@ -293,7 +297,7 @@ module OrigenSim
|
|
293
297
|
if c = read_reg_cycles[error[:cycle]]
|
294
298
|
if p = c[simulator.pins_by_rtl_name[error[:pin_name]]]
|
295
299
|
if p[:position]
|
296
|
-
diffs << [p[:position], error[:
|
300
|
+
diffs << [p[:position], error[:received], error[:expected]]
|
297
301
|
end
|
298
302
|
end
|
299
303
|
end
|
@@ -301,6 +305,7 @@ module OrigenSim
|
|
301
305
|
if diffs.empty?
|
302
306
|
if @read_reg_meta_supplied
|
303
307
|
Origen.log.warning 'It looks like the miscompare(s) occurred on pins/cycles that are not associated with register data'
|
308
|
+
non_data_miscompare = true
|
304
309
|
else
|
305
310
|
Origen.log.warning 'It looks like your current read register driver does not provide the necessary meta-data to map these errors to an actual register value'
|
306
311
|
end
|
@@ -323,7 +328,11 @@ module OrigenSim
|
|
323
328
|
end
|
324
329
|
|
325
330
|
diffs.each do |position, received, expected|
|
326
|
-
|
331
|
+
if received == -1
|
332
|
+
reg_or_val[position].unknown = true
|
333
|
+
else
|
334
|
+
reg_or_val[position].data = received
|
335
|
+
end
|
327
336
|
end
|
328
337
|
|
329
338
|
actual = bit_names.map do |name|
|
@@ -357,7 +366,8 @@ module OrigenSim
|
|
357
366
|
Origen.log.error msg
|
358
367
|
end
|
359
368
|
else
|
360
|
-
|
369
|
+
# This means that the correct data was read, but errors occurred on other pins/cycles during the transaction
|
370
|
+
msg += " received #{expected}" if non_data_miscompare
|
361
371
|
Origen.log.error msg
|
362
372
|
end
|
363
373
|
end
|
@@ -367,7 +377,10 @@ module OrigenSim
|
|
367
377
|
if actual_data_available
|
368
378
|
actual = reg_or_val
|
369
379
|
diffs.each do |position, received, expected|
|
370
|
-
if received == 1
|
380
|
+
if received == -1
|
381
|
+
actual = '?' * reg_or_val.to_s(16).size
|
382
|
+
break
|
383
|
+
elsif received == 1
|
371
384
|
actual |= (1 << position)
|
372
385
|
else
|
373
386
|
lower = actual[(position - 1)..0]
|
@@ -376,9 +389,14 @@ module OrigenSim
|
|
376
389
|
actual |= lower
|
377
390
|
end
|
378
391
|
end
|
379
|
-
|
392
|
+
if actual.is_a?(String)
|
393
|
+
msg += " received #{actual}"
|
394
|
+
else
|
395
|
+
msg += " received #{actual.to_s(16).upcase}"
|
396
|
+
end
|
380
397
|
else
|
381
|
-
|
398
|
+
# This means that the correct data was read, but errors occurred on other pins/cycles during the transaction
|
399
|
+
msg += " received #{reg_or_val.to_s(16).upcase}" if non_data_miscompare
|
382
400
|
end
|
383
401
|
Origen.log.error msg
|
384
402
|
end
|
@@ -409,6 +427,31 @@ module OrigenSim
|
|
409
427
|
@read_reg_meta_supplied = val
|
410
428
|
end
|
411
429
|
|
430
|
+
# Shorthand for simulator.poke
|
431
|
+
def poke(*args)
|
432
|
+
simulator.poke(*args)
|
433
|
+
end
|
434
|
+
|
435
|
+
# Shorthand for simulator.peek
|
436
|
+
def peek(*args)
|
437
|
+
simulator.peek(*args)
|
438
|
+
end
|
439
|
+
|
440
|
+
# Shorthand for simulator.peek_real
|
441
|
+
def peek_real(*args)
|
442
|
+
simulator.peek_real(*args)
|
443
|
+
end
|
444
|
+
|
445
|
+
# Shorthand for simulator.force
|
446
|
+
def force(*args)
|
447
|
+
simulator.force(*args)
|
448
|
+
end
|
449
|
+
|
450
|
+
# Shorthand for simulator.release
|
451
|
+
def release(*args)
|
452
|
+
simulator.release(*args)
|
453
|
+
end
|
454
|
+
|
412
455
|
private
|
413
456
|
|
414
457
|
def flush_comments
|
data/lib/origen_sim_dev/dut.rb
CHANGED
@@ -26,6 +26,8 @@ module OrigenSimDev
|
|
26
26
|
add_pin :v2, rtl_name: :nc
|
27
27
|
add_pin :done
|
28
28
|
add_pin :not_present
|
29
|
+
add_power_pin :vdd
|
30
|
+
add_pin :ana, type: :analog
|
29
31
|
|
30
32
|
timeset :func do |t|
|
31
33
|
# Generate a clock pulse on TCK
|
@@ -73,6 +75,15 @@ module OrigenSimDev
|
|
73
75
|
reg.bits 2..0, :b6
|
74
76
|
end
|
75
77
|
|
78
|
+
add_reg :ana_test, 0x1C do |reg|
|
79
|
+
reg.bit 0, :vdd_valid, access: :ro
|
80
|
+
reg.bit 1, :bgap_out
|
81
|
+
reg.bit 2, :osc_out
|
82
|
+
reg.bit 3, :vdd_div4
|
83
|
+
end
|
84
|
+
|
85
|
+
add_reg :x_reg, 0x20
|
86
|
+
|
76
87
|
sub_block :ip1, class_name: 'IP'
|
77
88
|
sub_block :ip2, class_name: 'IP'
|
78
89
|
end
|
@@ -84,6 +95,10 @@ module OrigenSimDev
|
|
84
95
|
end
|
85
96
|
end
|
86
97
|
|
98
|
+
def simulation_startup
|
99
|
+
power_pin(:vdd).drive(0)
|
100
|
+
end
|
101
|
+
|
87
102
|
def startup(options = {})
|
88
103
|
# tester.simulator.log_messages = true
|
89
104
|
tester.set_timeset('func', 100)
|
@@ -101,60 +116,65 @@ module OrigenSimDev
|
|
101
116
|
end
|
102
117
|
|
103
118
|
def write_register(reg, options = {})
|
104
|
-
|
105
|
-
|
106
|
-
|
107
|
-
|
108
|
-
|
109
|
-
|
110
|
-
|
111
|
-
|
112
|
-
|
113
|
-
|
114
|
-
|
115
|
-
|
116
|
-
|
117
|
-
|
118
|
-
|
119
|
-
|
119
|
+
PatSeq.serialize :jtag do
|
120
|
+
if reg.path =~ /ip(\d)/
|
121
|
+
ir_val = 0b0100 | Regexp.last_match(1).to_i
|
122
|
+
jtag.write_ir(ir_val, size: 4)
|
123
|
+
ip = reg.parent
|
124
|
+
ip.dr.bits(:write).write(1)
|
125
|
+
ip.dr.bits(:address).write(reg.address)
|
126
|
+
ip.dr.bits(:data).write(reg.data)
|
127
|
+
jtag.write_dr(ip.dr)
|
128
|
+
# Write to top-level reg
|
129
|
+
else
|
130
|
+
jtag.write_ir(0x8, size: 4)
|
131
|
+
dr.rg_enable.write(1)
|
132
|
+
dr.rg_read.write(0)
|
133
|
+
dr.rg_addr.write(reg.address)
|
134
|
+
dr.rg_data.write(reg.data)
|
135
|
+
jtag.write_dr(dr)
|
136
|
+
end
|
120
137
|
end
|
121
138
|
end
|
122
139
|
|
123
140
|
def read_register(reg, options = {})
|
124
|
-
|
125
|
-
|
126
|
-
|
127
|
-
|
128
|
-
|
129
|
-
|
130
|
-
|
141
|
+
PatSeq.serialize :jtag do
|
142
|
+
tester.read_register(reg, options) do
|
143
|
+
# Special read for this register to test sync'ing over a parallel port
|
144
|
+
if reg.id == :parallel_read
|
145
|
+
pins = []
|
146
|
+
reg.shift_out_with_index do |bit, i|
|
147
|
+
if bit.is_to_be_stored?
|
148
|
+
pins << dut.pins(:dout)[i]
|
149
|
+
end
|
131
150
|
end
|
132
|
-
|
133
|
-
|
134
|
-
|
135
|
-
dut.pins(:dout).dont_care
|
136
|
-
else
|
137
|
-
if reg.path =~ /ip(\d)/
|
138
|
-
ir_val = 0b0100 | Regexp.last_match(1).to_i
|
139
|
-
jtag.write_ir(ir_val, size: 4)
|
140
|
-
ip = reg.parent
|
141
|
-
ip.dr.bits(:write).write(0)
|
142
|
-
ip.dr.bits(:address).write(reg.address)
|
143
|
-
ip.dr.bits(:data).write(0)
|
144
|
-
jtag.write_dr(ip.dr)
|
145
|
-
ip.dr.bits(:data).copy_all(reg)
|
146
|
-
jtag.read_dr(ip.dr)
|
151
|
+
tester.store_next_cycle(*pins.reverse)
|
152
|
+
1.cycle
|
153
|
+
dut.pins(:dout).dont_care
|
147
154
|
else
|
148
|
-
|
149
|
-
|
150
|
-
|
151
|
-
|
152
|
-
|
153
|
-
|
154
|
-
|
155
|
-
|
155
|
+
if reg.path =~ /ip(\d)/
|
156
|
+
ir_val = 0b0100 | Regexp.last_match(1).to_i
|
157
|
+
jtag.write_ir(ir_val, size: 4)
|
158
|
+
ip = reg.parent
|
159
|
+
ip.dr.bits(:write).write(0)
|
160
|
+
ip.dr.bits(:address).write(reg.address)
|
161
|
+
ip.dr.bits(:data).write(0)
|
162
|
+
jtag.write_dr(ip.dr)
|
163
|
+
ip.dr.bits(:data).copy_all(reg)
|
164
|
+
jtag.read_dr(ip.dr)
|
165
|
+
else
|
166
|
+
jtag.write_ir(0x8, size: 4)
|
167
|
+
dr.rg_enable.write(1)
|
168
|
+
dr.rg_read.write(1)
|
169
|
+
dr.rg_addr.write(reg.address)
|
170
|
+
jtag.write_dr(dr)
|
171
|
+
dr.rg_enable.write(0)
|
172
|
+
dr.rg_data.copy_all(reg)
|
173
|
+
jtag.read_dr(dr)
|
174
|
+
end
|
156
175
|
end
|
157
176
|
end
|
177
|
+
reg.clear_flags
|
158
178
|
end
|
159
179
|
end
|
160
180
|
end
|
data/lib/origen_sim_dev/ip.rb
CHANGED
@@ -33,14 +33,21 @@ module OrigenSimDev
|
|
33
33
|
|
34
34
|
def execute_cmd(code)
|
35
35
|
ss "Execute command #{code}"
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
36
|
+
PatSeq.reserve :jtag do
|
37
|
+
# This is redundant, but added as a test that if an embedded reservation is made to the same
|
38
|
+
# resource then the end of the inner block does not release the reservation before completion
|
39
|
+
# of the outer block
|
40
|
+
PatSeq.reserve :jtag do
|
41
|
+
# Verify that no command is currently running
|
42
|
+
status.read!(0)
|
43
|
+
end
|
44
|
+
|
45
|
+
cmd.write!(code)
|
46
|
+
10.cycles
|
47
|
+
# Verify that the command has started
|
48
|
+
|
49
|
+
status.busy.read!(1)
|
50
|
+
end
|
44
51
|
|
45
52
|
# Wait for the command to complete, a 'command' lasts for
|
46
53
|
# 1000 cycles times the command code
|