origen 0.0.1 → 0.0.2
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 +4 -4
- data/bin/ctags +0 -0
- data/bin/origen +165 -1
- data/bin/rgen +2 -0
- data/config/application.rb +141 -0
- data/config/commands.rb +72 -0
- data/config/development.rb +7 -0
- data/config/environment.rb +0 -0
- data/config/rgen.policy +7 -0
- data/config/rubocop/easy.yml +620 -0
- data/config/rubocop/easy_disabled.yml +271 -0
- data/config/rubocop/easy_enabled.yml +731 -0
- data/config/rubocop/strict.yml +620 -0
- data/config/rubocop/strict_disabled.yml +247 -0
- data/config/rubocop/strict_enabled.yml +755 -0
- data/config/users.rb +20 -0
- data/config/version.rb +1 -1
- data/helpers/url.rb +68 -0
- data/lib/c99/doc_interface.rb +56 -0
- data/lib/c99/j750_interface.rb +85 -0
- data/lib/c99/nvm.rb +89 -0
- data/lib/c99/target/mock2.rb +1 -0
- data/lib/c99/target/subdir/mock3.rb +1 -0
- data/lib/option_parser/optparse.rb +12 -0
- data/lib/origen/acronyms.rb +60 -0
- data/lib/origen/application/command_dispatcher.rb +12 -0
- data/lib/origen/application/configuration.rb +206 -0
- data/lib/origen/application/configuration_manager.rb +78 -0
- data/lib/origen/application/deployer.rb +367 -0
- data/lib/origen/application/environment.rb +186 -0
- data/lib/origen/application/lsf.rb +145 -0
- data/lib/origen/application/lsf_manager.rb +657 -0
- data/lib/origen/application/plugins_manager.rb +280 -0
- data/lib/origen/application/release.rb +359 -0
- data/lib/origen/application/runner.rb +246 -0
- data/lib/origen/application/statistics.rb +191 -0
- data/lib/origen/application/target.rb +374 -0
- data/lib/origen/application/version_tracker.rb +59 -0
- data/lib/origen/application/workspace_manager.rb +151 -0
- data/lib/origen/application.rb +746 -0
- data/lib/origen/bugs/bug.rb +36 -0
- data/lib/origen/bugs.rb +45 -0
- data/lib/origen/callbacks.rb +35 -0
- data/lib/origen/chip_mode.rb +118 -0
- data/lib/origen/chip_package.rb +461 -0
- data/lib/origen/client.rb +87 -0
- data/lib/origen/code_generators/actions.rb +258 -0
- data/lib/origen/code_generators/base.rb +57 -0
- data/lib/origen/code_generators/bundler.rb +17 -0
- data/lib/origen/code_generators/gem_setup.rb +49 -0
- data/lib/origen/code_generators/rake.rb +13 -0
- data/lib/origen/code_generators/rspec.rb +12 -0
- data/lib/origen/code_generators/semver.rb +39 -0
- data/lib/origen/code_generators/timever.rb +37 -0
- data/lib/origen/code_generators.rb +111 -0
- data/lib/origen/commands/add.rb +12 -0
- data/lib/origen/commands/compile.rb +62 -0
- data/lib/origen/commands/ctags.rb +9 -0
- data/lib/origen/commands/dispatch.rb +22 -0
- data/lib/origen/commands/environment.rb +11 -0
- data/lib/origen/commands/fetch.rb +63 -0
- data/lib/origen/commands/generate.rb +130 -0
- data/lib/origen/commands/interactive.rb +73 -0
- data/lib/origen/commands/lint.rb +82 -0
- data/lib/origen/commands/lsf.rb +93 -0
- data/lib/origen/commands/merge.rb +55 -0
- data/lib/origen/commands/modifications.rb +12 -0
- data/lib/origen/commands/new.rb +113 -0
- data/lib/origen/commands/plugin.rb +105 -0
- data/lib/origen/commands/program.rb +70 -0
- data/lib/origen/commands/rc.rb +442 -0
- data/lib/origen/commands/save.rb +56 -0
- data/lib/origen/commands/target.rb +27 -0
- data/lib/origen/commands/time.rb +127 -0
- data/lib/origen/commands/version.rb +17 -0
- data/lib/origen/commands/web.rb +221 -0
- data/lib/origen/commands.rb +272 -0
- data/lib/origen/commands_global.rb +76 -0
- data/lib/origen/controller.rb +94 -0
- data/lib/origen/core_ext/array.rb +23 -0
- data/lib/origen/core_ext/bignum.rb +36 -0
- data/lib/origen/core_ext/enumerable.rb +76 -0
- data/lib/origen/core_ext/fixnum.rb +46 -0
- data/lib/origen/core_ext/hash.rb +52 -0
- data/lib/origen/core_ext/module.rb +14 -0
- data/lib/origen/core_ext/numeric.rb +126 -0
- data/lib/origen/core_ext/object.rb +13 -0
- data/lib/origen/core_ext/range.rb +7 -0
- data/lib/origen/core_ext/string.rb +124 -0
- data/lib/origen/core_ext.rb +10 -0
- data/lib/origen/database/key_value_store.rb +111 -0
- data/lib/origen/database/key_value_stores.rb +108 -0
- data/lib/origen/database.rb +6 -0
- data/lib/origen/encodings.rb +102 -0
- data/lib/origen/features/feature.rb +22 -0
- data/lib/origen/features.rb +104 -0
- data/lib/origen/file_handler.rb +429 -0
- data/lib/origen/generator/comparator.rb +56 -0
- data/lib/origen/generator/compiler.rb +277 -0
- data/lib/origen/generator/flow.rb +49 -0
- data/lib/origen/generator/job.rb +131 -0
- data/lib/origen/generator/pattern.rb +356 -0
- data/lib/origen/generator/pattern_finder.rb +155 -0
- data/lib/origen/generator/pattern_iterator.rb +55 -0
- data/lib/origen/generator/renderer.rb +113 -0
- data/lib/origen/generator/resources.rb +40 -0
- data/lib/origen/generator/stage.rb +89 -0
- data/lib/origen/generator.rb +85 -0
- data/lib/origen/global_methods.rb +205 -0
- data/lib/origen/import_manager.rb +596 -0
- data/lib/origen/location/base.rb +116 -0
- data/lib/origen/location/map.rb +83 -0
- data/lib/origen/location.rb +6 -0
- data/lib/origen/log.rb +217 -0
- data/lib/origen/logger_methods.rb +56 -0
- data/lib/origen/mode.rb +61 -0
- data/lib/origen/model.rb +267 -0
- data/lib/origen/model_initializer.rb +45 -0
- data/lib/origen/nvm/block_array.rb +72 -0
- data/lib/origen/nvm.rb +6 -0
- data/lib/origen/parameters/live.rb +22 -0
- data/lib/origen/parameters/missing.rb +28 -0
- data/lib/origen/parameters/set.rb +144 -0
- data/lib/origen/parameters.rb +107 -0
- data/lib/origen/pdm.rb +218 -0
- data/lib/origen/pins/function_proxy.rb +36 -0
- data/lib/origen/pins/ground_pin.rb +6 -0
- data/lib/origen/pins/pin.rb +860 -0
- data/lib/origen/pins/pin_bank.rb +349 -0
- data/lib/origen/pins/pin_clock.rb +124 -0
- data/lib/origen/pins/pin_collection.rb +492 -0
- data/lib/origen/pins/pin_common.rb +206 -0
- data/lib/origen/pins/port.rb +268 -0
- data/lib/origen/pins/power_pin.rb +30 -0
- data/lib/origen/pins.rb +696 -0
- data/lib/origen/registers/bit.rb +562 -0
- data/lib/origen/registers/bit_collection.rb +787 -0
- data/lib/origen/registers/container.rb +288 -0
- data/lib/origen/registers/domain.rb +16 -0
- data/lib/origen/registers/reg.rb +1406 -0
- data/lib/origen/registers/reg_collection.rb +24 -0
- data/lib/origen/registers.rb +652 -0
- data/lib/origen/regression_manager.rb +251 -0
- data/lib/origen/remote_manager.rb +340 -0
- data/lib/origen/revision_control/base.rb +257 -0
- data/lib/origen/revision_control/design_sync.rb +276 -0
- data/lib/origen/revision_control/git.rb +243 -0
- data/lib/origen/revision_control/subversion.rb +6 -0
- data/lib/origen/revision_control.rb +44 -0
- data/lib/origen/ruby_version_check.rb +131 -0
- data/lib/origen/site_config.rb +61 -0
- data/lib/origen/specs/checkers.rb +103 -0
- data/lib/origen/specs/creation_info.rb +17 -0
- data/lib/origen/specs/doc_resource.rb +91 -0
- data/lib/origen/specs/exhibit.rb +17 -0
- data/lib/origen/specs/mode_select.rb +16 -0
- data/lib/origen/specs/note.rb +17 -0
- data/lib/origen/specs/override.rb +21 -0
- data/lib/origen/specs/power_supply.rb +13 -0
- data/lib/origen/specs/spec.rb +226 -0
- data/lib/origen/specs/version_history.rb +14 -0
- data/lib/origen/specs.rb +552 -0
- data/lib/origen/sub_blocks.rb +298 -0
- data/lib/origen/tester/api.rb +277 -0
- data/lib/origen/tester/bdm/bdm.rb +25 -0
- data/lib/origen/tester/command_based_tester.rb +46 -0
- data/lib/origen/tester/doc/doc.rb +226 -0
- data/lib/origen/tester/doc/generator/flow.rb +71 -0
- data/lib/origen/tester/doc/generator/flow_line.rb +203 -0
- data/lib/origen/tester/doc/generator/test.rb +68 -0
- data/lib/origen/tester/doc/generator/test_group.rb +66 -0
- data/lib/origen/tester/doc/generator/tests.rb +47 -0
- data/lib/origen/tester/doc/generator.rb +126 -0
- data/lib/origen/tester/doc/model.rb +162 -0
- data/lib/origen/tester/generator/flow_control_api.rb +606 -0
- data/lib/origen/tester/generator/identity_map.rb +25 -0
- data/lib/origen/tester/generator/placeholder.rb +13 -0
- data/lib/origen/tester/generator/test_numberer.rb +25 -0
- data/lib/origen/tester/generator.rb +271 -0
- data/lib/origen/tester/interface.rb +154 -0
- data/lib/origen/tester/j750/files.rb +45 -0
- data/lib/origen/tester/j750/generator/flow.rb +123 -0
- data/lib/origen/tester/j750/generator/flow_line.rb +288 -0
- data/lib/origen/tester/j750/generator/patgroup.rb +111 -0
- data/lib/origen/tester/j750/generator/patgroups.rb +41 -0
- data/lib/origen/tester/j750/generator/patset.rb +111 -0
- data/lib/origen/tester/j750/generator/patsets.rb +41 -0
- data/lib/origen/tester/j750/generator/templates/flow.txt.erb +9 -0
- data/lib/origen/tester/j750/generator/templates/instances.txt.erb +16 -0
- data/lib/origen/tester/j750/generator/templates/patgroups.txt.erb +8 -0
- data/lib/origen/tester/j750/generator/templates/patsets.txt.erb +10 -0
- data/lib/origen/tester/j750/generator/test_instance.rb +846 -0
- data/lib/origen/tester/j750/generator/test_instance_group.rb +60 -0
- data/lib/origen/tester/j750/generator/test_instances.rb +182 -0
- data/lib/origen/tester/j750/generator.rb +203 -0
- data/lib/origen/tester/j750/j750.rb +845 -0
- data/lib/origen/tester/j750/j750_hpt.rb +35 -0
- data/lib/origen/tester/j750/parser/ac_spec.rb +11 -0
- data/lib/origen/tester/j750/parser/ac_specs.rb +0 -0
- data/lib/origen/tester/j750/parser/dc_spec.rb +36 -0
- data/lib/origen/tester/j750/parser/dc_specs.rb +50 -0
- data/lib/origen/tester/j750/parser/descriptions.rb +340 -0
- data/lib/origen/tester/j750/parser/flow.rb +111 -0
- data/lib/origen/tester/j750/parser/flow_line.rb +207 -0
- data/lib/origen/tester/j750/parser/flows.rb +23 -0
- data/lib/origen/tester/j750/parser/pattern_set.rb +94 -0
- data/lib/origen/tester/j750/parser/pattern_sets.rb +33 -0
- data/lib/origen/tester/j750/parser/test_instance.rb +322 -0
- data/lib/origen/tester/j750/parser/test_instances.rb +26 -0
- data/lib/origen/tester/j750/parser/timeset.rb +15 -0
- data/lib/origen/tester/j750/parser/timesets.rb +0 -0
- data/lib/origen/tester/j750/parser.rb +104 -0
- data/lib/origen/tester/jlink/jlink.rb +33 -0
- data/lib/origen/tester/parser/description_lookup.rb +64 -0
- data/lib/origen/tester/parser/searchable_array.rb +32 -0
- data/lib/origen/tester/parser/searchable_hash.rb +32 -0
- data/lib/origen/tester/parser.rb +24 -0
- data/lib/origen/tester/time.rb +338 -0
- data/lib/origen/tester/timing.rb +253 -0
- data/lib/origen/tester/ultraflex/files.rb +45 -0
- data/lib/origen/tester/ultraflex/generator/flow.rb +119 -0
- data/lib/origen/tester/ultraflex/generator/flow_line.rb +269 -0
- data/lib/origen/tester/ultraflex/generator/patgroup.rb +111 -0
- data/lib/origen/tester/ultraflex/generator/patgroups.rb +41 -0
- data/lib/origen/tester/ultraflex/generator/patset.rb +111 -0
- data/lib/origen/tester/ultraflex/generator/patsets.rb +41 -0
- data/lib/origen/tester/ultraflex/generator/templates/flow.txt.erb +9 -0
- data/lib/origen/tester/ultraflex/generator/templates/instances.txt.erb +16 -0
- data/lib/origen/tester/ultraflex/generator/templates/patgroups.txt.erb +8 -0
- data/lib/origen/tester/ultraflex/generator/templates/patsets.txt.erb +10 -0
- data/lib/origen/tester/ultraflex/generator/test_instance.rb +622 -0
- data/lib/origen/tester/ultraflex/generator/test_instance_group.rb +60 -0
- data/lib/origen/tester/ultraflex/generator/test_instances.rb +174 -0
- data/lib/origen/tester/ultraflex/generator.rb +200 -0
- data/lib/origen/tester/ultraflex/parser/ac_spec.rb +11 -0
- data/lib/origen/tester/ultraflex/parser/ac_specs.rb +0 -0
- data/lib/origen/tester/ultraflex/parser/dc_spec.rb +36 -0
- data/lib/origen/tester/ultraflex/parser/dc_specs.rb +50 -0
- data/lib/origen/tester/ultraflex/parser/descriptions.rb +342 -0
- data/lib/origen/tester/ultraflex/parser/flow.rb +111 -0
- data/lib/origen/tester/ultraflex/parser/flow_line.rb +207 -0
- data/lib/origen/tester/ultraflex/parser/flows.rb +23 -0
- data/lib/origen/tester/ultraflex/parser/pattern_set.rb +94 -0
- data/lib/origen/tester/ultraflex/parser/pattern_sets.rb +33 -0
- data/lib/origen/tester/ultraflex/parser/test_instance.rb +262 -0
- data/lib/origen/tester/ultraflex/parser/test_instances.rb +26 -0
- data/lib/origen/tester/ultraflex/parser/timeset.rb +15 -0
- data/lib/origen/tester/ultraflex/parser/timesets.rb +0 -0
- data/lib/origen/tester/ultraflex/parser.rb +104 -0
- data/lib/origen/tester/ultraflex/ultraflex.rb +759 -0
- data/lib/origen/tester/v93k/generator/flow.rb +63 -0
- data/lib/origen/tester/v93k/generator/flow_node/print.rb +10 -0
- data/lib/origen/tester/v93k/generator/flow_node.rb +17 -0
- data/lib/origen/tester/v93k/generator/pattern.rb +16 -0
- data/lib/origen/tester/v93k/generator/pattern_master.rb +54 -0
- data/lib/origen/tester/v93k/generator/templates/_test_method.txt.erb +6 -0
- data/lib/origen/tester/v93k/generator/templates/_test_suite.txt.erb +11 -0
- data/lib/origen/tester/v93k/generator/templates/template.flow.erb +121 -0
- data/lib/origen/tester/v93k/generator/templates/template.pmfl.erb +9 -0
- data/lib/origen/tester/v93k/generator/test_function.rb +103 -0
- data/lib/origen/tester/v93k/generator/test_functions.rb +79 -0
- data/lib/origen/tester/v93k/generator/test_method.rb +46 -0
- data/lib/origen/tester/v93k/generator/test_methods.rb +75 -0
- data/lib/origen/tester/v93k/generator/test_suite.rb +54 -0
- data/lib/origen/tester/v93k/generator/test_suites.rb +65 -0
- data/lib/origen/tester/v93k/generator.rb +80 -0
- data/lib/origen/tester/v93k/v93k.rb +420 -0
- data/lib/origen/tester/vector.rb +86 -0
- data/lib/origen/tester/vector_generator.rb +633 -0
- data/lib/origen/tester/vector_pipeline.rb +150 -0
- data/lib/origen/tester.rb +56 -0
- data/lib/origen/top_level.rb +134 -0
- data/lib/origen/users/ldap.rb +65 -0
- data/lib/origen/users/user.rb +149 -0
- data/lib/origen/users.rb +30 -0
- data/lib/origen/utility/block_args.rb +93 -0
- data/lib/origen/utility/csv_data.rb +110 -0
- data/lib/origen/utility/design_sync.rb +494 -0
- data/lib/origen/utility/diff.rb +158 -0
- data/lib/origen/utility/input_capture.rb +121 -0
- data/lib/origen/utility/mailer.rb +143 -0
- data/lib/origen/utility/s_record.rb +205 -0
- data/lib/origen/utility/time_and_date.rb +30 -0
- data/lib/origen/utility.rb +12 -0
- data/lib/origen/version_checker.rb +117 -0
- data/lib/origen/version_string.rb +356 -0
- data/lib/origen.rb +648 -0
- data/lib/tasks/gem.rake +27 -22
- data/origen_site_config.yml +36 -0
- data/source_setup +17 -0
- data/spec/format/rgen_formatter.rb +14 -0
- data/templates/api_doc/README.txt.erb +24 -0
- data/templates/code_generators/gemfile_app.rb +4 -0
- data/templates/code_generators/gemfile_plugin.rb +6 -0
- data/templates/code_generators/gemspec.rb +33 -0
- data/templates/code_generators/rakefile.rb +10 -0
- data/templates/code_generators/spec_helper.rb +49 -0
- data/templates/code_generators/version.rb +8 -0
- data/templates/code_generators/version_time.rb +3 -0
- data/templates/git/gitignore.erb +33 -0
- data/templates/j750/_vt_flow.txt.erb +8 -0
- data/templates/j750/_vt_instances.txt.erb +4 -0
- data/templates/j750/program_sheet.txt.erb +9 -0
- data/templates/nanoc/Rules +74 -0
- data/templates/nanoc/config.yaml +77 -0
- data/templates/nanoc/content/favicon.ico +0 -0
- data/templates/nanoc/layouts/bootstrap.html.erb +63 -0
- data/templates/nanoc/layouts/bootstrap3.html.erb +71 -0
- data/templates/nanoc/layouts/freescale.html.erb +79 -0
- data/templates/nanoc/lib/bootstrap_filter.rb +49 -0
- data/templates/nanoc/lib/codeblocks_filter.rb +41 -0
- data/templates/nanoc/lib/default.rb +2 -0
- data/templates/nanoc/lib/gzip_filter.rb +16 -0
- data/templates/nanoc/lib/haml_code_filter.rb +41 -0
- data/templates/nanoc/lib/helpers.rb +1 -0
- data/templates/nanoc/lib/search_filter.rb +62 -0
- data/templates/nanoc_dynamic/content/search.js.erb +92 -0
- data/templates/shared/web/_logo.html +10 -0
- data/templates/test/_inline_sub.txt.erb +2 -0
- data/templates/test/environment.txt.erb +1 -0
- data/templates/test/inline.txt.erb +11 -0
- data/templates/test/inspections.txt.erb +19 -0
- data/templates/test/set1/_sub1.txt.erb +12 -0
- data/templates/test/set1/_sub4.txt.erb +1 -0
- data/templates/test/set1/_sub5.txt.erb +1 -0
- data/templates/test/set1/main.txt.erb +53 -0
- data/templates/test/set1/sub_dir/_sub2.txt.erb +20 -0
- data/templates/test/set1/sub_dir/_sub3.txt.erb +12 -0
- data/templates/test/set1/sub_dir/main2.txt.erb +4 -0
- data/templates/test/set2/template_with_no_erb_1.txt +9 -0
- data/templates/test/set2/template_with_no_erb_2.txt +9 -0
- data/templates/test/set3/_layout.html.erb +4 -0
- data/templates/test/set3/content.html.erb +6 -0
- data/templates/time/filter.rb.erb +15 -0
- data/templates/time/rules.rb.erb +45 -0
- metadata +639 -5
|
@@ -0,0 +1,271 @@
|
|
|
1
|
+
require 'active_support/concern'
|
|
2
|
+
require 'erb'
|
|
3
|
+
require 'yaml'
|
|
4
|
+
|
|
5
|
+
module Origen
|
|
6
|
+
module Tester
|
|
7
|
+
module Generator
|
|
8
|
+
autoload :Placeholder, 'origen/tester/generator/placeholder'
|
|
9
|
+
autoload :IdentityMap, 'origen/tester/generator/identity_map'
|
|
10
|
+
autoload :FlowControlAPI, 'origen/tester/generator/flow_control_api'
|
|
11
|
+
|
|
12
|
+
extend ActiveSupport::Concern
|
|
13
|
+
|
|
14
|
+
included do
|
|
15
|
+
include Origen::Generator::Comparator
|
|
16
|
+
end
|
|
17
|
+
|
|
18
|
+
# The program source files are executed by eval to allow the tester to filter the
|
|
19
|
+
# source contents before executing. For examples the doc tester replaces all comments
|
|
20
|
+
# with a method call containing each comment so that they can be captured.
|
|
21
|
+
def self.execute_source(file)
|
|
22
|
+
if Origen.tester.doc? && Origen.interface_loaded? && Origen.interface.respond_to?(:filter_source)
|
|
23
|
+
File.open(file) do |f|
|
|
24
|
+
src = f.read
|
|
25
|
+
src = Origen.interface.filter_source(src)
|
|
26
|
+
# With source file wrapping here to ensure that any calls to Origen.app! within
|
|
27
|
+
# the source code will evaluate to the correct app instance
|
|
28
|
+
Origen.with_source_file(file) do
|
|
29
|
+
eval(src, global_binding)
|
|
30
|
+
end
|
|
31
|
+
end
|
|
32
|
+
else
|
|
33
|
+
load file
|
|
34
|
+
end
|
|
35
|
+
end
|
|
36
|
+
|
|
37
|
+
# When called on a generater no output files will be created from it
|
|
38
|
+
def inhibit_output
|
|
39
|
+
@inhibit_output = true
|
|
40
|
+
end
|
|
41
|
+
|
|
42
|
+
# Returns true if the output files from this generator will be inhibited
|
|
43
|
+
def output_inhibited?
|
|
44
|
+
@inhibit_output
|
|
45
|
+
end
|
|
46
|
+
|
|
47
|
+
# Expands and inserts all render statements that have been encountered
|
|
48
|
+
def close(options = {})
|
|
49
|
+
Origen.profile "closing #{filename}" do
|
|
50
|
+
base_collection = collection
|
|
51
|
+
base_collection.each_with_index do |item, i|
|
|
52
|
+
if item.is_a? Placeholder
|
|
53
|
+
if item.type == :render
|
|
54
|
+
txt = ''
|
|
55
|
+
Origen.file_handler.preserve_current_file do
|
|
56
|
+
Origen.file_handler.default_extension = file_extension
|
|
57
|
+
placeholder = compiler.render(item.file, item.options)
|
|
58
|
+
txt = compiler.insert(placeholder).chomp
|
|
59
|
+
end
|
|
60
|
+
base_collection[i] = txt
|
|
61
|
+
else
|
|
62
|
+
fail 'Unknown placeholder encountered!'
|
|
63
|
+
end
|
|
64
|
+
end
|
|
65
|
+
end
|
|
66
|
+
@collection = base_collection.flatten.compact
|
|
67
|
+
on_close(options)
|
|
68
|
+
end
|
|
69
|
+
end
|
|
70
|
+
|
|
71
|
+
def file_pipeline
|
|
72
|
+
@@file_pipeline ||= []
|
|
73
|
+
end
|
|
74
|
+
|
|
75
|
+
# Returns the directory of the current source file being generated
|
|
76
|
+
def current_dir
|
|
77
|
+
if file_pipeline.empty?
|
|
78
|
+
Origen.file_handler.base_directory
|
|
79
|
+
else
|
|
80
|
+
Pathname.new(file_pipeline.last).dirname
|
|
81
|
+
end
|
|
82
|
+
end
|
|
83
|
+
|
|
84
|
+
# Redefine this in the parent which includes this module if you want anything to
|
|
85
|
+
# occur after closing the generator (expanding all render/import statements) but
|
|
86
|
+
# before writing to a file.
|
|
87
|
+
def on_close(_options = {})
|
|
88
|
+
end
|
|
89
|
+
|
|
90
|
+
# Redefine this in the parent which includes this module if you want anything to
|
|
91
|
+
# occur after all tests have been generated but before file writing starts.
|
|
92
|
+
def finalize(_options = {})
|
|
93
|
+
end
|
|
94
|
+
|
|
95
|
+
def compiler
|
|
96
|
+
Origen.generator.compiler
|
|
97
|
+
end
|
|
98
|
+
|
|
99
|
+
def filename=(name)
|
|
100
|
+
@filename = name
|
|
101
|
+
end
|
|
102
|
+
|
|
103
|
+
def filename(options = {})
|
|
104
|
+
options = {
|
|
105
|
+
include_extension: true
|
|
106
|
+
}.merge(options)
|
|
107
|
+
name = (@filename || Origen.file_handler.current_file.basename('.rb')).to_s
|
|
108
|
+
if Origen.config.program_prefix
|
|
109
|
+
unless name =~ /^#{Origen.config.program_prefix}/i
|
|
110
|
+
name = "#{Origen.config.program_prefix}_#{name}"
|
|
111
|
+
end
|
|
112
|
+
end
|
|
113
|
+
f = Pathname.new(name).basename
|
|
114
|
+
ext = f.extname.empty? ? file_extension : f.extname
|
|
115
|
+
body = f.basename(".#{ext}").to_s
|
|
116
|
+
body.gsub!('_resources', '')
|
|
117
|
+
if defined? self.class::OUTPUT_POSTFIX
|
|
118
|
+
# Unless the postfix is already in the name
|
|
119
|
+
unless body =~ /#{self.class::OUTPUT_POSTFIX}$/i
|
|
120
|
+
body = "#{body}_#{self.class::OUTPUT_POSTFIX}"
|
|
121
|
+
end
|
|
122
|
+
end
|
|
123
|
+
ext = ".#{ext}" unless ext =~ /^\./
|
|
124
|
+
if options[:include_extension]
|
|
125
|
+
"#{body}#{ext}"
|
|
126
|
+
else
|
|
127
|
+
"#{body}"
|
|
128
|
+
end
|
|
129
|
+
end
|
|
130
|
+
|
|
131
|
+
def dont_diff=(val)
|
|
132
|
+
@dont_diff = val
|
|
133
|
+
end
|
|
134
|
+
|
|
135
|
+
# All generators must implement a collection method that returns an
|
|
136
|
+
# array containing the generated items
|
|
137
|
+
def collection
|
|
138
|
+
@collection ||= []
|
|
139
|
+
end
|
|
140
|
+
|
|
141
|
+
def collection=(array)
|
|
142
|
+
@collection = array
|
|
143
|
+
end
|
|
144
|
+
|
|
145
|
+
def file_extension
|
|
146
|
+
if defined? self.class::OUTPUT_EXTENSION
|
|
147
|
+
self.class::OUTPUT_EXTENSION
|
|
148
|
+
elsif defined? self.class::TEMPLATE
|
|
149
|
+
p = Pathname.new(self.class::TEMPLATE)
|
|
150
|
+
ext = p.basename('.erb').extname
|
|
151
|
+
ext.empty? ? 'txt' : ext
|
|
152
|
+
else
|
|
153
|
+
'txt'
|
|
154
|
+
end
|
|
155
|
+
end
|
|
156
|
+
|
|
157
|
+
def write_to_file(options = {})
|
|
158
|
+
unless output_inhibited?
|
|
159
|
+
if defined? self.class::TEMPLATE || Origen.tester.is_a?(Origen::Tester::Doc)
|
|
160
|
+
write_from_template(options)
|
|
161
|
+
else
|
|
162
|
+
fail "Don't know hot to write without a template!"
|
|
163
|
+
end
|
|
164
|
+
stats.completed_files += 1
|
|
165
|
+
end
|
|
166
|
+
end
|
|
167
|
+
|
|
168
|
+
def write_from_template(options = {})
|
|
169
|
+
options = {
|
|
170
|
+
quiet: false,
|
|
171
|
+
skip_diff: false
|
|
172
|
+
}.merge(options)
|
|
173
|
+
unless output_inhibited?
|
|
174
|
+
# If this is not the first time we have written to the current output file
|
|
175
|
+
# then appen to it, otherwise clear it and start from scratch.
|
|
176
|
+
# The use of a class variable to store the opened files means that it will be
|
|
177
|
+
# shared by all generators in this run.
|
|
178
|
+
@@opened_files ||= []
|
|
179
|
+
if @@opened_files.include?(output_file) && !Origen.tester.is_a?(Origen::Tester::Doc)
|
|
180
|
+
@append = true
|
|
181
|
+
Origen.file_handler.preserve_state do
|
|
182
|
+
File.open(output_file, 'a') do |out|
|
|
183
|
+
content = compiler.insert(ERB.new(File.read(self.class::TEMPLATE), 0, Origen.config.erb_trim_mode).result(binding))
|
|
184
|
+
out.puts content unless content.empty?
|
|
185
|
+
end
|
|
186
|
+
end
|
|
187
|
+
Origen.log.info "Appending... #{output_file.basename}" unless options[:quiet]
|
|
188
|
+
else
|
|
189
|
+
@append = false
|
|
190
|
+
Origen.file_handler.preserve_state do
|
|
191
|
+
if Origen.tester.is_a?(Origen::Tester::Doc)
|
|
192
|
+
if options[:return_model]
|
|
193
|
+
Origen::Tester::Doc.model.add_flow(filename(include_extension: false), to_yaml)
|
|
194
|
+
else
|
|
195
|
+
Origen.file_handler.open_for_write(output_file) do |f|
|
|
196
|
+
f.puts YAML.dump(to_yaml(include_descriptions: false))
|
|
197
|
+
end
|
|
198
|
+
end
|
|
199
|
+
else
|
|
200
|
+
File.open(output_file, 'w') do |out|
|
|
201
|
+
out.puts compiler.insert(ERB.new(File.read(self.class::TEMPLATE), 0, Origen.config.erb_trim_mode).result(binding))
|
|
202
|
+
end
|
|
203
|
+
end
|
|
204
|
+
end
|
|
205
|
+
@@opened_files << output_file
|
|
206
|
+
Origen.log.info "Writing... #{output_file.basename}" unless options[:quiet]
|
|
207
|
+
end
|
|
208
|
+
if !@dont_diff && !options[:skip_diff] && !options[:quiet]
|
|
209
|
+
check_for_changes(output_file, reference_file,
|
|
210
|
+
compile_job: true,
|
|
211
|
+
comment_char: Origen.app.tester.program_comment_char)
|
|
212
|
+
end
|
|
213
|
+
end
|
|
214
|
+
end
|
|
215
|
+
|
|
216
|
+
def output_file
|
|
217
|
+
Pathname.new("#{Origen.file_handler.output_directory}/#{filename}")
|
|
218
|
+
end
|
|
219
|
+
|
|
220
|
+
def reference_file
|
|
221
|
+
Pathname.new("#{Origen.file_handler.reference_directory}/#{filename}")
|
|
222
|
+
end
|
|
223
|
+
|
|
224
|
+
def import(file, options = {})
|
|
225
|
+
file = Pathname.new(file).absolute? ? file : "#{current_dir}/#{file}"
|
|
226
|
+
file = Origen.file_handler.clean_path_to_sub_program(file)
|
|
227
|
+
base_collection = collection
|
|
228
|
+
@collection = []
|
|
229
|
+
Origen.generator.option_pipeline << options
|
|
230
|
+
file_pipeline << file
|
|
231
|
+
Origen::Tester::Generator.execute_source(file)
|
|
232
|
+
file_pipeline.pop
|
|
233
|
+
base_collection << @collection
|
|
234
|
+
@collection = base_collection.flatten
|
|
235
|
+
end
|
|
236
|
+
|
|
237
|
+
def render(file, options = {})
|
|
238
|
+
if options.delete(:_inline)
|
|
239
|
+
super Origen.file_handler.clean_path_to_sub_template(file), options
|
|
240
|
+
else
|
|
241
|
+
collection << Placeholder.new(:render, file, options)
|
|
242
|
+
end
|
|
243
|
+
end
|
|
244
|
+
|
|
245
|
+
def stats
|
|
246
|
+
Origen.app.stats
|
|
247
|
+
end
|
|
248
|
+
|
|
249
|
+
def to_be_written?
|
|
250
|
+
true
|
|
251
|
+
end
|
|
252
|
+
|
|
253
|
+
def set_flow_description(desc)
|
|
254
|
+
Origen.interface.descriptions.add_for_flow(output_file, desc)
|
|
255
|
+
end
|
|
256
|
+
|
|
257
|
+
def identity_map # :nodoc:
|
|
258
|
+
Origen.interface.identity_map
|
|
259
|
+
end
|
|
260
|
+
|
|
261
|
+
module ClassMethods
|
|
262
|
+
def new(*args, &block) # :nodoc:
|
|
263
|
+
x = allocate
|
|
264
|
+
x.send(:initialize, *args, &block)
|
|
265
|
+
Origen.interface.sheet_generators << x
|
|
266
|
+
x
|
|
267
|
+
end
|
|
268
|
+
end
|
|
269
|
+
end
|
|
270
|
+
end
|
|
271
|
+
end
|
|
@@ -0,0 +1,154 @@
|
|
|
1
|
+
require 'active_support/concern'
|
|
2
|
+
|
|
3
|
+
module Origen
|
|
4
|
+
module Tester
|
|
5
|
+
# Include this module in any class you define as a test interface
|
|
6
|
+
module Interface
|
|
7
|
+
extend ActiveSupport::Concern
|
|
8
|
+
|
|
9
|
+
included do
|
|
10
|
+
Origen.add_interface(self)
|
|
11
|
+
end
|
|
12
|
+
|
|
13
|
+
# This identifier will be used to make labels and other references unique to the
|
|
14
|
+
# current application. This will help to avoid name duplication if a program is
|
|
15
|
+
# comprised of many modules generated by Origen.
|
|
16
|
+
#
|
|
17
|
+
# Override in the application interface to customize, by default the identifier
|
|
18
|
+
# will be Origen.config.initials
|
|
19
|
+
def app_identifier
|
|
20
|
+
Origen.config.initials || 'Anon App'
|
|
21
|
+
end
|
|
22
|
+
|
|
23
|
+
def close(options = {})
|
|
24
|
+
sheet_generators.each do |generator|
|
|
25
|
+
generator.close(options)
|
|
26
|
+
end
|
|
27
|
+
end
|
|
28
|
+
|
|
29
|
+
# Compile a template file
|
|
30
|
+
def compile(file, options = {})
|
|
31
|
+
Origen.file_handler.preserve_state do
|
|
32
|
+
begin
|
|
33
|
+
file = Origen.file_handler.clean_path_to_template(file)
|
|
34
|
+
Origen.generator.compile_file_or_directory(file, initial_options: options)
|
|
35
|
+
rescue
|
|
36
|
+
file = Origen.file_handler.clean_path_to(file)
|
|
37
|
+
Origen.generator.compile_file_or_directory(file, initial_options: options)
|
|
38
|
+
end
|
|
39
|
+
end
|
|
40
|
+
end
|
|
41
|
+
|
|
42
|
+
def import(file, options = {})
|
|
43
|
+
# Attach the import request to the first generator, when it imports
|
|
44
|
+
# it any generated resources will automatically find their way to the
|
|
45
|
+
# correct generator/collection
|
|
46
|
+
generator = flow || sheet_generators.first
|
|
47
|
+
generator.import(file, options)
|
|
48
|
+
end
|
|
49
|
+
|
|
50
|
+
def render(file, options = {})
|
|
51
|
+
if sheet_generators.size > 1
|
|
52
|
+
fail "You must specify which generator to render content to! e.g. i.test_instances.render '#{file}'"
|
|
53
|
+
else
|
|
54
|
+
sheet_generators.first.render(file, options)
|
|
55
|
+
end
|
|
56
|
+
end
|
|
57
|
+
|
|
58
|
+
def write_files(options = {})
|
|
59
|
+
sheet_generators.each do |generator|
|
|
60
|
+
generator.finalize(options)
|
|
61
|
+
end
|
|
62
|
+
sheet_generators.each do |generator|
|
|
63
|
+
generator.write_to_file(options) if generator.to_be_written?
|
|
64
|
+
end
|
|
65
|
+
reset_globals
|
|
66
|
+
end
|
|
67
|
+
|
|
68
|
+
# All generators should push to this array whenever they reference a pattern
|
|
69
|
+
# so that it is captured in the pattern list, e.g.
|
|
70
|
+
# Origen.interface.referenced_patterns << pattern
|
|
71
|
+
def referenced_patterns
|
|
72
|
+
@@referenced_patterns ||= []
|
|
73
|
+
end
|
|
74
|
+
|
|
75
|
+
# Add a comment line into the buffer
|
|
76
|
+
def comment(text)
|
|
77
|
+
comments << text
|
|
78
|
+
end
|
|
79
|
+
|
|
80
|
+
def comments
|
|
81
|
+
@@comments ||= []
|
|
82
|
+
end
|
|
83
|
+
|
|
84
|
+
def discard_comments
|
|
85
|
+
@@comments = nil
|
|
86
|
+
end
|
|
87
|
+
|
|
88
|
+
# Returns the buffered description comments and clears the buffer
|
|
89
|
+
def consume_comments
|
|
90
|
+
c = comments
|
|
91
|
+
discard_comments
|
|
92
|
+
c
|
|
93
|
+
end
|
|
94
|
+
|
|
95
|
+
def top_level_flow
|
|
96
|
+
@@top_level_flow ||= nil
|
|
97
|
+
end
|
|
98
|
+
alias_method :top_level_flow_filename, :top_level_flow
|
|
99
|
+
|
|
100
|
+
def flow_generator
|
|
101
|
+
flow
|
|
102
|
+
end
|
|
103
|
+
|
|
104
|
+
def set_top_level_flow
|
|
105
|
+
@@top_level_flow = flow_generator.output_file
|
|
106
|
+
end
|
|
107
|
+
|
|
108
|
+
def clear_top_level_flow
|
|
109
|
+
@@top_level_flow = nil
|
|
110
|
+
end
|
|
111
|
+
|
|
112
|
+
# A storage Hash that all generators can push comment descriptions
|
|
113
|
+
# into when generating.
|
|
114
|
+
# At the end of a generation run this will contain all descriptions
|
|
115
|
+
# for all flows that were just created.
|
|
116
|
+
#
|
|
117
|
+
# Access via Origen.interface.descriptions
|
|
118
|
+
def descriptions
|
|
119
|
+
@@descriptions ||= Parser::DescriptionLookup.new
|
|
120
|
+
end
|
|
121
|
+
|
|
122
|
+
# Any tests generated within the given block will be generated in resources mode.
|
|
123
|
+
# Generally this means that all resources for a given test will be generated but
|
|
124
|
+
# flow entries will be inhibited.
|
|
125
|
+
def resources_mode
|
|
126
|
+
orig = @resources_mode
|
|
127
|
+
@resources_mode = true
|
|
128
|
+
yield
|
|
129
|
+
@resources_mode = orig
|
|
130
|
+
end
|
|
131
|
+
|
|
132
|
+
def resources_mode?
|
|
133
|
+
@resources_mode
|
|
134
|
+
end
|
|
135
|
+
|
|
136
|
+
def identity_map # :nodoc:
|
|
137
|
+
@@identity_map ||= Origen::Tester::Generator::IdentityMap.new
|
|
138
|
+
end
|
|
139
|
+
|
|
140
|
+
module ClassMethods
|
|
141
|
+
# Returns true if the interface class supports the
|
|
142
|
+
# given tester instance
|
|
143
|
+
def supports?(tester_instance)
|
|
144
|
+
# Testers uses different platform check than Origen core
|
|
145
|
+
if self.respond_to?('platform')
|
|
146
|
+
tester_instance.is_a?(platform)
|
|
147
|
+
else
|
|
148
|
+
tester_instance.is_a?(self::PLATFORM)
|
|
149
|
+
end
|
|
150
|
+
end
|
|
151
|
+
end
|
|
152
|
+
end
|
|
153
|
+
end
|
|
154
|
+
end
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
module Origen
|
|
2
|
+
module Tester
|
|
3
|
+
class J750
|
|
4
|
+
# Methods for handling all J750 file parsing, e.g. datalogs,
|
|
5
|
+
# test time profiles, etc.
|
|
6
|
+
module Files
|
|
7
|
+
# Reads all lines from a J750 detailed execution time file, returning the lines
|
|
8
|
+
# as an array like this:
|
|
9
|
+
#
|
|
10
|
+
# [
|
|
11
|
+
# {:name => "power_cycle", :index => 1, :group => 3, :time => 0.00461},
|
|
12
|
+
# {:name => "power_cycle", :index => 2, :group => 3, :time => 0.00481},
|
|
13
|
+
# {:name => "power_cycle", :index => 3, :group => 3, :time => 0.00438},
|
|
14
|
+
# {:name => "nvm_mass_erase", :index => nil, :group => nil, :time => 0.19863},
|
|
15
|
+
# ]
|
|
16
|
+
def read_test_times(file, _options = {})
|
|
17
|
+
tests = []
|
|
18
|
+
File.readlines(file).each do |line|
|
|
19
|
+
unless line.strip.empty? || line =~ /Entire Job/
|
|
20
|
+
# http://rubular.com/r/vZOcqovTsf
|
|
21
|
+
if line =~ /(\w+) ?(\(.*?\))? \d\d\d\d (\d+\.\d+).*/
|
|
22
|
+
t = { name: Regexp.last_match[1], time: Regexp.last_match[3].to_f.round(6) }
|
|
23
|
+
# If an indexed test
|
|
24
|
+
if Regexp.last_match[2]
|
|
25
|
+
str = Regexp.last_match[2].gsub('(', '').gsub(')', '')
|
|
26
|
+
fields = str.split('/')
|
|
27
|
+
i = fields[0].to_i
|
|
28
|
+
g = fields[1].to_i
|
|
29
|
+
t[:index] = i
|
|
30
|
+
t[:group] = g
|
|
31
|
+
|
|
32
|
+
else
|
|
33
|
+
t[:index] = nil
|
|
34
|
+
t[:group] = nil
|
|
35
|
+
end
|
|
36
|
+
tests << t
|
|
37
|
+
end
|
|
38
|
+
end
|
|
39
|
+
end
|
|
40
|
+
tests
|
|
41
|
+
end
|
|
42
|
+
end
|
|
43
|
+
end
|
|
44
|
+
end
|
|
45
|
+
end
|
|
@@ -0,0 +1,123 @@
|
|
|
1
|
+
module Origen
|
|
2
|
+
module Tester
|
|
3
|
+
class J750
|
|
4
|
+
module Generator
|
|
5
|
+
class Flow
|
|
6
|
+
include Origen::Tester::Generator
|
|
7
|
+
include Origen::Tester::Generator::FlowControlAPI
|
|
8
|
+
|
|
9
|
+
TEMPLATE = "#{Origen.top}/lib/origen/tester/j750/generator/templates/flow.txt.erb"
|
|
10
|
+
OUTPUT_POSTFIX = 'flow'
|
|
11
|
+
|
|
12
|
+
def add(type, options = {})
|
|
13
|
+
ins = false
|
|
14
|
+
options = save_context(options) if [:test, :cz].include?(type)
|
|
15
|
+
branch_unless_enabled(options) do |options|
|
|
16
|
+
ins = track_relationships(options) do |options|
|
|
17
|
+
FlowLine.new(type, options)
|
|
18
|
+
end
|
|
19
|
+
collection << ins unless Origen.interface.resources_mode?
|
|
20
|
+
if ins.test?
|
|
21
|
+
c = Origen.interface.consume_comments
|
|
22
|
+
unless Origen.interface.resources_mode?
|
|
23
|
+
Origen.interface.descriptions.add_for_test_usage(ins.parameter, Origen.interface.top_level_flow, c)
|
|
24
|
+
end
|
|
25
|
+
else
|
|
26
|
+
Origen.interface.discard_comments
|
|
27
|
+
end
|
|
28
|
+
end
|
|
29
|
+
ins
|
|
30
|
+
end
|
|
31
|
+
|
|
32
|
+
def logprint(message, options = {})
|
|
33
|
+
message.gsub!(/\s/, '_')
|
|
34
|
+
add(:logprint, options.merge(parameter: message))
|
|
35
|
+
end
|
|
36
|
+
|
|
37
|
+
def test(instance, options = {})
|
|
38
|
+
add(:test, options.merge(parameter: instance))
|
|
39
|
+
end
|
|
40
|
+
|
|
41
|
+
def cz(instance, cz_setup, options = {})
|
|
42
|
+
add(:cz, options.merge(parameter: instance, cz_setup: cz_setup))
|
|
43
|
+
end
|
|
44
|
+
|
|
45
|
+
def goto(label, options = {})
|
|
46
|
+
add(:goto, options.merge(parameter: label))
|
|
47
|
+
end
|
|
48
|
+
|
|
49
|
+
def nop(options = {})
|
|
50
|
+
add(:nop, options.merge(parameter: nil))
|
|
51
|
+
end
|
|
52
|
+
|
|
53
|
+
def set_device(options = {})
|
|
54
|
+
add(:set_device, options)
|
|
55
|
+
end
|
|
56
|
+
|
|
57
|
+
def set_error_bin(options = {})
|
|
58
|
+
add(:set_error_bin, options)
|
|
59
|
+
end
|
|
60
|
+
|
|
61
|
+
def enable_flow_word(word, options = {})
|
|
62
|
+
add(:enable_flow_word, options.merge(parameter: word))
|
|
63
|
+
end
|
|
64
|
+
|
|
65
|
+
def disable_flow_word(word, options = {})
|
|
66
|
+
add(:disable_flow_word, options.merge(parameter: word))
|
|
67
|
+
end
|
|
68
|
+
|
|
69
|
+
# All tests generated will not run unless the given enable word is asserted.
|
|
70
|
+
#
|
|
71
|
+
# This is specially implemented for J750 since it does not have a native
|
|
72
|
+
# support for flow word not enabled.
|
|
73
|
+
# It will generate a goto branch around the tests contained with the block
|
|
74
|
+
# if the given flow word is enabled.
|
|
75
|
+
def unless_enable(word, options = {})
|
|
76
|
+
if options[:or]
|
|
77
|
+
yield
|
|
78
|
+
else
|
|
79
|
+
@unless_enable_block = word
|
|
80
|
+
options = options.merge(unless_enable: word)
|
|
81
|
+
branch_unless_enabled(options.merge(_force_unless_enable: true)) do
|
|
82
|
+
yield
|
|
83
|
+
end
|
|
84
|
+
@unless_enable_block = nil
|
|
85
|
+
end
|
|
86
|
+
end
|
|
87
|
+
alias_method :unless_enabled, :unless_enable
|
|
88
|
+
|
|
89
|
+
def start_flow_branch(identifier, options = {})
|
|
90
|
+
goto(identifier, options)
|
|
91
|
+
end
|
|
92
|
+
|
|
93
|
+
def skip(identifier = nil, options = {})
|
|
94
|
+
identifier, options = nil, identifier if identifier.is_a?(Hash)
|
|
95
|
+
identifier = generate_unique_label(identifier)
|
|
96
|
+
goto(identifier, options)
|
|
97
|
+
yield
|
|
98
|
+
nop(label: identifier)
|
|
99
|
+
end
|
|
100
|
+
|
|
101
|
+
private
|
|
102
|
+
|
|
103
|
+
# If the test has an unless_enable then branch around it
|
|
104
|
+
def branch_unless_enabled(options)
|
|
105
|
+
word = options.delete(:unless_enable) || options.delete(:unless_enabled)
|
|
106
|
+
if word && (word != @unless_enable_block || options.delete(:_force_unless_enable))
|
|
107
|
+
# Not sure if this is really required, but duplicating these hashes here to ensure
|
|
108
|
+
# that all other flow context keys are preserved and applied to the branch lines
|
|
109
|
+
orig_options = options.merge({})
|
|
110
|
+
close_options = options.merge({})
|
|
111
|
+
label = generate_unique_label
|
|
112
|
+
goto(label, options.merge(if_enable: word))
|
|
113
|
+
yield orig_options
|
|
114
|
+
nop(close_options.merge(label: label))
|
|
115
|
+
else
|
|
116
|
+
yield options
|
|
117
|
+
end
|
|
118
|
+
end
|
|
119
|
+
end
|
|
120
|
+
end
|
|
121
|
+
end
|
|
122
|
+
end
|
|
123
|
+
end
|