예제 #1
0
파일: security.py 프로젝트: erose1337/pride
 def hash_password(password, iterations, algorithm="pbkdf2hmac", sub_algorithm="sha256",
                                         salt=None, salt_size=16, output_size=32,
                                         backend=BACKEND):
     salt = os.urandom(salt_size) if salt is None else salt
     header = save_data(algorithm, sub_algorithm, iterations, salt_size, output_size)
     if algorithm == "pbkdf2hmac":          
         hasher = PBKDF2HMAC(algorithm=getattr(hashes, sub_algorithm.upper())(),
                             length=output_size, salt=salt, iterations=iterations,
                             backend=backend)
         
         return save_data(header, salt, hasher.derive(header + password))
     else:
         raise ValueError()
예제 #2
0
    def decrypt(packed_encrypted_data, key, mac_key='', backend=BACKEND):
        """ Decrypts packed encrypted data as returned by encrypt with the same key. 
            If extra data is present, returns plaintext, extra_data. If not,
            returns plaintext. Raises InvalidTag on authentication failure. """
        header, ciphertext, iv, tag, extra_data = load_data(
            packed_encrypted_data)
        algorithm, mode, authentication_algorithm = header.split('_', 2)
        if algorithm.lower() in hashlib.algorithms_guaranteed:
            return cryptographyless.decrypt(packed_encrypted_data, key,
                                            mac_key, backend)

        mode_args = (iv, tag) if mode in AEAD_MODES else (iv, )
        decryptor = Cipher(getattr(algorithms, algorithm)(key),
                           getattr(modes, mode)(*mode_args),
                           backend=BACKEND).decryptor()
        if mode in AEAD_MODES:
            decryptor.authenticate_additional_data(extra_data)
        else:
            if not mac_key:
                raise ValueError(
                    "mac_key not supplied for {} mode".format(header))
            if not verify_mac(
                    mac_key,
                    save_data(tag, header + ciphertext + iv + extra_data),
                    authentication_algorithm):
                raise InvalidTag("Failed to authenticate data")

        plaintext = decryptor.update(ciphertext) + decryptor.finalize()
        if extra_data:
            return (plaintext, extra_data)
        else:
            return plaintext
예제 #3
0
파일: security.py 프로젝트: erose1337/pride
 def decrypt(packed_encrypted_data, key, mac_key='', backend=BACKEND):
     """ Decrypts packed encrypted data as returned by encrypt with the same key. 
         If extra data is present, returns plaintext, extra_data. If not,
         returns plaintext. Raises InvalidTag on authentication failure. """
     header, ciphertext, iv, tag, extra_data = load_data(packed_encrypted_data)        
     algorithm, mode, authentication_algorithm = header.split('_', 2)   
     if algorithm.lower() in hashlib.algorithms_guaranteed:
         return cryptographyless.decrypt(packed_encrypted_data, key, mac_key, backend)
         
     mode_args = (iv, tag) if mode in AEAD_MODES else (iv, )
     decryptor = Cipher(getattr(algorithms, algorithm)(key), 
                        getattr(modes, mode)(*mode_args), 
                        backend=BACKEND).decryptor()
     if mode in AEAD_MODES:
         decryptor.authenticate_additional_data(extra_data)
     else:
         if not mac_key:
             raise ValueError("mac_key not supplied for {} mode".format(header))
         if not verify_mac(mac_key, save_data(tag, header + ciphertext + iv + extra_data), authentication_algorithm):
             raise InvalidTag("Failed to authenticate data")
         
     plaintext = decryptor.update(ciphertext) + decryptor.finalize()
     if extra_data:
         return (plaintext, extra_data)     
     else:
         return plaintext
예제 #4
0
파일: security.py 프로젝트: erose1337/pride
 def encrypt(data='', key='', mac_key='', iv=None, extra_data='', algorithm="AES", 
             mode="GCM", backend=BACKEND, iv_size=16, hash_algorithm="SHA256",
             return_mode="cryptogram"):
     """ Encrypts data with the specified key. Returns packed encrypted bytes.
         If an iv is not supplied a random one of iv_size will be generated.
         By default, the GCM mode of operation is used and the iv is 
         automatically included in the extra_data authenticated by the mode. 
         
         Note that not all algorithms may support all modes of operation
         with all backends. 
         
         A mac key is required when GCM mode is not in used. This function
         will refuse to encrypt data without authentication/integrity checks,
         as this is considered a serious flaw in security. 
         
         Technically speaking, 'iv' is not always the correct term for the
         parameter passed, depending on the mode of operation used. However,
         using two different fields for what are functionally the same would
         increase complexity needlessly. """
     assert data and key, "data" if not data else "key"
     if algorithm.lower() in hashlib.algorithms_guaranteed:
         return cryptographyless.encrypt(data, key, iv, extra_data, algorithm, mode,
                                         backend, iv_size, mac_key, hash_algorithm)
                                         
     header = algorithm + '_' + mode 
     if mode not in AEAD_MODES:
         if not mac_key:
             raise ValueError("Unable to authenticate data because no mac key was supplied for {} mode".format(header))        
         else:
             header += "_" + hash_algorithm
     else:
         header += "_" + "AEAD"
         
     if not iv and iv != 0: # 0 is a valid nonce for CTR mode.
         iv = random_bytes(iv_size)
         
     if mode != "ECB":
         mode_args = (iv, )
     else:
         mode_args = tuple()
     
     encryptor = Cipher(getattr(algorithms, algorithm)(key), 
                        getattr(modes, mode)(*mode_args), 
                        backend=BACKEND).encryptor()        
         
     if mode in AEAD_MODES:       
         encryptor.authenticate_additional_data(extra_data)            
     ciphertext = encryptor.update(data) + encryptor.finalize()          
                  
     if mode in AEAD_MODES:
         mac_tag = encryptor.tag
     else:
         mac_tag = generate_mac(mac_key, header + ciphertext + iv + extra_data, hash_algorithm) 
     
     if return_mode == "cryptogram":
         return save_data(header, ciphertext, iv, mac_tag, extra_data)
     else:
         assert return_mode == "values"
         return header, ciphertext, iv, mac_tag, extra_data
예제 #5
0
    def save(self, _file=None):
        """ usage: base_object.save(_file=None)

            Saves the state of the calling objects __dict__. If _file is not
            specified, a serialized stream is returned. If _file is specified,
            the stream is written to the supplied file like object and then
            returned.

            This method and load are being reimplemented"""
        raise NotImplementedError()
        self.alert("Saving", level=self.verbosity["save"])
        attributes = self.__getstate__()
        self_objects = attributes.pop("objects", {})
        saved_objects = attributes["objects"] = {}
        found_objects = []
        for component_type, values in self_objects.items():
            saved_objects[component_type] = new_values = []
            for value in sorted(values, key=operator.attrgetter("reference")):
                if hasattr(value, "save"):
                    found_objects.append(value)
                    if not getattr(value, "dont_save", False):
                        new_values.append(value.save())

        attribute_type = attributes["_attribute_type"] = {}
        for key, value in attributes.items():
            if value in found_objects:
                attributes[key] = value.reference
                attribute_type[key] = "reference"
            elif hasattr(value, "save") and not getattr(value, "dont_save"):
                attributes[key] = value.save()
                attribute_type[key] = "saved"

        #required_modules = pride.functions.module_utilities.get_all_modules_for_class(type(self))
        #version_control = objects["/Program/Version_Control"]
        #user = objects["/User"]
        #hash_function = user.generate_tag
        #repo_id = hash_function(user.username)
        #_required_modules = []
        #for module_name, source, module_object in required_modules:
            #module_id = hash_function(source)
            #version_control.save_module(module_name, source, module_id, repo_id)
            #_required_modules.append(module_name)

        #attributes["_required_modules"] = _required_modules + [self.__class__.__name__]
        attributes["_type_info"] = (self.__module__, self.__class__.__name__)
        #try:
        #    saved_data = pride.objects["/User"].save_data(attributes)
        #except TypeError:
        #    self.alert("Unable to save attributes '{}'".format(pprint.pformat(attributes)), level=0)
        #    raise
        saved_data = utilities.save_data(attributes)
        if _file:
            _file.write(saved_data)
        return saved_data
예제 #6
0
파일: base.py 프로젝트: erose1337/pride
    def save(self, _file=None):
        """ usage: base_object.save(_file=None)

            Saves the state of the calling objects __dict__. If _file is not
            specified, a serialized stream is returned. If _file is specified,
            the stream is written to the supplied file like object and then
            returned.

            This method and load are being reimplemented"""
        self.alert("Saving", level=self.verbosity["save"])
        attributes = self.__getstate__()
        self_objects = attributes.pop("objects", {})
        saved_objects = attributes["objects"] = {}
        found_objects = []
        for component_type, values in self_objects.items():
            saved_objects[component_type] = new_values = []
            for value in sorted(values, key=operator.attrgetter("reference")):
                if hasattr(value, "save"):
                    found_objects.append(value)
                    if not getattr(value, "dont_save", False):
                        new_values.append(value.save())

        attribute_type = attributes["_attribute_type"] = {}
        for key, value in attributes.items():
            if value in found_objects:
                attributes[key] = value.reference
                attribute_type[key] = "reference"
            elif hasattr(value, "save") and not getattr(value, "dont_save"):
                attributes[key] = value.save()
                attribute_type[key] = "saved"

        #required_modules = pride.functions.module_utilities.get_all_modules_for_class(type(self))
        #version_control = objects["/Python/Version_Control"]
        #user = objects["/User"]
        #hash_function = user.generate_tag
        #repo_id = hash_function(user.username)
        #_required_modules = []
        #for module_name, source, module_object in required_modules:
            #module_id = hash_function(source)
            #version_control.save_module(module_name, source, module_id, repo_id)
            #_required_modules.append(module_name)

        #attributes["_required_modules"] = _required_modules + [self.__class__.__name__]
        attributes["_type_info"] = (self.__module__, self.__class__.__name__)
        #try:
        #    saved_data = pride.objects["/User"].save_data(attributes)
        #except TypeError:
        #    self.alert("Unable to save attributes '{}'".format(pprint.pformat(attributes)), level=0)
        #    raise
        saved_data = utilities.save_data(attributes)
        if _file:
            _file.write(saved_data)
        return saved_data
예제 #7
0
    def hash_password(password,
                      iterations,
                      algorithm="pbkdf2hmac",
                      sub_algorithm="sha256",
                      salt=None,
                      salt_size=16,
                      output_size=32,
                      backend=BACKEND):
        salt = os.urandom(salt_size) if salt is None else salt
        header = save_data(algorithm, sub_algorithm, iterations, salt_size,
                           output_size)
        if algorithm == "pbkdf2hmac":
            hasher = PBKDF2HMAC(algorithm=getattr(hashes,
                                                  sub_algorithm.upper())(),
                                length=output_size,
                                salt=salt,
                                iterations=iterations,
                                backend=backend)

            return save_data(header, salt, hasher.derive(header + password))
        else:
            raise ValueError()
예제 #8
0
파일: security.py 프로젝트: erose1337/pride
 def apply_mac(key, data, algorithm="SHA256", backend=BACKEND):
     """ Generates a message authentication code and prepends it to data.
         Mac and data are packed via pride.functions.utilities.save_data. 
         
         Applying a message authentication code facilitates the goals
         of authenticity and integrity. Note it does not protect
         confidentiality (i.e. encryption).
         
         Combining a mac with encryption is NOT straightforward;
         Authenticating/providing integrity of confidential data
         should preferably be accomplished via an appropriate
         block cipher mode of operation, such as GCM. If this is
         not possible, encrypt-then-mac is most secure solution in
         general. """
     return save_data(generate_mac(key, data, algorithm, backend), data)
예제 #9
0
 def apply_mac(key, data, algorithm="SHA256", backend=BACKEND):
     """ Generates a message authentication code and prepends it to data.
         Mac and data are packed via pride.functions.utilities.save_data. 
         
         Applying a message authentication code facilitates the goals
         of authenticity and integrity. Note it does not protect
         confidentiality (i.e. encryption).
         
         Combining a mac with encryption is NOT straightforward;
         Authenticating/providing integrity of confidential data
         should preferably be accomplished via an appropriate
         block cipher mode of operation, such as GCM. If this is
         not possible, encrypt-then-mac is most secure solution in
         general. """
     return save_data(generate_mac(key, data, algorithm, backend), data)
예제 #10
0
    def encrypt(data='',
                key='',
                mac_key='',
                iv=None,
                extra_data='',
                algorithm="AES",
                mode="GCM",
                backend=BACKEND,
                iv_size=16,
                hash_algorithm="SHA256",
                return_mode="cryptogram"):
        """ Encrypts data with the specified key. Returns packed encrypted bytes.
            If an iv is not supplied a random one of iv_size will be generated.
            By default, the GCM mode of operation is used and the iv is 
            automatically included in the extra_data authenticated by the mode. 
            
            Note that not all algorithms may support all modes of operation
            with all backends. 
            
            A mac key is required when GCM mode is not in used. This function
            will refuse to encrypt data without authentication/integrity checks,
            as this is considered a serious flaw in security. 
            
            Technically speaking, 'iv' is not always the correct term for the
            parameter passed, depending on the mode of operation used. However,
            using two different fields for what are functionally the same would
            increase complexity needlessly. """
        assert data and key, "data" if not data else "key"
        if algorithm.lower() in hashlib.algorithms_guaranteed:
            return cryptographyless.encrypt(data, key, iv, extra_data,
                                            algorithm, mode, backend, iv_size,
                                            mac_key, hash_algorithm)

        header = algorithm + '_' + mode
        if mode not in AEAD_MODES:
            if not mac_key:
                raise ValueError(
                    "Unable to authenticate data because no mac key was supplied for {} mode"
                    .format(header))
            else:
                header += "_" + hash_algorithm
        else:
            header += "_" + "AEAD"

        if not iv and iv != 0:  # 0 is a valid nonce for CTR mode.
            iv = random_bytes(iv_size)

        if mode != "ECB":
            mode_args = (iv, )
        else:
            mode_args = tuple()

        encryptor = Cipher(getattr(algorithms, algorithm)(key),
                           getattr(modes, mode)(*mode_args),
                           backend=BACKEND).encryptor()

        if mode in AEAD_MODES:
            encryptor.authenticate_additional_data(extra_data)
        ciphertext = encryptor.update(data) + encryptor.finalize()

        if mode in AEAD_MODES:
            mac_tag = encryptor.tag
        else:
            mac_tag = generate_mac(mac_key,
                                   header + ciphertext + iv + extra_data,
                                   hash_algorithm)

        if return_mode == "cryptogram":
            return save_data(header, ciphertext, iv, mac_tag, extra_data)
        else:
            assert return_mode == "values"
            return header, ciphertext, iv, mac_tag, extra_data