Пример #1
0
        /// <summary>
        /// Decrypts the selected file using the given password
        /// </summary>
        /// <param name="inputFile">Encrypted File</param>
        /// <param name="password">Password to decrypt the file</param>
        /// <param name="percentComplete">Percent of completion</param>
        /// <returns>If the decryption was successful</returns>
        internal bool Decrypt(string inputFile, string password, ref decimal percentComplete)
        {
            byte[] passwordBytes = Encoding.UTF8.GetBytes(password);

            FileStream fsCrypt = new FileStream(inputFile, FileMode.Open);

            fsCrypt = DecryptModeHandler(fsCrypt, out byte[] hash, out byte[] salt, out byte[] faesCBCMode, out byte[] faesMetaData, out var cipher);

            const int          keySize   = 256;
            const int          blockSize = 128;
            Rfc2898DeriveBytes key       = new Rfc2898DeriveBytes(passwordBytes, salt, 50000);
            RijndaelManaged    AES       = new RijndaelManaged
            {
                KeySize   = keySize,
                BlockSize = blockSize,
                Key       = key.GetBytes(keySize / 8),
                IV        = key.GetBytes(blockSize / 8),
                Padding   = PaddingMode.PKCS7,
                Mode      = cipher
            };

            try
            {
                CryptoStream cs         = new CryptoStream(fsCrypt, AES.CreateDecryptor(), CryptoStreamMode.Read);
                string       outputName = Path.ChangeExtension(inputFile, FileAES_Utilities.ExtentionUFAES);

                try
                {
                    FileStream fsOut = new FileStream(outputName, FileMode.Create);
                    File.SetAttributes(outputName, FileAttributes.Hidden);

                    byte[] buffer           = new byte[FileAES_Utilities.GetCryptoStreamBuffer()];
                    long   expectedComplete = fsCrypt.Length + hash.Length + salt.Length + faesCBCMode.Length + faesMetaData.Length + AES.KeySize + AES.BlockSize;

                    try
                    {
                        int read;
                        Logging.Log("Beginning writing decrypted data...", Severity.DEBUG);
                        while ((read = cs.Read(buffer, 0, buffer.Length)) > 0)
                        {
                            try
                            {
                                percentComplete = Math.Ceiling((decimal)((Convert.ToDouble(fsOut.Length) / Convert.ToDouble(expectedComplete)) * 100));
                                if (percentComplete > 100)
                                {
                                    percentComplete = 100;
                                }
                            }
                            catch
                            {
                                Logging.Log("Percentage completion calculation failed!", Severity.WARN);
                            }

                            fsOut.Write(buffer, 0, read);
                        }
                        Logging.Log("Finished writing decrypted data.", Severity.DEBUG);
                    }
                    catch
                    {
                        fsOut.Close();
                    }

                    cs.Close();
                    fsOut.Close();
                    fsCrypt.Close();

                    if (Checksums.ConvertHashToString(hash) != Checksums.ConvertHashToString(Checksums.GetSHA1(outputName)))
                    {
                        Logging.Log("Invalid Checksum detected! Assuming password is incorrect.", Severity.DEBUG);
                        FileAES_IntUtilities.SafeDeleteFile(outputName);
                        return(false);
                    }
                    Logging.Log("Valid Checksum detected!", Severity.DEBUG);
                    return(true);
                }
                catch
                {
                    cs.Close();
                    fsCrypt.Close();

                    return(false);
                }
            }
            catch (CryptographicException)
            {
                fsCrypt.Close();
                return(false);
            }
        }
Пример #2
0
        /// <summary>
        /// Decrypts the selected file using the given password
        /// </summary>
        /// <param name="faesMetaData">Formatted Metadata used at the start of a file</param>
        /// <param name="inputFilePath">File path for encrypted file</param>
        /// <param name="outputFilePath">File path for unencrypted file</param>
        /// <param name="encryptionPassword">Encryption Password</param>
        /// <param name="percentComplete">Percent completion of the encryption process</param>
        /// <returns>If the decryption was successful</returns>
        internal bool Decrypt(MetaData faesMetaData, string inputFilePath, string outputFilePath, string encryptionPassword, ref decimal percentComplete)
        {
            CipherMode cipher = CipherMode.CBC;

            byte[] metaData      = new byte[faesMetaData.GetLength()];
            byte[] salt          = new byte[32];
            byte[] passwordBytes = Encoding.UTF8.GetBytes(encryptionPassword);

            FileStream inputDataStream = new FileStream(inputFilePath, FileMode.Open);

            inputDataStream.Read(metaData, 0, faesMetaData.GetLength());
            inputDataStream.Read(salt, 0, salt.Length);

            const int          keySize   = 256;
            const int          blockSize = 128;
            Rfc2898DeriveBytes key       = new Rfc2898DeriveBytes(passwordBytes, salt, 51200);
            RijndaelManaged    AES       = new RijndaelManaged
            {
                KeySize   = blockSize,
                BlockSize = 128,
                Key       = key.GetBytes(keySize / 8),
                IV        = key.GetBytes(blockSize / 8),
                Padding   = PaddingMode.PKCS7,
                Mode      = cipher
            };

            try
            {
                CryptoStream crypto           = new CryptoStream(inputDataStream, AES.CreateDecryptor(), CryptoStreamMode.Read);
                FileStream   outputDataStream = new FileStream(outputFilePath, FileMode.Create);

                try
                {
                    byte[] buffer           = new byte[FileAES_Utilities.GetCryptoStreamBuffer()];
                    long   expectedComplete = salt.Length + AES.KeySize + AES.BlockSize;

                    try
                    {
                        Logging.Log("Beginning writing decrypted data...", Severity.DEBUG);
                        int read;
                        while ((read = crypto.Read(buffer, 0, buffer.Length)) > 0)
                        {
                            try
                            {
                                percentComplete = Math.Ceiling((decimal)((Convert.ToDouble(outputDataStream.Length) / Convert.ToDouble(expectedComplete)) * 100));
                                if (percentComplete > 100)
                                {
                                    percentComplete = 100;
                                }
                            }
                            catch
                            {
                                // ignored
                            }

                            outputDataStream.Write(buffer, 0, read);
                        }
                        Logging.Log("Finished writing decrypted data.", Severity.DEBUG);
                    }
                    catch
                    {
                        outputDataStream.Close();
                    }

                    crypto.Close();
                    outputDataStream.Close();
                    inputDataStream.Close();

                    bool doesHashMatch = false;

                    switch (faesMetaData.GetHashType())
                    {
                    case Checksums.ChecksumType.SHA1:
                        doesHashMatch = Checksums.CompareHash(faesMetaData.GetOrigHash(), Checksums.GetSHA1(outputFilePath));
                        break;

                    case Checksums.ChecksumType.SHA256:
                        doesHashMatch = Checksums.CompareHash(faesMetaData.GetOrigHash(), Checksums.GetSHA256(outputFilePath));
                        break;

                    case Checksums.ChecksumType.SHA512:
                        doesHashMatch = Checksums.CompareHash(faesMetaData.GetOrigHash(), Checksums.GetSHA512(outputFilePath));
                        break;

                    case Checksums.ChecksumType.SHA384:
                        doesHashMatch = Checksums.CompareHash(faesMetaData.GetOrigHash(), Checksums.GetSHA384(outputFilePath));
                        break;
                    }
                    if (!doesHashMatch)
                    {
                        Logging.Log("Invalid Checksum detected! Assuming password is incorrect.", Severity.DEBUG);
                        return(false);
                    }
                    Logging.Log("Valid Checksum detected!", Severity.DEBUG);
                    return(true);
                }
                catch
                {
                    crypto.Close();
                    inputDataStream.Close();
                    outputDataStream.Close();

                    return(false);
                }
            }
            catch (CryptographicException)
            {
                inputDataStream.Close();

                return(false);
            }
        }