In this website: http://elijahcaine.me/remote-timing-attacks/ the author describes well what is a constant time attack and how to protect against this type of vulnerability.
But in the code that the author have done:
# secret.py
from time import sleep # Used to exaggerate time difference.
from sys import argv # Used to read user input.
def is_equal(a,b):
"""Custom `==` operator"""
# Fail if the strings aren't the right length
if len(a) != len(b):
return False
for i in range(len(a)):
# Short-circuit if the strings don't match
if a[i] != b[i]:
return False
sleep(0.15) # This exaggerates it just enough for our purposes
return True
# Hard-coded secret globals FOR DEMONSTRATIONS ONLY
secret = 'l33t'
# This is python for "If someone uses you as a script, do this"
if __name__ == '__main__':
try:
# The user got it right!
if is_equal(str(argv[1]), secret):
print('You got the secret!')
# The user got it wrong
else:
print('Try again!')
# The user forgot to enter a guess.
except IndexError:
print('Usage: python secret.py yourguess\n' \
+'The secret may consist of characters in [a-z0-9] '\
+'and is {} characters long.'.format(len(secret)))
I don't understand why we have to add this line to make the constant time attack succeed:
sleep(0.15) # This exaggerates it just enough for our purposes
In the website, the author says :
it exaggerates the time it takes to evaluate the is_equal function.
I've tried it, and we need a "sleep" method to make this attack succeed. Why we need to exaggerate the time?
Edit 1:
We need to exaggerate the time to showcase the time difference when two characters match and when they don't. So in this case, if the first character of a and b match, the method sleeps, then if the second characters don't match the function returns. This took 1 comparasion time + sleep(0.15) + 1 comparasion time. On the other hand, if the first characters don't match, the functions returns in 1 comparasion time, so the attacker can see, if they match any character or not. The example uses this sleep to demonstrate this time difference.
For this to not happen, the is_equal function should be implemented in a way, that the response time of the function is static.
Using the example you provided:
There is a built-in function in the secrets module which solves this problem. compare_digest()