You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@lucenenet.apache.org by mh...@apache.org on 2014/04/19 01:11:09 UTC

git commit: working towards getting Util/Fst/TestBytesStore working without sbyte

Repository: lucenenet
Updated Branches:
  refs/heads/branch_4x 3de9f9f9d -> 23d1c0ac8


working towards getting Util/Fst/TestBytesStore working without sbyte


Project: http://git-wip-us.apache.org/repos/asf/lucenenet/repo
Commit: http://git-wip-us.apache.org/repos/asf/lucenenet/commit/23d1c0ac
Tree: http://git-wip-us.apache.org/repos/asf/lucenenet/tree/23d1c0ac
Diff: http://git-wip-us.apache.org/repos/asf/lucenenet/diff/23d1c0ac

Branch: refs/heads/branch_4x
Commit: 23d1c0ac8604157b5975db4a8b34ac388b67c982
Parents: 3de9f9f
Author: michael herndon <mh...@investure.com>
Authored: Fri Apr 18 19:10:33 2014 -0400
Committer: michael herndon <mh...@investure.com>
Committed: Fri Apr 18 19:10:33 2014 -0400

----------------------------------------------------------------------
 src/core/Store/DataOutput.cs                    |   6 +
 src/core/Util/Fst/BytesStore.cs                 |  37 ++---
 src/core/Util/Fst/FST.cs                        |   2 +-
 src/core/Util/Fst/ReverseBytesReader.cs         |  11 +-
 test/core/Lucene.Net.Test.csproj                |   9 +-
 test/core/Util/Fst/TestBytesStore.cs            |  55 ++++----
 .../Lucene.Net.TestFramework.csproj             |   3 +
 test/test-framework/LuceneTestCase.cs           | 139 +++++++++++++++++++
 .../Randomized/Attributes/SeedAttribute.cs      |  18 ++-
 .../Attributes/ThreadLeakScopeAttribute.cs      |  19 ++-
 .../Randomized/Generators/RandomInts.cs         |  28 ++++
 .../Randomized/RandomizedContext.cs             |  38 ++++-
 test/test-framework/Randomized/ThreadGroup.cs   |  14 +-
 .../Store/BaseDirectoryWrapper.cs               | 139 +++++++++++++++++++
 .../Store/MockDirectoryWrapper.cs               |  34 +++++
 test/test-framework/Util/_TestUtil.cs           |   4 +
 16 files changed, 497 insertions(+), 59 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/lucenenet/blob/23d1c0ac/src/core/Store/DataOutput.cs
----------------------------------------------------------------------
diff --git a/src/core/Store/DataOutput.cs b/src/core/Store/DataOutput.cs
index 4310f93..9cd515b 100644
--- a/src/core/Store/DataOutput.cs
+++ b/src/core/Store/DataOutput.cs
@@ -11,6 +11,7 @@ namespace Lucene.Net.Store
     {
         public abstract void WriteByte(byte b);
 
+        // TODO: CLSCompliance Remove
         public void WriteBytes(sbyte[] b, int length)
         {
             // helper method to account for java's byte being signed
@@ -22,6 +23,8 @@ namespace Lucene.Net.Store
             WriteBytes((byte[])(Array)b, offset, length);
         }
 
+       
+
         public virtual void WriteBytes(byte[] b, int length)
         {
             WriteBytes(b, 0, length);
@@ -29,6 +32,9 @@ namespace Lucene.Net.Store
 
         public abstract void WriteBytes(byte[] b, int offset, int length);
 
+
+
+        // TODO: CLSCompliance Remove
         public void WriteByte(sbyte b)
         {
             // helper method to account for java's byte being signed

http://git-wip-us.apache.org/repos/asf/lucenenet/blob/23d1c0ac/src/core/Util/Fst/BytesStore.cs
----------------------------------------------------------------------
diff --git a/src/core/Util/Fst/BytesStore.cs b/src/core/Util/Fst/BytesStore.cs
index d441a9b..0ba99a4 100644
--- a/src/core/Util/Fst/BytesStore.cs
+++ b/src/core/Util/Fst/BytesStore.cs
@@ -3,18 +3,19 @@ using Lucene.Net.Support;
 using System;
 using System.Collections.Generic;
 using System.Diagnostics;
+using System.Linq;
 
 namespace Lucene.Net.Util.Fst
 {
     public class BytesStore : DataOutput
     {
-        private readonly List<sbyte[]> blocks = new List<sbyte[]>();
+        private readonly List<byte[]> blocks = new List<byte[]>();
 
         private readonly int blockSize;
         private readonly int blockBits;
         private readonly int blockMask;
 
-        private sbyte[] current;
+        private byte[] current;
         private int nextWrite;
 
         public BytesStore(int blockBits)
@@ -41,7 +42,7 @@ namespace Lucene.Net.Util.Fst
             while (left > 0)
             {
                 var chunk = (int) Math.Min(blockSize, left);
-                var block = new sbyte[chunk];
+                var block = new byte[chunk];
                 input.ReadBytes(block, 0, block.Length);
                 blocks.Add(block);
                 left -= chunk;
@@ -54,7 +55,7 @@ namespace Lucene.Net.Util.Fst
         {
             var blockIndex = dest >> blockBits;
             var block = blocks[blockIndex];
-            block[dest & blockMask] = (sbyte)b;
+            block[dest & blockMask] = b;
         }
 
 
@@ -62,11 +63,11 @@ namespace Lucene.Net.Util.Fst
         {
             if (nextWrite == blockSize)
             {
-                current = new sbyte[blockSize];
+                current = new byte[blockSize];
                 blocks.Add(current);
                 nextWrite = 0;
             }
-            current[nextWrite++] = (sbyte)b;
+            current[nextWrite++] = b;
         }
 
 
@@ -89,7 +90,7 @@ namespace Lucene.Net.Util.Fst
                         offset += chunk;
                         len -= chunk;
                     }
-                    current = new sbyte[blockSize];
+                    current = new byte[blockSize];
                     blocks.Add(current);
                     nextWrite = 0;
                 }
@@ -102,7 +103,9 @@ namespace Lucene.Net.Util.Fst
         }
 
 
-        internal void WriteBytes(long dest, sbyte[] b, int offset, int len)
+       
+
+        internal void WriteBytes(long dest, byte[] b, int offset, int len)
         {
             Debug.Assert(dest + len <= GetPosition(), "dest=" + dest + " pos=" + GetPosition() + " len=" + len);
 
@@ -176,7 +179,7 @@ namespace Lucene.Net.Util.Fst
             var shift = 24;
             for (var i = 0; i < 4; i++)
             {
-                block[upto++] = (sbyte) (value >> shift);
+                block[upto++] =  (byte)(value >> shift);
                 shift -= 8;
                 if (upto == blockSize)
                 {
@@ -238,7 +241,7 @@ namespace Lucene.Net.Util.Fst
                 else
                 {
                     len -= chunk;
-                    current = new sbyte[blockSize];
+                    current = new byte[blockSize];
                     blocks.Add(current);
                     nextWrite = 0;
                 }
@@ -281,7 +284,7 @@ namespace Lucene.Net.Util.Fst
         {
             if (current != null)
             {
-                var lastBuffer = new sbyte[nextWrite];
+                var lastBuffer = new byte[nextWrite];
                 System.Buffer.BlockCopy(current, 0, lastBuffer, 0, nextWrite);
                 blocks[blocks.Count - 1] = lastBuffer;
                 current = null;
@@ -298,7 +301,7 @@ namespace Lucene.Net.Util.Fst
 
         private class AnonForwardBytesReader : FST.BytesReader
         {
-            private sbyte[] current;
+            private byte[] current;
             private int nextBuffer;
             private int nextRead;
 
@@ -373,8 +376,9 @@ namespace Lucene.Net.Util.Fst
         public FST.BytesReader GetForwardReader()
         {
             if (blocks.Count == 1)
-            {
-                return new ForwardBytesReader(blocks[0]);
+            {   
+                // TODO: CLSCompliance
+                return new ForwardBytesReader(blocks[0].Select(o => (sbyte)o).ToArray());
             }
             return new AnonForwardBytesReader(this);
         }
@@ -382,7 +386,7 @@ namespace Lucene.Net.Util.Fst
 
         private class AnonReverseBytesReader : FST.BytesReader
         {
-            private sbyte[] current;
+            private byte[] current;
             private int nextBuffer = -1;
             private int nextRead = 0;
 
@@ -449,7 +453,8 @@ namespace Lucene.Net.Util.Fst
         {
             if (allowSingle && blocks.Count == 1)
             {
-                return new ReverseBytesReader(blocks[0]);
+                var result = blocks[0];
+                return new ReverseBytesReader(result);
             }
             return new AnonReverseBytesReader(this);
         }

http://git-wip-us.apache.org/repos/asf/lucenenet/blob/23d1c0ac/src/core/Util/Fst/FST.cs
----------------------------------------------------------------------
diff --git a/src/core/Util/Fst/FST.cs b/src/core/Util/Fst/FST.cs
index 8b6e302..ea16de8 100644
--- a/src/core/Util/Fst/FST.cs
+++ b/src/core/Util/Fst/FST.cs
@@ -595,7 +595,7 @@ namespace Lucene.Net.Util.Fst
                 }
 
                 // now write the header
-                bytes.WriteBytes(startAddress, (sbyte[])(Array)header, 0, headerLen);
+                bytes.WriteBytes(startAddress, header, 0, headerLen);
             }
 
             var thisNodeAddress = bytes.GetPosition() - 1;

http://git-wip-us.apache.org/repos/asf/lucenenet/blob/23d1c0ac/src/core/Util/Fst/ReverseBytesReader.cs
----------------------------------------------------------------------
diff --git a/src/core/Util/Fst/ReverseBytesReader.cs b/src/core/Util/Fst/ReverseBytesReader.cs
index 2df7b8c..a03978e 100644
--- a/src/core/Util/Fst/ReverseBytesReader.cs
+++ b/src/core/Util/Fst/ReverseBytesReader.cs
@@ -1,11 +1,14 @@
-namespace Lucene.Net.Util.Fst
+
+namespace Lucene.Net.Util.Fst
 {
+    using System;
+
     public class ReverseBytesReader : FST.BytesReader
     {
-        private readonly sbyte[] bytes;
+        private readonly byte[] bytes;
         public override long Position { get; set; }
 
-        public ReverseBytesReader(sbyte[] bytes)
+        public ReverseBytesReader(byte[] bytes)
         {
             this.bytes = bytes;
         }
@@ -19,7 +22,7 @@
         {
             for (var i = 0; i < len; i++)
             {
-                b[offset + i] = (byte)bytes[Position--];
+                b[offset + i] = bytes[Position--];
             }
         }
 

http://git-wip-us.apache.org/repos/asf/lucenenet/blob/23d1c0ac/test/core/Lucene.Net.Test.csproj
----------------------------------------------------------------------
diff --git a/test/core/Lucene.Net.Test.csproj b/test/core/Lucene.Net.Test.csproj
index c5b05d8..34c4c30 100644
--- a/test/core/Lucene.Net.Test.csproj
+++ b/test/core/Lucene.Net.Test.csproj
@@ -177,12 +177,9 @@
       <SpecificVersion>False</SpecificVersion>
       <HintPath>..\..\lib\ICSharpCode\SharpZipLib\0.85\ICSharpCode.SharpZipLib.dll</HintPath>
     </Reference>
-    <Reference Include="nunit.framework">
-      <HintPath>..\..\lib\NUnit.2.6.3\lib\nunit.framework.dll</HintPath>
-    </Reference>
-    <Reference Include="nunit.mocks, Version=2.5.9.10348, Culture=neutral, PublicKeyToken=96d09a1eb7f44a77, processorArchitecture=MSIL">
+    <Reference Include="nunit.framework, Version=2.5.9.10348, Culture=neutral, PublicKeyToken=96d09a1eb7f44a77, processorArchitecture=MSIL">
       <SpecificVersion>False</SpecificVersion>
-      <HintPath>..\..\lib\NUnit.org\NUnit\2.5.9\bin\net-2.0\framework\nunit.mocks.dll</HintPath>
+      <HintPath>..\..\build\vs2013\test\packages\NUnit.2.6.3\lib\nunit.framework.dll</HintPath>
     </Reference>
     <Reference Include="System">
       <Name>System</Name>
@@ -209,6 +206,7 @@
     <Compile Include="Document\TestDateTools.cs" />
     <Compile Include="Document\TestDocument.cs" />
     <Compile Include="SupportClassException.cs" />
+    <Compile Include="Util\Fst\TestBytesStore.cs" />
     <Compile Include="Util\LocalizedTestCase.cs" />
     <None Include="App.config" />
     <None Include="Index\index.19.cfs.zip" />
@@ -278,7 +276,6 @@
     <Folder Include="Store\" />
     <Folder Include="Support\" />
     <Folder Include="Util\Automaton\" />
-    <Folder Include="Util\Fst\" />
     <Folder Include="Util\Packed\" />
   </ItemGroup>
   <ItemGroup>

http://git-wip-us.apache.org/repos/asf/lucenenet/blob/23d1c0ac/test/core/Util/Fst/TestBytesStore.cs
----------------------------------------------------------------------
diff --git a/test/core/Util/Fst/TestBytesStore.cs b/test/core/Util/Fst/TestBytesStore.cs
index df435a2..5e39751 100644
--- a/test/core/Util/Fst/TestBytesStore.cs
+++ b/test/core/Util/Fst/TestBytesStore.cs
@@ -1,26 +1,29 @@
 using System;
 using Lucene.Net.Store;
 using Lucene.Net.Support;
-using Lucene.Net.Test.Support;
 using Lucene.Net.Util;
 using Lucene.Net.Util.Fst;
 using NUnit.Framework;
+using Lucene.Net.Randomized.Generators;
 
 namespace Lucene.Net.Test.Util.Fst
 {
     [TestFixture]
     public class TestBytesStore : LuceneTestCase
     {
+
+        
         [Test]
         public void TestRandom()
         {
 
             int iters = AtLeast(10);
+
             for (var iter = 0; iter < iters; iter++)
             {
-                int numBytes = _TestUtil.NextInt(new Random(), 1, 200000);
-                var expected = new sbyte[numBytes];
-                int blockBits = _TestUtil.NextInt(new Random(), 8, 15);
+                int numBytes = new Random().NextIntBetween(1, 200000);
+                var expected = new byte[numBytes];
+                int blockBits = new Random().NextIntBetween(8, 15);
                 var bytes = new BytesStore(blockBits);
                 if (VERBOSE)
                 {
@@ -41,7 +44,7 @@ namespace Lucene.Net.Test.Util.Fst
                         case 0:
                             {
                                 // write random byte
-                                var b = (sbyte)new Random().Next(256);
+                                var b = (byte)new Random().Next(256);
                                 if (VERBOSE)
                                 {
                                     Console.WriteLine("    writeByte b=" + b);
@@ -80,10 +83,10 @@ namespace Lucene.Net.Test.Util.Fst
                                         Console.WriteLine("    abs writeInt pos=" + randomPos + " x=" + x);
                                     }
                                     bytes.WriteInt(randomPos, x);
-                                    expected[randomPos++] = (sbyte)(x >> 24);
-                                    expected[randomPos++] = (sbyte)(x >> 16);
-                                    expected[randomPos++] = (sbyte)(x >> 8);
-                                    expected[randomPos++] = (sbyte)x;
+                                    expected[randomPos++] = (byte)(x >> 24);
+                                    expected[randomPos++] = (byte)(x >> 16);
+                                    expected[randomPos++] = (byte)(x >> 8);
+                                    expected[randomPos++] = (byte)x;
                                 }
                             }
                             break;
@@ -93,7 +96,7 @@ namespace Lucene.Net.Test.Util.Fst
                                 // reverse bytes
                                 if (pos > 1)
                                 {
-                                    int len = _TestUtil.NextInt(new Random(), 2, Math.Min(100, pos));
+                                    int len = new Random().NextIntBetween(2, Math.Min(100, pos));
                                     int start;
                                     if (len == pos)
                                     {
@@ -128,7 +131,7 @@ namespace Lucene.Net.Test.Util.Fst
                                 if (pos > 2)
                                 {
                                     int randomPos = new Random().Next(pos - 1);
-                                    int len = _TestUtil.NextInt(new Random(), 1, Math.Min(pos - randomPos - 1, 100));
+                                    int len = new Random().NextIntBetween(1, Math.Min(pos - randomPos - 1, 100));
                                     byte[] temp = new byte[len];
                                     new Random().NextBytes(temp);
                                     if (VERBOSE)
@@ -147,8 +150,8 @@ namespace Lucene.Net.Test.Util.Fst
                                 if (pos > 1)
                                 {
                                     int src = new Random().Next(pos - 1);
-                                    int dest = _TestUtil.NextInt(new Random(), src + 1, pos - 1);
-                                    int len = _TestUtil.NextInt(new Random(), 1, Math.Min(300, pos - dest));
+                                    int dest = new Random().NextIntBetween(src + 1, pos - 1);
+                                    int len = new Random().NextIntBetween( 1, Math.Min(300, pos - dest));
                                     if (VERBOSE)
                                     {
                                         Console.WriteLine("    copyBytes src=" + src + " dest=" + dest + " len=" + len);
@@ -176,7 +179,7 @@ namespace Lucene.Net.Test.Util.Fst
                                 // used, else we get false fails:
                                 if (len > 0)
                                 {
-                                    var zeros = new sbyte[len];
+                                    var zeros = new byte[len];
                                     bytes.WriteBytes(pos - len, zeros, 0, len);
                                 }
                             }
@@ -188,7 +191,7 @@ namespace Lucene.Net.Test.Util.Fst
                                 if (pos > 0)
                                 {
                                     var dest = new Random().Next(pos);
-                                    var b = (sbyte)new Random().Next(256);
+                                    var b = (byte)new Random().Next(256);
                                     expected[dest] = b;
                                     bytes.WriteByte(dest, b);
                                 }
@@ -201,10 +204,10 @@ namespace Lucene.Net.Test.Util.Fst
                     if (pos > 0 && new Random().Next(50) == 17)
                     {
                         // truncate
-                        int len = _TestUtil.NextInt(new Random(), 1, Math.Min(pos, 100));
+                        int len = new Random().NextIntBetween(1, Math.Min(pos, 100));
                         bytes.Truncate(pos - len);
                         pos -= len;
-                        Arrays.Fill(expected, pos, pos + len, (sbyte)0);
+                        Arrays.Fill(expected, pos, pos + len, (byte)0);
                         if (VERBOSE)
                         {
                             Console.WriteLine("    truncate len=" + len + " newPos=" + pos);
@@ -219,7 +222,7 @@ namespace Lucene.Net.Test.Util.Fst
 
                 BytesStore bytesToVerify;
 
-                if (new Random().NextBool())
+                if (new Random().NextBoolean())
                 {
                     if (VERBOSE)
                     {
@@ -230,7 +233,7 @@ namespace Lucene.Net.Test.Util.Fst
                     bytes.WriteTo(output);
                     output.Dispose();
                     var input = dir.OpenInput("bytes", IOContext.DEFAULT);
-                    bytesToVerify = new BytesStore(input, numBytes, _TestUtil.NextInt(new Random(), 256, int.MaxValue));
+                    bytesToVerify = new BytesStore(input, numBytes, new Random().NextIntBetween(256, int.MaxValue));
                     input.Dispose();
                     dir.Dispose();
                 }
@@ -243,7 +246,7 @@ namespace Lucene.Net.Test.Util.Fst
             }
         }
 
-        private void Verify(BytesStore bytes, sbyte[] expected, int totalLength)
+        private void Verify(BytesStore bytes, byte[] expected, int totalLength)
         {
             Assert.AreEqual(totalLength, bytes.GetPosition());
             if (totalLength == 0)
@@ -256,8 +259,8 @@ namespace Lucene.Net.Test.Util.Fst
             }
 
             // First verify whole thing in one blast:
-            var actual = new sbyte[totalLength];
-            if (new Random().NextBool())
+            var actual = new byte[totalLength];
+            if (new Random().NextBoolean())
             {
                 if (VERBOSE)
                 {
@@ -299,7 +302,7 @@ namespace Lucene.Net.Test.Util.Fst
             FST.BytesReader r;
 
             // Then verify ops:
-            bool reversed = new Random().NextBool();
+            bool reversed = new Random().NextBoolean();
             if (reversed)
             {
                 if (VERBOSE)
@@ -319,7 +322,7 @@ namespace Lucene.Net.Test.Util.Fst
 
             if (totalLength > 1)
             {
-                int numOps = _TestUtil.NextInt(new Random(), 100, 200);
+                int numOps = new Random().NextIntBetween(100, 200);
                 for (int op = 0; op < numOps; op++)
                 {
 
@@ -327,7 +330,7 @@ namespace Lucene.Net.Test.Util.Fst
                     int pos;
                     if (reversed)
                     {
-                        pos = _TestUtil.NextInt(new Random(), numBytes, totalLength - 1);
+                        pos = new Random().NextIntBetween(numBytes, totalLength - 1);
                     }
                     else
                     {
@@ -343,7 +346,7 @@ namespace Lucene.Net.Test.Util.Fst
                     r.ReadBytes(temp, 0, temp.Length);
                     for (int i = 0; i < numBytes; i++)
                     {
-                        sbyte expectedByte;
+                        byte expectedByte;
                         if (reversed)
                         {
                             expectedByte = expected[pos - i];

http://git-wip-us.apache.org/repos/asf/lucenenet/blob/23d1c0ac/test/test-framework/Lucene.Net.TestFramework.csproj
----------------------------------------------------------------------
diff --git a/test/test-framework/Lucene.Net.TestFramework.csproj b/test/test-framework/Lucene.Net.TestFramework.csproj
index 0416531..0e56061 100644
--- a/test/test-framework/Lucene.Net.TestFramework.csproj
+++ b/test/test-framework/Lucene.Net.TestFramework.csproj
@@ -66,6 +66,7 @@
     <Compile Include="JavaCompatibility\SystemTypesHelpers.cs" />
     <Compile Include="Randomized\Attributes\SeedDecoratorAttribute.cs" />
     <Compile Include="Randomized\Attributes\ThreadLeakScopeAttribute.cs" />
+    <Compile Include="Randomized\Generators\RandomInts.cs" />
     <Compile Include="Randomized\IllegalStateException.cs" />
     <Compile Include="Randomized\InternalAssumptionViolatedException.cs">
       <CustomToolNamespace>In</CustomToolNamespace>
@@ -78,6 +79,8 @@
     <Compile Include="Randomized\SeedUtils.cs" />
     <Compile Include="Randomized\SingleThreadedRandom.cs" />
     <Compile Include="Randomized\ThreadGroup.cs" />
+    <Compile Include="Store\BaseDirectoryWrapper.cs" />
+    <Compile Include="Store\MockDirectoryWrapper.cs" />
     <Compile Include="Support\RandomizedTest.cs" />
     <Compile Include="Support\SystemProperties.cs" />
     <Compile Include="Attributes.cs" />

http://git-wip-us.apache.org/repos/asf/lucenenet/blob/23d1c0ac/test/test-framework/LuceneTestCase.cs
----------------------------------------------------------------------
diff --git a/test/test-framework/LuceneTestCase.cs b/test/test-framework/LuceneTestCase.cs
index dc0bcd4..8586c9c 100644
--- a/test/test-framework/LuceneTestCase.cs
+++ b/test/test-framework/LuceneTestCase.cs
@@ -31,6 +31,7 @@ using Lucene.Net.Search;
 
 using Lucene.Net.TestFramework;
 using Version = Lucene.Net.Util.Version;
+using Lucene.Net.Store;
 
 namespace Lucene.Net
 {
@@ -390,6 +391,127 @@ namespace Lucene.Net
             DumpIterator(label, iter, stream);
         }
 
+
+        /**
+        * Returns true if something should happen rarely,
+        * <p>
+        * The actual number returned will be influenced by whether {@link #TEST_NIGHTLY}
+        * is active and <see cref="RANDOM_MULTIPLIER"/>
+        */
+        public static bool Rarely(Random random)
+        {
+            int p = TEST_NIGHTLY ? 10 : 1;
+            p += (p * (int)Math.Log((double)RANDOM_MULTIPLIER));
+            int min = 100 - Math.Min(p, 50); // never more than 50
+            return random.Next(100) >= min;
+        }
+
+        public static bool Rarely()
+        {
+            return Rarely(new Random());
+        }
+
+        public static BaseDirectoryWrapper NewDirectory()
+        {
+            // return newDirectory(random());
+            return null;
+        }
+
+
+        protected static void Verbose(string message)
+        {
+            if(LuceneTestCase.VERBOSE) {
+                Console.WriteLine(message);
+            }
+        }
+
+        private static BaseDirectoryWrapper WrapDirectory(Random random, Directory directory, bool bare) 
+        {
+            if (Rarely(random)) {
+                directory = new NRTCachingDirectory(directory, random.NextDouble(), random.NextDouble());
+            }
+
+            if (Rarely(random))
+            {
+                double maxMBPerSec = 10 + 5 * (random.NextDouble() - 0.5);
+                if (LuceneTestCase.VERBOSE)
+                {
+                    Verbose("LuceneTestCase: will rate limit output IndexOutput to " + maxMBPerSec + " MB/sec");
+                }
+
+                /*
+                  RateLimitedDirectoryWrapper rateLimitedDirectoryWrapper = new RateLimitedDirectoryWrapper(directory);
+                  switch (random.Next(10)) {
+                    case 3: // sometimes rate limit on flush
+                      rateLimitedDirectoryWrapper.SetMaxWriteMBPerSec(maxMBPerSec, Context.FLUSH);
+                      break;
+                    case 2: // sometimes rate limit flush & merge
+                      rateLimitedDirectoryWrapper.SetMaxWriteMBPerSec(maxMBPerSec, Context.FLUSH);
+                      rateLimitedDirectoryWrapper.SetMaxWriteMBPerSec(maxMBPerSec, Context.MERGE);
+                      break;
+                    default:
+                      rateLimitedDirectoryWrapper.SetMaxWriteMBPerSec(maxMBPerSec, Context.MERGE);
+                  }
+                  directory =  rateLimitedDirectoryWrapper;
+      
+                }
+
+                if (bare) {
+                  var wrapper = new BaseDirectoryWrapper(directory);
+                  closeAfterSuite(new CloseableDirectory(wrapper, suiteFailureMarker));
+                  return wrapper;
+                } else {
+                  var mock = new MockDirectoryWrapper(random, directory);
+      
+                  mock.setThrottling(TEST_THROTTLING);
+                  closeAfterSuite(new CloseableDirectory(mock, suiteFailureMarker));
+                  return mock;
+                }*/
+            }
+            return null;
+      }
+
+        public class Disposable<T> : IDisposable
+            where T:class
+        {
+            private T resource;
+
+            public Disposable(T resource)
+            {
+                this.resource = resource;
+            }
+
+            public void Dispose()
+            {
+                GC.SuppressFinalize(this);
+                this.Dispose(true);
+            }
+
+            protected void Dispose(bool dispose)
+            {
+                if(dispose)
+                {
+                    if(this.resource is IDisposable)
+                    {
+                        ((IDisposable)this.resource).Dispose();
+                    }
+
+                    this.resource = null;
+                }
+            }
+
+            ~Disposable()
+            {
+                this.Dispose(false);
+            }
+        }
+
+        public static Disposable<T> CloseAfterSuite<T>(T resource) where T:class
+        {
+            // maps to random context
+            return new Disposable<T>(resource);
+        }
+
         /// <summary> Returns a {@link Random} instance for generating random numbers during the test.
         /// The random seed is logged during test execution and printed to System.out on any failure
         /// for reproducing the test using {@link #NewRandom(long)} with the recorded seed
@@ -426,6 +548,23 @@ namespace Lucene.Net
         [NonSerialized] private static readonly System.Random seedRnd = new System.Random();
 
 
+        public static int AtLeast(Random random, int minimum)
+        {
+            int min = (TEST_NIGHTLY ? 2 * minimum : minimum) * RANDOM_MULTIPLIER;
+            var max = min + (min / 2);
+            return Randomized.Generators.RandomInts.NextIntBetween(random, min, max);
+        }
+
+        public static int AtLeast(int minimum)
+        {
+            return AtLeast(RandomizedContext.Current.Random, minimum);
+        }
+
+        /// <summary>
+        /// Same as Assert.True, but shorter.
+        /// </summary>
+        /// <param name="condition"></param>
+        /// <param name="message"></param>
         protected static void Ok(bool condition, string message = null)
         {
             if (!string.IsNullOrWhiteSpace(message))

http://git-wip-us.apache.org/repos/asf/lucenenet/blob/23d1c0ac/test/test-framework/Randomized/Attributes/SeedAttribute.cs
----------------------------------------------------------------------
diff --git a/test/test-framework/Randomized/Attributes/SeedAttribute.cs b/test/test-framework/Randomized/Attributes/SeedAttribute.cs
index a2b8c27..e2d65b7 100644
--- a/test/test-framework/Randomized/Attributes/SeedAttribute.cs
+++ b/test/test-framework/Randomized/Attributes/SeedAttribute.cs
@@ -1,4 +1,20 @@
-using System;
+/* 
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ * 
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+using System;
 using System.Collections.Generic;
 using System.Linq;
 using System.Text;

http://git-wip-us.apache.org/repos/asf/lucenenet/blob/23d1c0ac/test/test-framework/Randomized/Attributes/ThreadLeakScopeAttribute.cs
----------------------------------------------------------------------
diff --git a/test/test-framework/Randomized/Attributes/ThreadLeakScopeAttribute.cs b/test/test-framework/Randomized/Attributes/ThreadLeakScopeAttribute.cs
index 5cbe83b..390cbca 100644
--- a/test/test-framework/Randomized/Attributes/ThreadLeakScopeAttribute.cs
+++ b/test/test-framework/Randomized/Attributes/ThreadLeakScopeAttribute.cs
@@ -1,4 +1,21 @@
-using System;
+/* 
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ * 
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+using System;
 using System.Collections.Generic;
 using System.Linq;
 using System.Text;

http://git-wip-us.apache.org/repos/asf/lucenenet/blob/23d1c0ac/test/test-framework/Randomized/Generators/RandomInts.cs
----------------------------------------------------------------------
diff --git a/test/test-framework/Randomized/Generators/RandomInts.cs b/test/test-framework/Randomized/Generators/RandomInts.cs
new file mode 100644
index 0000000..9b88257
--- /dev/null
+++ b/test/test-framework/Randomized/Generators/RandomInts.cs
@@ -0,0 +1,28 @@
+using System;
+using System.Collections.Generic;
+using System.Diagnostics;
+using System.Linq;
+using System.Text;
+
+namespace Lucene.Net.Randomized.Generators
+{
+    public static class RandomInts
+    {
+        public static int NextIntBetween(this Random random, int min, int max)
+        {
+            Debug.Assert(min <= max, String.Format("Min must be less than or equal max int. min: {0}, max: {1}", min, max));
+            var range = max - min;
+            if (range < Int32.MaxValue)
+                return min + random.Next(1 + range);
+           
+            return min + (int)Math.Round(random.NextDouble() * range);
+        }
+
+        public static Boolean NextBoolean(this Random random)
+        {
+            return random.NextDouble() > 0.5;
+        }
+
+        /* .NET has random.Next(max) which negates the need for randomInt(Random random, int max) as  */
+    }
+}

http://git-wip-us.apache.org/repos/asf/lucenenet/blob/23d1c0ac/test/test-framework/Randomized/RandomizedContext.cs
----------------------------------------------------------------------
diff --git a/test/test-framework/Randomized/RandomizedContext.cs b/test/test-framework/Randomized/RandomizedContext.cs
index 6823229..69567be 100644
--- a/test/test-framework/Randomized/RandomizedContext.cs
+++ b/test/test-framework/Randomized/RandomizedContext.cs
@@ -65,6 +65,33 @@ namespace Lucene.Net.Randomized
             }
         }
 
+        public Random Random
+        {
+            get { return this.Randomness.Random; }
+        }
+
+        public Randomness Randomness
+        {
+            get {
+                var randomness = this.PerThreadResources.Queue.Peek();
+                return randomness;
+            }
+        }
+
+        private ThreadResources PerThreadResources
+        {
+            get
+            {
+                this.GuardDiposed();
+                lock (contextLock)
+                {
+                    var resource = threadResources[Thread.CurrentThread];
+
+                    return resource;
+                }
+            }
+        }
+
         private RandomizedContext(ThreadGroup group, Type suiteClass, RandomizedRunner runner)
         {
             this.threadGroup = group;
@@ -92,11 +119,18 @@ namespace Lucene.Net.Randomized
                     else
                         break;
                 }
+
+                // TODO: revisit
+                if(context == null)
+                {
+                    context = contexts[group] = new RandomizedContext(group, null, null);
+
+                }
             }
 
-            if(contexts == null)
+            if(context == null)
             {
-                // TODO: revist
+                // TODO: revisit
                 var message = "No context information for thread," + thread.Name + ". " +
                             "Is this thread running under a " + typeof(RandomizedRunner).Name + " context? ";
 

http://git-wip-us.apache.org/repos/asf/lucenenet/blob/23d1c0ac/test/test-framework/Randomized/ThreadGroup.cs
----------------------------------------------------------------------
diff --git a/test/test-framework/Randomized/ThreadGroup.cs b/test/test-framework/Randomized/ThreadGroup.cs
index cf67783..d63a5ce 100644
--- a/test/test-framework/Randomized/ThreadGroup.cs
+++ b/test/test-framework/Randomized/ThreadGroup.cs
@@ -55,13 +55,23 @@ namespace Lucene.Net.Randomized
     public class ThreadGroup : IEnumerable<WeakReference>, IDisposable
     {
         private List<WeakReference> threads;
-        internal static readonly object GroupLock = new Object();
+        private static object s_groupLock = new Object();
+        internal static object GroupLock
+        {
+            get
+            {
+                if (s_groupLock == null)
+                    s_groupLock = new Object();
+                return s_groupLock;
+            }
+        }
         internal static List<ThreadGroup> Groups {get; set;}
 
         static ThreadGroup()
         {
-            Root = new ThreadGroup("Root");
             Groups = new List<ThreadGroup>();
+            Root = new ThreadGroup("Root");
+           
         }
 
         public static ThreadGroup Root { get; set; }

http://git-wip-us.apache.org/repos/asf/lucenenet/blob/23d1c0ac/test/test-framework/Store/BaseDirectoryWrapper.cs
----------------------------------------------------------------------
diff --git a/test/test-framework/Store/BaseDirectoryWrapper.cs b/test/test-framework/Store/BaseDirectoryWrapper.cs
new file mode 100644
index 0000000..6ce5ab8
--- /dev/null
+++ b/test/test-framework/Store/BaseDirectoryWrapper.cs
@@ -0,0 +1,139 @@
+/* 
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ * 
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+using Lucene.Net.Index;
+using Lucene.Net.Util;
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+
+namespace Lucene.Net.Store
+{
+
+    /**
+     * Calls check index on close.
+     */
+    // do NOT make any methods in this class synchronized, volatile
+    // do NOT import anything from the concurrency package.
+    // no randoms, no nothing.
+    public class BaseDirectoryWrapper : Directory
+    {
+        protected readonly Directory @delegate;
+
+
+        public BaseDirectoryWrapper(Directory @delegate)
+        {
+            this.@delegate = @delegate;
+            this.CheckIndexOnClose = false;
+            this.CrossCheckTermVectorysOnClose = false;
+        }
+
+        public bool CheckIndexOnClose { get; private set; }
+        public bool CrossCheckTermVectorysOnClose {get; private set;}
+
+        public bool IsOpenFlag
+        {
+            get { return this.isOpen; }
+        }
+
+        public override LockFactory LockFactory
+        {
+	       get{ return this.@delegate.LockFactory;}
+           set{this.@delegate.LockFactory = value;}
+        }

        public override string LockId
+        {
+	        get 
+	        { 
+		         return this.@delegate.LockId;
+	        }
+        }
+
+        public override void Copy(Directory to, string src, string dest, IOContext context)
+        {
+ 	         this.@delegate.Copy(to, src, dest, context);
+        }
+
+        public override void ClearLock(string name)
+        {
+ 	         this.@delegate.ClearLock(name);
+        }
+
+        public override Directory.IndexInputSlicer CreateSlicer(string name, IOContext context)
+        {
+ 	
+             return this.@delegate.CreateSlicer(name, context);
+        }
+
+        public override string[] ListAll()
+        {
+            
+            return this.@delegate.ListAll();
+        }
+
+
+        public override Lock MakeLock(string name)
+        {
+ 	         return this.@delegate.MakeLock(name);
+        }
+
+        public override bool FileExists(string name)
+        {
+           return this.@delegate.FileExists(name);
+        }
+
+        public override void DeleteFile(string name)
+        {
+            this.@delegate.DeleteFile(name);
+        }
+
+        public override long FileLength(string name)
+        {
+            return this.@delegate.FileLength(name);
+        }
+
+        public override IndexOutput CreateOutput(string name, IOContext context)
+        {
+            return this.@delegate.CreateOutput(name, context);
+        }
+
+        public override void Sync(ICollection<string> names)
+        {
+           this.@delegate.Sync(names);
+        }
+
+        public override IndexInput OpenInput(string name, IOContext context)
+        {
+           return this.@delegate.OpenInput(name, context); 
+        }
+
+        public override string ToString()
+        {
+ 	         return string.Format("BaseDirectoryWrapper({0})", this.@delegate.ToString());
+        }
+
+        protected override void Dispose(bool disposing)
+        {
+            this.isOpen = false;
+            if(this.CheckIndexOnClose && DirectoryReader.IndexExists(this))
+            {
+                _TestUtil.CheckIndex(this, this.CrossCheckTermVectorysOnClose);
+            }
+            this.@delegate.Dispose();
+        }
+    }
+}

http://git-wip-us.apache.org/repos/asf/lucenenet/blob/23d1c0ac/test/test-framework/Store/MockDirectoryWrapper.cs
----------------------------------------------------------------------
diff --git a/test/test-framework/Store/MockDirectoryWrapper.cs b/test/test-framework/Store/MockDirectoryWrapper.cs
new file mode 100644
index 0000000..03fff25
--- /dev/null
+++ b/test/test-framework/Store/MockDirectoryWrapper.cs
@@ -0,0 +1,34 @@
+/* 
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ * 
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+
+namespace Lucene.Net.Store
+{
+    public class MockDirectoryWrapper : BaseDirectoryWrapper
+    {
+
+        public MockDirectoryWrapper(Random random, Directory @delegate)
+            : base(@delegate)
+        {
+
+        }
+    }
+}

http://git-wip-us.apache.org/repos/asf/lucenenet/blob/23d1c0ac/test/test-framework/Util/_TestUtil.cs
----------------------------------------------------------------------
diff --git a/test/test-framework/Util/_TestUtil.cs b/test/test-framework/Util/_TestUtil.cs
index dd10f5f..ed019ab 100644
--- a/test/test-framework/Util/_TestUtil.cs
+++ b/test/test-framework/Util/_TestUtil.cs
@@ -16,5 +16,9 @@ namespace Lucene.Net.Util
 //    });
 //    Assert.AreEqual(reflectedValues, map, "Reflection does not produce same map");
 //  }
+        internal static void CheckIndex(Store.BaseDirectoryWrapper baseDirectoryWrapper, bool p)
+        {
+            throw new NotImplementedException();
+        }
     }
 }