mirror of
https://salsa.debian.org/freeipa-team/freeipa.git
synced 2024-12-23 15:40:01 -06:00
Explicitly remove support of SSLv2/3
It was possible to set tls_version_min/max to 'ssl2' or 'ssl3', even though newer versions of NSS will fail to set this as a valid TLS version. This patch explicitly checks for deprecated TLS versions prior to creating a TLS connection. Also, we don't allow tls_version_min/max to be set to a random string anymore. https://fedorahosted.org/freeipa/ticket/6607 Reviewed-By: Jan Cholasta <jcholast@redhat.com> Reviewed-By: Tomas Krizek <tkrizek@redhat.com>
This commit is contained in:
parent
d0642bfa55
commit
ac6f573a30
@ -41,8 +41,11 @@ from six.moves.configparser import RawConfigParser, ParsingError
|
||||
|
||||
from ipapython.dn import DN
|
||||
from ipalib.base import check_name
|
||||
from ipalib.constants import CONFIG_SECTION
|
||||
from ipalib.constants import OVERRIDE_ERROR, SET_ERROR, DEL_ERROR
|
||||
from ipalib.constants import (
|
||||
CONFIG_SECTION,
|
||||
OVERRIDE_ERROR, SET_ERROR, DEL_ERROR,
|
||||
TLS_VERSIONS
|
||||
)
|
||||
from ipalib import errors
|
||||
|
||||
if six.PY3:
|
||||
@ -578,6 +581,26 @@ class Env(object):
|
||||
|
||||
self._merge(**defaults)
|
||||
|
||||
# set the best known TLS version if min/max versions are not set
|
||||
if 'tls_version_min' not in self:
|
||||
self.tls_version_min = TLS_VERSIONS[-1]
|
||||
elif self.tls_version_min not in TLS_VERSIONS:
|
||||
raise errors.EnvironmentError(
|
||||
"Unknown TLS version '{ver}' set in tls_version_min."
|
||||
.format(ver=self.tls_version_min))
|
||||
|
||||
if 'tls_version_max' not in self:
|
||||
self.tls_version_max = TLS_VERSIONS[-1]
|
||||
elif self.tls_version_max not in TLS_VERSIONS:
|
||||
raise errors.EnvironmentError(
|
||||
"Unknown TLS version '{ver}' set in tls_version_max."
|
||||
.format(ver=self.tls_version_max))
|
||||
|
||||
if self.tls_version_max < self.tls_version_min:
|
||||
raise errors.EnvironmentError(
|
||||
"tls_version_min is set to a higher TLS version than "
|
||||
"tls_version_max.")
|
||||
|
||||
def _finalize(self, **lastchance):
|
||||
"""
|
||||
Finalize and lock environment.
|
||||
|
@ -283,3 +283,13 @@ ANON_USER = 'WELLKNOWN/ANONYMOUS'
|
||||
# IPA API Framework user
|
||||
IPAAPI_USER = 'ipaapi'
|
||||
IPAAPI_GROUP = 'ipaapi'
|
||||
|
||||
# TLS related constants
|
||||
TLS_VERSIONS = [
|
||||
"ssl2",
|
||||
"ssl3",
|
||||
"tls1.0",
|
||||
"tls1.1",
|
||||
"tls1.2"
|
||||
]
|
||||
TLS_VERSION_MINIMAL = "tls1.0"
|
||||
|
@ -23,6 +23,8 @@ from __future__ import print_function
|
||||
import getpass
|
||||
import socket
|
||||
from ipapython.ipa_log_manager import root_logger
|
||||
from ipapython.ipa_log_manager import log_mgr
|
||||
from ipalib.constants import TLS_VERSIONS, TLS_VERSION_MINIMAL
|
||||
|
||||
from nss.error import NSPRError
|
||||
import nss.io as io
|
||||
@ -38,6 +40,9 @@ except ImportError:
|
||||
# pylint: disable=import-error
|
||||
import http.client as httplib
|
||||
|
||||
# get a logger for this module
|
||||
logger = log_mgr.get_logger(__name__)
|
||||
|
||||
# NSS database currently open
|
||||
current_dbdir = None
|
||||
|
||||
@ -129,6 +134,56 @@ _af_dict = {
|
||||
socket.AF_UNSPEC: io.PR_AF_UNSPEC
|
||||
}
|
||||
|
||||
|
||||
def get_proper_tls_version_span(tls_version_min, tls_version_max):
|
||||
"""
|
||||
This function checks whether the given TLS versions are known in FreeIPA
|
||||
and that these versions fulfill the requirements for minimal TLS version
|
||||
(see `ipalib.constants: TLS_VERSIONS, TLS_VERSION_MINIMAL`).
|
||||
|
||||
:param tls_version_min:
|
||||
the lower value in the TLS min-max span, raised to the lowest allowed
|
||||
value if too low
|
||||
:param tls_version_max:
|
||||
the higher value in the TLS min-max span, raised to tls_version_min
|
||||
if lower than TLS_VERSION_MINIMAL
|
||||
:raises: ValueError
|
||||
"""
|
||||
min_allowed_idx = TLS_VERSIONS.index(TLS_VERSION_MINIMAL)
|
||||
|
||||
try:
|
||||
min_version_idx = TLS_VERSIONS.index(tls_version_min)
|
||||
except ValueError:
|
||||
raise ValueError("tls_version_min ('{val}') is not a known "
|
||||
"TLS version.".format(val=tls_version_min))
|
||||
|
||||
try:
|
||||
max_version_idx = TLS_VERSIONS.index(tls_version_max)
|
||||
except ValueError:
|
||||
raise ValueError("tls_version_max ('{val}') is not a known "
|
||||
"TLS version.".format(val=tls_version_max))
|
||||
|
||||
if min_version_idx > max_version_idx:
|
||||
raise ValueError("tls_version_min is higher than "
|
||||
"tls_version_max.")
|
||||
|
||||
if min_version_idx < min_allowed_idx:
|
||||
min_version_idx = min_allowed_idx
|
||||
logger.warning("tls_version_min set too low ('{old}'),"
|
||||
"using '{new}' instead"
|
||||
.format(old=tls_version_min,
|
||||
new=TLS_VERSIONS[min_version_idx]))
|
||||
|
||||
if max_version_idx < min_allowed_idx:
|
||||
max_version_idx = min_version_idx
|
||||
logger.warning("tls_version_max set too low ('{old}'),"
|
||||
"using '{new}' instead"
|
||||
.format(old=tls_version_max,
|
||||
new=TLS_VERSIONS[max_version_idx]))
|
||||
|
||||
return TLS_VERSIONS[min_version_idx:max_version_idx+1]
|
||||
|
||||
|
||||
class NSSAddressFamilyFallback(object):
|
||||
def __init__(self, family):
|
||||
self.sock_family = family
|
||||
@ -217,8 +272,10 @@ class NSSConnection(httplib.HTTPConnection, NSSAddressFamilyFallback):
|
||||
|
||||
ssl.set_domestic_policy()
|
||||
nss.set_password_callback(self.password_callback)
|
||||
self.tls_version_min = str(tls_version_min)
|
||||
self.tls_version_max = str(tls_version_max)
|
||||
tls_versions = get_proper_tls_version_span(
|
||||
tls_version_min, tls_version_max)
|
||||
self.tls_version_min = tls_versions[0]
|
||||
self.tls_version_max = tls_versions[-1]
|
||||
|
||||
def _create_socket(self):
|
||||
ssl_enable_renegotiation = getattr(
|
||||
|
Loading…
Reference in New Issue
Block a user