private void FlushWriteBuffer(bool calledFromFinalizer = false)
{
if (_writePos == 0) return;
Debug.Assert(_readPos == 0 && _readLength == 0, "FileStream: Read buffer must be empty in FlushWrite!");
if (_useAsyncIO)
{
Task writeTask = FlushWriteAsync(CancellationToken.None);
// With our Whidbey async IO & overlapped support for AD unloads,
// we don't strictly need to block here to release resources
// since that support takes care of the pinning & freeing the
// overlapped struct. We need to do this when called from
// Close so that the handle is closed when Close returns, but
// we don't need to call EndWrite from the finalizer.
// Additionally, if we do call EndWrite, we block forever
// because AD unloads prevent us from running the managed
// callback from the IO completion port. Blocking here when
// called from the finalizer during AD unload is clearly wrong,
// but we can't use any sort of test for whether the AD is
// unloading because if we weren't unloading, an AD unload
// could happen on a separate thread before we call EndWrite.
if (!calledFromFinalizer)
{
writeTask.GetAwaiter().GetResult();
}
}
else
{
WriteCore(GetBuffer(), 0, _writePos);
}
_writePos = 0;
}