Commits

Jeff Hardy committed b00168f

Add IronPython zlib module based on zlib.net

Comments (0)

Files changed (21)

IronPython.Zlib/Compress.cs

+using System;
+using System.Collections.Generic;
+using System.Text;
+using IronPython.Runtime;
+using ComponentAce.Compression.Libs.zlib;
+
+namespace IronPython.Zlib
+{
+    [PythonType]
+    public class Compress
+    {
+        private const int Z_OK = ZlibModule.Z_OK;
+        private const int Z_BUF_ERROR = ZlibModule.Z_BUF_ERROR;
+        private const int Z_STREAM_END = ZlibModule.Z_STREAM_END;
+        
+        private const int Z_NO_FLUSH = ZlibModule.Z_NO_FLUSH;
+        private const int Z_FINISH = ZlibModule.Z_FINISH;
+
+        internal Compress(int level, int method, int wbits, int memlevel, int strategy)
+        {
+            zst = new ZStream();
+            int err = zst.deflateInit(level, wbits);
+
+            if(err != Z_OK)
+            {
+                throw new ZStreamException();
+            }
+        }
+
+        public string compress(string data)
+        {
+            byte[] input = ZlibModule.Latin1.GetBytes(data);
+            byte[] output = new byte[ZlibModule.DEFAULTALLOC];
+
+            long start_total_out = zst.total_out;
+            zst.next_in = input;
+            zst.next_in_index = 0;
+            zst.avail_in = input.Length;
+            zst.next_out = output;
+            zst.next_out_index = 0;
+            zst.avail_out = output.Length;
+
+            int err = zst.deflate(Z_NO_FLUSH);
+
+            while(err == Z_OK && zst.avail_out == 0)
+            {
+                int length = output.Length;
+                Array.Resize(ref output, output.Length * 2);
+
+                zst.next_out = output;
+                zst.avail_out = length;
+
+                err = zst.deflate(Z_NO_FLUSH);
+            }
+
+            if(err != Z_OK && err != Z_BUF_ERROR)
+            {
+                throw new ZStreamException();
+            }
+
+            return ZlibModule.Latin1.GetString(output, 0, (int)(zst.total_out - start_total_out));
+        }
+
+        public string flush()
+        {
+            return flush(Z_FINISH);
+        }
+
+        public string flush(int mode)
+        {
+            byte[] output = new byte[ZlibModule.DEFAULTALLOC];
+
+            if(mode == Z_NO_FLUSH)
+            {
+                return string.Empty;
+            }
+
+            long start_total_out = zst.total_out;
+            zst.avail_in = 0;
+            zst.next_out = output;
+            zst.next_out_index = 0;
+            zst.avail_out = output.Length;
+
+            int err = zst.deflate(mode);
+            while(err == Z_OK && zst.avail_out == 0)
+            {
+                int old_length = output.Length;
+                Array.Resize(ref output, output.Length * 2);
+
+                zst.next_out = output;
+                zst.avail_out = old_length;
+
+                err = zst.deflate(mode);
+            }
+
+            if(err == Z_STREAM_END && mode == Z_FINISH)
+            {
+                err = zst.deflateEnd();
+                if(err != Z_OK)
+                {
+                    throw new ZStreamException();
+                }
+            }
+            else if(err != Z_OK && err != Z_BUF_ERROR)
+            {
+                throw new ZStreamException();
+            }
+
+            return ZlibModule.Latin1.GetString(output, 0, (int)(zst.total_out - start_total_out));
+        }
+
+        //public Compress copy()
+        //{
+        //    throw new NotImplementedException();
+        //}
+
+        private ZStream zst;
+    }
+}

IronPython.Zlib/Crc32.cs

+using System;
+using System.Security.Cryptography;
+
+namespace IronPython.Zlib
+{
+    public class Crc32 : HashAlgorithm
+    {
+        public const UInt32 DefaultPolynomial = 0xedb88320;
+        public const UInt32 DefaultSeed = 0xffffffff;
+
+        private UInt32 hash;
+        private UInt32 seed;
+        private UInt32[] table;
+
+        public Crc32()
+        {
+            table = InitializeTable(DefaultPolynomial);
+            seed = DefaultSeed;
+            Initialize();
+        }
+
+        public Crc32(UInt32 polynomial, UInt32 seed)
+        {
+            table = InitializeTable(polynomial);
+            this.seed = seed;
+            Initialize();
+        }
+
+        public override void Initialize()
+        {
+            hash = seed;
+        }
+
+        protected override void HashCore(byte[] buffer, int start, int length)
+        {
+            hash = CalculateHash(table, hash, buffer, start, length);
+        }
+
+        protected override byte[] HashFinal()
+        {
+            byte[] hashBuffer = UInt32ToBigEndianBytes(hash);
+            this.HashValue = hashBuffer;
+            return hashBuffer;
+        }
+
+        public override int HashSize
+        {
+            get { return 32; }
+        }
+
+        public static UInt32 Compute(UInt32 polynomial, UInt32 seed, byte[] buffer)
+        {
+            return CalculateHash(InitializeTable(polynomial), ~seed, buffer, 0, buffer.Length);
+        }
+
+        private static UInt32[] InitializeTable(UInt32 polynomial)
+        {
+            UInt32[] createTable = new UInt32[256];
+            for(int i = 0; i < 256; i++)
+            {
+                UInt32 entry = (UInt32)i;
+                for(int j = 0; j < 8; j++)
+                    if((entry & 1) == 1)
+                        entry = (entry >> 1) ^ polynomial;
+                    else
+                        entry = entry >> 1;
+                createTable[i] = entry;
+            }
+            return createTable;
+        }
+
+        private static UInt32 CalculateHash(UInt32[] table, UInt32 seed, byte[] buffer, int start, int size)
+        {
+            UInt32 crc = seed;
+            for(int i = start; i < size; i++)
+                unchecked
+                {
+                    crc = (crc >> 8) ^ table[buffer[i] ^ crc & 0xff];
+                }
+            return ~crc;
+        }
+
+        private byte[] UInt32ToBigEndianBytes(UInt32 x)
+        {
+            return new byte[] {
+			(byte)((x >> 24) & 0xff),
+			(byte)((x >> 16) & 0xff),
+			(byte)((x >> 8) & 0xff),
+			(byte)(x & 0xff)
+		};
+        }
+    }
+}

IronPython.Zlib/Decompress.cs

+using System;
+using System.Collections.Generic;
+using System.Text;
+using IronPython.Runtime;
+using ComponentAce.Compression.Libs.zlib;
+
+namespace IronPython.Zlib
+{
+    [PythonType]
+    public class Decompress
+    {
+        private const int Z_OK = ZlibModule.Z_OK;
+        private const int Z_STREAM_END = ZlibModule.Z_STREAM_END;
+        private const int Z_BUF_ERROR = ZlibModule.Z_BUF_ERROR;
+
+        private const int Z_SYNC_FLUSH = ZlibModule.Z_SYNC_FLUSH;
+        private const int Z_FINISH = ZlibModule.Z_FINISH;
+
+        internal Decompress(int wbits)
+        {
+            zst = new ZStream();
+            int err = zst.inflateInit(wbits);
+
+            if(err != ZlibModule.Z_OK)
+            {
+                throw new ZStreamException();
+            }
+
+            _unused_data = string.Empty;
+            _unconsumed_tail = string.Empty;
+        }
+
+        private string _unused_data;
+        public string unused_data
+        {
+            get { return _unused_data; }
+        }
+
+        private string _unconsumed_tail;
+        public string unconsumed_tail
+        {
+            get { return _unconsumed_tail; }
+        }
+
+        public string decompress(string value)
+        {
+            return decompress(value, 0);
+        }
+
+        public string decompress(string value, int max_length)
+        {
+            if(max_length < 0) throw new ArgumentException("max_length must be greater than zero");
+
+            byte[] input = ZlibModule.Latin1.GetBytes(value);
+            byte[] output = new byte[max_length > 0 ? max_length : ZlibModule.DEFAULTALLOC];
+
+            long start_total_out = zst.total_out;
+            zst.next_in = input;
+            zst.next_in_index = 0;
+            zst.avail_in = input.Length;
+            zst.next_out = output;
+            zst.next_out_index = 0;
+            zst.avail_out = output.Length;
+
+            int err = zst.inflate(Z_SYNC_FLUSH);
+
+            while(err == Z_OK && zst.avail_out == 0)
+            {
+                if(max_length > 0 && output.Length >= max_length)
+                    break;
+
+                int old_length = output.Length;
+                Array.Resize(ref output, output.Length * 2);
+                zst.next_out = output;
+                zst.avail_out = old_length;
+
+                err = zst.inflate(Z_SYNC_FLUSH);
+            }
+
+            if(max_length > 0)
+            {
+                _unconsumed_tail = ZlibModule.Latin1.GetString(zst.next_in, 0, zst.avail_in);
+            }
+
+            if(err == Z_STREAM_END)
+            {
+                _unused_data += ZlibModule.Latin1.GetString(zst.next_in, 0, zst.avail_in);
+            }
+            else if(err != Z_OK && err != Z_BUF_ERROR)
+            {
+                throw new ZStreamException();
+            }
+
+            return ZlibModule.Latin1.GetString(output, 0, (int)(zst.total_out - start_total_out));
+        }
+
+        public string flush()
+        {
+            return flush(ZlibModule.DEFAULTALLOC);
+        }
+
+        public string flush(int length)
+        {
+            byte[] output = new byte[length];
+
+            long start_total_out = zst.total_out;
+            zst.next_out = output;
+            zst.next_out_index = 0;
+            zst.avail_out = output.Length;
+
+            int err = zst.inflate(Z_FINISH);
+
+            while((err == Z_OK || err == Z_BUF_ERROR) &&zst.avail_out == 0)
+            {
+                int old_length = output.Length;
+                Array.Resize(ref output, output.Length * 2);
+                zst.next_out = output;
+                zst.avail_out = old_length;
+
+                err = zst.inflate(Z_FINISH);
+            }
+
+            if(err == Z_STREAM_END)
+            {
+                err = zst.inflateEnd();
+                if(err != Z_OK)
+                {
+                    throw new ZStreamException();
+                }
+            }
+
+            return ZlibModule.Latin1.GetString(output, 0, (int)(zst.total_out - start_total_out));
+        }
+
+        //public Compress copy()
+        //{
+        //    throw new NotImplementedException();
+        //}
+
+        private ZStream zst;
+    }
+}

IronPython.Zlib/IronPython.Zlib.csproj

+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="3.5" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <PropertyGroup>
+    <Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
+    <Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
+    <ProductVersion>9.0.30729</ProductVersion>
+    <SchemaVersion>2.0</SchemaVersion>
+    <ProjectGuid>{BE07EA78-4A7F-41B7-AF4F-7C36CEC6FB50}</ProjectGuid>
+    <OutputType>Library</OutputType>
+    <AppDesignerFolder>Properties</AppDesignerFolder>
+    <RootNamespace>IronPython.Zlib</RootNamespace>
+    <AssemblyName>IronPython.Zlib</AssemblyName>
+    <TargetFrameworkVersion>v2.0</TargetFrameworkVersion>
+    <FileAlignment>512</FileAlignment>
+  </PropertyGroup>
+  <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
+    <DebugSymbols>true</DebugSymbols>
+    <DebugType>full</DebugType>
+    <Optimize>false</Optimize>
+    <OutputPath>bin\Debug\</OutputPath>
+    <DefineConstants>DEBUG;TRACE</DefineConstants>
+    <ErrorReport>prompt</ErrorReport>
+    <WarningLevel>4</WarningLevel>
+  </PropertyGroup>
+  <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
+    <DebugType>pdbonly</DebugType>
+    <Optimize>true</Optimize>
+    <OutputPath>bin\Release\</OutputPath>
+    <DefineConstants>TRACE</DefineConstants>
+    <ErrorReport>prompt</ErrorReport>
+    <WarningLevel>4</WarningLevel>
+  </PropertyGroup>
+  <ItemGroup>
+    <Reference Include="IronPython, Version=2.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35, processorArchitecture=MSIL">
+      <SpecificVersion>False</SpecificVersion>
+      <HintPath>..\..\..\..\Bin\IronPython-2.0\IronPython.dll</HintPath>
+    </Reference>
+    <Reference Include="Microsoft.Scripting, Version=0.9.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35, processorArchitecture=MSIL">
+      <SpecificVersion>False</SpecificVersion>
+      <HintPath>..\..\..\..\Bin\IronPython-2.0\Microsoft.Scripting.dll</HintPath>
+    </Reference>
+    <Reference Include="Microsoft.Scripting.Core, Version=0.9.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35, processorArchitecture=MSIL">
+      <SpecificVersion>False</SpecificVersion>
+      <HintPath>..\..\..\..\Bin\IronPython-2.0\Microsoft.Scripting.Core.dll</HintPath>
+    </Reference>
+    <Reference Include="System" />
+    <Reference Include="System.Data" />
+    <Reference Include="System.Xml" />
+  </ItemGroup>
+  <ItemGroup>
+    <Compile Include="Compress.cs" />
+    <Compile Include="Crc32.cs" />
+    <Compile Include="Decompress.cs" />
+    <Compile Include="zlib.net\Adler32.cs" />
+    <Compile Include="zlib.net\Deflate.cs" />
+    <Compile Include="zlib.net\InfBlocks.cs" />
+    <Compile Include="zlib.net\InfCodes.cs" />
+    <Compile Include="zlib.net\Inflate.cs" />
+    <Compile Include="zlib.net\InfTree.cs" />
+    <Compile Include="zlib.net\StaticTree.cs" />
+    <Compile Include="zlib.net\SupportClass.cs" />
+    <Compile Include="zlib.net\Tree.cs" />
+    <Compile Include="zlib.net\Zlib.cs" />
+    <Compile Include="zlib.net\ZStream.cs" />
+    <Compile Include="zlib.net\ZStreamException.cs" />
+    <Compile Include="ZlibModule.cs" />
+    <Compile Include="Properties\AssemblyInfo.cs" />
+  </ItemGroup>
+  <Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
+  <!-- To modify your build process, add your task inside one of the targets below and uncomment it. 
+       Other similar extension points exist, see Microsoft.Common.targets.
+  <Target Name="BeforeBuild">
+  </Target>
+  <Target Name="AfterBuild">
+  </Target>
+  -->
+</Project>

IronPython.Zlib/IronPython.Zlib.sln

+
+Microsoft Visual Studio Solution File, Format Version 10.00
+# Visual Studio 2008
+Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "IronPython.Zlib", "IronPython.Zlib.csproj", "{BE07EA78-4A7F-41B7-AF4F-7C36CEC6FB50}"
+EndProject
+Global
+	GlobalSection(SolutionConfigurationPlatforms) = preSolution
+		Debug|Any CPU = Debug|Any CPU
+		Release|Any CPU = Release|Any CPU
+	EndGlobalSection
+	GlobalSection(ProjectConfigurationPlatforms) = postSolution
+		{BE07EA78-4A7F-41B7-AF4F-7C36CEC6FB50}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+		{BE07EA78-4A7F-41B7-AF4F-7C36CEC6FB50}.Debug|Any CPU.Build.0 = Debug|Any CPU
+		{BE07EA78-4A7F-41B7-AF4F-7C36CEC6FB50}.Release|Any CPU.ActiveCfg = Release|Any CPU
+		{BE07EA78-4A7F-41B7-AF4F-7C36CEC6FB50}.Release|Any CPU.Build.0 = Release|Any CPU
+	EndGlobalSection
+	GlobalSection(SolutionProperties) = preSolution
+		HideSolutionNode = FALSE
+	EndGlobalSection
+EndGlobal
Add a comment to this file

IronPython.Zlib/IronPython.Zlib.suo

Binary file added.

IronPython.Zlib/Properties/AssemblyInfo.cs

+using System.Reflection;
+using System.Runtime.CompilerServices;
+using System.Runtime.InteropServices;
+
+// General Information about an assembly is controlled through the following 
+// set of attributes. Change these attribute values to modify the information
+// associated with an assembly.
+[assembly: AssemblyTitle("IronPython.Zlib")]
+[assembly: AssemblyDescription("")]
+[assembly: AssemblyConfiguration("")]
+[assembly: AssemblyCompany("Microsoft")]
+[assembly: AssemblyProduct("IronPython.Zlib")]
+[assembly: AssemblyCopyright("Copyright © Microsoft 2008")]
+[assembly: AssemblyTrademark("")]
+[assembly: AssemblyCulture("")]
+
+// Setting ComVisible to false makes the types in this assembly not visible 
+// to COM components.  If you need to access a type in this assembly from 
+// COM, set the ComVisible attribute to true on that type.
+[assembly: ComVisible(false)]
+
+// The following GUID is for the ID of the typelib if this project is exposed to COM
+[assembly: Guid("14ac6f33-7ab9-4468-abe7-5cd7addf9853")]
+
+// Version information for an assembly consists of the following four values:
+//
+//      Major Version
+//      Minor Version 
+//      Build Number
+//      Revision
+//
+// You can specify all the values or you can default the Build and Revision Numbers 
+// by using the '*' as shown below:
+// [assembly: AssemblyVersion("1.0.*")]
+[assembly: AssemblyVersion("1.0.0.0")]
+[assembly: AssemblyFileVersion("1.0.0.0")]

IronPython.Zlib/ZlibModule.cs

+using System;
+using System.Collections.Generic;
+using System.Text;
+using IronPython.Runtime;
+using IronPython.Runtime.Types;
+using ComponentAce.Compression.Libs.zlib;
+
+[assembly: PythonModule("zlib", typeof(IronPython.Zlib.ZlibModule))]
+
+namespace IronPython.Zlib
+{
+    public static class ZlibModule
+    {
+        public static string ZLIB_VERSION
+        {
+            get { return zlibConst.version(); }
+        }
+
+        internal const int Z_OK = zlibConst.Z_OK;
+        internal const int Z_STREAM_END = zlibConst.Z_STREAM_END;
+        internal const int Z_NEED_DICT = zlibConst.Z_NEED_DICT;
+        internal const int Z_ERRNO = zlibConst.Z_ERRNO;
+        internal const int Z_STREAM_ERROR = zlibConst.Z_STREAM_ERROR;
+        internal const int Z_DATA_ERROR = zlibConst.Z_DATA_ERROR;
+        internal const int Z_MEM_ERROR = zlibConst.Z_MEM_ERROR;
+        internal const int Z_BUF_ERROR = zlibConst.Z_BUF_ERROR;
+        internal const int Z_VERSION_ERROR = zlibConst.Z_VERSION_ERROR;
+
+        public const int Z_NO_FLUSH = zlibConst.Z_NO_FLUSH;
+        public const int Z_SYNC_FLUSH = zlibConst.Z_SYNC_FLUSH;
+        public const int Z_FULL_FLUSH = zlibConst.Z_FULL_FLUSH;
+        public const int Z_FINISH = zlibConst.Z_FINISH;
+
+        public const int Z_BEST_SPEED = zlibConst.Z_BEST_SPEED;
+        public const int Z_BEST_COMPRESSION = zlibConst.Z_BEST_COMPRESSION;
+        public const int Z_DEFAULT_COMPRESSION = zlibConst.Z_DEFAULT_COMPRESSION;
+
+        public const int Z_FILTERED = zlibConst.Z_FILTERED;
+        public const int Z_HUFFMAN_ONLY = zlibConst.Z_HUFFMAN_ONLY;
+        public const int Z_DEFAULT_STRATEGY = zlibConst.Z_DEFAULT_STRATEGY;
+
+        public const int DEFLATED = 8;
+        public const int DEF_MEM_LEVEL = 8;
+        public const int MAX_WBITS = 15;
+
+        internal const int DEFAULTALLOC = 16 * 1024;
+
+        #region adler32
+
+        public static long adler32(string data)
+        {
+            return adler32(data, 0);
+        }
+
+        public static long adler32(string data, uint value)
+        {
+            Adler32 a32 = new Adler32();
+            byte[] bytes = Latin1.GetBytes(data);
+            return a32.adler32(value, bytes, 0, bytes.Length);
+        }
+
+        #endregion
+
+        #region crc32
+
+        public static int crc32(string data)
+        {
+            return crc32(data, 0);
+        }
+
+        public static int crc32(string data, uint value)
+        {
+            return (int)Crc32.Compute(Crc32.DefaultPolynomial, value, Latin1.GetBytes(data));
+        }
+
+        #endregion
+
+        #region compress
+
+        public static string compress(string data)
+        {
+            return compress(data, Z_DEFAULT_COMPRESSION);
+        }
+
+        public static string compress(string data, int level)
+        {
+            byte[] input = Latin1.GetBytes(data);
+            byte[] output = new byte[input.Length + input.Length / 1000 + 12 + 1];
+
+            ZStream zst = new ZStream();
+            zst.next_in = input;
+            zst.avail_in = input.Length;
+            zst.next_out = output;
+            zst.avail_out = output.Length;
+
+            int err = zst.deflateInit(level);
+            if(err != Z_OK)
+            {
+                throw new ZStreamException();
+            }
+
+            err = zst.deflate(Z_FINISH);
+
+            if(err != Z_STREAM_END)
+            {
+                zst.deflateEnd();
+                throw new ZStreamException();
+            }
+
+            err = zst.deflateEnd();
+
+            if(err == Z_OK)
+                return Latin1.GetString(output, 0, (int)zst.total_out);
+            else
+                throw new ZStreamException();
+        }
+
+        #endregion
+
+        #region compressobj
+
+        public static Compress compressobj()
+        {
+            return compressobj(Z_DEFAULT_COMPRESSION, DEFLATED, MAX_WBITS, DEF_MEM_LEVEL, Z_DEFAULT_STRATEGY);
+        }
+
+        public static Compress compressobj(int level)
+        {
+            return new Compress(level, DEFLATED, MAX_WBITS, DEF_MEM_LEVEL, Z_DEFAULT_STRATEGY);
+        }
+
+        public static Compress compressobj(int level, int method)
+        {
+            return new Compress(level, method, MAX_WBITS, DEF_MEM_LEVEL, Z_DEFAULT_STRATEGY);
+        }
+
+        public static Compress compressobj(int level, int method, int wbits)
+        {
+            return new Compress(level, method, wbits, DEF_MEM_LEVEL, Z_DEFAULT_STRATEGY);
+        }
+
+        public static Compress compressobj(int level, int method, int wbits, int memlevel)
+        {
+            return new Compress(level, method, wbits, memlevel, Z_DEFAULT_STRATEGY);
+        }
+
+        public static Compress compressobj(int level, int method, int wbits, int memlevel, int strategy)
+        {
+            return new Compress(level, method, wbits, memlevel, strategy);
+        }
+
+        #endregion
+
+        #region decompress
+
+        public static string decompress(string data)
+        {
+            return decompress(data, MAX_WBITS, DEFAULTALLOC);
+        }
+
+        public static string decompress(string data, int wbits)
+        {
+            return decompress(data, wbits, DEFAULTALLOC);
+        }
+
+        public static string decompress(string data, int wbits, int bufsize)
+        {
+            byte[] input = Latin1.GetBytes(data);
+
+            byte[] outputBuffer = new byte[bufsize];
+            byte[] output = new byte[bufsize];
+            int outputOffset = 0;
+
+            ZStream zst = new ZStream();
+            zst.next_in = input;
+            zst.avail_in = input.Length;
+            zst.next_out = outputBuffer;
+            zst.avail_out = outputBuffer.Length;
+
+            int err = zst.inflateInit(wbits);
+            if(err != Z_OK)
+            {
+                throw new ZStreamException();
+            }
+
+            do
+            {
+                err = zst.inflate(Z_FINISH);
+
+                if(err != Z_STREAM_END)
+                {
+                    if(err == Z_BUF_ERROR && zst.avail_out > 0)
+                    {
+                        zst.inflateEnd();
+                        throw new ZStreamException();
+                    }
+                    else if(err == Z_OK || (err == Z_BUF_ERROR && zst.avail_out == 0))
+                    {
+                        // copy to the output and reset the buffer
+                        if(outputOffset + outputBuffer.Length > output.Length)
+                            Array.Resize(ref output, output.Length * 2);
+
+                        Array.Copy(outputBuffer, 0, output, outputOffset, outputBuffer.Length);
+                        outputOffset += outputBuffer.Length;
+
+                        zst.next_out = outputBuffer;
+                        zst.avail_out = outputBuffer.Length;
+                        zst.next_out_index = 0;
+                    }
+                    else
+                    {
+                        zst.inflateEnd();
+                        throw new ZStreamException();
+                    }
+                }
+
+            } while(err != Z_STREAM_END);
+
+            err = zst.inflateEnd();
+            if(err != Z_OK)
+            {
+                throw new ZStreamException();
+            }
+
+            if(outputOffset + outputBuffer.Length - zst.avail_out > output.Length)
+                Array.Resize(ref output, output.Length * 2);
+
+            Array.Copy(outputBuffer, 0, output, outputOffset, outputBuffer.Length - zst.avail_out);
+            outputOffset += outputBuffer.Length - zst.avail_out;
+
+            return Latin1.GetString(output, 0, outputOffset);
+        }
+
+        #endregion
+
+        #region decompressobj
+
+        public static Decompress decompressobj()
+        {
+            return decompressobj(MAX_WBITS);
+        }
+
+        public static Decompress decompressobj(int wbits)
+        {
+            return new Decompress(wbits);
+        }
+
+        #endregion
+
+        public static readonly PythonType/*!*/ ZlibErrorType = DynamicHelpers.GetPythonTypeFromType(typeof(ZStreamException));
+        public static readonly PythonType/*!*/ error = ZlibErrorType;
+
+        internal static System.Text.Encoding Latin1 = System.Text.Encoding.GetEncoding("iso-8859-1");
+    }
+}

IronPython.Zlib/run_tests.py

+import sys
+p = r'C:\Users\Jeff\Documents\Repositories\python\Lib'
+if p not in sys.path:
+    sys.path.append(p)
+
+import clr
+clr.AddReference('IronPython.Zlib')
+
+import zlib
+
+from test import test_zlib
+test_zlib.test_main()
+
+#~ lipsum = """
+#~ Lorem ipsum dolor sit amet, consectetur adipiscing elit. Ut vel nisl quis neque venenatis volutpat. Pellentesque viverra placerat lectus. Vestibulum eleifend purus eget diam. Etiam porta, nisi a commodo hendrerit, orci odio feugiat quam, posuere molestie felis velit ullamcorper sem. Aenean pretium posuere turpis. Donec dapibus arcu ut neque. Praesent pretium tempor nisi. Etiam dapibus, arcu eget semper tincidunt, diam mi suscipit felis, non congue orci neque blandit ligula. Suspendisse potenti. Quisque auctor ligula sit amet ipsum. Sed convallis arcu quis arcu. Cras bibendum ligula sit amet tellus. Curabitur et nulla vel libero tempus facilisis. Nullam gravida, ligula id venenatis ornare, justo lacus pretium diam, aliquet ullamcorper leo turpis id quam. Fusce quis magna. Donec facilisis velit ut risus. Mauris eros. Ut luctus turpis eget dolor dictum suscipit. 
+
+#~ Etiam diam. Duis semper lorem nec neque. Donec fermentum varius pede. Aliquam venenatis diam eu risus. Nunc cursus elit id urna. Donec tellus metus, interdum vitae, egestas nec, mattis et, elit. Suspendisse potenti. Donec dignissim, nunc sit amet volutpat volutpat, enim tellus bibendum neque, eget pharetra purus nulla vitae lorem. Phasellus quis ante sed enim dictum molestie. Vivamus accumsan nunc et enim. Quisque pulvinar dignissim quam. Pellentesque habitant morbi tristique senectus et netus et malesuada fames ac turpis egestas. Maecenas eu erat vel sapien sollicitudin rutrum. 
+
+#~ Nulla vel risus. Ut aliquam, massa ac scelerisque feugiat, justo nisl vulputate ante, ac tincidunt nibh dui vel dui. Fusce faucibus mauris. Donec porta. In hac habitasse platea dictumst. Donec pretium mauris quis arcu. Curabitur fermentum dapibus quam. Pellentesque habitant morbi tristique senectus et netus et malesuada fames ac turpis egestas. Cras eu turpis. Nunc quis ligula vel velit vestibulum auctor. Nunc leo eros, ornare id, fermentum id, auctor sed, dui. Morbi et sapien sit amet purus placerat tempor. 
+
+#~ Maecenas quis sapien. Duis imperdiet volutpat felis. In imperdiet, metus sed gravida venenatis, eros augue vehicula nunc, sed mattis nisi lacus in magna. Aenean molestie aliquet mi. Nunc at dolor et urna tincidunt congue. Cras odio metus, tristique eu, lobortis a, pretium elementum, dolor. Nam consectetur tortor. Vivamus sapien. Etiam blandit, diam ac blandit volutpat, erat enim pulvinar sapien, ut mattis enim nunc sit amet sapien. Sed feugiat nulla ut eros. Donec mi enim, molestie ac, interdum at, euismod et, felis. Mauris augue augue, accumsan a, consequat eleifend, iaculis quis, ligula. 
+
+#~ Proin nisl tellus, faucibus id, hendrerit id, ultricies tempus, nisl. Class aptent taciti sociosqu ad litora torquent per conubia nostra, per inceptos himenaeos. Etiam posuere nunc id ligula accumsan auctor. Sed cursus accumsan sapien. Quisque lacus. Praesent in mi id quam iaculis ultricies. Nunc posuere augue eget urna. Curabitur nunc. Nam libero purus, gravida in, molestie a, commodo in, pede. Integer vel dui. Nunc cursus imperdiet eros. Sed molestie volutpat dolor. Fusce neque metus, adipiscing non, fermentum et, porttitor bibendum, felis. Nam placerat ante id tellus. 
+
+#~ Duis vitae lorem vitae eros consectetur tristique. Sed interdum consectetur nisl. Curabitur metus dolor, tempor sit amet, sagittis id, scelerisque vitae, nisl. Nam sed sapien in dui consequat faucibus. Vivamus euismod, velit ut aliquam rutrum, nisl orci pharetra augue, ac ultrices nisi sapien sed ipsum. Vivamus ac turpis. Sed vulputate orci. Quisque varius neque ut nunc. Phasellus imperdiet tellus a lorem. Nulla nibh justo, commodo ac, elementum quis, imperdiet sed, orci. Maecenas non justo eget leo tempus tristique. Nam aliquam erat eget eros. Sed tellus ipsum, fringilla non, tristique ut, posuere id, libero. Suspendisse ultrices urna sit amet nisl. Donec ut arcu vel sem faucibus imperdiet. Quisque pharetra, dui a molestie placerat, mi nibh congue mi, eu lacinia risus velit nec quam. Donec vel turpis eget sem ultricies congue. Maecenas lectus. 
+
+#~ Etiam venenatis vehicula felis. Aliquam placerat. Donec posuere. Morbi aliquet metus ac nibh. Proin augue mi, dictum et, rhoncus sit amet, condimentum non, pede. Phasellus cursus, erat sollicitudin pulvinar consectetur, quam mi porttitor elit, non facilisis velit elit eget purus. Aliquam non est. Aliquam metus leo, pharetra ut, vehicula sit amet, porttitor vitae, massa. Sed eget purus at dolor pretium vulputate. Vivamus a eros vitae lorem consequat sollicitudin. Sed posuere, lectus eget feugiat vulputate, libero purus gravida lacus, ut ornare ligula turpis in lorem. Lorem ipsum dolor sit amet, consectetur adipiscing elit. Mauris consectetur. Phasellus odio augue, bibendum at, fringilla id, interdum sed, odio. Maecenas nibh nisi, lobortis non, convallis in, commodo ullamcorper, mi. Pellentesque tincidunt vulputate diam. Sed ultrices. Vivamus libero. Cras non purus. 
+
+#~ Fusce dolor. Curabitur ultrices pellentesque ante. Phasellus eleifend mi sit amet risus. Maecenas ornare, felis eget lobortis consequat, est lacus iaculis mauris, in venenatis ligula metus ac nulla. Nullam lobortis adipiscing elit. Curabitur suscipit. Proin quis dolor. Etiam porta dolor. Curabitur eget nisl in eros ultrices pellentesque. Aliquam purus ligula, dignissim id, egestas et, luctus at, dolor. Sed id velit. Aliquam erat volutpat. Ut dapibus vulputate libero. Etiam eget est. 
+
+#~ Nam ac nulla. Fusce augue leo, dictum sed, vestibulum eu, fringilla quis, risus. Nunc orci pede, lobortis eget, condimentum elementum, porttitor non, magna. Nam sollicitudin. Quisque quis velit eu quam sodales placerat. Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia Curae; Vestibulum et massa. Sed nisl. Suspendisse ac metus. Nulla rutrum felis vitae augue. Fusce fermentum velit a dolor. Vestibulum dignissim ante a sapien. Vivamus ut sapien in augue euismod scelerisque. Quisque purus. Phasellus lobortis volutpat ante. Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nam ultrices sodales quam. Morbi tincidunt vulputate nunc. 
+
+#~ Aliquam rutrum nibh et mi. Vestibulum non lectus vel magna feugiat fringilla. Mauris pretium. Quisque consequat libero accumsan purus. Proin vel urna a velit laoreet aliquet. Proin luctus magna id leo. Fusce vel nunc. Class aptent taciti sociosqu ad litora torquent per conubia nostra, per inceptos himenaeos. Donec gravida tortor non ipsum. Suspendisse euismod congue dolor. 
+
+#~ Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nullam diam nunc, sagittis vel, lacinia nec, suscipit id, ipsum. Nunc augue nisi, elementum vehicula, iaculis vitae, mattis dapibus, elit. Morbi suscipit, quam vel interdum sollicitudin, metus neque sollicitudin lectus, sit amet varius eros leo id tortor. Cum sociis natoque penatibus et magnis dis parturient montes, nascetur ridiculus mus. Mauris nulla dolor, commodo vel, varius aliquet, pellentesque eget, ligula. Maecenas id orci. Donec congue. Nam mollis massa id orci. Maecenas tristique lacinia magna. Mauris aliquet, tortor eget consequat luctus, metus elit accumsan est, nec iaculis leo nisl et leo. Nullam sed nulla. 
+
+#~ Proin at mi. Sed volutpat. Aenean mi. Nam ornare. Mauris volutpat diam non eros. Sed lectus massa, porta nec, congue quis, aliquam et, neque. Donec quis velit. Praesent tincidunt accumsan augue. In hac habitasse platea dictumst. Maecenas odio. Suspendisse neque. Curabitur quis diam eget metus eleifend pellentesque. Pellentesque vitae est in lorem aliquet pharetra. Vestibulum ac ante non ligula pulvinar accumsan. Curabitur est est, semper a, fringilla vel, facilisis ac, urna. Nulla arcu quam, fermentum quis, dictum a, euismod vitae, est. 
+
+#~ Nam lobortis enim quis justo convallis viverra. Vivamus tempor malesuada mi. Nullam ipsum. Nam dignissim, elit at dignissim elementum, orci nisi egestas massa, sit amet ullamcorper est nulla et dui. Praesent non ante aliquet libero pellentesque hendrerit. In congue purus vel dolor. Integer venenatis tortor ut mauris. In lacus libero, dignissim sit amet, fringilla a, dignissim nec, ligula. Cras dignissim lobortis nibh. Vestibulum sit amet tortor sit amet neque volutpat faucibus. Sed aliquam. Vestibulum fringilla orci ut leo. Vivamus id purus. Mauris ornare, erat malesuada imperdiet molestie, tellus lectus tempor ipsum, sit amet pharetra elit risus eleifend lacus. Fusce imperdiet turpis sit amet erat. 
+
+#~ Integer eu mauris. Phasellus purus nisi, suscipit quis, egestas eget, tincidunt non, dolor. Integer accumsan, pede et blandit tempus, nibh tellus ornare dolor, a imperdiet velit neque egestas nisi. Vestibulum lobortis, sapien sit amet malesuada imperdiet, dolor pede malesuada mi, in facilisis libero dolor id enim. Morbi eu diam vel justo dignissim imperdiet. Vivamus massa est, varius a, ultricies vitae, rhoncus quis, sem. Quisque nibh lorem, aliquam et, pharetra et, sodales ut, nisi. Pellentesque egestas magna. Etiam et tortor. Aliquam eget neque id odio semper vestibulum. Quisque suscipit pulvinar turpis. Suspendisse placerat faucibus magna. Mauris bibendum lorem sed odio. Quisque molestie. Donec nec eros mollis ipsum tempus auctor. 
+
+#~ Donec lacus. Pellentesque habitant morbi tristique senectus et netus et malesuada fames ac turpis egestas. Sed porta eleifend ipsum. Cras auctor. Nullam vel libero. Integer eget dolor ut diam malesuada gravida. Vivamus tortor turpis, commodo a, posuere at, ornare at, leo. Suspendisse potenti. Etiam volutpat, orci eu vehicula ultricies, lorem purus adipiscing ante, in feugiat massa sapien sit amet massa. Donec malesuada. Suspendisse eget quam eget lectus blandit blandit. Praesent sed justo at libero porttitor pulvinar. Suspendisse non quam. Ut enim arcu, congue ut, pretium vel, adipiscing ut, ante. Nam et magna. Cras vitae turpis. 
+
+#~ Vivamus congue nulla id quam. Vestibulum pulvinar consequat tortor. Nam varius sem et mi. Maecenas pede magna, dictum et, placerat nec, auctor id, libero. Vivamus lectus odio, blandit a, vehicula et, congue nec, est. Vestibulum mollis accumsan neque. Aliquam arcu ligula, convallis sed, convallis vel, viverra non, elit. Maecenas massa. Proin et pede vitae nisi consequat hendrerit. Cras ultricies blandit orci. Cum sociis natoque penatibus et magnis dis parturient montes, nascetur ridiculus mus. Aenean imperdiet pulvinar nibh. Nulla imperdiet ligula sit amet lectus. Vivamus commodo consequat sem. Vestibulum tristique orci sodales massa. Sed mi. 
+
+#~ Sed urna arcu, auctor eget, faucibus id, auctor ac, purus. Nunc sollicitudin enim non ipsum lacinia interdum. Quisque eu nulla ac sapien faucibus fringilla. Suspendisse ante. Aenean non sapien. Donec tincidunt lobortis libero. Sed sit amet tortor. Phasellus ac elit. Sed tempus, erat id facilisis elementum, nisl dui congue ipsum, vitae consectetur dui erat faucibus augue. Praesent ligula. Fusce tincidunt, sem eget convallis venenatis, ante magna consectetur dolor, et venenatis neque est nec odio. Sed ante massa, suscipit id, viverra eu, congue vitae, nisi. 
+
+#~ Nullam elit urna, accumsan at, dapibus non, facilisis sit amet, nisi. Vivamus lacus. Nunc vitae lacus non libero lobortis fringilla. Sed suscipit ipsum vitae eros. Ut a risus. Nulla tortor turpis, ultrices eget, fermentum porta, pharetra vel, ante. Nunc urna. Proin lacinia velit et mi. Maecenas semper, lacus et porta semper, libero justo iaculis orci, in convallis erat diam nec ipsum. Maecenas porttitor velit vel tellus. Praesent eu massa. Vestibulum ante nisi, dictum id, fermentum pharetra, porta vel, lectus. Donec est. 
+
+#~ Pellentesque habitant morbi tristique senectus et netus et malesuada fames ac turpis egestas. Cras non nisl eu ipsum dignissim adipiscing. Morbi quis ligula. Sed pharetra, enim nec interdum aliquam, mauris erat facilisis purus, at euismod ante libero in justo. Praesent sollicitudin mi a arcu. Sed bibendum risus vitae metus. Nunc nunc nunc, molestie sed, vulputate ac, molestie nec, pede. Vivamus congue elementum nisi. Phasellus suscipit fringilla elit. Ut tristique vehicula eros. Morbi placerat elementum nibh. 
+
+#~ Fusce porta lorem. Aliquam erat volutpat. Pellentesque habitant morbi tristique senectus et netus et malesuada fames ac turpis egestas. Maecenas faucibus pede vitae metus. Nunc luctus mi in magna. Duis blandit purus sit amet pede. In vel tortor. Sed arcu magna, placerat vitae, mattis sit amet, eleifend a, ante. Maecenas rutrum varius erat. Suspendisse blandit nunc in purus. Integer ullamcorper, eros sit amet volutpat viverra, massa risus laoreet odio, nec mattis dolor velit ac leo. 
+
+#~ Mauris id nisi sollicitudin nisi rutrum euismod. Quisque convallis, lacus ac ullamcorper porttitor, turpis risus luctus massa, non sollicitudin dui sapien eu elit. Donec id quam non mi ornare consequat. Vestibulum mi. Suspendisse elementum. In hac habitasse platea dictumst. Suspendisse nibh justo, dignissim et, lobortis vel, imperdiet a, augue. Pellentesque non odio ac ipsum porttitor egestas. Vestibulum eleifend dolor tempor purus. Quisque eget est. Sed lectus erat, ultricies nec, mattis vel, placerat ac, augue. Donec semper pellentesque nisi. Praesent congue arcu. Nulla euismod venenatis lacus. 
+
+#~ Fusce nec metus. Quisque pede dui, placerat ut, pellentesque eu, rhoncus ut, quam. Praesent facilisis, arcu sollicitudin pellentesque viverra, tortor augue adipiscing ligula, vel feugiat nibh lorem eget quam. Mauris sit amet dui ac turpis dapibus tempus. Cras vel arcu. Aenean tincidunt. Sed dignissim fermentum velit. Lorem ipsum dolor sit amet, consectetur adipiscing elit. Suspendisse ultrices odio id libero. Quisque accumsan, ante nec ullamcorper placerat, libero augue luctus augue, vel ultricies mi metus non ipsum. Sed porta metus nec turpis. Nunc euismod aliquam dui. Vivamus commodo eleifend elit. Duis mauris magna, pellentesque ut, accumsan vel, elementum at, libero. Sed enim odio, interdum ac, ultrices et, dapibus eu, ante. Aenean leo. Vivamus feugiat metus a neque. 
+
+#~ Sed dapibus rhoncus enim. Maecenas dapibus. Mauris placerat turpis at massa. Nulla pretium diam. Ut fermentum turpis eu magna convallis laoreet. Duis non tellus eget sem vulputate consequat. Proin eu tellus. Phasellus lobortis, massa ac sagittis mollis, risus sapien pulvinar erat, ac dictum est nisi sed justo. Integer dictum nibh vel pede. Aenean ut est. Nulla facilisi. Mauris convallis massa a eros. Mauris interdum, pede eleifend rhoncus semper, augue pede pharetra tortor, a venenatis nibh urna id eros. Quisque mattis. Sed dignissim mauris sit amet tellus. Donec et ipsum in ligula hendrerit laoreet. Suspendisse mollis lorem ut neque. 
+
+#~ Donec leo mi, aliquet vitae, placerat sit amet, posuere in, mi. Suspendisse id tortor. Pellentesque quis diam non massa vestibulum sollicitudin. Duis sit amet mauris a nulla tristique rutrum. Nam convallis, ipsum pretium vulputate porttitor, justo sem mattis diam, non tempor libero felis eget metus. Sed sit amet dui eu velit pharetra luctus. Nunc a nibh at mauris placerat imperdiet. Sed arcu metus, aliquet eget, facilisis vel, varius nec, quam. Vivamus vitae purus in tortor pharetra fermentum. Proin vestibulum. Aenean at nulla ut ligula ullamcorper interdum. Sed pulvinar. Donec quam massa, tempor eu, commodo bibendum, iaculis quis, risus. Integer posuere, nisl ac fermentum condimentum, dolor erat lacinia ipsum, tristique dignissim nulla dui consectetur sapien. Sed dictum, orci vel venenatis hendrerit, nulla est commodo ipsum, vitae tristique nisi justo vel pede. Maecenas vulputate adipiscing neque. Proin eu sem vitae dolor luctus lobortis. 
+
+#~ Maecenas eget eros sit amet velit vulputate suscipit. Sed vel augue sed nunc porttitor accumsan. Morbi erat turpis, rutrum non, feugiat euismod, fermentum eu, lacus. Class aptent taciti sociosqu ad litora torquent per conubia nostra, per inceptos himenaeos. Maecenas ante magna, porta et, placerat vitae, ornare sed, risus. Nullam arcu. Pellentesque erat pede, volutpat nec, consectetur ac, sagittis vel, dolor. Praesent tristique nunc sit amet nisl. Sed cursus lacinia quam. Morbi sapien. Vivamus accumsan, turpis et ultricies interdum, dui mauris bibendum mauris, in tempor eros turpis ut lectus. Cras adipiscing. Cras porttitor nibh vel pede. Curabitur ac metus non velit suscipit ullamcorper. Duis aliquam sem a nibh. Cras at neque. 
+
+#~ Vivamus eget odio. In sed felis. Nunc nec lacus in est tempor consequat. Donec lectus. Vivamus elit massa, porta at, ullamcorper vitae, semper a, dui. Nullam libero nibh, tempus eget, laoreet vel, vehicula quis, ipsum. Nunc lacus mauris, consequat ac, vulputate ac, bibendum et, eros. Vivamus eget metus nec lacus malesuada ullamcorper. Nullam felis. Phasellus vestibulum iaculis urna. In hac habitasse platea dictumst. 
+
+#~ Nam sit amet quam. In hac habitasse platea dictumst. Phasellus non erat. Vestibulum ut turpis vitae purus accumsan lacinia. Ut erat ante, aliquet sed, suscipit vel, facilisis at, orci. Mauris dapibus purus id purus varius ultricies. Suspendisse potenti. Suspendisse rutrum enim tincidunt tortor. Proin eros. Donec tincidunt ipsum sed urna. Sed eget tellus et enim pretium malesuada. 
+
+#~ Sed augue. Mauris eget massa a arcu convallis tincidunt. Cras vulputate, mi a tincidunt posuere, ipsum leo aliquet neque, venenatis consectetur diam arcu et arcu. Donec interdum consequat nibh. Nam semper, nulla et rutrum placerat, risus diam placerat ipsum, vel vehicula lectus orci mattis dolor. Etiam consectetur, enim sed fermentum venenatis, purus magna rutrum pede, non condimentum metus sem a felis. Integer lobortis mattis dolor. Donec adipiscing, elit quis dictum interdum, sapien nisl eleifend nulla, et cursus neque erat sed libero. Vestibulum ornare, dui ac vehicula vestibulum, tortor tellus hendrerit nibh, vestibulum rutrum diam nunc sit amet justo. Curabitur commodo, orci sit amet ultrices egestas, metus leo varius orci, sit amet eleifend elit risus quis ligula. Nam arcu est, semper non, molestie eget, mollis nec, ante. Nullam sed urna vel purus molestie mollis. 
+
+#~ Integer sem pede, posuere eu, pharetra vel, lacinia ut, ante. Fusce facilisis. Duis fringilla. Vestibulum luctus velit molestie tellus. Suspendisse tortor. Ut gravida felis eu dolor. Suspendisse potenti. Class aptent taciti sociosqu ad litora torquent per conubia nostra, per inceptos himenaeos. Praesent hendrerit mi ac odio ultricies venenatis. Duis ultrices pellentesque nisl. Fusce eu tellus sit amet lorem consequat lacinia. Curabitur vitae risus. Ut rutrum mollis eros. Mauris ut massa. Fusce dolor orci, dignissim ut, semper ac, tempor ut, ante. Nunc aliquam tempor ante. Integer vitae felis. Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia Curae; 
+
+#~ Sed pellentesque semper quam. Aliquam rutrum quam ac ante. Aliquam et magna id sem posuere bibendum. Integer aliquam sollicitudin nisl. Sed eget tellus at erat gravida ullamcorper. Curabitur mauris felis, cursus non, pellentesque tristique, adipiscing id, lorem. Duis eget urna. Ut eget quam. In porta tempus diam. Proin elementum tellus nec mauris. In ornare quam sit amet massa. Aliquam pulvinar eleifend diam. Nulla laoreet ipsum. Praesent vel arcu. Maecenas convallis volutpat leo. In dapibus neque. Nullam sollicitudin convallis turpis. Maecenas adipiscing. 
+
+#~ Pellentesque dolor. Maecenas lobortis, enim eu malesuada ornare, urna ante viverra eros, vel mattis sapien massa eget enim. Etiam posuere orci a mi. Nullam sit amet mauris eget velit ultricies commodo. Proin sed arcu. Vestibulum ante nibh, ultrices ut, lacinia dictum, vehicula sit amet, augue. Nam luctus imperdiet ipsum. Mauris laoreet pede et augue. Donec viverra augue quis mauris. Nullam tristique leo sit amet urna. Vestibulum in mauris. 
+
+#~ Mauris molestie suscipit ipsum. Curabitur ullamcorper sollicitudin ligula. Suspendisse tincidunt. Sed turpis lectus, commodo a, ornare viverra, varius vitae, diam. Praesent nibh magna, varius et, malesuada egestas, faucibus in, lorem. Praesent lacus nibh, pharetra in, congue id, tincidunt eu, diam. Quisque ligula massa, ullamcorper et, auctor eu, tempor vitae, urna. Nam vestibulum arcu et leo. Suspendisse luctus lorem nec nunc. Aliquam ultricies auctor mauris. Curabitur vehicula. Phasellus ac velit. Mauris eget nisi. Suspendisse neque. Phasellus lobortis, mi non dapibus fermentum, ante magna lobortis enim, eget elementum ante arcu vel lacus. Aliquam rhoncus, lorem id commodo porta, mi urna hendrerit pede, sit amet molestie libero elit id urna. Integer augue ipsum, ullamcorper vitae, posuere a, pulvinar sed, augue. 
+
+#~ Donec commodo ultricies ligula. Aliquam erat volutpat. Phasellus sagittis. Donec enim. Sed aliquam, mi quis vestibulum gravida, dolor sapien imperdiet enim, in ultricies mi ante nec lacus. Morbi elit. Quisque neque urna, adipiscing porttitor, bibendum ut, faucibus ut, nunc. Vestibulum iaculis aliquet purus. Nunc tincidunt tellus. Fusce erat justo, luctus sed, sollicitudin vel, viverra eu, ligula. Nullam sit amet ipsum id purus congue mattis. Sed non ligula. Mauris aliquet arcu quis purus. Donec luctus est vel odio. Ut felis. Sed sollicitudin diam ut mi. Morbi at sapien. Quisque sodales dui at elit. Morbi iaculis sodales massa. Nulla facilisi. 
+
+#~ Maecenas dictum erat non massa. Sed odio quam, lobortis in, sagittis vitae, dictum eu, orci. Sed velit felis, faucibus at, pretium sit amet, pellentesque quis, urna. Donec velit lectus, pulvinar sit amet, bibendum sit amet, tempor id, sapien. Morbi quis felis sed metus tincidunt facilisis. Suspendisse malesuada aliquet sem. Nam dapibus tortor eu sem. Fusce ultrices, tellus ac placerat varius, metus turpis dignissim massa, et gravida turpis velit fringilla nibh. Duis tristique dolor et erat. Aliquam erat volutpat. Nam ac arcu. Proin nisl. 
+
+#~ Lorem ipsum dolor sit amet, consectetur adipiscing elit. Ut commodo, diam vitae convallis pharetra, felis orci feugiat lectus, a luctus ligula ligula ac augue. Cras tincidunt convallis ligula. Integer dapibus tortor accumsan dui. Vestibulum accumsan sem at tortor. Phasellus aliquet sem iaculis augue hendrerit feugiat. Nam tincidunt. Nam magna mauris, accumsan quis, volutpat a, rutrum non, quam. Phasellus semper blandit ante. Vivamus pulvinar dictum felis. Vivamus dictum. Etiam ligula. Lorem ipsum dolor sit amet, consectetur adipiscing elit. Morbi vitae turpis. Ut tempus dolor vel ipsum. Ut ullamcorper nulla non dui. Morbi tortor metus, blandit eu, consequat sit amet, sagittis vel, lacus. Duis imperdiet nulla eu libero. Pellentesque semper euismod dolor. 
+
+#~ In fringilla semper lorem. Donec tempor tristique lectus. Duis ultricies lectus ut augue. Mauris eget nulla. Aliquam erat volutpat. Vivamus ac felis. Sed sollicitudin vulputate nibh. Nam nec magna. Vivamus tellus. Duis pellentesque enim at metus. Etiam eu nisi sit amet turpis imperdiet imperdiet. Cras placerat tortor et pede. Ut est erat, gravida sit amet, mollis et, elementum ac, odio. Fusce a eros. Donec sed ligula quis pede fermentum laoreet. Nullam porta urna et nulla. Aliquam lobortis adipiscing neque. Donec urna augue, condimentum non, pulvinar at, scelerisque vel, lorem. Vestibulum iaculis vulputate nisl. Etiam non arcu nec odio luctus sagittis. 
+
+#~ Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia Curae; Nulla imperdiet, odio in pharetra convallis, tellus lorem porta dui, ut scelerisque erat sapien quis tortor. Praesent in lacus. Integer eget felis ut dui lacinia volutpat. Mauris nibh libero, egestas vitae, tincidunt auctor, egestas non, nibh. Vestibulum sapien. Cras sollicitudin dignissim metus. Quisque at tortor in leo vestibulum condimentum. Sed eget sem. Quisque facilisis volutpat nibh. Donec quis nisi sit amet enim blandit pretium. Quisque quis velit. Maecenas et elit. Vivamus hendrerit, mi nec eleifend ultricies, urna mauris blandit nunc, sed molestie risus erat vitae risus. Proin rutrum lorem sed lorem. 
+
+#~ Morbi vel elit. Duis varius est. Nam aliquam blandit ante. Praesent sollicitudin, ligula pharetra rhoncus interdum, lorem mauris molestie massa, non ultrices nisi erat vitae mi. Praesent et lorem non est pellentesque euismod. Mauris nec justo. Maecenas aliquam nibh eu lacus. Nulla id felis in arcu hendrerit iaculis. Duis magna. Pellentesque vel risus nec tortor ultricies rhoncus. Suspendisse velit. Maecenas tellus tortor, auctor nec, luctus ac, faucibus non, nulla. 
+
+#~ Aenean congue imperdiet justo. Quisque hendrerit, leo eget tincidunt lacinia, tellus mi ullamcorper lectus, ut sagittis lectus ligula consequat est. Pellentesque faucibus hendrerit dui. Pellentesque eu pede. Etiam metus nibh, laoreet at, cursus id, aliquet ac, libero. Morbi at dolor. Duis fermentum. Nullam rhoncus ipsum vel arcu. Aliquam erat volutpat. Etiam mollis malesuada orci. Nulla in tellus tempor nulla suscipit fermentum. 
+
+#~ Praesent non nibh et tortor dapibus molestie. Praesent feugiat sapien nec lacus tempor mattis. Aliquam ut sem. Aenean accumsan. Pellentesque interdum. Donec vitae magna nec turpis malesuada feugiat. Nullam neque. In hac habitasse platea dictumst. In sollicitudin ornare nibh. Donec pretium ornare mi. Nullam placerat pede quis sem. Suspendisse nisl. Pellentesque habitant morbi tristique senectus et netus et malesuada fames ac turpis egestas. Mauris faucibus nisi et quam. 
+
+#~ Etiam nisi nisi, mollis eget, rutrum eget, cursus at, urna. Duis imperdiet odio nec diam. Nulla facilisi. Nunc suscipit est vitae orci. Ut orci felis, sagittis vel, lobortis eu, elementum ac, ante. Donec porttitor vulputate est. Nulla vitae sem. Aliquam egestas vulputate metus. Vivamus nec massa quis lacus porttitor fringilla. Donec in sapien. Suspendisse quam. 
+
+#~ Cras libero ipsum, luctus eget, tincidunt imperdiet, iaculis sit amet, arcu. Aliquam erat volutpat. Mauris eu risus in enim tincidunt commodo. Praesent eget metus volutpat lorem consequat commodo. In sodales sem nec libero fermentum porttitor. Donec sodales tincidunt ante. In egestas rhoncus dolor. Ut pulvinar consequat libero. Praesent ligula lacus, tempor placerat, congue non, rutrum quis, augue. Fusce dapibus arcu. Pellentesque neque. Aenean sem enim, vehicula eu, lobortis sit amet, dictum ut, mauris. Pellentesque nibh ipsum, euismod sit amet, aliquam a, dictum sed, mauris. Maecenas nibh. Integer rhoncus enim eu leo. In laoreet. 
+
+#~ Nulla facilisi. Mauris pretium auctor enim. Nullam gravida metus ac nulla. Nam urna. Morbi mattis convallis enim. Nunc rhoncus ornare odio. Vivamus luctus faucibus metus. Maecenas varius elit at lacus. Vivamus eu urna. Integer vel lectus. Phasellus scelerisque. Vestibulum vehicula nibh vitae erat. Lorem ipsum dolor sit amet, consectetur adipiscing elit. Suspendisse et ipsum non velit ultrices varius. Lorem ipsum dolor sit amet, consectetur adipiscing elit. 
+
+#~ In hac habitasse platea dictumst. Ut dictum metus nec neque. Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nullam tristique mattis erat. Ut vitae lacus sed orci pulvinar fringilla. Nulla luctus semper diam. Proin felis nisi, ullamcorper in, sagittis vitae, scelerisque sed, libero. Nunc nulla. Mauris adipiscing, sapien vitae lacinia bibendum, nulla mauris ullamcorper nunc, at suscipit arcu nisi elementum tellus. Aenean porttitor. Aenean eget eros. Curabitur nibh est, tincidunt id, pellentesque sed, commodo sit amet, neque. Vestibulum dictum vulputate leo. Quisque euismod tempus enim. 
+
+#~ Aliquam vitae mi eget erat elementum tempus. Quisque pretium elit. Class aptent taciti sociosqu ad litora torquent per conubia nostra, per inceptos himenaeos. Donec ut elit pretium justo ultrices iaculis. Praesent sagittis enim id magna. Duis lorem tortor, rutrum nec, consequat in, bibendum sed, leo. Vestibulum elit. Suspendisse potenti. Curabitur tempor malesuada erat. Vivamus quis est vitae enim fermentum mollis. Pellentesque orci lectus, pellentesque vel, iaculis quis, sollicitudin tincidunt, diam. Integer elit justo, placerat sed, suscipit nec, faucibus ac, est. Integer pulvinar ornare mauris. Nullam magna erat, tincidunt sit amet, interdum a, aliquam a, nisi. Integer aliquam. Ut vulputate augue ut massa. Class aptent taciti sociosqu ad litora torquent per conubia nostra, per inceptos himenaeos. Mauris feugiat. 
+
+#~ Vivamus quis metus. Cras pharetra lectus adipiscing libero. Aenean ipsum mi, dictum a, vulputate ut, pretium eget, sapien. In lacus ipsum, vestibulum vel, dapibus id, bibendum a, nisl. Ut commodo tellus at purus. Suspendisse potenti. Donec vitae pede vel urna cursus dictum. Donec sed lorem. Suspendisse rutrum dolor. Nam odio dolor, tempor vel, varius ac, malesuada in, pede. Morbi pulvinar mauris vel nunc. Praesent posuere, purus non sodales viverra, justo dui malesuada ligula, quis interdum tellus nunc id ligula. Nam sapien nisl, scelerisque ut, pretium ac, bibendum nec, turpis. Pellentesque venenatis diam quis metus. Nulla non metus eu orci pulvinar condimentum. Nam nec nulla. Fusce porttitor sagittis nulla. Donec dignissim, libero id vulputate dignissim, mi ligula egestas diam, id pharetra erat pede non magna. Aliquam erat volutpat. 
+
+#~ Maecenas auctor lacus. Aenean porttitor laoreet erat. Pellentesque mattis ante eget justo. Duis gravida sodales elit. Fusce sit amet velit. Mauris eu nulla sit amet dolor tincidunt semper. Nunc neque enim, congue quis, pharetra ac, condimentum a, ante. Fusce ut elit. Fusce imperdiet erat vitae ligula. Sed dictum. Proin ac diam tempor mi commodo blandit. Etiam vel lorem. Integer ut neque. Curabitur aliquam fermentum nulla. Duis accumsan convallis purus. Sed lobortis, ligula vitae laoreet convallis, mi mi vestibulum velit, quis euismod nulla ligula et urna. Vivamus diam nulla, feugiat et, ornare sit amet, lobortis ac, orci. Mauris non nibh. Cras urna nisl, suscipit id, dapibus at, tempus faucibus, purus. 
+
+#~ Morbi et nunc quis felis iaculis feugiat. Donec laoreet mi nec velit. Nulla nisl. Praesent odio ante, egestas scelerisque, euismod a, posuere eu, massa. In hac habitasse platea dictumst. In hac habitasse platea dictumst. Aliquam iaculis mauris vitae ante. Lorem ipsum dolor sit amet, consectetur adipiscing elit. Vivamus tincidunt auctor augue. Praesent elit lectus, varius et, ullamcorper quis, ullamcorper vel, ante. Nullam dapibus. Praesent sem nunc, condimentum a, pharetra vel, ultrices vitae, tortor. Vivamus diam dolor, congue ac, tempus vitae, lobortis sed, nulla. Pellentesque tincidunt sagittis sem. Suspendisse sollicitudin, dui quis pellentesque aliquet, est urna rutrum enim, vel cursus mi tortor nec neque. Nulla eu nunc non odio pulvinar aliquam. Suspendisse pharetra, dui vel ullamcorper feugiat, arcu enim porta augue, eget facilisis sem mauris in sem. Morbi ullamcorper. 
+
+#~ Nullam libero massa, gravida eu, ultricies vitae, ornare vitae, nisi. Ut purus libero, sagittis vel, fringilla vel, lacinia quis, elit. Integer a pede sit amet enim rhoncus imperdiet. Lorem ipsum dolor sit amet, consectetur adipiscing elit. Ut facilisis vulputate mauris. Nam eleifend placerat sapien. Donec metus lorem, mollis sit amet, tempus at, imperdiet nec, neque. Maecenas ac ipsum non ligula pellentesque aliquam. Cras a velit. Integer purus. Mauris rhoncus, nibh eu elementum tincidunt, nunc sem auctor sem, ut facilisis tortor nisi sit amet massa. Suspendisse non elit id urna dapibus tincidunt. Phasellus lectus quam, malesuada eu, aliquam id, semper in, lectus. Pellentesque varius ligula vitae arcu. Curabitur vel sem. Maecenas dictum, nibh sed tincidunt fringilla, sem justo molestie libero, eget aliquet dui sem et nulla. 
+
+#~ Nulla sed erat. Proin ut ipsum. Duis ut lectus eget ipsum rhoncus imperdiet. Fusce posuere nisi ac lorem. Mauris semper. Duis iaculis, turpis et viverra suscipit, purus diam blandit diam, id ultricies massa enim non metus. Suspendisse eleifend ligula ac velit. Vestibulum iaculis. Praesent sed tortor vehicula neque aliquet ultricies. Donec molestie placerat ipsum. Vestibulum ligula. Fusce bibendum congue neque. Donec gravida mollis ipsum. In imperdiet ullamcorper sem. Proin dignissim luctus tellus. Vivamus consequat. Morbi sed quam. Mauris neque neque, iaculis eget, cursus ac, tincidunt at, sapien. Duis ac nibh. Nulla accumsan diam vel risus. 
+
+#~ Nullam ac nibh. Mauris lacinia enim non nulla. Sed mollis lacus id odio. Praesent condimentum. In justo eros, vehicula eu, eleifend vestibulum, dapibus a, dui. Curabitur luctus velit eu massa. Mauris bibendum. Cras lacus velit, pharetra a, vulputate nec, eleifend et, dolor. Proin a sem. Aliquam eleifend purus venenatis felis. Sed fringilla bibendum lectus. Morbi pellentesque sollicitudin lorem. Sed pulvinar dui vel dolor. Integer malesuada elementum leo. Aenean pretium tincidunt magna. Curabitur dui. Aenean justo risus, ultrices quis, dignissim sed, feugiat ut, velit. Cras gravida. Nunc eu felis. 
+
+#~ Pellentesque consequat lacus sit amet augue. Vivamus vel lectus. In blandit aliquam lectus. Phasellus vel felis. Fusce ac massa. Morbi nisi elit, gravida vitae, aliquam non, molestie non, quam. Nam eu risus. Maecenas pretium. Suspendisse quam. Donec ut lacus et mi fringilla commodo. Mauris blandit. Fusce tortor eros, fringilla laoreet, ultrices sit amet, cursus ut, odio. 
+
+#~ Cras semper mi a dui. Fusce vitae ante ac augue consectetur placerat. Cras placerat ornare ligula. Nulla tempor tincidunt arcu. Aliquam erat volutpat. Cras id felis. In hac habitasse platea dictumst. Morbi ac erat. Suspendisse dapibus leo ut pede. Integer enim nisi, adipiscing quis, egestas sit amet, hendrerit in, velit. Donec libero. In hac habitasse platea dictumst. Donec imperdiet massa. Cras varius magna. Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia Curae; Pellentesque habitant morbi tristique senectus et netus et malesuada fames ac turpis egestas. Nunc luctus. Proin vehicula, mauris non tincidunt imperdiet, mauris eros imperdiet mauris, in volutpat tortor metus quis arcu. Donec sit amet diam. 
+
+#~ Morbi gravida, purus quis semper posuere, erat dolor egestas risus, vitae ullamcorper enim erat et tellus. Integer lacinia, est ac accumsan adipiscing, elit augue placerat libero, nec tempus nisl leo nec augue. Cras rhoncus elementum mi. Aenean nec ante id lacus aliquet varius. Nulla orci dui, aliquet quis, fermentum sed, commodo quis, lectus. Class aptent taciti sociosqu ad litora torquent per conubia nostra, per inceptos himenaeos. Aliquam ut pede id quam pharetra porta. Nunc sit amet turpis. Morbi elementum augue. Aliquam gravida urna eget tortor. Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia Curae; Cras ut lorem a odio suscipit tempus. Integer iaculis, magna sit amet bibendum tempus, sapien metus pellentesque arcu, congue euismod neque neque sed massa. Etiam enim urna, varius eget, feugiat vitae, blandit eget, est. Etiam accumsan placerat elit. Quisque sed tellus non dui condimentum posuere. Suspendisse potenti. Nulla lacus. 
+
+#~ Quisque cursus consequat felis. Maecenas condimentum, enim nec elementum condimentum, dolor urna tincidunt nulla, quis suscipit diam nisi varius elit. Maecenas ligula. Nulla vestibulum semper quam. Nunc mattis dapibus nunc. Praesent tempor iaculis sem. Donec turpis. Ut pulvinar libero id nulla. Ut ut velit. Nulla turpis. 
+
+#~ In hac habitasse platea dictumst. Maecenas quis metus. In pharetra varius metus. Cras congue sapien sit amet metus. Cum sociis natoque penatibus et magnis dis parturient montes, nascetur ridiculus mus. Suspendisse nisl. Ut neque eros, interdum condimentum, suscipit in, elementum sed, orci. In justo erat, blandit ac, mollis a, viverra quis, ipsum. In quis nulla eu tortor iaculis dictum. Donec est. 
+
+#~ Curabitur eu tortor. Nam eu arcu quis turpis consectetur auctor. Class aptent taciti sociosqu ad litora torquent per conubia nostra, per inceptos himenaeos. Class aptent taciti sociosqu ad litora torquent per conubia nostra, per inceptos himenaeos. Proin a diam sit amet augue suscipit iaculis. Aenean tincidunt arcu. Vivamus libero lacus, vulputate et, lobortis venenatis, eleifend vel, mauris. Donec venenatis, felis eu malesuada pellentesque, leo est ullamcorper nunc, vitae feugiat ipsum purus quis nisl. Donec nec justo nec nisl scelerisque porttitor. Quisque blandit malesuada mi. Nunc dignissim placerat elit. Donec gravida pharetra libero. Cras non turpis quis enim viverra dapibus. Cras dui justo, lobortis vel, euismod eu, vulputate varius, augue. 
+
+#~ Proin sit amet tortor. Integer bibendum consequat odio. Aliquam arcu metus, porttitor quis, luctus a, semper vel, nunc. Quisque sagittis. Phasellus eget felis. Pellentesque tincidunt, ante id dapibus egestas, velit nisl mollis magna, non posuere libero diam sit amet nisl. In hac habitasse platea dictumst. Nulla sem nisi, venenatis feugiat, tristique aliquet, tincidunt et, dolor. Pellentesque habitant morbi tristique senectus et netus et malesuada fames ac turpis egestas. Nullam aliquet. Nam augue sapien, euismod sed, tempus sed, porta nec, sapien. Proin sed tortor ut mauris laoreet condimentum. Suspendisse neque. Suspendisse ac neque. Integer aliquam libero in arcu. Sed risus. Praesent nec nisi. Ut rutrum imperdiet lectus. Maecenas quis libero. 
+
+#~ Phasellus euismod fermentum diam. Donec felis lorem, sollicitudin at, tincidunt sit amet, pharetra vitae, tortor. Lorem ipsum dolor sit amet, consectetur adipiscing elit. Suspendisse at nulla. Praesent cursus pellentesque nunc. Pellentesque et erat. Nam tincidunt ullamcorper purus. Ut accumsan mattis magna. Sed quis est. Aenean eros neque, lacinia ut, aliquam quis, molestie sit amet, lacus. 
+
+#~ Ut arcu orci, cursus a, vestibulum non, sollicitudin eu, nibh. Nullam porttitor leo eu justo. Donec sit amet orci ac odio tristique cursus. Phasellus accumsan consequat elit. In lectus. Proin ultrices sollicitudin quam. Fusce eget nulla. Aliquam bibendum aliquam felis. Praesent vitae orci ut eros auctor rhoncus. Vivamus congue laoreet lacus. Aenean lobortis dui id nunc. Nulla vel erat quis purus fermentum vestibulum. Vivamus sit amet eros. 
+
+#~ Etiam justo lectus, gravida vel, tempor sed, dignissim vel, massa. Nunc tortor. Vestibulum velit elit, mattis ac, malesuada sed, commodo ut, ante. Sed adipiscing. Pellentesque eget magna. Mauris ut ante. Aliquam congue magna non sapien volutpat bibendum. Quisque diam turpis, feugiat vitae, tincidunt vel, varius nec, pede. Suspendisse potenti. Maecenas vestibulum elit. Etiam mi nulla, tempus quis, interdum faucibus, elementum non, urna. Cras eu erat. 
+
+#~ Integer eu est. Donec mattis auctor arcu. Phasellus faucibus est sit amet nisi. Proin varius dui ut mi. Sed neque. Morbi urna purus, sodales eget, eleifend eu, imperdiet a, risus. Nunc sit amet sapien in augue malesuada semper. Nulla sed nibh in dolor lobortis vestibulum. Cras et risus at nisi aliquet tristique. Maecenas dui urna, viverra ac, interdum eu, adipiscing ut, turpis. Ut purus nisi, gravida quis, rutrum dapibus, malesuada pellentesque, erat. Aliquam augue. Nam mi urna, pharetra et, tincidunt id, rhoncus ac, lacus. Sed id nisi non nulla tincidunt sodales. Nam consectetur velit hendrerit purus. 
+
+#~ Vestibulum eu tortor. Sed et eros id justo eleifend vehicula. Mauris quis dui. Nam luctus lacinia pede. Suspendisse id eros. Vestibulum at neque. Morbi eu nisi. Suspendisse mi nisl, varius nec, aliquet vel, ultrices interdum, diam. Integer consequat felis vitae dolor. Suspendisse potenti. Duis molestie, metus ut mollis condimentum, eros nibh bibendum erat, sit amet fermentum sapien est at velit. Mauris tincidunt, metus eu rhoncus eleifend, lorem eros lacinia ipsum, sit amet tempus ante risus at massa. 
+
+#~ Mauris pellentesque. Pellentesque vitae felis eu tellus venenatis pellentesque. Praesent adipiscing malesuada mi. Nulla sagittis hendrerit ante. Morbi vitae massa. Donec arcu urna, blandit tempus, posuere ut, mattis sed, lacus. Vestibulum sed lectus quis massa ornare volutpat. Mauris sodales elit et est. Morbi tristique euismod elit. Aliquam vitae dui non odio convallis volutpat. Aenean ligula leo, pretium eget, adipiscing ut, pellentesque a, leo. Praesent aliquet felis sed eros. Ut venenatis eros a dolor. Donec sapien nulla, blandit ornare, egestas nec, faucibus in, eros. Vestibulum vitae quam in felis accumsan ullamcorper. Nam justo. Aenean quis enim eu enim faucibus vehicula. Praesent sem turpis, pharetra non, hendrerit id, adipiscing id, urna. Suspendisse dolor. 
+
+#~ Donec urna. Fusce volutpat tortor sed mi. Maecenas metus erat, condimentum ac, venenatis eget, euismod in, eros. Aenean eros turpis, semper non, suscipit sed, facilisis quis, erat. Nunc hendrerit. Vivamus dapibus pede sit amet urna. Nunc auctor. Maecenas consequat ullamcorper est. Maecenas sodales. Praesent luctus mattis magna. Quisque elementum, lacus eget imperdiet aliquet, justo mi dapibus arcu, et pretium felis metus in urna. 
+
+#~ Vestibulum diam. Maecenas ante neque, pulvinar non, vestibulum at, feugiat vitae, orci. Cras elit. Mauris ultricies odio quis pede. Sed tristique lacus ac erat. Donec mattis dignissim metus. Sed pharetra lorem consequat sem. Sed mauris. Proin sed urna. Vestibulum in mi vitae libero venenatis eleifend. Suspendisse viverra neque. Aenean non elit. Vestibulum pellentesque magna vel lacus. 
+
+#~ Phasellus rutrum facilisis ligula. Vivamus et nunc. Fusce tristique lectus non ligula. Integer a urna id pede viverra tincidunt. Phasellus consequat auctor lectus. Suspendisse potenti. Fusce imperdiet, massa vitae tristique sodales, lorem odio consequat ipsum, eu commodo ante elit quis diam. Vestibulum et magna. Cras tincidunt, felis at congue egestas, ligula dolor condimentum erat, et bibendum ligula pede at dolor. Nullam ac tortor non lectus feugiat porta. Aliquam ultricies tincidunt felis. Vestibulum placerat. 
+
+#~ Mauris tincidunt massa quis arcu. Suspendisse placerat vehicula urna. Donec ut nunc non elit aliquam posuere. Sed est leo, convallis id, elementum vitae, elementum eu, ante. Aenean vitae lectus at risus condimentum suscipit. Nulla hendrerit blandit velit. Sed metus. Donec pellentesque dignissim quam. Pellentesque habitant morbi tristique senectus et netus et malesuada fames ac turpis egestas. Pellentesque eleifend lectus euismod orci. Donec ligula massa, volutpat a, facilisis sed, tincidunt luctus, neque. Pellentesque felis sem, fermentum non, luctus sit amet, sollicitudin non, odio. Praesent ac turpis nec leo congue sodales. Donec consectetur ante ut mi. Donec turpis. Ut varius lobortis metus. 
+
+#~ Sed rhoncus interdum tortor. Ut imperdiet turpis vel ante. Phasellus lobortis sodales ipsum. Fusce lectus. Praesent malesuada velit ac nulla. Quisque porttitor, dolor in egestas iaculis, urna quam eleifend diam, sit amet mollis ante metus id nibh. Nullam bibendum pellentesque est. Integer risus. Suspendisse molestie rutrum ligula. Mauris augue. Sed augue nisi, ornare nec, luctus a, elementum id, dolor. Nulla eros purus, pulvinar elementum, lacinia non, rhoncus in, elit. Sed quis nunc. Phasellus euismod, lectus vitae lobortis faucibus, ipsum nibh elementum massa, non fermentum elit sem vel diam. 
+
+#~ Aliquam aliquet nibh non massa. Nunc vulputate metus sed lacus. Integer varius. Ut viverra magna ut metus. Phasellus nisi. Donec a quam et nisl varius suscipit. Phasellus ornare tristique lacus. Nam tempor magna sed felis. Pellentesque habitant morbi tristique senectus et netus et malesuada fames ac turpis egestas. Sed vitae eros ut metus ullamcorper porta. In ultrices quam quis mi. Integer lorem magna, rhoncus ac, suscipit vitae, sagittis sit amet, velit. Cras vestibulum fermentum erat. Ut tincidunt semper odio. Maecenas rhoncus, sapien eu vulputate egestas, urna purus pharetra tortor, in fringilla leo sapien posuere erat. Fusce sit amet diam ut velit elementum imperdiet. Quisque nibh. 
+
+#~ Aenean libero enim, gravida ut, feugiat tempor, consectetur convallis, nisi. Etiam convallis nibh eu diam. Curabitur enim est, viverra ac, fringilla ut, consectetur quis, sem. Suspendisse malesuada malesuada felis. Mauris accumsan accumsan tellus. Ut sit amet est. Sed lacinia, turpis sed eleifend porta, justo orci cursus nunc, non tempus mauris ipsum id nisl. Aliquam justo urna, vulputate ut, dictum a, sollicitudin ut, mi. Pellentesque ullamcorper tristique velit. Ut tempor commodo justo. Etiam ut risus. In leo. Nunc scelerisque velit. Suspendisse potenti. Phasellus luctus sagittis erat. Sed placerat. Lorem ipsum dolor sit amet, consectetur adipiscing elit. Mauris nibh augue, ultrices et, sagittis sit amet, mattis posuere, nisl. Aliquam placerat metus at pede. Vestibulum dictum ipsum eu diam. 
+
+#~ Curabitur et neque. Suspendisse bibendum interdum purus. Aenean ac ipsum eget arcu molestie commodo. Vivamus sapien eros, volutpat quis, malesuada non, dignissim quis, nulla. Vivamus vel leo ut tellus dignissim placerat. Suspendisse nunc tortor, egestas sed, egestas vitae, tincidunt eget, nulla. Phasellus eget velit. Aenean ultricies venenatis lacus. Nunc et lorem id eros scelerisque volutpat. Nunc accumsan fermentum leo. Mauris fermentum sodales erat. Phasellus ac erat commodo metus ullamcorper rhoncus. Quisque consequat, urna non egestas suscipit, velit diam cursus nisl, at porta quam diam id neque. Quisque ut odio. Aenean leo est, ultricies eget, porttitor at, gravida et, est. Nunc quis ligula id tortor congue mollis. Vivamus vel enim vel erat eleifend ornare. Pellentesque ut purus eu neque rhoncus vehicula. 
+
+#~ Morbi viverra orci non purus. Donec nisl. Mauris mollis pretium felis. Quisque hendrerit porta metus. Integer lorem lacus, vestibulum sit amet, laoreet non, lacinia quis, arcu. Sed fringilla luctus ipsum. Duis venenatis turpis egestas enim. Ut odio orci, suscipit vitae, sagittis sit amet, viverra euismod, urna. Nunc varius, turpis sit amet facilisis convallis, justo nulla mattis augue, vitae consequat lorem sem a lectus. Sed id nulla. Nullam laoreet velit nec sapien. Donec condimentum faucibus arcu. Pellentesque a felis non felis bibendum posuere. Cum sociis natoque penatibus et magnis dis parturient montes, nascetur ridiculus mus. Integer semper. Phasellus feugiat magna nec nulla. 
+
+#~ Duis commodo, mauris ac imperdiet convallis, lectus turpis molestie odio, id fringilla diam nisi at ante. Donec venenatis augue id nunc. Nullam eget quam. Ut vehicula nisl. Vivamus et nisl. Fusce faucibus enim in erat. Cum sociis natoque penatibus et magnis dis parturient montes, nascetur ridiculus mus. Suspendisse ac enim. Phasellus massa orci, viverra ut, scelerisque quis, laoreet eu, augue. Pellentesque malesuada pharetra velit. Proin volutpat commodo odio. Quisque vehicula bibendum purus. Ut elit. Sed magna lacus, condimentum id, congue vel, pellentesque non, elit. 
+
+#~ Nam a massa sodales enim molestie vulputate. Class aptent taciti sociosqu ad litora torquent per conubia nostra, per inceptos himenaeos. Suspendisse fermentum eros id nibh. Vivamus sagittis aliquet quam. Mauris convallis lectus non velit imperdiet varius. Etiam quis urna. Nulla consequat. Curabitur congue laoreet orci. Suspendisse potenti. Donec scelerisque pellentesque nisl. In pharetra. Curabitur sit amet ligula. Vestibulum justo purus, facilisis ut, molestie eget, pellentesque eget, felis. Ut in nisl. Duis magna. Curabitur eleifend lorem sed dolor. 
+
+#~ In porta, ligula at pharetra vestibulum, mauris risus viverra nulla, ut convallis ipsum ligula vitae ligula. Quisque vel est ac magna iaculis ultricies. Cras facilisis laoreet tortor. Nunc vitae lorem. Vestibulum facilisis felis nec risus. Nunc non pede eget leo hendrerit vehicula. Sed dapibus eros nec urna. Etiam non metus et nisi ultricies dapibus. Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia Curae; Quisque orci. Aliquam bibendum egestas sapien. Praesent sit amet mi. Duis tristique aliquet massa. Curabitur at eros non magna gravida semper. Proin nulla metus, aliquam in, congue ac, mollis eu, leo. Ut eros justo, sagittis non, pharetra quis, gravida et, mauris. Vestibulum blandit euismod metus. Etiam faucibus neque vel pede. Pellentesque vulputate vestibulum massa. 
+
+#~ Sed tincidunt, massa nec sollicitudin aliquet, nibh quam semper mi, non dictum ligula enim quis libero. Vestibulum et tortor. Sed dapibus, neque id lobortis viverra, augue tortor hendrerit elit, at tristique odio est sit amet risus. Integer sollicitudin. Etiam eget urna. In semper nunc ut pede. Praesent elit dolor, aliquam vel, placerat eu, imperdiet eget, mi. Duis non leo. Integer dictum sapien non massa. Mauris lectus. Quisque erat tortor, mattis sit amet, semper eu, rutrum eget, tellus. Etiam ultrices. Morbi eu urna ornare lectus imperdiet ultrices. Etiam vitae massa at felis interdum venenatis. Nam tempor risus sit amet nunc. Aliquam et mi eget pede fermentum imperdiet. 
+
+#~ Fusce mauris nisi, venenatis id, laoreet id, luctus et, mauris. Proin ut nisi ut massa tincidunt sagittis. Donec auctor tincidunt ante. Maecenas nec ipsum id turpis congue semper. Morbi blandit, metus ut consectetur tristique, lorem risus rutrum lacus, et vehicula nulla nisl nec tortor. Integer feugiat congue diam. Maecenas in erat. Nullam consequat augue. Aenean rhoncus. Donec sollicitudin ullamcorper eros. Proin varius magna vel sem. Vestibulum ultricies rutrum ipsum. Praesent blandit tellus vitae pede. Duis dictum venenatis orci. Quisque dapibus neque et enim. 
+
+#~ Curabitur eget augue ut nulla rhoncus mattis. Nunc varius. Pellentesque habitant morbi tristique senectus et netus et malesuada fames ac turpis egestas. Duis metus justo, lobortis et, ultrices sed, varius in, lectus. Nam ornare ante sagittis lacus. Etiam cursus. Sed purus mi, sagittis non, accumsan at, rutrum a, urna. Sed nec neque. Donec dolor. Aenean rutrum tempor neque. Quisque sodales hendrerit arcu. 
+
+#~ Ut lobortis. Cras ultricies dapibus nisi. Maecenas at arcu eget nisi mattis malesuada. Mauris imperdiet accumsan urna. Morbi enim lectus, posuere quis, euismod et, ultrices at, mauris. Duis velit. Vestibulum commodo placerat mi. Suspendisse gravida leo id urna. Aliquam vestibulum. Cum sociis natoque penatibus et magnis dis parturient montes, nascetur ridiculus mus. Ut tristique. Nam sapien lacus, mattis sed, blandit vel, imperdiet eu, nunc. Nullam nisi nisi, tincidunt at, consequat et, rhoncus vitae, lectus. Fusce nibh. Mauris ligula erat, rhoncus eget, vehicula nec, dictum et, libero. Pellentesque tincidunt. 
+
+#~ Nullam dui urna, fermentum a, facilisis eget, aliquam nec, ligula. Maecenas ut tellus. Donec pharetra, odio at dignissim aliquam, dui tellus interdum arcu, dignissim convallis ipsum pede eget lacus. Etiam laoreet justo mollis ligula. Vivamus feugiat enim quis quam. Nulla pretium placerat nunc. Aliquam id lectus. Maecenas in diam. Suspendisse lorem enim, tempor a, tincidunt nec, dignissim vel, sem. Nam feugiat neque aliquam nisi. Proin viverra sem ut justo. Vestibulum ut ligula dictum justo facilisis pellentesque. Cras laoreet nunc vitae dolor. Sed et mi eu tortor euismod accumsan. Donec nec justo. Proin vulputate. Nunc ipsum nibh, interdum at, dictum sit amet, ultrices at, dolor. Integer a nisl in eros sodales feugiat. Vivamus adipiscing ullamcorper nulla. 
+
+#~ Integer in tortor. Donec rhoncus lectus in felis. Mauris vehicula. Ut dignissim libero sit amet quam. Nam sit amet ante. Fusce vel urna vel mi sollicitudin hendrerit. Mauris nec libero. Nunc eros nisi, egestas id, tempor eu, sagittis non, diam. Lorem ipsum dolor sit amet, consectetur adipiscing elit. Duis placerat. Cras dolor est, dapibus ut, adipiscing ac, ullamcorper in, lorem. Donec odio magna, pulvinar viverra, euismod nec, placerat in, purus. Praesent a ante. Curabitur ac nibh a nulla hendrerit porta. Donec sapien dolor, suscipit et, egestas ac, ultrices in, nisi. Morbi augue metus, aliquam a, adipiscing a, rhoncus id, massa. 
+
+#~ Duis quam. Sed elementum. Phasellus vulputate tempus risus. Suspendisse potenti. Vestibulum mi ligula, convallis eu, pretium non, molestie in, neque. Vivamus malesuada, sapien scelerisque sollicitudin mollis, leo nisi laoreet tortor, sed aliquet neque velit in pede. Praesent consectetur sem ut tellus. Integer ac diam. Praesent leo magna, suscipit vitae, vulputate quis, dictum ac, justo. Maecenas rutrum lobortis felis. In tincidunt tellus sed dui. Proin est dui, fringilla vitae, blandit at, pharetra at, augue. Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nunc eros velit, tempus dapibus, semper nec, sagittis non, nisl. Nulla id ipsum. Aliquam feugiat vulputate velit. Sed nec urna. Cras ac risus. Maecenas augue dui, dapibus a, porttitor eget, consectetur sed, urna. 
+
+#~ Phasellus quis metus sed ante egestas laoreet. Cras sed nibh vel quam rhoncus venenatis. Ut cursus iaculis urna. Morbi fermentum, neque ut interdum vestibulum, lectus mi malesuada velit, vitae ultricies erat mi eu urna. Nulla facilisi. Maecenas rhoncus bibendum ante. Phasellus volutpat ante a nisi commodo molestie. Praesent enim. Quisque ullamcorper interdum purus. Vestibulum egestas, nisi non lacinia tristique, mauris ipsum vehicula tellus, cursus dignissim arcu lectus a nisi. In rhoncus imperdiet sapien. Donec eu leo vitae felis vehicula malesuada. Mauris sagittis nulla pretium odio. Donec quis turpis. In venenatis. Curabitur eleifend vestibulum arcu. Fusce iaculis volutpat quam. 
+
+#~ Donec semper varius felis. Pellentesque accumsan, sapien eu interdum eleifend, felis metus dapibus nibh, a vehicula risus eros at lectus. In laoreet placerat massa. Nullam ipsum elit, tempor eget, dignissim in, facilisis ut, est. Quisque sed risus eget dolor porta cursus. Pellentesque habitant morbi tristique senectus et netus et malesuada fames ac turpis egestas. Maecenas volutpat auctor nibh. Aliquam dui mi, gravida ut, tempus vitae, ultrices quis, arcu. In hac habitasse platea dictumst. Nam dapibus, elit eu ultrices tristique, felis arcu ultricies orci, et rhoncus urna sem nec pede. Maecenas erat nibh, volutpat sed, posuere a, tempor a, tellus. In neque. Pellentesque nec tellus. Aliquam consectetur tristique tellus. Mauris congue, nulla non consequat scelerisque, enim magna luctus risus, at condimentum purus lectus quis tellus. Phasellus erat ipsum, tempus aliquet, mattis et, convallis non, dolor. Morbi nec justo. Quisque ut nunc eu dolor suscipit auctor. Vestibulum commodo nisi non enim. Maecenas risus ipsum, auctor eget, posuere non, faucibus nec, ligula. 
+
+#~ Donec ornare ligula a augue. Suspendisse eget magna sed nisi accumsan porta. Donec in eros. Class aptent taciti sociosqu ad litora torquent per conubia nostra, per inceptos himenaeos. Sed velit ipsum, accumsan hendrerit, porta in, accumsan fermentum, est. Suspendisse porttitor. Cras vel nisl at nulla cursus gravida. Donec molestie, lacus et dictum faucibus, turpis ante ultricies risus, non varius velit nibh vitae erat. Fusce accumsan eros eget libero. Nam mollis dolor. Donec auctor luctus lorem. Nunc vel dui. Vivamus dolor sapien, porta non, pellentesque at, dictum quis, elit. Sed et mi. Mauris volutpat. Duis pretium rutrum velit. Nulla facilisi. Nullam imperdiet dui. In tincidunt, arcu id aliquet porttitor, urna tellus dignissim metus, non auctor leo mauris sed quam. Suspendisse nunc tellus, eleifend eget, malesuada suscipit, interdum vitae, lorem. 
+
+#~ In sed tortor at justo lobortis eleifend. Aliquam arcu. Aenean gravida hendrerit orci. Etiam eu metus. Duis at nisi sed est posuere hendrerit. Nunc lacus. Nunc ut pede vel lectus venenatis commodo. Praesent purus. Aliquam quis elit vitae erat volutpat euismod. Duis adipiscing scelerisque lectus. In hac habitasse platea dictumst. Donec in libero a dui sollicitudin rutrum. 
+
+#~ In hac habitasse platea dictumst. Donec molestie, tellus ac fringilla lacinia, lectus ipsum euismod sem, interdum scelerisque tellus dui in tortor. Curabitur ornare elit quis lectus. Quisque consectetur ullamcorper metus. Suspendisse hendrerit. Quisque quam. Pellentesque augue. Aliquam eu dui accumsan lacus tincidunt condimentum. Vestibulum sollicitudin elit sed quam. Nulla eleifend, est non iaculis feugiat, ante turpis sagittis sapien, id porta urna turpis a felis. Proin tincidunt laoreet turpis. Proin nunc. Nulla ac sapien. Mauris ultrices odio sed metus. Quisque bibendum odio a nisl. Suspendisse placerat sapien vel orci. Nunc nec nulla. Phasellus convallis, ipsum sit amet interdum interdum, justo nisi interdum dolor, sit amet volutpat tortor ante vitae nunc. Vivamus molestie. Nunc volutpat, augue et iaculis tempor, elit enim accumsan eros, eu ornare ipsum sapien vitae leo. 
+
+#~ Phasellus porta. Ut ultrices, arcu non vehicula varius, massa quam consectetur enim, a suscipit purus est non felis. Aliquam dui. Sed in erat. Morbi nisl. Etiam aliquet. In vitae quam et justo cursus laoreet. Morbi rutrum sem ac ligula. Sed eget tortor vel mi condimentum dignissim. Nullam semper tellus sed tortor. Nulla cursus pede non purus. Nulla facilisi. Nam varius. Integer sit amet sem. Nullam cursus mauris sed massa. Maecenas in tellus vel elit venenatis viverra. Cras quis neque quis sapien elementum porttitor. Aliquam pulvinar. Cras tincidunt tristique urna. 
+
+#~ Aliquam erat volutpat. Curabitur sit amet augue nec ligula pellentesque auctor. Proin pharetra risus ut tortor. Donec sagittis mauris vel mi. Morbi erat diam, egestas eget, rutrum et, ultrices ac, lorem. Nunc ut massa. Vivamus at est. Mauris leo leo, ultricies facilisis, dictum porttitor, fringilla a, odio. Nunc vel libero eu ipsum fermentum malesuada. Phasellus vestibulum aliquam mauris. Sed interdum. Sed hendrerit placerat neque. Phasellus malesuada justo eu ipsum. Vivamus luctus, justo eu condimentum mattis, lectus nunc congue ante, ut convallis tortor tortor id dui. Aliquam erat volutpat. Etiam placerat, nisi eget pulvinar facilisis, erat enim hendrerit massa, sit amet luctus massa massa et orci. 
+
+#~ Ut accumsan, nulla eu lacinia fermentum, eros orci dictum eros, et viverra odio augue sed dui. Fusce bibendum. Nulla sollicitudin tellus sit amet nulla. Nunc orci tellus, viverra vitae, accumsan ut, sodales quis, dolor. Phasellus interdum, ante at elementum malesuada, arcu leo porta diam, vel sagittis nulla diam ornare lacus. Pellentesque at erat at arcu rhoncus adipiscing. Ut vel pede et massa sodales euismod. Etiam ut dolor. Fusce nisi. Proin tortor. Donec vel nisl vel sem porta sagittis. Sed id purus eu lorem facilisis aliquam. Vivamus sapien magna, condimentum quis, lobortis sed, rutrum id, lacus. Vivamus quis elit at magna viverra consectetur. Etiam mollis accumsan justo. Aenean sem. Donec ante felis, laoreet in, lobortis a, dapibus id, eros. Sed congue turpis sed urna scelerisque sagittis. 
+
+#~ Sed viverra, orci vitae posuere convallis, elit ipsum tincidunt turpis, id gravida est purus sed felis. Quisque aliquet. Suspendisse sit amet erat. Maecenas gravida dapibus justo. In hac habitasse platea dictumst. Maecenas eleifend justo lacinia tortor. Suspendisse tristique semper dolor. Nam imperdiet dapibus risus. Vestibulum bibendum orci. Pellentesque congue, sem vitae malesuada ultrices, diam turpis mollis nibh, at malesuada dui est at magna. 
+
+#~ Morbi ornare nisi pellentesque odio. Maecenas sit amet lectus. Aenean elit. Donec vestibulum, diam non mattis cursus, justo sapien semper nibh, vel sagittis ligula nisl non nibh. Nullam sem mauris, malesuada et, tincidunt aliquet, venenatis porta, sem. Donec convallis aliquet massa. In in elit vel magna semper blandit. Etiam vulputate turpis. Curabitur porta tincidunt augue. Duis interdum gravida quam. Lorem ipsum dolor sit amet, consectetur adipiscing elit. Sed odio justo, venenatis sit amet, semper et, tincidunt posuere, lorem. Nulla in quam. Sed iaculis. Nulla scelerisque rhoncus nunc. Proin in mauris. Nam nulla ipsum, pharetra sed, ultricies at, sodales sit amet, ligula. 
+
+#~ Vivamus tincidunt aliquam nunc. Morbi sapien ipsum, tempor in, mattis at, tincidunt a, nisl. Sed vitae urna. Mauris id velit. Nunc tempor libero nec sapien. Curabitur vestibulum, dui ut posuere ultricies, risus magna gravida enim, nec luctus augue mauris et nibh. Nunc enim. In hac habitasse platea dictumst. Etiam consequat tempor mi. Aenean eget nisl non quam condimentum dapibus. Curabitur varius erat vel dui. Nam ac sem nec quam sagittis ultricies. Nullam turpis libero, molestie et, posuere eu, vestibulum nec, elit. 
+
+#~ Nullam hendrerit. Vestibulum fermentum. Morbi est. Duis ut orci. Sed condimentum, tortor id ornare cursus, mi mauris fermentum purus, nec fermentum nisi risus id tortor. Quisque lectus nisl, facilisis ac, tincidunt sit amet, cursus ac, velit. Nulla a ante. Aliquam suscipit mauris eget justo. Suspendisse eu turpis fermentum felis suscipit ornare. Sed ornare. Quisque commodo luctus mauris. Morbi bibendum metus in quam. Cras faucibus sapien id turpis. Phasellus a ante. In hac habitasse platea dictumst. 
+
+#~ Vestibulum facilisis. Vestibulum eget orci vitae ligula dignissim pulvinar. Aliquam et massa. Mauris dictum ornare quam. Nulla eu augue. Mauris elementum justo at mi. Vestibulum ornare. Nunc dolor tortor, euismod vitae, pretium fringilla, porta in, mi. Aliquam varius. Sed sit amet lacus. Cras ac purus. Donec pulvinar, urna eget cursus vehicula, mauris turpis iaculis arcu, et condimentum lacus tortor quis ante. Donec aliquam. Suspendisse sapien. Donec nec nibh. Quisque vitae massa. Nam accumsan lobortis sem. 
+
+#~ Aenean laoreet imperdiet diam. Maecenas ante mauris, auctor nec, dapibus ut, hendrerit nec, purus. Quisque lobortis volutpat ligula. Nulla ullamcorper diam. Fusce sed magna nec turpis elementum malesuada. Fusce placerat felis sodales tellus. Nunc sit amet risus quis tortor viverra aliquet. Nam sagittis. Donec scelerisque laoreet est. Morbi blandit egestas erat. 
+
+#~ Morbi nulla ipsum, feugiat a, molestie et, commodo id, eros. Nam in orci quis risus adipiscing convallis. Ut posuere mi. Duis accumsan. Mauris condimentum arcu. Donec facilisis metus ac tellus. Maecenas sit amet leo. Morbi ultricies molestie arcu. Pellentesque sollicitudin fringilla pede. Donec eros. In et leo. In felis. Fusce justo turpis, auctor nec, gravida eu, aliquet sit amet, diam. Curabitur consectetur pulvinar nisi. Nam eu neque eu turpis tristique sollicitudin. Sed aliquam viverra enim. Sed sit amet justo. 
+
+#~ Donec sed justo. Pellentesque habitant morbi tristique senectus et netus et malesuada fames ac turpis egestas. Nam velit. Nulla pharetra justo. Curabitur pulvinar eleifend turpis. Mauris tempus urna in nisl. Etiam convallis viverra tellus. Curabitur elit dui, convallis ac, tempor in, pharetra vitae, leo. Nullam erat. Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia Curae; 
+
+#~ Nulla tempus, ipsum vel ultrices imperdiet, odio odio varius risus, ut pulvinar diam nisl ut turpis. Maecenas imperdiet est at neque. Suspendisse fringilla. Donec molestie libero molestie sem. Curabitur a orci at augue pretium sollicitudin. Aliquam condimentum commodo nisi. In rhoncus volutpat nibh. Aliquam eget lectus quis nisl tristique elementum. Sed ultricies augue. Etiam semper malesuada nunc. Vestibulum nisl. Maecenas viverra lectus at lorem. Fusce gravida commodo lorem. Donec nulla. Nulla facilisi. 
+
+#~ Duis sapien. Suspendisse ullamcorper hendrerit libero. Suspendisse a odio. Aliquam placerat. Vivamus facilisis tempor urna. Vivamus eu tellus volutpat risus adipiscing pellentesque. Suspendisse nunc. Donec dignissim orci tincidunt massa. Pellentesque eget lorem quis enim lacinia placerat. Sed ac quam ut ligula consectetur molestie. Maecenas sodales est vel ligula. 
+
+#~ Nullam faucibus bibendum ipsum. Class aptent taciti sociosqu ad litora torquent per conubia nostra, per inceptos himenaeos. Quisque sapien. Cum sociis natoque penatibus et magnis dis parturient montes, nascetur ridiculus mus. In sed mauris vitae nisl blandit condimentum. Nulla diam. Nam ullamcorper risus ac risus. Vivamus gravida risus non enim luctus auctor. Praesent arcu eros, elementum condimentum, tempor ut, sollicitudin sed, libero. Morbi et ligula. 
+
+#~ Donec at nunc. Nulla ullamcorper laoreet purus. Duis rhoncus sem a nisi. Nulla cursus, metus in tincidunt tincidunt, est nisl egestas nisl, at mollis neque nisi vel magna. Aenean eros. Vestibulum odio. Curabitur gravida semper urna. Maecenas vitae arcu elementum nulla porta sagittis. Cras vulputate sapien quis orci consectetur aliquet. Nam at lacus. Sed ut ligula et libero feugiat lacinia. Phasellus eget elit. 
+
+#~ Aliquam erat volutpat. Cras laoreet massa vel ligula molestie mattis. Suspendisse in tortor non sem congue congue. Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia Curae; Vestibulum egestas dui sit amet lorem. Suspendisse potenti. Phasellus lacus magna, aliquet a, dapibus non, adipiscing in, nunc. Sed adipiscing placerat dui. Fusce tellus dolor, semper sit amet, euismod sit amet, semper id, elit. Nam massa leo, malesuada a, congue ut, elementum et, magna. Nulla porta justo sit amet nisl. Sed vel sem nec sem auctor mattis. Donec iaculis leo a dolor. Donec tempus, lacus nec bibendum dapibus, ante nulla porttitor tellus, eu eleifend arcu neque quis est. Vestibulum id nisl eget est pellentesque lacinia. Class aptent taciti sociosqu ad litora torquent per conubia nostra, per inceptos himenaeos. Phasellus eleifend pede et dui. Donec posuere, purus auctor scelerisque sagittis, mi diam venenatis nisi, eget sollicitudin justo mauris eu massa. Suspendisse at massa. Aliquam semper. 
+
+#~ Suspendisse aliquam, tortor vitae euismod laoreet, erat augue ultrices augue, eget sollicitudin quam odio venenatis diam. Aenean semper. In vel ipsum. Nullam nulla eros, fermentum in, malesuada auctor, condimentum eu, magna. Phasellus porta metus. Donec sit amet neque. Fusce gravida. Cras massa. Aenean dapibus velit vel nisl. Praesent pede. Maecenas condimentum accumsan lacus. 
+
+#~ Lorem ipsum dolor sit amet, consectetur adipiscing elit. Maecenas fringilla, sem nec elementum imperdiet, est augue mattis ante, ac posuere eros metus quis felis. Nullam molestie molestie ipsum. Suspendisse risus. Mauris ac urna eu neque aliquam tincidunt. Cras pellentesque feugiat nunc. Etiam eget dolor. Vestibulum quis tortor ut mi tempor cursus. Etiam sit amet nibh id justo lobortis congue. Ut nec turpis ut nunc interdum adipiscing. 
+
+#~ Duis nunc. Suspendisse sit amet eros a felis euismod convallis. Pellentesque ligula orci, molestie in, sodales ac, suscipit nec, velit. Mauris tincidunt dui. Praesent augue. Morbi eros. Aenean leo nisi, tempus eu, euismod vitae, rhoncus at, lorem. Donec congue varius sem. Cras sed nibh vel sem vehicula fringilla. Suspendisse potenti. Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia Curae; Pellentesque nunc nibh, convallis et, dictum vitae, hendrerit eu, magna. Proin vulputate. 
+
+#~ Cum sociis natoque penatibus et magnis dis parturient montes, nascetur ridiculus mus. Phasellus vestibulum purus id justo. Maecenas eu sapien. Nam consequat luctus ligula. Praesent ac ipsum. Proin vitae sapien vel elit fringilla auctor. Aenean metus neque, varius ac, aliquam viverra, condimentum eu, dolor. In at ante sed nisl gravida convallis. Morbi nisl est, sodales ut, tristique ac, molestie vel, enim. Integer nec nulla non magna pharetra blandit. Donec in lacus. Suspendisse et erat. Curabitur augue augue, aliquam nec, pharetra ut, convallis ut, lectus. 
+
+#~ Nullam elementum viverra orci. Curabitur a tortor sed libero lobortis vehicula. Cras nec nisl. Duis pretium, tortor vel accumsan egestas, arcu orci viverra odio, in sodales erat neque vitae lacus. Curabitur facilisis mauris quis quam. Donec sagittis, purus sed tempor consectetur, tortor tellus fermentum massa, eu condimentum dolor ligula a nunc. Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia Curae; Nunc id ligula. Suspendisse consectetur aliquam nisi. Aenean magna mauris, molestie a, volutpat vel, porta id, mi. Vestibulum lacus est, porta sed, sodales ac, rutrum sit amet, libero. Sed eros leo, malesuada volutpat, tempus non, tempus ac, purus. Vestibulum sagittis, sem quis elementum vulputate, nisl eros semper nisl, et malesuada urna turpis ut nunc. Nunc scelerisque magna. Fusce convallis. Sed elit risus, sodales id, porta at, bibendum ac, nunc. Fusce sed sem eu felis tincidunt suscipit. Pellentesque habitant morbi tristique senectus et netus et malesuada fames ac turpis egestas. 
+
+#~ In dignissim elementum nunc. Suspendisse ornare odio lacinia nulla. Morbi tristique mollis augue. Morbi luctus, sem vitae molestie molestie, ligula libero gravida diam, ac posuere magna magna sit amet leo. Vestibulum in quam ut massa egestas vestibulum. Maecenas suscipit, tortor id vestibulum blandit, orci orci fermentum enim, sed rhoncus nunc magna sed neque. Nunc vel tellus. Sed lectus odio, varius sed, rhoncus a, adipiscing ut, erat. Phasellus ornare eros. Vestibulum eleifend, mi id pulvinar adipiscing, sem diam lacinia felis, vel consequat sem nulla sit amet neque. Etiam commodo nibh nec libero. Aenean blandit vehicula eros. Nam consectetur arcu eu tellus. Cras id erat. In hac habitasse platea dictumst. Quisque vehicula tortor eget purus. Nam est. 
+
+#~ Proin lectus. Etiam laoreet sagittis massa. Donec sed dui. Nulla eget enim. Nullam augue. Duis nulla pede, laoreet sed, venenatis a, hendrerit in, lectus. Sed et est. Maecenas ullamcorper varius tellus. Nam ultricies leo quis sapien. Fusce nec justo at erat congue consequat. Quisque dictum elementum enim. Quisque viverra hendrerit nisi. Fusce suscipit ullamcorper augue. 
+
+#~ Fusce molestie vestibulum sem. Aenean aliquet iaculis nisl. In a ante. Integer lectus odio, viverra vitae, fermentum sit amet, sagittis quis, orci. Vestibulum mattis nunc vitae libero. Cras tempus lorem et odio hendrerit ornare. Nulla euismod massa et nunc blandit eleifend. Etiam in quam quis libero euismod sodales. Mauris tellus magna, mollis non, mollis ac, condimentum non, enim. Mauris quis neque sit amet sem scelerisque facilisis. Duis consectetur congue ipsum. Fusce metus purus, fringilla a, rhoncus nec, rhoncus ut, sem. Suspendisse purus tortor, tincidunt eu, eleifend at, tempor id, lectus. In erat nunc, faucibus sit amet, imperdiet in, adipiscing nec, dui. Quisque a turpis. Cras posuere ante ut magna. Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia Curae; 
+
+#~ Proin erat nulla, sodales quis, faucibus sodales, rutrum in, neque. Mauris a velit a mauris fringilla porta. Proin a dui. Vestibulum id justo eget quam elementum dictum. Donec ultrices ultricies dui. Mauris volutpat leo eget nisl. Maecenas odio. Donec dapibus convallis nisi. Nullam quis mauris ac est faucibus auctor. Pellentesque venenatis urna sed magna. Aliquam lacinia risus eu libero. Sed rhoncus neque in libero. Maecenas pellentesque nunc vitae augue. 
+
+#~ Vestibulum imperdiet diam vel nibh. Sed enim. Praesent sodales, tortor vitae scelerisque accumsan, augue dui vestibulum magna, in interdum augue libero eget ligula. Maecenas orci. Pellentesque ligula. Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia Curae; Morbi sapien. Proin felis diam, consectetur sit amet, faucibus non, scelerisque a, est. Donec malesuada. Sed dignissim lorem vel nulla. Sed congue, enim vel sollicitudin sollicitudin, enim diam feugiat neque, a feugiat purus nulla in lacus. Phasellus libero. Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia Curae; Morbi sit amet arcu. Praesent eleifend enim. Phasellus vel justo et massa fringilla consectetur. Etiam consectetur pharetra odio. 
+
+#~ Proin eget ipsum nec tellus ullamcorper accumsan. Nunc ac lectus vitae nisl suscipit suscipit. Suspendisse commodo, diam vel consequat elementum, leo magna bibendum massa, in lacinia ligula ligula non lacus. Aliquam egestas. Cras arcu elit, suscipit sed, malesuada sed, euismod non, quam. Maecenas porttitor, tellus eget posuere gravida, libero felis lobortis ante, vitae viverra nibh pede at eros. Ut in sapien ut libero commodo eleifend. Quisque tincidunt. Nullam ut felis. In aliquet lectus id dui congue tincidunt. Vivamus pellentesque sem sed urna. Phasellus sed massa at felis porttitor tempor. Phasellus eu leo. In augue est, ullamcorper tincidunt, fringilla condimentum, imperdiet vel, est. Donec pellentesque semper orci. Etiam blandit congue nisl. Aliquam aliquam. Donec lectus. Maecenas volutpat consectetur nulla. Maecenas justo posuere. 
+#~ """
+
+#~ def a():
+    #~ comp = zlib.compress(lipsum)
+    #~ d = zlib.decompress(comp)
+    #~ print d == lipsum
+#~ a()
+
+#~ def b():
+    #~ comp = zlib.compress(lipsum)
+    
+    #~ dco = zlib.decompressobj()
+    #~ bufs = []
+    #~ combuf = comp
+    #~ for i in range(0, len(combuf), 1024):
+        #~ bufs.append(dco.decompress(combuf[i:i+1024]))
+    #~ bufs.append(dco.flush())
+
+    #~ print ''.join(bufs) == lipsum
+#~ b()
+
+#~ def c():
+    #~ comp = zlib.compress(lipsum)
+
+    #~ dco = zlib.decompressobj()
+    #~ bufs = []
+    #~ combuf = comp + lipsum
+    #~ for i in range(0, len(combuf), 1024):
+        #~ bufs.append(dco.decompress(combuf[i:i+1024]))
+    #~ bufs.append(dco.flush())
+
+    #~ print ''.join(bufs) == lipsum
+    #~ print dco.unused_data == lipsum
+#~ c()

IronPython.Zlib/zlib.net/Adler32.cs

+// Copyright (c) 2006, ComponentAce
+// http://www.componentace.com
+// All rights reserved.
+
+// Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met:
+
+// Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 
+// Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 
+// Neither the name of ComponentAce nor the names of its contributors may be used to endorse or promote products derived from this software without specific prior written permission. 
+// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+
+
+
+/*
+Copyright (c) 2000,2001,2002,2003 ymnk, JCraft,Inc. All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are met:
+
+1. Redistributions of source code must retain the above copyright notice,
+this list of conditions and the following disclaimer.
+
+2. Redistributions in binary form must reproduce the above copyright 
+notice, this list of conditions and the following disclaimer in 
+the documentation and/or other materials provided with the distribution.
+
+3. The names of the authors may not be used to endorse or promote products
+derived from this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES,
+INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
+FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT,
+INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT,
+INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA,
+OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
+EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+*/
+/*
+* This program is based on zlib-1.1.3, so all credit should go authors
+* Jean-loup Gailly(jloup@gzip.org) and Mark Adler(madler@alumni.caltech.edu)
+* and contributors of zlib.
+*/
+using System;
+namespace ComponentAce.Compression.Libs.zlib
+{
+	
+	sealed class Adler32
+	{
+		
+		// largest prime smaller than 65536
+		private const int BASE = 65521;
+		// NMAX is the largest n such that 255n(n+1)/2 + (n+1)(BASE-1) <= 2^32-1
+		private const int NMAX = 5552;
+		
+		internal long adler32(long adler, byte[] buf, int index, int len)
+		{
+			if (buf == null)
+			{
+				return 1L;
+			}
+			
+			long s1 = adler & 0xffff;
+			long s2 = (adler >> 16) & 0xffff;
+			int k;
+			
+			while (len > 0)
+			{
+				k = len < NMAX?len:NMAX;
+				len -= k;
+				while (k >= 16)
+				{
+					s1 += (buf[index++] & 0xff); s2 += s1;
+					s1 += (buf[index++] & 0xff); s2 += s1;
+					s1 += (buf[index++] & 0xff); s2 += s1;
+					s1 += (buf[index++] & 0xff); s2 += s1;
+					s1 += (buf[index++] & 0xff); s2 += s1;
+					s1 += (buf[index++] & 0xff); s2 += s1;
+					s1 += (buf[index++] & 0xff); s2 += s1;
+					s1 += (buf[index++] & 0xff); s2 += s1;
+					s1 += (buf[index++] & 0xff); s2 += s1;
+					s1 += (buf[index++] & 0xff); s2 += s1;
+					s1 += (buf[index++] & 0xff); s2 += s1;
+					s1 += (buf[index++] & 0xff); s2 += s1;
+					s1 += (buf[index++] & 0xff); s2 += s1;
+					s1 += (buf[index++] & 0xff); s2 += s1;
+					s1 += (buf[index++] & 0xff); s2 += s1;
+					s1 += (buf[index++] & 0xff); s2 += s1;
+					k -= 16;
+				}
+				if (k != 0)
+				{
+					do 
+					{
+						s1 += (buf[index++] & 0xff); s2 += s1;
+					}
+					while (--k != 0);
+				}
+				s1 %= BASE;
+				s2 %= BASE;
+			}
+			return (s2 << 16) | s1;
+		}
+		
+	}
+}

IronPython.Zlib/zlib.net/Deflate.cs

+// Copyright (c) 2006, ComponentAce
+// http://www.componentace.com
+// All rights reserved.
+
+// Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met:
+
+// Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 
+// Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 
+// Neither the name of ComponentAce nor the names of its contributors may be used to endorse or promote products derived from this software without specific prior written permission. 
+// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+
+/*
+Copyright (c) 2000,2001,2002,2003 ymnk, JCraft,Inc. All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are met:
+
+1. Redistributions of source code must retain the above copyright notice,
+this list of conditions and the following disclaimer.
+
+2. Redistributions in binary form must reproduce the above copyright 
+notice, this list of conditions and the following disclaimer in 
+the documentation and/or other materials provided with the distribution.
+
+3. The names of the authors may not be used to endorse or promote products
+derived from this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES,
+INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
+FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT,
+INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT,
+INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA,
+OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
+EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+*/
+/*
+* This program is based on zlib-1.1.3, so all credit should go authors
+* Jean-loup Gailly(jloup@gzip.org) and Mark Adler(madler@alumni.caltech.edu)
+* and contributors of zlib.
+*/
+using System;
+namespace ComponentAce.Compression.Libs.zlib
+{
+	
+	public sealed class Deflate
+	{
+		
+		private const int MAX_MEM_LEVEL = 9;
+		
+		private const int Z_DEFAULT_COMPRESSION = - 1;
+		
+		private const int MAX_WBITS = 15; // 32K LZ77 window
+		private const int DEF_MEM_LEVEL = 8;
+		
+		internal class Config
+		{
+			internal int good_length; // reduce lazy search above this match length
+			internal int max_lazy; // do not perform lazy search above this match length
+			internal int nice_length; // quit search above this match length
+			internal int max_chain;
+			internal int func;
+			internal Config(int good_length, int max_lazy, int nice_length, int max_chain, int func)
+			{
+				this.good_length = good_length;
+				this.max_lazy = max_lazy;
+				this.nice_length = nice_length;
+				this.max_chain = max_chain;
+				this.func = func;
+			}
+		}
+		
+		private const int STORED = 0;
+		private const int FAST = 1;
+		private const int SLOW = 2;
+		private static Config[] config_table;
+				
+		private static readonly System.String[] z_errmsg = new System.String[]{"need dictionary", "stream end", "", "file error", "stream error", "data error", "insufficient memory", "buffer error", "incompatible version", ""};
+		
+		// block not completed, need more input or more output
+		private const int NeedMore = 0;
+		
+		// block flush performed
+		private const int BlockDone = 1;
+		
+		// finish started, need only more output at next deflate
+		private const int FinishStarted = 2;
+		
+		// finish done, accept no more input or output
+		private const int FinishDone = 3;
+		
+		// preset dictionary flag in zlib header
+		private const int PRESET_DICT = 0x20;
+		
+		private const int Z_FILTERED = 1;
+		private const int Z_HUFFMAN_ONLY = 2;
+		private const int Z_DEFAULT_STRATEGY = 0;
+		
+		private const int Z_NO_FLUSH = 0;
+		private const int Z_PARTIAL_FLUSH = 1;
+		private const int Z_SYNC_FLUSH = 2;
+		private const int Z_FULL_FLUSH = 3;
+		private const int Z_FINISH = 4;
+		
+		private const int Z_OK = 0;
+		private const int Z_STREAM_END = 1;
+		private const int Z_NEED_DICT = 2;
+		private const int Z_ERRNO = - 1;
+		private const int Z_STREAM_ERROR = - 2;
+		private const int Z_DATA_ERROR = - 3;
+		private const int Z_MEM_ERROR = - 4;
+		private const int Z_BUF_ERROR = - 5;
+		private const int Z_VERSION_ERROR = - 6;
+		
+		private const int INIT_STATE = 42;
+		private const int BUSY_STATE = 113;
+		private const int FINISH_STATE = 666;
+		
+		// The deflate compression method
+		private const int Z_DEFLATED = 8;
+		
+		private const int STORED_BLOCK = 0;
+		private const int STATIC_TREES = 1;
+		private const int DYN_TREES = 2;
+		
+		// The three kinds of block type
+		private const int Z_BINARY = 0;
+		private const int Z_ASCII = 1;
+		private const int Z_UNKNOWN = 2;
+		
+		private const int Buf_size = 8 * 2;
+		
+		// repeat previous bit length 3-6 times (2 bits of repeat count)
+		private const int REP_3_6 = 16;
+		
+		// repeat a zero length 3-10 times  (3 bits of repeat count)
+		private const int REPZ_3_10 = 17;
+		
+		// repeat a zero length 11-138 times  (7 bits of repeat count)
+		private const int REPZ_11_138 = 18;
+		
+		private const int MIN_MATCH = 3;
+		private const int MAX_MATCH = 258;		
+		private static readonly int MIN_LOOKAHEAD = (MAX_MATCH + MIN_MATCH + 1);
+		
+		private const int MAX_BITS = 15;
+		private const int D_CODES = 30;
+		private const int BL_CODES = 19;
+		private const int LENGTH_CODES = 29;
+		private const int LITERALS = 256;		
+		private static readonly int L_CODES = (LITERALS + 1 + LENGTH_CODES);		
+		private static readonly int HEAP_SIZE = (2 * L_CODES + 1);
+		
+		private const int END_BLOCK = 256;
+		
+		internal ZStream strm; // pointer back to this zlib stream
+		internal int status; // as the name implies
+		internal byte[] pending_buf; // output still pending
+		internal int pending_buf_size; // size of pending_buf
+		internal int pending_out; // next pending byte to output to the stream
+		internal int pending; // nb of bytes in the pending buffer
+		internal int noheader; // suppress zlib header and adler32
+		internal byte data_type; // UNKNOWN, BINARY or ASCII
+		internal byte method; // STORED (for zip only) or DEFLATED
+		internal int last_flush; // value of flush param for previous deflate call
+		
+		internal int w_size; // LZ77 window size (32K by default)
+		internal int w_bits; // log2(w_size)  (8..16)
+		internal int w_mask; // w_size - 1
+		
+		internal byte[] window;
+		// Sliding window. Input bytes are read into the second half of the window,
+		// and move to the first half later to keep a dictionary of at least wSize
+		// bytes. With this organization, matches are limited to a distance of
+		// wSize-MAX_MATCH bytes, but this ensures that IO is always
+		// performed with a length multiple of the block size. Also, it limits
+		// the window size to 64K, which is quite useful on MSDOS.
+		// To do: use the user input buffer as sliding window.
+		
+		internal int window_size;
+		// Actual size of window: 2*wSize, except when the user input buffer
+		// is directly used as sliding window.
+		
+		internal short[] prev;
+		// Link to older string with same hash index. To limit the size of this
+		// array to 64K, this link is maintained only for the last 32K strings.
+		// An index in this array is thus a window index modulo 32K.
+		
+		internal short[] head; // Heads of the hash chains or NIL.
+		
+		internal int ins_h; // hash index of string to be inserted
+		internal int hash_size; // number of elements in hash table
+		internal int hash_bits; // log2(hash_size)
+		internal int hash_mask; // hash_size-1
+		
+		// Number of bits by which ins_h must be shifted at each input
+		// step. It must be such that after MIN_MATCH steps, the oldest
+		// byte no longer takes part in the hash key, that is:
+		// hash_shift * MIN_MATCH >= hash_bits
+		internal int hash_shift;
+		
+		// Window position at the beginning of the current output block. Gets
+		// negative when the window is moved backwards.
+		
+		internal int block_start;
+		
+		internal int match_length; // length of best match
+		internal int prev_match; // previous match
+		internal int match_available; // set if previous match exists
+		internal int strstart; // start of string to insert
+		internal int match_start; // start of matching string
+		internal int lookahead; // number of valid bytes ahead in window
+		
+		// Length of the best match at previous step. Matches not greater than this
+		// are discarded. This is used in the lazy match evaluation.
+		internal int prev_length;
+		
+		// To speed up deflation, hash chains are never searched beyond this
+		// length.  A higher limit improves compression ratio but degrades the speed.
+		internal int max_chain_length;
+		
+		// Attempt to find a better match only when the current match is strictly
+		// smaller than this value. This mechanism is used only for compression
+		// levels >= 4.
+		internal int max_lazy_match;
+		
+		// Insert new strings in the hash table only if the match length is not
+		// greater than this length. This saves time but degrades compression.
+		// max_insert_length is used only for compression levels <= 3.
+		
+		internal int level; // compression level (1..9)
+		internal int strategy; // favor or force Huffman coding
+		
+		// Use a faster search when the previous match is longer than this
+		internal int good_match;
+		
+		// Stop searching when current match exceeds this
+		internal int nice_match;
+		
+		internal short[] dyn_ltree; // literal and length tree
+		internal short[] dyn_dtree; // distance tree
+		internal short[] bl_tree; // Huffman tree for bit lengths
+		
+		internal Tree l_desc = new Tree(); // desc for literal tree
+		internal Tree d_desc = new Tree(); // desc for distance tree
+		internal Tree bl_desc = new Tree(); // desc for bit length tree
+		
+		// number of codes at each bit length for an optimal tree
+		internal short[] bl_count = new short[MAX_BITS + 1];
+		
+		// heap used to build the Huffman trees
+		internal int[] heap = new int[2 * L_CODES + 1];
+		
+		internal int heap_len; // number of elements in the heap
+		internal int heap_max; // element of largest frequency
+		// The sons of heap[n] are heap[2*n] and heap[2*n+1]. heap[0] is not used.
+		// The same heap array is used to build all trees.
+		
+		// Depth of each subtree used as tie breaker for trees of equal frequency
+		internal byte[] depth = new byte[2 * L_CODES + 1];
+		
+		internal int l_buf; // index for literals or lengths */
+		
+		// Size of match buffer for literals/lengths.  There are 4 reasons for
+		// limiting lit_bufsize to 64K:
+		//   - frequencies can be kept in 16 bit counters
+		//   - if compression is not successful for the first block, all input
+		//     data is still in the window so we can still emit a stored block even
+		//     when input comes from standard input.  (This can also be done for
+		//     all blocks if lit_bufsize is not greater than 32K.)
+		//   - if compression is not successful for a file smaller than 64K, we can
+		//     even emit a stored file instead of a stored block (saving 5 bytes).
+		//     This is applicable only for zip (not gzip or zlib).
+		//   - creating new Huffman trees less frequently may not provide fast
+		//     adaptation to changes in the input data statistics. (Take for
+		//     example a binary file with poorly compressible code followed by
+		//     a highly compressible string table.) Smaller buffer sizes give
+		//     fast adaptation but have of course the overhead of transmitting
+		//     trees more frequently.
+		//   - I can't count above 4
+		internal int lit_bufsize;
+		
+		internal int last_lit; // running index in l_buf
+		
+		// Buffer for distances. To simplify the code, d_buf and l_buf have
+		// the same number of elements. To use different lengths, an extra flag
+		// array would be necessary.
+		
+		internal int d_buf; // index of pendig_buf
+		
+		internal int opt_len; // bit length of current block with optimal trees
+		internal int static_len; // bit length of current block with static trees
+		internal int matches; // number of string matches in current block
+		internal int last_eob_len; // bit length of EOB code for last block
+		
+		// Output buffer. bits are inserted starting at the bottom (least
+		// significant bits).
+		internal short bi_buf;
+		
+		// Number of valid bits in bi_buf.  All bits above the last valid bit
+		// are always zero.
+		internal int bi_valid;
+		
+		internal Deflate()
+		{
+			dyn_ltree = new short[HEAP_SIZE * 2];
+			dyn_dtree = new short[(2 * D_CODES + 1) * 2]; // distance tree
+			bl_tree = new short[(2 * BL_CODES + 1) * 2]; // Huffman tree for bit lengths
+		}
+		
+		internal void  lm_init()
+		{
+			window_size = 2 * w_size;
+			
+			head[hash_size - 1] = 0;
+			for (int i = 0; i < hash_size - 1; i++)
+			{
+				head[i] = 0;
+			}
+			
+			// Set the default configuration parameters:
+			max_lazy_match = Deflate.config_table[level].max_lazy;
+			good_match = Deflate.config_table[level].good_length;
+			nice_match = Deflate.config_table[level].nice_length;
+			max_chain_length = Deflate.config_table[level].max_chain;
+			
+			strstart = 0;
+			block_start = 0;
+			lookahead = 0;
+			match_length = prev_length = MIN_MATCH - 1;
+			match_available = 0;
+			ins_h = 0;
+		}
+		
+		// Initialize the tree data structures for a new zlib stream.
+		internal void  tr_init()
+		{
+			
+			l_desc.dyn_tree = dyn_ltree;
+			l_desc.stat_desc = StaticTree.static_l_desc;
+			
+			d_desc.dyn_tree = dyn_dtree;
+			d_desc.stat_desc = StaticTree.static_d_desc;
+			
+			bl_desc.dyn_tree = bl_tree;
+			bl_desc.stat_desc = StaticTree.static_bl_desc;
+			
+			bi_buf = 0;
+			bi_valid = 0;
+			last_eob_len = 8; // enough lookahead for inflate
+			
+			// Initialize the first block of the first file:
+			init_block();
+		}
+		
+		internal void  init_block()
+		{
+			// Initialize the trees.
+			for (int i = 0; i < L_CODES; i++)
+				dyn_ltree[i * 2] = 0;
+			for (int i = 0; i < D_CODES; i++)
+				dyn_dtree[i * 2] = 0;
+			for (int i = 0; i < BL_CODES; i++)
+				bl_tree[i * 2] = 0;
+			
+			dyn_ltree[END_BLOCK * 2] = 1;
+			opt_len = static_len = 0;
+			last_lit = matches = 0;
+		}
+		
+		// Restore the heap property by moving down the tree starting at node k,
+		// exchanging a node with the smallest of its two sons if necessary, stopping
+		// when the heap property is re-established (each father smaller than its
+		// two sons).
+		internal void  pqdownheap(short[] tree, int k)
+		{
+			int v = heap[k];
+			int j = k << 1; // left son of k
+			while (j <= heap_len)
+			{
+				// Set j to the smallest of the two sons:
+				if (j < heap_len && smaller(tree, heap[j + 1], heap[j], depth))
+				{
+					j++;
+				}
+				// Exit if v is smaller than both sons
+				if (smaller(tree, v, heap[j], depth))
+					break;
+				
+				// Exchange v with the smallest son
+				heap[k] = heap[j]; k = j;
+				// And continue down the tree, setting j to the left son of k
+				j <<= 1;
+			}
+			heap[k] = v;
+		}
+		
+		internal static bool smaller(short[] tree, int n, int m, byte[] depth)
+		{
+			return (tree[n * 2] < tree[m * 2] || (tree[n * 2] == tree[m * 2] && depth[n] <= depth[m]));
+		}
+		
+		// Scan a literal or distance tree to determine the frequencies of the codes
+		// in the bit length tree.
+		internal void  scan_tree(short[] tree, int max_code)
+		{
+			int n; // iterates over all tree elements
+			int prevlen = - 1; // last emitted length
+			int curlen; // length of current code
+			int nextlen = tree[0 * 2 + 1]; // length of next code
+			int count = 0; // repeat count of the current code
+			int max_count = 7; // max repeat count
+			int min_count = 4; // min repeat count
+			
+			if (nextlen == 0)
+			{
+				max_count = 138; min_count = 3;
+			}
+			tree[(max_code + 1) * 2 + 1] = (short) SupportClass.Identity(0xffff); // guard
+			
+			for (n = 0; n <= max_code; n++)
+			{
+				curlen = nextlen; nextlen = tree[(n + 1) * 2 + 1];
+				if (++count < max_count && curlen == nextlen)
+				{
+					continue;
+				}
+				else if (count < min_count)
+				{
+					bl_tree[curlen * 2] = (short) (bl_tree[curlen * 2] + count);
+				}
+				else if (curlen != 0)
+				{
+					if (curlen != prevlen)
+						bl_tree[curlen * 2]++;
+					bl_tree[REP_3_6 * 2]++;
+				}
+				else if (count <= 10)
+				{
+					bl_tree[REPZ_3_10 * 2]++;
+				}
+				else
+				{
+					bl_tree[REPZ_11_138 * 2]++;
+				}
+				count = 0; prevlen = curlen;
+				if (nextlen == 0)
+				{
+					max_count = 138; min_count = 3;
+				}
+				else if (curlen == nextlen)
+				{
+					max_count = 6; min_count = 3;
+				}
+				else
+				{
+					max_count = 7; min_count = 4;
+				}
+			}
+		}
+		
+		// Construct the Huffman tree for the bit lengths and return the index in
+		// bl_order of the last bit length code to send.
+		internal int build_bl_tree()
+		{
+			int max_blindex; // index of last bit length code of non zero freq
+			
+			// Determine the bit length frequencies for literal and distance trees
+			scan_tree(dyn_ltree, l_desc.max_code);
+			scan_tree(dyn_dtree, d_desc.max_code);
+			
+			// Build the bit length tree:
+			bl_desc.build_tree(this);
+			// opt_len now includes the length of the tree representations, except
+			// the lengths of the bit lengths codes and the 5+5+4 bits for the counts.
+			
+			// Determine the number of bit length codes to send. The pkzip format
+			// requires that at least 4 bit length codes be sent. (appnote.txt says
+			// 3 but the actual value used is 4.)
+			for (max_blindex = BL_CODES - 1; max_blindex >= 3; max_blindex--)
+			{
+				if (bl_tree[Tree.bl_order[max_blindex] * 2 + 1] != 0)
+					break;
+			}
+			// Update opt_len to include the bit length tree and counts
+			opt_len += 3 * (max_blindex + 1) + 5 + 5 + 4;
+			
+			return max_blindex;
+		}
+		
+		
+		// Send the header for a block using dynamic Huffman trees: the counts, the
+		// lengths of the bit length codes, the literal tree and the distance tree.
+		// IN assertion: lcodes >= 257, dcodes >= 1, blcodes >= 4.
+		internal void  send_all_trees(int lcodes, int dcodes, int blcodes)
+		{
+			int rank; // index in bl_order
+			
+			send_bits(lcodes - 257, 5); // not +255 as stated in appnote.txt
+			send_bits(dcodes - 1, 5);
+			send_bits(blcodes - 4, 4); // not -3 as stated in appnote.txt
+			for (rank = 0; rank < blcodes; rank++)
+			{
+				send_bits(bl_tree[Tree.bl_order[rank] * 2 + 1], 3);
+			}
+			send_tree(dyn_ltree, lcodes - 1); // literal tree
+			send_tree(dyn_dtree, dcodes - 1); // distance tree
+		}
+		
+		// Send a literal or distance tree in compressed form, using the codes in
+		// bl_tree.
+		internal void  send_tree(short[] tree, int max_code)
+		{
+			int n; // iterates over all tree elements
+			int prevlen = - 1; // last emitted length
+			int curlen; // length of current code
+			int nextlen = tree[0 * 2 + 1]; // length of next code
+			int count = 0; // repeat count of the current code
+			int max_count = 7; // max repeat count
+			int min_count = 4; // min repeat count
+			
+			if (nextlen == 0)
+			{
+				max_count = 138; min_count = 3;
+			}
+			
+			for (n = 0; n <= max_code; n++)
+			{
+				curlen = nextlen; nextlen = tree[(n + 1) * 2 + 1];
+				if (++count < max_count && curlen == nextlen)
+				{
+					continue;
+				}
+				else if (count < min_count)
+				{
+					do 
+					{
+						send_code(curlen, bl_tree);
+					}
+					while (--count != 0);
+				}
+				else if (curlen != 0)
+				{
+					if (curlen != prevlen)
+					{
+						send_code(curlen, bl_tree); count--;
+					}
+					send_code(REP_3_6, bl_tree);
+					send_bits(count - 3, 2);
+				}
+				else if (count <= 10)
+				{
+					send_code(REPZ_3_10, bl_tree);
+					send_bits(count - 3, 3);
+				}
+				else
+				{
+					send_code(REPZ_11_138, bl_tree);
+					send_bits(count - 11, 7);
+				}
+				count = 0; prevlen = curlen;
+				if (nextlen == 0)
+				{
+					max_count = 138; min_count = 3;
+				}
+				else if (curlen == nextlen)
+				{
+					max_count = 6; min_count = 3;
+				}
+				else
+				{
+					max_count = 7; min_count = 4;
+				}
+			}
+		}
+		
+		// Output a byte on the stream.
+		// IN assertion: there is enough room in pending_buf.
+		internal void  put_byte(byte[] p, int start, int len)
+		{
+			Array.Copy(p, start, pending_buf, pending, len);
+			pending += len;
+		}
+		
+		internal void  put_byte(byte c)
+		{
+			pending_buf[pending++] = c;
+		}
+		internal void  put_short(int w)
+		{
+			put_byte((byte) (w));
+			put_byte((byte) (SupportClass.URShift(w, 8)));
+		}
+		internal void  putShortMSB(int b)
+		{
+			put_byte((byte) (b >> 8));
+			put_byte((byte) (b));
+		}
+		
+		internal void  send_code(int c, short[] tree)
+		{
+			send_bits((tree[c * 2] & 0xffff), (tree[c * 2 + 1] & 0xffff));
+		}
+		
+		internal void  send_bits(int value_Renamed, int length)
+		{
+			int len = length;
+			if (bi_valid > (int) Buf_size - len)
+			{
+				int val = value_Renamed;
+				//      bi_buf |= (val << bi_valid);
+				bi_buf = (short) ((ushort) bi_buf | (ushort) (((val << bi_valid) & 0xffff)));
+				put_short(bi_buf);
+				bi_buf = (short) (SupportClass.URShift(val, (Buf_size - bi_valid)));
+				bi_valid += len - Buf_size;
+			}
+			else
+			{
+				//      bi_buf |= (value) << bi_valid;
+				bi_buf = (short)((ushort)bi_buf | (ushort)((((value_Renamed) << bi_valid) & 0xffff)));
+				bi_valid += len;
+			}
+		}
+		
+		// Send one empty static block to give enough lookahead for inflate.
+		// This takes 10 bits, of which 7 may remain in the bit buffer.
+		// The current inflate code requires 9 bits of lookahead. If the
+		// last two codes for the previous block (real code plus EOB) were coded
+		// on 5 bits or less, inflate may have only 5+3 bits of lookahead to decode
+		// the last real code. In this case we send two empty static blocks instead
+		// of one. (There are no problems if the previous block is stored or fixed.)
+		// To simplify the code, we assume the worst case of last real code encoded
+		// on one bit only.
+		internal void  _tr_align()
+		{
+			send_bits(STATIC_TREES << 1, 3);
+			send_code(END_BLOCK, StaticTree.static_ltree);
+			
+			bi_flush();
+			
+			// Of the 10 bits for the empty block, we have already sent
+			// (10 - bi_valid) bits. The lookahead for the last real code (before
+			// the EOB of the previous block) was thus at least one plus the length
+			// of the EOB plus what we have just sent of the empty static block.
+			if (1 + last_eob_len + 10 - bi_valid < 9)
+			{
+				send_bits(STATIC_TREES << 1, 3);
+				send_code(END_BLOCK, StaticTree.static_ltree);
+				bi_flush();
+			}
+			last_eob_len = 7;
+		}
+		
+		
+		// Save the match info and tally the frequency counts. Return true if
+		// the current block must be flushed.
+		internal bool _tr_tally(int dist, int lc)
+		{
+			
+			pending_buf[d_buf + last_lit * 2] = (byte) (SupportClass.URShift(dist, 8));
+			pending_buf[d_buf + last_lit * 2 + 1] = (byte) dist;
+			
+			pending_buf[l_buf + last_lit] = (byte) lc; last_lit++;
+			
+			if (dist == 0)
+			{
+				// lc is the unmatched char
+				dyn_ltree[lc * 2]++;
+			}
+			else
+			{
+				matches++;
+				// Here, lc is the match length - MIN_MATCH
+				dist--; // dist = match distance - 1
+				dyn_ltree[(Tree._length_code[lc] + LITERALS + 1) * 2]++;
+				dyn_dtree[Tree.d_code(dist) * 2]++;
+			}
+			
+			if ((last_lit & 0x1fff) == 0 && level > 2)
+			{
+				// Compute an upper bound for the compressed length
+				int out_length = last_lit * 8;
+				int in_length = strstart - block_start;
+				int dcode;
+				for (dcode = 0; dcode < D_CODES; dcode++)
+				{
+					out_length = (int) (out_length + (int) dyn_dtree[dcode * 2] * (5L + Tree.extra_dbits[dcode]));
+				}
+				out_length = SupportClass.URShift(out_length, 3);
+				if ((matches < (last_lit / 2)) && out_length < in_length / 2)
+					return true;
+			}
+			
+			return (last_lit == lit_bufsize - 1);
+			// We avoid equality with lit_bufsize because of wraparound at 64K
+			// on 16 bit machines and because stored blocks are restricted to
+			// 64K-1 bytes.
+		}
+		
+		// Send the block data compressed using the given Huffman trees
+		internal void  compress_block(short[] ltree, short[] dtree)
+		{
+			int dist; // distance of matched string
+			int lc; // match length or unmatched char (if dist == 0)
+			int lx = 0; // running index in l_buf
+			int code; // the code to send
+			int extra; // number of extra bits to send
+			
+			if (last_lit != 0)
+			{
+				do 
+				{
+					dist = ((pending_buf[d_buf + lx * 2] << 8) & 0xff00) | (pending_buf[d_buf + lx * 2 + 1] & 0xff);
+					lc = (pending_buf[l_buf + lx]) & 0xff; lx++;
+					
+					if (dist == 0)
+					{
+						send_code(lc, ltree); // send a literal byte
+					}
+					else
+					{
+						// Here, lc is the match length - MIN_MATCH
+						code = Tree._length_code[lc];
+						
+						send_code(code + LITERALS + 1, ltree); // send the length code
+						extra = Tree.extra_lbits[code];
+						if (extra != 0)
+						{
+							lc -= Tree.base_length[code];
+							send_bits(lc, extra); // send the extra length bits
+						}
+						dist--; // dist is now the match distance - 1
+						code = Tree.d_code(dist);
+						
+						send_code(code, dtree); // send the distance code
+						extra = Tree.extra_dbits[code];
+						if (extra != 0)
+						{
+							dist -= Tree.base_dist[code];
+							send_bits(dist, extra); // send the extra distance bits
+						}
+					} // literal or match pair ?
+					
+					// Check that the overlay between pending_buf and d_buf+l_buf is ok:
+				}
+				while (lx < last_lit);
+			}
+			
+			send_code(END_BLOCK, ltree);
+			last_eob_len = ltree[END_BLOCK * 2 + 1];
+		}
+		
+		// Set the data type to ASCII or BINARY, using a crude approximation:
+		// binary if more than 20% of the bytes are <= 6 or >= 128, ascii otherwise.
+		// IN assertion: the fields freq of dyn_ltree are set and the total of all
+		// frequencies does not exceed 64K (to fit in an int on 16 bit machines).
+		internal void  set_data_type()
+		{
+			int n = 0;
+			int ascii_freq = 0;
+			int bin_freq = 0;
+			while (n < 7)
+			{
+				bin_freq += dyn_ltree[n * 2]; n++;
+			}
+			while (n < 128)
+			{
+				ascii_freq += dyn_ltree[n * 2]; n++;
+			}
+			while (n < LITERALS)
+			{
+				bin_freq += dyn_ltree[n * 2]; n++;
+			}
+			data_type = (byte) (bin_freq > (SupportClass.URShift(ascii_freq, 2))?Z_BINARY:Z_ASCII);
+		}
+		
+		// Flush the bit buffer, keeping at most 7 bits in it.
+		internal void  bi_flush()
+		{
+			if (bi_valid == 16)
+			{
+				put_short(bi_buf);
+				bi_buf = 0;
+				bi_valid = 0;
+			}
+			else if (bi_valid >= 8)
+			{
+				put_byte((byte) bi_buf);
+				bi_buf = (short) (SupportClass.URShift(bi_buf, 8));
+				bi_valid -= 8;
+			}
+		}
+		
+		// Flush the bit buffer and align the output on a byte boundary
+		internal void  bi_windup()
+		{
+			if (bi_valid > 8)
+			{
+				put_short(bi_buf);
+			}
+			else if (bi_valid > 0)
+			{
+				put_byte((byte) bi_buf);
+			}
+			bi_buf = 0;
+			bi_valid = 0;
+		}
+		
+		// Copy a stored block, storing first the length and its
+		// one's complement if requested.
+		internal void  copy_block(int buf, int len, bool header)
+		{
+			
+			bi_windup(); // align on byte boundary
+			last_eob_len = 8; // enough lookahead for inflate
+			
+			if (header)
+			{
+				put_short((short) len);
+				put_short((short) ~ len);
+			}
+			
+			//  while(len--!=0) {
+			//    put_byte(window[buf+index]);
+			//    index++;
+			//  }
+			put_byte(window, buf, len);
+		}
+		
+		internal void  flush_block_only(bool eof)