Skip to content

Instantly share code, notes, and snippets.

@robvinson
Last active December 20, 2015 05:58
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save robvinson/6081872 to your computer and use it in GitHub Desktop.
Save robvinson/6081872 to your computer and use it in GitHub Desktop.
#!/usr/bin/env ruby
require 'openssl'
SHA1 = OpenSSL::Digest::SHA1.new
# Verified functionality against
# Test Vector (http://tools.ietf.org/html/draft-josefsson-pbkdf2-test-vectors-06#page-3)
# Input:
# P = "password" (8 octets)
# S = "salt" (4 octets)
# c = 4096
# dkLen = 20
#
# Output:
# DK = 4b 00 79 01 b7 65 48 9a
# be ad 49 d9 26 f7 21 d0
# 65 a4 29 c1 (20 octets)
# With a known salt and password and derived key, we can brute force the
# number of iterations it took to derive the key.
def bf_iteration(salt, password, derived_key, pbkdf2_dKeyLen)
(1..65536).each do |i|
try_iteration(salt, password, derived_key, pbkdf2_dKeyLen, i)
end
puts "Sorry, number of iterations not found"
end
def try_iteration(salt, password, hash, pbkdf2_dKeyLen, pbkdf2_num_iterations)
dk = OpenSSL::PKCS5.pbkdf2_hmac_sha1(password, salt, pbkdf2_num_iterations, pbkdf2_dKeyLen)
if dk == hash
puts "!!! Found, form of PBKDF2(salt, password, dKLen:#{pbkdf2_dKeyLen}, Iterations:#{pbkdf2_num_iterations})"
puts "input hash:#{hash.unpack('H*')[0]} generated hash:#{dk.unpack('H*')[0]}"
exit
elsif ((hash.length == 20) and (SHA1.digest(dk) == hash))
puts "!!! Found, form of SHA1(PBKDF2(salt, password, dKlen:#{pbkdf2_dKeyLen}, Iterations:#{pbkdf2_num_iterations}))"
puts "input hash:#{hash.unpack('H*')[0]} generated hash:#{SHA1.digest(dk).unpack('H*')[0]}"
exit
end
end
if ARGV.length != 3
puts "Usage: #{$0} password salt hash\n"
puts "Password: The password"
puts "Salt: salt bytes as a hex string"
puts "Hash: hash bytes as a hex string"
exit
end
password = ARGV[0]
salt_hex = ARGV[1]
hash_hex = ARGV[2]
unless ((salt_hex =~ /[0-9a-zA-z]/) and ((salt_hex.length % 2) == 0))
puts "Error: Invalid salt, try again"
exit
end
unless ((hash_hex =~ /[0-9a-zA-z]/) and ((hash_hex.length % 2) == 0))
puts "Error: Invalid key, try again"
exit
end
salt = [salt_hex].pack('H*')
hash = [hash_hex].pack('H*')
#bf_iteration(salt, password, hash, 20)
#[20, 24].each do |dklen|
(1..1024).each do |dklen|
puts "12,345 iterations: trying with derived key length of #{dklen}(#{dklen*8}bits)"
try_iteration(salt, password, hash, dklen, 12345)
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment