| // ZlibStream.cs | |
| // ------------------------------------------------------------------ | |
| // | |
| // Copyright (c) 2009 Dino Chiesa and Microsoft Corporation. | |
| // All rights reserved. | |
| // | |
| // This code module is part of DotNetZip, a zipfile class library. | |
| // | |
| // ------------------------------------------------------------------ | |
| // | |
| // This code is licensed under the Microsoft Public License. | |
| // See the file License.txt for the license details. | |
| // More info on: http://dotnetzip.codeplex.com | |
| // | |
| // ------------------------------------------------------------------ | |
| // | |
| // last saved (in emacs): | |
| // Time-stamp: <2011-July-31 14:53:33> | |
| // | |
| // ------------------------------------------------------------------ | |
| // | |
| // This module defines the ZlibStream class, which is similar in idea to | |
| // the System.IO.Compression.DeflateStream and | |
| // System.IO.Compression.GZipStream classes in the .NET BCL. | |
| // | |
| // ------------------------------------------------------------------ | |
| using System; | |
| using System.IO; | |
| namespace OfficeOpenXml.Packaging.Ionic.Zlib | |
| { | |
| /// <summary> | |
| /// Represents a Zlib stream for compression or decompression. | |
| /// </summary> | |
| /// <remarks> | |
| /// | |
| /// <para> | |
| /// The ZlibStream is a <see | |
| /// href="http://en.wikipedia.org/wiki/Decorator_pattern">Decorator</see> on a <see | |
| /// cref="System.IO.Stream"/>. It adds ZLIB compression or decompression to any | |
| /// stream. | |
| /// </para> | |
| /// | |
| /// <para> Using this stream, applications can compress or decompress data via | |
| /// stream <c>Read()</c> and <c>Write()</c> operations. Either compresssion or | |
| /// decompression can occur through either reading or writing. The compression | |
| /// format used is ZLIB, which is documented in <see | |
| /// href="http://www.ietf.org/rfc/rfc1950.txt">IETF RFC 1950</see>, "ZLIB Compressed | |
| /// Data Format Specification version 3.3". This implementation of ZLIB always uses | |
| /// DEFLATE as the compression method. (see <see | |
| /// href="http://www.ietf.org/rfc/rfc1951.txt">IETF RFC 1951</see>, "DEFLATE | |
| /// Compressed Data Format Specification version 1.3.") </para> | |
| /// | |
| /// <para> | |
| /// The ZLIB format allows for varying compression methods, window sizes, and dictionaries. | |
| /// This implementation always uses the DEFLATE compression method, a preset dictionary, | |
| /// and 15 window bits by default. | |
| /// </para> | |
| /// | |
| /// <para> | |
| /// This class is similar to <see cref="DeflateStream"/>, except that it adds the | |
| /// RFC1950 header and trailer bytes to a compressed stream when compressing, or expects | |
| /// the RFC1950 header and trailer bytes when decompressing. It is also similar to the | |
| /// <see cref="GZipStream"/>. | |
| /// </para> | |
| /// </remarks> | |
| /// <seealso cref="DeflateStream" /> | |
| /// <seealso cref="GZipStream" /> | |
| public class ZlibStream : System.IO.Stream | |
| { | |
| internal ZlibBaseStream _baseStream; | |
| bool _disposed; | |
| /// <summary> | |
| /// Create a <c>ZlibStream</c> using the specified <c>CompressionMode</c>. | |
| /// </summary> | |
| /// <remarks> | |
| /// | |
| /// <para> | |
| /// When mode is <c>CompressionMode.Compress</c>, the <c>ZlibStream</c> | |
| /// will use the default compression level. The "captive" stream will be | |
| /// closed when the <c>ZlibStream</c> is closed. | |
| /// </para> | |
| /// | |
| /// </remarks> | |
| /// | |
| /// <example> | |
| /// This example uses a <c>ZlibStream</c> to compress a file, and writes the | |
| /// compressed data to another file. | |
| /// <code> | |
| /// using (System.IO.Stream input = System.IO.File.OpenRead(fileToCompress)) | |
| /// { | |
| /// using (var raw = System.IO.File.Create(fileToCompress + ".zlib")) | |
| /// { | |
| /// using (Stream compressor = new ZlibStream(raw, CompressionMode.Compress)) | |
| /// { | |
| /// byte[] buffer = new byte[WORKING_BUFFER_SIZE]; | |
| /// int n; | |
| /// while ((n= input.Read(buffer, 0, buffer.Length)) != 0) | |
| /// { | |
| /// compressor.Write(buffer, 0, n); | |
| /// } | |
| /// } | |
| /// } | |
| /// } | |
| /// </code> | |
| /// <code lang="VB"> | |
| /// Using input As Stream = File.OpenRead(fileToCompress) | |
| /// Using raw As FileStream = File.Create(fileToCompress & ".zlib") | |
| /// Using compressor As Stream = New ZlibStream(raw, CompressionMode.Compress) | |
| /// Dim buffer As Byte() = New Byte(4096) {} | |
| /// Dim n As Integer = -1 | |
| /// Do While (n <> 0) | |
| /// If (n > 0) Then | |
| /// compressor.Write(buffer, 0, n) | |
| /// End If | |
| /// n = input.Read(buffer, 0, buffer.Length) | |
| /// Loop | |
| /// End Using | |
| /// End Using | |
| /// End Using | |
| /// </code> | |
| /// </example> | |
| /// | |
| /// <param name="stream">The stream which will be read or written.</param> | |
| /// <param name="mode">Indicates whether the ZlibStream will compress or decompress.</param> | |
| public ZlibStream(System.IO.Stream stream, CompressionMode mode) | |
| : this(stream, mode, CompressionLevel.Default, false) | |
| { | |
| } | |
| /// <summary> | |
| /// Create a <c>ZlibStream</c> using the specified <c>CompressionMode</c> and | |
| /// the specified <c>CompressionLevel</c>. | |
| /// </summary> | |
| /// | |
| /// <remarks> | |
| /// | |
| /// <para> | |
| /// When mode is <c>CompressionMode.Decompress</c>, the level parameter is ignored. | |
| /// The "captive" stream will be closed when the <c>ZlibStream</c> is closed. | |
| /// </para> | |
| /// | |
| /// </remarks> | |
| /// | |
| /// <example> | |
| /// This example uses a <c>ZlibStream</c> to compress data from a file, and writes the | |
| /// compressed data to another file. | |
| /// | |
| /// <code> | |
| /// using (System.IO.Stream input = System.IO.File.OpenRead(fileToCompress)) | |
| /// { | |
| /// using (var raw = System.IO.File.Create(fileToCompress + ".zlib")) | |
| /// { | |
| /// using (Stream compressor = new ZlibStream(raw, | |
| /// CompressionMode.Compress, | |
| /// CompressionLevel.BestCompression)) | |
| /// { | |
| /// byte[] buffer = new byte[WORKING_BUFFER_SIZE]; | |
| /// int n; | |
| /// while ((n= input.Read(buffer, 0, buffer.Length)) != 0) | |
| /// { | |
| /// compressor.Write(buffer, 0, n); | |
| /// } | |
| /// } | |
| /// } | |
| /// } | |
| /// </code> | |
| /// | |
| /// <code lang="VB"> | |
| /// Using input As Stream = File.OpenRead(fileToCompress) | |
| /// Using raw As FileStream = File.Create(fileToCompress & ".zlib") | |
| /// Using compressor As Stream = New ZlibStream(raw, CompressionMode.Compress, CompressionLevel.BestCompression) | |
| /// Dim buffer As Byte() = New Byte(4096) {} | |
| /// Dim n As Integer = -1 | |
| /// Do While (n <> 0) | |
| /// If (n > 0) Then | |
| /// compressor.Write(buffer, 0, n) | |
| /// End If | |
| /// n = input.Read(buffer, 0, buffer.Length) | |
| /// Loop | |
| /// End Using | |
| /// End Using | |
| /// End Using | |
| /// </code> | |
| /// </example> | |
| /// | |
| /// <param name="stream">The stream to be read or written while deflating or inflating.</param> | |
| /// <param name="mode">Indicates whether the ZlibStream will compress or decompress.</param> | |
| /// <param name="level">A tuning knob to trade speed for effectiveness.</param> | |
| public ZlibStream(System.IO.Stream stream, CompressionMode mode, CompressionLevel level) | |
| : this(stream, mode, level, false) | |
| { | |
| } | |
| /// <summary> | |
| /// Create a <c>ZlibStream</c> using the specified <c>CompressionMode</c>, and | |
| /// explicitly specify whether the captive stream should be left open after | |
| /// Deflation or Inflation. | |
| /// </summary> | |
| /// | |
| /// <remarks> | |
| /// | |
| /// <para> | |
| /// When mode is <c>CompressionMode.Compress</c>, the <c>ZlibStream</c> will use | |
| /// the default compression level. | |
| /// </para> | |
| /// | |
| /// <para> | |
| /// This constructor allows the application to request that the captive stream | |
| /// remain open after the deflation or inflation occurs. By default, after | |
| /// <c>Close()</c> is called on the stream, the captive stream is also | |
| /// closed. In some cases this is not desired, for example if the stream is a | |
| /// <see cref="System.IO.MemoryStream"/> that will be re-read after | |
| /// compression. Specify true for the <paramref name="leaveOpen"/> parameter to leave the stream | |
| /// open. | |
| /// </para> | |
| /// | |
| /// <para> | |
| /// See the other overloads of this constructor for example code. | |
| /// </para> | |
| /// | |
| /// </remarks> | |
| /// | |
| /// <param name="stream">The stream which will be read or written. This is called the | |
| /// "captive" stream in other places in this documentation.</param> | |
| /// <param name="mode">Indicates whether the ZlibStream will compress or decompress.</param> | |
| /// <param name="leaveOpen">true if the application would like the stream to remain | |
| /// open after inflation/deflation.</param> | |
| public ZlibStream(System.IO.Stream stream, CompressionMode mode, bool leaveOpen) | |
| : this(stream, mode, CompressionLevel.Default, leaveOpen) | |
| { | |
| } | |
| /// <summary> | |
| /// Create a <c>ZlibStream</c> using the specified <c>CompressionMode</c> | |
| /// and the specified <c>CompressionLevel</c>, and explicitly specify | |
| /// whether the stream should be left open after Deflation or Inflation. | |
| /// </summary> | |
| /// | |
| /// <remarks> | |
| /// | |
| /// <para> | |
| /// This constructor allows the application to request that the captive | |
| /// stream remain open after the deflation or inflation occurs. By | |
| /// default, after <c>Close()</c> is called on the stream, the captive | |
| /// stream is also closed. In some cases this is not desired, for example | |
| /// if the stream is a <see cref="System.IO.MemoryStream"/> that will be | |
| /// re-read after compression. Specify true for the <paramref | |
| /// name="leaveOpen"/> parameter to leave the stream open. | |
| /// </para> | |
| /// | |
| /// <para> | |
| /// When mode is <c>CompressionMode.Decompress</c>, the level parameter is | |
| /// ignored. | |
| /// </para> | |
| /// | |
| /// </remarks> | |
| /// | |
| /// <example> | |
| /// | |
| /// This example shows how to use a ZlibStream to compress the data from a file, | |
| /// and store the result into another file. The filestream remains open to allow | |
| /// additional data to be written to it. | |
| /// | |
| /// <code> | |
| /// using (var output = System.IO.File.Create(fileToCompress + ".zlib")) | |
| /// { | |
| /// using (System.IO.Stream input = System.IO.File.OpenRead(fileToCompress)) | |
| /// { | |
| /// using (Stream compressor = new ZlibStream(output, CompressionMode.Compress, CompressionLevel.BestCompression, true)) | |
| /// { | |
| /// byte[] buffer = new byte[WORKING_BUFFER_SIZE]; | |
| /// int n; | |
| /// while ((n= input.Read(buffer, 0, buffer.Length)) != 0) | |
| /// { | |
| /// compressor.Write(buffer, 0, n); | |
| /// } | |
| /// } | |
| /// } | |
| /// // can write additional data to the output stream here | |
| /// } | |
| /// </code> | |
| /// <code lang="VB"> | |
| /// Using output As FileStream = File.Create(fileToCompress & ".zlib") | |
| /// Using input As Stream = File.OpenRead(fileToCompress) | |
| /// Using compressor As Stream = New ZlibStream(output, CompressionMode.Compress, CompressionLevel.BestCompression, True) | |
| /// Dim buffer As Byte() = New Byte(4096) {} | |
| /// Dim n As Integer = -1 | |
| /// Do While (n <> 0) | |
| /// If (n > 0) Then | |
| /// compressor.Write(buffer, 0, n) | |
| /// End If | |
| /// n = input.Read(buffer, 0, buffer.Length) | |
| /// Loop | |
| /// End Using | |
| /// End Using | |
| /// ' can write additional data to the output stream here. | |
| /// End Using | |
| /// </code> | |
| /// </example> | |
| /// | |
| /// <param name="stream">The stream which will be read or written.</param> | |
| /// | |
| /// <param name="mode">Indicates whether the ZlibStream will compress or decompress.</param> | |
| /// | |
| /// <param name="leaveOpen"> | |
| /// true if the application would like the stream to remain open after | |
| /// inflation/deflation. | |
| /// </param> | |
| /// | |
| /// <param name="level"> | |
| /// A tuning knob to trade speed for effectiveness. This parameter is | |
| /// effective only when mode is <c>CompressionMode.Compress</c>. | |
| /// </param> | |
| public ZlibStream(System.IO.Stream stream, CompressionMode mode, CompressionLevel level, bool leaveOpen) | |
| { | |
| _baseStream = new ZlibBaseStream(stream, mode, level, ZlibStreamFlavor.ZLIB, leaveOpen); | |
| } | |
| #region Zlib properties | |
| /// <summary> | |
| /// This property sets the flush behavior on the stream. | |
| /// Sorry, though, not sure exactly how to describe all the various settings. | |
| /// </summary> | |
| virtual public FlushType FlushMode | |
| { | |
| get { return (this._baseStream._flushMode); } | |
| set | |
| { | |
| if (_disposed) throw new ObjectDisposedException("ZlibStream"); | |
| this._baseStream._flushMode = value; | |
| } | |
| } | |
| /// <summary> | |
| /// The size of the working buffer for the compression codec. | |
| /// </summary> | |
| /// | |
| /// <remarks> | |
| /// <para> | |
| /// The working buffer is used for all stream operations. The default size is | |
| /// 1024 bytes. The minimum size is 128 bytes. You may get better performance | |
| /// with a larger buffer. Then again, you might not. You would have to test | |
| /// it. | |
| /// </para> | |
| /// | |
| /// <para> | |
| /// Set this before the first call to <c>Read()</c> or <c>Write()</c> on the | |
| /// stream. If you try to set it afterwards, it will throw. | |
| /// </para> | |
| /// </remarks> | |
| public int BufferSize | |
| { | |
| get | |
| { | |
| return this._baseStream._bufferSize; | |
| } | |
| set | |
| { | |
| if (_disposed) throw new ObjectDisposedException("ZlibStream"); | |
| if (this._baseStream._workingBuffer != null) | |
| throw new ZlibException("The working buffer is already set."); | |
| if (value < ZlibConstants.WorkingBufferSizeMin) | |
| throw new ZlibException(String.Format("Don't be silly. {0} bytes?? Use a bigger buffer, at least {1}.", value, ZlibConstants.WorkingBufferSizeMin)); | |
| this._baseStream._bufferSize = value; | |
| } | |
| } | |
| /// <summary> Returns the total number of bytes input so far.</summary> | |
| virtual public long TotalIn | |
| { | |
| get { return this._baseStream._z.TotalBytesIn; } | |
| } | |
| /// <summary> Returns the total number of bytes output so far.</summary> | |
| virtual public long TotalOut | |
| { | |
| get { return this._baseStream._z.TotalBytesOut; } | |
| } | |
| #endregion | |
| #region System.IO.Stream methods | |
| /// <summary> | |
| /// Dispose the stream. | |
| /// </summary> | |
| /// <remarks> | |
| /// <para> | |
| /// This may or may not result in a <c>Close()</c> call on the captive | |
| /// stream. See the constructors that have a <c>leaveOpen</c> parameter | |
| /// for more information. | |
| /// </para> | |
| /// <para> | |
| /// This method may be invoked in two distinct scenarios. If disposing | |
| /// == true, the method has been called directly or indirectly by a | |
| /// user's code, for example via the public Dispose() method. In this | |
| /// case, both managed and unmanaged resources can be referenced and | |
| /// disposed. If disposing == false, the method has been called by the | |
| /// runtime from inside the object finalizer and this method should not | |
| /// reference other objects; in that case only unmanaged resources must | |
| /// be referenced or disposed. | |
| /// </para> | |
| /// </remarks> | |
| /// <param name="disposing"> | |
| /// indicates whether the Dispose method was invoked by user code. | |
| /// </param> | |
| protected override void Dispose(bool disposing) | |
| { | |
| try | |
| { | |
| if (!_disposed) | |
| { | |
| if (disposing && (this._baseStream != null)) | |
| this._baseStream.Close(); | |
| _disposed = true; | |
| } | |
| } | |
| finally | |
| { | |
| base.Dispose(disposing); | |
| } | |
| } | |
| /// <summary> | |
| /// Indicates whether the stream can be read. | |
| /// </summary> | |
| /// <remarks> | |
| /// The return value depends on whether the captive stream supports reading. | |
| /// </remarks> | |
| public override bool CanRead | |
| { | |
| get | |
| { | |
| if (_disposed) throw new ObjectDisposedException("ZlibStream"); | |
| return _baseStream._stream.CanRead; | |
| } | |
| } | |
| /// <summary> | |
| /// Indicates whether the stream supports Seek operations. | |
| /// </summary> | |
| /// <remarks> | |
| /// Always returns false. | |
| /// </remarks> | |
| public override bool CanSeek | |
| { | |
| get { return false; } | |
| } | |
| /// <summary> | |
| /// Indicates whether the stream can be written. | |
| /// </summary> | |
| /// <remarks> | |
| /// The return value depends on whether the captive stream supports writing. | |
| /// </remarks> | |
| public override bool CanWrite | |
| { | |
| get | |
| { | |
| if (_disposed) throw new ObjectDisposedException("ZlibStream"); | |
| return _baseStream._stream.CanWrite; | |
| } | |
| } | |
| /// <summary> | |
| /// Flush the stream. | |
| /// </summary> | |
| public override void Flush() | |
| { | |
| if (_disposed) throw new ObjectDisposedException("ZlibStream"); | |
| _baseStream.Flush(); | |
| } | |
| /// <summary> | |
| /// Reading this property always throws a <see cref="NotSupportedException"/>. | |
| /// </summary> | |
| public override long Length | |
| { | |
| get { throw new NotSupportedException(); } | |
| } | |
| /// <summary> | |
| /// The position of the stream pointer. | |
| /// </summary> | |
| /// | |
| /// <remarks> | |
| /// Setting this property always throws a <see | |
| /// cref="NotSupportedException"/>. Reading will return the total bytes | |
| /// written out, if used in writing, or the total bytes read in, if used in | |
| /// reading. The count may refer to compressed bytes or uncompressed bytes, | |
| /// depending on how you've used the stream. | |
| /// </remarks> | |
| public override long Position | |
| { | |
| get | |
| { | |
| if (this._baseStream._streamMode == Ionic.Zlib.ZlibBaseStream.StreamMode.Writer) | |
| return this._baseStream._z.TotalBytesOut; | |
| if (this._baseStream._streamMode == Ionic.Zlib.ZlibBaseStream.StreamMode.Reader) | |
| return this._baseStream._z.TotalBytesIn; | |
| return 0; | |
| } | |
| set { throw new NotSupportedException(); } | |
| } | |
| /// <summary> | |
| /// Read data from the stream. | |
| /// </summary> | |
| /// | |
| /// <remarks> | |
| /// | |
| /// <para> | |
| /// If you wish to use the <c>ZlibStream</c> to compress data while reading, | |
| /// you can create a <c>ZlibStream</c> with <c>CompressionMode.Compress</c>, | |
| /// providing an uncompressed data stream. Then call <c>Read()</c> on that | |
| /// <c>ZlibStream</c>, and the data read will be compressed. If you wish to | |
| /// use the <c>ZlibStream</c> to decompress data while reading, you can create | |
| /// a <c>ZlibStream</c> with <c>CompressionMode.Decompress</c>, providing a | |
| /// readable compressed data stream. Then call <c>Read()</c> on that | |
| /// <c>ZlibStream</c>, and the data will be decompressed as it is read. | |
| /// </para> | |
| /// | |
| /// <para> | |
| /// A <c>ZlibStream</c> can be used for <c>Read()</c> or <c>Write()</c>, but | |
| /// not both. | |
| /// </para> | |
| /// | |
| /// </remarks> | |
| /// | |
| /// <param name="buffer"> | |
| /// The buffer into which the read data should be placed.</param> | |
| /// | |
| /// <param name="offset"> | |
| /// the offset within that data array to put the first byte read.</param> | |
| /// | |
| /// <param name="count">the number of bytes to read.</param> | |
| /// | |
| /// <returns>the number of bytes read</returns> | |
| public override int Read(byte[] buffer, int offset, int count) | |
| { | |
| if (_disposed) throw new ObjectDisposedException("ZlibStream"); | |
| return _baseStream.Read(buffer, offset, count); | |
| } | |
| /// <summary> | |
| /// Calling this method always throws a <see cref="NotSupportedException"/>. | |
| /// </summary> | |
| /// <param name="offset"> | |
| /// The offset to seek to.... | |
| /// IF THIS METHOD ACTUALLY DID ANYTHING. | |
| /// </param> | |
| /// <param name="origin"> | |
| /// The reference specifying how to apply the offset.... IF | |
| /// THIS METHOD ACTUALLY DID ANYTHING. | |
| /// </param> | |
| /// | |
| /// <returns>nothing. This method always throws.</returns> | |
| public override long Seek(long offset, System.IO.SeekOrigin origin) | |
| { | |
| throw new NotSupportedException(); | |
| } | |
| /// <summary> | |
| /// Calling this method always throws a <see cref="NotSupportedException"/>. | |
| /// </summary> | |
| /// <param name="value"> | |
| /// The new value for the stream length.... IF | |
| /// THIS METHOD ACTUALLY DID ANYTHING. | |
| /// </param> | |
| public override void SetLength(long value) | |
| { | |
| throw new NotSupportedException(); | |
| } | |
| /// <summary> | |
| /// Write data to the stream. | |
| /// </summary> | |
| /// | |
| /// <remarks> | |
| /// | |
| /// <para> | |
| /// If you wish to use the <c>ZlibStream</c> to compress data while writing, | |
| /// you can create a <c>ZlibStream</c> with <c>CompressionMode.Compress</c>, | |
| /// and a writable output stream. Then call <c>Write()</c> on that | |
| /// <c>ZlibStream</c>, providing uncompressed data as input. The data sent to | |
| /// the output stream will be the compressed form of the data written. If you | |
| /// wish to use the <c>ZlibStream</c> to decompress data while writing, you | |
| /// can create a <c>ZlibStream</c> with <c>CompressionMode.Decompress</c>, and a | |
| /// writable output stream. Then call <c>Write()</c> on that stream, | |
| /// providing previously compressed data. The data sent to the output stream | |
| /// will be the decompressed form of the data written. | |
| /// </para> | |
| /// | |
| /// <para> | |
| /// A <c>ZlibStream</c> can be used for <c>Read()</c> or <c>Write()</c>, but not both. | |
| /// </para> | |
| /// </remarks> | |
| /// <param name="buffer">The buffer holding data to write to the stream.</param> | |
| /// <param name="offset">the offset within that data array to find the first byte to write.</param> | |
| /// <param name="count">the number of bytes to write.</param> | |
| public override void Write(byte[] buffer, int offset, int count) | |
| { | |
| if (_disposed) throw new ObjectDisposedException("ZlibStream"); | |
| _baseStream.Write(buffer, offset, count); | |
| } | |
| #endregion | |
| /// <summary> | |
| /// Compress a string into a byte array using ZLIB. | |
| /// </summary> | |
| /// | |
| /// <remarks> | |
| /// Uncompress it with <see cref="ZlibStream.UncompressString(byte[])"/>. | |
| /// </remarks> | |
| /// | |
| /// <seealso cref="ZlibStream.UncompressString(byte[])"/> | |
| /// <seealso cref="ZlibStream.CompressBuffer(byte[])"/> | |
| /// <seealso cref="GZipStream.CompressString(string)"/> | |
| /// | |
| /// <param name="s"> | |
| /// A string to compress. The string will first be encoded | |
| /// using UTF8, then compressed. | |
| /// </param> | |
| /// | |
| /// <returns>The string in compressed form</returns> | |
| public static byte[] CompressString(String s) | |
| { | |
| using (var ms = new MemoryStream()) | |
| { | |
| Stream compressor = | |
| new ZlibStream(ms, CompressionMode.Compress, CompressionLevel.BestCompression); | |
| ZlibBaseStream.CompressString(s, compressor); | |
| return ms.ToArray(); | |
| } | |
| } | |
| /// <summary> | |
| /// Compress a byte array into a new byte array using ZLIB. | |
| /// </summary> | |
| /// | |
| /// <remarks> | |
| /// Uncompress it with <see cref="ZlibStream.UncompressBuffer(byte[])"/>. | |
| /// </remarks> | |
| /// | |
| /// <seealso cref="ZlibStream.CompressString(string)"/> | |
| /// <seealso cref="ZlibStream.UncompressBuffer(byte[])"/> | |
| /// | |
| /// <param name="b"> | |
| /// A buffer to compress. | |
| /// </param> | |
| /// | |
| /// <returns>The data in compressed form</returns> | |
| public static byte[] CompressBuffer(byte[] b) | |
| { | |
| using (var ms = new MemoryStream()) | |
| { | |
| Stream compressor = | |
| new ZlibStream( ms, CompressionMode.Compress, CompressionLevel.BestCompression ); | |
| ZlibBaseStream.CompressBuffer(b, compressor); | |
| return ms.ToArray(); | |
| } | |
| } | |
| /// <summary> | |
| /// Uncompress a ZLIB-compressed byte array into a single string. | |
| /// </summary> | |
| /// | |
| /// <seealso cref="ZlibStream.CompressString(String)"/> | |
| /// <seealso cref="ZlibStream.UncompressBuffer(byte[])"/> | |
| /// | |
| /// <param name="compressed"> | |
| /// A buffer containing ZLIB-compressed data. | |
| /// </param> | |
| /// | |
| /// <returns>The uncompressed string</returns> | |
| public static String UncompressString(byte[] compressed) | |
| { | |
| using (var input = new MemoryStream(compressed)) | |
| { | |
| Stream decompressor = | |
| new ZlibStream(input, CompressionMode.Decompress); | |
| return ZlibBaseStream.UncompressString(compressed, decompressor); | |
| } | |
| } | |
| /// <summary> | |
| /// Uncompress a ZLIB-compressed byte array into a byte array. | |
| /// </summary> | |
| /// | |
| /// <seealso cref="ZlibStream.CompressBuffer(byte[])"/> | |
| /// <seealso cref="ZlibStream.UncompressString(byte[])"/> | |
| /// | |
| /// <param name="compressed"> | |
| /// A buffer containing ZLIB-compressed data. | |
| /// </param> | |
| /// | |
| /// <returns>The data in uncompressed form</returns> | |
| public static byte[] UncompressBuffer(byte[] compressed) | |
| { | |
| using (var input = new MemoryStream(compressed)) | |
| { | |
| Stream decompressor = | |
| new ZlibStream( input, CompressionMode.Decompress ); | |
| return ZlibBaseStream.UncompressBuffer(compressed, decompressor); | |
| } | |
| } | |
| } | |
| } |