abide_dev_utils 0.11.0 → 0.11.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/Gemfile.lock +1 -14
- data/lib/abide_dev_utils/cem/benchmark.rb +330 -136
- data/lib/abide_dev_utils/cem/generate/coverage_report.rb +380 -0
- data/lib/abide_dev_utils/cem/generate/reference.rb +157 -33
- data/lib/abide_dev_utils/cem/generate.rb +5 -4
- data/lib/abide_dev_utils/cem/hiera_data/mapping_data/map_data.rb +110 -0
- data/lib/abide_dev_utils/cem/hiera_data/mapping_data/mixins.rb +46 -0
- data/lib/abide_dev_utils/cem/hiera_data/mapping_data.rb +146 -0
- data/lib/abide_dev_utils/cem/hiera_data/resource_data/control.rb +127 -0
- data/lib/abide_dev_utils/cem/hiera_data/resource_data/parameters.rb +90 -0
- data/lib/abide_dev_utils/cem/hiera_data/resource_data/resource.rb +102 -0
- data/lib/abide_dev_utils/cem/hiera_data/resource_data.rb +310 -0
- data/lib/abide_dev_utils/cem/hiera_data.rb +7 -0
- data/lib/abide_dev_utils/cem/mapping/mapper.rb +161 -34
- data/lib/abide_dev_utils/cem/validate/resource_data.rb +33 -0
- data/lib/abide_dev_utils/cem/validate.rb +10 -0
- data/lib/abide_dev_utils/cem.rb +0 -1
- data/lib/abide_dev_utils/cli/cem.rb +20 -2
- data/lib/abide_dev_utils/dot_number_comparable.rb +75 -0
- data/lib/abide_dev_utils/errors/cem.rb +10 -0
- data/lib/abide_dev_utils/ppt/class_utils.rb +1 -1
- data/lib/abide_dev_utils/ppt/code_gen/data_types.rb +51 -0
- data/lib/abide_dev_utils/ppt/code_gen/generate.rb +15 -0
- data/lib/abide_dev_utils/ppt/code_gen/resource.rb +59 -0
- data/lib/abide_dev_utils/ppt/code_gen/resource_types/base.rb +93 -0
- data/lib/abide_dev_utils/ppt/code_gen/resource_types/class.rb +17 -0
- data/lib/abide_dev_utils/ppt/code_gen/resource_types/manifest.rb +16 -0
- data/lib/abide_dev_utils/ppt/code_gen/resource_types/parameter.rb +16 -0
- data/lib/abide_dev_utils/ppt/code_gen/resource_types/strings.rb +13 -0
- data/lib/abide_dev_utils/ppt/code_gen/resource_types.rb +6 -0
- data/lib/abide_dev_utils/ppt/code_gen.rb +15 -0
- data/lib/abide_dev_utils/ppt/code_introspection.rb +102 -0
- data/lib/abide_dev_utils/ppt/hiera.rb +4 -1
- data/lib/abide_dev_utils/ppt/puppet_module.rb +2 -1
- data/lib/abide_dev_utils/ppt.rb +3 -0
- data/lib/abide_dev_utils/version.rb +1 -1
- data/lib/abide_dev_utils/xccdf/parser/helpers.rb +146 -0
- data/lib/abide_dev_utils/xccdf/parser/objects.rb +87 -144
- data/lib/abide_dev_utils/xccdf/parser.rb +5 -0
- data/lib/abide_dev_utils/xccdf/utils.rb +89 -0
- data/lib/abide_dev_utils/xccdf.rb +3 -0
- metadata +27 -3
- data/lib/abide_dev_utils/cem/coverage_report.rb +0 -348
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 1b3b154482634fc055b078ce36dbf15a387c4da25f6061f96128f33fb3f29e18
|
4
|
+
data.tar.gz: ecf7d53d1b06680970bc21affdbd7603193a84a9c1cac46d53cc1e95b13abbb6
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: f8c1b8d427bcde511d53dc505c4c10853a6cd963d0da3d27148b81342f0bd497e364f17cd6212fde0a4d97fb3e0a25d566d11cef679c7220a05c696c6df95191
|
7
|
+
data.tar.gz: 54fd1971163662139121b3e9b7b31a7be8ad42127f8a08b4271cb995454a3b90460477d11b6e13148dfa3d950cfb2b86d84ea491e436ee6b28518c9ae66486bb
|
data/Gemfile.lock
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
PATH
|
2
2
|
remote: .
|
3
3
|
specs:
|
4
|
-
abide_dev_utils (0.11.
|
4
|
+
abide_dev_utils (0.11.1)
|
5
5
|
amatch (~> 0.4)
|
6
6
|
cmdparse (~> 3.0)
|
7
7
|
facterdb (>= 1.18)
|
@@ -143,8 +143,6 @@ GEM
|
|
143
143
|
nio4r (2.5.8)
|
144
144
|
nokogiri (1.13.6-x86_64-darwin)
|
145
145
|
racc (~> 1.4)
|
146
|
-
nokogiri (1.13.6-x86_64-linux)
|
147
|
-
racc (~> 1.4)
|
148
146
|
oauth (0.5.10)
|
149
147
|
octokit (4.25.0)
|
150
148
|
faraday (>= 1, < 3)
|
@@ -166,17 +164,6 @@ GEM
|
|
166
164
|
coderay (~> 1.1)
|
167
165
|
method_source (~> 1.0)
|
168
166
|
public_suffix (4.0.7)
|
169
|
-
puppet (7.17.0)
|
170
|
-
concurrent-ruby (~> 1.0)
|
171
|
-
deep_merge (~> 1.0)
|
172
|
-
facter (> 2.0.1, < 5)
|
173
|
-
fast_gettext (>= 1.1, < 3)
|
174
|
-
hiera (>= 3.2.1, < 4)
|
175
|
-
locale (~> 2.1)
|
176
|
-
multi_json (~> 1.10)
|
177
|
-
puppet-resource_api (~> 1.5)
|
178
|
-
scanf (~> 1.0)
|
179
|
-
semantic_puppet (~> 1.0)
|
180
167
|
puppet (7.17.0-universal-darwin)
|
181
168
|
CFPropertyList (~> 2.2)
|
182
169
|
concurrent-ruby (~> 1.0)
|
@@ -1,14 +1,313 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
|
+
require 'set'
|
4
|
+
require 'abide_dev_utils/dot_number_comparable'
|
3
5
|
require 'abide_dev_utils/errors'
|
4
|
-
require 'abide_dev_utils/ppt
|
6
|
+
require 'abide_dev_utils/ppt'
|
5
7
|
require 'abide_dev_utils/cem/mapping/mapper'
|
6
8
|
|
7
9
|
module AbideDevUtils
|
8
10
|
module CEM
|
9
|
-
#
|
11
|
+
# Represents a resource data resource statement
|
12
|
+
class Resource
|
13
|
+
attr_reader :title, :type
|
14
|
+
|
15
|
+
def initialize(title, data, framework, mapper)
|
16
|
+
@title = title
|
17
|
+
@data = data
|
18
|
+
@type = data['type']
|
19
|
+
@framework = framework
|
20
|
+
@mapper = mapper
|
21
|
+
@dependent = []
|
22
|
+
end
|
23
|
+
|
24
|
+
def manifest
|
25
|
+
@manifest ||= load_manifest
|
26
|
+
end
|
27
|
+
|
28
|
+
def manifest?
|
29
|
+
!manifest.nil?
|
30
|
+
end
|
31
|
+
|
32
|
+
def file_path
|
33
|
+
@file_path ||= AbideDevUtils::Ppt::ClassUtils.path_from_class_name((type == 'class' ? title : type))
|
34
|
+
end
|
35
|
+
|
36
|
+
def controls
|
37
|
+
@controls || load_controls
|
38
|
+
end
|
39
|
+
|
40
|
+
def cem_options?
|
41
|
+
!cem_options.empty?
|
42
|
+
end
|
43
|
+
|
44
|
+
def cem_options
|
45
|
+
@cem_options ||= resource_properties('cem_options')
|
46
|
+
end
|
47
|
+
|
48
|
+
def cem_protected?
|
49
|
+
!cem_protected.empty?
|
50
|
+
end
|
51
|
+
|
52
|
+
def cem_protected
|
53
|
+
@cem_protected ||= resource_properties('cem_protected')
|
54
|
+
end
|
55
|
+
|
56
|
+
def dependent_controls
|
57
|
+
@dependent_controls ||= @dependent.flatten.uniq.filter_map { |x| controls.find { |y| y.id == x } }
|
58
|
+
end
|
59
|
+
|
60
|
+
def to_reference
|
61
|
+
"#{type.split('::').map(&:capitalize).join('::')}['#{title}']"
|
62
|
+
end
|
63
|
+
|
64
|
+
private
|
65
|
+
|
66
|
+
attr_reader :data, :framework, :mapper
|
67
|
+
|
68
|
+
def load_manifest
|
69
|
+
AbideDevUtils::Ppt::CodeIntrospection::Manifest.new(file_path)
|
70
|
+
rescue StandardError
|
71
|
+
nil
|
72
|
+
end
|
73
|
+
|
74
|
+
def resource_properties(prop_name)
|
75
|
+
props = Set.new
|
76
|
+
return props unless data.key?(prop_name)
|
77
|
+
|
78
|
+
data[prop_name].each do |param, param_val|
|
79
|
+
props << { name: param,
|
80
|
+
type: ruby_class_to_puppet_type(param_val.class.to_s),
|
81
|
+
default: param_val }
|
82
|
+
end
|
83
|
+
props
|
84
|
+
end
|
85
|
+
|
86
|
+
def load_controls
|
87
|
+
if data['controls'].respond_to?(:keys)
|
88
|
+
load_hash_controls(data['controls'], framework, mapper)
|
89
|
+
elsif data['controls'].respond_to?(:each_with_index)
|
90
|
+
load_array_controls(data['controls'], framework, mapper)
|
91
|
+
else
|
92
|
+
raise "Control type is invalid. Type: #{data['controls'].class}"
|
93
|
+
end
|
94
|
+
end
|
95
|
+
|
96
|
+
def load_hash_controls(ctrls, framework, mapper)
|
97
|
+
ctrls.each_with_object([]) do |(name, data), arr|
|
98
|
+
if name == 'dependent'
|
99
|
+
@dependent << data
|
100
|
+
next
|
101
|
+
end
|
102
|
+
ctrl = Control.new(name, data, self, framework, mapper)
|
103
|
+
arr << ctrl
|
104
|
+
rescue AbideDevUtils::Errors::ControlIdFrameworkMismatchError,
|
105
|
+
AbideDevUtils::Errors::NoMappingDataForControlError
|
106
|
+
next
|
107
|
+
end
|
108
|
+
end
|
109
|
+
|
110
|
+
def load_array_controls(ctrls, framework, mapper)
|
111
|
+
ctrls.each_with_object([]) do |c, arr|
|
112
|
+
if c == 'dependent'
|
113
|
+
@dependent << c
|
114
|
+
next
|
115
|
+
end
|
116
|
+
ctrl = Control.new(c, 'no_params', self, framework, mapper)
|
117
|
+
arr << ctrl
|
118
|
+
rescue AbideDevUtils::Errors::ControlIdFrameworkMismatchError,
|
119
|
+
AbideDevUtils::Errors::NoMappingDataForControlError
|
120
|
+
next
|
121
|
+
end
|
122
|
+
end
|
123
|
+
|
124
|
+
def ruby_class_to_puppet_type(class_name)
|
125
|
+
pup_type = class_name.split('::').last.capitalize
|
126
|
+
case pup_type
|
127
|
+
when %r{(Trueclass|Falseclass)}
|
128
|
+
'Boolean'
|
129
|
+
when %r{(String|Pathname)}
|
130
|
+
'String'
|
131
|
+
when %r{(Integer|Fixnum)}
|
132
|
+
'Integer'
|
133
|
+
when %r{(Float|Double)}
|
134
|
+
'Float'
|
135
|
+
when %r{Nilclass}
|
136
|
+
'Optional'
|
137
|
+
else
|
138
|
+
pup_type
|
139
|
+
end
|
140
|
+
end
|
141
|
+
end
|
142
|
+
|
143
|
+
# Represents a singular rule in a benchmark
|
144
|
+
class Control
|
145
|
+
include AbideDevUtils::DotNumberComparable
|
146
|
+
attr_reader :id, :params, :resource, :framework, :dependent
|
147
|
+
|
148
|
+
def initialize(id, params, resource, framework, mapper)
|
149
|
+
validate_id_with_framework(id, framework, mapper)
|
150
|
+
@id = id
|
151
|
+
@params = params
|
152
|
+
@resource = resource
|
153
|
+
@framework = framework
|
154
|
+
@mapper = mapper
|
155
|
+
raise AbideDevUtils::Errors::NoMappingDataForControlError, @id unless @mapper.get(id)
|
156
|
+
end
|
157
|
+
|
158
|
+
def params?
|
159
|
+
!(params.nil? || params.empty? || params == 'no_params') || (resource.cem_options? || resource.cem_protected?)
|
160
|
+
end
|
161
|
+
|
162
|
+
def resource_properties?
|
163
|
+
resource.cem_options? || resource.cem_protected?
|
164
|
+
end
|
165
|
+
|
166
|
+
def param_hashes
|
167
|
+
return [no_params] unless params?
|
168
|
+
|
169
|
+
params.each_with_object([]) do |(param, param_val), ar|
|
170
|
+
ar << { name: param,
|
171
|
+
type: ruby_class_to_puppet_type(param_val.class.to_s),
|
172
|
+
default: param_val }
|
173
|
+
end
|
174
|
+
end
|
175
|
+
|
176
|
+
def alternate_ids(level: nil, profile: nil)
|
177
|
+
id_map = @mapper.get(id, level: level, profile: profile)
|
178
|
+
if display_title_type.to_s == @mapper.map_type(id)
|
179
|
+
id_map
|
180
|
+
else
|
181
|
+
alt_ids = id_map.each_with_object([]) do |mapval, arr|
|
182
|
+
arr << if display_title_type.to_s == @mapper.map_type(mapval)
|
183
|
+
@mapper.get(mapval, level: level, profile: profile)
|
184
|
+
else
|
185
|
+
mapval
|
186
|
+
end
|
187
|
+
end
|
188
|
+
alt_ids.flatten.uniq
|
189
|
+
end
|
190
|
+
end
|
191
|
+
|
192
|
+
def id_map_type
|
193
|
+
@mapper.map_type(id)
|
194
|
+
end
|
195
|
+
|
196
|
+
def display_title
|
197
|
+
send(display_title_type) unless display_title_type.nil?
|
198
|
+
end
|
199
|
+
|
200
|
+
def levels
|
201
|
+
levels_and_profiles[0]
|
202
|
+
end
|
203
|
+
|
204
|
+
def profiles
|
205
|
+
levels_and_profiles[1]
|
206
|
+
end
|
207
|
+
|
208
|
+
def valid_maps?
|
209
|
+
valid = AbideDevUtils::CEM::Mapping::FRAMEWORK_TYPES[framework].each_with_object([]) do |mtype, arr|
|
210
|
+
arr << if @mapper.map_type(id) == mtype
|
211
|
+
id
|
212
|
+
else
|
213
|
+
@mapper.get(id).find { |x| @mapper.map_type(x) == mtype }
|
214
|
+
end
|
215
|
+
end
|
216
|
+
valid.compact.length == AbideDevUtils::CEM::Mapping::FRAMEWORK_TYPES[framework].length
|
217
|
+
end
|
218
|
+
|
219
|
+
def method_missing(meth, *args, &block)
|
220
|
+
meth_s = meth.to_s
|
221
|
+
if AbideDevUtils::CEM::Mapping::ALL_TYPES.include?(meth_s)
|
222
|
+
@mapper.get(id).find { |x| @mapper.map_type(x) == meth_s }
|
223
|
+
else
|
224
|
+
super
|
225
|
+
end
|
226
|
+
end
|
227
|
+
|
228
|
+
def respond_to_missing?(meth, include_private = false)
|
229
|
+
AbideDevUtils::CEM::Mapping::ALL_TYPES.include?(meth.to_s) || super
|
230
|
+
end
|
231
|
+
|
232
|
+
def to_h
|
233
|
+
{
|
234
|
+
id: id,
|
235
|
+
display_title: display_title,
|
236
|
+
alternate_ids: alternate_ids,
|
237
|
+
levels: levels,
|
238
|
+
profiles: profiles,
|
239
|
+
params: param_hashes,
|
240
|
+
resource: resource.to_stubbed_h,
|
241
|
+
}
|
242
|
+
end
|
243
|
+
|
244
|
+
private
|
245
|
+
|
246
|
+
def display_title_type
|
247
|
+
if (!vulnid.nil? && !vulnid.is_a?(String)) || !title.is_a?(String)
|
248
|
+
nil
|
249
|
+
elsif framework == 'stig' && vulnid
|
250
|
+
:vulnid
|
251
|
+
else
|
252
|
+
:title
|
253
|
+
end
|
254
|
+
end
|
255
|
+
|
256
|
+
def validate_id_with_framework(id, framework, mapper)
|
257
|
+
mtype = mapper.map_type(id)
|
258
|
+
return if AbideDevUtils::CEM::Mapping::FRAMEWORK_TYPES[framework].include?(mtype)
|
259
|
+
|
260
|
+
raise AbideDevUtils::Errors::ControlIdFrameworkMismatchError, [id, mtype, framework]
|
261
|
+
end
|
262
|
+
|
263
|
+
def map
|
264
|
+
@map ||= @mapper.get(id)
|
265
|
+
end
|
266
|
+
|
267
|
+
def levels_and_profiles
|
268
|
+
@levels_and_profiles ||= find_levels_and_profiles
|
269
|
+
end
|
270
|
+
|
271
|
+
def find_levels_and_profiles
|
272
|
+
lvls = []
|
273
|
+
profs = []
|
274
|
+
@mapper.levels.each do |lvl|
|
275
|
+
@mapper.profiles.each do |prof|
|
276
|
+
unless @mapper.get(id, level: lvl, profile: prof).nil?
|
277
|
+
lvls << lvl
|
278
|
+
profs << prof
|
279
|
+
end
|
280
|
+
end
|
281
|
+
end
|
282
|
+
[lvls.flatten.compact.uniq, profs.flatten.compact.uniq]
|
283
|
+
end
|
284
|
+
|
285
|
+
def ruby_class_to_puppet_type(class_name)
|
286
|
+
pup_type = class_name.split('::').last.capitalize
|
287
|
+
case pup_type
|
288
|
+
when %r{(Trueclass|Falseclass)}
|
289
|
+
'Boolean'
|
290
|
+
when %r{(String|Pathname)}
|
291
|
+
'String'
|
292
|
+
when %r{(Integer|Fixnum)}
|
293
|
+
'Integer'
|
294
|
+
when %r{(Float|Double)}
|
295
|
+
'Float'
|
296
|
+
when %r{Nilclass}
|
297
|
+
'Optional'
|
298
|
+
else
|
299
|
+
pup_type
|
300
|
+
end
|
301
|
+
end
|
302
|
+
|
303
|
+
def no_params
|
304
|
+
{ name: 'No parameters', type: nil, default: nil }
|
305
|
+
end
|
306
|
+
end
|
307
|
+
|
308
|
+
# Repesents a benchmark based on resource and mapping data
|
10
309
|
class Benchmark
|
11
|
-
attr_reader :osname, :major_version, :os_facts, :osfamily, :hiera_conf, :module_name, :framework
|
310
|
+
attr_reader :osname, :major_version, :os_facts, :osfamily, :hiera_conf, :module_name, :framework
|
12
311
|
|
13
312
|
def initialize(osname, major_version, hiera_conf, module_name, framework: 'cis')
|
14
313
|
@osname = osname
|
@@ -18,10 +317,8 @@ module AbideDevUtils
|
|
18
317
|
@hiera_conf = hiera_conf
|
19
318
|
@module_name = module_name
|
20
319
|
@framework = framework
|
21
|
-
@rules = {}
|
22
320
|
@map_cache = {}
|
23
321
|
@rules_in_map = {}
|
24
|
-
load_rules
|
25
322
|
end
|
26
323
|
|
27
324
|
# Creates Benchmark objects from a Puppet module
|
@@ -38,23 +335,47 @@ module AbideDevUtils
|
|
38
335
|
if majver.is_a?(Array)
|
39
336
|
majver.sort.each do |v|
|
40
337
|
frameworks.each do |fw|
|
41
|
-
benchmark = Benchmark.new(osname,
|
338
|
+
benchmark = Benchmark.new(osname,
|
339
|
+
v,
|
340
|
+
pupmod.hiera_conf,
|
341
|
+
pupmod.name(strip_namespace: true),
|
342
|
+
framework: fw)
|
343
|
+
benchmark.controls
|
42
344
|
ary << benchmark
|
345
|
+
rescue AbideDevUtils::Errors::MappingDataFrameworkMismatchError => e
|
346
|
+
raise e unless ignore_all_errors || ignore_framework_mismatch
|
43
347
|
rescue StandardError => e
|
44
|
-
raise e unless ignore_all_errors
|
348
|
+
raise e unless ignore_all_errors
|
45
349
|
end
|
46
350
|
end
|
47
351
|
else
|
48
352
|
frameworks.each do |fw|
|
49
|
-
benchmark = Benchmark.new(osname,
|
353
|
+
benchmark = Benchmark.new(osname,
|
354
|
+
majver,
|
355
|
+
pupmod.hiera_conf,
|
356
|
+
pupmod.name(strip_namespace: true),
|
357
|
+
framework: fw)
|
358
|
+
benchmark.controls
|
50
359
|
ary << benchmark
|
360
|
+
rescue AbideDevUtils::Errors::MappingDataFrameworkMismatchError => e
|
361
|
+
raise e unless ignore_all_errors || ignore_framework_mismatch
|
51
362
|
rescue StandardError => e
|
52
|
-
raise e unless ignore_all_errors
|
363
|
+
raise e unless ignore_all_errors
|
53
364
|
end
|
54
365
|
end
|
55
366
|
end
|
56
367
|
end
|
57
368
|
|
369
|
+
def resources
|
370
|
+
@resources ||= resource_data["#{module_name}::resources"].each_with_object([]) do |(rtitle, rdata), arr|
|
371
|
+
arr << Resource.new(rtitle, rdata, framework, mapper)
|
372
|
+
end
|
373
|
+
end
|
374
|
+
|
375
|
+
def controls
|
376
|
+
@controls ||= resources.map(&:controls).flatten.sort
|
377
|
+
end
|
378
|
+
|
58
379
|
def mapper
|
59
380
|
@mapper ||= AbideDevUtils::CEM::Mapping::Mapper.new(module_name, framework, load_mapping_data)
|
60
381
|
end
|
@@ -113,131 +434,6 @@ module AbideDevUtils
|
|
113
434
|
|
114
435
|
private
|
115
436
|
|
116
|
-
def load_rules
|
117
|
-
resource_data["#{module_name}::resources"].each do |_, rdata|
|
118
|
-
unless rdata.key?('controls')
|
119
|
-
puts "Controls key not found in #{rdata}"
|
120
|
-
next
|
121
|
-
end
|
122
|
-
rdata['controls'].each do |control, control_data|
|
123
|
-
rule_title = map(control)
|
124
|
-
next if rule_title.nil? || rule_title.empty?
|
125
|
-
|
126
|
-
rule_title.find { |id| map_type(id) == 'title' }
|
127
|
-
alternate_ids = map(rule_title)
|
128
|
-
|
129
|
-
next unless rule_title.is_a?(String)
|
130
|
-
|
131
|
-
@rules[rule_title] = {} unless @rules&.key?(rule_title)
|
132
|
-
@rules[rule_title]['number'] = alternate_ids.find { |id| map_type(id) == 'number' }
|
133
|
-
@rules[rule_title]['alternate_ids'] = alternate_ids
|
134
|
-
@rules[rule_title]['params'] = [] unless @rules[rule_title].key?('params')
|
135
|
-
@rules[rule_title]['level'] = [] unless @rules[rule_title].key?('level')
|
136
|
-
@rules[rule_title]['profile'] = [] unless @rules[rule_title].key?('profile')
|
137
|
-
param_hashes(control_data).each do |param_hash|
|
138
|
-
next if @rules[rule_title]['params'].include?(param_hash[:name])
|
139
|
-
|
140
|
-
@rules[rule_title]['params'] << param_hash
|
141
|
-
end
|
142
|
-
levels, profiles = find_levels_and_profiles(control)
|
143
|
-
unless @rules[rule_title]['level'] == levels
|
144
|
-
@rules[rule_title]['level'] = @rules[rule_title]['level'] | levels
|
145
|
-
end
|
146
|
-
unless @rules[rule_title]['profile'] == profiles
|
147
|
-
@rules[rule_title]['profile'] = @rules[rule_title]['profile'] | profiles
|
148
|
-
end
|
149
|
-
@rules[rule_title]['resource'] = rdata['type']
|
150
|
-
end
|
151
|
-
end
|
152
|
-
@rules = sort_rules
|
153
|
-
end
|
154
|
-
|
155
|
-
def param_hashes(control_data)
|
156
|
-
return [] if control_data.nil? || control_data.empty?
|
157
|
-
|
158
|
-
p_hashes = []
|
159
|
-
if !control_data.respond_to?(:each) && control_data == 'no_params'
|
160
|
-
p_hashes << no_params
|
161
|
-
else
|
162
|
-
control_data.each do |param, param_val|
|
163
|
-
p_hashes << {
|
164
|
-
name: param,
|
165
|
-
type: ruby_class_to_puppet_type(param_val.class.to_s),
|
166
|
-
default: param_val,
|
167
|
-
}
|
168
|
-
end
|
169
|
-
end
|
170
|
-
p_hashes
|
171
|
-
end
|
172
|
-
|
173
|
-
def no_params
|
174
|
-
{ name: 'No parameters', type: nil, default: nil }
|
175
|
-
end
|
176
|
-
|
177
|
-
# We sort the rules by their control number so they
|
178
|
-
# appear in the REFERENCE in benchmark order
|
179
|
-
def sort_rules
|
180
|
-
sorted = @rules.dup.sort_by do |_, v|
|
181
|
-
control_num_to_int(v['number'])
|
182
|
-
end
|
183
|
-
sorted.to_h
|
184
|
-
end
|
185
|
-
|
186
|
-
# In order to sort the rules by their control number,
|
187
|
-
# we need to convert the control number to an integer.
|
188
|
-
# This is a rough conversion, but should be sufficient
|
189
|
-
# for the purposes of sorting. The multipliers are
|
190
|
-
# the 20th, 15th, 10th, and 5th numbers in the Fibonacci
|
191
|
-
# sequence, then 1 after that. The reason for this is to
|
192
|
-
# ensure a "spiraled" wieghting of the sections in the control
|
193
|
-
# number, with 1st section having the most sorting weight, 2nd
|
194
|
-
# having second most, etc. However, the differences in the multipliers
|
195
|
-
# are such that it would be difficult for the product of a lesser-weighted
|
196
|
-
# section to be greater than a greater-weighted section.
|
197
|
-
def control_num_to_int(control_num)
|
198
|
-
multipliers = [6765, 610, 55, 5, 1]
|
199
|
-
nsum = 0
|
200
|
-
midx = 0
|
201
|
-
control_num.split('.').each do |num|
|
202
|
-
multiplier = midx >= multipliers.length ? 1 : multipliers[midx]
|
203
|
-
nsum += num.to_i * multiplier
|
204
|
-
midx += 1
|
205
|
-
end
|
206
|
-
nsum
|
207
|
-
end
|
208
|
-
|
209
|
-
def find_levels_and_profiles(control_id)
|
210
|
-
levels = []
|
211
|
-
profiles = []
|
212
|
-
mapper.each_like(control_id) do |lvl, profile_hash|
|
213
|
-
next if lvl == 'benchmark'
|
214
|
-
|
215
|
-
profile_hash.each do |prof, _|
|
216
|
-
unless map(control_id, level: lvl, profile: prof).nil?
|
217
|
-
levels << lvl
|
218
|
-
profiles << prof
|
219
|
-
end
|
220
|
-
end
|
221
|
-
end
|
222
|
-
[levels, profiles]
|
223
|
-
end
|
224
|
-
|
225
|
-
def ruby_class_to_puppet_type(class_name)
|
226
|
-
pup_type = class_name.split('::').last.capitalize
|
227
|
-
case pup_type
|
228
|
-
when %r{(Trueclass|Falseclass)}
|
229
|
-
'Boolean'
|
230
|
-
when %r{(String|Pathname)}
|
231
|
-
'String'
|
232
|
-
when %r{(Integer|Fixnum)}
|
233
|
-
'Integer'
|
234
|
-
when %r{(Float|Double)}
|
235
|
-
'Float'
|
236
|
-
else
|
237
|
-
pup_type
|
238
|
-
end
|
239
|
-
end
|
240
|
-
|
241
437
|
def load_mapping_data
|
242
438
|
files = case module_name
|
243
439
|
when /_windows$/
|
@@ -248,8 +444,6 @@ module AbideDevUtils
|
|
248
444
|
raise "Module name '#{module_name}' is not a CEM module"
|
249
445
|
end
|
250
446
|
validate_mapping_files_framework(files).each_with_object({}) do |f, h|
|
251
|
-
next unless f.path.include?(framework)
|
252
|
-
|
253
447
|
h[File.basename(f.path, '.yaml')] = YAML.load_file(f.path)
|
254
448
|
end
|
255
449
|
end
|