summaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authorJeff Forcier <jeff@bitprophet.org>2015-09-30 15:44:08 -0700
committerJeff Forcier <jeff@bitprophet.org>2015-09-30 15:44:08 -0700
commitff7c400d3d54f233fb5fe82d7233bc2f93f5aab4 (patch)
tree60495d398e5b8a8b65d5447c79ed97a46e6df2e7
parentc0f1da60bd7da55bf7a2051a329192c1c018f099 (diff)
parent8bf03014128b074bf6988100f18e48a94671cca2 (diff)
Merge branch '1.15'
-rw-r--r--paramiko/auth_handler.py24
-rw-r--r--paramiko/kex_gss.py5
-rw-r--r--paramiko/server.py2
-rw-r--r--paramiko/ssh_gss.py31
-rw-r--r--sites/www/changelog.rst3
5 files changed, 26 insertions, 39 deletions
diff --git a/paramiko/auth_handler.py b/paramiko/auth_handler.py
index c001aeee..ef4a8c7e 100644
--- a/paramiko/auth_handler.py
+++ b/paramiko/auth_handler.py
@@ -34,7 +34,7 @@ from paramiko.common import cMSG_SERVICE_REQUEST, cMSG_DISCONNECT, \
cMSG_USERAUTH_GSSAPI_ERRTOK, cMSG_USERAUTH_GSSAPI_MIC,\
MSG_USERAUTH_GSSAPI_RESPONSE, MSG_USERAUTH_GSSAPI_TOKEN, \
MSG_USERAUTH_GSSAPI_EXCHANGE_COMPLETE, MSG_USERAUTH_GSSAPI_ERROR, \
- MSG_USERAUTH_GSSAPI_ERRTOK, MSG_USERAUTH_GSSAPI_MIC
+ MSG_USERAUTH_GSSAPI_ERRTOK, MSG_USERAUTH_GSSAPI_MIC, MSG_NAMES
from paramiko.message import Message
from paramiko.py3compat import bytestring
@@ -510,15 +510,11 @@ class AuthHandler (object):
result = AUTH_FAILED
self._send_auth_result(username, method, result)
raise
- if retval == 0:
- # TODO: Implement client credential saving.
- # The OpenSSH server is able to create a TGT with the delegated
- # client credentials, but this is not supported by GSS-API.
- result = AUTH_SUCCESSFUL
- self.transport.server_object.check_auth_gssapi_with_mic(
- username, result)
- else:
- result = AUTH_FAILED
+ # TODO: Implement client credential saving.
+ # The OpenSSH server is able to create a TGT with the delegated
+ # client credentials, but this is not supported by GSS-API.
+ result = AUTH_SUCCESSFUL
+ self.transport.server_object.check_auth_gssapi_with_mic(username, result)
elif method == "gssapi-keyex" and gss_auth:
mic_token = m.get_string()
sshgss = self.transport.kexgss_ctxt
@@ -534,12 +530,8 @@ class AuthHandler (object):
result = AUTH_FAILED
self._send_auth_result(username, method, result)
raise
- if retval == 0:
- result = AUTH_SUCCESSFUL
- self.transport.server_object.check_auth_gssapi_keyex(username,
- result)
- else:
- result = AUTH_FAILED
+ result = AUTH_SUCCESSFUL
+ self.transport.server_object.check_auth_gssapi_keyex(username, result)
else:
result = self.transport.server_object.check_auth_none(username)
# okay, send result
diff --git a/paramiko/kex_gss.py b/paramiko/kex_gss.py
index d026807c..69969f8a 100644
--- a/paramiko/kex_gss.py
+++ b/paramiko/kex_gss.py
@@ -37,6 +37,7 @@ This module provides GSS-API / SSPI Key Exchange as defined in :rfc:`4462`.
.. versionadded:: 1.15
"""
+import os
from hashlib import sha1
from paramiko.common import *
@@ -130,7 +131,7 @@ class KexGSSGroup1(object):
larger than q (but this is a tiny tiny subset of potential x).
"""
while 1:
- x_bytes = self.transport.rng.read(128)
+ x_bytes = os.urandom(128)
x_bytes = byte_mask(x_bytes[0], 0x7f) + x_bytes[1:]
if (x_bytes[:8] != self.b7fffffffffffffff) and \
(x_bytes[:8] != self.b0000000000000000):
@@ -366,7 +367,7 @@ class KexGSSGex(object):
qhbyte <<= 1
qmask >>= 1
while True:
- x_bytes = self.transport.rng.read(byte_count)
+ x_bytes = os.urandom(byte_count)
x_bytes = byte_mask(x_bytes[0], qmask) + x_bytes[1:]
x = util.inflate_long(x_bytes, 1)
if (x > 1) and (x < q):
diff --git a/paramiko/server.py b/paramiko/server.py
index bf5039a2..f79a1748 100644
--- a/paramiko/server.py
+++ b/paramiko/server.py
@@ -22,7 +22,7 @@
import threading
from paramiko import util
-from paramiko.common import DEBUG, ERROR, OPEN_FAILED_ADMINISTRATIVELY_PROHIBITED, AUTH_FAILED
+from paramiko.common import DEBUG, ERROR, OPEN_FAILED_ADMINISTRATIVELY_PROHIBITED, AUTH_FAILED, AUTH_SUCCESSFUL
from paramiko.py3compat import string_types
diff --git a/paramiko/ssh_gss.py b/paramiko/ssh_gss.py
index aa28e2ec..e9b13a66 100644
--- a/paramiko/ssh_gss.py
+++ b/paramiko/ssh_gss.py
@@ -360,8 +360,8 @@ class _SSH_GSSAPI(_SSH_GSSAuth):
:param str mic_token: The MIC token received from the client
:param str session_id: The SSH session ID
:param str username: The name of the user who attempts to login
- :return: 0 if the MIC check was successful and 1 if it fails
- :rtype: int
+ :return: None if the MIC check was successful
+ :raises gssapi.GSSException: if the MIC check failed
"""
self._session_id = session_id
self._username = username
@@ -371,11 +371,7 @@ class _SSH_GSSAPI(_SSH_GSSAuth):
self._username,
self._service,
self._auth_method)
- try:
- self._gss_srv_ctxt.verify_mic(mic_field,
- mic_token)
- except gssapi.BadSignature:
- raise Exception("GSS-API MIC check failed.")
+ self._gss_srv_ctxt.verify_mic(mic_field, mic_token)
else:
# for key exchange with gssapi-keyex
# client mode
@@ -534,31 +530,26 @@ class _SSH_SSPI(_SSH_GSSAuth):
:param str mic_token: The MIC token received from the client
:param str session_id: The SSH session ID
:param str username: The name of the user who attempts to login
- :return: 0 if the MIC check was successful
- :rtype: int
+ :return: None if the MIC check was successful
+ :raises sspi.error: if the MIC check failed
"""
self._session_id = session_id
self._username = username
- mic_status = 1
if username is not None:
# server mode
mic_field = self._ssh_build_mic(self._session_id,
self._username,
self._service,
self._auth_method)
- mic_status = self._gss_srv_ctxt.verify(mic_field,
- mic_token)
+ # Verifies data and its signature. If verification fails, an
+ # sspi.error will be raised.
+ self._gss_srv_ctxt.verify(mic_field, mic_token)
else:
# for key exchange with gssapi-keyex
# client mode
- mic_status = self._gss_ctxt.verify(self._session_id,
- mic_token)
- """
- The SSPI method C{verify} has no return value, so if no SSPI error
- is returned, set C{mic_status} to 0.
- """
- mic_status = 0
- return mic_status
+ # Verifies data and its signature. If verification fails, an
+ # sspi.error will be raised.
+ self._gss_ctxt.verify(self._session_id, mic_token)
@property
def credentials_delegated(self):
diff --git a/sites/www/changelog.rst b/sites/www/changelog.rst
index bbc89b75..df4a8d82 100644
--- a/sites/www/changelog.rst
+++ b/sites/www/changelog.rst
@@ -2,6 +2,9 @@
Changelog
=========
+* :bug:`496` Fix a handful of small but critical bugs in Paramiko's GSSAPI
+ support (note: this includes switching from PyCrypo's Random to
+ `os.urandom`). Thanks to Anselm Kruis for catch & patch.
* :bug:`491` (combines :issue:`62` and :issue:`439`) Implement timeout
functionality to address hangs from dropped network connections and/or failed
handshakes. Credit to ``@vazir`` and ``@dacut`` for the original patches and