def get_channel_bindings(ssl_socket): try: server_certificate = ssl_socket.getpeercert(True) except: # it is not SSL socket return None try: from cryptography import x509 from cryptography.hazmat.backends import default_backend from cryptography.hazmat.primitives import hashes except ImportError: raise LDAPPackageUnavailableError('package cryptography missing') cert = x509.load_der_x509_certificate(server_certificate, default_backend()) hash_algorithm = cert.signature_hash_algorithm # According to https://tools.ietf.org/html/rfc5929#section-4.1, we have to convert the the hash function for md5 and sha1 if hash_algorithm.name in ('md5', 'sha1'): digest = hashes.Hash(hashes.SHA256(), default_backend()) else: digest = hashes.Hash(hash_algorithm, default_backend()) digest.update(server_certificate) application_data = b'tls-server-end-point:' + digest.finalize() # posix gssapi and windows winkerberos use different channel bindings classes if not posix_gssapi_unavailable: return ChannelBindings(application_data=application_data) else: return winkerberos.channelBindings(application_data=application_data)
def init_context(self): if self.auth_provider != self._AUTH_PROVIDERS['kerberos']: name_type = gssapi.NameType.user else: name_type = gssapi.NameType.kerberos_principal mech = gssapi.OID.from_int_seq(self.auth_provider) cbt_app_data = None if self.cbt_app_data is not None: cbt_app_data = ChannelBindings(application_data=self.cbt_app_data) log.debug("GSSAPI: Acquiring security context for user %s with mech " "%s" % (self.username, self.auth_provider)) self._context = GSSAPIContext._get_security_context( name_type, mech, self._target_spn, self.username, self.password, self._delegate, self.wrap_required, cbt_app_data)
def __init__(self, username=None, password=None, hostname=None, service=None, channel_bindings=None, context_req=ContextReq.default, usage='initiate', protocol='negotiate', options=0, _is_wrapped=False): if not HAS_GSSAPI: reraise( ImportError("GSSAPIProxy requires the Python gssapi library"), GSSAPI_IMP_ERR) super(GSSAPIProxy, self).__init__(username, password, hostname, service, channel_bindings, context_req, usage, protocol, options, _is_wrapped) mech_str = { 'kerberos': GSSMech.kerberos.value, 'negotiate': GSSMech.spnego.value, 'ntlm': GSSMech.ntlm.value, }[self.protocol] mech = gssapi.OID.from_int_seq(mech_str) cred = None try: cred = _get_gssapi_credential(mech, self.usage, username=username, password=password, context_req=context_req) except GSSError as gss_err: reraise( SpnegoError(base_error=gss_err, context_msg="Getting GSSAPI credential")) context_kwargs = {} if self.channel_bindings: context_kwargs['channel_bindings'] = ChannelBindings( initiator_address_type=self.channel_bindings. initiator_addrtype, initiator_address=self.channel_bindings.initiator_address, acceptor_address_type=self.channel_bindings.acceptor_addrtype, acceptor_address=self.channel_bindings.acceptor_address, application_data=self.channel_bindings.application_data) if self.usage == 'initiate': spn = to_text("%s@%s" % (service.lower() if service else 'host', hostname or 'unspecified')) context_kwargs['name'] = gssapi.Name( spn, name_type=gssapi.NameType.hostbased_service) context_kwargs['mech'] = mech context_kwargs['flags'] = self._context_req self._context = gssapi.SecurityContext(creds=cred, usage=self.usage, **context_kwargs)