Beispiel #1
0
 public override byte[] GetHashAndReset()
 {
     hasher.TransformFinalBlock(bb0, 0, 0);
     byte[] result = hasher.Hash;
     hasher.Initialize();
     return(result);
 }
        /// <summary>
        /// Return the MD5 of the whole item data
        /// </summary>
        /// <returns></returns>
        public string MD5()
        {
            if (CompleteDataStream != null)
            {
                return(CompleteDataStream.MD5());
            }
            else
            {
                lock (dataLocker)
                {
                    using (System.Security.Cryptography.HashAlgorithm md5 = System.Security.Cryptography.MD5.Create())
                    {
                        byte[] chunkBytes;
                        for (int i = 0; i < ChunkDataStreams.Length; i++)
                        {
                            chunkBytes = ChunkDataStreams[i].ToArray();

                            if (i < ChunkDataStreams.Length - 1)
                            {
                                md5.TransformBlock(chunkBytes, 0, chunkBytes.Length, chunkBytes, 0);
                            }
                            else
                            {
                                md5.TransformFinalBlock(chunkBytes, 0, chunkBytes.Length);
                            }
                        }

                        return(BitConverter.ToString(md5.Hash).Replace("-", ""));
                    }
                }
            }
        }
        private void verifyTask_RunTask(object param, ref object result)
        {
            byte[] buffer;
            byte[] oldBuffer;
            int    bytesRead;
            int    oldBytesRead;
            long   size;
            long   totalBytesRead = 0;

            using (Stream stream = File.OpenRead(_fileName)) //Change to MD5.Create for MD5 verification
                using (System.Security.Cryptography.HashAlgorithm hashAlgorithm = System.Security.Cryptography.SHA1.Create())
                {
                    size = stream.Length;

                    buffer = new byte[4096];

                    bytesRead       = stream.Read(buffer, 0, buffer.Length);
                    totalBytesRead += bytesRead;

                    do
                    {
                        if (_verifyTask.Cancelled)
                        {
                            return;
                        }

                        oldBytesRead = bytesRead;
                        oldBuffer    = buffer;

                        buffer    = new byte[4096];
                        bytesRead = stream.Read(buffer, 0, buffer.Length);

                        totalBytesRead += bytesRead;

                        if (bytesRead == 0)
                        {
                            hashAlgorithm.TransformFinalBlock(oldBuffer, 0, oldBytesRead);
                        }
                        else
                        {
                            hashAlgorithm.TransformBlock(oldBuffer, 0, oldBytesRead, oldBuffer, 0);
                        }

                        if (this.IsHandleCreated)
                        {
                            this.BeginInvoke(new MethodInvoker(() =>
                            {
                                int value = (int)((double)totalBytesRead * 100 / size);

                                if (value >= this.progressDownload.Minimum && value <= this.progressDownload.Maximum)
                                {
                                    this.progressDownload.Value = value;
                                }
                            }));
                        }
                    } while (bytesRead != 0);

                    result = hashAlgorithm.Hash;
                }
        }
 public byte[] GetFinalHash()
 {
     if (m_finalHash == null)
     {
         m_hash.TransformFinalBlock(m_hashbuffer, 0, m_hashbufferLength);
         m_finalHash = m_hash.Hash;
     }
     return(m_finalHash);
 }
        public override HashResult TransformFinal()
        {
            m_hash_algorithm.TransformFinalBlock(EMPTY, 0, 0);
            byte[] result = m_hash_algorithm.Hash;

            Debug.Assert(result.Length == HashSize);

            Initialize();
            return(new HashResult(result));
        }
Beispiel #6
0
        private static void HashMultiple(System.Security.Cryptography.HashAlgorithm md5, byte[] bytes1, byte[] bytes2)
        {
            int offset = 0;

            // For each block:
            offset += md5.TransformBlock(bytes1, 0, bytes1.Length, bytes1, 0);
            offset += md5.TransformBlock(bytes2, 0, bytes2.Length, bytes2, 0);
            offset += md5.TransformBlock(bytes1, 0, bytes1.Length, null, 0);
            offset += md5.TransformBlock(bytes2, 0, bytes2.Length, null, 0);
            // For last block:
            //md5.TransformFinalBlock(bytes2, 0, bytes2.Length);
            md5.TransformFinalBlock(new byte[0], 0, 0);
        }
Beispiel #7
0
        private static byte[] PerformanceTest(System.Security.Cryptography.HashAlgorithm alg, int seed = 42, int blocksize = 64)
        {
            var block = new byte[blocksize];

            new Random(seed).NextBytes(block);

            alg.Initialize();
            foreach (var n in Enumerable.Range(0, 1000000))
            {
                alg.TransformBlock(block, 0, block.Length, block, 0);
            }

            return(alg.TransformFinalBlock(block, 0, 0));
        }
        protected override byte[] HashFinal()
        {
            if (_hashing == false)
            {
                _hash1.TransformBlock(_inner, 0, _inner.Length, _inner, 0);
                _hashing = true;
            }

            _hash1.TransformFinalBlock(new Byte[0], 0, 0);
            byte[] hashValue1 = _hash1.Hash;

            _hash2.TransformBlock(_outer, 0, _outer.Length, _outer, 0);
            _hash2.TransformBlock(hashValue1, 0, hashValue1.Length, hashValue1, 0);
            _hashing = false;

            _hash2.TransformFinalBlock(new Byte[0], 0, 0);
            return(_hash2.Hash);
        }
 public override byte[] TransformFinalBlock(byte[] inputBuffer, int inputOffset, int inputCount)
 {
     return(_hashAlgorithm.TransformFinalBlock(inputBuffer, inputOffset, inputCount));
 }
        protected byte[] WriteCryptFileAndHash(
            Stream sourceFileStream,
            byte[] keyData,
            String destFilePath,
            String hashType = CryptUtilities.DefaultHashType)
        {
            long bytesToSkip       = 0;
            long bytesReadUntilNow = 0;

            FileStream destFileStream = null;

            System.Security.Cryptography.CryptoStream cryptoStream = null;

            try
            {
                if (File.Exists(destFilePath))
                {
                    bytesToSkip = new FileInfo(destFilePath).Length;

                    destFileStream =
                        File.Open(destFilePath, FileMode.Append);

                    // TODO: Use delegate for console like in other classes
                    System.Console.WriteLine(
                        "Appending after " +
                        bytesToSkip.ToString() +
                        " bytes...");
                }
                else
                {
                    // Set up the dest file streams
                    destFileStream =
                        File.OpenWrite(destFilePath);
                }

                // Set up a temporary stream to hold encrypted data chunks so
                // that we can send the encrypted data to the file and to the
                // hash algorithm.
                MemoryStream encryptedMemoryStream =
                    new MemoryStream();

                // Set up a CryptoStream and attach it to the temporary stream
                cryptoStream =
                    CryptUtilities.MakeEncryptionWriteStreamFrom(
                        encryptedMemoryStream,
                        keyData);

                // Set up the hash algorithm
                System.Security.Cryptography.HashAlgorithm hashAlgorithm =
                    CryptUtilities.GetHashAlgorithm(hashType);

                // Buffers and chunks
                int    chunkSize       = 1024;
                byte[] fileReadBuffer  = new byte[chunkSize];
                byte[] encryptedBuffer = null;

                // Read the first chunk to set up the loop
                int newBytesRead = sourceFileStream.Read(
                    fileReadBuffer,
                    0,
                    chunkSize);

                // Read until the end
                while (newBytesRead > 0)
                {
                    // Encrypt to the MemoryStream
                    cryptoStream.Write(fileReadBuffer, 0, newBytesRead);
                    encryptedBuffer = encryptedMemoryStream.GetBuffer();
                    long newBytesEncrypted = encryptedMemoryStream.Length;

                    // Figure out the number of bytes to write
                    long bytesToWrite =
                        bytesReadUntilNow + newBytesEncrypted - bytesToSkip;

                    if (bytesToWrite < 0)
                    {
                        bytesToWrite = 0;
                    }
                    else if (bytesToWrite > newBytesEncrypted)
                    {
                        bytesToWrite = newBytesEncrypted;
                    }

                    if (bytesToWrite > 0)
                    {
                        long bufferStartPosition =
                            newBytesEncrypted - bytesToWrite;

                        // Write encrypted data to file
                        destFileStream.Write(
                            encryptedBuffer,
                            (int)bufferStartPosition,
                            (int)bytesToWrite);
                    }

                    bytesReadUntilNow += newBytesEncrypted;

                    // Hash encrypted data
                    hashAlgorithm.TransformBlock(
                        encryptedBuffer,
                        0,
                        (int)newBytesEncrypted,
                        encryptedBuffer,
                        0);

                    // Read next chunk
                    newBytesRead = sourceFileStream.Read(
                        fileReadBuffer,
                        0,
                        chunkSize);

                    // Reset position so we don't use a lot of memory
                    encryptedMemoryStream.SetLength(0);
                }

                // Need to do this - I think it writes special padding
                // information to the end of the data.
                cryptoStream.FlushFinalBlock();
                encryptedBuffer = encryptedMemoryStream.GetBuffer();

                // Write final data to file
                destFileStream.Write(
                    encryptedBuffer,
                    0,
                    (int)encryptedMemoryStream.Length);

                // Hash final data
                hashAlgorithm.TransformFinalBlock(
                    encryptedBuffer,
                    0,
                    (int)encryptedMemoryStream.Length);

                sourceFileStream.Close();
                cryptoStream.Close();
                destFileStream.Close();

                return(hashAlgorithm.Hash);
            }
            catch (Exception e)
            {
                sourceFileStream.Close();

                if (cryptoStream != null)
                {
                    cryptoStream.Close();
                }

                if (destFileStream != null)
                {
                    destFileStream.Close();
                    File.Delete(destFilePath);
                }

                throw e;
            }
        }
Beispiel #11
0
        private static void ScanForExistingTargetBlocks(LocalRestoreDatabase database, byte[] blockbuffer, System.Security.Cryptography.HashAlgorithm blockhasher, System.Security.Cryptography.HashAlgorithm filehasher, Options options, RestoreResults result)
        {
            // Scan existing files for existing BLOCKS
            using (var blockmarker = database.CreateBlockMarker())
            {
                var updateCount = 0L;
                foreach (var restorelist in database.GetExistingFilesWithBlocks())
                {
                    var rename         = !options.Overwrite;
                    var targetpath     = restorelist.TargetPath;
                    var targetfileid   = restorelist.TargetFileID;
                    var targetfilehash = restorelist.TargetHash;
                    if (m_systemIO.FileExists(targetpath))
                    {
                        try
                        {
                            if (result.TaskControlRendevouz() == TaskControlState.Stop)
                            {
                                return;
                            }

                            if (rename)
                            {
                                filehasher.Initialize();
                            }

                            using (var file = m_systemIO.FileOpenReadWrite(targetpath))
                                using (var block = new Blockprocessor(file, blockbuffer))
                                    foreach (var targetblock in restorelist.Blocks)
                                    {
                                        var size = block.Readblock();
                                        if (size <= 0)
                                        {
                                            break;
                                        }

                                        if (size == targetblock.Size)
                                        {
                                            var key = Convert.ToBase64String(blockhasher.ComputeHash(blockbuffer, 0, size));
                                            if (key == targetblock.Hash)
                                            {
                                                blockmarker.SetBlockRestored(targetfileid, targetblock.Index, key, size);
                                            }
                                        }

                                        if (rename)
                                        {
                                            filehasher.TransformBlock(blockbuffer, 0, size, blockbuffer, 0);
                                        }
                                    }

                            if (rename)
                            {
                                filehasher.TransformFinalBlock(blockbuffer, 0, 0);
                                var filekey = Convert.ToBase64String(filehasher.Hash);
                                if (filekey == targetfilehash)
                                {
                                    result.AddVerboseMessage("Target file exists and is correct version: {0}", targetpath);
                                    rename = false;
                                }
                                else
                                {
                                    // The new file will have none of the correct blocks,
                                    // even if the scanned file had some
                                    blockmarker.SetAllBlocksMissing(targetfileid);
                                }
                            }

                            if (updateCount++ % 20 == 0)
                            {
                                blockmarker.UpdateProcessed(result.OperationProgressUpdater);
                                if (result.TaskControlRendevouz() == TaskControlState.Stop)
                                {
                                    return;
                                }
                            }
                        }
                        catch (Exception ex)
                        {
                            result.AddWarning(string.Format("Failed to read target file: \"{0}\", message: {1}", targetpath, ex.Message), ex);
                            if (ex is System.Threading.ThreadAbortException)
                            {
                                throw;
                            }
                        }
                    }
                    else
                    {
                        result.AddVerboseMessage("Target file does not exist: {0}", targetpath);
                        rename = false;
                    }

                    if (rename)
                    {
                        //Select a new filename
                        var ext = m_systemIO.PathGetExtension(targetpath) ?? "";
                        if (!string.IsNullOrEmpty(ext) && !ext.StartsWith("."))
                        {
                            ext = "." + ext;
                        }

                        // First we try with a simple date append, assuming that there are not many conflicts there
                        var newname = m_systemIO.PathChangeExtension(targetpath, null) + "." + database.RestoreTime.ToLocalTime().ToString("yyyy-MM-dd");
                        var tr      = newname + ext;
                        var c       = 0;
                        while (m_systemIO.FileExists(tr) && c < 1000)
                        {
                            try
                            {
                                // If we have a file with the correct name,
                                // it is most likely the file we want
                                filehasher.Initialize();

                                string key;
                                using (var file = m_systemIO.FileOpenReadWrite(tr))
                                    key = Convert.ToBase64String(filehasher.ComputeHash(file));

                                if (key == targetfilehash)
                                {
                                    blockmarker.SetAllBlocksRestored(targetfileid);
                                    break;
                                }
                            }
                            catch (Exception ex)
                            {
                                result.AddWarning(string.Format("Failed to read candidate restore target {0}", tr), ex);
                            }
                            tr = newname + " (" + (c++).ToString() + ")" + ext;
                        }

                        newname = tr;

                        result.AddVerboseMessage("Target file exists and will be restored to: {0}", newname);
                        database.UpdateTargetPath(targetfileid, newname);
                    }
                }

                blockmarker.UpdateProcessed(result.OperationProgressUpdater);
                blockmarker.Commit(result);
            }
        }
Beispiel #12
0
        /// <summary>
        /// Returns data hashed with provided algorithm.
        /// </summary>
        /// <param name="hashAlgorithm">The hash algorithm.</param>
        /// <returns>Byte array containing hash of data.</returns>
        /// <exception cref="TimestampException">
        /// Invalid digest length for given algorithm
        /// </exception>
        public byte[] GetHashedData(HashAlgorithm hashAlgorithm)
        {
            System.Security.Cryptography.HashAlgorithm algorithm = System.Security.Cryptography.HashAlgorithm.Create(hashAlgorithm.ToString());

            switch (mode)
            {
            case DataMode.DATA_1:
                return(algorithm.ComputeHash(data));

            case DataMode.STREAM_1:
                return(algorithm.ComputeHash(stream));

            case DataMode.PATH_1:
                try
                {
                    return(algorithm.ComputeHash(File.OpenRead(pathToFile)));
                }
                catch (Exception e)
                {
                    throw new TimestampException("Can't calculate message digest from file: " + pathToFile, e);
                }

            case DataMode.HASHED_1:
                if (digest.Length != hashAlgorithm.GetLength())
                {
                    throw new TimestampException("Invalid digest length for given algorithm");
                }
                return(digest);

            case DataMode.DATA_N:
                for (int i = 0; i < datas.Length - 1; i++)
                {
                    algorithm.TransformBlock(datas[i], 0, datas[i].Length, datas[i], 0);
                }
                algorithm.TransformFinalBlock(datas[datas.Length - 1], 0, datas[datas.Length - 1].Length);
                return(algorithm.Hash);

            case DataMode.STREAM_N:
                using (MemoryStream finalStream = new MemoryStream())
                {
                    foreach (Stream stream in streams)
                    {
                        stream.CopyTo(finalStream);
                    }
                    return(algorithm.ComputeHash(finalStream.ToArray()));
                }

            case DataMode.PATH_N:
                int numberOfFiles = pathsToFiles.Length;
                for (int i = 0; i < numberOfFiles - 1; i++)
                {
                    try
                    {
                        byte[] currentData = File.ReadAllBytes(pathsToFiles[i]);
                        algorithm.TransformBlock(currentData, 0, currentData.Length, currentData, 0);
                    }
                    catch (Exception e)
                    {
                        throw new TimestampException("Can't calculate message digest from file: " + pathsToFiles[i], e);
                    }
                }
                try
                {
                    byte[] lastData = File.ReadAllBytes(pathsToFiles[numberOfFiles - 1]);
                    algorithm.TransformFinalBlock(lastData, 0, lastData.Length);
                    return(algorithm.Hash);
                }
                catch (Exception e)
                {
                    throw new TimestampException("Can't calculate message digest from file: " + pathsToFiles[numberOfFiles - 1], e);
                }


            case DataMode.HASHED_N:
                int algorithmLength = hashAlgorithm.GetLength();
                for (int i = 0; i < digests.Length - 1; i++)
                {
                    algorithm.TransformBlock(digests[i], 0, digests[i].Length, digests[i], 0);
                }
                algorithm.TransformFinalBlock(digests[digests.Length - 1], 0, digests[digests.Length - 1].Length);
                return(algorithm.Hash);
            }
            return(null);
        }