|
7 | 7 |
|
8 | 8 | namespace MySql.Data.Protocol.Serialization
|
9 | 9 | {
|
10 |
| - internal static class ProtocolUtility |
11 |
| - { |
| 10 | + internal static class ProtocolUtility |
| 11 | + { |
12 | 12 | public static ValueTask<Packet> ReadPacketAsync(BufferedByteReader bufferedByteReader, IByteHandler byteHandler, Func<int> getNextSequenceNumber, ProtocolErrorBehavior protocolErrorBehavior, IOBehavior ioBehavior)
|
13 | 13 | {
|
14 | 14 | var headerBytesTask = bufferedByteReader.ReadBytesAsync(byteHandler, 4, ioBehavior);
|
@@ -135,14 +135,25 @@ public static ValueTask<int> WritePacketAsync(IByteHandler byteHandler, int sequ
|
135 | 135 | SerializationUtility.WriteUInt32((uint) contents.Count, buffer, 0, 3);
|
136 | 136 | buffer[3] = (byte) sequenceNumber;
|
137 | 137 | Buffer.BlockCopy(contents.Array, contents.Offset, buffer, 4, contents.Count);
|
138 |
| - return byteHandler.WriteBytesAsync(new ArraySegment<byte>(buffer, 0, bufferLength), ioBehavior) |
139 |
| - .ContinueWith(x => |
| 138 | + var task = byteHandler.WriteBytesAsync(new ArraySegment<byte>(buffer, 0, bufferLength), ioBehavior); |
| 139 | + if (task.IsCompletedSuccessfully) |
| 140 | + { |
| 141 | + ArrayPool<byte>.Shared.Return(buffer); |
| 142 | + return default(ValueTask<int>); |
| 143 | + } |
| 144 | + return AddContinuation(task, buffer); |
| 145 | + |
| 146 | + // NOTE: use a local function (with no captures) to defer creation of lambda objects |
| 147 | + ValueTask<int> AddContinuation(ValueTask<int> task_, byte[] buffer_) |
| 148 | + { |
| 149 | + return task_.ContinueWith(x => |
140 | 150 | {
|
141 |
| - ArrayPool<byte>.Shared.Return(buffer); |
| 151 | + ArrayPool<byte>.Shared.Return(buffer_); |
142 | 152 | return default(ValueTask<int>);
|
143 | 153 | });
|
| 154 | + } |
144 | 155 | }
|
145 | 156 |
|
146 |
| - public const int MaxPacketSize = 16777215; |
147 |
| - } |
| 157 | + public const int MaxPacketSize = 16777215; |
| 158 | + } |
148 | 159 | }
|
0 commit comments