Ejemplo n.º 1
0
Archivo: xtls.py Proyecto: clones/kaa
 def x509_init(self):
     """
     Set of X.509 certificate and read known_clients file.
     """
     pemfile = os.path.join(xmpp.config.cachedir, self.client.appname + '.pem')
     if not os.path.isfile(pemfile):
         # FIXME: hide output and check for openssl
         os.system("openssl req -subj '/CN=%s' -x509 -nodes -days 365 -newkey "\
             "rsa:1024 -keyout %s -out %s" % (self.client.appname, pemfile, pemfile))
     self.x509_keyinfo = KeyInfo()
     self.x509_keyinfo.load_pemfile(pemfile)
     self.known_clients_x509 = []
     known = os.path.join(xmpp.config.cachedir, 'known_clients')
     if os.path.isfile(known):
         for line in open(known).readlines():
             key = KeyInfo()
             key.certificate.base64 = line.split(' ')[1]
             self.known_clients_x509.append(key.certificate)
Ejemplo n.º 2
0
Archivo: xtls.py Proyecto: clones/kaa
class Credentials(object):
    """
    Credentials for TLS authentication. As a default X.509
    certificates from known_clients are read and openssl is used to
    create a client certificate.
    """
    def __init__(self, client):
        self.client = client
        self.x509_init()

    def x509_init(self):
        """
        Set of X.509 certificate and read known_clients file.
        """
        pemfile = os.path.join(xmpp.config.cachedir, self.client.appname + '.pem')
        if not os.path.isfile(pemfile):
            # FIXME: hide output and check for openssl
            os.system("openssl req -subj '/CN=%s' -x509 -nodes -days 365 -newkey "\
                "rsa:1024 -keyout %s -out %s" % (self.client.appname, pemfile, pemfile))
        self.x509_keyinfo = KeyInfo()
        self.x509_keyinfo.load_pemfile(pemfile)
        self.known_clients_x509 = []
        known = os.path.join(xmpp.config.cachedir, 'known_clients')
        if os.path.isfile(known):
            for line in open(known).readlines():
                key = KeyInfo()
                key.certificate.base64 = line.split(' ')[1]
                self.known_clients_x509.append(key.certificate)

    def x509_supported(self):
        """
        Return if X.509 certificates are supported. Default is true.
        """
        return True

    def x509_check(self, certificate):
        """
        Check the remote certificate. The default behaviour is only to
        allow known clients. If the certificate is ok, return True.
        """
        return certificate.validate(self.known_clients_x509)

    def srp_supported(self):
        """
        Return if SRP is supported
        """
        return False

    def srp_get_password(self, remote):
        """
        Function to return the SRP password. This can be a coroutine if needed.
        The function must be implemented by an inherting class and srp_supported()
        should return True in that case.
        """
        raise NotImplementedError

    def handshake_initiator(self):
        """
        Handshake part 1: initiator offer
        """
        security = xmpp.Element('security', NS_XTLS)
        if self.x509_supported():
            security.add_child('fingerprint', algo='sha1', content=self.x509_keyinfo.fingerprint)
            security.add_child('method', name='x509')
        if self.srp_supported():
            security.add_child('method', name='srp')
        return security

    def handshake_responder(self, offer):
        """
        Handshake part 2: responder offer
        """
        security = xmpp.Element('security', NS_XTLS)
        for method in offer.get_children('method'):
            if method.name == 'x509' and self.x509_supported() and offer.fingerprint:
                fingerprint = offer.fingerprint.content
                for known in self.known_clients_x509:
                    if fingerprint == known.fingerprint:
                        security.add_child('fingerprint', algo='sha1', content=self.x509_keyinfo.fingerprint)
                        security.add_child('method', name='x509')
                        break
            if method.name == 'srp' and self.srp_supported():
                security.add_child('method', name='srp')
        return security

    def handshake_finalize(self, offer):
        """
        Handshake part 3: initiator final methods
        """
        security = xmpp.Element('security', NS_XTLS)
        for m in offer.get_children('method'):
            if m.name == 'x509' and self.x509_supported() and offer.fingerprint:
                fingerprint = offer.fingerprint.content
                for known in self.known_clients_x509:
                    if fingerprint == known.fingerprint:
                        security.add_child('method', name='x509')
                        return security
        for m in offer.get_children('method'):
            if m.name == 'srp' and self.srp_supported():
                security.add_child('method', name='srp')
                return security
        return None

    @classmethod
    def install(cls):
        Client.credentials = cls