private static Stream RemoveHash(Stream stream) { if (stream == null) { throw new ArgumentNullException(nameof(stream)); } int type = (int)VintUtils.GetUInt64(stream); if (type == (int)ConvertHashAlgorithm.Sha256) { var value = new byte[32]; stream.Read(value, 0, value.Length); var dataStream = new RangeStream(stream, true); if (!Unsafe.Equals(value, Sha256.ComputeHash(new WrapperStream(dataStream, true)))) { throw new ArgumentException("Hash"); } dataStream.Seek(0, SeekOrigin.Begin); return(dataStream); } else { throw new NotSupportedException(); } }
private static Stream RemoveVersion(Stream stream, int version) { if (stream == null) { throw new ArgumentNullException(nameof(stream)); } if (VintUtils.GetUInt64(stream) != (uint)version) { throw new FormatException(); } return(new RangeStream(stream, true)); }
private static Stream RemovePadding(Stream stream) { if (stream == null) { throw new ArgumentNullException(nameof(stream)); } try { int length = (int)VintUtils.GetUInt64(stream); return(new RangeStream(stream, stream.Position, length)); } catch (Exception e) { if (stream != null) { stream.Dispose(); } throw new ArgumentException(e.Message, e); } }
private static T FromStream <T>(int version, Stream stream) where T : ItemBase <T> { try { stream.Seek(0, SeekOrigin.Begin); // Check { var verifyCrc = Crc32_Castagnoli.ComputeHash(new RangeStream(stream, 0, stream.Length - 4, true)); var orignalCrc = new byte[4]; using (var crcStream = new RangeStream(stream, stream.Length - 4, 4, true)) { crcStream.Read(orignalCrc, 0, orignalCrc.Length); } if (!Unsafe.Equals(verifyCrc, orignalCrc)) { throw new ArgumentException("Crc Error"); } } stream.Seek(0, SeekOrigin.Begin); if (version != (int)VintUtils.GetUInt64(stream)) { throw new ArgumentException("version"); } int type = (int)VintUtils.GetUInt64(stream); using (var dataStream = new RangeStream(stream, stream.Position, stream.Length - stream.Position - 4, true)) { if (type == (int)ConvertCompressionAlgorithm.None) { return(ItemBase <T> .Import(dataStream, _bufferManager)); } else if (type == (int)ConvertCompressionAlgorithm.Deflate) { using (var deflateBufferStream = new BufferStream(_bufferManager)) { using (var deflateStream = new DeflateStream(dataStream, CompressionMode.Decompress, true)) using (var safeBuffer = _bufferManager.CreateSafeBuffer(1024 * 4)) { int length; while ((length = deflateStream.Read(safeBuffer.Value, 0, safeBuffer.Value.Length)) > 0) { deflateBufferStream.Write(safeBuffer.Value, 0, length); if (deflateBufferStream.Length > 1024 * 1024 * 32) { throw new Exception("too large"); } } } deflateBufferStream.Seek(0, SeekOrigin.Begin); return(ItemBase <T> .Import(deflateBufferStream, _bufferManager)); } } else { throw new ArgumentException("ArgumentException"); } } } catch (Exception e) { throw new ArgumentException(e.Message, e); } finally { if (stream != null) { stream.Dispose(); } } }
private static Stream Decrypt(Stream stream, ExchangePrivateKey privateKey) { if (stream == null) { throw new ArgumentNullException(nameof(stream)); } if (privateKey == null) { throw new ArgumentNullException(nameof(privateKey)); } try { int type = (int)VintUtils.GetUInt64(stream); if (type == (int)ConvertCryptoAlgorithm.Aes256) { byte[] cryptoKey; { int length = (int)VintUtils.GetUInt64(stream); var encryptedBuffer = new byte[length]; if (stream.Read(encryptedBuffer, 0, encryptedBuffer.Length) != encryptedBuffer.Length) { throw new ArgumentException(); } cryptoKey = Exchange.Decrypt(privateKey, encryptedBuffer); } var iv = new byte[32]; stream.Read(iv, 0, iv.Length); BufferStream outStream = null; try { outStream = new BufferStream(_bufferManager); using (var aes = Aes.Create()) { aes.KeySize = 256; aes.Mode = CipherMode.CBC; aes.Padding = PaddingMode.PKCS7; using (var inStream = new RangeStream(stream, stream.Position, stream.Length - stream.Position, true)) using (var cs = new CryptoStream(inStream, aes.CreateDecryptor(cryptoKey, iv), CryptoStreamMode.Read)) using (var safeBuffer = _bufferManager.CreateSafeBuffer(1024 * 4)) { int length; while ((length = cs.Read(safeBuffer.Value, 0, safeBuffer.Value.Length)) > 0) { outStream.Write(safeBuffer.Value, 0, length); } } } outStream.Seek(0, SeekOrigin.Begin); } catch (Exception) { if (outStream != null) { outStream.Dispose(); } throw; } return(outStream); } else { throw new NotSupportedException(); } } catch (Exception e) { throw new ArgumentException(e.Message, e); } finally { if (stream != null) { stream.Dispose(); } } }
private static Stream Decompress(Stream stream) { if (stream == null) { throw new ArgumentNullException(nameof(stream)); } try { stream.Seek(0, SeekOrigin.Begin); int type = (int)VintUtils.GetUInt64(stream); if (type == (int)ConvertCompressionAlgorithm.None) { return(new RangeStream(stream)); } else if (type == (int)ConvertCompressionAlgorithm.Deflate) { BufferStream deflateBufferStream = null; try { deflateBufferStream = new BufferStream(_bufferManager); using (var deflateStream = new DeflateStream(stream, CompressionMode.Decompress)) using (var safeBuffer = _bufferManager.CreateSafeBuffer(1024 * 4)) { int length; while ((length = deflateStream.Read(safeBuffer.Value, 0, safeBuffer.Value.Length)) > 0) { deflateBufferStream.Write(safeBuffer.Value, 0, length); if (deflateBufferStream.Length > 1024 * 1024 * 256) { throw new Exception("too large"); } } } deflateBufferStream.Seek(0, SeekOrigin.Begin); return(deflateBufferStream); } catch (Exception) { if (deflateBufferStream != null) { deflateBufferStream.Dispose(); } throw; } } else { throw new ArgumentException("ArgumentException"); } } catch (Exception e) { if (stream != null) { stream.Dispose(); } throw new ArgumentException(e.Message, e); } }