- make sure we honor 2-factor for all auth_pkey blocks

- explicit check for ['password'] as remaining auth type
(cherry picked from commit 53a3421da6d74333c4679fd6289d418917833b44)
This commit is contained in:
Andrew 2012-08-02 22:56:40 -07:00 committed by Jeff Forcier
parent b592eb1074
commit 38dec6fc5b
1 changed files with 27 additions and 21 deletions

View File

@ -423,27 +423,33 @@ class SSHClient (object):
The password is required for two-factor authentication.
"""
saved_exception = None
two_factor = False
if pkey is not None:
try:
self._log(DEBUG, 'Trying SSH key %s' % hexlify(pkey.get_fingerprint()))
self._transport.auth_publickey(username, pkey)
return
allowed_types = self._transport.auth_publickey(username, pkey)
two_factor = (allowed_types == ['password'])
if not two_factor:
return
except SSHException, e:
saved_exception = e
for key_filename in key_filenames:
for pkey_class in (RSAKey, DSSKey):
try:
key = pkey_class.from_private_key_file(key_filename, password)
self._log(DEBUG, 'Trying key %s from %s' % (hexlify(key.get_fingerprint()), key_filename))
self._transport.auth_publickey(username, key)
return
except SSHException, e:
saved_exception = e
if not two_factor:
for key_filename in key_filenames:
for pkey_class in (RSAKey, DSSKey):
try:
key = pkey_class.from_private_key_file(key_filename, password)
self._log(DEBUG, 'Trying key %s from %s' % (hexlify(key.get_fingerprint()), key_filename))
self._transport.auth_publickey(username, key)
two_factor = (allowed_types == ['password'])
if not two_factor:
return
break
except SSHException, e:
saved_exception = e
two_factor = False
if allow_agent:
if not two_factor and allow_agent:
if self._agent == None:
self._agent = Agent()
@ -451,14 +457,15 @@ class SSHClient (object):
try:
self._log(DEBUG, 'Trying SSH agent key %s' % hexlify(key.get_fingerprint()))
# for 2-factor auth a successfully auth'd key will result in ['password']
remaining_auth_types = self._transport.auth_publickey(username, key)
if not remaining_auth_types:
allowed_types = self._transport.auth_publickey(username, key)
two_factor = (allowed_types == ['password'])
if not two_factor:
return
two_factor = True
break
except SSHException, e:
saved_exception = e
else:
if not two_factor:
keyfiles = []
rsa_key = os.path.expanduser('~/.ssh/id_rsa')
dsa_key = os.path.expanduser('~/.ssh/id_dsa')
@ -482,10 +489,10 @@ class SSHClient (object):
key = pkey_class.from_private_key_file(filename, password)
self._log(DEBUG, 'Trying discovered key %s in %s' % (hexlify(key.get_fingerprint()), filename))
# for 2-factor auth a successfully auth'd key will result in ['password']
remaining_auth_types = self._transport.auth_publickey(username, key)
if not remaining_auth_types:
allowed_types = self._transport.auth_publickey(username, key)
two_factor = (allowed_types == ['password'])
if not two_factor:
return
two_factor = True
break
except SSHException, e:
saved_exception = e
@ -499,7 +506,6 @@ class SSHClient (object):
except SSHException, e:
saved_exception = e
elif two_factor:
# for 2-factor auth requires a password
raise SSHException('Two-factor authentication requires a password')
# if we got an auth-failed exception earlier, re-raise it