rggen-core 0.9.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (87) hide show
  1. checksums.yaml +7 -0
  2. data/CODE_OF_CONDUCT.md +46 -0
  3. data/LICENSE +21 -0
  4. data/README.md +46 -0
  5. data/exe/rggen +13 -0
  6. data/lib/rggen/core.rb +101 -0
  7. data/lib/rggen/core/base/component.rb +54 -0
  8. data/lib/rggen/core/base/component_factory.rb +84 -0
  9. data/lib/rggen/core/base/feature.rb +46 -0
  10. data/lib/rggen/core/base/feature_factory.rb +37 -0
  11. data/lib/rggen/core/base/hierarchical_accessors.rb +91 -0
  12. data/lib/rggen/core/base/hierarchical_feature_accessors.rb +83 -0
  13. data/lib/rggen/core/base/internal_struct.rb +21 -0
  14. data/lib/rggen/core/base/shared_context.rb +18 -0
  15. data/lib/rggen/core/builder.rb +13 -0
  16. data/lib/rggen/core/builder/builder.rb +150 -0
  17. data/lib/rggen/core/builder/category.rb +116 -0
  18. data/lib/rggen/core/builder/component_entry.rb +29 -0
  19. data/lib/rggen/core/builder/component_registry.rb +47 -0
  20. data/lib/rggen/core/builder/feature_registry.rb +126 -0
  21. data/lib/rggen/core/builder/input_component_registry.rb +35 -0
  22. data/lib/rggen/core/builder/list_feature_entry.rb +98 -0
  23. data/lib/rggen/core/builder/output_component_registry.rb +10 -0
  24. data/lib/rggen/core/builder/simple_feature_entry.rb +39 -0
  25. data/lib/rggen/core/cli.rb +29 -0
  26. data/lib/rggen/core/configuration.rb +19 -0
  27. data/lib/rggen/core/configuration/component.rb +10 -0
  28. data/lib/rggen/core/configuration/component_factory.rb +19 -0
  29. data/lib/rggen/core/configuration/error.rb +16 -0
  30. data/lib/rggen/core/configuration/feature.rb +13 -0
  31. data/lib/rggen/core/configuration/feature_factory.rb +11 -0
  32. data/lib/rggen/core/configuration/hash_loader.rb +15 -0
  33. data/lib/rggen/core/configuration/json_loader.rb +18 -0
  34. data/lib/rggen/core/configuration/loader.rb +11 -0
  35. data/lib/rggen/core/configuration/ruby_loader.rb +15 -0
  36. data/lib/rggen/core/configuration/yaml_loader.rb +18 -0
  37. data/lib/rggen/core/core_extensions/casecmp.rb +12 -0
  38. data/lib/rggen/core/core_extensions/forwardable.rb +12 -0
  39. data/lib/rggen/core/core_extensions/forwardable_workaround.rb +22 -0
  40. data/lib/rggen/core/core_extensions/object.rb +14 -0
  41. data/lib/rggen/core/dsl.rb +30 -0
  42. data/lib/rggen/core/exceptions.rb +29 -0
  43. data/lib/rggen/core/facets.rb +7 -0
  44. data/lib/rggen/core/generator.rb +51 -0
  45. data/lib/rggen/core/input_base/component.rb +30 -0
  46. data/lib/rggen/core/input_base/component_factory.rb +88 -0
  47. data/lib/rggen/core/input_base/feature.rb +130 -0
  48. data/lib/rggen/core/input_base/feature_factory.rb +80 -0
  49. data/lib/rggen/core/input_base/input_data.rb +98 -0
  50. data/lib/rggen/core/input_base/input_matcher.rb +79 -0
  51. data/lib/rggen/core/input_base/input_value.rb +34 -0
  52. data/lib/rggen/core/input_base/json_loader.rb +16 -0
  53. data/lib/rggen/core/input_base/loader.rb +44 -0
  54. data/lib/rggen/core/input_base/property.rb +76 -0
  55. data/lib/rggen/core/input_base/verifier.rb +41 -0
  56. data/lib/rggen/core/input_base/yaml_loader.rb +34 -0
  57. data/lib/rggen/core/options.rb +181 -0
  58. data/lib/rggen/core/output_base/code_generator.rb +59 -0
  59. data/lib/rggen/core/output_base/component.rb +100 -0
  60. data/lib/rggen/core/output_base/component_factory.rb +35 -0
  61. data/lib/rggen/core/output_base/erb_engine.rb +21 -0
  62. data/lib/rggen/core/output_base/feature.rb +147 -0
  63. data/lib/rggen/core/output_base/feature_factory.rb +13 -0
  64. data/lib/rggen/core/output_base/file_writer.rb +40 -0
  65. data/lib/rggen/core/output_base/template_engine.rb +27 -0
  66. data/lib/rggen/core/printers.rb +53 -0
  67. data/lib/rggen/core/register_map.rb +21 -0
  68. data/lib/rggen/core/register_map/component.rb +20 -0
  69. data/lib/rggen/core/register_map/component_factory.rb +19 -0
  70. data/lib/rggen/core/register_map/error.rb +16 -0
  71. data/lib/rggen/core/register_map/feature.rb +22 -0
  72. data/lib/rggen/core/register_map/feature_factory.rb +11 -0
  73. data/lib/rggen/core/register_map/hash_loader.rb +47 -0
  74. data/lib/rggen/core/register_map/input_data.rb +34 -0
  75. data/lib/rggen/core/register_map/json_loader.rb +18 -0
  76. data/lib/rggen/core/register_map/loader.rb +15 -0
  77. data/lib/rggen/core/register_map/ruby_loader.rb +15 -0
  78. data/lib/rggen/core/register_map/yaml_loader.rb +18 -0
  79. data/lib/rggen/core/utility/attribute_setter.rb +53 -0
  80. data/lib/rggen/core/utility/code_utility.rb +64 -0
  81. data/lib/rggen/core/utility/code_utility/code_block.rb +88 -0
  82. data/lib/rggen/core/utility/code_utility/line.rb +51 -0
  83. data/lib/rggen/core/utility/code_utility/source_file.rb +104 -0
  84. data/lib/rggen/core/utility/code_utility/structure_definition.rb +54 -0
  85. data/lib/rggen/core/utility/regexp_patterns.rb +38 -0
  86. data/lib/rggen/core/version.rb +10 -0
  87. metadata +188 -0
@@ -0,0 +1,91 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RgGen
4
+ module Core
5
+ module Base
6
+ module HierarchicalAccessors
7
+ module RegisterMap
8
+ def hierarchy
9
+ :register_map
10
+ end
11
+
12
+ def register_blocks
13
+ children
14
+ end
15
+
16
+ def registers
17
+ register_blocks.flat_map(&:children)
18
+ end
19
+
20
+ def bit_fields
21
+ registers.flat_map(&:children)
22
+ end
23
+ end
24
+
25
+ module RegisterBlock
26
+ def hierarchy
27
+ :register_block
28
+ end
29
+
30
+ def register_map
31
+ parent
32
+ end
33
+
34
+ def registers
35
+ children
36
+ end
37
+
38
+ def bit_fields
39
+ registers.flat_map(&:children)
40
+ end
41
+ end
42
+
43
+ module Register
44
+ def hierarchy
45
+ :register
46
+ end
47
+
48
+ def register_map
49
+ register_block.parent
50
+ end
51
+
52
+ def register_block
53
+ parent
54
+ end
55
+
56
+ def bit_fields
57
+ children
58
+ end
59
+ end
60
+
61
+ module BitField
62
+ def hierarchy
63
+ :bit_field
64
+ end
65
+
66
+ def register_map
67
+ register_block.parent
68
+ end
69
+
70
+ def register_block
71
+ register.parent
72
+ end
73
+
74
+ def register
75
+ parent
76
+ end
77
+ end
78
+
79
+ private
80
+
81
+ ACCESSOR_EXTENSIONS = [
82
+ RegisterMap, RegisterBlock, Register, BitField
83
+ ].freeze
84
+
85
+ def define_hierarchical_accessors
86
+ extend ACCESSOR_EXTENSIONS[level]
87
+ end
88
+ end
89
+ end
90
+ end
91
+ end
@@ -0,0 +1,83 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RgGen
4
+ module Core
5
+ module Base
6
+ module HierarchicalFeatureAccessors
7
+ module RegisterMap
8
+ def hierarchy
9
+ :register_map
10
+ end
11
+
12
+ def register_map
13
+ @component
14
+ end
15
+ end
16
+
17
+ module RegisterBlock
18
+ def hierarchy
19
+ :register_block
20
+ end
21
+
22
+ def register_map
23
+ register_block.parent
24
+ end
25
+
26
+ def register_block
27
+ @component
28
+ end
29
+ end
30
+
31
+ module Register
32
+ def hierarchy
33
+ :register
34
+ end
35
+
36
+ def register_map
37
+ register_block.parent
38
+ end
39
+
40
+ def register_block
41
+ register.parent
42
+ end
43
+
44
+ def register
45
+ @component
46
+ end
47
+ end
48
+
49
+ module BitField
50
+ def hierarchy
51
+ :bit_field
52
+ end
53
+
54
+ def register_map
55
+ register_block.parent
56
+ end
57
+
58
+ def register_block
59
+ register.parent
60
+ end
61
+
62
+ def register
63
+ bit_field.parent
64
+ end
65
+
66
+ def bit_field
67
+ @component
68
+ end
69
+ end
70
+
71
+ private
72
+
73
+ ACCESSOR_EXTENSIONS = [
74
+ RegisterMap, RegisterBlock, Register, BitField
75
+ ].freeze
76
+
77
+ def define_hierarchical_accessors
78
+ extend ACCESSOR_EXTENSIONS[@component.level]
79
+ end
80
+ end
81
+ end
82
+ end
83
+ end
@@ -0,0 +1,21 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RgGen
4
+ module Core
5
+ module Base
6
+ module InternalStruct
7
+ def self.included(klass)
8
+ klass.extend(self)
9
+ end
10
+
11
+ private
12
+
13
+ def define_struct(name, members, &body)
14
+ struct = Struct.new(*members, &body)
15
+ define_method(name) { struct }
16
+ private name
17
+ end
18
+ end
19
+ end
20
+ end
21
+ end
@@ -0,0 +1,18 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RgGen
4
+ module Core
5
+ module Base
6
+ module SharedContext
7
+ def attach_context(context)
8
+ if is_a?(Module)
9
+ define_method(:shared_context) { context }
10
+ else
11
+ instance_variable_set(:@shared_context, context)
12
+ singleton_exec { attr_reader :shared_context }
13
+ end
14
+ end
15
+ end
16
+ end
17
+ end
18
+ end
@@ -0,0 +1,13 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RgGen
4
+ module Core
5
+ module Builder
6
+ def self.create
7
+ builder = Builder.new
8
+ builder.register_input_components
9
+ builder
10
+ end
11
+ end
12
+ end
13
+ end
@@ -0,0 +1,150 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RgGen
4
+ module Core
5
+ module Builder
6
+ class Builder
7
+ def initialize
8
+ initialize_component_registries
9
+ initialize_categories
10
+ end
11
+
12
+ def input_component_registry(name, &body)
13
+ component_registry(:input, name, body)
14
+ end
15
+
16
+ def output_component_registry(name, &body)
17
+ component_registry(:output, name, body)
18
+ end
19
+
20
+ def register_loader(component, loader)
21
+ @component_registries[:input][component].register_loader(loader)
22
+ end
23
+
24
+ def register_loaders(component, loaders)
25
+ @component_registries[:input][component].register_loaders(loaders)
26
+ end
27
+
28
+ def define_loader(component, &body)
29
+ @component_registries[:input][component].define_loader(&body)
30
+ end
31
+
32
+ def add_feature_registry(name, target_category, registry)
33
+ target_categories =
34
+ if target_category
35
+ Array(@categories[target_category])
36
+ else
37
+ @categories.values
38
+ end
39
+ target_categories.each do |category|
40
+ category.add_feature_registry(name, registry)
41
+ end
42
+ end
43
+
44
+ [
45
+ :define_simple_feature,
46
+ :define_list_feature,
47
+ :define_list_item_feature
48
+ ].each do |method_name|
49
+ define_method(method_name) do |category, *args, &body|
50
+ @categories[category].__send__(__method__, *args, &body)
51
+ end
52
+ end
53
+
54
+ def enable(category, *args)
55
+ @categories[category].enable(*args)
56
+ end
57
+
58
+ def disable_all
59
+ @categories.each_value(&:disable)
60
+ end
61
+
62
+ def disable(category, *args)
63
+ @categories.key?(category) && @categories[category].disable(*args)
64
+ end
65
+
66
+ def build_factory(type, component)
67
+ @component_registries[type][component].build_factory
68
+ end
69
+
70
+ def build_factories(type, targets)
71
+ registries =
72
+ if targets.empty?
73
+ @component_registries[type]
74
+ else
75
+ @component_registries[type]
76
+ .select { |name, _| targets.include?(name) }
77
+ end
78
+ registries.each_value.map(&:build_factory)
79
+ end
80
+
81
+ def delete(category, *args)
82
+ @categories.key?(category) && @categories[category].delete(*args)
83
+ end
84
+
85
+ def register_input_components
86
+ Configuration.setup(self)
87
+ RegisterMap.setup(self)
88
+ end
89
+
90
+ def setup(library_name, library_module)
91
+ library_versions[library_name] =
92
+ if library_module.const_defined?(:VERSION)
93
+ library_module.const_get(:VERSION)
94
+ elsif library_module.respond_to?(:version)
95
+ library_module.version
96
+ else
97
+ '0.0.0'
98
+ end
99
+ library_module.setup(self)
100
+ end
101
+
102
+ def library_versions
103
+ @library_versions ||= {}
104
+ end
105
+
106
+ def load_setup_file(file)
107
+ (file.nil? || file.empty?) &&
108
+ (raise Core::LoadError.new('no setup file is given'))
109
+ File.readable?(file) ||
110
+ (raise Core::LoadError.new("cannot load such setup file: #{file}"))
111
+ RgGen.builder(self)
112
+ load(file)
113
+ end
114
+
115
+ private
116
+
117
+ def initialize_component_registries
118
+ @component_registries = {}
119
+ [:input, :output].each do |type|
120
+ @component_registries[type] = Hash.new do |_, component_name|
121
+ raise BuilderError.new("unknown component: #{component_name}")
122
+ end
123
+ end
124
+ end
125
+
126
+ def initialize_categories
127
+ @categories = Hash.new do |_, category_name|
128
+ raise BuilderError.new("unknown category: #{category_name}")
129
+ end
130
+ [
131
+ :global, :register_map, :register_block, :register, :bit_field
132
+ ].each do |category|
133
+ @categories[category] = Category.new(category)
134
+ end
135
+ end
136
+
137
+ COMPONENT_REGISTRIES = {
138
+ input: InputComponentRegistry, output: OutputComponentRegistry
139
+ }
140
+
141
+ def component_registry(type, name, body)
142
+ registries = @component_registries[type]
143
+ klass = COMPONENT_REGISTRIES[type]
144
+ registries.key?(name) || (registries[name] = klass.new(name, self))
145
+ Docile.dsl_eval(registries[name], &body)
146
+ end
147
+ end
148
+ end
149
+ end
150
+ end
@@ -0,0 +1,116 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RgGen
4
+ module Core
5
+ module Builder
6
+ class Category
7
+ class Proxy
8
+ def initialize(body)
9
+ body.call(self)
10
+ end
11
+
12
+ attr_setter :method
13
+ attr_setter :list_names
14
+ attr_setter :feature_names
15
+
16
+ def shared_context(&body)
17
+ if block_given?
18
+ @shared_context ||= Object.new
19
+ @shared_context.instance_eval(&body)
20
+ end
21
+ @shared_context
22
+ end
23
+
24
+ def register_execution(registry, args, body)
25
+ @executions ||= []
26
+ @executions << { registry: registry, args: args, body: body }
27
+ end
28
+
29
+ def execute(category, body)
30
+ Docile.dsl_eval(category, &body)
31
+ Array(@executions).each { |execution| call_execution(execution) }
32
+ end
33
+
34
+ private
35
+
36
+ def call_execution(execution)
37
+ send_args = [
38
+ list_names, feature_names, shared_context, *execution[:args]
39
+ ].compact
40
+ execution[:registry].__send__(
41
+ method, *send_args, &execution[:body]
42
+ )
43
+ end
44
+ end
45
+
46
+ def initialize(name)
47
+ @name = name
48
+ @feature_registries = {}
49
+ end
50
+
51
+ def add_feature_registry(name, registry)
52
+ @feature_registries[name] = registry
53
+ define_proxy_call(name)
54
+ end
55
+
56
+ def shared_context(&body)
57
+ block_given? && @proxy&.shared_context(&body)
58
+ end
59
+
60
+ def define_simple_feature(feature_names, &body)
61
+ do_proxy_call(body) do |proxy|
62
+ proxy.method(__method__)
63
+ proxy.feature_names(feature_names)
64
+ end
65
+ end
66
+
67
+ def define_list_feature(list_names, &body)
68
+ do_proxy_call(body) do |proxy|
69
+ proxy.method(__method__)
70
+ proxy.list_names(list_names)
71
+ end
72
+ end
73
+
74
+ def define_list_item_feature(list_name, feature_names, &body)
75
+ do_proxy_call(body) do |proxy|
76
+ proxy.method(__method__)
77
+ proxy.list_names(list_name)
78
+ proxy.feature_names(feature_names)
79
+ end
80
+ end
81
+
82
+ def enable(feature_or_list_names, feature_names = nil)
83
+ @feature_registries.each_value do |registry|
84
+ registry.enable(feature_or_list_names, feature_names)
85
+ end
86
+ end
87
+
88
+ def disable(feature_or_list_names = nil, feature_names = nil)
89
+ @feature_registries.each_value do |registry|
90
+ registry.disable(*[feature_or_list_names, feature_names].compact)
91
+ end
92
+ end
93
+
94
+ def delete(feature_or_list_names = nil, feature_names = nil)
95
+ @feature_registries.each_value do |registry|
96
+ registry.delete(*[feature_or_list_names, feature_names].compact)
97
+ end
98
+ end
99
+
100
+ private
101
+
102
+ def define_proxy_call(name)
103
+ define_singleton_method(name) do |*args, &body|
104
+ @proxy.register_execution(@feature_registries[name], args, body)
105
+ end
106
+ end
107
+
108
+ def do_proxy_call(body, &proxy_block)
109
+ @proxy = Proxy.new(proxy_block)
110
+ @proxy.execute(self, body)
111
+ remove_instance_variable(:@proxy)
112
+ end
113
+ end
114
+ end
115
+ end
116
+ end