origen_sim 0.20.7 → 0.21.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/config/commands.rb +27 -1
- data/config/shared_commands.rb +9 -2
- data/config/version.rb +2 -2
- data/ext/bridge.c +11 -11
- data/ext/common.h +1 -0
- data/ext/defines.h.erb +3 -0
- data/lib/origen_sim/commands/build.rb +190 -92
- data/lib/origen_sim/origen/pins/pin.rb +4 -4
- data/lib/origen_sim/origen/top_level.rb +17 -8
- data/lib/origen_sim/origen_testers/api.rb +1 -1
- data/lib/origen_sim/simulator.rb +127 -31
- data/lib/origen_sim/tester.rb +7 -3
- data/lib/origen_sim.rb +13 -0
- data/pattern/test.rb +1 -1
- data/templates/probe.tcl.erb +1 -2
- data/templates/rtl_v/origen.v.erb +104 -34
- metadata +5 -6
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 33d839d0d39003f94420f011ba006246dc9ff62bbf2435fd5ae269fe4d1f459c
|
4
|
+
data.tar.gz: 9a99d9f31fe6535f00df5feb82f78a6a2e90f4af70e38f685c37af61592be7e7
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 75f75689510b1978d0650c6de92267acb4386b25a5f6d528f253ce282406d406b7c5e4942ed26d6d8188e9a49b337d34069343834fec8c0e28334d7caf36b765
|
7
|
+
data.tar.gz: 1e5e23dae2c4e20a5b969cd2322e9aafde47988a468f69f958ba602fbb74e2b4bfc083d2b1752ae481f4b45e8475f083bf54d3ab661c3f211ccf7908bdce0222
|
data/config/commands.rb
CHANGED
@@ -23,13 +23,36 @@ when "sim:build_example"
|
|
23
23
|
ARGV.delete_at(index)
|
24
24
|
Origen.environment.temporary = ARGV.delete_at(index)
|
25
25
|
end
|
26
|
+
if ['cadence'].include?(Origen.environment.name)
|
27
|
+
cmd += ' --define ORIGEN_SIM_CADENCE'
|
28
|
+
elsif ['synopsys', 'synopsys_verdi'].include?(Origen.environment.name)
|
29
|
+
cmd += ' --define ORIGEN_SIM_SYNOPSIS'
|
30
|
+
elsif ['icarus'].include?(Origen.environment.name)
|
31
|
+
cmd += ' --define ORIGEN_SIM_ICARUS'
|
32
|
+
end
|
33
|
+
|
34
|
+
clean = false
|
35
|
+
if ARGV.include?('--clean')
|
36
|
+
ARGV.delete_at(ARGV.index('--clean'))
|
37
|
+
clean = true
|
38
|
+
end
|
26
39
|
cmd += ' ' + ARGV.join(' ') unless ARGV.empty?
|
40
|
+
|
41
|
+
|
27
42
|
# Enable wreal pins in the DUT RTL
|
28
43
|
cmd += ' --define ORIGEN_WREAL' if ARGV.include?('--wreal')
|
44
|
+
#cmd += " --define ORIGEN_WREALAVG --sv --force_pin_type vdd:real --force_pin_type ana:real --passthrough \"-sysv_ext +.v -define ORIGEN_WREALAVG +define+ORIGEN_SIM_CADENCE #{Origen.app.root}/top.scs\"" if ARGV.include?('--wrealavg')
|
45
|
+
cmd += " --define ORIGEN_WREALAVG --sv --force_pin_type vdd:real --force_pin_type ana:real --passthrough \"+define+ORIGEN_SIM_SYNOPSIS\"" if ARGV.include?('--wrealavg')
|
29
46
|
output = `#{cmd}`
|
30
47
|
puts output
|
31
48
|
Origen.load_target
|
32
49
|
dir = "simulation/default/#{tester.simulator.config[:vendor]}"
|
50
|
+
|
51
|
+
if clean
|
52
|
+
puts "Cleaning directory: #{dir}"
|
53
|
+
FileUtils.rm_r(dir)
|
54
|
+
end
|
55
|
+
|
33
56
|
FileUtils.mkdir_p(dir)
|
34
57
|
Dir.chdir dir do
|
35
58
|
case tester.simulator.config[:vendor]
|
@@ -42,7 +65,10 @@ when "sim:build_example"
|
|
42
65
|
|
43
66
|
when :cadence
|
44
67
|
output =~ /\n(.*irun .*)\n/
|
45
|
-
|
68
|
+
compile_cmd = $1.gsub('stub', 'dut1')
|
69
|
+
compile_cmd.gsub!('origen.v', 'origen.sv') if cmd.include?('--define ORIGEN_SV')
|
70
|
+
puts compile_cmd.green
|
71
|
+
system compile_cmd
|
46
72
|
|
47
73
|
when :synopsys
|
48
74
|
if tester.simulator.config[:verdi]
|
data/config/shared_commands.rb
CHANGED
@@ -48,7 +48,7 @@ when "sim:unpack"
|
|
48
48
|
when "sim:run"
|
49
49
|
OrigenSim.run_source(ARGV[0])
|
50
50
|
exit 0
|
51
|
-
|
51
|
+
|
52
52
|
#when "sim:list"
|
53
53
|
# require "#{Origen.root!}/lib/origen_sim/commands/pack"
|
54
54
|
# OrigenSim::Commands::Pack.list
|
@@ -60,7 +60,14 @@ else
|
|
60
60
|
sim:co Checkout a simulation snapshot
|
61
61
|
sim:pack Packs the snapshot into a compressed directory
|
62
62
|
sim:unpack Unpacks a snapshot
|
63
|
-
sim:list List the available snapshot packs
|
64
63
|
EOT
|
64
|
+
# sim:list List the available snapshot packs
|
65
|
+
|
66
|
+
if OrigenTesters.respond_to?(:decompile)
|
67
|
+
@plugin_commands << <<-EOT
|
68
|
+
sim:run Simulates the given source without using any of Origen's 'startup' collateral.
|
69
|
+
Requires: a decompiler for the given source and timing information setup beforehand.
|
70
|
+
EOT
|
71
|
+
end
|
65
72
|
|
66
73
|
end
|
data/config/version.rb
CHANGED
data/ext/bridge.c
CHANGED
@@ -112,11 +112,11 @@ static void define_pin(char * name, char * pin_ix, char * drive_wave_ix, char *
|
|
112
112
|
(*pin).drive_data = 0;
|
113
113
|
|
114
114
|
|
115
|
-
char * driver = (char *) malloc(strlen(name) +
|
115
|
+
char * driver = (char *) malloc(strlen(name) + ORIGEN_SIM_TB_NAME_LEN + 7); // testbench name + . + 'pins.' + '\0'
|
116
116
|
strcpy(driver, ORIGEN_SIM_TESTBENCH_CAT("pins."));
|
117
117
|
strcat(driver, name);
|
118
118
|
|
119
|
-
char * data = (char *) malloc(strlen(driver) +
|
119
|
+
char * data = (char *) malloc(strlen(driver) + 6);
|
120
120
|
strcpy(data, driver);
|
121
121
|
strcat(data, ".data");
|
122
122
|
(*pin).data = vpi_handle_by_name(data, NULL);
|
@@ -129,25 +129,25 @@ static void define_pin(char * name, char * pin_ix, char * drive_wave_ix, char *
|
|
129
129
|
(*pin).present = true;
|
130
130
|
}
|
131
131
|
|
132
|
-
char * drive = (char *) malloc(strlen(driver) +
|
132
|
+
char * drive = (char *) malloc(strlen(driver) + 7);
|
133
133
|
strcpy(drive, driver);
|
134
134
|
strcat(drive, ".drive");
|
135
135
|
(*pin).drive = vpi_handle_by_name(drive, NULL);
|
136
136
|
free(drive);
|
137
137
|
|
138
|
-
char * force = (char *) malloc(strlen(driver) +
|
138
|
+
char * force = (char *) malloc(strlen(driver) + 12);
|
139
139
|
strcpy(force, driver);
|
140
140
|
strcat(force, ".force_data");
|
141
141
|
(*pin).force_data = vpi_handle_by_name(force, NULL);
|
142
142
|
free(force);
|
143
143
|
|
144
|
-
char * compare = (char *) malloc(strlen(driver) +
|
144
|
+
char * compare = (char *) malloc(strlen(driver) + 9);
|
145
145
|
strcpy(compare, driver);
|
146
146
|
strcat(compare, ".compare");
|
147
147
|
(*pin).compare = vpi_handle_by_name(compare, NULL);
|
148
148
|
free(compare);
|
149
149
|
|
150
|
-
char * capture = (char *) malloc(strlen(driver) +
|
150
|
+
char * capture = (char *) malloc(strlen(driver) + 9);
|
151
151
|
strcpy(capture, driver);
|
152
152
|
strcat(capture, ".capture");
|
153
153
|
(*pin).capture = vpi_handle_by_name(capture, NULL);
|
@@ -764,7 +764,7 @@ PLI_INT32 bridge_wait_for_msg(p_cb_data data) {
|
|
764
764
|
// Set Pattern Name
|
765
765
|
// a^atd_ramp_25mhz
|
766
766
|
case 'a' :
|
767
|
-
handle = vpi_handle_by_name(ORIGEN_SIM_TESTBENCH_CAT("
|
767
|
+
handle = vpi_handle_by_name(ORIGEN_SIM_TESTBENCH_CAT(ORIGEN_SIM_DEBUG_MODULE_CAT("pattern")), NULL);
|
768
768
|
arg1 = strtok(NULL, "^");
|
769
769
|
|
770
770
|
v.format = vpiStringVal;
|
@@ -800,7 +800,7 @@ PLI_INT32 bridge_wait_for_msg(p_cb_data data) {
|
|
800
800
|
arg1 = strtok(NULL, "^");
|
801
801
|
arg2 = strtok(NULL, "^");
|
802
802
|
|
803
|
-
strcpy(comment, ORIGEN_SIM_TESTBENCH_CAT("
|
803
|
+
strcpy(comment, ORIGEN_SIM_TESTBENCH_CAT(ORIGEN_SIM_DEBUG_MODULE_CAT("comments")));
|
804
804
|
strcat(comment, arg1);
|
805
805
|
|
806
806
|
handle = vpi_handle_by_name(comment, NULL);
|
@@ -1003,7 +1003,7 @@ static void end_simulation() {
|
|
1003
1003
|
s_vpi_value v;
|
1004
1004
|
|
1005
1005
|
// Setting this node will cause the testbench to call $finish
|
1006
|
-
handle = vpi_handle_by_name(ORIGEN_SIM_TESTBENCH_CAT(
|
1006
|
+
handle = vpi_handle_by_name(ORIGEN_SIM_TESTBENCH_CAT(ORIGEN_FINISH_SIG_NAME), NULL);
|
1007
1007
|
v.format = vpiDecStrVal;
|
1008
1008
|
v.value.str = "1";
|
1009
1009
|
vpi_put_value(handle, &v, NULL, vpiNoDelay);
|
@@ -1071,7 +1071,7 @@ PLI_INT32 bridge_on_miscompare(PLI_BYTE8 * user_dat) {
|
|
1071
1071
|
if (match_loop_open) {
|
1072
1072
|
match_loop_error_count++;
|
1073
1073
|
|
1074
|
-
handle = vpi_handle_by_name(ORIGEN_SIM_TESTBENCH_CAT("
|
1074
|
+
handle = vpi_handle_by_name(ORIGEN_SIM_TESTBENCH_CAT(ORIGEN_SIM_DEBUG_MODULE_CAT("match_errors")), NULL);
|
1075
1075
|
val.format = vpiIntVal;
|
1076
1076
|
val.value.integer = match_loop_error_count;
|
1077
1077
|
vpi_put_value(handle, &val, NULL, vpiNoDelay);
|
@@ -1108,7 +1108,7 @@ PLI_INT32 bridge_on_miscompare(PLI_BYTE8 * user_dat) {
|
|
1108
1108
|
|
1109
1109
|
error_count++;
|
1110
1110
|
|
1111
|
-
handle = vpi_handle_by_name(ORIGEN_SIM_TESTBENCH_CAT("
|
1111
|
+
handle = vpi_handle_by_name(ORIGEN_SIM_TESTBENCH_CAT(ORIGEN_SIM_DEBUG_MODULE_CAT("errors")), NULL);
|
1112
1112
|
val.format = vpiIntVal;
|
1113
1113
|
val.value.integer = error_count;
|
1114
1114
|
vpi_put_value(handle, &val, NULL, vpiNoDelay);
|
data/ext/common.h
CHANGED
@@ -14,6 +14,7 @@
|
|
14
14
|
/// Prepends the testbench name to the signal.
|
15
15
|
/// e.g.: TESTBENCH_CAT(pins) => TESTBENCH_NAME.pins => origen.pins
|
16
16
|
#define ORIGEN_SIM_TESTBENCH_CAT(signal) ORIGEN_SIM_TESTBENCH_NAME "." signal
|
17
|
+
#define ORIGEN_SIM_DEBUG_MODULE_CAT(signal) ORIGEN_SIM_DEBUG_MODULE_NAME "." signal
|
17
18
|
|
18
19
|
#ifdef ENABLE_DEBUG
|
19
20
|
/* #define DEBUG(fmt, args...) fprintf(stderr, "DEBUG: %s:%d:%s(): " fmt, \
|
data/ext/defines.h.erb
CHANGED
@@ -1,8 +1,11 @@
|
|
1
1
|
#ifndef DEFINES_H
|
2
2
|
#define DEFINES_H
|
3
3
|
|
4
|
+
#define ORIGEN_FINISH_SIG_NAME "<%= options[:finish_signal] %>"
|
4
5
|
#define ORIGEN_SIM_VERSION "<%= OrigenSim::VERSION %>"
|
5
6
|
#define ORIGEN_SIM_TESTBENCH_NAME "<%= options[:testbench_name] %>"
|
7
|
+
#define ORIGEN_SIM_DEBUG_MODULE_NAME "<%= options[:debug_module_name] %>"
|
8
|
+
#define ORIGEN_SIM_TB_NAME_LEN <%= options[:testbench_name].size %>
|
6
9
|
#define LOG_DEBUG 0
|
7
10
|
#define LOG_INFO 1
|
8
11
|
#define LOG_WARN 2
|
@@ -3,7 +3,22 @@ require 'origen_sim'
|
|
3
3
|
require_relative '../../../config/version'
|
4
4
|
require 'origen_verilog'
|
5
5
|
|
6
|
-
options = {
|
6
|
+
options = {
|
7
|
+
incl_files: [],
|
8
|
+
source_dirs: [],
|
9
|
+
testbench_name: 'origen',
|
10
|
+
defines: [],
|
11
|
+
user_details: {},
|
12
|
+
initial_pin_states: {},
|
13
|
+
forced_pin_types: {},
|
14
|
+
verilog_top_output_name: 'origen',
|
15
|
+
file_type: :v,
|
16
|
+
power_pins: [],
|
17
|
+
ground_pins: [],
|
18
|
+
virtual_pins: [],
|
19
|
+
other_pins: [],
|
20
|
+
passthrough: []
|
21
|
+
}
|
7
22
|
|
8
23
|
# App options are options that the application can supply to extend this command
|
9
24
|
app_options = @application_options || []
|
@@ -22,8 +37,9 @@ Usage: origen sim:build TOP_LEVEL_VERILOG_FILE [options]
|
|
22
37
|
opts.on('-s', '--source_dir PATH', 'Directories to look for include files in (the directory containing the top-level is already considered)') do |path|
|
23
38
|
options[:source_dirs] << path
|
24
39
|
end
|
25
|
-
opts.on('--sv', 'Generate a .sv file instead of a .v file.') { |t| options[:sv] = t }
|
40
|
+
opts.on('--sv', 'Generate a .sv file instead of a .v file.') { |t| options[:sv] = t; options[:file_type] = :sv }
|
26
41
|
opts.on('--wreal', 'Enable real number modeling support on DUT pins defined as real wires (wreal)') { |t| options[:wreal] = t }
|
42
|
+
opts.on('--wrealavg', 'Enable real number modeling support on DUT pins defined as real wires - averaged (wrealavg)') { |t| options[:wrealavg] = t }
|
27
43
|
opts.on('--verilog_top_output_name NAME', 'Renames the output filename from origen.v to NAME.v') do |name|
|
28
44
|
options[:verilog_top_output_name] = name
|
29
45
|
end
|
@@ -39,7 +55,25 @@ Usage: origen sim:build TOP_LEVEL_VERILOG_FILE [options]
|
|
39
55
|
end
|
40
56
|
(options[:initial_pin_states])[name.to_sym] = OrigenSim::INIT_PIN_STATE_MAPPING[state]
|
41
57
|
end
|
42
|
-
opts.on('--
|
58
|
+
opts.on('--force_pin_type PIN_AND_TYPE', 'Overwrite the pin driver discerned from DUT module') do |pin_and_type|
|
59
|
+
name, type = pin_and_type.split(':')
|
60
|
+
(options[:forced_pin_types])[name] = OrigenSim::FORCE_PIN_TYPES_MAPPING[type]
|
61
|
+
end
|
62
|
+
opts.on('--power_pins PINS_AND_REGEXES', 'Using pin names or regexes, indicate which pins are power pins, seperated by tildas') do |str_or_regex|
|
63
|
+
options[:power_pins] << str_or_regex
|
64
|
+
end
|
65
|
+
opts.on('--ground_pins PINS_AND_REGEXES', 'Using pin names or regexes, indicate which pins are ground pins, seperated by tildas') do |str_or_regex|
|
66
|
+
options[:ground_pins] << str_or_regex
|
67
|
+
end
|
68
|
+
opts.on('--virtual_pins PINS_AND_REGEXES', 'Using pin names or regexes, indicate which pins are virtual pins, seperated by tildas') do |str_or_regex|
|
69
|
+
options[:virtual_pins] << str_or_regex
|
70
|
+
end
|
71
|
+
opts.on('--other_pins PINS_AND_REGEXES', 'Using pin names or regexes, indicate which pins are \'other\' pins, seperated by tildas') do |str_or_regex|
|
72
|
+
options[:other_pins] << str_or_regex
|
73
|
+
end
|
74
|
+
opts.on('--include FILE', 'Specify files to include in the top verilog file.') { |f| options[:incl_files] << f }
|
75
|
+
opts.on('--vendor VENDOR', 'Specify the target vendor (Cadence, Synopsis, Icarus') { |v| options[:vendor] = v.downcase.to_sym }
|
76
|
+
opts.on('--passthrough SWITCHES', 'Raw switches that will be ignored by OrigenSim, but appear in the final build command') { |s| options[:passthrough] << s }
|
43
77
|
|
44
78
|
# Specifying snapshot details
|
45
79
|
opts.on('--device_name NAME', '(Snapshot Detail) Specify a device name') { |n| options[:device_name] = n }
|
@@ -48,6 +82,9 @@ Usage: origen sim:build TOP_LEVEL_VERILOG_FILE [options]
|
|
48
82
|
opts.on('--revision_note REV_NOTE', '(Snapshot Detail) Specify a brief note on this revision of the snapshot') { |n| options[:revision_note] = n }
|
49
83
|
opts.on('--author AUTHOR', '(Snapshot Detail) Specify the author of the snapshot (default is just Origen.current_user)') { |a| options[:author] = a }
|
50
84
|
|
85
|
+
opts.on('--finish_signal FINISH_SIGNAL', 'Specify the finish signal') { |f| options[:finish_signal] = f }
|
86
|
+
opts.on('--debug_module_name MOD_NAME', 'Specify the debug module name') { |d| options[:debug_module_name] = d }
|
87
|
+
|
51
88
|
# User-defined snapshot details
|
52
89
|
opts.on('--USER_DETAIL NAME_AND_VALUE', 'Specify custom user-defined details to build into the snapshot details. Format as NAME:VALUE, e.g.: \'--USER_DETAIL BUILD_TYPE:RTL\'') do |name_and_value|
|
53
90
|
name, value = name_and_value.split(':')
|
@@ -68,8 +105,41 @@ Usage: origen sim:build TOP_LEVEL_VERILOG_FILE [options]
|
|
68
105
|
opts.on('-h', '--help', 'Show this message') { puts opts; exit 0 }
|
69
106
|
end
|
70
107
|
|
108
|
+
build_cmd = 'origen sim:build ' + ARGV.map do |arg|
|
109
|
+
# Command-line-ify some of the argument values.
|
110
|
+
if arg.include?(' ') || (arg[0] == '/' && arg[1] == '/' && arg.size > 1)
|
111
|
+
# if the argument is a string, wrap it in quotes.
|
112
|
+
# Likewise, if the argument looks like a regex, wrap it in quotes as well.
|
113
|
+
arg = "\"#{arg}\""
|
114
|
+
end
|
115
|
+
|
116
|
+
# If the argument includes any !s, escape them
|
117
|
+
arg = arg.gsub('!', '\!')
|
118
|
+
|
119
|
+
arg
|
120
|
+
end.join(' ')
|
71
121
|
opt_parser.parse! ARGV
|
72
122
|
|
123
|
+
options.select { |k, v| [:power_pins, :ground_pins, :virtual_pins, :other_pins].include?(k) }.each do |k, pins_or_regexes|
|
124
|
+
options[k] = pins_or_regexes.map { |input| input.split('~') }.flatten.map do |p|
|
125
|
+
if p.start_with?('/') && p.end_with?('/')
|
126
|
+
Regexp.new(p[1..-2])
|
127
|
+
else
|
128
|
+
p
|
129
|
+
end
|
130
|
+
end
|
131
|
+
end
|
132
|
+
|
133
|
+
options[:forced_pin_types] = options[:forced_pin_types].map do |pin_or_regex, type|
|
134
|
+
if pin_or_regex.start_with?('/') && pin_or_regex.end_with?('/')
|
135
|
+
# run this as a regex, not as a single pin name
|
136
|
+
# Cut out the leading / and trailing / characters though
|
137
|
+
[Regexp.new(pin_or_regex.to_s[1..-2]), type]
|
138
|
+
else
|
139
|
+
[pin_or_regex, type]
|
140
|
+
end
|
141
|
+
end.to_h
|
142
|
+
|
73
143
|
def _exit_fail_
|
74
144
|
if $_testing_build_return_dut_
|
75
145
|
return nil
|
@@ -115,7 +185,7 @@ end
|
|
115
185
|
|
116
186
|
rtl_top_module = mod.name
|
117
187
|
|
118
|
-
mod.to_top_level # Creates dut
|
188
|
+
mod.to_top_level(options) # Creates dut
|
119
189
|
|
120
190
|
# Update the pins with any settings from the command line
|
121
191
|
options[:initial_pin_states].each do |pin, state|
|
@@ -138,7 +208,7 @@ else
|
|
138
208
|
quiet: true,
|
139
209
|
preserve_target: true,
|
140
210
|
options: {
|
141
|
-
vendor: :
|
211
|
+
vendor: options[:vendor],
|
142
212
|
top: dut.name,
|
143
213
|
testbench_name: options[:testbench_name],
|
144
214
|
incl: options[:incl_files],
|
@@ -147,7 +217,13 @@ else
|
|
147
217
|
revision_note: options[:revision_note],
|
148
218
|
parent_tb_version: options[:testbench_version],
|
149
219
|
user_details: options[:user_details],
|
150
|
-
author: options[:author]
|
220
|
+
author: options[:author],
|
221
|
+
build_cmd: build_cmd,
|
222
|
+
file_type: options[:file_type],
|
223
|
+
testbench: options[:testbench_name] || 'origen',
|
224
|
+
top_level_name: options[:top_level_name] || 'dut',
|
225
|
+
finish_signal: options[:finish_signal] || 'finish',
|
226
|
+
debug_module_name: options[:debug_module_name] || 'debug'
|
151
227
|
}
|
152
228
|
|
153
229
|
Origen.app.runner.launch action: :compile,
|
@@ -183,6 +259,16 @@ else
|
|
183
259
|
)
|
184
260
|
end
|
185
261
|
|
262
|
+
if options[:wrealavg]
|
263
|
+
SYNOPSYS_SWITCHES += %w(
|
264
|
+
+define+ORIGEN_WREALAVG
|
265
|
+
-realport
|
266
|
+
-sverilog
|
267
|
+
-lca
|
268
|
+
-xlrm\ coerce_nettype
|
269
|
+
)
|
270
|
+
end
|
271
|
+
|
186
272
|
SYNOPSYS_DVE_SWITCHES = SYNOPSYS_SWITCHES + %w(
|
187
273
|
+define+ORIGEN_VPD
|
188
274
|
)
|
@@ -212,96 +298,108 @@ else
|
|
212
298
|
)
|
213
299
|
end
|
214
300
|
|
215
|
-
|
216
|
-
|
217
|
-
|
218
|
-
|
219
|
-
puts '-----------------------------------------------------------'
|
220
|
-
puts
|
221
|
-
puts 'Compile the VPI extension using the following command:'
|
222
|
-
puts
|
223
|
-
puts " cd #{output_directory} && #{ENV['ORIGEN_SIM_IVERILOG_VPI'] || 'iverilog-vpi'} *.c --name=origen && cd #{Pathname.pwd}"
|
224
|
-
puts
|
225
|
-
puts 'Add the following to your build script (AND REMOVE ANY OTHER TESTBENCH!):'
|
226
|
-
puts
|
227
|
-
puts " #{output_directory}/#{output_name} \\"
|
228
|
-
puts ' -o origen.vvp \\'
|
229
|
-
puts ' -DORIGEN_VCD'
|
230
|
-
puts
|
231
|
-
puts 'Here is an example which may work for the file you just parsed (add additional source dirs with more -I options at the end if required):'
|
232
|
-
puts
|
233
|
-
puts " #{ENV['ORIGEN_SIM_IVERILOG'] || 'iverilog'} #{rtl_top} #{output_directory}/#{output_name} -o origen.vvp -DORIGEN_VCD -I #{Pathname.new(rtl_top).dirname}"
|
234
|
-
puts
|
235
|
-
puts 'Copy the following files (produced by iverilog) to simulation/<target>/icarus/. within your Origen application:'
|
236
|
-
puts
|
237
|
-
puts " #{output_directory}/origen.vpi"
|
238
|
-
puts ' origen.vvp'
|
239
|
-
puts
|
240
|
-
puts '-----------------------------------------------------------'
|
241
|
-
puts 'Synopsys VCS w/ DVE Waveviewer'
|
242
|
-
puts '-----------------------------------------------------------'
|
243
|
-
puts
|
244
|
-
puts 'Add the following to your build script (AND REMOVE ANY OTHER TESTBENCH!):'
|
245
|
-
puts
|
246
|
-
SYNOPSYS_DVE_SWITCHES.each do |switch|
|
247
|
-
puts " #{switch} \\"
|
301
|
+
if options[:wrealavg]
|
302
|
+
CADENCE_SWITCHES += %w(
|
303
|
+
+define+ORIGEN_WREALAVG
|
304
|
+
)
|
248
305
|
end
|
306
|
+
|
249
307
|
puts
|
250
|
-
|
251
|
-
|
252
|
-
|
253
|
-
|
254
|
-
|
255
|
-
|
256
|
-
|
257
|
-
|
258
|
-
|
259
|
-
|
260
|
-
|
261
|
-
|
262
|
-
|
263
|
-
|
264
|
-
|
265
|
-
|
266
|
-
puts
|
308
|
+
if options[:vendor].nil? || options[:vendor] == :icarus
|
309
|
+
puts
|
310
|
+
puts '-----------------------------------------------------------'
|
311
|
+
puts 'Icarus Verilog'
|
312
|
+
puts '-----------------------------------------------------------'
|
313
|
+
puts
|
314
|
+
puts 'Compile the VPI extension using the following command:'
|
315
|
+
puts
|
316
|
+
puts " cd #{output_directory} && #{ENV['ORIGEN_SIM_IVERILOG_VPI'] || 'iverilog-vpi'} *.c --name=origen && cd #{Pathname.pwd}"
|
317
|
+
puts
|
318
|
+
puts 'Add the following to your build script (AND REMOVE ANY OTHER TESTBENCH!):'
|
319
|
+
puts
|
320
|
+
puts " #{output_directory}/#{output_name} \\"
|
321
|
+
puts ' -o origen.vvp \\'
|
322
|
+
puts ' -DORIGEN_VCD'
|
323
|
+
puts
|
324
|
+
puts 'Here is an example which may work for the file you just parsed (add additional source dirs with more -I options at the end if required):'
|
325
|
+
puts
|
326
|
+
puts " #{ENV['ORIGEN_SIM_IVERILOG'] || 'iverilog'} #{rtl_top} #{output_directory}/#{output_name} -o origen.vvp -DORIGEN_VCD -I #{Pathname.new(rtl_top).dirname}"
|
327
|
+
puts
|
328
|
+
puts 'Copy the following files (produced by iverilog) to simulation/<target>/icarus/. within your Origen application:'
|
329
|
+
puts
|
330
|
+
puts " #{output_directory}/origen.vpi"
|
331
|
+
puts ' origen.vvp'
|
267
332
|
end
|
268
|
-
|
269
|
-
|
270
|
-
|
271
|
-
|
272
|
-
|
273
|
-
|
274
|
-
|
275
|
-
|
276
|
-
|
277
|
-
|
278
|
-
|
279
|
-
|
280
|
-
|
281
|
-
|
282
|
-
|
283
|
-
|
284
|
-
|
285
|
-
puts
|
333
|
+
if options[:vendor].nil? || options[:vendor] == :synopsis
|
334
|
+
puts
|
335
|
+
puts '-----------------------------------------------------------'
|
336
|
+
puts 'Synopsys VCS w/ DVE Waveviewer'
|
337
|
+
puts '-----------------------------------------------------------'
|
338
|
+
puts
|
339
|
+
puts 'Add the following to your build script (AND REMOVE ANY OTHER TESTBENCH!):'
|
340
|
+
puts
|
341
|
+
SYNOPSYS_DVE_SWITCHES.each do |switch|
|
342
|
+
puts " #{switch} \\"
|
343
|
+
end
|
344
|
+
puts
|
345
|
+
puts 'Here is an example which may work for the file you just parsed (add additional +incdir+ options at the end if required):'
|
346
|
+
puts
|
347
|
+
puts " #{ENV['ORIGEN_SIM_VCS'] || 'vcs'} #{rtl_top} +incdir+#{Pathname.new(rtl_top).dirname} " + SYNOPSYS_DVE_SWITCHES.join(' ') + (options[:passthrough] ? " #{options[:passthrough].join(' ')}" : '')
|
348
|
+
puts
|
349
|
+
puts 'Copy the following files (produced by vcs) to simulation/<target>/synopsys/. within your Origen application:'
|
350
|
+
puts
|
351
|
+
puts ' simv'
|
352
|
+
puts ' simv.daidir'
|
353
|
+
puts
|
354
|
+
puts '-----------------------------------------------------------'
|
355
|
+
puts 'Synopsys VCS w/ Verdi Waveviewer'
|
356
|
+
puts '-----------------------------------------------------------'
|
357
|
+
puts
|
358
|
+
puts 'Add the following to your build script (AND REMOVE ANY OTHER TESTBENCH!):'
|
359
|
+
puts
|
360
|
+
SYNOPSYS_VERDI_SWITCHES.each do |switch|
|
361
|
+
puts " #{switch} \\"
|
362
|
+
end
|
363
|
+
puts
|
364
|
+
puts 'Here is an example which may work for the file you just parsed (add additional +incdir+ options at the end if required):'
|
365
|
+
puts
|
366
|
+
puts " #{ENV['ORIGEN_SIM_VCS'] || 'vcs'} #{rtl_top} +incdir+#{Pathname.new(rtl_top).dirname} " + SYNOPSYS_VERDI_SWITCHES.join(' ') + (options[:passthrough] ? " #{options[:passthrough].join(' ')}" : '')
|
367
|
+
puts
|
368
|
+
puts 'Copy the following files (produced by vcs) to simulation/<target>/synopsys/. within your Origen application:'
|
369
|
+
puts
|
370
|
+
puts ' simv'
|
371
|
+
puts ' simv.daidir'
|
372
|
+
puts
|
373
|
+
puts '-----------------------------------------------------------'
|
374
|
+
puts 'Cadence Incisive (irun)'
|
375
|
+
puts '-----------------------------------------------------------'
|
376
|
+
puts
|
377
|
+
puts 'Add the following to your build script (AND REMOVE ANY OTHER TESTBENCH!):'
|
378
|
+
end
|
379
|
+
if options[:vendor].nil? || options[:vendor] == :cadence
|
380
|
+
puts
|
381
|
+
CADENCE_SWITCHES.each do |switch|
|
382
|
+
puts " #{switch} \\"
|
383
|
+
end
|
384
|
+
puts
|
385
|
+
puts 'Here is an example which may work for the file you just parsed (add additional -incdir options at the end if required):'
|
386
|
+
puts
|
387
|
+
puts " #{ENV['ORIGEN_SIM_IRUN'] || 'irun'} #{rtl_top} -incdir #{Pathname.new(rtl_top).dirname} " + CADENCE_SWITCHES.join(' ') + (options[:passthrough] ? " #{options[:passthrough].join(' ')}" : '')
|
388
|
+
puts
|
389
|
+
puts 'Copy the following directory (produced by irun) to simulation/<target>/cadence/. within your Origen application:'
|
390
|
+
puts
|
391
|
+
puts ' INCA_libs'
|
392
|
+
puts
|
393
|
+
puts '-----------------------------------------------------------'
|
394
|
+
puts
|
395
|
+
puts 'Testbench and VPI extension created!'
|
396
|
+
puts
|
397
|
+
puts 'This file can be imported into an Origen top-level DUT model to define the pins:'
|
398
|
+
puts
|
399
|
+
puts " #{output_directory}/#{rtl_top_module}.rb"
|
400
|
+
puts
|
401
|
+
puts 'See above for what to do now to create an Origen-enabled simulation object for your particular simulator.'
|
286
402
|
end
|
287
|
-
puts
|
288
|
-
puts 'Here is an example which may work for the file you just parsed (add additional -incdir options at the end if required):'
|
289
|
-
puts
|
290
|
-
puts " #{ENV['ORIGEN_SIM_IRUN'] || 'irun'} #{rtl_top} -incdir #{Pathname.new(rtl_top).dirname} " + CADENCE_SWITCHES.join(' ')
|
291
|
-
puts
|
292
|
-
puts 'Copy the following directory (produced by irun) to simulation/<target>/cadence/. within your Origen application:'
|
293
|
-
puts
|
294
|
-
puts ' INCA_libs'
|
295
|
-
puts
|
296
|
-
puts '-----------------------------------------------------------'
|
297
|
-
puts
|
298
|
-
puts 'Testbench and VPI extension created!'
|
299
|
-
puts
|
300
|
-
puts 'This file can be imported into an Origen top-level DUT model to define the pins:'
|
301
|
-
puts
|
302
|
-
puts " #{output_directory}/#{rtl_top_module}.rb"
|
303
|
-
puts
|
304
|
-
puts 'See above for what to do now to create an Origen-enabled simulation object for your particular simulator.'
|
305
403
|
puts
|
306
404
|
|
307
405
|
end
|
@@ -57,7 +57,7 @@ module Origen
|
|
57
57
|
|
58
58
|
alias_method :_orig_drive, :drive
|
59
59
|
def drive(*args)
|
60
|
-
if _analog_pin_? && simulation_running? && tester.simulator.
|
60
|
+
if _analog_pin_? && simulation_running? && tester.simulator.real?
|
61
61
|
tester.poke("#{driver_net}.drive_en", 1)
|
62
62
|
tester.poke("#{driver_net}.drive", args.first + 0.0)
|
63
63
|
else
|
@@ -68,11 +68,11 @@ module Origen
|
|
68
68
|
|
69
69
|
alias_method :_orig_assert, :assert
|
70
70
|
def assert(*args)
|
71
|
-
if _analog_pin_? && simulation_running? && tester.simulator.
|
71
|
+
if _analog_pin_? && simulation_running? && tester.simulator.real?
|
72
72
|
drive_enabled = tester.peek("#{driver_net}.drive_en").to_i
|
73
73
|
if drive_enabled == 1
|
74
|
-
tester.poke("#{driver_net}.drive_en", 0)
|
75
|
-
tester.cycle
|
74
|
+
# tester.poke("#{driver_net}.drive_en", 0)
|
75
|
+
# tester.cycle
|
76
76
|
end
|
77
77
|
measured = tester.peek("#{driver_net}.pin", true)
|
78
78
|
# Could implement checking/limits here in future
|
@@ -6,18 +6,27 @@ module Origen
|
|
6
6
|
# Optionally pass in a type: option set to either :analog or :digital to
|
7
7
|
# have only the pins with that type returned
|
8
8
|
def rtl_pins(options = {})
|
9
|
+
_add_rtl_pin_ = lambda do |name, pin, opts, p|
|
10
|
+
options = {}
|
11
|
+
unless pin.rtl_name.to_s.downcase == 'nc' ||
|
12
|
+
(opts[:type] && pin.type && opts[:type] != pin.type) ||
|
13
|
+
(pin.meta[:origen_sim_init_pin_state] && pin.meta[:origen_sim_init_pin_state] == -2)
|
14
|
+
if pin.primary_group
|
15
|
+
options[:group] = true
|
16
|
+
end
|
17
|
+
p << [name, pin, options]
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
21
|
+
pin_roles = [:pins, :power_pins, :ground_pins, :virtual_pins, :other_pins]
|
9
22
|
@rtl_pins ||= {}
|
10
23
|
@rtl_pins[options[:type]] ||= begin
|
11
24
|
opts = options.dup
|
12
25
|
p = []
|
13
|
-
pins.each do |name, pin|
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
if pin.primary_group
|
18
|
-
options[:group] = true
|
19
|
-
end
|
20
|
-
p << [name, pin, options]
|
26
|
+
# pins.each do |name, pin|
|
27
|
+
pin_roles.each do |role|
|
28
|
+
dut.send(role).each do |name, pin|
|
29
|
+
_add_rtl_pin_.call(name, pin, opts, p)
|
21
30
|
end
|
22
31
|
end
|
23
32
|
p
|
@@ -26,7 +26,7 @@ module OrigenTesters
|
|
26
26
|
if @sim_capture || @sim_delay
|
27
27
|
fail 'Nesting of sim_capture and/or sim_delay blocks is not yet supported!'
|
28
28
|
end
|
29
|
-
Origen::OrgFile.open(id, path: OrigenSim.capture_dir) do |org_file|
|
29
|
+
Origen::OrgFile.open(id, path: (options[:path] || OrigenSim.capture_dir)) do |org_file|
|
30
30
|
@org_file = org_file
|
31
31
|
if update_capture?
|
32
32
|
@sim_delay = true
|
data/lib/origen_sim/simulator.rb
CHANGED
@@ -21,7 +21,7 @@ module OrigenSim
|
|
21
21
|
|
22
22
|
# These config attributes are accepted by OrigenSim, but cannot be
|
23
23
|
# 'Marshal-ed'.
|
24
|
-
NON_DATA_CONFIG_ATTRIBUTES = [:post_process_run_cmd]
|
24
|
+
NON_DATA_CONFIG_ATTRIBUTES = [:post_process_run_cmd, :post_process_view_wave_cmd, :post_process_probe_cmd]
|
25
25
|
|
26
26
|
TIMESCALES = { -15 => '1fs',
|
27
27
|
-14 => '10fs',
|
@@ -86,6 +86,26 @@ module OrigenSim
|
|
86
86
|
config[:post_process_run_cmd]
|
87
87
|
end
|
88
88
|
|
89
|
+
def post_process_view_wave_cmd
|
90
|
+
config[:post_process_view_wave_cmd]
|
91
|
+
end
|
92
|
+
|
93
|
+
def post_process_probe_cmd
|
94
|
+
config[:post_process_probe_cmd]
|
95
|
+
end
|
96
|
+
|
97
|
+
def post_process_probe_cmd?
|
98
|
+
!post_process_probe_cmd.nil?
|
99
|
+
end
|
100
|
+
|
101
|
+
def force_config_update?
|
102
|
+
!!config[:force_config_update]
|
103
|
+
end
|
104
|
+
|
105
|
+
def debug_path
|
106
|
+
config[:debug_module_path] || 'debug'
|
107
|
+
end
|
108
|
+
|
89
109
|
def fetch_simulation_objects(options = {})
|
90
110
|
sid = options[:id] || id
|
91
111
|
ldir = "#{Origen.root}/simulation/#{sid}"
|
@@ -166,8 +186,8 @@ module OrigenSim
|
|
166
186
|
clear_artifacts
|
167
187
|
|
168
188
|
# Add any artifacts in the given artifact path
|
169
|
-
if Dir.exist?(default_artifact_dir)
|
170
|
-
default_artifact_dir.children.each { |a| artifact(a.basename.to_s, target: a) }
|
189
|
+
if Dir.exist?(self.class.default_artifact_dir)
|
190
|
+
self.class.default_artifact_dir.children.each { |a| artifact(a.basename.to_s, target: a) }
|
171
191
|
end
|
172
192
|
|
173
193
|
# Add any artifacts from the target-specific path (simulation/<target>/artifacts). Files of the same name
|
@@ -197,7 +217,7 @@ module OrigenSim
|
|
197
217
|
self
|
198
218
|
end
|
199
219
|
|
200
|
-
def default_artifact_dir
|
220
|
+
def self.default_artifact_dir
|
201
221
|
# Removed this from a constant at the top of the file since it gave boot errors when the file was
|
202
222
|
# being required while Origen.app was still loading
|
203
223
|
Pathname("#{Origen.app.root}/simulation/application/artifacts")
|
@@ -212,7 +232,7 @@ module OrigenSim
|
|
212
232
|
end
|
213
233
|
|
214
234
|
def target_artifact_dir
|
215
|
-
Pathname(@configuration[:target_artifact_dir] || "#{Origen.app.root}/simulation
|
235
|
+
Pathname(@configuration[:target_artifact_dir] || "#{Origen.app.root}/simulation/").join("#{id}/artifacts")
|
216
236
|
end
|
217
237
|
|
218
238
|
def artifact_run_dir
|
@@ -253,9 +273,11 @@ module OrigenSim
|
|
253
273
|
# be checked into your Origen app's repository
|
254
274
|
def compiled_dir
|
255
275
|
@compiled_dir ||= begin
|
256
|
-
|
257
|
-
|
258
|
-
|
276
|
+
config[:compiled_dir] || begin
|
277
|
+
d = "#{Origen.root}/simulation/#{id}/#{config[:vendor]}"
|
278
|
+
FileUtils.mkdir_p(d)
|
279
|
+
d
|
280
|
+
end
|
259
281
|
end
|
260
282
|
end
|
261
283
|
|
@@ -323,35 +345,45 @@ module OrigenSim
|
|
323
345
|
when :cadence
|
324
346
|
input_file = "#{tmp_dir}/#{wave_file_basename}.tcl"
|
325
347
|
if !File.exist?(input_file) || config_changed?
|
348
|
+
probe_cmd = "probe -create -shm #{testbench_top} -depth all -database waves"
|
349
|
+
if post_process_probe_cmd?
|
350
|
+
probe_cmd = post_process_probe_cmd.call(probe_cmd, self, fast_probe: false)
|
351
|
+
end
|
352
|
+
|
326
353
|
Origen.app.runner.launch action: :compile,
|
327
354
|
files: "#{Origen.root!}/templates/probe.tcl.erb",
|
328
355
|
output: tmp_dir,
|
329
356
|
check_for_changes: false,
|
330
357
|
quiet: true,
|
331
|
-
options: { dir:
|
332
|
-
wave_file:
|
333
|
-
force:
|
334
|
-
setup:
|
335
|
-
|
336
|
-
|
358
|
+
options: { dir: wave_dir,
|
359
|
+
wave_file: wave_file_basename,
|
360
|
+
force: config[:force],
|
361
|
+
setup: config[:setup],
|
362
|
+
tcl_inputs: config[:tcl_inputs],
|
363
|
+
probe_cmd: probe_cmd
|
337
364
|
},
|
338
365
|
output_file_name: "#{wave_file_basename}.tcl",
|
339
366
|
preserve_target: true
|
340
367
|
end
|
368
|
+
|
341
369
|
input_file_fast = "#{tmp_dir}/#{wave_file_basename}_fast.tcl"
|
342
370
|
if !File.exist?(input_file_fast) || config_changed?
|
343
371
|
fast_probe_depth = config[:fast_probe_depth] || 1
|
372
|
+
probe_cmd = "probe -create -shm #{testbench_top} -depth #{fast_probe_depth} -database waves"
|
373
|
+
if post_process_probe_cmd?
|
374
|
+
probe_cmd = post_process_probe_cmd.call(probe_cmd, self, fast_probe: true)
|
375
|
+
end
|
376
|
+
|
344
377
|
Origen.app.runner.launch action: :compile,
|
345
378
|
files: "#{Origen.root!}/templates/probe.tcl.erb",
|
346
379
|
output: tmp_dir,
|
347
380
|
check_for_changes: false,
|
348
381
|
quiet: true,
|
349
|
-
options: { dir:
|
350
|
-
wave_file:
|
351
|
-
force:
|
352
|
-
setup:
|
353
|
-
|
354
|
-
testbench_top: config[:testbench_top] || 'origen'
|
382
|
+
options: { dir: wave_dir,
|
383
|
+
wave_file: wave_file_basename,
|
384
|
+
force: config[:force],
|
385
|
+
setup: config[:setup],
|
386
|
+
probe_cmd: probe_cmd
|
355
387
|
},
|
356
388
|
output_file_name: "#{wave_file_basename}_fast.tcl",
|
357
389
|
preserve_target: true
|
@@ -365,10 +397,11 @@ module OrigenSim
|
|
365
397
|
cmd += " -nclibdirpath #{compiled_dir}"
|
366
398
|
|
367
399
|
when :synopsys
|
400
|
+
syn_comp_n = config[:synopsys_compiled_name] || 'simv'
|
368
401
|
if configuration[:verdi]
|
369
|
-
cmd = "#{compiled_dir}
|
402
|
+
cmd = "#{compiled_dir}/#{syn_comp_n} +socket+#{socket_id} +FSDB_ON +fsdbfile+#{Origen.root}/waves/#{id}/#{wave_file_basename}.fsdb +memcbk +vcsd"
|
370
403
|
else
|
371
|
-
cmd = "#{compiled_dir}
|
404
|
+
cmd = "#{compiled_dir}/#{syn_comp_n} +socket+#{socket_id} -vpd_file #{wave_file_basename}.vpd"
|
372
405
|
end
|
373
406
|
|
374
407
|
when :generic
|
@@ -490,6 +523,10 @@ module OrigenSim
|
|
490
523
|
Origen.log.warn "OrigenSim does not know the command to view waveforms for vendor :#{config[:vendor]}!"
|
491
524
|
|
492
525
|
end
|
526
|
+
|
527
|
+
cmd = post_process_view_wave_cmd.call(cmd, self) if post_process_view_wave_cmd
|
528
|
+
fail "OrigenSim: :post_process_view_wave_cmd returned object of class #{cmd.class}. Must return a String." unless cmd.is_a?(String)
|
529
|
+
|
493
530
|
cmd
|
494
531
|
end
|
495
532
|
|
@@ -906,13 +943,13 @@ module OrigenSim
|
|
906
943
|
|
907
944
|
def error(message)
|
908
945
|
simulation.logged_errors = true
|
909
|
-
poke "#{testbench_top}.
|
946
|
+
poke "#{testbench_top}.#{debug_path}.errors", error_count + 1
|
910
947
|
log message, :error
|
911
948
|
end
|
912
949
|
|
913
950
|
# Returns the current simulation error count
|
914
951
|
def error_count
|
915
|
-
peek("#{testbench_top}.
|
952
|
+
peek("#{testbench_top}.#{debug_path}.errors").to_i
|
916
953
|
end
|
917
954
|
|
918
955
|
# Returns the current value of the given net, or nil if the given path does not
|
@@ -1091,7 +1128,7 @@ module OrigenSim
|
|
1091
1128
|
|
1092
1129
|
# Returns true if the config has been changed since the last time we called save_config_signature
|
1093
1130
|
def config_changed?
|
1094
|
-
Origen.app.session.origen_sim["#{id}_config"] != config.except(*NON_DATA_CONFIG_ATTRIBUTES)
|
1131
|
+
config[:force_config_update] || Origen.app.session.origen_sim["#{id}_config"] != config.except(*NON_DATA_CONFIG_ATTRIBUTES)
|
1095
1132
|
end
|
1096
1133
|
|
1097
1134
|
# Locally saves a signature for the current config, this will cause config_changed? to return false
|
@@ -1154,7 +1191,7 @@ module OrigenSim
|
|
1154
1191
|
|
1155
1192
|
def match_errors
|
1156
1193
|
if dut_version > '0.15.0'
|
1157
|
-
peek("#{testbench_top}.
|
1194
|
+
peek("#{testbench_top}.#{debug_path}.match_errors").to_i
|
1158
1195
|
else
|
1159
1196
|
peek("#{testbench_top}.pins.match_errors").to_i
|
1160
1197
|
end
|
@@ -1165,7 +1202,7 @@ module OrigenSim
|
|
1165
1202
|
unless val.nil?
|
1166
1203
|
# All zeros seems to be what an empty string is returned from the VPI,
|
1167
1204
|
# Otherwise, break the string up into 8-bit chunks and decode the ASCII>
|
1168
|
-
val = (val.to_s == 'b00000000' ? '' : val.to_s[1..-1].scan(/.{1,8}/).collect { |char| char.to_i(2).chr }.join)
|
1205
|
+
val = (val.to_s == 'b00000000' ? '' : val.to_s[1..-1].scan(/.{1,8}/).select { |char| char != '00000000' }.collect { |char| char.to_i(2).chr }.join)
|
1169
1206
|
end
|
1170
1207
|
val
|
1171
1208
|
end
|
@@ -1179,7 +1216,7 @@ module OrigenSim
|
|
1179
1216
|
end
|
1180
1217
|
|
1181
1218
|
def marker=(val)
|
1182
|
-
poke("#{testbench_top}.
|
1219
|
+
poke("#{testbench_top}.#{debug_path}.marker", val)
|
1183
1220
|
end
|
1184
1221
|
|
1185
1222
|
def start_read_reg_transaction
|
@@ -1216,14 +1253,73 @@ module OrigenSim
|
|
1216
1253
|
end
|
1217
1254
|
end
|
1218
1255
|
|
1256
|
+
# Returns true if the snapshot has been compiled with some kind of REAL support.
|
1257
|
+
# Not picky about what type of real support though.
|
1258
|
+
def real?
|
1259
|
+
@real ||= begin
|
1260
|
+
if dut_version > '0.19.0' && dut_version < '0.20.3'
|
1261
|
+
# These versions of OrigenSim only support WREAL
|
1262
|
+
if wreal?
|
1263
|
+
@real_type = :wreal
|
1264
|
+
true
|
1265
|
+
else
|
1266
|
+
false
|
1267
|
+
end
|
1268
|
+
elsif dut_version >= '0.20.3'
|
1269
|
+
# These versions support multiple REAL types.
|
1270
|
+
if peek_str("#{testbench_top}.#{debug_path}.real_type").nil?
|
1271
|
+
@real_type = false
|
1272
|
+
else
|
1273
|
+
@real_type = peek_str("#{testbench_top}.#{debug_path}.real_type").to_sym
|
1274
|
+
peek("#{testbench_top}.#{debug_path}.real_enabled").to_i == 1
|
1275
|
+
end
|
1276
|
+
else
|
1277
|
+
# Older version don't support REAL at all
|
1278
|
+
@real_type = false
|
1279
|
+
false
|
1280
|
+
end
|
1281
|
+
end
|
1282
|
+
end
|
1283
|
+
alias_method :real_enabled?, :real?
|
1284
|
+
|
1285
|
+
# Returns the type of REAL support or <code>false</code> if no REAL support is enabled.
|
1286
|
+
# @note Calling {#real?} will set the value of <code>real_type</code> appropriately
|
1287
|
+
def real_type
|
1288
|
+
@real_type || begin
|
1289
|
+
real?
|
1290
|
+
@real_type
|
1291
|
+
end
|
1292
|
+
end
|
1293
|
+
|
1219
1294
|
# Returns true if the snapshot has been compiled with WREAL support
|
1220
1295
|
def wreal?
|
1221
|
-
|
1222
|
-
|
1223
|
-
|
1296
|
+
if dut_version > '0.19.0' && dut_version < '0.20.3'
|
1297
|
+
@wreal ||= peek("#{testbench_top}.#{debug_path}.wreal_enabled").to_i == 1
|
1298
|
+
elsif dut_version >= '0.20.3'
|
1299
|
+
puts 'wreal?'.cyan
|
1300
|
+
puts @real_type.class
|
1301
|
+
puts @real_type[0]
|
1302
|
+
puts @real_type.to_s.size
|
1303
|
+
puts 'wreal'.size
|
1304
|
+
puts @real_type.to_s == 'wreal'
|
1305
|
+
(@real_type || begin
|
1306
|
+
real?
|
1307
|
+
@real_type
|
1308
|
+
end) == :wreal
|
1309
|
+
else
|
1310
|
+
false
|
1311
|
+
end
|
1224
1312
|
end
|
1225
1313
|
alias_method :wreal_enabled?, :wreal?
|
1226
1314
|
|
1315
|
+
def wrealavg?
|
1316
|
+
(@real_type || begin
|
1317
|
+
real?
|
1318
|
+
@real_type
|
1319
|
+
end) == :wrealavg
|
1320
|
+
end
|
1321
|
+
alias_method :wrealavg_enabled?, :wrealavg?
|
1322
|
+
|
1227
1323
|
private
|
1228
1324
|
|
1229
1325
|
# Will be called when the simulator has aborted due to the max error count being exceeded
|
data/lib/origen_sim/tester.rb
CHANGED
@@ -81,11 +81,15 @@ module OrigenSim
|
|
81
81
|
simulator.flush(*args)
|
82
82
|
end
|
83
83
|
|
84
|
-
def set_timeset(name, period_in_ns)
|
84
|
+
def set_timeset(name, period_in_ns = nil)
|
85
85
|
super
|
86
|
+
|
86
87
|
# Need to remove this once OrigenTesters does it
|
87
|
-
|
88
|
-
|
88
|
+
# OrigenTesters with decompiler supports this.
|
89
|
+
if period_in_ns
|
90
|
+
dut.timeset = name
|
91
|
+
dut.current_timeset_period = period_in_ns
|
92
|
+
end
|
89
93
|
|
90
94
|
# Now update the simulator with the new waves
|
91
95
|
simulator.on_timeset_changed
|
data/lib/origen_sim.rb
CHANGED
@@ -64,6 +64,15 @@ module OrigenSim
|
|
64
64
|
'disconnected' => -2
|
65
65
|
}
|
66
66
|
|
67
|
+
FORCE_PIN_TYPES_MAPPING = {
|
68
|
+
'real' => :analog,
|
69
|
+
'ana' => :analog,
|
70
|
+
'analog' => :analog,
|
71
|
+
|
72
|
+
'dig' => :digital,
|
73
|
+
'digital' => :digital
|
74
|
+
}
|
75
|
+
|
67
76
|
def self.__instantiate_simulator__
|
68
77
|
@simulator ||= Simulator.new
|
69
78
|
end
|
@@ -216,6 +225,10 @@ module OrigenSim
|
|
216
225
|
Origen.load_application
|
217
226
|
Origen.app.load_target!
|
218
227
|
|
228
|
+
unless tester.simulator?
|
229
|
+
Origen.app!.fail!(message: 'OrigenSim.run cannot be used when the simulator is not the current tester!')
|
230
|
+
end
|
231
|
+
|
219
232
|
# Start up the simulator and run whatever's in the target block.
|
220
233
|
# After the block completes, shutdown the simulator
|
221
234
|
tester.simulator.setup_simulation(name)
|
data/pattern/test.rb
CHANGED
data/templates/probe.tcl.erb
CHANGED
@@ -1,6 +1,5 @@
|
|
1
1
|
database -open waves -into <%= options[:dir] %>/<%= options[:wave_file] %> -default -event
|
2
|
-
|
3
|
-
#probe -create -assertions -transaction <%= options[:testbench_top] || 'origen' %> -depth all -database waves
|
2
|
+
<%= options[:probe_cmd] %>
|
4
3
|
% Array(options[:tcl_inputs]).each do |line|
|
5
4
|
<%= line %>
|
6
5
|
% end
|
@@ -1,4 +1,53 @@
|
|
1
|
-
|
1
|
+
// This is an auto-generated file from OrigenSim
|
2
|
+
// (https://origen-sdk.org/origen/guides/simulation/introduction/)
|
3
|
+
// This file was generated with this command:
|
4
|
+
// <%= options[:build_cmd] %>
|
5
|
+
|
6
|
+
% pins_by_type = [[nil]]
|
7
|
+
% type = nil
|
8
|
+
% dut.rtl_pins.each do |n, p|
|
9
|
+
% if p.type == type
|
10
|
+
% pins_by_type.last << p
|
11
|
+
% else
|
12
|
+
% pins_by_type << [p.type, p]
|
13
|
+
% type = p.type
|
14
|
+
% end
|
15
|
+
% end
|
16
|
+
|
17
|
+
// Utility Macros
|
18
|
+
// Cast define value as a string.
|
19
|
+
`define ORIGEN_SIM_TO_S(s) `"s`"
|
20
|
+
|
21
|
+
// Indicate the target vendor
|
22
|
+
% if options[:vendor] == :cadence
|
23
|
+
`define ORIGEN_SIM_CADENCE
|
24
|
+
% elsif options[:vendor] == :synopsis
|
25
|
+
`define ORIGEN_SIM_SYNOPSIS
|
26
|
+
% elsif options[:vendor] == :icarus
|
27
|
+
`define ORIGEN_SIM_ICARUS
|
28
|
+
% end
|
29
|
+
|
30
|
+
// Indicate the file type, without resorting to System Verilog or vendor-specific functions
|
31
|
+
% if options[:file_type] == :sv
|
32
|
+
`define ORIGEN_SV_FILE
|
33
|
+
% elsif options[:file_type] == :vams
|
34
|
+
`define ORIGEN_VAMS_FILE
|
35
|
+
% else
|
36
|
+
`define ORIGEN_V_FILE
|
37
|
+
% end
|
38
|
+
|
39
|
+
`ifdef ORIGEN_WREAL
|
40
|
+
`define ORIGEN_USE_REAL
|
41
|
+
`define ORIGEN_REAL_TYPE wreal
|
42
|
+
`elsif ORIGEN_WREALAVG
|
43
|
+
`define ORIGEN_USE_REAL
|
44
|
+
`define ORIGEN_REAL_TYPE wrealavg
|
45
|
+
`ifdef ORIGEN_SIM_CADENCE
|
46
|
+
import cds_rnm_pkg::*;
|
47
|
+
`elsif ORIGEN_SIM_SYNOPSIS
|
48
|
+
import snps_msv_nettype_pkg::*;
|
49
|
+
`endif
|
50
|
+
`endif
|
2
51
|
|
3
52
|
// To create the big fonts - http://patorjk.com/software/taag/#p=display&f=Big
|
4
53
|
|
@@ -103,7 +152,7 @@ module pin_driver(pin, sync);
|
|
103
152
|
endmodule
|
104
153
|
|
105
154
|
|
106
|
-
`ifdef
|
155
|
+
`ifdef ORIGEN_USE_REAL
|
107
156
|
// _ _____ _ _____ _
|
108
157
|
// /\ | | | __ (_) | __ \ (_)
|
109
158
|
// / \ _ __ __ _| | ___ __ _ | |__) | _ __ | | | |_ __ ___ _____ _ __
|
@@ -113,13 +162,13 @@ endmodule
|
|
113
162
|
// __/ |
|
114
163
|
// |___/
|
115
164
|
|
116
|
-
// A simple WREAL pin driver that can drive real value on a pin or else hi-Z, when the driver is in
|
165
|
+
// A simple WREAL/WREALAVG pin driver that can drive real value on a pin or else hi-Z, when the driver is in
|
117
166
|
// hi-Z mode the value applied by any other driver connected to the pin can be measured by peeking
|
118
167
|
// the value on pin
|
119
168
|
module ana_pin_driver(pin);
|
120
169
|
inout pin;
|
121
170
|
|
122
|
-
|
171
|
+
`ORIGEN_REAL_TYPE pin;
|
123
172
|
|
124
173
|
reg drive_en = 0;
|
125
174
|
real drive = 0.0; // Value that will be driven on pin when drive is enabled
|
@@ -140,36 +189,52 @@ endmodule
|
|
140
189
|
// drivers are therefore accessible via origen.pins.my_pin_name
|
141
190
|
module pin_drivers(<%= dut.rtl_pins.map { |n, p, o| "#{p.id}_o" }.join(', ') %>);
|
142
191
|
|
143
|
-
%
|
144
|
-
% if
|
145
|
-
`ifdef
|
192
|
+
% pins_by_type.each do |group|
|
193
|
+
% if group.first == :analog
|
194
|
+
`ifdef ORIGEN_USE_REAL
|
195
|
+
% group[1..-1].each do |pin|
|
146
196
|
inout <%= pin.id %>_o;
|
197
|
+
% end
|
147
198
|
`else
|
199
|
+
% group[1..-1].each do |pin|
|
148
200
|
output <%= pin.id %>_o;
|
201
|
+
% end
|
149
202
|
`endif
|
150
203
|
% else
|
204
|
+
% group[1..-1].each do |pin|
|
151
205
|
output <%= pin.id %>_o;
|
206
|
+
% end
|
152
207
|
% end
|
153
208
|
% end
|
154
209
|
|
155
|
-
`ifdef
|
210
|
+
`ifdef ORIGEN_USE_REAL
|
156
211
|
% dut.rtl_pins(type: :analog).each do |name, pin, options|
|
157
|
-
|
212
|
+
`ORIGEN_REAL_TYPE <%= pin.id %>_o;
|
158
213
|
% end
|
159
214
|
`endif
|
160
215
|
|
161
216
|
reg sync = 0;
|
162
217
|
|
163
|
-
%
|
164
|
-
%
|
165
|
-
|
166
|
-
|
218
|
+
% pins_by_type.each do |group|
|
219
|
+
% if group.first == :analog
|
220
|
+
`ifdef ORIGEN_USE_REAL
|
221
|
+
% group[1..-1].each do |pin|
|
222
|
+
% unless pin.meta[:origen_sim_init_pin_state] == -2
|
167
223
|
ana_pin_driver <%= pin.id %>(.pin(<%= pin.id %>_o));
|
224
|
+
% end
|
225
|
+
% end
|
168
226
|
`else
|
227
|
+
% group[1..-1].each do |pin|
|
228
|
+
% unless pin.meta[:origen_sim_init_pin_state] == -2
|
169
229
|
pin_driver #(<%= pin.meta[:origen_sim_init_pin_state].nil? ? '' : ".init_drive(#{pin.meta[:origen_sim_init_pin_state]}), "%>.pin_name("<%= pin.id %>")) <%= pin.id %>(.pin(<%= pin.id %>_o), .sync(sync));
|
230
|
+
% end
|
231
|
+
% end
|
170
232
|
`endif
|
171
|
-
%
|
233
|
+
% else
|
234
|
+
% group[1..-1].each do |pin|
|
235
|
+
% unless pin.meta[:origen_sim_init_pin_state] == -2
|
172
236
|
pin_driver #(<%= pin.meta[:origen_sim_init_pin_state].nil? ? '' : ".init_drive(#{pin.meta[:origen_sim_init_pin_state]}), "%>.pin_name("<%= pin.id %>")) <%= pin.id %>(.pin(<%= pin.id %>_o), .sync(sync));
|
237
|
+
% end
|
173
238
|
% end
|
174
239
|
% end
|
175
240
|
% end
|
@@ -224,7 +289,7 @@ endmodule
|
|
224
289
|
|
225
290
|
// Instantiated as origen.debug, this module contains the error count, current pattern name and comments,
|
226
291
|
// metadata associated with the snapshot build, and other debug information
|
227
|
-
module
|
292
|
+
module <%= options[:debug_module_name] %>;
|
228
293
|
reg [31:0] errors = 0;
|
229
294
|
reg [15:0] marker = 0;
|
230
295
|
reg [31:0] match_errors = 0;
|
@@ -238,10 +303,16 @@ module debug;
|
|
238
303
|
|
239
304
|
snapshot_details snapshot_details();
|
240
305
|
|
241
|
-
`ifdef
|
242
|
-
reg
|
306
|
+
`ifdef ORIGEN_USE_REAL
|
307
|
+
reg real_enabled = 1;
|
308
|
+
`ifdef ORIGEN_SV_FILE
|
309
|
+
reg [1023:0] real_type = `ORIGEN_SIM_TO_S(`ORIGEN_REAL_TYPE`);
|
310
|
+
`else
|
311
|
+
reg [1023:0] real_type = "wreal";
|
312
|
+
`endif
|
243
313
|
`else
|
244
|
-
reg
|
314
|
+
reg real_enabled = 0;
|
315
|
+
reg [1023:0] real_type = 0;
|
245
316
|
`endif
|
246
317
|
|
247
318
|
endmodule
|
@@ -255,19 +326,25 @@ endmodule
|
|
255
326
|
// | |
|
256
327
|
// |_|
|
257
328
|
|
258
|
-
module <%= options[:
|
329
|
+
module <%= options[:testbench] %>;
|
259
330
|
|
260
|
-
reg
|
331
|
+
reg <%= options[:finish_signal] %> = 0;
|
261
332
|
|
262
|
-
%
|
263
|
-
% if
|
264
|
-
`ifdef
|
265
|
-
|
333
|
+
% pins_by_type.each do |group|
|
334
|
+
% if group.first == :analog
|
335
|
+
`ifdef ORIGEN_USE_REAL
|
336
|
+
% group[1..-1].each do |pin|
|
337
|
+
`ORIGEN_REAL_TYPE <%= pin.id %>;
|
338
|
+
% end
|
266
339
|
`else
|
340
|
+
% group[1..-1].each do |pin|
|
267
341
|
wire <%= pin.id %>;
|
342
|
+
% end
|
268
343
|
`endif
|
269
344
|
% else
|
345
|
+
% group[1..-1].each do |pin|
|
270
346
|
wire <%= pin.id %>;
|
347
|
+
% end
|
271
348
|
% end
|
272
349
|
% end
|
273
350
|
|
@@ -278,13 +355,7 @@ module <%= options[:testbench_name] || 'origen' %>;
|
|
278
355
|
);
|
279
356
|
|
280
357
|
// Instantiate the DUT
|
281
|
-
<%= options[:top].sub(/\..*/, '') %>
|
282
|
-
% dut.power_pins.each do |name, pin, options|
|
283
|
-
.<%= pin.id %>(<%= pin.id %>),
|
284
|
-
% end
|
285
|
-
% dut.ground_pins.each do |name, pin, options|
|
286
|
-
.<%= pin.id %>(<%= pin.id %>),
|
287
|
-
% end
|
358
|
+
<%= options[:top].sub(/\..*/, '') %> <%= options[:top_level_name] %> (
|
288
359
|
% # Keep track of the primary groups seen.
|
289
360
|
% seen_groups = []
|
290
361
|
% dut.rtl_pins.each_with_index do |(name, pin, options), i|
|
@@ -303,7 +374,7 @@ module <%= options[:testbench_name] || 'origen' %>;
|
|
303
374
|
% end
|
304
375
|
);
|
305
376
|
|
306
|
-
|
377
|
+
<%= options[:debug_module_name] %> <%= options[:debug_module_name] %> ();
|
307
378
|
|
308
379
|
initial
|
309
380
|
begin
|
@@ -319,12 +390,11 @@ module <%= options[:testbench_name] || 'origen' %>;
|
|
319
390
|
$vcdplusmemon;
|
320
391
|
`endif
|
321
392
|
`ifdef ORIGEN_FSDB
|
322
|
-
$fsdbDumpfile("origen.fsdb");
|
323
393
|
$fsdbDumpvars(0, "+all");
|
324
394
|
`endif
|
325
395
|
end
|
326
396
|
|
327
|
-
always @(posedge
|
397
|
+
always @(posedge <%= options[:finish_signal] %>) begin
|
328
398
|
$finish(2);
|
329
399
|
end
|
330
400
|
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: origen_sim
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.21.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Stephen McGinty
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2025-02-22 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: origen
|
@@ -44,14 +44,14 @@ dependencies:
|
|
44
44
|
requirements:
|
45
45
|
- - ">="
|
46
46
|
- !ruby/object:Gem::Version
|
47
|
-
version: 0.6.
|
47
|
+
version: 0.6.3
|
48
48
|
type: :runtime
|
49
49
|
prerelease: false
|
50
50
|
version_requirements: !ruby/object:Gem::Requirement
|
51
51
|
requirements:
|
52
52
|
- - ">="
|
53
53
|
- !ruby/object:Gem::Version
|
54
|
-
version: 0.6.
|
54
|
+
version: 0.6.3
|
55
55
|
description:
|
56
56
|
email:
|
57
57
|
- stephen.f.mcginty@gmail.com
|
@@ -147,8 +147,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
147
147
|
- !ruby/object:Gem::Version
|
148
148
|
version: 1.8.11
|
149
149
|
requirements: []
|
150
|
-
|
151
|
-
rubygems_version: 2.7.7
|
150
|
+
rubygems_version: 3.1.6
|
152
151
|
signing_key:
|
153
152
|
specification_version: 4
|
154
153
|
summary: Plugin that provides a testbench environment to simulate Origen test patterns
|