2015-06-07 15:09:02 +00:00
|
|
|
|
# encoding: utf-8
|
2015-07-15 13:15:18 +00:00
|
|
|
|
# copyright: 2015, Vulcano Security GmbH
|
2015-10-06 16:55:44 +00:00
|
|
|
|
# author: Christoph Hartmann
|
2015-06-07 15:09:02 +00:00
|
|
|
|
# license: All rights reserved
|
|
|
|
|
|
2015-04-17 13:37:17 +00:00
|
|
|
|
require 'json'
|
|
|
|
|
|
2015-09-05 20:36:32 +00:00
|
|
|
|
# Usage:
|
|
|
|
|
# describe registry_key('Task Scheduler','HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\services\Schedule') do
|
|
|
|
|
# its('Start') { should eq 2 }
|
|
|
|
|
# end
|
|
|
|
|
|
2015-10-26 03:04:18 +00:00
|
|
|
|
class RegistryKey < Inspec.resource(1)
|
2015-08-28 18:52:22 +00:00
|
|
|
|
name 'registry_key'
|
2015-04-17 13:37:17 +00:00
|
|
|
|
|
2015-07-26 10:30:12 +00:00
|
|
|
|
attr_accessor :reg_key
|
2015-04-17 13:37:17 +00:00
|
|
|
|
|
2015-08-28 18:52:22 +00:00
|
|
|
|
def initialize(name, reg_key = nil)
|
|
|
|
|
# if we have one parameter, we use it as name
|
2015-09-09 16:52:27 +00:00
|
|
|
|
reg_key ||= name
|
2015-08-28 18:52:22 +00:00
|
|
|
|
@name = name
|
|
|
|
|
@reg_key = reg_key
|
|
|
|
|
end
|
|
|
|
|
|
2015-11-17 21:10:16 +00:00
|
|
|
|
def exists?
|
|
|
|
|
!registry_value(@reg_key).nil?
|
2015-07-26 10:30:12 +00:00
|
|
|
|
end
|
2015-04-17 13:37:17 +00:00
|
|
|
|
|
2015-11-17 21:10:16 +00:00
|
|
|
|
def has_value?(value)
|
|
|
|
|
val = registry_value(@reg_key)
|
|
|
|
|
!val.nil? && val['(default)'.to_s]['value'] == value ? true : false
|
|
|
|
|
end
|
|
|
|
|
|
|
|
|
|
def has_property?(property_name, property_type = nil)
|
|
|
|
|
val = registry_value(@reg_key)
|
|
|
|
|
!val.nil? && !val[property_name.to_s].nil? && (property_type.nil? || val[property_name.to_s]['type'] == map2type(property_type)) ? true : false
|
|
|
|
|
end
|
|
|
|
|
|
|
|
|
|
# deactivate rubocop, because we need to stay compatible with Serverspe
|
|
|
|
|
# rubocop:disable Style/OptionalArguments
|
|
|
|
|
def has_property_value?(property_name, property_type = nil, value)
|
|
|
|
|
# rubocop:enable Style/OptionalArguments
|
|
|
|
|
val = registry_value(@reg_key)
|
|
|
|
|
|
|
|
|
|
# convert value to binary if required
|
|
|
|
|
value = value.bytes if !property_type.nil? && map2type(property_type) == 3 && !value.is_a?(Array)
|
|
|
|
|
|
|
|
|
|
!val.nil? && val[property_name.to_s]['value'] == value && (property_type.nil? || val[property_name.to_s]['type'] == map2type(property_type)) ? true : false
|
2015-07-26 10:30:12 +00:00
|
|
|
|
end
|
2015-04-17 13:37:17 +00:00
|
|
|
|
|
2015-07-26 10:30:12 +00:00
|
|
|
|
# returns nil, if not existant or value
|
|
|
|
|
def method_missing(meth)
|
|
|
|
|
# get data
|
2015-11-17 21:10:16 +00:00
|
|
|
|
val = registry_value(@reg_key)
|
|
|
|
|
return nil if val.nil?
|
|
|
|
|
val[meth.to_s]['value']
|
2015-07-26 10:30:12 +00:00
|
|
|
|
end
|
2015-04-17 13:37:17 +00:00
|
|
|
|
|
2015-07-26 10:30:12 +00:00
|
|
|
|
def to_s
|
|
|
|
|
"Registry Key #{@name}"
|
|
|
|
|
end
|
2015-11-17 21:10:16 +00:00
|
|
|
|
|
|
|
|
|
private
|
|
|
|
|
|
|
|
|
|
def registry_value(path)
|
|
|
|
|
return @registy_cache if defined?(@registy_cache)
|
|
|
|
|
|
|
|
|
|
# load registry key and all properties
|
|
|
|
|
script = <<-EOH
|
|
|
|
|
$reg = Get-Item 'Registry::#{path}'
|
|
|
|
|
$object = New-Object -Type PSObject
|
|
|
|
|
$reg.Property | ForEach-Object {
|
|
|
|
|
$key = $_
|
|
|
|
|
if ("(default)".Equals($key)) { $key = '' }
|
|
|
|
|
$value = New-Object psobject -Property @{
|
|
|
|
|
"value" = $reg.GetValue($key);
|
|
|
|
|
"type" = $reg.GetValueKind($key);
|
|
|
|
|
}
|
|
|
|
|
$object | Add-Member –MemberType NoteProperty –Name $_ –Value $value
|
|
|
|
|
}
|
|
|
|
|
$object | ConvertTo-Json
|
|
|
|
|
EOH
|
|
|
|
|
|
|
|
|
|
cmd = inspec.script(script)
|
|
|
|
|
|
|
|
|
|
# cannot rely on exit code for now, successful command returns exit code 1
|
|
|
|
|
# return nil if cmd.exit_status != 0, try to parse json
|
|
|
|
|
begin
|
|
|
|
|
@registy_cache = JSON.parse(cmd.stdout)
|
|
|
|
|
rescue JSON::ParserError => _e
|
|
|
|
|
@registy_cache = nil
|
|
|
|
|
end
|
|
|
|
|
|
|
|
|
|
@registy_cache
|
|
|
|
|
end
|
|
|
|
|
|
|
|
|
|
# Registry key value types
|
|
|
|
|
# @see https://msdn.microsoft.com/en-us/library/windows/desktop/ms724884(v=vs.85).aspx
|
|
|
|
|
# REG_NONE 0
|
|
|
|
|
# REG_SZ 1
|
|
|
|
|
# REG_EXPAND_SZ 2
|
|
|
|
|
# REG_BINARY 3
|
|
|
|
|
# REG_DWORD 4
|
|
|
|
|
# REG_DWORD_LITTLE_ENDIAN 4
|
|
|
|
|
# REG_DWORD_BIG_ENDIAN 5
|
|
|
|
|
# REG_LINK 6
|
|
|
|
|
# REG_MULTI_SZ 7
|
|
|
|
|
# REG_RESOURCE_LIST 8
|
|
|
|
|
# REG_FULL_RESOURCE_DESCRIPTOR 9
|
|
|
|
|
# REG_RESOURCE_REQUIREMENTS_LIST 10
|
|
|
|
|
# REG_QWORD 11
|
|
|
|
|
# REG_QWORD_LITTLE_ENDIAN 11
|
|
|
|
|
def map2type(symbol)
|
|
|
|
|
options = {}
|
|
|
|
|
|
|
|
|
|
# chef symbols, we prefer those
|
|
|
|
|
options[:binary] = 3
|
|
|
|
|
options[:string] = 1
|
|
|
|
|
options[:multi_string] = 7
|
|
|
|
|
options[:expand_string] = 2
|
|
|
|
|
options[:dword] = 4
|
|
|
|
|
options[:dword_big_endian] = 5
|
|
|
|
|
options[:qword] = 11
|
|
|
|
|
|
|
|
|
|
# serverspec symbols
|
|
|
|
|
options[:type_string] = 1
|
|
|
|
|
options[:type_binary] = 3
|
|
|
|
|
options[:type_dword] = 4
|
|
|
|
|
options[:type_qword] = 11
|
|
|
|
|
options[:type_multistring] = 7
|
|
|
|
|
options[:type_expandstring] = 2
|
|
|
|
|
|
|
|
|
|
options[symbol]
|
|
|
|
|
end
|
|
|
|
|
end
|
|
|
|
|
|
|
|
|
|
# for compatability with serverspec
|
|
|
|
|
# this is deprecated syntax and will be removed in future versions
|
|
|
|
|
class WindowsRegistryKey < RegistryKey
|
|
|
|
|
name 'windows_registry_key'
|
|
|
|
|
|
|
|
|
|
def initialize(name)
|
|
|
|
|
deprecated
|
|
|
|
|
super(name)
|
|
|
|
|
end
|
|
|
|
|
|
|
|
|
|
def deprecated
|
|
|
|
|
warn '[DEPRECATION] `yumrepo(reponame)` is deprecated. Please use `yum.repo(reponame)` instead.'
|
|
|
|
|
end
|
2015-07-26 10:30:12 +00:00
|
|
|
|
end
|