origen 0.2.6 → 0.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (158) hide show
  1. checksums.yaml +4 -4
  2. data/bin/origen +3 -1
  3. data/config/boot.rb +1 -7
  4. data/config/commands.rb +0 -1
  5. data/config/version.rb +2 -2
  6. data/lib/c99/{j750_interface.rb → ate_interface.rb} +3 -11
  7. data/lib/c99/doc_interface.rb +1 -1
  8. data/lib/origen.rb +9 -30
  9. data/lib/origen/application.rb +10 -8
  10. data/lib/origen/application/configuration.rb +13 -26
  11. data/lib/origen/application/plugins.rb +122 -0
  12. data/lib/origen/application/plugins_manager.rb +16 -254
  13. data/lib/origen/application/release.rb +2 -2
  14. data/lib/origen/application/runner.rb +2 -4
  15. data/lib/origen/chips.rb +0 -0
  16. data/lib/origen/chips/chip.rb +0 -0
  17. data/lib/origen/chips/design_entry.rb +0 -0
  18. data/lib/origen/chips/doc_entry.rb +0 -0
  19. data/lib/origen/chips/note.rb +0 -0
  20. data/lib/origen/commands.rb +4 -44
  21. data/lib/origen/commands/compile.rb +1 -2
  22. data/lib/origen/commands/generate.rb +1 -1
  23. data/lib/origen/commands/interactive.rb +1 -2
  24. data/lib/origen/commands/plugin.rb +49 -56
  25. data/lib/origen/commands/program.rb +1 -1
  26. data/lib/origen/commands/rc.rb +2 -2
  27. data/lib/origen/commands/version.rb +2 -17
  28. data/lib/origen/commands_global.rb +3 -0
  29. data/lib/origen/file_handler.rb +10 -10
  30. data/lib/origen/generator.rb +1 -1
  31. data/lib/origen/generator/job.rb +1 -1
  32. data/lib/origen/generator/pattern.rb +2 -2
  33. data/lib/origen/generator/pattern_finder.rb +10 -9
  34. data/lib/origen/pins/pin.rb +0 -0
  35. data/lib/origen/regression_manager.rb +0 -0
  36. data/lib/origen/remote_manager.rb +2 -8
  37. data/lib/origen/revision_control/design_sync.rb +0 -0
  38. data/lib/origen/revision_control/git.rb +0 -0
  39. data/lib/origen/specs.rb +0 -0
  40. data/lib/origen/specs/checkers.rb +0 -0
  41. data/lib/origen/specs/creation_info.rb +0 -0
  42. data/lib/origen/specs/exhibit.rb +0 -0
  43. data/lib/origen/specs/spec.rb +0 -0
  44. data/lib/origen/utility.rb +0 -1
  45. data/lib/origen/utility/diff.rb +0 -0
  46. metadata +42 -119
  47. data/lib/origen/import_manager.rb +0 -596
  48. data/lib/origen/nvm.rb +0 -6
  49. data/lib/origen/nvm/block_array.rb +0 -72
  50. data/lib/origen/tester.rb +0 -56
  51. data/lib/origen/tester/api.rb +0 -277
  52. data/lib/origen/tester/bdm/bdm.rb +0 -25
  53. data/lib/origen/tester/doc/doc.rb +0 -226
  54. data/lib/origen/tester/doc/generator.rb +0 -126
  55. data/lib/origen/tester/doc/generator/flow.rb +0 -71
  56. data/lib/origen/tester/doc/generator/flow_line.rb +0 -203
  57. data/lib/origen/tester/doc/generator/test.rb +0 -68
  58. data/lib/origen/tester/doc/generator/test_group.rb +0 -66
  59. data/lib/origen/tester/doc/generator/tests.rb +0 -47
  60. data/lib/origen/tester/doc/model.rb +0 -162
  61. data/lib/origen/tester/generator.rb +0 -271
  62. data/lib/origen/tester/generator/flow_control_api.rb +0 -606
  63. data/lib/origen/tester/generator/identity_map.rb +0 -25
  64. data/lib/origen/tester/generator/placeholder.rb +0 -13
  65. data/lib/origen/tester/generator/test_numberer.rb +0 -25
  66. data/lib/origen/tester/interface.rb +0 -154
  67. data/lib/origen/tester/j750/files.rb +0 -45
  68. data/lib/origen/tester/j750/generator.rb +0 -203
  69. data/lib/origen/tester/j750/generator/flow.rb +0 -123
  70. data/lib/origen/tester/j750/generator/flow_line.rb +0 -288
  71. data/lib/origen/tester/j750/generator/patgroup.rb +0 -111
  72. data/lib/origen/tester/j750/generator/patgroups.rb +0 -41
  73. data/lib/origen/tester/j750/generator/patset.rb +0 -111
  74. data/lib/origen/tester/j750/generator/patsets.rb +0 -41
  75. data/lib/origen/tester/j750/generator/templates/flow.txt.erb +0 -9
  76. data/lib/origen/tester/j750/generator/templates/instances.txt.erb +0 -16
  77. data/lib/origen/tester/j750/generator/templates/patgroups.txt.erb +0 -8
  78. data/lib/origen/tester/j750/generator/templates/patsets.txt.erb +0 -10
  79. data/lib/origen/tester/j750/generator/test_instance.rb +0 -846
  80. data/lib/origen/tester/j750/generator/test_instance_group.rb +0 -60
  81. data/lib/origen/tester/j750/generator/test_instances.rb +0 -182
  82. data/lib/origen/tester/j750/j750.rb +0 -845
  83. data/lib/origen/tester/j750/j750_hpt.rb +0 -35
  84. data/lib/origen/tester/j750/parser.rb +0 -104
  85. data/lib/origen/tester/j750/parser/ac_spec.rb +0 -11
  86. data/lib/origen/tester/j750/parser/ac_specs.rb +0 -0
  87. data/lib/origen/tester/j750/parser/dc_spec.rb +0 -36
  88. data/lib/origen/tester/j750/parser/dc_specs.rb +0 -50
  89. data/lib/origen/tester/j750/parser/descriptions.rb +0 -340
  90. data/lib/origen/tester/j750/parser/flow.rb +0 -111
  91. data/lib/origen/tester/j750/parser/flow_line.rb +0 -207
  92. data/lib/origen/tester/j750/parser/flows.rb +0 -23
  93. data/lib/origen/tester/j750/parser/pattern_set.rb +0 -94
  94. data/lib/origen/tester/j750/parser/pattern_sets.rb +0 -33
  95. data/lib/origen/tester/j750/parser/test_instance.rb +0 -322
  96. data/lib/origen/tester/j750/parser/test_instances.rb +0 -26
  97. data/lib/origen/tester/j750/parser/timeset.rb +0 -15
  98. data/lib/origen/tester/j750/parser/timesets.rb +0 -0
  99. data/lib/origen/tester/jlink/jlink.rb +0 -33
  100. data/lib/origen/tester/parser.rb +0 -24
  101. data/lib/origen/tester/parser/description_lookup.rb +0 -64
  102. data/lib/origen/tester/parser/searchable_array.rb +0 -32
  103. data/lib/origen/tester/parser/searchable_hash.rb +0 -32
  104. data/lib/origen/tester/time.rb +0 -338
  105. data/lib/origen/tester/timing.rb +0 -253
  106. data/lib/origen/tester/ultraflex/files.rb +0 -45
  107. data/lib/origen/tester/ultraflex/generator.rb +0 -200
  108. data/lib/origen/tester/ultraflex/generator/flow.rb +0 -119
  109. data/lib/origen/tester/ultraflex/generator/flow_line.rb +0 -269
  110. data/lib/origen/tester/ultraflex/generator/patgroup.rb +0 -111
  111. data/lib/origen/tester/ultraflex/generator/patgroups.rb +0 -41
  112. data/lib/origen/tester/ultraflex/generator/patset.rb +0 -111
  113. data/lib/origen/tester/ultraflex/generator/patsets.rb +0 -41
  114. data/lib/origen/tester/ultraflex/generator/templates/flow.txt.erb +0 -9
  115. data/lib/origen/tester/ultraflex/generator/templates/instances.txt.erb +0 -16
  116. data/lib/origen/tester/ultraflex/generator/templates/patgroups.txt.erb +0 -8
  117. data/lib/origen/tester/ultraflex/generator/templates/patsets.txt.erb +0 -10
  118. data/lib/origen/tester/ultraflex/generator/test_instance.rb +0 -622
  119. data/lib/origen/tester/ultraflex/generator/test_instance_group.rb +0 -60
  120. data/lib/origen/tester/ultraflex/generator/test_instances.rb +0 -174
  121. data/lib/origen/tester/ultraflex/parser.rb +0 -104
  122. data/lib/origen/tester/ultraflex/parser/ac_spec.rb +0 -11
  123. data/lib/origen/tester/ultraflex/parser/ac_specs.rb +0 -0
  124. data/lib/origen/tester/ultraflex/parser/dc_spec.rb +0 -36
  125. data/lib/origen/tester/ultraflex/parser/dc_specs.rb +0 -50
  126. data/lib/origen/tester/ultraflex/parser/descriptions.rb +0 -342
  127. data/lib/origen/tester/ultraflex/parser/flow.rb +0 -111
  128. data/lib/origen/tester/ultraflex/parser/flow_line.rb +0 -207
  129. data/lib/origen/tester/ultraflex/parser/flows.rb +0 -23
  130. data/lib/origen/tester/ultraflex/parser/pattern_set.rb +0 -94
  131. data/lib/origen/tester/ultraflex/parser/pattern_sets.rb +0 -33
  132. data/lib/origen/tester/ultraflex/parser/test_instance.rb +0 -262
  133. data/lib/origen/tester/ultraflex/parser/test_instances.rb +0 -26
  134. data/lib/origen/tester/ultraflex/parser/timeset.rb +0 -15
  135. data/lib/origen/tester/ultraflex/parser/timesets.rb +0 -0
  136. data/lib/origen/tester/ultraflex/ultraflex.rb +0 -759
  137. data/lib/origen/tester/v93k/generator.rb +0 -80
  138. data/lib/origen/tester/v93k/generator/flow.rb +0 -63
  139. data/lib/origen/tester/v93k/generator/flow_node.rb +0 -17
  140. data/lib/origen/tester/v93k/generator/flow_node/print.rb +0 -10
  141. data/lib/origen/tester/v93k/generator/pattern.rb +0 -16
  142. data/lib/origen/tester/v93k/generator/pattern_master.rb +0 -54
  143. data/lib/origen/tester/v93k/generator/templates/_test_method.txt.erb +0 -6
  144. data/lib/origen/tester/v93k/generator/templates/_test_suite.txt.erb +0 -11
  145. data/lib/origen/tester/v93k/generator/templates/template.flow.erb +0 -121
  146. data/lib/origen/tester/v93k/generator/templates/template.pmfl.erb +0 -9
  147. data/lib/origen/tester/v93k/generator/test_function.rb +0 -103
  148. data/lib/origen/tester/v93k/generator/test_functions.rb +0 -79
  149. data/lib/origen/tester/v93k/generator/test_method.rb +0 -46
  150. data/lib/origen/tester/v93k/generator/test_methods.rb +0 -75
  151. data/lib/origen/tester/v93k/generator/test_suite.rb +0 -54
  152. data/lib/origen/tester/v93k/generator/test_suites.rb +0 -65
  153. data/lib/origen/tester/v93k/v93k.rb +0 -420
  154. data/lib/origen/tester/vector.rb +0 -86
  155. data/lib/origen/tester/vector_generator.rb +0 -637
  156. data/lib/origen/tester/vector_pipeline.rb +0 -150
  157. data/lib/origen/utility/design_sync.rb +0 -494
  158. data/lib/origen/version_checker.rb +0 -117
@@ -1,262 +0,0 @@
1
- module Origen
2
- module Tester
3
- class Ultraflex
4
- class Parser
5
- class TestInstance
6
- attr_accessor :parser
7
-
8
- TYPES = %w(
9
- functional board_pmu empty pin_pmu power_supply
10
- )
11
-
12
- TYPE_ALIASES = {
13
- functional_t: :functional,
14
- boardpmu_t: :board_pmu,
15
- nvmboardpmucal_t: :board_pmu,
16
- nvmboardpmumeasure_t: :board_pmu,
17
- empty_t: :empty,
18
- pinpmu_t: :pin_pmu,
19
- nvmpinpmucal_t: :pin_pmu,
20
- nvmpinpmumeas_t: :pin_pmu,
21
- powersupply_t: :power_supply
22
- }
23
-
24
- attributes = %w(
25
- test_name proc_type proc_name proc_called_as dc_category dc_selector ac_category ac_selector
26
- time_sets edge_sets pin_levels overlay
27
- )
28
- 80.times do |i|
29
- attributes << "arg#{i}"
30
- end
31
- attributes << 'comment'
32
-
33
- ATTRS = attributes
34
-
35
- ALIASES = {
36
- name: :test_name,
37
-
38
- functional: {
39
- pattern: :arg0,
40
- start_func: :arg1,
41
- pre_pat_func: :arg2,
42
- pre_test_func: :arg3,
43
- post_test_func: :arg4,
44
- post_pat_func: :arg5,
45
- end_func: :arg6,
46
- set_pass_fail: :arg7,
47
- start_func_args: :arg13,
48
- pre_pat_func_args: :arg14,
49
- pre_test_func_args: :arg15,
50
- post_test_func_args: :arg16,
51
- post_pat_func_args: :arg17,
52
- end_func_args: :arg18,
53
- wait_flags: :arg21,
54
- wait_time: :arg22,
55
- pat_flag_func: :arg23,
56
- pat_flag_func_args: :arg24,
57
- relay_mode: :arg25,
58
- threading: :arg26,
59
- match_all_sites: :arg27,
60
- capture_mode: :arg30,
61
- capture_what: :arg31,
62
- capture_memory: :arg32,
63
- capture_size: :arg33,
64
- datalog_mode: :arg34,
65
- data_type: :arg35
66
- },
67
-
68
- board_pmu: {
69
- hsp_start: :arg0,
70
- start_func: :arg1,
71
- pre_pat_func: :arg2,
72
- pre_test_func: :arg3,
73
- post_test_func: :arg4,
74
- post_pat_func: :arg5,
75
- end_func: :arg6,
76
- precond_pat: :arg7,
77
- hold_state_pat: :arg8,
78
- holdstate_pat: :arg8,
79
- pattern: :arg8,
80
- pcp_stop: :arg9,
81
- wait_flags: :arg10,
82
- start_lo: :arg11,
83
- init_lo: :arg11,
84
- start_hi: :arg12,
85
- init_hi: :arg12,
86
- start_hiz: :arg13,
87
- init_hiz: :arg13,
88
- float_pins: :arg14,
89
- pinlist: :arg15,
90
- measure_mode: :arg16,
91
- irange: :arg17,
92
- clamp: :arg18,
93
- vrange: :arg19,
94
- sampling_time: :arg20,
95
- samples: :arg21,
96
- setting_time: :arg22,
97
- hi_lo_lim_valid: :arg23,
98
- hi_limit: :arg24,
99
- lo_limit: :arg25,
100
- force_cond_1: :arg26,
101
- force_cond_2: :arg27,
102
- gang_pins_tested: :arg28,
103
- relay_mode: :arg29,
104
- wait_time_out: :arg30,
105
- start_func_args: :arg31,
106
- pre_pat_func_args: :arg32,
107
- pre_test_func_args: :arg33,
108
- post_test_func_args: :arg34,
109
- post_pat_func_args: :arg35,
110
- end_func_args: :arg36,
111
- pcp_start: :arg37,
112
- pcp_check_pg: :arg38,
113
- hsp_stop: :arg39,
114
- hsp_check_pg: :arg40,
115
- resume_pat: :arg41,
116
- utility_pins_1: :arg42,
117
- utility_pins_0: :arg43,
118
- pre_charge_enable: :arg44,
119
- pre_charge: :arg45,
120
- threading: :arg46
121
- },
122
-
123
- pin_pmu: {
124
- hsp_start: :arg0,
125
- start_func: :arg1,
126
- pre_pat_func: :arg2,
127
- pre_test_func: :arg3,
128
- post_test_func: :arg4,
129
- post_pat_func: :arg5,
130
- end_func: :arg6,
131
- precond_pat: :arg7,
132
- hold_state_pat: :arg8,
133
- holdstate_pat: :arg8,
134
- pattern: :arg8,
135
- pcp_stop: :arg9,
136
- wait_flags: :arg10,
137
- start_lo: :arg11,
138
- init_lo: :arg11,
139
- start_hi: :arg12,
140
- init_hi: :arg12,
141
- start_hiz: :arg13,
142
- init_hiz: :arg13,
143
- float_pins: :arg14,
144
- pinlist: :arg15,
145
- measure_mode: :arg16,
146
- irange: :arg17,
147
- setting_time: :arg18,
148
- hi_lo_lim_valid: :arg19,
149
- hi_limit: :arg20,
150
- lo_limit: :arg21,
151
- force_cond_1: :arg22,
152
- force_cond_2: :arg23,
153
- fload: :arg24,
154
- f_load: :arg24,
155
- relay_mode: :arg25,
156
- wait_time_out: :arg26,
157
- start_func_args: :arg27,
158
- pre_pat_func_args: :arg28,
159
- pre_test_func_args: :arg29,
160
- post_test_func_args: :arg30,
161
- post_pat_func_args: :arg31,
162
- end_func_args: :arg32,
163
- pcp_start: :arg33,
164
- pcp_check_pg: :arg34,
165
- hsp_stop: :arg35,
166
- hsp_check_pg: :arg36,
167
- sampling_time: :arg37,
168
- samples: :arg38,
169
- resume_pat: :arg39,
170
- vcl: :arg40,
171
- vch: :arg41,
172
- utility_pins_1: :arg42,
173
- utility_pins_0: :arg43,
174
- pre_charge_enable: :arg44,
175
- pre_charge: :arg45,
176
- threading: :arg46
177
- }
178
- }
179
-
180
- # Make readers for each low level attribute
181
- ATTRS.each do |attr|
182
- attr_reader attr
183
- end
184
-
185
- # And the aliases
186
- ALIASES.each do |alias_, attr|
187
- define_method("#{alias_}") do
188
- send(attr)
189
- end
190
- end
191
-
192
- def initialize(line, options = {})
193
- @parser = options[:parser]
194
- @line = line
195
- parse
196
- if valid?
197
- ATTRS.each_with_index do |attr, i|
198
- instance_variable_set("@#{attr}", components[i + 1])
199
- end
200
- if ALIASES[type]
201
- ALIASES[type].each do |alias_, attr|
202
- define_singleton_method("#{alias_}") do
203
- send(attr)
204
- end
205
- end
206
- end
207
- end
208
- end
209
-
210
- def inspect # :nodoc:
211
- "<TestInstance: #{name}, Type: #{type}>"
212
- end
213
-
214
- def description
215
- parser.descriptions.test_instance(name: name)
216
- end
217
-
218
- def type
219
- TYPE_ALIASES[proc_name.downcase.to_sym] || :unsupported
220
- end
221
-
222
- def parse
223
- @components = @line.split("\t") unless @line.strip.empty?
224
- end
225
-
226
- def valid?
227
- components[4] && ['Excel Macro', 'VB DLL'].include?(components[4])
228
- end
229
-
230
- def components
231
- @components ||= []
232
- end
233
-
234
- # Returns an array of all pattern names referenced in this test instance
235
- def patterns
236
- if self.respond_to?(:pattern)
237
- pattern.split(',').map do |pat|
238
- extract_pattern_from_patset(pat)
239
- end.flatten.map { |pat| pat.gsub(/.*[\\\/]/, '').gsub(/\..*/, '') }
240
- end
241
- end
242
-
243
- def extract_pattern_from_patset(patset)
244
- pset = parser.pattern_sets.where(name: patset, exact: true)
245
- if pset.size > 1
246
- puts "Warning multiple pattern sets called #{patset} found, using the first one"
247
- end
248
- if pset.size == 0
249
- patset
250
- else
251
- pset.first.pattern_names
252
- end
253
- end
254
-
255
- def vdd
256
- parser.dc_specs.where(name: 'VDD', exact: true).first.lookup(dc_category, dc_selector)
257
- end
258
- end
259
- end
260
- end
261
- end
262
- end
@@ -1,26 +0,0 @@
1
- module Origen
2
- module Tester
3
- class Ultraflex
4
- class Parser
5
- class TestInstances < Origen::Tester::Parser::SearchableHash
6
- attr_accessor :parser
7
-
8
- def initialize(options = {})
9
- @parser = options[:parser]
10
- end
11
-
12
- def import(file)
13
- File.readlines(file).each do |line|
14
- l = TestInstance.new(line, parser: parser)
15
- self[l.name] = l if l.valid?
16
- end
17
- end
18
-
19
- def inspect
20
- "<TestInstances: #{size}>"
21
- end
22
- end
23
- end
24
- end
25
- end
26
- end
@@ -1,15 +0,0 @@
1
- module Origen
2
- module Tester
3
- class Ultraflex
4
- class Parser
5
- class Timeset
6
- attr_accessor :parser
7
-
8
- def initialize(options = {})
9
- @parser = options[:parser]
10
- end
11
- end
12
- end
13
- end
14
- end
15
- end
File without changes
@@ -1,759 +0,0 @@
1
- module Origen
2
- module Tester
3
- # This class has been deprecated
4
- Origen.deprecate <<-END
5
- UltraFlex Tester in Origen core has been moved to a dedicated plugin,
6
- use Testers::UltraFLEX from this plugin instead of Origen::Tester::Ultraflex
7
- http://origen.freescale.net/testers
8
- END
9
-
10
- # Tester model to generate .atp patterns for the Teradyne Ultraflex
11
- #
12
- # == Basic Usage
13
- # $tester = Origen::Tester::Ultraflex.new
14
- # $tester.cycle # Generate a vector
15
- #
16
- # Many more methods exist to generate Ultraflex specific micro-code, see below for
17
- # details.
18
- #
19
- # Also note that this class inherits from the base Tester class and so all methods
20
- # described there are also available.
21
- class Ultraflex
22
- include Tester
23
- include Parser
24
- require 'origen/tester/ultraflex/files'
25
- include Files
26
-
27
- autoload :Parser, 'origen/tester/ultraflex/parser'
28
- autoload :Generator, 'origen/tester/ultraflex/generator'
29
-
30
- attr_accessor :use_hv_pin
31
- attr_accessor :software_version
32
-
33
- # Returns a new Ultraflex instance, normally there would only ever be one of these
34
- # assigned to the global variable such as $tester by your target:
35
- # $tester = Ultraflex.new
36
- #
37
- # NOTE: Ultraflex features not yet supported;
38
- # - dual mode (assumes single mode)
39
- # - multiple modules per pattern (only one per for now)
40
- def initialize
41
- @unique_counter = 0
42
- @max_repeat_loop = 65_535
43
- @min_repeat_loop = 2
44
- @pat_extension = 'atp'
45
- @active_loads = true
46
- @pipeline_depth = 255 # for single mode on UP1600
47
- @use_hv_pin = false # allows to use high voltage for a pin for all patterns
48
- @software_version = '8.10.10'
49
- @compress = true
50
- @support_repeat_previous = true
51
- @match_entries = 10
52
- @name = 'ultraflex'
53
- @program_comment_char = ['logprint', "'"]
54
- @min_module_size = 64 # min number of vectors in a module for single
55
- end
56
-
57
- def flows
58
- parser.flows
59
- end
60
-
61
- # Main accessor to all content parsed from existing test program sheets found in the
62
- # supplied directory or in Origen.config.test_program_output_directory
63
- def parser(prog_dir = Origen.config.test_program_output_directory)
64
- unless prog_dir
65
- fail 'You must supply the directory containing the test program sheets, or define it via Origen.config.test_program_output_directory'
66
- end
67
- @parser ||= ULTRAFLEX::Parser.new
68
- @parsed_dir ||= false
69
- if @parsed_dir != prog_dir
70
- @parser.parse(prog_dir)
71
- @parsed_dir = prog_dir
72
- end
73
- @parser
74
- end
75
-
76
- # Capture a vector to the tester HRAM.
77
- #
78
- # This method applys a store vector (stv) opcode to the previous vector, note that is does
79
- # not actually generate a new vector.
80
- #
81
- # Sometimes when generating vectors within a loop you may want to apply a stv opcode
82
- # retrospectively to a previous vector, passing in an offset option will allow you
83
- # to do this.
84
- #
85
- # On Ultraflex the pins argument is ignored since the tester only supports whole vector capture.
86
- #
87
- # @example
88
- # $tester.cycle # This is the vector you want to capture
89
- # $tester.store # This applys the STV opcode
90
- #
91
- # $tester.cycle # This one gets stored
92
- # $tester.cycle
93
- # $tester.cycle
94
- # $tester.store(:offset => -2) # Just realized I need to capture that earlier vector
95
- def store(*pins)
96
- options = pins.last.is_a?(Hash) ? pins.pop : {}
97
- options = { offset: 0
98
- }.merge(options)
99
- update_vector microcode: 'stv', offset: options[:offset]
100
- end
101
- alias_method :to_hram, :store
102
- alias_method :capture, :store
103
-
104
- # Capture the next vector generated to HRAM
105
- #
106
- # This method applys a store vector (stv) opcode to the next vector to be generated,
107
- # note that is does not actually generate a new vector.
108
- #
109
- # On Ultraflex the pins argument is ignored since the tester only supports whole vector capture.
110
- #
111
- # @example
112
- # $tester.store_next_cycle
113
- # $tester.cycle # This is the vector that will be captured
114
- def store_next_cycle(*pins)
115
- options = pins.last.is_a?(Hash) ? pins.pop : {}
116
- options = {
117
- }.merge(options)
118
- preset_next_vector microcode: 'stv'
119
- end
120
-
121
- # Call a subroutine.
122
- #
123
- # This method applies a call subroutine opcode to the previous vector, it does not
124
- # generate a new vector.
125
- #
126
- # Subroutines should always be called through this method as it ensures a running
127
- # log of called subroutines is maintained and which then gets output in the pattern
128
- # header to import the right dependencies.
129
- #
130
- # An offset option is available to make the call on earlier vectors.
131
- #
132
- # ==== Examples
133
- # $tester.call_subroutine("mysub")
134
- # $tester.call_subroutine("my_other_sub", :offset => -1)
135
- def call_subroutine(name, options = {})
136
- options = {
137
- offset: 0
138
- }.merge(options)
139
- called_subroutines << name.to_s.chomp unless called_subroutines.include?(name.to_s.chomp) || @inhibit_vectors
140
- update_vector microcode: "call #{name}", offset: options[:offset]
141
- end
142
-
143
- # Start a subroutine.
144
- #
145
- # Generates a global subroutine label. Global is used to adhere to the best practice of
146
- # containing all subroutines in dedicated patterns, e.g. global_subs.atp
147
- #
148
- # ==== Examples
149
- # $tester.start_subroutine("wait_for_done")
150
- # < generate your subroutine vectors here >
151
- # $tester.end_subroutine
152
- def start_subroutine(name)
153
- local_subroutines << name.to_s.chomp unless local_subroutines.include?(name.to_s.chomp) || @inhibit_vectors
154
- microcode "global subr #{name}:"
155
- end
156
-
157
- # * Ultraflex Specific *
158
- #
159
- #
160
- def enable_flag(options = {})
161
- options = { flagnum: 4, # which flag to enable for later checking
162
- }.merge(options)
163
-
164
- case options[:flagnum]
165
- when 1
166
- flagname = 'cpuA_cond'
167
- when 2
168
- flagname = 'cpuB_cond'
169
- when 3
170
- flagname = 'cpuC_cond'
171
- when 4
172
- flagname = 'cpuD_cond'
173
- else
174
- abort "ERROR! Invalid flag name passed to 'enable_flag' method!\n"
175
- end
176
- update_vector(microcode: "branch_expr(#{flagname})")
177
- end
178
-
179
- # * Ultraflex Specific *
180
- #
181
- #
182
- def set_flag(options = {})
183
- options = { flagnum: 4, # which flag to set
184
- }.merge(options)
185
-
186
- case options[:flagnum]
187
- when 1
188
- flagname = 'cpuA_cond'
189
- when 2
190
- flagname = 'cpuB_cond'
191
- when 3
192
- flagname = 'cpuC_cond'
193
- when 4
194
- flagname = 'cpuD_cond'
195
- else
196
- abort "ERROR! Invalid flag name passed to 'set_flag' method!\n"
197
- end
198
- update_vector(microcode: "set_cpu_cond(#{flagname})")
199
- end
200
-
201
- # End a subroutine.
202
- #
203
- # Generates a return opcode on the last vector.
204
- #
205
- # ==== Examples
206
- # $tester.start_subroutine("wait_for_done")
207
- # < generate your subroutine vectors here >
208
- # $tester.end_subroutine
209
- # cond: whether return is conditional on a flag (to permit to mix subrs together)
210
- def end_subroutine(cond = false)
211
- if cond
212
- update_vector microcode: 'if (flag) return'
213
- else
214
- update_vector microcode: 'return'
215
- end
216
- end
217
-
218
- # Handshake with the tester.
219
- #
220
- # Will set a cpu flag (A) and wait for it to be cleared by the tester, optionally
221
- # pass in a read code to pass information to the tester.
222
- #
223
- # ==== Examples
224
- # $tester.handshake # Pass control to the tester for a measurement
225
- # $tester.handshake(:readcode => 10) # Trigger a specific action by the tester
226
- def handshake(options = {})
227
- options = {
228
- readcode: false,
229
- manual_stop: false, # set a 2nd CPU flag in case 1st flag is automatically cleared
230
- }.merge(options)
231
- if options[:readcode]
232
- cycle(microcode: "set_code #{options[:readcode]}")
233
- end
234
- if options[:manual_stop]
235
- cycle(microcode: 'enable (cpuB)')
236
- cycle(microcode: 'set_cpu (cpuA cpuB)')
237
- cycle(microcode: "loop_here_#{@unique_counter}: if (flag) jump loop_here_#{@unique_counter}")
238
- else
239
- cycle(microcode: 'set_cpu (cpuA)')
240
- cycle(microcode: "loop_here_#{@unique_counter}: if (cpuA) jump loop_here_#{@unique_counter}")
241
- end
242
- @unique_counter += 1 # Increment so a different label will be applied if another
243
- # handshake is called in the same pattern
244
- end
245
-
246
- # Do a frequency measure.
247
- #
248
- # Write the necessary micro code to do a frequency measure on the given pin,
249
- # optionally supply a read code to pass information to the tester.
250
- #
251
- # ==== Examples
252
- # $tester.freq_count($top.pin(:d_out)) # Freq measure on pin "d_out"
253
- # $tester.freq_count($top.pin(:d_out):readcode => 10)
254
- def freq_count(pin, options = {})
255
- options = { readcode: false
256
- }.merge(options)
257
-
258
- cycle(microcode: "set_code #{options[:readcode]}") if options[:readcode]
259
- cycle(microcode: 'set_cpu (cpuA)')
260
- cycle(microcode: 'set_cpu (cpuA)')
261
- cycle(microcode: 'set_cpu (cpuB)')
262
- cycle(microcode: 'set_cpu (cpuC)')
263
- cycle(microcode: 'freq_loop_1:')
264
- cycle(microcode: 'if (cpuA) jump freq_loop_1')
265
- pin.drive_lo
266
- delay(2000)
267
- pin.dont_care
268
- cycle(microcode: 'freq_loop_2: enable (cpuB)')
269
- cycle(microcode: 'if (flag) jump freq_loop_2')
270
- cycle(microcode: 'enable (cpuC)')
271
- cycle(microcode: 'if (flag) jump freq_loop_1')
272
- end
273
-
274
- # * Ultraflex Specific *
275
- #
276
- # No MTO avail on Ultraflex-- need to work with DSSC
277
- #
278
- # def memory_test
279
-
280
- # Generates a match loop on up to two pins.
281
- #
282
- # This method is not really intended to be called directly, rather you should call
283
- # via Tester#wait e.g. $tester.wait(:match => true).
284
- #
285
- # The timeout should be provided in cycles, however when called via the wait method the
286
- # time-based helpers (time_in_us, etc) will be converted to cycles for you.
287
- # The following options are available to tailor the match loop behavior, defaults in
288
- # parenthesis:
289
- # * :pin - The pin object to match on (*required*)
290
- # * :state - The pin state to match on, :low or :high (*required*)
291
- # * :pin2 (nil) - Optionally supply a second pin to match on
292
- # * :state2 (nil) - State for the second pin (required if :pin2 is supplied)
293
- # * :check_for_fails (false) - Flushes the pipeline and handshakes with the tester (passing readcode 100) prior to the match (to allow binout of fails encountered before the match)
294
- # * :force_fail_on_timeout (true) - Force a vector mis-compare if the match loop times out
295
- # * :on_timeout_goto ("") - Optionally supply a label to branch to on timeout, by default will continue from the end of the match loop
296
- # * :on_pin_match_goto ("") - Optionally supply a label to branch to when pin 1 matches, by default will continue from the end of the match loop
297
- # * :on_pin2_match_goto ("") - Optionally supply a label to branch to when pin 2 matches, by default will continue from the end of the match loop
298
- # * :multiple_entries (false) - Supply an integer to generate multiple entries into the match (each with a unique readcode), this can be useful when debugging patterns with multiple matches
299
- # * :force_fail_on_timeout (true) - force pattern to fail if timeout occurs
300
- # * :global_loops (false) - whether match loop loops should use global labels
301
- # * :manual_stop (false) - whether to use extra cpuB flag to resolve IG-XL v.3.50.xx bug where VBT clears cpuA immediately
302
- # at start of PatFlagFunc instead of at end. Use will have to manually clear cpuB to resume this pattern.
303
- # ==== Examples
304
- # $tester.wait(:match => true, :time_in_us => 5000, :pin => $top.pin(:done), :state => :high)
305
- def match(pin, state, timeout, options = {})
306
- options = {
307
- check_for_fails: false,
308
- on_timeout_goto: false,
309
- pin2: false,
310
- state2: false,
311
- on_pin_match_goto: false,
312
- on_pin2_match_goto: false,
313
- multiple_entries: false,
314
- force_fail_on_timeout: true,
315
- global_loops: false,
316
- manual_stop: false,
317
- clr_fail_post_match: false
318
- }.merge(options)
319
-
320
- # Flush the pipeline first and then pass control to the program to bin out any failures
321
- # prior to entering the match loop
322
- if options[:check_for_fails]
323
- if options[:multiple_entries]
324
- @match_entries.times do |i|
325
- microcode "global subr match_done_#{i}:"
326
- cycle(microcode: "set_code #{i + 100}")
327
- cycle(microcode: 'jump call_tester') unless i == @match_entries - 1
328
- end
329
- microcode 'call_tester:'
330
- else
331
- cycle(microcode: 'set_code 100')
332
- end
333
- cc 'Wait for any prior failures to propagate through the pipeline'
334
- cycle(microcode: 'pipe_minus 1')
335
- cc 'Now handshake with the tester to bin out and parts that have failed before they got here'
336
- handshake(manual_stop: options[:manual_stop])
337
- end
338
-
339
- # Now do the main match loop
340
- cc 'Start the match loop'
341
-
342
- # Calculate the loop counts for the 2 loops to appropriately hit the timeout requested
343
- inner_loop_vectors = (@pipeline_depth - 1) + 4 # num vectors in inner loop
344
- if timeout.to_f < @max_repeat_loop * inner_loop_vectors * @min_repeat_loop
345
- # Handle case for smaller timeouts (that would force small outer loop count)
346
- inner_loop_count = (timeout.to_f / (inner_loop_vectors * @min_repeat_loop)).ceil
347
- outer_loop_count = @min_repeat_loop
348
- else
349
- # Handle longer delays
350
- inner_loop_count = @max_repeat_loop
351
- outer_loop_count = (timeout.to_f / (@max_repeat_loop * inner_loop_vectors)).ceil # Will do a minimum of 1 * max_repeat_loop * (pipeline_depth-1)
352
- end
353
-
354
- global_opt = (options[:global_loops]) ? 'global ' : ''
355
- microcode "#{global_opt}match_outer_loop_#{@unique_counter}:"
356
- cycle(microcode: "loopB #{outer_loop_count}")
357
- microcode "#{global_opt}match_inner_loop_#{@unique_counter}:"
358
- state == :low ? pin.expect_lo : pin.expect_hi
359
- cc "Check if #{pin.name} is #{state == :low ? 'low' : 'high'} yet"
360
- cycle(microcode: "loopA #{inner_loop_count}")
361
- pin.dont_care
362
- cc ' Wait for the result to propagate through the pipeline'
363
- cycle(microcode: 'pipe_minus 1')
364
- cc "Branch if #{pin.name} was #{state == :low ? 'low' : 'high'}"
365
- cycle(microcode: "if (pass) jump #{pin.name}_matched_#{@unique_counter} icc ifc")
366
- cycle(microcode: 'clr_flag (fail) icc')
367
- if options[:pin2]
368
- cc "Check if #{options[:pin2].name} is #{options[:state2] == :low ? 'low' : 'high'} yet"
369
- options[:state2] == :low ? options[:pin2].expect_lo : options[:pin2].expect_hi
370
- state == :low ? pin.expect_hi : pin.expect_lo # Give priority to pin 1, don't match pin 2 on this cycle
371
- # if it is really a pin 1 match
372
- cycle # Read for pin 2 and !pin 1
373
- options[:pin2].dont_care
374
- pin.dont_care
375
- cc 'Again wait for the result to propagate through the pipeline'
376
- cycle(microcode: 'pipe_minus 1')
377
- cc "Branch if #{options[:pin2].name} was #{options[:state2] == :low ? 'low' : 'high'}"
378
- cycle(microcode: "if (pass) jump #{options[:pin2].name}_matched_#{@unique_counter} icc ifc")
379
- cycle(microcode: 'clr_flag (fail) icc')
380
- end
381
- cc 'Loop back around if time remaining'
382
- cycle(microcode: "end_loopA match_inner_loop_#{@unique_counter} icc")
383
- cycle(microcode: "end_loopB match_outer_loop_#{@unique_counter} icc")
384
- if options[:force_fail_on_timeout]
385
- cc 'To get here something has gone wrong, strobe again to force a pattern failure'
386
- state == :low ? pin.expect_lo : pin.expect_hi
387
- options[:state2] == :low ? options[:pin2].expect_lo : options[:pin2].expect_hi if options[:pin2]
388
- cycle
389
- pin.dont_care
390
- options[:pin2].dont_care if options[:pin2]
391
- end
392
- if options[:on_timeout_goto]
393
- cycle(microcode: "jump #{options[:on_timeout_goto]} icc")
394
- else
395
- cycle(microcode: "jump match_loop_end_#{@unique_counter} icc")
396
- # cycle(:microcode => 'halt')
397
- end
398
- microcode "#{pin.name}_matched_#{@unique_counter}:"
399
- cycle(microcode: 'pop_loop icc')
400
- unless options[:clr_fail_post_match]
401
- cycle(microcode: 'clr_fail')
402
- end
403
- if options[:on_pin_match_goto]
404
- cycle(microcode: "jump #{options[:on_pin_match_goto]}")
405
- end
406
- if options[:pin2]
407
- microcode "#{options[:pin2].name}_matched_#{@unique_counter}:"
408
- cycle(microcode: 'pop_loop icc')
409
- cycle(microcode: 'clr_fail')
410
- if options[:on_pin2_match_goto]
411
- cycle(microcode: "jump #{options[:on_pin2_match_goto]}")
412
- end
413
- end
414
- microcode "match_loop_end_#{@unique_counter}:"
415
- if options[:clr_fail_post_match]
416
- cycle(microcode: 'clr_fail')
417
- end
418
-
419
- @unique_counter += 1 # Increment so a different label will be applied if another
420
- # handshake is called in the same pattern
421
- end
422
-
423
- # Generates a match loop based on vector condition passed in via block
424
- #
425
- # This method is not really intended to be called directly, rather you should call
426
- # via Tester#wait:
427
- # e.g. $tester.wait(:match => true) do
428
- # reg(:status_reg).bit(:done).read(1)! # vector condition that you want to match
429
- # end
430
- #
431
- # The timeout should be provided in cycles, however when called via the wait method the
432
- # time-based helpers (time_in_us, etc) will be converted to cycles for you.
433
- #
434
- # The following options are available to tailor the match loop behavior, defaults in
435
- # parenthesis:
436
- # * :check_for_fails (false) - Flushes the pipeline and handshakes with the tester (passing readcode 100) prior to the match (to allow binout of fails encountered before the match)
437
- # * :force_fail_on_timeout (true) - Force a vector mis-compare if the match loop times out
438
- # * :on_timeout_goto ("") - Optionally supply a label to branch to on timeout, by default will continue from the end of the match loop
439
- # * :on_block_match_goto ("") - Optionally supply a label to branch to when block condition is met, by default will continue from the end of the match loop
440
- # * :multiple_entries (false) - Supply an integer to generate multiple entries into the match (each with a unique readcode), this can be useful when debugging patterns with multiple matches
441
- # * :force_fail_on_timeout (true) - force pattern to fail if timeout occurs
442
- # * :global_loops (false) - whether match loop loops should use global labels
443
- # * :manual_stop (false) - whether to use extra cpuB flag to resolve IG-XL v.3.50.xx bug where VBT clears cpuA immediately
444
- # at start of PatFlagFunc instead of at end. Use will have to manually clear cpuB to resume this pattern.
445
- # ==== Examples
446
- # $tester.wait(:match => true, :time_in_us => 5000, :pin => $top.pin(:done), :state => :high)
447
- def match_block(timeout, options = {})
448
- options = {
449
- check_for_fails: false,
450
- on_timeout_goto: false,
451
- on_block_match_goto: false,
452
- multiple_entries: false,
453
- force_fail_on_timeout: true,
454
- global_loops: false,
455
- manual_stop: false,
456
- clr_fail_post_match: false
457
- }.merge(options)
458
-
459
- unless block_given?
460
- fail 'ERROR: block not passed to match_block!'
461
- end
462
-
463
- # Flush the pipeline first and then pass control to the program to bin out any failures
464
- # prior to entering the match loop
465
- if options[:check_for_fails]
466
- if options[:multiple_entries]
467
- @match_entries.times do |i|
468
- microcode "global subr match_done_#{i}:"
469
- cycle(microcode: "set_code #{i + 100}")
470
- cycle(microcode: 'jump call_tester') unless i == @match_entries - 1
471
- end
472
- microcode 'call_tester:'
473
- else
474
- cycle(microcode: 'set_code 100')
475
- end
476
- cc 'Wait for any prior failures to propagate through the pipeline'
477
- cycle(microcode: 'pipe_minus 1')
478
- cc 'Now handshake with the tester to bin out and parts that have failed before they got here'
479
- handshake(manual_stop: options[:manual_stop])
480
- end
481
-
482
- # Now do the main match loop
483
- cc 'Start the match loop'
484
-
485
- # Calculate the loop counts for the 2 loops to appropriately hit the timeout requested
486
- inner_loop_vectors = (@pipeline_depth - 1) + 4 # num vectors in inner loop
487
- if timeout.to_f < @max_repeat_loop * inner_loop_vectors * @min_repeat_loop
488
- # Handle case for smaller timeouts (that would force small outer loop count)
489
- inner_loop_count = (timeout.to_f / (inner_loop_vectors * @min_repeat_loop)).ceil
490
- outer_loop_count = @min_repeat_loop
491
- else
492
- # Handle longer delays
493
- inner_loop_count = @max_repeat_loop
494
- outer_loop_count = (timeout.to_f / (@max_repeat_loop * inner_loop_vectors)).ceil # Will do a minimum of 1 * max_repeat_loop * (pipeline_depth-1)
495
- end
496
-
497
- global_opt = (options[:global_loops]) ? 'global ' : ''
498
- microcode "#{global_opt}match_outer_loop_#{@unique_counter}:"
499
- cycle(microcode: "loopB #{outer_loop_count}")
500
- microcode "#{global_opt}match_inner_loop_#{@unique_counter}:"
501
- cycle(microcode: "loopA #{inner_loop_count}")
502
- cc 'Check if block condition met'
503
- yield
504
- cc ' Wait for the result to propagate through the pipeline'
505
- cycle(microcode: 'pipe_minus 1')
506
- cc 'Branch if block condition met'
507
- cycle(microcode: "if (pass) jump block_matched_#{@unique_counter} icc ifc")
508
- cycle(microcode: 'clr_flag (fail) icc')
509
- cc 'Loop back around if time remaining'
510
- cycle(microcode: "end_loopA match_inner_loop_#{@unique_counter} icc")
511
- cycle(microcode: "end_loopB match_outer_loop_#{@unique_counter} icc")
512
- if options[:force_fail_on_timeout]
513
- cc 'To get here something has gone wrong, check block again to force a pattern failure'
514
- yield
515
- end
516
- if options[:on_timeout_goto]
517
- cycle(microcode: "jump #{options[:on_timeout_goto]} icc")
518
- else
519
- cycle(microcode: "jump match_loop_end_#{@unique_counter} icc")
520
- # cycle(:microcode => 'halt')
521
- end
522
- microcode "block_matched_#{@unique_counter}:"
523
- cycle(microcode: 'pop_loop icc')
524
- unless options[:clr_fail_post_match]
525
- cycle(microcode: 'clr_fail')
526
- end
527
- if options[:on_block_match_goto]
528
- cycle(microcode: "jump #{options[:on_block_match_goto]}")
529
- end
530
- microcode "match_loop_end_#{@unique_counter}:"
531
- if options[:clr_fail_post_match]
532
- cycle(microcode: 'clr_fail')
533
- end
534
-
535
- @unique_counter += 1 # Increment so a different label will be applied if another
536
- # handshake is called in the same pattern
537
- end
538
-
539
- # Call a match loop.
540
- #
541
- # Normally you would put your match loop in a global subs pattern, then you can
542
- # call it via this method. This method automatically syncs match loop naming with
543
- # the match generation flow, no arguments required.
544
- #
545
- # This is a Ultraflex specific API.
546
- #
547
- # ==== Examples
548
- # $tester.cycle
549
- # $tester.call_match # Calls the match loop, or the first entry point if you have multiple
550
- # $tester.cycle
551
- # $tester.call_match # Calls the match loop, or the second entry point if you have multiple
552
- def call_match
553
- @match_counter = @match_counter || 0
554
- call_subroutine("match_done_#{@match_counter}")
555
- @match_counter += 1 unless @match_counter == (@match_entries || 1) - 1
556
- end
557
-
558
- # Apply a label to the pattern.
559
- #
560
- # No additional vector is generated.
561
- # Arguments:
562
- # name : label name
563
- # global : (optional) whether to apply global label, default=false
564
- #
565
- # ==== Examples
566
- # $tester.label("something_significant")
567
- # $tester.label("something_significant",true) # apply global label
568
- def label(name, global = false)
569
- global_opt = (global) ? 'global ' : ''
570
- microcode global_opt + name + ':'
571
- end
572
-
573
- # * Ultraflex Specific *
574
- #
575
- # Set a readcode.
576
- #
577
- # Use the set an explicit readcode for communicating with the tester. This method
578
- # will generate an additional vector.
579
- #
580
- # ==== Examples
581
- # $tester.set_code(55)
582
- def set_code(code)
583
- cycle(microcode: "set_code #{code}")
584
- end
585
-
586
- # Branch execution to the given point.
587
- #
588
- # This generates a new vector with a jump instruction to a given label. This method
589
- # will generate an additional vector.
590
- #
591
- # ==== Examples
592
- # $tester.branch_to("something_significant")
593
- def branch_to(label)
594
- cycle(microcode: "jump #{label}")
595
- end
596
- alias_method :branch, :branch_to
597
-
598
- # Add loop to the pattern.
599
- #
600
- # Pass in a name for the loop and the number of times to execute it, all vectors
601
- # generated by the given block will be captured in the loop.
602
- #
603
- # Optional arguments: global - whether to apply global label (default=false)
604
- # label_first - whether to apply loop label before loop vector or not
605
- #
606
- # ==== Examples
607
- # $tester.loop_vectors("pulse_loop", 3) do # Do this 3 times...
608
- # $tester.cycle
609
- # some_other_method_to_generate_vectors
610
- # end
611
- def loop_vectors(name, number_of_loops, global = false, label_first = false)
612
- if number_of_loops > 1
613
- @loop_counters ||= {}
614
- if @loop_counters[name]
615
- @loop_counters[name] += 1
616
- else
617
- @loop_counters[name] = 0
618
- end
619
- loop_name = @loop_counters[name] == 0 ? name : "#{name}_#{@loop_counters[name]}"
620
- if label_first
621
- global_opt = (global) ? 'global ' : ''
622
- microcode "#{global_opt}#{loop_name}: "
623
- end
624
- cycle(microcode: "loopA #{number_of_loops}")
625
- unless label_first
626
- global_opt = (global) ? 'global ' : ''
627
- cycle(microcode: "#{global_opt}#{loop_name}: ")
628
- end
629
- yield
630
- cycle(microcode: "end_loopA #{loop_name}")
631
- else
632
- yield
633
- end
634
- end
635
- alias_method :loop_vector, :loop_vectors
636
-
637
- # An internal method called by Origen to create the pattern header
638
- def pattern_header(options = {})
639
- options = {
640
- subroutine_pat: false,
641
- group: false, # If true the end pattern is intended to run within a pattern group
642
- high_voltage: false, # Supply a pin name here to declare it as an HV instrument
643
- freq_counter: false, # Supply a pin name here to declare it as a frequency counter
644
- }.merge(options)
645
-
646
- called_timesets.each do |timeset|
647
- microcode "import tset #{timeset.name};"
648
- end
649
- unless options[:group] # Withhold imports for pattern groups, is this correct?
650
- called_subroutines.each do |sub_name|
651
- # Don't import any called subroutines that are declared in the current pattern
652
- microcode "import svm_subr #{sub_name};" unless local_subroutines.include?(sub_name)
653
- end
654
- end
655
- # Should implement this more like @instruments.each...
656
- microcode 'opcode_mode = single;'
657
- microcode 'digital_inst = hsdm;'
658
- microcode 'compressed = yes;' # if $soc.gzip_patterns
659
- options[:high_voltage] = @use_hv_pin
660
- microcode "pin_setup = {#{options[:high_voltage]} high_voltage;}" if options[:high_voltage]
661
- microcode "pin_setup = {#{options[:freq_counter]} freq_count;}" if options[:freq_counter]
662
- microcode ''
663
-
664
- pin_list = ordered_pins.map(&:name).join(', ')
665
-
666
- microcode "#{options[:subroutine_pat] ? 'srm_vector' : 'vm_vector'}"
667
- microcode "#{options[:pattern]} ($tset, #{pin_list})"
668
- microcode '{'
669
- unless options[:subroutine_pat]
670
- microcode "start_label #{options[:pattern]}_st:"
671
- end
672
- end
673
-
674
- # DDHH pad vector for single mode if pattern is less than 64 vectors??
675
-
676
- # An internal method called by Origen to generate the pattern footer
677
- def pattern_footer(options = {})
678
- options = {
679
- subroutine_pat: false,
680
- end_in_ka: false,
681
- end_with_halt: false
682
- }.merge(options)
683
- # cycle(:microcode => "#{$soc.end_of_pattern_label}:") if $soc.end_of_pattern_label
684
- if options[:end_in_ka]
685
- $tester.cycle microcode: 'keep_alive'
686
- else
687
- if options[:end_with_halt]
688
- $tester.cycle microcode: 'halt'
689
- else
690
- $tester.cycle
691
- end
692
- end
693
- microcode '}'
694
- end
695
-
696
- # Returns an array of subroutines called while generating the current pattern
697
- def called_subroutines
698
- @called_subroutines ||= []
699
- end
700
-
701
- # Returns an array of subroutines created by the current pattern
702
- def local_subroutines # :nodoc:
703
- @local_subroutines ||= []
704
- end
705
-
706
- # This is an internal method use by Origen which returns a fully formatted vector
707
- # You can override this if you wish to change the output formatting at vector level
708
- def format_vector(vec)
709
- timeset = vec.timeset ? "> #{vec.timeset.name}" : ''
710
- pin_vals = vec.pin_vals ? "#{vec.pin_vals} ;" : ''
711
- if vec.repeat > 1
712
- microcode = "repeat #{vec.repeat}"
713
- else
714
- microcode = vec.microcode ? vec.microcode : ''
715
- end
716
- # if vec.pin_vals && vec.number && vec.cycle_number
717
- # comment = " // Vector #{@pattern_vectors}, Cycle #{@pattern_cycles}"
718
- # else
719
- comment = ''
720
- # end
721
- "#{microcode.ljust(65)}#{timeset.ljust(31)}#{pin_vals}#{comment}"
722
- end
723
-
724
- # Override this to force the formatting to match the v1 Ultraflex model (easier diffs)
725
- def push_microcode(code) # :nodoc:
726
- stage.store(code.ljust(65) + ''.ljust(31))
727
- end
728
- alias_method :microcode, :push_microcode
729
-
730
- # All vectors generated with the supplied block will have all pins set
731
- # to the repeat previous state. Any pins that are changed state within
732
- # the block will still update to the supplied value.
733
- # ==== Example
734
- # # All pins except invoke will be assigned the repeat previous code
735
- # # in the generated vector. On completion of the block they will
736
- # # return to their previous state, except for invoke which will
737
- # # retain the value assigned within the block.
738
- # $tester.repeat_previous do
739
- # $top.pin(:invoke).drive(1)
740
- # $tester.cycle
741
- # end
742
- def repeat_previous
743
- Origen.app.pin_map.each { |_id, pin| pin.repeat_previous = true }
744
- yield
745
- Origen.app.pin_map.each { |_id, pin| pin.repeat_previous = false }
746
- end
747
-
748
- def ignore_fails(*pins)
749
- pins.each(&:suspend)
750
- yield
751
- pins.each(&:resume)
752
- end
753
-
754
- def ultraflex?
755
- true
756
- end
757
- end
758
- end
759
- end