origen_testers 0.4.1 → 0.5.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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: dc27fe7836db3c3c77b2ea70f6b82fa845480749
4
- data.tar.gz: 05f95c91897e5e88b89b40e81739f285f8e4bd29
3
+ metadata.gz: 6023b80a1b6acff09fb009dfe06653086cde1101
4
+ data.tar.gz: 7983d124ed3453e03611bbe18c311e1478d4d837
5
5
  SHA512:
6
- metadata.gz: c4154784dad3a7fd28dc2ad103342b2a175692d7f7e92e1cbd2542db8bd47d61faba84c8ca7353b4408bcb4366ec474ce7d8f26080cded6eab68cd981b7cc581
7
- data.tar.gz: 93d476e8c2bb23cd5166d0ab7ef26fc2115c292579eb5f4dfb878ca1a1fb44f5a8a4a4c42550831117e30b6c9c9d4ca5143033cc32b6bcbb845994a41f445f8b
6
+ metadata.gz: 7048fcf4fa639db5f22bfc616e4bab64168dbd551ea44f079b624245c9d1b23929d53548eebea074b9a6eece440753584b312a7be776ce34087cfe55742219bd
7
+ data.tar.gz: 60e493228741d4c898014d1c85a91957f2a2c32fe42319a87665283d84d912c419aba44ef226f03e837b3977d3b7aa23126b96428541a2bedd64c870453b90cc
data/config/version.rb CHANGED
@@ -1,7 +1,7 @@
1
1
  module OrigenTesters
2
2
  MAJOR = 0
3
- MINOR = 4
4
- BUGFIX = 1
3
+ MINOR = 5
4
+ BUGFIX = 0
5
5
  DEV = nil
6
6
 
7
7
  VERSION = [MAJOR, MINOR, BUGFIX].join(".") + (DEV ? ".pre#{DEV}" : '')
@@ -0,0 +1,45 @@
1
+
2
+ module OrigenTesters
3
+ # A base class that can be used to model command-based, rather than
4
+ # vector-based testers.
5
+ class CommandBasedTester
6
+ include VectorBasedTester
7
+
8
+ def initialize
9
+ @vector_based = false
10
+ end
11
+
12
+ # Write a string directly to the output file without being processed
13
+ # or modified in any way
14
+ def direct_write(str)
15
+ microcode str
16
+ end
17
+ alias_method :dw, :direct_write
18
+
19
+ # Concept of a cycle not supported, print out an error to the output
20
+ # file to alert the user that execution has hit code that is not
21
+ # compatible with a command based tester.
22
+ def cycle(*_args)
23
+ microcode '*** Cycle called ***'
24
+ end
25
+
26
+ # Concept of a subroutine not supported, print out an error to the output
27
+ # file to alert the user that execution has hit code that is not
28
+ # compatible with a command based tester.
29
+ def call_subroutine(sub)
30
+ microcode "Call_subroutine called to #{sub}"
31
+ end
32
+
33
+ def format_vector(vec)
34
+ vec.microcode
35
+ end
36
+
37
+ # Loop the content embedded in the supplied block
38
+ def loop(_name = nil, number_of_loops)
39
+ number_of_loops.times do
40
+ yield
41
+ end
42
+ end
43
+ alias_method :loop_vector, :loop
44
+ end
45
+ end
@@ -0,0 +1,69 @@
1
+ module OrigenTesters
2
+ class Doc
3
+ module Generator
4
+ class Flow
5
+ include OrigenTesters::Generator
6
+ include OrigenTesters::Generator::FlowControlAPI
7
+
8
+ OUTPUT_POSTFIX = 'flow'
9
+ OUTPUT_EXTENSION = 'yaml'
10
+
11
+ def add(type, options = {})
12
+ preserve_comments = options.delete(:preserve_comments)
13
+ line = track_relationships(options) do |options|
14
+ FlowLine.new(type, options)
15
+ end
16
+ collection << line unless Origen.interface.resources_mode?
17
+ if preserve_comments
18
+ line.description = Origen.interface.doc_comments
19
+ else
20
+ line.description = Origen.interface.doc_comments_consume
21
+ end
22
+ line
23
+ end
24
+
25
+ def start_section(options = {})
26
+ l = FlowLine.new(:section_start, options)
27
+ if options[:name]
28
+ desc = [options[:name]]
29
+ else
30
+ desc = []
31
+ end
32
+ l.description = desc + Origen.interface.doc_comments_consume
33
+ collection << l
34
+ end
35
+
36
+ def stop_section(options = {})
37
+ collection << FlowLine.new(:section_stop, options)
38
+ end
39
+
40
+ def test(instance, options = {})
41
+ options = save_context(options)
42
+ add(:test, { test: instance }.merge(options))
43
+ end
44
+
45
+ def set_device(options = {})
46
+ add(:set_device, options)
47
+ end
48
+
49
+ def to_yaml(options = {})
50
+ collection.map { |l| l.to_yaml(options) }
51
+ end
52
+
53
+ def render(file, options = {})
54
+ options[:file] = file
55
+ add(:render, options)
56
+ end
57
+
58
+ def skip(identifier = nil, options = {})
59
+ identifier, options = nil, identifier if identifier.is_a?(Hash)
60
+ identifier = generate_unique_label(identifier)
61
+ options[:test] = identifier
62
+ add(:branch, options)
63
+ yield
64
+ add(:label, test: identifier)
65
+ end
66
+ end
67
+ end
68
+ end
69
+ end
@@ -0,0 +1,201 @@
1
+ module OrigenTesters
2
+ class Doc
3
+ module Generator
4
+ class FlowLine
5
+ attr_accessor :type, :id, :test, :context, :attributes, :description
6
+
7
+ def initialize(type, attrs = {})
8
+ @type = type
9
+ @test = attrs.delete(:test)
10
+ @context = {}
11
+ @attributes = {}
12
+ flow_control_options = Origen.interface.extract_flow_control_options!(attrs)
13
+ flow_control_options.each do |opt, val|
14
+ send("#{opt}=", val)
15
+ end
16
+ attrs.each do |attribute, val|
17
+ @attributes[attribute] = val
18
+ end
19
+ end
20
+
21
+ def to_yaml(options = {})
22
+ options = {
23
+ include_descriptions: true
24
+ }.merge(options)
25
+ y = {
26
+ 'type' => @type,
27
+ 'description' => description,
28
+ 'instance' => test_to_yaml(options),
29
+ 'flow' => {
30
+ 'attributes' => attributes_to_yaml(options),
31
+ 'context' => context_to_yaml(options)
32
+ }
33
+ }
34
+ y.delete('description') unless options[:include_descriptions]
35
+ y
36
+ end
37
+
38
+ def attributes_to_yaml(_options = {})
39
+ a = {}
40
+ @attributes.each do |name, val|
41
+ a[name.to_s] = val if val
42
+ end
43
+ a
44
+ end
45
+
46
+ def context_to_yaml(_options = {})
47
+ # Turn attribute keys into strings for prettier yaml, this includes all
48
+ # relationship meta data
49
+ c = @context.reduce({}) { |memo, (k, v)| memo[k.to_s] = v; memo }
50
+ # Now add job/enable word data
51
+ if @enable
52
+ c['if_enable'] = @enable
53
+ end
54
+ if @unless_enable
55
+ c['unless_enable'] = @unless_enable
56
+ end
57
+ unless if_jobs.empty?
58
+ c['if_jobs'] = if_jobs
59
+ end
60
+ unless unless_jobs.empty?
61
+ c['unless_jobs'] = unless_jobs
62
+ end
63
+ c
64
+ end
65
+
66
+ def test_to_yaml(options = {})
67
+ if @test
68
+ if @test.is_a?(String) || @test.is_a?(Symbol)
69
+ {
70
+ 'attributes' => {
71
+ 'name' => @test.to_s
72
+ }
73
+ }
74
+ else
75
+ @test.to_yaml(options)
76
+ end
77
+ end
78
+ end
79
+
80
+ def method_missing(method, *args, &_block)
81
+ method = method.to_s
82
+ if method.gsub!('=', '')
83
+ @attributes[method] = args.first
84
+ else
85
+ @attributes[method]
86
+ end
87
+ end
88
+
89
+ def job
90
+ if !if_jobs.empty? && !unless_jobs.empty?
91
+ fail "Both if and unless jobs have been defined for test: #{parameter}"
92
+ elsif !if_jobs.empty?
93
+ if_jobs.join(',')
94
+ elsif !unless_jobs.empty?
95
+ unless_jobs.map { |j| "!#{j}" }.join(',')
96
+ else
97
+ ''
98
+ end
99
+ end
100
+ alias_method :jobs, :job
101
+
102
+ def if_jobs
103
+ @if_jobs ||= []
104
+ end
105
+
106
+ def unless_jobs
107
+ @unless_jobs ||= []
108
+ end
109
+
110
+ def if_enable=(val)
111
+ @enable = val
112
+ end
113
+ alias_method :enable=, :if_enable=
114
+ alias_method :if_enabled=, :if_enable=
115
+
116
+ def unless_enable=(val)
117
+ @unless_enable = val
118
+ end
119
+ alias_method :unless_enabled=, :unless_enable=
120
+
121
+ def if_job=(jobs)
122
+ [jobs].flatten.compact.each do |job|
123
+ job = job.to_s.upcase
124
+ if job =~ /!/
125
+ self.unless_job = job
126
+ else
127
+ if_jobs << job unless if_jobs.include?(job)
128
+ end
129
+ end
130
+ end
131
+ alias_method :if_jobs=, :if_job=
132
+ alias_method :add_if_jobs, :if_job=
133
+ alias_method :add_if_job, :if_job=
134
+
135
+ def unless_job=(jobs)
136
+ [jobs].flatten.compact.each do |job|
137
+ job = job.to_s.upcase
138
+ job.gsub!('!', '')
139
+ unless_jobs << job unless unless_jobs.include?(job)
140
+ end
141
+ end
142
+ alias_method :unless_jobs=, :unless_job=
143
+ alias_method :add_unless_jobs, :unless_job=
144
+ alias_method :add_unless_job, :unless_job=
145
+
146
+ def run_if_failed(id)
147
+ @context[:if_failed] = id
148
+ end
149
+
150
+ def run_if_passed(id)
151
+ @context[:if_passed] = id
152
+ end
153
+
154
+ def run_if_ran(id)
155
+ @context[:if_ran] = id
156
+ end
157
+
158
+ def run_unless_ran(id)
159
+ @context[:unless_ran] = id
160
+ end
161
+
162
+ def run_if_any_passed(parent)
163
+ @context[:if_any_passed] = parent.id
164
+ end
165
+
166
+ def run_if_all_passed(parent)
167
+ @context[:if_all_passed] = parent.id
168
+ end
169
+
170
+ def run_if_any_failed(parent)
171
+ @context[:if_any_failed] = parent.id
172
+ end
173
+
174
+ def run_if_all_failed(parent)
175
+ @context[:if_all_failed] = parent.id
176
+ end
177
+
178
+ def continue_on_fail
179
+ @attributes[:continue] = true
180
+ end
181
+
182
+ def id
183
+ @id || "#{parameter}_#{unique_counter}"
184
+ end
185
+
186
+ def unique_counter
187
+ @unique_counter ||= self.class.unique_counter
188
+ end
189
+
190
+ def self.unique_counter
191
+ @ix ||= -1
192
+ @ix += 1
193
+ end
194
+
195
+ def test?
196
+ @type == :test
197
+ end
198
+ end
199
+ end
200
+ end
201
+ end
@@ -0,0 +1,66 @@
1
+ module OrigenTesters
2
+ class Doc
3
+ module Generator
4
+ class Test
5
+ attr_accessor :name, :index, :version, :append_version, :attributes
6
+
7
+ def initialize(name, attrs = {})
8
+ attrs = {}.merge(attrs) # Important to keep this to clone the original options
9
+ # so that the caller's copy if not affected by stripping
10
+ # out the flow/relation options
11
+ @attributes = {}
12
+ @append_version = true
13
+ self.name = name
14
+ Origen.interface.extract_relation_options!(attrs)
15
+ Origen.interface.extract_flow_control_options!(attrs)
16
+ attrs.each do |attribute, val|
17
+ @attributes[attribute] = val
18
+ end
19
+ end
20
+
21
+ def to_yaml(options = {})
22
+ {
23
+ 'attributes' => attributes_to_yaml(options)
24
+ }
25
+ end
26
+
27
+ def attributes_to_yaml(_options = {})
28
+ a = {}
29
+ @attributes.each do |name, val|
30
+ a[name.to_s] = val if val
31
+ end
32
+ a['name'] = name
33
+ a
34
+ end
35
+
36
+ def method_missing(method, *args, &_block)
37
+ method = method.to_s
38
+ if method.gsub!('=', '')
39
+ @attributes[method] = args.first
40
+ else
41
+ @attributes[method]
42
+ end
43
+ end
44
+
45
+ def ==(other_test)
46
+ self.class == other_test.class &&
47
+ unversioned_name.to_s == other_test.unversioned_name.to_s &&
48
+ attributes.size == other_test.attributes.size &&
49
+ attributes.all? { |name, val| other_test.attributes[name] == val }
50
+ end
51
+
52
+ def name
53
+ if version && @append_version
54
+ "#{@name}_v#{version}"
55
+ else
56
+ @name.to_s
57
+ end
58
+ end
59
+
60
+ def unversioned_name
61
+ @name.to_s
62
+ end
63
+ end
64
+ end
65
+ end
66
+ end
@@ -0,0 +1,64 @@
1
+ module OrigenTesters
2
+ class Doc
3
+ module Generator
4
+ class TestGroup
5
+ attr_accessor :name, :version, :append_version
6
+
7
+ include Enumerable
8
+
9
+ def initialize(name, _options = {})
10
+ @name = name
11
+ @store = []
12
+ @append_version = true
13
+ end
14
+
15
+ def name
16
+ if unversioned_name
17
+ if version && @append_version
18
+ "#{unversioned_name}_v#{version}"
19
+ else
20
+ unversioned_name.to_s
21
+ end
22
+ end
23
+ end
24
+
25
+ def to_yaml(options = {})
26
+ y = {}
27
+ y['group'] = @store.map { |t| t.to_yaml(options) }
28
+ y
29
+ end
30
+
31
+ def unversioned_name
32
+ if @name
33
+ if @name =~ /grp$/
34
+ @name
35
+ else
36
+ "#{@name}_grp"
37
+ end
38
+ end
39
+ end
40
+
41
+ def <<(instance)
42
+ @store << instance
43
+ end
44
+
45
+ def size
46
+ @store.size
47
+ end
48
+
49
+ def each
50
+ @store.each { |ins| yield ins }
51
+ end
52
+
53
+ def ==(other_instance_group)
54
+ self.class == other_instance_group.class &&
55
+ unversioned_name.to_s == other_instance_group.unversioned_name.to_s &&
56
+ size == other_instance_group.size &&
57
+ self.all? do |ins|
58
+ other_instance_group.any? { |other_ins| ins == other_ins }
59
+ end
60
+ end
61
+ end
62
+ end
63
+ end
64
+ end
@@ -0,0 +1,45 @@
1
+ module OrigenTesters
2
+ class Doc
3
+ module Generator
4
+ class Tests
5
+ attr_accessor :collection
6
+
7
+ def initialize
8
+ @collection = []
9
+ end
10
+
11
+ class IndexedString < ::String
12
+ attr_accessor :index
13
+
14
+ def name
15
+ self
16
+ end
17
+ end
18
+
19
+ def add(name, attrs = {})
20
+ test = Test.new(name, attrs)
21
+ if @current_group
22
+ @current_group << test
23
+ else
24
+ collection << test
25
+ end
26
+ test
27
+ end
28
+
29
+ # Arbitrarily group a subset of tests together, see the J750 API for details on how to use
30
+ # this.
31
+ def group(name = nil, options = {})
32
+ name, options = nil, name if name.is_a?(Hash)
33
+ @current_group = TestGroup.new(name, options)
34
+ collection << @current_group
35
+ yield @current_group
36
+ @current_group = nil
37
+ end
38
+ alias_method :add_group, :group
39
+
40
+ def render(_file, _options = {})
41
+ end
42
+ end
43
+ end
44
+ end
45
+ end
@@ -0,0 +1,124 @@
1
+ require 'active_support/concern'
2
+
3
+ module OrigenTesters
4
+ class Doc
5
+ module Generator
6
+ extend ActiveSupport::Concern
7
+
8
+ autoload :Test, 'origen_testers/doc/generator/test'
9
+ autoload :TestGroup, 'origen_testers/doc/generator/test_group'
10
+ autoload :Tests, 'origen_testers/doc/generator/tests'
11
+ autoload :Flow, 'origen_testers/doc/generator/flow'
12
+ autoload :FlowLine, 'origen_testers/doc/generator/flow_line'
13
+ autoload :Placeholder, 'origen_testers/generator/placeholder'
14
+
15
+ included do
16
+ include OrigenTesters::Interface # adds the interface helpers/Origen hook-up
17
+ include OrigenTesters::Generator::FlowControlAPI::Interface
18
+ PLATFORM = OrigenTesters::Doc
19
+ end
20
+
21
+ # Returns the current flow (as defined by the name of the current top
22
+ # level flow source file).
23
+ #
24
+ # Pass in a filename argument to have a specific flow returned instead.
25
+ #
26
+ # If the flow does not exist yet it will be created.
27
+ def flow(filename = nil)
28
+ unless filename
29
+ if Origen.file_handler.current_file
30
+ filename = Origen.file_handler.current_file.basename('.rb').to_s
31
+ else
32
+ filename = 'anonymous'
33
+ end
34
+ end
35
+ f = filename.to_sym
36
+ return flows[f] if flows[f]
37
+ p = Flow.new
38
+ p.inhibit_output if Origen.interface.resources_mode?
39
+ p.filename = f
40
+ flows[f] = p
41
+ end
42
+
43
+ # @api private
44
+ def at_flow_start
45
+ end
46
+
47
+ # @api private
48
+ def at_run_start
49
+ flow.at_run_start
50
+ @@tests = nil
51
+ @@flows = nil
52
+ end
53
+ alias_method :reset_globals, :at_run_start
54
+
55
+ # Returns a container for all generated tests.
56
+ def tests
57
+ @@tests ||= Tests.new
58
+ end
59
+ alias_method :test_instances, :tests
60
+
61
+ # Returns a hash containing all flows
62
+ def flows
63
+ @@flows ||= {}
64
+ end
65
+
66
+ # Returns an array containing all sheet generators where a sheet generator is a flow,
67
+ # test instance, patset or pat group sheet.
68
+ # All Origen program generators must implement this method
69
+ def sheet_generators # :nodoc:
70
+ g = []
71
+ [flows].each do |sheets|
72
+ sheets.each do |_name, sheet|
73
+ g << sheet
74
+ end
75
+ end
76
+ g
77
+ end
78
+
79
+ # Returns an array containing all flow generators.
80
+ # All Origen program generators must implement this method
81
+ def flow_generators
82
+ g = []
83
+ flows.each do |_name, sheet|
84
+ g << sheet
85
+ end
86
+ g
87
+ end
88
+
89
+ # The source of all program files is passed in here before executing.
90
+ # This will replace all comments with a method call containing the comment so that
91
+ # they can be captured.
92
+ def filter_source(source) # :nodoc:
93
+ src = ''
94
+ source.split(/\r?\n/).each do |line|
95
+ if line !~ /^\s*#-/ && line =~ /^\s*#(.*)/
96
+ comment = Regexp.last_match[1].gsub("'", "\\\\'")
97
+ src << "Origen.interface.doc_comments_capture('#{comment}')\n"
98
+ else
99
+ src << "#{line}\n"
100
+ end
101
+ end
102
+ src
103
+ end
104
+
105
+ def doc_comments_capture(comment)
106
+ doc_comments << "#{comment}"
107
+ end
108
+
109
+ def doc_comments
110
+ @doc_comments ||= []
111
+ end
112
+
113
+ def doc_comments_consume
114
+ c = doc_comments
115
+ doc_comments_discard
116
+ c
117
+ end
118
+
119
+ def doc_comments_discard
120
+ @doc_comments = []
121
+ end
122
+ end
123
+ end
124
+ end