mirror of
https://github.com/rails/rails.git
synced 2022-11-09 12:12:34 -05:00
Fix timing attack vulnerability in ActiveSupport::MessageVerifier.
Use a constant-time comparison algorithm to compare the candidate HMAC with the calculated HMAC to prevent leaking information about the calculated HMAC. Signed-off-by: Michael Koziarski <michael@koziarski.com>
This commit is contained in:
parent
bd97c3044a
commit
5e6dab8b34
1 changed files with 16 additions and 3 deletions
|
@ -25,10 +25,10 @@ module ActiveSupport
|
||||||
|
|
||||||
def verify(signed_message)
|
def verify(signed_message)
|
||||||
data, digest = signed_message.split("--")
|
data, digest = signed_message.split("--")
|
||||||
if digest != generate_digest(data)
|
if secure_compare(digest, generate_digest(data))
|
||||||
raise InvalidSignature
|
|
||||||
else
|
|
||||||
Marshal.load(ActiveSupport::Base64.decode64(data))
|
Marshal.load(ActiveSupport::Base64.decode64(data))
|
||||||
|
else
|
||||||
|
raise InvalidSignature
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -38,6 +38,19 @@ module ActiveSupport
|
||||||
end
|
end
|
||||||
|
|
||||||
private
|
private
|
||||||
|
# constant-time comparison algorithm to prevent timing attacks
|
||||||
|
def secure_compare(a, b)
|
||||||
|
if a.length == b.length
|
||||||
|
result = 0
|
||||||
|
for i in 0..(a.length - 1)
|
||||||
|
result |= a[i] ^ b[i]
|
||||||
|
end
|
||||||
|
result == 0
|
||||||
|
else
|
||||||
|
false
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
def generate_digest(data)
|
def generate_digest(data)
|
||||||
require 'openssl' unless defined?(OpenSSL)
|
require 'openssl' unless defined?(OpenSSL)
|
||||||
OpenSSL::HMAC.hexdigest(OpenSSL::Digest::Digest.new(@digest), @secret, data)
|
OpenSSL::HMAC.hexdigest(OpenSSL::Digest::Digest.new(@digest), @secret, data)
|
||||||
|
|
Loading…
Reference in a new issue