From b3a62122203026dacc76c178a61ac29d3ff5d119 Mon Sep 17 00:00:00 2001 From: Stephen Toub Date: Wed, 7 Jul 2021 11:21:52 -0400 Subject: [PATCH] Fix length caching --- .../System/IO/Strategies/OSFileStreamStrategy.cs | 13 +++++++++---- 1 file changed, 9 insertions(+), 4 deletions(-) diff --git a/src/libraries/System.Private.CoreLib/src/System/IO/Strategies/OSFileStreamStrategy.cs b/src/libraries/System.Private.CoreLib/src/System/IO/Strategies/OSFileStreamStrategy.cs index dc3429eb4dc5a..2be66fffde521 100644 --- a/src/libraries/System.Private.CoreLib/src/System/IO/Strategies/OSFileStreamStrategy.cs +++ b/src/libraries/System.Private.CoreLib/src/System/IO/Strategies/OSFileStreamStrategy.cs @@ -17,7 +17,7 @@ internal abstract class OSFileStreamStrategy : FileStreamStrategy protected long _filePosition; private long _appendStart; // When appending, prevent overwriting file. - private long _length = -1; // When the file is locked for writes (_share <= FileShare.Read) cache file length in-memory, negative means that hasn't been fetched. + private long _length = -1; // When the file is locked for writes on Windows (_share <= FileShare.Read) cache file length in-memory, negative means that hasn't been fetched. private bool _exposedHandle; // created from handle, or SafeFileHandle was used and the handle got exposed internal OSFileStreamStrategy(SafeFileHandle handle, FileAccess access, FileShare share) @@ -84,7 +84,7 @@ public unsafe sealed override long Length { get { - if (!OperatingSystem.IsWindows() || _share > FileShare.Read || _exposedHandle) + if (!LengthCachingSupported) { return RandomAccess.GetFileLength(_fileHandle); } @@ -105,7 +105,7 @@ protected void UpdateLengthOnChangePosition() { // Do not update the cached length if the file is not locked // or if the length hasn't been fetched. - if (!OperatingSystem.IsWindows() || _share > FileShare.Read || _length < 0 || _exposedHandle) + if (!LengthCachingSupported || _length < 0) { Debug.Assert(_length < 0); return; @@ -117,6 +117,8 @@ protected void UpdateLengthOnChangePosition() } } + private bool LengthCachingSupported => OperatingSystem.IsWindows() && _share <= FileShare.Read && !_exposedHandle; + /// Gets or sets the position within the current stream public sealed override long Position { @@ -235,7 +237,10 @@ protected unsafe void SetLengthCore(long value) Debug.Assert(value >= 0, "value >= 0"); FileStreamHelpers.SetFileLength(_fileHandle, value); - _length = value; + if (LengthCachingSupported) + { + _length = value; + } if (_filePosition > value) {