Skip to content

Commit 3dadb06

Browse files
committed
Read buffer fix (DNET-847) (+refactoring).
1 parent cbe87e3 commit 3dadb06

File tree

7 files changed

+71
-134
lines changed

7 files changed

+71
-134
lines changed

Provider/src/FirebirdSql.Data.FirebirdClient/Client/Managed/Version10/GdsArray.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -46,7 +46,7 @@ public override long Handle
4646
set { _handle = value; }
4747
}
4848

49-
public override IDatabase DB
49+
public override IDatabase Database
5050
{
5151
get { return _database; }
5252
set { _database = (GdsDatabase)value; }

Provider/src/FirebirdSql.Data.FirebirdClient/Client/Managed/XdrStream.cs

Lines changed: 64 additions & 47 deletions
Original file line numberDiff line numberDiff line change
@@ -46,7 +46,7 @@ internal class XdrStream : Stream
4646

4747
private long _position;
4848
private List<byte> _outputBuffer;
49-
private ReadBuffer _inputBuffer;
49+
private Queue<byte> _inputBuffer;
5050
private Ionic.Zlib.ZlibCodec _deflate;
5151
private Ionic.Zlib.ZlibCodec _inflate;
5252
private byte[] _compressionBuffer;
@@ -119,7 +119,7 @@ public XdrStream(Stream innerStream, Charset charset, bool compression, bool own
119119

120120
_position = 0;
121121
_outputBuffer = new List<byte>(PreferredBufferSize);
122-
_inputBuffer = new ReadBuffer(PreferredBufferSize);
122+
_inputBuffer = new Queue<byte>(PreferredBufferSize);
123123
if (_compression)
124124
{
125125
_deflate = new Ionic.Zlib.ZlibCodec(Ionic.Zlib.CompressionMode.Compress);
@@ -157,19 +157,7 @@ public override void Flush()
157157
var count = buffer.Length;
158158
if (_compression)
159159
{
160-
_deflate.OutputBuffer = _compressionBuffer;
161-
_deflate.AvailableBytesOut = _compressionBuffer.Length;
162-
_deflate.NextOut = 0;
163-
_deflate.InputBuffer = buffer;
164-
_deflate.AvailableBytesIn = buffer.Length;
165-
_deflate.NextIn = 0;
166-
var rc = _deflate.Deflate(Ionic.Zlib.FlushType.Sync);
167-
if (rc != Ionic.Zlib.ZlibConstants.Z_OK)
168-
throw new IOException($"Error '{rc}' while compressing the data.");
169-
if (_deflate.AvailableBytesIn != 0)
170-
throw new IOException("Compression buffer too small.");
171-
buffer = _compressionBuffer;
172-
count = _deflate.NextOut;
160+
HandleCompression(ref buffer, ref count);
173161
}
174162
try
175163
{
@@ -210,7 +198,7 @@ public override int Read(byte[] buffer, int offset, int count)
210198
CheckDisposed();
211199
EnsureReadable();
212200

213-
if (_inputBuffer.Length < count)
201+
if (_inputBuffer.Count < count)
214202
{
215203
var readBuffer = new byte[PreferredBufferSize];
216204
var read = default(int);
@@ -227,33 +215,22 @@ public override int Read(byte[] buffer, int offset, int count)
227215
{
228216
if (_compression)
229217
{
230-
_inflate.OutputBuffer = _compressionBuffer;
231-
_inflate.AvailableBytesOut = _compressionBuffer.Length;
232-
_inflate.NextOut = 0;
233-
_inflate.InputBuffer = readBuffer;
234-
_inflate.AvailableBytesIn = read;
235-
_inflate.NextIn = 0;
236-
var rc = _inflate.Inflate(Ionic.Zlib.FlushType.None);
237-
if (rc != Ionic.Zlib.ZlibConstants.Z_OK)
238-
throw new IOException($"Error '{rc}' while decompressing the data.");
239-
if (_inflate.AvailableBytesIn != 0)
240-
throw new IOException("Decompression buffer too small.");
241-
readBuffer = _compressionBuffer;
242-
read = _inflate.NextOut;
218+
HandleDecompression(ref readBuffer, ref read);
243219
}
244-
_inputBuffer.AddRange(readBuffer, read);
220+
WriteToInputBuffer(readBuffer, read);
245221
}
246222
}
247-
var dataLength = _inputBuffer.ReadInto(ref buffer, offset, count);
223+
var dataLength = ReadFromInputBuffer(buffer, offset, count);
248224
_position += dataLength;
249225
return dataLength;
250226
}
227+
251228
public override async Task<int> ReadAsync(byte[] buffer, int offset, int count, CancellationToken cancellationToken)
252229
{
253230
CheckDisposed();
254231
EnsureReadable();
255232

256-
if (_inputBuffer.Length < count)
233+
if (_inputBuffer.Count < count)
257234
{
258235
var readBuffer = new byte[PreferredBufferSize];
259236
var read = default(int);
@@ -270,24 +247,12 @@ public override async Task<int> ReadAsync(byte[] buffer, int offset, int count,
270247
{
271248
if (_compression)
272249
{
273-
_inflate.OutputBuffer = _compressionBuffer;
274-
_inflate.AvailableBytesOut = _compressionBuffer.Length;
275-
_inflate.NextOut = 0;
276-
_inflate.InputBuffer = readBuffer;
277-
_inflate.AvailableBytesIn = read;
278-
_inflate.NextIn = 0;
279-
var rc = _inflate.Inflate(Ionic.Zlib.FlushType.None);
280-
if (rc != Ionic.Zlib.ZlibConstants.Z_OK)
281-
throw new IOException($"Error '{rc}' while decompressing the data.");
282-
if (_inflate.AvailableBytesIn != 0)
283-
throw new IOException("Decompression buffer too small.");
284-
readBuffer = _compressionBuffer;
285-
read = _inflate.NextOut;
250+
HandleDecompression(ref readBuffer, ref read);
286251
}
287-
_inputBuffer.AddRange(readBuffer, read);
252+
WriteToInputBuffer(readBuffer, read);
288253
}
289254
}
290-
var dataLength = _inputBuffer.ReadInto(ref buffer, offset, count);
255+
var dataLength = ReadFromInputBuffer(buffer, offset, count);
291256
_position += dataLength;
292257
return dataLength;
293258
}
@@ -746,6 +711,58 @@ private void EnsureReadable()
746711
throw new InvalidOperationException("Read operations are not allowed by this stream.");
747712
}
748713

714+
private int ReadFromInputBuffer(byte[] buffer, int offset, int count)
715+
{
716+
var read = Math.Min(count, _inputBuffer.Count);
717+
for (var i = 0; i < read; i++)
718+
{
719+
buffer[offset + i] = _inputBuffer.Dequeue();
720+
}
721+
return read;
722+
}
723+
724+
private void WriteToInputBuffer(byte[] data, int count)
725+
{
726+
for (var i = 0; i < count; i++)
727+
{
728+
_inputBuffer.Enqueue(data[i]);
729+
}
730+
}
731+
732+
private void HandleDecompression(ref byte[] buffer, ref int count)
733+
{
734+
_inflate.OutputBuffer = _compressionBuffer;
735+
_inflate.AvailableBytesOut = _compressionBuffer.Length;
736+
_inflate.NextOut = 0;
737+
_inflate.InputBuffer = buffer;
738+
_inflate.AvailableBytesIn = count;
739+
_inflate.NextIn = 0;
740+
var rc = _inflate.Inflate(Ionic.Zlib.FlushType.None);
741+
if (rc != Ionic.Zlib.ZlibConstants.Z_OK)
742+
throw new IOException($"Error '{rc}' while decompressing the data.");
743+
if (_inflate.AvailableBytesIn != 0)
744+
throw new IOException("Decompression buffer too small.");
745+
buffer = _compressionBuffer;
746+
count = _inflate.NextOut;
747+
}
748+
749+
private void HandleCompression(ref byte[] buffer, ref int count)
750+
{
751+
_deflate.OutputBuffer = _compressionBuffer;
752+
_deflate.AvailableBytesOut = _compressionBuffer.Length;
753+
_deflate.NextOut = 0;
754+
_deflate.InputBuffer = buffer;
755+
_deflate.AvailableBytesIn = buffer.Length;
756+
_deflate.NextIn = 0;
757+
var rc = _deflate.Deflate(Ionic.Zlib.FlushType.Sync);
758+
if (rc != Ionic.Zlib.ZlibConstants.Z_OK)
759+
throw new IOException($"Error '{rc}' while compressing the data.");
760+
if (_deflate.AvailableBytesIn != 0)
761+
throw new IOException("Compression buffer too small.");
762+
buffer = _compressionBuffer;
763+
count = _deflate.NextOut;
764+
}
765+
749766
private readonly static byte[] PadArray = new byte[] { 0, 0, 0, 0 };
750767
private void WritePad(int length)
751768
{

Provider/src/FirebirdSql.Data.FirebirdClient/Client/Native/FesArray.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -48,7 +48,7 @@ public override long Handle
4848
set { _handle = value; }
4949
}
5050

51-
public override IDatabase DB
51+
public override IDatabase Database
5252
{
5353
get { return _db; }
5454
set { _db = (FesDatabase)value; }

Provider/src/FirebirdSql.Data.FirebirdClient/Common/ArrayBase.cs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -41,7 +41,7 @@ internal abstract class ArrayBase
4141
#region Abstract Properties
4242

4343
public abstract long Handle { get; set; }
44-
public abstract IDatabase DB { get; set; }
44+
public abstract IDatabase Database { get; set; }
4545
public abstract TransactionBase Transaction { get; set; }
4646

4747
#endregion
@@ -96,7 +96,7 @@ public void LookupBounds()
9696
{
9797
LookupDesc();
9898

99-
using (var lookup = DB.CreateStatement(Transaction))
99+
using (var lookup = Database.CreateStatement(Transaction))
100100
{
101101
lookup.Prepare(GetArrayBounds());
102102
lookup.Execute();
@@ -116,7 +116,7 @@ public void LookupBounds()
116116

117117
public void LookupDesc()
118118
{
119-
using (var lookup = DB.CreateStatement(Transaction))
119+
using (var lookup = Database.CreateStatement(Transaction))
120120
{
121121
lookup.Prepare(GetArrayDesc());
122122
lookup.Execute();

Provider/src/FirebirdSql.Data.FirebirdClient/Common/DbValue.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -424,7 +424,7 @@ private Array GetArrayData(long handle)
424424
var gdsArray = _statement.CreateArray(_field.ArrayHandle.Descriptor);
425425

426426
gdsArray.Handle = handle;
427-
gdsArray.DB = _statement.Database;
427+
gdsArray.Database = _statement.Database;
428428
gdsArray.Transaction = _statement.Transaction;
429429

430430
return gdsArray.Read();

Provider/src/FirebirdSql.Data.FirebirdClient/Common/ReadBuffer.cs

Lines changed: 0 additions & 80 deletions
This file was deleted.

Provider/src/FirebirdSql.Data.FirebirdClient/FirebirdClient/FbCommand.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1031,7 +1031,7 @@ private void UpdateParameterValues()
10311031
}
10321032
else
10331033
{
1034-
statementParameter.ArrayHandle.DB = _statement.Database;
1034+
statementParameter.ArrayHandle.Database = _statement.Database;
10351035
statementParameter.ArrayHandle.Transaction = _statement.Transaction;
10361036
}
10371037

0 commit comments

Comments
 (0)