diff options
Diffstat (limited to 'contrib/dotzlib/DotZLib')
-rw-r--r-- | contrib/dotzlib/DotZLib/AssemblyInfo.cs | 58 | ||||
-rw-r--r-- | contrib/dotzlib/DotZLib/ChecksumImpl.cs | 202 | ||||
-rw-r--r-- | contrib/dotzlib/DotZLib/CircularBuffer.cs | 83 | ||||
-rw-r--r-- | contrib/dotzlib/DotZLib/CodecBase.cs | 198 | ||||
-rw-r--r-- | contrib/dotzlib/DotZLib/Deflater.cs | 106 | ||||
-rw-r--r-- | contrib/dotzlib/DotZLib/DotZLib.cs | 288 | ||||
-rw-r--r-- | contrib/dotzlib/DotZLib/DotZLib.csproj | 141 | ||||
-rw-r--r-- | contrib/dotzlib/DotZLib/GZipStream.cs | 301 | ||||
-rw-r--r-- | contrib/dotzlib/DotZLib/Inflater.cs | 105 | ||||
-rw-r--r-- | contrib/dotzlib/DotZLib/UnitTests.cs | 274 |
10 files changed, 1756 insertions, 0 deletions
diff --git a/contrib/dotzlib/DotZLib/AssemblyInfo.cs b/contrib/dotzlib/DotZLib/AssemblyInfo.cs new file mode 100644 index 0000000..6fc0fdc --- /dev/null +++ b/contrib/dotzlib/DotZLib/AssemblyInfo.cs | |||
@@ -0,0 +1,58 @@ | |||
1 | using System.Reflection; | ||
2 | using System.Runtime.CompilerServices; | ||
3 | |||
4 | // | ||
5 | // General Information about an assembly is controlled through the following | ||
6 | // set of attributes. Change these attribute values to modify the information | ||
7 | // associated with an assembly. | ||
8 | // | ||
9 | [assembly: AssemblyTitle("DotZLib")] | ||
10 | [assembly: AssemblyDescription(".Net bindings for ZLib compression dll 1.2.x")] | ||
11 | [assembly: AssemblyConfiguration("")] | ||
12 | [assembly: AssemblyCompany("Henrik Ravn")] | ||
13 | [assembly: AssemblyProduct("")] | ||
14 | [assembly: AssemblyCopyright("(c) 2004 by Henrik Ravn")] | ||
15 | [assembly: AssemblyTrademark("")] | ||
16 | [assembly: AssemblyCulture("")] | ||
17 | |||
18 | // | ||
19 | // Version information for an assembly consists of the following four values: | ||
20 | // | ||
21 | // Major Version | ||
22 | // Minor Version | ||
23 | // Build Number | ||
24 | // Revision | ||
25 | // | ||
26 | // You can specify all the values or you can default the Revision and Build Numbers | ||
27 | // by using the '*' as shown below: | ||
28 | |||
29 | [assembly: AssemblyVersion("1.0.*")] | ||
30 | |||
31 | // | ||
32 | // In order to sign your assembly you must specify a key to use. Refer to the | ||
33 | // Microsoft .NET Framework documentation for more information on assembly signing. | ||
34 | // | ||
35 | // Use the attributes below to control which key is used for signing. | ||
36 | // | ||
37 | // Notes: | ||
38 | // (*) If no key is specified, the assembly is not signed. | ||
39 | // (*) KeyName refers to a key that has been installed in the Crypto Service | ||
40 | // Provider (CSP) on your machine. KeyFile refers to a file which contains | ||
41 | // a key. | ||
42 | // (*) If the KeyFile and the KeyName values are both specified, the | ||
43 | // following processing occurs: | ||
44 | // (1) If the KeyName can be found in the CSP, that key is used. | ||
45 | // (2) If the KeyName does not exist and the KeyFile does exist, the key | ||
46 | // in the KeyFile is installed into the CSP and used. | ||
47 | // (*) In order to create a KeyFile, you can use the sn.exe (Strong Name) utility. | ||
48 | // When specifying the KeyFile, the location of the KeyFile should be | ||
49 | // relative to the project output directory which is | ||
50 | // %Project Directory%\obj\<configuration>. For example, if your KeyFile is | ||
51 | // located in the project directory, you would specify the AssemblyKeyFile | ||
52 | // attribute as [assembly: AssemblyKeyFile("..\\..\\mykey.snk")] | ||
53 | // (*) Delay Signing is an advanced option - see the Microsoft .NET Framework | ||
54 | // documentation for more information on this. | ||
55 | // | ||
56 | [assembly: AssemblyDelaySign(false)] | ||
57 | [assembly: AssemblyKeyFile("")] | ||
58 | [assembly: AssemblyKeyName("")] | ||
diff --git a/contrib/dotzlib/DotZLib/ChecksumImpl.cs b/contrib/dotzlib/DotZLib/ChecksumImpl.cs new file mode 100644 index 0000000..dfe7e90 --- /dev/null +++ b/contrib/dotzlib/DotZLib/ChecksumImpl.cs | |||
@@ -0,0 +1,202 @@ | |||
1 | // | ||
2 | // © Copyright Henrik Ravn 2004 | ||
3 | // | ||
4 | // Use, modification and distribution are subject to the Boost Software License, Version 1.0. | ||
5 | // (See accompanying file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) | ||
6 | // | ||
7 | |||
8 | using System; | ||
9 | using System.Runtime.InteropServices; | ||
10 | using System.Text; | ||
11 | |||
12 | |||
13 | namespace DotZLib | ||
14 | { | ||
15 | #region ChecksumGeneratorBase | ||
16 | /// <summary> | ||
17 | /// Implements the common functionality needed for all <see cref="ChecksumGenerator"/>s | ||
18 | /// </summary> | ||
19 | /// <example></example> | ||
20 | public abstract class ChecksumGeneratorBase : ChecksumGenerator | ||
21 | { | ||
22 | /// <summary> | ||
23 | /// The value of the current checksum | ||
24 | /// </summary> | ||
25 | protected uint _current; | ||
26 | |||
27 | /// <summary> | ||
28 | /// Initializes a new instance of the checksum generator base - the current checksum is | ||
29 | /// set to zero | ||
30 | /// </summary> | ||
31 | public ChecksumGeneratorBase() | ||
32 | { | ||
33 | _current = 0; | ||
34 | } | ||
35 | |||
36 | /// <summary> | ||
37 | /// Initializes a new instance of the checksum generator basewith a specified value | ||
38 | /// </summary> | ||
39 | /// <param name="initialValue">The value to set the current checksum to</param> | ||
40 | public ChecksumGeneratorBase(uint initialValue) | ||
41 | { | ||
42 | _current = initialValue; | ||
43 | } | ||
44 | |||
45 | /// <summary> | ||
46 | /// Resets the current checksum to zero | ||
47 | /// </summary> | ||
48 | public void Reset() { _current = 0; } | ||
49 | |||
50 | /// <summary> | ||
51 | /// Gets the current checksum value | ||
52 | /// </summary> | ||
53 | public uint Value { get { return _current; } } | ||
54 | |||
55 | /// <summary> | ||
56 | /// Updates the current checksum with part of an array of bytes | ||
57 | /// </summary> | ||
58 | /// <param name="data">The data to update the checksum with</param> | ||
59 | /// <param name="offset">Where in <c>data</c> to start updating</param> | ||
60 | /// <param name="count">The number of bytes from <c>data</c> to use</param> | ||
61 | /// <exception cref="ArgumentException">The sum of offset and count is larger than the length of <c>data</c></exception> | ||
62 | /// <exception cref="NullReferenceException"><c>data</c> is a null reference</exception> | ||
63 | /// <exception cref="ArgumentOutOfRangeException">Offset or count is negative.</exception> | ||
64 | /// <remarks>All the other <c>Update</c> methods are implmeneted in terms of this one. | ||
65 | /// This is therefore the only method a derived class has to implement</remarks> | ||
66 | public abstract void Update(byte[] data, int offset, int count); | ||
67 | |||
68 | /// <summary> | ||
69 | /// Updates the current checksum with an array of bytes. | ||
70 | /// </summary> | ||
71 | /// <param name="data">The data to update the checksum with</param> | ||
72 | public void Update(byte[] data) | ||
73 | { | ||
74 | Update(data, 0, data.Length); | ||
75 | } | ||
76 | |||
77 | /// <summary> | ||
78 | /// Updates the current checksum with the data from a string | ||
79 | /// </summary> | ||
80 | /// <param name="data">The string to update the checksum with</param> | ||
81 | /// <remarks>The characters in the string are converted by the UTF-8 encoding</remarks> | ||
82 | public void Update(string data) | ||
83 | { | ||
84 | Update(Encoding.UTF8.GetBytes(data)); | ||
85 | } | ||
86 | |||
87 | /// <summary> | ||
88 | /// Updates the current checksum with the data from a string, using a specific encoding | ||
89 | /// </summary> | ||
90 | /// <param name="data">The string to update the checksum with</param> | ||
91 | /// <param name="encoding">The encoding to use</param> | ||
92 | public void Update(string data, Encoding encoding) | ||
93 | { | ||
94 | Update(encoding.GetBytes(data)); | ||
95 | } | ||
96 | |||
97 | } | ||
98 | #endregion | ||
99 | |||
100 | #region CRC32 | ||
101 | /// <summary> | ||
102 | /// Implements a CRC32 checksum generator | ||
103 | /// </summary> | ||
104 | public sealed class CRC32Checksum : ChecksumGeneratorBase | ||
105 | { | ||
106 | #region DLL imports | ||
107 | |||
108 | [DllImport("ZLIB1.dll", CallingConvention=CallingConvention.Cdecl)] | ||
109 | private static extern uint crc32(uint crc, int data, uint length); | ||
110 | |||
111 | #endregion | ||
112 | |||
113 | /// <summary> | ||
114 | /// Initializes a new instance of the CRC32 checksum generator | ||
115 | /// </summary> | ||
116 | public CRC32Checksum() : base() {} | ||
117 | |||
118 | /// <summary> | ||
119 | /// Initializes a new instance of the CRC32 checksum generator with a specified value | ||
120 | /// </summary> | ||
121 | /// <param name="initialValue">The value to set the current checksum to</param> | ||
122 | public CRC32Checksum(uint initialValue) : base(initialValue) {} | ||
123 | |||
124 | /// <summary> | ||
125 | /// Updates the current checksum with part of an array of bytes | ||
126 | /// </summary> | ||
127 | /// <param name="data">The data to update the checksum with</param> | ||
128 | /// <param name="offset">Where in <c>data</c> to start updating</param> | ||
129 | /// <param name="count">The number of bytes from <c>data</c> to use</param> | ||
130 | /// <exception cref="ArgumentException">The sum of offset and count is larger than the length of <c>data</c></exception> | ||
131 | /// <exception cref="NullReferenceException"><c>data</c> is a null reference</exception> | ||
132 | /// <exception cref="ArgumentOutOfRangeException">Offset or count is negative.</exception> | ||
133 | public override void Update(byte[] data, int offset, int count) | ||
134 | { | ||
135 | if (offset < 0 || count < 0) throw new ArgumentOutOfRangeException(); | ||
136 | if ((offset+count) > data.Length) throw new ArgumentException(); | ||
137 | GCHandle hData = GCHandle.Alloc(data, GCHandleType.Pinned); | ||
138 | try | ||
139 | { | ||
140 | _current = crc32(_current, hData.AddrOfPinnedObject().ToInt32()+offset, (uint)count); | ||
141 | } | ||
142 | finally | ||
143 | { | ||
144 | hData.Free(); | ||
145 | } | ||
146 | } | ||
147 | |||
148 | } | ||
149 | #endregion | ||
150 | |||
151 | #region Adler | ||
152 | /// <summary> | ||
153 | /// Implements a checksum generator that computes the Adler checksum on data | ||
154 | /// </summary> | ||
155 | public sealed class AdlerChecksum : ChecksumGeneratorBase | ||
156 | { | ||
157 | #region DLL imports | ||
158 | |||
159 | [DllImport("ZLIB1.dll", CallingConvention=CallingConvention.Cdecl)] | ||
160 | private static extern uint adler32(uint adler, int data, uint length); | ||
161 | |||
162 | #endregion | ||
163 | |||
164 | /// <summary> | ||
165 | /// Initializes a new instance of the Adler checksum generator | ||
166 | /// </summary> | ||
167 | public AdlerChecksum() : base() {} | ||
168 | |||
169 | /// <summary> | ||
170 | /// Initializes a new instance of the Adler checksum generator with a specified value | ||
171 | /// </summary> | ||
172 | /// <param name="initialValue">The value to set the current checksum to</param> | ||
173 | public AdlerChecksum(uint initialValue) : base(initialValue) {} | ||
174 | |||
175 | /// <summary> | ||
176 | /// Updates the current checksum with part of an array of bytes | ||
177 | /// </summary> | ||
178 | /// <param name="data">The data to update the checksum with</param> | ||
179 | /// <param name="offset">Where in <c>data</c> to start updating</param> | ||
180 | /// <param name="count">The number of bytes from <c>data</c> to use</param> | ||
181 | /// <exception cref="ArgumentException">The sum of offset and count is larger than the length of <c>data</c></exception> | ||
182 | /// <exception cref="NullReferenceException"><c>data</c> is a null reference</exception> | ||
183 | /// <exception cref="ArgumentOutOfRangeException">Offset or count is negative.</exception> | ||
184 | public override void Update(byte[] data, int offset, int count) | ||
185 | { | ||
186 | if (offset < 0 || count < 0) throw new ArgumentOutOfRangeException(); | ||
187 | if ((offset+count) > data.Length) throw new ArgumentException(); | ||
188 | GCHandle hData = GCHandle.Alloc(data, GCHandleType.Pinned); | ||
189 | try | ||
190 | { | ||
191 | _current = adler32(_current, hData.AddrOfPinnedObject().ToInt32()+offset, (uint)count); | ||
192 | } | ||
193 | finally | ||
194 | { | ||
195 | hData.Free(); | ||
196 | } | ||
197 | } | ||
198 | |||
199 | } | ||
200 | #endregion | ||
201 | |||
202 | } \ No newline at end of file | ||
diff --git a/contrib/dotzlib/DotZLib/CircularBuffer.cs b/contrib/dotzlib/DotZLib/CircularBuffer.cs new file mode 100644 index 0000000..16997e9 --- /dev/null +++ b/contrib/dotzlib/DotZLib/CircularBuffer.cs | |||
@@ -0,0 +1,83 @@ | |||
1 | // | ||
2 | // © Copyright Henrik Ravn 2004 | ||
3 | // | ||
4 | // Use, modification and distribution are subject to the Boost Software License, Version 1.0. | ||
5 | // (See accompanying file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) | ||
6 | // | ||
7 | |||
8 | using System; | ||
9 | using System.Diagnostics; | ||
10 | |||
11 | namespace DotZLib | ||
12 | { | ||
13 | |||
14 | /// <summary> | ||
15 | /// This class implements a circular buffer | ||
16 | /// </summary> | ||
17 | internal class CircularBuffer | ||
18 | { | ||
19 | #region Private data | ||
20 | private int _capacity; | ||
21 | private int _head; | ||
22 | private int _tail; | ||
23 | private int _size; | ||
24 | private byte[] _buffer; | ||
25 | #endregion | ||
26 | |||
27 | public CircularBuffer(int capacity) | ||
28 | { | ||
29 | Debug.Assert( capacity > 0 ); | ||
30 | _buffer = new byte[capacity]; | ||
31 | _capacity = capacity; | ||
32 | _head = 0; | ||
33 | _tail = 0; | ||
34 | _size = 0; | ||
35 | } | ||
36 | |||
37 | public int Size { get { return _size; } } | ||
38 | |||
39 | public int Put(byte[] source, int offset, int count) | ||
40 | { | ||
41 | Debug.Assert( count > 0 ); | ||
42 | int trueCount = Math.Min(count, _capacity - Size); | ||
43 | for (int i = 0; i < trueCount; ++i) | ||
44 | _buffer[(_tail+i) % _capacity] = source[offset+i]; | ||
45 | _tail += trueCount; | ||
46 | _tail %= _capacity; | ||
47 | _size += trueCount; | ||
48 | return trueCount; | ||
49 | } | ||
50 | |||
51 | public bool Put(byte b) | ||
52 | { | ||
53 | if (Size == _capacity) // no room | ||
54 | return false; | ||
55 | _buffer[_tail++] = b; | ||
56 | _tail %= _capacity; | ||
57 | ++_size; | ||
58 | return true; | ||
59 | } | ||
60 | |||
61 | public int Get(byte[] destination, int offset, int count) | ||
62 | { | ||
63 | int trueCount = Math.Min(count,Size); | ||
64 | for (int i = 0; i < trueCount; ++i) | ||
65 | destination[offset + i] = _buffer[(_head+i) % _capacity]; | ||
66 | _head += trueCount; | ||
67 | _head %= _capacity; | ||
68 | _size -= trueCount; | ||
69 | return trueCount; | ||
70 | } | ||
71 | |||
72 | public int Get() | ||
73 | { | ||
74 | if (Size == 0) | ||
75 | return -1; | ||
76 | |||
77 | int result = (int)_buffer[_head++ % _capacity]; | ||
78 | --_size; | ||
79 | return result; | ||
80 | } | ||
81 | |||
82 | } | ||
83 | } | ||
diff --git a/contrib/dotzlib/DotZLib/CodecBase.cs b/contrib/dotzlib/DotZLib/CodecBase.cs new file mode 100644 index 0000000..954db7d --- /dev/null +++ b/contrib/dotzlib/DotZLib/CodecBase.cs | |||
@@ -0,0 +1,198 @@ | |||
1 | // | ||
2 | // © Copyright Henrik Ravn 2004 | ||
3 | // | ||
4 | // Use, modification and distribution are subject to the Boost Software License, Version 1.0. | ||
5 | // (See accompanying file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) | ||
6 | // | ||
7 | |||
8 | using System; | ||
9 | using System.Runtime.InteropServices; | ||
10 | |||
11 | namespace DotZLib | ||
12 | { | ||
13 | /// <summary> | ||
14 | /// Implements the common functionality needed for all <see cref="Codec"/>s | ||
15 | /// </summary> | ||
16 | public abstract class CodecBase : Codec, IDisposable | ||
17 | { | ||
18 | |||
19 | #region Data members | ||
20 | |||
21 | /// <summary> | ||
22 | /// Instance of the internal zlib buffer structure that is | ||
23 | /// passed to all functions in the zlib dll | ||
24 | /// </summary> | ||
25 | internal ZStream _ztream = new ZStream(); | ||
26 | |||
27 | /// <summary> | ||
28 | /// True if the object instance has been disposed, false otherwise | ||
29 | /// </summary> | ||
30 | protected bool _isDisposed = false; | ||
31 | |||
32 | /// <summary> | ||
33 | /// The size of the internal buffers | ||
34 | /// </summary> | ||
35 | protected const int kBufferSize = 16384; | ||
36 | |||
37 | private byte[] _outBuffer = new byte[kBufferSize]; | ||
38 | private byte[] _inBuffer = new byte[kBufferSize]; | ||
39 | |||
40 | private GCHandle _hInput; | ||
41 | private GCHandle _hOutput; | ||
42 | |||
43 | private uint _checksum = 0; | ||
44 | |||
45 | #endregion | ||
46 | |||
47 | /// <summary> | ||
48 | /// Initializes a new instance of the <c>CodeBase</c> class. | ||
49 | /// </summary> | ||
50 | public CodecBase() | ||
51 | { | ||
52 | try | ||
53 | { | ||
54 | _hInput = GCHandle.Alloc(_inBuffer, GCHandleType.Pinned); | ||
55 | _hOutput = GCHandle.Alloc(_outBuffer, GCHandleType.Pinned); | ||
56 | } | ||
57 | catch (Exception) | ||
58 | { | ||
59 | CleanUp(false); | ||
60 | throw; | ||
61 | } | ||
62 | } | ||
63 | |||
64 | |||
65 | #region Codec Members | ||
66 | |||
67 | /// <summary> | ||
68 | /// Occurs when more processed data are available. | ||
69 | /// </summary> | ||
70 | public event DataAvailableHandler DataAvailable; | ||
71 | |||
72 | /// <summary> | ||
73 | /// Fires the <see cref="DataAvailable"/> event | ||
74 | /// </summary> | ||
75 | protected void OnDataAvailable() | ||
76 | { | ||
77 | if (_ztream.total_out > 0) | ||
78 | { | ||
79 | if (DataAvailable != null) | ||
80 | DataAvailable( _outBuffer, 0, (int)_ztream.total_out); | ||
81 | resetOutput(); | ||
82 | } | ||
83 | } | ||
84 | |||
85 | /// <summary> | ||
86 | /// Adds more data to the codec to be processed. | ||
87 | /// </summary> | ||
88 | /// <param name="data">Byte array containing the data to be added to the codec</param> | ||
89 | /// <remarks>Adding data may, or may not, raise the <c>DataAvailable</c> event</remarks> | ||
90 | public void Add(byte[] data) | ||
91 | { | ||
92 | Add(data,0,data.Length); | ||
93 | } | ||
94 | |||
95 | /// <summary> | ||
96 | /// Adds more data to the codec to be processed. | ||
97 | /// </summary> | ||
98 | /// <param name="data">Byte array containing the data to be added to the codec</param> | ||
99 | /// <param name="offset">The index of the first byte to add from <c>data</c></param> | ||
100 | /// <param name="count">The number of bytes to add</param> | ||
101 | /// <remarks>Adding data may, or may not, raise the <c>DataAvailable</c> event</remarks> | ||
102 | /// <remarks>This must be implemented by a derived class</remarks> | ||
103 | public abstract void Add(byte[] data, int offset, int count); | ||
104 | |||
105 | /// <summary> | ||
106 | /// Finishes up any pending data that needs to be processed and handled. | ||
107 | /// </summary> | ||
108 | /// <remarks>This must be implemented by a derived class</remarks> | ||
109 | public abstract void Finish(); | ||
110 | |||
111 | /// <summary> | ||
112 | /// Gets the checksum of the data that has been added so far | ||
113 | /// </summary> | ||
114 | public uint Checksum { get { return _checksum; } } | ||
115 | |||
116 | #endregion | ||
117 | |||
118 | #region Destructor & IDisposable stuff | ||
119 | |||
120 | /// <summary> | ||
121 | /// Destroys this instance | ||
122 | /// </summary> | ||
123 | ~CodecBase() | ||
124 | { | ||
125 | CleanUp(false); | ||
126 | } | ||
127 | |||
128 | /// <summary> | ||
129 | /// Releases any unmanaged resources and calls the <see cref="CleanUp()"/> method of the derived class | ||
130 | /// </summary> | ||
131 | public void Dispose() | ||
132 | { | ||
133 | CleanUp(true); | ||
134 | } | ||
135 | |||
136 | /// <summary> | ||
137 | /// Performs any codec specific cleanup | ||
138 | /// </summary> | ||
139 | /// <remarks>This must be implemented by a derived class</remarks> | ||
140 | protected abstract void CleanUp(); | ||
141 | |||
142 | // performs the release of the handles and calls the dereived CleanUp() | ||
143 | private void CleanUp(bool isDisposing) | ||
144 | { | ||
145 | if (!_isDisposed) | ||
146 | { | ||
147 | CleanUp(); | ||
148 | if (_hInput.IsAllocated) | ||
149 | _hInput.Free(); | ||
150 | if (_hOutput.IsAllocated) | ||
151 | _hOutput.Free(); | ||
152 | |||
153 | _isDisposed = true; | ||
154 | } | ||
155 | } | ||
156 | |||
157 | |||
158 | #endregion | ||
159 | |||
160 | #region Helper methods | ||
161 | |||
162 | /// <summary> | ||
163 | /// Copies a number of bytes to the internal codec buffer - ready for proccesing | ||
164 | /// </summary> | ||
165 | /// <param name="data">The byte array that contains the data to copy</param> | ||
166 | /// <param name="startIndex">The index of the first byte to copy</param> | ||
167 | /// <param name="count">The number of bytes to copy from <c>data</c></param> | ||
168 | protected void copyInput(byte[] data, int startIndex, int count) | ||
169 | { | ||
170 | Array.Copy(data, startIndex, _inBuffer,0, count); | ||
171 | _ztream.next_in = _hInput.AddrOfPinnedObject(); | ||
172 | _ztream.total_in = 0; | ||
173 | _ztream.avail_in = (uint)count; | ||
174 | |||
175 | } | ||
176 | |||
177 | /// <summary> | ||
178 | /// Resets the internal output buffers to a known state - ready for processing | ||
179 | /// </summary> | ||
180 | protected void resetOutput() | ||
181 | { | ||
182 | _ztream.total_out = 0; | ||
183 | _ztream.avail_out = kBufferSize; | ||
184 | _ztream.next_out = _hOutput.AddrOfPinnedObject(); | ||
185 | } | ||
186 | |||
187 | /// <summary> | ||
188 | /// Updates the running checksum property | ||
189 | /// </summary> | ||
190 | /// <param name="newSum">The new checksum value</param> | ||
191 | protected void setChecksum(uint newSum) | ||
192 | { | ||
193 | _checksum = newSum; | ||
194 | } | ||
195 | #endregion | ||
196 | |||
197 | } | ||
198 | } | ||
diff --git a/contrib/dotzlib/DotZLib/Deflater.cs b/contrib/dotzlib/DotZLib/Deflater.cs new file mode 100644 index 0000000..d7b8dcc --- /dev/null +++ b/contrib/dotzlib/DotZLib/Deflater.cs | |||
@@ -0,0 +1,106 @@ | |||
1 | // | ||
2 | // © Copyright Henrik Ravn 2004 | ||
3 | // | ||
4 | // Use, modification and distribution are subject to the Boost Software License, Version 1.0. | ||
5 | // (See accompanying file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) | ||
6 | // | ||
7 | |||
8 | using System; | ||
9 | using System.Diagnostics; | ||
10 | using System.Runtime.InteropServices; | ||
11 | |||
12 | namespace DotZLib | ||
13 | { | ||
14 | |||
15 | /// <summary> | ||
16 | /// Implements a data compressor, using the deflate algorithm in the ZLib dll | ||
17 | /// </summary> | ||
18 | public sealed class Deflater : CodecBase | ||
19 | { | ||
20 | #region Dll imports | ||
21 | [DllImport("ZLIB1.dll", CallingConvention=CallingConvention.Cdecl, CharSet=CharSet.Ansi)] | ||
22 | private static extern int deflateInit_(ref ZStream sz, int level, string vs, int size); | ||
23 | |||
24 | [DllImport("ZLIB1.dll", CallingConvention=CallingConvention.Cdecl)] | ||
25 | private static extern int deflate(ref ZStream sz, int flush); | ||
26 | |||
27 | [DllImport("ZLIB1.dll", CallingConvention=CallingConvention.Cdecl)] | ||
28 | private static extern int deflateReset(ref ZStream sz); | ||
29 | |||
30 | [DllImport("ZLIB1.dll", CallingConvention=CallingConvention.Cdecl)] | ||
31 | private static extern int deflateEnd(ref ZStream sz); | ||
32 | #endregion | ||
33 | |||
34 | /// <summary> | ||
35 | /// Constructs an new instance of the <c>Deflater</c> | ||
36 | /// </summary> | ||
37 | /// <param name="level">The compression level to use for this <c>Deflater</c></param> | ||
38 | public Deflater(CompressLevel level) : base() | ||
39 | { | ||
40 | int retval = deflateInit_(ref _ztream, (int)level, Info.Version, Marshal.SizeOf(_ztream)); | ||
41 | if (retval != 0) | ||
42 | throw new ZLibException(retval, "Could not initialize deflater"); | ||
43 | |||
44 | resetOutput(); | ||
45 | } | ||
46 | |||
47 | /// <summary> | ||
48 | /// Adds more data to the codec to be processed. | ||
49 | /// </summary> | ||
50 | /// <param name="data">Byte array containing the data to be added to the codec</param> | ||
51 | /// <param name="offset">The index of the first byte to add from <c>data</c></param> | ||
52 | /// <param name="count">The number of bytes to add</param> | ||
53 | /// <remarks>Adding data may, or may not, raise the <c>DataAvailable</c> event</remarks> | ||
54 | public override void Add(byte[] data, int offset, int count) | ||
55 | { | ||
56 | if (data == null) throw new ArgumentNullException(); | ||
57 | if (offset < 0 || count < 0) throw new ArgumentOutOfRangeException(); | ||
58 | if ((offset+count) > data.Length) throw new ArgumentException(); | ||
59 | |||
60 | int total = count; | ||
61 | int inputIndex = offset; | ||
62 | int err = 0; | ||
63 | |||
64 | while (err >= 0 && inputIndex < total) | ||
65 | { | ||
66 | copyInput(data, inputIndex, Math.Min(total - inputIndex, kBufferSize)); | ||
67 | while (err >= 0 && _ztream.avail_in > 0) | ||
68 | { | ||
69 | err = deflate(ref _ztream, (int)FlushTypes.None); | ||
70 | if (err == 0) | ||
71 | while (_ztream.avail_out == 0) | ||
72 | { | ||
73 | OnDataAvailable(); | ||
74 | err = deflate(ref _ztream, (int)FlushTypes.None); | ||
75 | } | ||
76 | inputIndex += (int)_ztream.total_in; | ||
77 | } | ||
78 | } | ||
79 | setChecksum( _ztream.adler ); | ||
80 | } | ||
81 | |||
82 | |||
83 | /// <summary> | ||
84 | /// Finishes up any pending data that needs to be processed and handled. | ||
85 | /// </summary> | ||
86 | public override void Finish() | ||
87 | { | ||
88 | int err; | ||
89 | do | ||
90 | { | ||
91 | err = deflate(ref _ztream, (int)FlushTypes.Finish); | ||
92 | OnDataAvailable(); | ||
93 | } | ||
94 | while (err == 0); | ||
95 | setChecksum( _ztream.adler ); | ||
96 | deflateReset(ref _ztream); | ||
97 | resetOutput(); | ||
98 | } | ||
99 | |||
100 | /// <summary> | ||
101 | /// Closes the internal zlib deflate stream | ||
102 | /// </summary> | ||
103 | protected override void CleanUp() { deflateEnd(ref _ztream); } | ||
104 | |||
105 | } | ||
106 | } | ||
diff --git a/contrib/dotzlib/DotZLib/DotZLib.cs b/contrib/dotzlib/DotZLib/DotZLib.cs new file mode 100644 index 0000000..410deb0 --- /dev/null +++ b/contrib/dotzlib/DotZLib/DotZLib.cs | |||
@@ -0,0 +1,288 @@ | |||
1 | // | ||
2 | // © Copyright Henrik Ravn 2004 | ||
3 | // | ||
4 | // Use, modification and distribution are subject to the Boost Software License, Version 1.0. | ||
5 | // (See accompanying file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) | ||
6 | // | ||
7 | |||
8 | using System; | ||
9 | using System.IO; | ||
10 | using System.Runtime.InteropServices; | ||
11 | using System.Text; | ||
12 | |||
13 | |||
14 | namespace DotZLib | ||
15 | { | ||
16 | |||
17 | #region Internal types | ||
18 | |||
19 | /// <summary> | ||
20 | /// Defines constants for the various flush types used with zlib | ||
21 | /// </summary> | ||
22 | internal enum FlushTypes | ||
23 | { | ||
24 | None, Partial, Sync, Full, Finish, Block | ||
25 | } | ||
26 | |||
27 | #region ZStream structure | ||
28 | // internal mapping of the zlib zstream structure for marshalling | ||
29 | [StructLayoutAttribute(LayoutKind.Sequential, Pack=4, Size=0, CharSet=CharSet.Ansi)] | ||
30 | internal struct ZStream | ||
31 | { | ||
32 | public IntPtr next_in; | ||
33 | public uint avail_in; | ||
34 | public uint total_in; | ||
35 | |||
36 | public IntPtr next_out; | ||
37 | public uint avail_out; | ||
38 | public uint total_out; | ||
39 | |||
40 | [MarshalAs(UnmanagedType.LPStr)] | ||
41 | string msg; | ||
42 | uint state; | ||
43 | |||
44 | uint zalloc; | ||
45 | uint zfree; | ||
46 | uint opaque; | ||
47 | |||
48 | int data_type; | ||
49 | public uint adler; | ||
50 | uint reserved; | ||
51 | } | ||
52 | |||
53 | #endregion | ||
54 | |||
55 | #endregion | ||
56 | |||
57 | #region Public enums | ||
58 | /// <summary> | ||
59 | /// Defines constants for the available compression levels in zlib | ||
60 | /// </summary> | ||
61 | public enum CompressLevel : int | ||
62 | { | ||
63 | /// <summary> | ||
64 | /// The default compression level with a reasonable compromise between compression and speed | ||
65 | /// </summary> | ||
66 | Default = -1, | ||
67 | /// <summary> | ||
68 | /// No compression at all. The data are passed straight through. | ||
69 | /// </summary> | ||
70 | None = 0, | ||
71 | /// <summary> | ||
72 | /// The maximum compression rate available. | ||
73 | /// </summary> | ||
74 | Best = 9, | ||
75 | /// <summary> | ||
76 | /// The fastest available compression level. | ||
77 | /// </summary> | ||
78 | Fastest = 1 | ||
79 | } | ||
80 | #endregion | ||
81 | |||
82 | #region Exception classes | ||
83 | /// <summary> | ||
84 | /// The exception that is thrown when an error occurs on the zlib dll | ||
85 | /// </summary> | ||
86 | public class ZLibException : ApplicationException | ||
87 | { | ||
88 | /// <summary> | ||
89 | /// Initializes a new instance of the <see cref="ZLibException"/> class with a specified | ||
90 | /// error message and error code | ||
91 | /// </summary> | ||
92 | /// <param name="errorCode">The zlib error code that caused the exception</param> | ||
93 | /// <param name="msg">A message that (hopefully) describes the error</param> | ||
94 | public ZLibException(int errorCode, string msg) : base(String.Format("ZLib error {0} {1}", errorCode, msg)) | ||
95 | { | ||
96 | } | ||
97 | |||
98 | /// <summary> | ||
99 | /// Initializes a new instance of the <see cref="ZLibException"/> class with a specified | ||
100 | /// error code | ||
101 | /// </summary> | ||
102 | /// <param name="errorCode">The zlib error code that caused the exception</param> | ||
103 | public ZLibException(int errorCode) : base(String.Format("ZLib error {0}", errorCode)) | ||
104 | { | ||
105 | } | ||
106 | } | ||
107 | #endregion | ||
108 | |||
109 | #region Interfaces | ||
110 | |||
111 | /// <summary> | ||
112 | /// Declares methods and properties that enables a running checksum to be calculated | ||
113 | /// </summary> | ||
114 | public interface ChecksumGenerator | ||
115 | { | ||
116 | /// <summary> | ||
117 | /// Gets the current value of the checksum | ||
118 | /// </summary> | ||
119 | uint Value { get; } | ||
120 | |||
121 | /// <summary> | ||
122 | /// Clears the current checksum to 0 | ||
123 | /// </summary> | ||
124 | void Reset(); | ||
125 | |||
126 | /// <summary> | ||
127 | /// Updates the current checksum with an array of bytes | ||
128 | /// </summary> | ||
129 | /// <param name="data">The data to update the checksum with</param> | ||
130 | void Update(byte[] data); | ||
131 | |||
132 | /// <summary> | ||
133 | /// Updates the current checksum with part of an array of bytes | ||
134 | /// </summary> | ||
135 | /// <param name="data">The data to update the checksum with</param> | ||
136 | /// <param name="offset">Where in <c>data</c> to start updating</param> | ||
137 | /// <param name="count">The number of bytes from <c>data</c> to use</param> | ||
138 | /// <exception cref="ArgumentException">The sum of offset and count is larger than the length of <c>data</c></exception> | ||
139 | /// <exception cref="ArgumentNullException"><c>data</c> is a null reference</exception> | ||
140 | /// <exception cref="ArgumentOutOfRangeException">Offset or count is negative.</exception> | ||
141 | void Update(byte[] data, int offset, int count); | ||
142 | |||
143 | /// <summary> | ||
144 | /// Updates the current checksum with the data from a string | ||
145 | /// </summary> | ||
146 | /// <param name="data">The string to update the checksum with</param> | ||
147 | /// <remarks>The characters in the string are converted by the UTF-8 encoding</remarks> | ||
148 | void Update(string data); | ||
149 | |||
150 | /// <summary> | ||
151 | /// Updates the current checksum with the data from a string, using a specific encoding | ||
152 | /// </summary> | ||
153 | /// <param name="data">The string to update the checksum with</param> | ||
154 | /// <param name="encoding">The encoding to use</param> | ||
155 | void Update(string data, Encoding encoding); | ||
156 | } | ||
157 | |||
158 | |||
159 | /// <summary> | ||
160 | /// Represents the method that will be called from a codec when new data | ||
161 | /// are available. | ||
162 | /// </summary> | ||
163 | /// <paramref name="data">The byte array containing the processed data</paramref> | ||
164 | /// <paramref name="startIndex">The index of the first processed byte in <c>data</c></paramref> | ||
165 | /// <paramref name="count">The number of processed bytes available</paramref> | ||
166 | /// <remarks>On return from this method, the data may be overwritten, so grab it while you can. | ||
167 | /// You cannot assume that startIndex will be zero. | ||
168 | /// </remarks> | ||
169 | public delegate void DataAvailableHandler(byte[] data, int startIndex, int count); | ||
170 | |||
171 | /// <summary> | ||
172 | /// Declares methods and events for implementing compressors/decompressors | ||
173 | /// </summary> | ||
174 | public interface Codec | ||
175 | { | ||
176 | /// <summary> | ||
177 | /// Occurs when more processed data are available. | ||
178 | /// </summary> | ||
179 | event DataAvailableHandler DataAvailable; | ||
180 | |||
181 | /// <summary> | ||
182 | /// Adds more data to the codec to be processed. | ||
183 | /// </summary> | ||
184 | /// <param name="data">Byte array containing the data to be added to the codec</param> | ||
185 | /// <remarks>Adding data may, or may not, raise the <c>DataAvailable</c> event</remarks> | ||
186 | void Add(byte[] data); | ||
187 | |||
188 | /// <summary> | ||
189 | /// Adds more data to the codec to be processed. | ||
190 | /// </summary> | ||
191 | /// <param name="data">Byte array containing the data to be added to the codec</param> | ||
192 | /// <param name="offset">The index of the first byte to add from <c>data</c></param> | ||
193 | /// <param name="count">The number of bytes to add</param> | ||
194 | /// <remarks>Adding data may, or may not, raise the <c>DataAvailable</c> event</remarks> | ||
195 | void Add(byte[] data, int offset, int count); | ||
196 | |||
197 | /// <summary> | ||
198 | /// Finishes up any pending data that needs to be processed and handled. | ||
199 | /// </summary> | ||
200 | void Finish(); | ||
201 | |||
202 | /// <summary> | ||
203 | /// Gets the checksum of the data that has been added so far | ||
204 | /// </summary> | ||
205 | uint Checksum { get; } | ||
206 | |||
207 | |||
208 | } | ||
209 | |||
210 | #endregion | ||
211 | |||
212 | #region Classes | ||
213 | /// <summary> | ||
214 | /// Encapsulates general information about the ZLib library | ||
215 | /// </summary> | ||
216 | public class Info | ||
217 | { | ||
218 | #region DLL imports | ||
219 | [DllImport("ZLIB1.dll", CallingConvention=CallingConvention.Cdecl)] | ||
220 | private static extern uint zlibCompileFlags(); | ||
221 | |||
222 | [DllImport("ZLIB1.dll", CallingConvention=CallingConvention.Cdecl)] | ||
223 | private static extern string zlibVersion(); | ||
224 | #endregion | ||
225 | |||
226 | #region Private stuff | ||
227 | private uint _flags; | ||
228 | |||
229 | // helper function that unpacks a bitsize mask | ||
230 | private static int bitSize(uint bits) | ||
231 | { | ||
232 | switch (bits) | ||
233 | { | ||
234 | case 0: return 16; | ||
235 | case 1: return 32; | ||
236 | case 2: return 64; | ||
237 | } | ||
238 | return -1; | ||
239 | } | ||
240 | #endregion | ||
241 | |||
242 | /// <summary> | ||
243 | /// Constructs an instance of the <c>Info</c> class. | ||
244 | /// </summary> | ||
245 | public Info() | ||
246 | { | ||
247 | _flags = zlibCompileFlags(); | ||
248 | } | ||
249 | |||
250 | /// <summary> | ||
251 | /// True if the library is compiled with debug info | ||
252 | /// </summary> | ||
253 | public bool HasDebugInfo { get { return 0 != (_flags & 0x100); } } | ||
254 | |||
255 | /// <summary> | ||
256 | /// True if the library is compiled with assembly optimizations | ||
257 | /// </summary> | ||
258 | public bool UsesAssemblyCode { get { return 0 != (_flags & 0x200); } } | ||
259 | |||
260 | /// <summary> | ||
261 | /// Gets the size of the unsigned int that was compiled into Zlib | ||
262 | /// </summary> | ||
263 | public int SizeOfUInt { get { return bitSize(_flags & 3); } } | ||
264 | |||
265 | /// <summary> | ||
266 | /// Gets the size of the unsigned long that was compiled into Zlib | ||
267 | /// </summary> | ||
268 | public int SizeOfULong { get { return bitSize((_flags >> 2) & 3); } } | ||
269 | |||
270 | /// <summary> | ||
271 | /// Gets the size of the pointers that were compiled into Zlib | ||
272 | /// </summary> | ||
273 | public int SizeOfPointer { get { return bitSize((_flags >> 4) & 3); } } | ||
274 | |||
275 | /// <summary> | ||
276 | /// Gets the size of the z_off_t type that was compiled into Zlib | ||
277 | /// </summary> | ||
278 | public int SizeOfOffset { get { return bitSize((_flags >> 6) & 3); } } | ||
279 | |||
280 | /// <summary> | ||
281 | /// Gets the version of ZLib as a string, e.g. "1.2.1" | ||
282 | /// </summary> | ||
283 | public static string Version { get { return zlibVersion(); } } | ||
284 | } | ||
285 | |||
286 | #endregion | ||
287 | |||
288 | } | ||
diff --git a/contrib/dotzlib/DotZLib/DotZLib.csproj b/contrib/dotzlib/DotZLib/DotZLib.csproj new file mode 100644 index 0000000..71eeb85 --- /dev/null +++ b/contrib/dotzlib/DotZLib/DotZLib.csproj | |||
@@ -0,0 +1,141 @@ | |||
1 | <VisualStudioProject> | ||
2 | <CSHARP | ||
3 | ProjectType = "Local" | ||
4 | ProductVersion = "7.10.3077" | ||
5 | SchemaVersion = "2.0" | ||
6 | ProjectGuid = "{BB1EE0B1-1808-46CB-B786-949D91117FC5}" | ||
7 | > | ||
8 | <Build> | ||
9 | <Settings | ||
10 | ApplicationIcon = "" | ||
11 | AssemblyKeyContainerName = "" | ||
12 | AssemblyName = "DotZLib" | ||
13 | AssemblyOriginatorKeyFile = "" | ||
14 | DefaultClientScript = "JScript" | ||
15 | DefaultHTMLPageLayout = "Grid" | ||
16 | DefaultTargetSchema = "IE50" | ||
17 | DelaySign = "false" | ||
18 | OutputType = "Library" | ||
19 | PreBuildEvent = "" | ||
20 | PostBuildEvent = "" | ||
21 | RootNamespace = "DotZLib" | ||
22 | RunPostBuildEvent = "OnBuildSuccess" | ||
23 | StartupObject = "" | ||
24 | > | ||
25 | <Config | ||
26 | Name = "Debug" | ||
27 | AllowUnsafeBlocks = "false" | ||
28 | BaseAddress = "285212672" | ||
29 | CheckForOverflowUnderflow = "false" | ||
30 | ConfigurationOverrideFile = "" | ||
31 | DefineConstants = "DEBUG;TRACE" | ||
32 | DocumentationFile = "docs\DotZLib.xml" | ||
33 | DebugSymbols = "true" | ||
34 | FileAlignment = "4096" | ||
35 | IncrementalBuild = "false" | ||
36 | NoStdLib = "false" | ||
37 | NoWarn = "1591" | ||
38 | Optimize = "false" | ||
39 | OutputPath = "bin\Debug\" | ||
40 | RegisterForComInterop = "false" | ||
41 | RemoveIntegerChecks = "false" | ||
42 | TreatWarningsAsErrors = "false" | ||
43 | WarningLevel = "4" | ||
44 | /> | ||
45 | <Config | ||
46 | Name = "Release" | ||
47 | AllowUnsafeBlocks = "false" | ||
48 | BaseAddress = "285212672" | ||
49 | CheckForOverflowUnderflow = "false" | ||
50 | ConfigurationOverrideFile = "" | ||
51 | DefineConstants = "TRACE" | ||
52 | DocumentationFile = "docs\DotZLib.xml" | ||
53 | DebugSymbols = "false" | ||
54 | FileAlignment = "4096" | ||
55 | IncrementalBuild = "false" | ||
56 | NoStdLib = "false" | ||
57 | NoWarn = "" | ||
58 | Optimize = "true" | ||
59 | OutputPath = "bin\Release\" | ||
60 | RegisterForComInterop = "false" | ||
61 | RemoveIntegerChecks = "false" | ||
62 | TreatWarningsAsErrors = "false" | ||
63 | WarningLevel = "4" | ||
64 | /> | ||
65 | </Settings> | ||
66 | <References> | ||
67 | <Reference | ||
68 | Name = "System" | ||
69 | AssemblyName = "System" | ||
70 | HintPath = "C:\WINNT\Microsoft.NET\Framework\v1.1.4322\System.dll" | ||
71 | /> | ||
72 | <Reference | ||
73 | Name = "System.Data" | ||
74 | AssemblyName = "System.Data" | ||
75 | HintPath = "C:\WINNT\Microsoft.NET\Framework\v1.1.4322\System.Data.dll" | ||
76 | /> | ||
77 | <Reference | ||
78 | Name = "System.XML" | ||
79 | AssemblyName = "System.Xml" | ||
80 | HintPath = "C:\WINNT\Microsoft.NET\Framework\v1.1.4322\System.XML.dll" | ||
81 | /> | ||
82 | <Reference | ||
83 | Name = "nunit.framework" | ||
84 | AssemblyName = "nunit.framework" | ||
85 | HintPath = "E:\apps\NUnit V2.1\\bin\nunit.framework.dll" | ||
86 | AssemblyFolderKey = "hklm\dn\nunit.framework" | ||
87 | /> | ||
88 | </References> | ||
89 | </Build> | ||
90 | <Files> | ||
91 | <Include> | ||
92 | <File | ||
93 | RelPath = "AssemblyInfo.cs" | ||
94 | SubType = "Code" | ||
95 | BuildAction = "Compile" | ||
96 | /> | ||
97 | <File | ||
98 | RelPath = "ChecksumImpl.cs" | ||
99 | SubType = "Code" | ||
100 | BuildAction = "Compile" | ||
101 | /> | ||
102 | <File | ||
103 | RelPath = "CircularBuffer.cs" | ||
104 | SubType = "Code" | ||
105 | BuildAction = "Compile" | ||
106 | /> | ||
107 | <File | ||
108 | RelPath = "CodecBase.cs" | ||
109 | SubType = "Code" | ||
110 | BuildAction = "Compile" | ||
111 | /> | ||
112 | <File | ||
113 | RelPath = "Deflater.cs" | ||
114 | SubType = "Code" | ||
115 | BuildAction = "Compile" | ||
116 | /> | ||
117 | <File | ||
118 | RelPath = "DotZLib.cs" | ||
119 | SubType = "Code" | ||
120 | BuildAction = "Compile" | ||
121 | /> | ||
122 | <File | ||
123 | RelPath = "GZipStream.cs" | ||
124 | SubType = "Code" | ||
125 | BuildAction = "Compile" | ||
126 | /> | ||
127 | <File | ||
128 | RelPath = "Inflater.cs" | ||
129 | SubType = "Code" | ||
130 | BuildAction = "Compile" | ||
131 | /> | ||
132 | <File | ||
133 | RelPath = "UnitTests.cs" | ||
134 | SubType = "Code" | ||
135 | BuildAction = "Compile" | ||
136 | /> | ||
137 | </Include> | ||
138 | </Files> | ||
139 | </CSHARP> | ||
140 | </VisualStudioProject> | ||
141 | |||
diff --git a/contrib/dotzlib/DotZLib/GZipStream.cs b/contrib/dotzlib/DotZLib/GZipStream.cs new file mode 100644 index 0000000..f861675 --- /dev/null +++ b/contrib/dotzlib/DotZLib/GZipStream.cs | |||
@@ -0,0 +1,301 @@ | |||
1 | // | ||
2 | // © Copyright Henrik Ravn 2004 | ||
3 | // | ||
4 | // Use, modification and distribution are subject to the Boost Software License, Version 1.0. | ||
5 | // (See accompanying file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) | ||
6 | // | ||
7 | |||
8 | using System; | ||
9 | using System.IO; | ||
10 | using System.Runtime.InteropServices; | ||
11 | |||
12 | namespace DotZLib | ||
13 | { | ||
14 | /// <summary> | ||
15 | /// Implements a compressed <see cref="Stream"/>, in GZip (.gz) format. | ||
16 | /// </summary> | ||
17 | public class GZipStream : Stream, IDisposable | ||
18 | { | ||
19 | #region Dll Imports | ||
20 | [DllImport("ZLIB1.dll", CallingConvention=CallingConvention.Cdecl, CharSet=CharSet.Ansi)] | ||
21 | private static extern IntPtr gzopen(string name, string mode); | ||
22 | |||
23 | [DllImport("ZLIB1.dll", CallingConvention=CallingConvention.Cdecl)] | ||
24 | private static extern int gzclose(IntPtr gzFile); | ||
25 | |||
26 | [DllImport("ZLIB1.dll", CallingConvention=CallingConvention.Cdecl)] | ||
27 | private static extern int gzwrite(IntPtr gzFile, int data, int length); | ||
28 | |||
29 | [DllImport("ZLIB1.dll", CallingConvention=CallingConvention.Cdecl)] | ||
30 | private static extern int gzread(IntPtr gzFile, int data, int length); | ||
31 | |||
32 | [DllImport("ZLIB1.dll", CallingConvention=CallingConvention.Cdecl)] | ||
33 | private static extern int gzgetc(IntPtr gzFile); | ||
34 | |||
35 | [DllImport("ZLIB1.dll", CallingConvention=CallingConvention.Cdecl)] | ||
36 | private static extern int gzputc(IntPtr gzFile, int c); | ||
37 | |||
38 | #endregion | ||
39 | |||
40 | #region Private data | ||
41 | private IntPtr _gzFile; | ||
42 | private bool _isDisposed = false; | ||
43 | private bool _isWriting; | ||
44 | #endregion | ||
45 | |||
46 | #region Constructors | ||
47 | /// <summary> | ||
48 | /// Creates a new file as a writeable GZipStream | ||
49 | /// </summary> | ||
50 | /// <param name="fileName">The name of the compressed file to create</param> | ||
51 | /// <param name="level">The compression level to use when adding data</param> | ||
52 | /// <exception cref="ZLibException">If an error occurred in the internal zlib function</exception> | ||
53 | public GZipStream(string fileName, CompressLevel level) | ||
54 | { | ||
55 | _isWriting = true; | ||
56 | _gzFile = gzopen(fileName, String.Format("wb{0}", (int)level)); | ||
57 | if (_gzFile == IntPtr.Zero) | ||
58 | throw new ZLibException(-1, "Could not open " + fileName); | ||
59 | } | ||
60 | |||
61 | /// <summary> | ||
62 | /// Opens an existing file as a readable GZipStream | ||
63 | /// </summary> | ||
64 | /// <param name="fileName">The name of the file to open</param> | ||
65 | /// <exception cref="ZLibException">If an error occurred in the internal zlib function</exception> | ||
66 | public GZipStream(string fileName) | ||
67 | { | ||
68 | _isWriting = false; | ||
69 | _gzFile = gzopen(fileName, "rb"); | ||
70 | if (_gzFile == IntPtr.Zero) | ||
71 | throw new ZLibException(-1, "Could not open " + fileName); | ||
72 | |||
73 | } | ||
74 | #endregion | ||
75 | |||
76 | #region Access properties | ||
77 | /// <summary> | ||
78 | /// Returns true of this stream can be read from, false otherwise | ||
79 | /// </summary> | ||
80 | public override bool CanRead | ||
81 | { | ||
82 | get | ||
83 | { | ||
84 | return !_isWriting; | ||
85 | } | ||
86 | } | ||
87 | |||
88 | |||
89 | /// <summary> | ||
90 | /// Returns false. | ||
91 | /// </summary> | ||
92 | public override bool CanSeek | ||
93 | { | ||
94 | get | ||
95 | { | ||
96 | return false; | ||
97 | } | ||
98 | } | ||
99 | |||
100 | /// <summary> | ||
101 | /// Returns true if this tsream is writeable, false otherwise | ||
102 | /// </summary> | ||
103 | public override bool CanWrite | ||
104 | { | ||
105 | get | ||
106 | { | ||
107 | return _isWriting; | ||
108 | } | ||
109 | } | ||
110 | #endregion | ||
111 | |||
112 | #region Destructor & IDispose stuff | ||
113 | |||
114 | /// <summary> | ||
115 | /// Destroys this instance | ||
116 | /// </summary> | ||
117 | ~GZipStream() | ||
118 | { | ||
119 | cleanUp(false); | ||
120 | } | ||
121 | |||
122 | /// <summary> | ||
123 | /// Closes the external file handle | ||
124 | /// </summary> | ||
125 | public void Dispose() | ||
126 | { | ||
127 | cleanUp(true); | ||
128 | } | ||
129 | |||
130 | // Does the actual closing of the file handle. | ||
131 | private void cleanUp(bool isDisposing) | ||
132 | { | ||
133 | if (!_isDisposed) | ||
134 | { | ||
135 | gzclose(_gzFile); | ||
136 | _isDisposed = true; | ||
137 | } | ||
138 | } | ||
139 | #endregion | ||
140 | |||
141 | #region Basic reading and writing | ||
142 | /// <summary> | ||
143 | /// Attempts to read a number of bytes from the stream. | ||
144 | /// </summary> | ||
145 | /// <param name="buffer">The destination data buffer</param> | ||
146 | /// <param name="offset">The index of the first destination byte in <c>buffer</c></param> | ||
147 | /// <param name="count">The number of bytes requested</param> | ||
148 | /// <returns>The number of bytes read</returns> | ||
149 | /// <exception cref="ArgumentNullException">If <c>buffer</c> is null</exception> | ||
150 | /// <exception cref="ArgumentOutOfRangeException">If <c>count</c> or <c>offset</c> are negative</exception> | ||
151 | /// <exception cref="ArgumentException">If <c>offset</c> + <c>count</c> is > buffer.Length</exception> | ||
152 | /// <exception cref="NotSupportedException">If this stream is not readable.</exception> | ||
153 | /// <exception cref="ObjectDisposedException">If this stream has been disposed.</exception> | ||
154 | public override int Read(byte[] buffer, int offset, int count) | ||
155 | { | ||
156 | if (!CanRead) throw new NotSupportedException(); | ||
157 | if (buffer == null) throw new ArgumentNullException(); | ||
158 | if (offset < 0 || count < 0) throw new ArgumentOutOfRangeException(); | ||
159 | if ((offset+count) > buffer.Length) throw new ArgumentException(); | ||
160 | if (_isDisposed) throw new ObjectDisposedException("GZipStream"); | ||
161 | |||
162 | GCHandle h = GCHandle.Alloc(buffer, GCHandleType.Pinned); | ||
163 | int result; | ||
164 | try | ||
165 | { | ||
166 | result = gzread(_gzFile, h.AddrOfPinnedObject().ToInt32() + offset, count); | ||
167 | if (result < 0) | ||
168 | throw new IOException(); | ||
169 | } | ||
170 | finally | ||
171 | { | ||
172 | h.Free(); | ||
173 | } | ||
174 | return result; | ||
175 | } | ||
176 | |||
177 | /// <summary> | ||
178 | /// Attempts to read a single byte from the stream. | ||
179 | /// </summary> | ||
180 | /// <returns>The byte that was read, or -1 in case of error or End-Of-File</returns> | ||
181 | public override int ReadByte() | ||
182 | { | ||
183 | if (!CanRead) throw new NotSupportedException(); | ||
184 | if (_isDisposed) throw new ObjectDisposedException("GZipStream"); | ||
185 | return gzgetc(_gzFile); | ||
186 | } | ||
187 | |||
188 | /// <summary> | ||
189 | /// Writes a number of bytes to the stream | ||
190 | /// </summary> | ||
191 | /// <param name="buffer"></param> | ||
192 | /// <param name="offset"></param> | ||
193 | /// <param name="count"></param> | ||
194 | /// <exception cref="ArgumentNullException">If <c>buffer</c> is null</exception> | ||
195 | /// <exception cref="ArgumentOutOfRangeException">If <c>count</c> or <c>offset</c> are negative</exception> | ||
196 | /// <exception cref="ArgumentException">If <c>offset</c> + <c>count</c> is > buffer.Length</exception> | ||
197 | /// <exception cref="NotSupportedException">If this stream is not writeable.</exception> | ||
198 | /// <exception cref="ObjectDisposedException">If this stream has been disposed.</exception> | ||
199 | public override void Write(byte[] buffer, int offset, int count) | ||
200 | { | ||
201 | if (!CanWrite) throw new NotSupportedException(); | ||
202 | if (buffer == null) throw new ArgumentNullException(); | ||
203 | if (offset < 0 || count < 0) throw new ArgumentOutOfRangeException(); | ||
204 | if ((offset+count) > buffer.Length) throw new ArgumentException(); | ||
205 | if (_isDisposed) throw new ObjectDisposedException("GZipStream"); | ||
206 | |||
207 | GCHandle h = GCHandle.Alloc(buffer, GCHandleType.Pinned); | ||
208 | try | ||
209 | { | ||
210 | int result = gzwrite(_gzFile, h.AddrOfPinnedObject().ToInt32() + offset, count); | ||
211 | if (result < 0) | ||
212 | throw new IOException(); | ||
213 | } | ||
214 | finally | ||
215 | { | ||
216 | h.Free(); | ||
217 | } | ||
218 | } | ||
219 | |||
220 | /// <summary> | ||
221 | /// Writes a single byte to the stream | ||
222 | /// </summary> | ||
223 | /// <param name="value">The byte to add to the stream.</param> | ||
224 | /// <exception cref="NotSupportedException">If this stream is not writeable.</exception> | ||
225 | /// <exception cref="ObjectDisposedException">If this stream has been disposed.</exception> | ||
226 | public override void WriteByte(byte value) | ||
227 | { | ||
228 | if (!CanWrite) throw new NotSupportedException(); | ||
229 | if (_isDisposed) throw new ObjectDisposedException("GZipStream"); | ||
230 | |||
231 | int result = gzputc(_gzFile, (int)value); | ||
232 | if (result < 0) | ||
233 | throw new IOException(); | ||
234 | } | ||
235 | #endregion | ||
236 | |||
237 | #region Position & length stuff | ||
238 | /// <summary> | ||
239 | /// Not supported. | ||
240 | /// </summary> | ||
241 | /// <param name="value"></param> | ||
242 | /// <exception cref="NotSupportedException">Always thrown</exception> | ||
243 | public override void SetLength(long value) | ||
244 | { | ||
245 | throw new NotSupportedException(); | ||
246 | } | ||
247 | |||
248 | /// <summary> | ||
249 | /// Not suppported. | ||
250 | /// </summary> | ||
251 | /// <param name="offset"></param> | ||
252 | /// <param name="origin"></param> | ||
253 | /// <returns></returns> | ||
254 | /// <exception cref="NotSupportedException">Always thrown</exception> | ||
255 | public override long Seek(long offset, SeekOrigin origin) | ||
256 | { | ||
257 | throw new NotSupportedException(); | ||
258 | } | ||
259 | |||
260 | /// <summary> | ||
261 | /// Flushes the <c>GZipStream</c>. | ||
262 | /// </summary> | ||
263 | /// <remarks>In this implementation, this method does nothing. This is because excessive | ||
264 | /// flushing may degrade the achievable compression rates.</remarks> | ||
265 | public override void Flush() | ||
266 | { | ||
267 | // left empty on purpose | ||
268 | } | ||
269 | |||
270 | /// <summary> | ||
271 | /// Gets/sets the current position in the <c>GZipStream</c>. Not suppported. | ||
272 | /// </summary> | ||
273 | /// <remarks>In this implementation this property is not supported</remarks> | ||
274 | /// <exception cref="NotSupportedException">Always thrown</exception> | ||
275 | public override long Position | ||
276 | { | ||
277 | get | ||
278 | { | ||
279 | throw new NotSupportedException(); | ||
280 | } | ||
281 | set | ||
282 | { | ||
283 | throw new NotSupportedException(); | ||
284 | } | ||
285 | } | ||
286 | |||
287 | /// <summary> | ||
288 | /// Gets the size of the stream. Not suppported. | ||
289 | /// </summary> | ||
290 | /// <remarks>In this implementation this property is not supported</remarks> | ||
291 | /// <exception cref="NotSupportedException">Always thrown</exception> | ||
292 | public override long Length | ||
293 | { | ||
294 | get | ||
295 | { | ||
296 | throw new NotSupportedException(); | ||
297 | } | ||
298 | } | ||
299 | #endregion | ||
300 | } | ||
301 | } | ||
diff --git a/contrib/dotzlib/DotZLib/Inflater.cs b/contrib/dotzlib/DotZLib/Inflater.cs new file mode 100644 index 0000000..4e60cda --- /dev/null +++ b/contrib/dotzlib/DotZLib/Inflater.cs | |||
@@ -0,0 +1,105 @@ | |||
1 | // | ||
2 | // © Copyright Henrik Ravn 2004 | ||
3 | // | ||
4 | // Use, modification and distribution are subject to the Boost Software License, Version 1.0. | ||
5 | // (See accompanying file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) | ||
6 | // | ||
7 | |||
8 | using System; | ||
9 | using System.Diagnostics; | ||
10 | using System.Runtime.InteropServices; | ||
11 | |||
12 | namespace DotZLib | ||
13 | { | ||
14 | |||
15 | /// <summary> | ||
16 | /// Implements a data decompressor, using the inflate algorithm in the ZLib dll | ||
17 | /// </summary> | ||
18 | public class Inflater : CodecBase | ||
19 | { | ||
20 | #region Dll imports | ||
21 | [DllImport("ZLIB1.dll", CallingConvention=CallingConvention.Cdecl, CharSet=CharSet.Ansi)] | ||
22 | private static extern int inflateInit_(ref ZStream sz, string vs, int size); | ||
23 | |||
24 | [DllImport("ZLIB1.dll", CallingConvention=CallingConvention.Cdecl)] | ||
25 | private static extern int inflate(ref ZStream sz, int flush); | ||
26 | |||
27 | [DllImport("ZLIB1.dll", CallingConvention=CallingConvention.Cdecl)] | ||
28 | private static extern int inflateReset(ref ZStream sz); | ||
29 | |||
30 | [DllImport("ZLIB1.dll", CallingConvention=CallingConvention.Cdecl)] | ||
31 | private static extern int inflateEnd(ref ZStream sz); | ||
32 | #endregion | ||
33 | |||
34 | /// <summary> | ||
35 | /// Constructs an new instance of the <c>Inflater</c> | ||
36 | /// </summary> | ||
37 | public Inflater() : base() | ||
38 | { | ||
39 | int retval = inflateInit_(ref _ztream, Info.Version, Marshal.SizeOf(_ztream)); | ||
40 | if (retval != 0) | ||
41 | throw new ZLibException(retval, "Could not initialize inflater"); | ||
42 | |||
43 | resetOutput(); | ||
44 | } | ||
45 | |||
46 | |||
47 | /// <summary> | ||
48 | /// Adds more data to the codec to be processed. | ||
49 | /// </summary> | ||
50 | /// <param name="data">Byte array containing the data to be added to the codec</param> | ||
51 | /// <param name="offset">The index of the first byte to add from <c>data</c></param> | ||
52 | /// <param name="count">The number of bytes to add</param> | ||
53 | /// <remarks>Adding data may, or may not, raise the <c>DataAvailable</c> event</remarks> | ||
54 | public override void Add(byte[] data, int offset, int count) | ||
55 | { | ||
56 | if (data == null) throw new ArgumentNullException(); | ||
57 | if (offset < 0 || count < 0) throw new ArgumentOutOfRangeException(); | ||
58 | if ((offset+count) > data.Length) throw new ArgumentException(); | ||
59 | |||
60 | int total = count; | ||
61 | int inputIndex = offset; | ||
62 | int err = 0; | ||
63 | |||
64 | while (err >= 0 && inputIndex < total) | ||
65 | { | ||
66 | copyInput(data, inputIndex, Math.Min(total - inputIndex, kBufferSize)); | ||
67 | err = inflate(ref _ztream, (int)FlushTypes.None); | ||
68 | if (err == 0) | ||
69 | while (_ztream.avail_out == 0) | ||
70 | { | ||
71 | OnDataAvailable(); | ||
72 | err = inflate(ref _ztream, (int)FlushTypes.None); | ||
73 | } | ||
74 | |||
75 | inputIndex += (int)_ztream.total_in; | ||
76 | } | ||
77 | setChecksum( _ztream.adler ); | ||
78 | } | ||
79 | |||
80 | |||
81 | /// <summary> | ||
82 | /// Finishes up any pending data that needs to be processed and handled. | ||
83 | /// </summary> | ||
84 | public override void Finish() | ||
85 | { | ||
86 | int err; | ||
87 | do | ||
88 | { | ||
89 | err = inflate(ref _ztream, (int)FlushTypes.Finish); | ||
90 | OnDataAvailable(); | ||
91 | } | ||
92 | while (err == 0); | ||
93 | setChecksum( _ztream.adler ); | ||
94 | inflateReset(ref _ztream); | ||
95 | resetOutput(); | ||
96 | } | ||
97 | |||
98 | /// <summary> | ||
99 | /// Closes the internal zlib inflate stream | ||
100 | /// </summary> | ||
101 | protected override void CleanUp() { inflateEnd(ref _ztream); } | ||
102 | |||
103 | |||
104 | } | ||
105 | } | ||
diff --git a/contrib/dotzlib/DotZLib/UnitTests.cs b/contrib/dotzlib/DotZLib/UnitTests.cs new file mode 100644 index 0000000..2f374b6 --- /dev/null +++ b/contrib/dotzlib/DotZLib/UnitTests.cs | |||
@@ -0,0 +1,274 @@ | |||
1 | // | ||
2 | // © Copyright Henrik Ravn 2004 | ||
3 | // | ||
4 | // Use, modification and distribution are subject to the Boost Software License, Version 1.0. | ||
5 | // (See accompanying file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) | ||
6 | // | ||
7 | |||
8 | using System; | ||
9 | using System.Collections; | ||
10 | using System.IO; | ||
11 | |||
12 | // uncomment the define below to include unit tests | ||
13 | //#define nunit | ||
14 | #if nunit | ||
15 | using NUnit.Framework; | ||
16 | |||
17 | // Unit tests for the DotZLib class library | ||
18 | // ---------------------------------------- | ||
19 | // | ||
20 | // Use this with NUnit 2 from http://www.nunit.org | ||
21 | // | ||
22 | |||
23 | namespace DotZLibTests | ||
24 | { | ||
25 | using DotZLib; | ||
26 | |||
27 | // helper methods | ||
28 | internal class Utils | ||
29 | { | ||
30 | public static bool byteArrEqual( byte[] lhs, byte[] rhs ) | ||
31 | { | ||
32 | if (lhs.Length != rhs.Length) | ||
33 | return false; | ||
34 | for (int i = lhs.Length-1; i >= 0; --i) | ||
35 | if (lhs[i] != rhs[i]) | ||
36 | return false; | ||
37 | return true; | ||
38 | } | ||
39 | |||
40 | } | ||
41 | |||
42 | |||
43 | [TestFixture] | ||
44 | public class CircBufferTests | ||
45 | { | ||
46 | #region Circular buffer tests | ||
47 | [Test] | ||
48 | public void SinglePutGet() | ||
49 | { | ||
50 | CircularBuffer buf = new CircularBuffer(10); | ||
51 | Assert.AreEqual( 0, buf.Size ); | ||
52 | Assert.AreEqual( -1, buf.Get() ); | ||
53 | |||
54 | Assert.IsTrue(buf.Put( 1 )); | ||
55 | Assert.AreEqual( 1, buf.Size ); | ||
56 | Assert.AreEqual( 1, buf.Get() ); | ||
57 | Assert.AreEqual( 0, buf.Size ); | ||
58 | Assert.AreEqual( -1, buf.Get() ); | ||
59 | } | ||
60 | |||
61 | [Test] | ||
62 | public void BlockPutGet() | ||
63 | { | ||
64 | CircularBuffer buf = new CircularBuffer(10); | ||
65 | byte[] arr = {1,2,3,4,5,6,7,8,9,10}; | ||
66 | Assert.AreEqual( 10, buf.Put(arr,0,10) ); | ||
67 | Assert.AreEqual( 10, buf.Size ); | ||
68 | Assert.IsFalse( buf.Put(11) ); | ||
69 | Assert.AreEqual( 1, buf.Get() ); | ||
70 | Assert.IsTrue( buf.Put(11) ); | ||
71 | |||
72 | byte[] arr2 = (byte[])arr.Clone(); | ||
73 | Assert.AreEqual( 9, buf.Get(arr2,1,9) ); | ||
74 | Assert.IsTrue( Utils.byteArrEqual(arr,arr2) ); | ||
75 | } | ||
76 | |||
77 | #endregion | ||
78 | } | ||
79 | |||
80 | [TestFixture] | ||
81 | public class ChecksumTests | ||
82 | { | ||
83 | #region CRC32 Tests | ||
84 | [Test] | ||
85 | public void CRC32_Null() | ||
86 | { | ||
87 | CRC32Checksum crc32 = new CRC32Checksum(); | ||
88 | Assert.AreEqual( 0, crc32.Value ); | ||
89 | |||
90 | crc32 = new CRC32Checksum(1); | ||
91 | Assert.AreEqual( 1, crc32.Value ); | ||
92 | |||
93 | crc32 = new CRC32Checksum(556); | ||
94 | Assert.AreEqual( 556, crc32.Value ); | ||
95 | } | ||
96 | |||
97 | [Test] | ||
98 | public void CRC32_Data() | ||
99 | { | ||
100 | CRC32Checksum crc32 = new CRC32Checksum(); | ||
101 | byte[] data = { 1,2,3,4,5,6,7 }; | ||
102 | crc32.Update(data); | ||
103 | Assert.AreEqual( 0x70e46888, crc32.Value ); | ||
104 | |||
105 | crc32 = new CRC32Checksum(); | ||
106 | crc32.Update("penguin"); | ||
107 | Assert.AreEqual( 0x0e5c1a120, crc32.Value ); | ||
108 | |||
109 | crc32 = new CRC32Checksum(1); | ||
110 | crc32.Update("penguin"); | ||
111 | Assert.AreEqual(0x43b6aa94, crc32.Value); | ||
112 | |||
113 | } | ||
114 | #endregion | ||
115 | |||
116 | #region Adler tests | ||
117 | |||
118 | [Test] | ||
119 | public void Adler_Null() | ||
120 | { | ||
121 | AdlerChecksum adler = new AdlerChecksum(); | ||
122 | Assert.AreEqual(0, adler.Value); | ||
123 | |||
124 | adler = new AdlerChecksum(1); | ||
125 | Assert.AreEqual( 1, adler.Value ); | ||
126 | |||
127 | adler = new AdlerChecksum(556); | ||
128 | Assert.AreEqual( 556, adler.Value ); | ||
129 | } | ||
130 | |||
131 | [Test] | ||
132 | public void Adler_Data() | ||
133 | { | ||
134 | AdlerChecksum adler = new AdlerChecksum(1); | ||
135 | byte[] data = { 1,2,3,4,5,6,7 }; | ||
136 | adler.Update(data); | ||
137 | Assert.AreEqual( 0x5b001d, adler.Value ); | ||
138 | |||
139 | adler = new AdlerChecksum(); | ||
140 | adler.Update("penguin"); | ||
141 | Assert.AreEqual(0x0bcf02f6, adler.Value ); | ||
142 | |||
143 | adler = new AdlerChecksum(1); | ||
144 | adler.Update("penguin"); | ||
145 | Assert.AreEqual(0x0bd602f7, adler.Value); | ||
146 | |||
147 | } | ||
148 | #endregion | ||
149 | } | ||
150 | |||
151 | [TestFixture] | ||
152 | public class InfoTests | ||
153 | { | ||
154 | #region Info tests | ||
155 | [Test] | ||
156 | public void Info_Version() | ||
157 | { | ||
158 | Info info = new Info(); | ||
159 | Assert.AreEqual("1.2.2", Info.Version); | ||
160 | Assert.AreEqual(32, info.SizeOfUInt); | ||
161 | Assert.AreEqual(32, info.SizeOfULong); | ||
162 | Assert.AreEqual(32, info.SizeOfPointer); | ||
163 | Assert.AreEqual(32, info.SizeOfOffset); | ||
164 | } | ||
165 | #endregion | ||
166 | } | ||
167 | |||
168 | [TestFixture] | ||
169 | public class DeflateInflateTests | ||
170 | { | ||
171 | #region Deflate tests | ||
172 | [Test] | ||
173 | public void Deflate_Init() | ||
174 | { | ||
175 | using (Deflater def = new Deflater(CompressLevel.Default)) | ||
176 | { | ||
177 | } | ||
178 | } | ||
179 | |||
180 | private ArrayList compressedData = new ArrayList(); | ||
181 | private uint adler1; | ||
182 | |||
183 | private ArrayList uncompressedData = new ArrayList(); | ||
184 | private uint adler2; | ||
185 | |||
186 | public void CDataAvail(byte[] data, int startIndex, int count) | ||
187 | { | ||
188 | for (int i = 0; i < count; ++i) | ||
189 | compressedData.Add(data[i+startIndex]); | ||
190 | } | ||
191 | |||
192 | [Test] | ||
193 | public void Deflate_Compress() | ||
194 | { | ||
195 | compressedData.Clear(); | ||
196 | |||
197 | byte[] testData = new byte[35000]; | ||
198 | for (int i = 0; i < testData.Length; ++i) | ||
199 | testData[i] = 5; | ||
200 | |||
201 | using (Deflater def = new Deflater((CompressLevel)5)) | ||
202 | { | ||
203 | def.DataAvailable += new DataAvailableHandler(CDataAvail); | ||
204 | def.Add(testData); | ||
205 | def.Finish(); | ||
206 | adler1 = def.Checksum; | ||
207 | } | ||
208 | } | ||
209 | #endregion | ||
210 | |||
211 | #region Inflate tests | ||
212 | [Test] | ||
213 | public void Inflate_Init() | ||
214 | { | ||
215 | using (Inflater inf = new Inflater()) | ||
216 | { | ||
217 | } | ||
218 | } | ||
219 | |||
220 | private void DDataAvail(byte[] data, int startIndex, int count) | ||
221 | { | ||
222 | for (int i = 0; i < count; ++i) | ||
223 | uncompressedData.Add(data[i+startIndex]); | ||
224 | } | ||
225 | |||
226 | [Test] | ||
227 | public void Inflate_Expand() | ||
228 | { | ||
229 | uncompressedData.Clear(); | ||
230 | |||
231 | using (Inflater inf = new Inflater()) | ||
232 | { | ||
233 | inf.DataAvailable += new DataAvailableHandler(DDataAvail); | ||
234 | inf.Add((byte[])compressedData.ToArray(typeof(byte))); | ||
235 | inf.Finish(); | ||
236 | adler2 = inf.Checksum; | ||
237 | } | ||
238 | Assert.AreEqual( adler1, adler2 ); | ||
239 | } | ||
240 | #endregion | ||
241 | } | ||
242 | |||
243 | [TestFixture] | ||
244 | public class GZipStreamTests | ||
245 | { | ||
246 | #region GZipStream test | ||
247 | [Test] | ||
248 | public void GZipStream_WriteRead() | ||
249 | { | ||
250 | using (GZipStream gzOut = new GZipStream("gzstream.gz", CompressLevel.Best)) | ||
251 | { | ||
252 | BinaryWriter writer = new BinaryWriter(gzOut); | ||
253 | writer.Write("hi there"); | ||
254 | writer.Write(Math.PI); | ||
255 | writer.Write(42); | ||
256 | } | ||
257 | |||
258 | using (GZipStream gzIn = new GZipStream("gzstream.gz")) | ||
259 | { | ||
260 | BinaryReader reader = new BinaryReader(gzIn); | ||
261 | string s = reader.ReadString(); | ||
262 | Assert.AreEqual("hi there",s); | ||
263 | double d = reader.ReadDouble(); | ||
264 | Assert.AreEqual(Math.PI, d); | ||
265 | int i = reader.ReadInt32(); | ||
266 | Assert.AreEqual(42,i); | ||
267 | } | ||
268 | |||
269 | } | ||
270 | #endregion | ||
271 | } | ||
272 | } | ||
273 | |||
274 | #endif \ No newline at end of file | ||