1 1.1 christos // 2 1.1 christos // Copyright Henrik Ravn 2004 3 1.1 christos // 4 1.1.1.2 christos // Use, modification and distribution are subject to the Boost Software License, Version 1.0. 5 1.1 christos // (See accompanying file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) 6 1.1 christos // 7 1.1 christos 8 1.1 christos using System; 9 1.1 christos using System.IO; 10 1.1 christos using System.Runtime.InteropServices; 11 1.1 christos using System.Text; 12 1.1 christos 13 1.1 christos 14 1.1 christos namespace DotZLib 15 1.1 christos { 16 1.1 christos 17 1.1 christos #region Internal types 18 1.1 christos 19 1.1 christos /// <summary> 20 1.1 christos /// Defines constants for the various flush types used with zlib 21 1.1 christos /// </summary> 22 1.1.1.2 christos internal enum FlushTypes 23 1.1 christos { 24 1.1 christos None, Partial, Sync, Full, Finish, Block 25 1.1 christos } 26 1.1 christos 27 1.1 christos #region ZStream structure 28 1.1 christos // internal mapping of the zlib zstream structure for marshalling 29 1.1 christos [StructLayoutAttribute(LayoutKind.Sequential, Pack=4, Size=0, CharSet=CharSet.Ansi)] 30 1.1 christos internal struct ZStream 31 1.1 christos { 32 1.1 christos public IntPtr next_in; 33 1.1 christos public uint avail_in; 34 1.1 christos public uint total_in; 35 1.1 christos 36 1.1 christos public IntPtr next_out; 37 1.1 christos public uint avail_out; 38 1.1 christos public uint total_out; 39 1.1 christos 40 1.1 christos [MarshalAs(UnmanagedType.LPStr)] 41 1.1.1.2 christos string msg; 42 1.1 christos uint state; 43 1.1 christos 44 1.1 christos uint zalloc; 45 1.1 christos uint zfree; 46 1.1 christos uint opaque; 47 1.1 christos 48 1.1 christos int data_type; 49 1.1 christos public uint adler; 50 1.1 christos uint reserved; 51 1.1 christos } 52 1.1 christos 53 1.1 christos #endregion 54 1.1.1.2 christos 55 1.1 christos #endregion 56 1.1 christos 57 1.1 christos #region Public enums 58 1.1 christos /// <summary> 59 1.1 christos /// Defines constants for the available compression levels in zlib 60 1.1 christos /// </summary> 61 1.1 christos public enum CompressLevel : int 62 1.1 christos { 63 1.1 christos /// <summary> 64 1.1 christos /// The default compression level with a reasonable compromise between compression and speed 65 1.1 christos /// </summary> 66 1.1.1.2 christos Default = -1, 67 1.1 christos /// <summary> 68 1.1 christos /// No compression at all. The data are passed straight through. 69 1.1 christos /// </summary> 70 1.1 christos None = 0, 71 1.1 christos /// <summary> 72 1.1 christos /// The maximum compression rate available. 73 1.1 christos /// </summary> 74 1.1.1.2 christos Best = 9, 75 1.1 christos /// <summary> 76 1.1 christos /// The fastest available compression level. 77 1.1 christos /// </summary> 78 1.1 christos Fastest = 1 79 1.1 christos } 80 1.1 christos #endregion 81 1.1 christos 82 1.1 christos #region Exception classes 83 1.1 christos /// <summary> 84 1.1 christos /// The exception that is thrown when an error occurs on the zlib dll 85 1.1 christos /// </summary> 86 1.1 christos public class ZLibException : ApplicationException 87 1.1 christos { 88 1.1 christos /// <summary> 89 1.1.1.2 christos /// Initializes a new instance of the <see cref="ZLibException"/> class with a specified 90 1.1 christos /// error message and error code 91 1.1 christos /// </summary> 92 1.1 christos /// <param name="errorCode">The zlib error code that caused the exception</param> 93 1.1 christos /// <param name="msg">A message that (hopefully) describes the error</param> 94 1.1 christos public ZLibException(int errorCode, string msg) : base(String.Format("ZLib error {0} {1}", errorCode, msg)) 95 1.1 christos { 96 1.1 christos } 97 1.1 christos 98 1.1 christos /// <summary> 99 1.1.1.2 christos /// Initializes a new instance of the <see cref="ZLibException"/> class with a specified 100 1.1 christos /// error code 101 1.1 christos /// </summary> 102 1.1 christos /// <param name="errorCode">The zlib error code that caused the exception</param> 103 1.1 christos public ZLibException(int errorCode) : base(String.Format("ZLib error {0}", errorCode)) 104 1.1 christos { 105 1.1 christos } 106 1.1 christos } 107 1.1 christos #endregion 108 1.1 christos 109 1.1 christos #region Interfaces 110 1.1 christos 111 1.1 christos /// <summary> 112 1.1.1.2 christos /// Declares methods and properties that enables a running checksum to be calculated 113 1.1 christos /// </summary> 114 1.1 christos public interface ChecksumGenerator 115 1.1 christos { 116 1.1 christos /// <summary> 117 1.1 christos /// Gets the current value of the checksum 118 1.1 christos /// </summary> 119 1.1 christos uint Value { get; } 120 1.1 christos 121 1.1 christos /// <summary> 122 1.1 christos /// Clears the current checksum to 0 123 1.1 christos /// </summary> 124 1.1 christos void Reset(); 125 1.1 christos 126 1.1 christos /// <summary> 127 1.1 christos /// Updates the current checksum with an array of bytes 128 1.1 christos /// </summary> 129 1.1 christos /// <param name="data">The data to update the checksum with</param> 130 1.1 christos void Update(byte[] data); 131 1.1 christos 132 1.1 christos /// <summary> 133 1.1 christos /// Updates the current checksum with part of an array of bytes 134 1.1 christos /// </summary> 135 1.1 christos /// <param name="data">The data to update the checksum with</param> 136 1.1 christos /// <param name="offset">Where in <c>data</c> to start updating</param> 137 1.1 christos /// <param name="count">The number of bytes from <c>data</c> to use</param> 138 1.1 christos /// <exception cref="ArgumentException">The sum of offset and count is larger than the length of <c>data</c></exception> 139 1.1 christos /// <exception cref="ArgumentNullException"><c>data</c> is a null reference</exception> 140 1.1 christos /// <exception cref="ArgumentOutOfRangeException">Offset or count is negative.</exception> 141 1.1 christos void Update(byte[] data, int offset, int count); 142 1.1 christos 143 1.1 christos /// <summary> 144 1.1 christos /// Updates the current checksum with the data from a string 145 1.1 christos /// </summary> 146 1.1 christos /// <param name="data">The string to update the checksum with</param> 147 1.1 christos /// <remarks>The characters in the string are converted by the UTF-8 encoding</remarks> 148 1.1 christos void Update(string data); 149 1.1 christos 150 1.1 christos /// <summary> 151 1.1 christos /// Updates the current checksum with the data from a string, using a specific encoding 152 1.1 christos /// </summary> 153 1.1 christos /// <param name="data">The string to update the checksum with</param> 154 1.1 christos /// <param name="encoding">The encoding to use</param> 155 1.1 christos void Update(string data, Encoding encoding); 156 1.1 christos } 157 1.1 christos 158 1.1 christos 159 1.1 christos /// <summary> 160 1.1 christos /// Represents the method that will be called from a codec when new data 161 1.1 christos /// are available. 162 1.1 christos /// </summary> 163 1.1 christos /// <paramref name="data">The byte array containing the processed data</paramref> 164 1.1 christos /// <paramref name="startIndex">The index of the first processed byte in <c>data</c></paramref> 165 1.1 christos /// <paramref name="count">The number of processed bytes available</paramref> 166 1.1.1.2 christos /// <remarks>On return from this method, the data may be overwritten, so grab it while you can. 167 1.1 christos /// You cannot assume that startIndex will be zero. 168 1.1 christos /// </remarks> 169 1.1 christos public delegate void DataAvailableHandler(byte[] data, int startIndex, int count); 170 1.1 christos 171 1.1 christos /// <summary> 172 1.1 christos /// Declares methods and events for implementing compressors/decompressors 173 1.1 christos /// </summary> 174 1.1 christos public interface Codec 175 1.1 christos { 176 1.1 christos /// <summary> 177 1.1 christos /// Occurs when more processed data are available. 178 1.1 christos /// </summary> 179 1.1 christos event DataAvailableHandler DataAvailable; 180 1.1 christos 181 1.1 christos /// <summary> 182 1.1 christos /// Adds more data to the codec to be processed. 183 1.1 christos /// </summary> 184 1.1 christos /// <param name="data">Byte array containing the data to be added to the codec</param> 185 1.1 christos /// <remarks>Adding data may, or may not, raise the <c>DataAvailable</c> event</remarks> 186 1.1 christos void Add(byte[] data); 187 1.1 christos 188 1.1 christos /// <summary> 189 1.1 christos /// Adds more data to the codec to be processed. 190 1.1 christos /// </summary> 191 1.1 christos /// <param name="data">Byte array containing the data to be added to the codec</param> 192 1.1 christos /// <param name="offset">The index of the first byte to add from <c>data</c></param> 193 1.1 christos /// <param name="count">The number of bytes to add</param> 194 1.1 christos /// <remarks>Adding data may, or may not, raise the <c>DataAvailable</c> event</remarks> 195 1.1 christos void Add(byte[] data, int offset, int count); 196 1.1 christos 197 1.1 christos /// <summary> 198 1.1 christos /// Finishes up any pending data that needs to be processed and handled. 199 1.1 christos /// </summary> 200 1.1 christos void Finish(); 201 1.1 christos 202 1.1 christos /// <summary> 203 1.1 christos /// Gets the checksum of the data that has been added so far 204 1.1 christos /// </summary> 205 1.1 christos uint Checksum { get; } 206 1.1 christos 207 1.1 christos 208 1.1 christos } 209 1.1 christos 210 1.1 christos #endregion 211 1.1 christos 212 1.1 christos #region Classes 213 1.1 christos /// <summary> 214 1.1 christos /// Encapsulates general information about the ZLib library 215 1.1 christos /// </summary> 216 1.1 christos public class Info 217 1.1 christos { 218 1.1 christos #region DLL imports 219 1.1 christos [DllImport("ZLIB1.dll", CallingConvention=CallingConvention.Cdecl)] 220 1.1 christos private static extern uint zlibCompileFlags(); 221 1.1 christos 222 1.1 christos [DllImport("ZLIB1.dll", CallingConvention=CallingConvention.Cdecl)] 223 1.1 christos private static extern string zlibVersion(); 224 1.1 christos #endregion 225 1.1 christos 226 1.1 christos #region Private stuff 227 1.1 christos private uint _flags; 228 1.1 christos 229 1.1 christos // helper function that unpacks a bitsize mask 230 1.1 christos private static int bitSize(uint bits) 231 1.1 christos { 232 1.1 christos switch (bits) 233 1.1 christos { 234 1.1 christos case 0: return 16; 235 1.1 christos case 1: return 32; 236 1.1 christos case 2: return 64; 237 1.1 christos } 238 1.1 christos return -1; 239 1.1 christos } 240 1.1 christos #endregion 241 1.1 christos 242 1.1 christos /// <summary> 243 1.1 christos /// Constructs an instance of the <c>Info</c> class. 244 1.1 christos /// </summary> 245 1.1 christos public Info() 246 1.1 christos { 247 1.1 christos _flags = zlibCompileFlags(); 248 1.1 christos } 249 1.1 christos 250 1.1 christos /// <summary> 251 1.1 christos /// True if the library is compiled with debug info 252 1.1 christos /// </summary> 253 1.1 christos public bool HasDebugInfo { get { return 0 != (_flags & 0x100); } } 254 1.1 christos 255 1.1 christos /// <summary> 256 1.1 christos /// True if the library is compiled with assembly optimizations 257 1.1 christos /// </summary> 258 1.1 christos public bool UsesAssemblyCode { get { return 0 != (_flags & 0x200); } } 259 1.1 christos 260 1.1 christos /// <summary> 261 1.1 christos /// Gets the size of the unsigned int that was compiled into Zlib 262 1.1 christos /// </summary> 263 1.1 christos public int SizeOfUInt { get { return bitSize(_flags & 3); } } 264 1.1 christos 265 1.1 christos /// <summary> 266 1.1 christos /// Gets the size of the unsigned long that was compiled into Zlib 267 1.1 christos /// </summary> 268 1.1 christos public int SizeOfULong { get { return bitSize((_flags >> 2) & 3); } } 269 1.1 christos 270 1.1 christos /// <summary> 271 1.1 christos /// Gets the size of the pointers that were compiled into Zlib 272 1.1 christos /// </summary> 273 1.1 christos public int SizeOfPointer { get { return bitSize((_flags >> 4) & 3); } } 274 1.1 christos 275 1.1 christos /// <summary> 276 1.1 christos /// Gets the size of the z_off_t type that was compiled into Zlib 277 1.1 christos /// </summary> 278 1.1 christos public int SizeOfOffset { get { return bitSize((_flags >> 6) & 3); } } 279 1.1 christos 280 1.1 christos /// <summary> 281 1.1 christos /// Gets the version of ZLib as a string, e.g. "1.2.1" 282 1.1 christos /// </summary> 283 1.1 christos public static string Version { get { return zlibVersion(); } } 284 1.1 christos } 285 1.1 christos 286 1.1 christos #endregion 287 1.1 christos 288 1.1 christos } 289