Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix: Use constant time comparison for HMAC #35

Merged
merged 1 commit into from Sep 5, 2016
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
fix: Use constant time comparison for HMAC
  • Loading branch information
Michael Davis committed Sep 5, 2016
commit 89b46353b9f611e9da38de3d2fedf52331167b93
3 changes: 2 additions & 1 deletion jose/jwk.py
Expand Up @@ -19,6 +19,7 @@
from jose.constants import ALGORITHMS
from jose.exceptions import JWKError
from jose.utils import base64url_decode
from jose.utils import constant_time_string_compare

# PyCryptodome's RSA module doesn't have PyCrypto's _RSAobj class
# Instead it has a class named RsaKey, which serves the same purpose.
Expand Down Expand Up @@ -159,7 +160,7 @@ def sign(self, msg):
return hmac.new(self.prepared_key, msg, self.hash_alg).digest()

def verify(self, msg, sig):
return sig == self.sign(msg)
return constant_time_string_compare(sig, self.sign(msg))


class RSAKey(Key):
Expand Down
25 changes: 25 additions & 0 deletions jose/utils.py
@@ -1,5 +1,6 @@

import base64
import hmac


def calculate_at_hash(access_token, hash_alg):
Expand Down Expand Up @@ -58,3 +59,27 @@ def timedelta_total_seconds(delta):
delta (timedelta): A timedelta to convert to seconds.
"""
return delta.days * 24 * 60 * 60 + delta.seconds


def constant_time_string_compare(a, b):
"""Helper for comparing string in constant time, independent
of the python version being used.

Args:
a (str): A string to compare
b (str): A string to compare
"""

try:
return hmac.compare_digest(a, b)
except AttributeError:

if len(a) != len(b):
return False

result = 0

for x, y in zip(a, b):
result |= ord(x) ^ ord(y)

return result == 0