This is an automated email from the ASF dual-hosted git repository.
paulirwin pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/lucenenet.git
The following commit(s) were added to refs/heads/master by this push:
new d597a5f38 Fix overflow in ByteBlockPool, #1003 (#1055)
d597a5f38 is described below
commit d597a5f38a6a2d78e075545190368735596ddcab
Author: Paul Irwin <[email protected]>
AuthorDate: Tue Dec 3 17:57:07 2024 -0700
Fix overflow in ByteBlockPool, #1003 (#1055)
---
src/Lucene.Net.Tests/Util/TestByteBlockPool.cs | 53 +++++++++++++++++++++++++-
src/Lucene.Net/Util/ByteBlockPool.cs | 6 ++-
2 files changed, 57 insertions(+), 2 deletions(-)
diff --git a/src/Lucene.Net.Tests/Util/TestByteBlockPool.cs
b/src/Lucene.Net.Tests/Util/TestByteBlockPool.cs
index 522f894c8..4e70dd09a 100644
--- a/src/Lucene.Net.Tests/Util/TestByteBlockPool.cs
+++ b/src/Lucene.Net.Tests/Util/TestByteBlockPool.cs
@@ -1,5 +1,7 @@
-using NUnit.Framework;
+using Lucene.Net.Attributes;
+using NUnit.Framework;
using RandomizedTesting.Generators;
+using System;
using System.Collections.Generic;
using JCG = J2N.Collections.Generic;
using Assert = Lucene.Net.TestFramework.Assert;
@@ -68,5 +70,54 @@ namespace Lucene.Net.Util
}
}
}
+
+ [Test]
+ [LuceneNetSpecific] // LUCENENET issue #1003
+ public void TestTooManyAllocs()
+ {
+ // Use a mock allocator that doesn't waste memory
+ ByteBlockPool pool = new ByteBlockPool(new MockAllocator(0));
+ pool.NextBuffer();
+
+ bool throwsException = false;
+ int maxIterations = int.MaxValue / ByteBlockPool.BYTE_BLOCK_SIZE +
1;
+
+ for (int i = 0; i < maxIterations; i++)
+ {
+ try
+ {
+ pool.NextBuffer();
+ }
+ catch (OverflowException)
+ {
+ // The offset overflows on the last attempt to call
NextBuffer()
+ throwsException = true;
+ break;
+ }
+ }
+
+ Assert.IsTrue(throwsException);
+ Assert.IsTrue(pool.ByteOffset + ByteBlockPool.BYTE_BLOCK_SIZE <
pool.ByteOffset);
+ }
+
+ private class MockAllocator : ByteBlockPool.Allocator
+ {
+ private readonly byte[] buffer;
+
+ public MockAllocator(int blockSize) : base(blockSize)
+ {
+ buffer = Array.Empty<byte>();
+ }
+
+ public override void RecycleByteBlocks(byte[][] blocks, int start,
int end)
+ {
+ // No-op
+ }
+
+ public override byte[] GetByteBlock()
+ {
+ return buffer;
+ }
+ }
}
}
diff --git a/src/Lucene.Net/Util/ByteBlockPool.cs
b/src/Lucene.Net/Util/ByteBlockPool.cs
index 898eaf077..a2df7defb 100644
--- a/src/Lucene.Net/Util/ByteBlockPool.cs
+++ b/src/Lucene.Net/Util/ByteBlockPool.cs
@@ -262,7 +262,11 @@ namespace Lucene.Net.Util
bufferUpto++;
ByteUpto = 0;
- ByteOffset += BYTE_BLOCK_SIZE;
+
+ checked // LUCENENET specific - added checked to prevent overflow,
issue #1003
+ {
+ ByteOffset += BYTE_BLOCK_SIZE;
+ }
}
/// <summary>