Module: Msf::Util::WindowsRegistry::Sam
- Defined in:
- lib/msf/util/windows_registry/sam.rb
Overview
This module include helpers for the SAM hive
Instance Method Summary collapse
-
#get_hboot_key(boot_key) ⇒ String
Returns the HashedBootKey from a given BootKey.
-
#get_user_keys(&block) ⇒ Hash
Returns the ‘Users` key information under HKLMSAMDomainsAccountUsers.
- #normalize_key(key) ⇒ Object
Instance Method Details
#get_hboot_key(boot_key) ⇒ String
Returns the HashedBootKey from a given BootKey.
19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 |
# File 'lib/msf/util/windows_registry/sam.rb', line 19 def get_hboot_key(boot_key) qwerty = "!@#$%^&*()qwertyUIOPAzxcvbnmQQQQQQQQQQQQ)(*@&%\0" digits = "0123456789012345678901234567890123456789\0" _value_type, value_data = get_value(normalize_key('HKLM\\SAM\\SAM\\Domains\\Account'), 'F') revision = value_data[0x68, 4].unpack('V')[0] case revision when 1 hash = Digest::MD5.new hash.update(value_data[0x70, 16] + qwerty + boot_key + digits) rc4 = OpenSSL::Cipher.new('rc4') rc4.decrypt rc4.key = hash.digest hboot_key = rc4.update(value_data[0x80, 32]) hboot_key << rc4.final hboot_key when 2 aes = OpenSSL::Cipher.new('aes-128-cbc') aes.decrypt aes.key = boot_key aes.padding = 0 aes.iv = value_data[0x78, 16] aes.update(value_data[0x88, 16]) # we need only 16 bytes else elog("[Msf::Util::WindowsRegistry::Sam::get_hboot_key] Unknown hbootKey revision: #{revision}") ''.b end end |
#get_user_keys(&block) ⇒ Hash
Returns the ‘Users` key information under HKLMSAMDomainsAccountUsers. This includes the RID, name and `V` value for each user.
56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 |
# File 'lib/msf/util/windows_registry/sam.rb', line 56 def get_user_keys(&block) users = {} users_key = normalize_key('HKLM\\SAM\\SAM\\Domains\\Account\\Users') rids = enum_key(users_key) if rids rids.delete('Names') rids.each do |rid| rid = rid.to_s rid.encode!(::Encoding::UTF_8) unless rid.encoding == ::Encoding::UTF_8 key = "#{users_key}\\#{rid}" yield key if block _value_type, value_data = get_value(key, 'V') next unless value_data users[rid.to_i(16)] ||= {} users[rid.to_i(16)][:V] = value_data # Attempt to get Hints _value_type, value_data = get_value("#{users_key}\\#{rid}", 'UserPasswordHint') next unless value_data users[rid.to_i(16)][:UserPasswordHint] = value_data.dup.force_encoding(::Encoding::UTF_16LE).encode(::Encoding::UTF_8).strip end end # Retrieve the user names for each RID # TODO: use a proper structure to do this, since the user names are included in V data names = enum_key("#{users_key}\\Names") if names names.each do |name| name = name.to_s name.encode!(::Encoding::UTF_8) unless name.encoding == ::Encoding::UTF_8 key = "#{users_key}\\Names\\#{name}" yield key if block value_type, _value_data = get_value(key, '') users[value_type] ||= {} # Apparently, key names are ISO-8859-1 encoded users[value_type][:Name] = name.dup.force_encoding(::Encoding::ISO_8859_1).encode(::Encoding::UTF_8) end end users end |
#normalize_key(key) ⇒ Object
10 11 12 |
# File 'lib/msf/util/windows_registry/sam.rb', line 10 def normalize_key(key) @root.blank? ? key : key.delete_prefix(@root) end |