Make ReadToEnd static helper resilient against stream.Length changes. (dotnet/corefx...
authorAhson Khan <ahkha@microsoft.com>
Thu, 24 Jan 2019 14:13:05 +0000 (06:13 -0800)
committerStephen Toub <stoub@microsoft.com>
Thu, 24 Jan 2019 14:13:05 +0000 (09:13 -0500)
Commit migrated from https://github.com/dotnet/corefx/commit/49109de03f113bb87117a4e3aaa9ffabc5c06bfb

src/libraries/System.Text.Json/src/System/Text/Json/Document/JsonDocument.Parse.cs

index 9267342..b0feda6 100644 (file)
@@ -180,11 +180,11 @@ namespace System.Text.Json
 
             try
             {
-                long expectedLength = 0;
-
                 if (stream.CanSeek)
                 {
-                    expectedLength = Math.Max(1L, stream.Length - stream.Position);
+                    // Ask for 1 more than the length to avoid resizing later,
+                    // which is unnecessary in the common case where the stream length doesn't change.
+                    long expectedLength = Math.Max(0, stream.Length - stream.Position) + 1;
                     rented = ArrayPool<byte>.Shared.Rent(checked((int)expectedLength));
                 }
                 else
@@ -196,7 +196,7 @@ namespace System.Text.Json
 
                 do
                 {
-                    if (expectedLength == 0 && rented.Length == written)
+                    if (rented.Length == written)
                     {
                         byte[] toReturn = rented;
                         rented = ArrayPool<byte>.Shared.Rent(checked(toReturn.Length * 2));
@@ -239,11 +239,11 @@ namespace System.Text.Json
 
             try
             {
-                long expectedLength = 0;
-
                 if (stream.CanSeek)
                 {
-                    expectedLength = Math.Max(1L, stream.Length - stream.Position);
+                    // Ask for 1 more than the length to avoid resizing later,
+                    // which is unnecessary in the common case where the stream length doesn't change.
+                    long expectedLength = Math.Max(0, stream.Length - stream.Position) + 1;
                     rented = ArrayPool<byte>.Shared.Rent(checked((int)expectedLength));
                 }
                 else
@@ -255,7 +255,7 @@ namespace System.Text.Json
 
                 do
                 {
-                    if (expectedLength == 0 && rented.Length == written)
+                    if (rented.Length == written)
                     {
                         byte[] toReturn = rented;
                         rented = ArrayPool<byte>.Shared.Rent(toReturn.Length * 2);