From b1d2844a5e864298112c88e8f00638a939de5e68 Mon Sep 17 00:00:00 2001
From: Hao Kung <HaoK@users.noreply.github.com>
Date: Wed, 4 May 2022 15:45:30 -0700
Subject: [PATCH] release/6.0 port of abort handling (#41360)

---
 src/Servers/IIS/IIS/src/Core/IISHttpContext.IO.cs   |  5 +++++
 src/Servers/IIS/IIS/src/Core/OutputProducer.cs      | 13 ++++++++-----
 .../IIS/IIS/test/IIS.Tests/ResponseAbortTests.cs    |  1 -
 3 files changed, 13 insertions(+), 6 deletions(-)

diff --git a/src/Servers/IIS/IIS/src/Core/IISHttpContext.IO.cs b/src/Servers/IIS/IIS/src/Core/IISHttpContext.IO.cs
index e8ca5be6867..9a456258161 100644
--- a/src/Servers/IIS/IIS/src/Core/IISHttpContext.IO.cs
+++ b/src/Servers/IIS/IIS/src/Core/IISHttpContext.IO.cs
@@ -162,6 +162,11 @@ namespace Microsoft.AspNetCore.Server.IIS.Core
                     var buffer = result.Buffer;
                     try
                     {
+                        if (_bodyOutput.Aborted)
+                        {
+                            break;
+                        }
+
                         if (!buffer.IsEmpty)
                         {
                             await AsyncIO!.WriteAsync(buffer);
diff --git a/src/Servers/IIS/IIS/src/Core/OutputProducer.cs b/src/Servers/IIS/IIS/src/Core/OutputProducer.cs
index 8bf887d1b86..3b52dc8e284 100644
--- a/src/Servers/IIS/IIS/src/Core/OutputProducer.cs
+++ b/src/Servers/IIS/IIS/src/Core/OutputProducer.cs
@@ -13,9 +13,10 @@ namespace Microsoft.AspNetCore.Server.IIS.Core
 {
     internal class OutputProducer
     {
-        // This locks access to _completed.
+        // This locks access to _completed and _aborted.
         private readonly object _contextLock = new object();
         private bool _completed;
+        private volatile bool _aborted;
 
         private readonly Pipe _pipe;
 
@@ -32,6 +33,8 @@ namespace Microsoft.AspNetCore.Server.IIS.Core
         }
 
         public PipeReader Reader => _pipe.Reader;
+        
+        public bool Aborted => _aborted;
 
         public Task FlushAsync(CancellationToken cancellationToken)
         {
@@ -44,7 +47,7 @@ namespace Microsoft.AspNetCore.Server.IIS.Core
         {
             lock (_contextLock)
             {
-                if (_completed)
+                if (_completed || _aborted)
                 {
                     return;
                 }
@@ -58,12 +61,12 @@ namespace Microsoft.AspNetCore.Server.IIS.Core
         {
             lock (_contextLock)
             {
-                if (_completed)
+                if (_completed || _aborted)
                 {
                     return;
                 }
 
-                _completed = true;
+                _aborted = true;
 
                 _pipe.Reader.CancelPendingRead();
                 _pipe.Writer.Complete();
@@ -74,7 +77,7 @@ namespace Microsoft.AspNetCore.Server.IIS.Core
         {
             lock (_contextLock)
             {
-                if (_completed)
+                if (_completed || _aborted)
                 {
                     return Task.CompletedTask;
                 }
diff --git a/src/Servers/IIS/IIS/test/IIS.Tests/ResponseAbortTests.cs b/src/Servers/IIS/IIS/test/IIS.Tests/ResponseAbortTests.cs
index 1cec8d64149..9f8c1dbb6f9 100644
--- a/src/Servers/IIS/IIS/test/IIS.Tests/ResponseAbortTests.cs
+++ b/src/Servers/IIS/IIS/test/IIS.Tests/ResponseAbortTests.cs
@@ -33,7 +33,6 @@ namespace Microsoft.AspNetCore.Server.IIS.FunctionalTests
         }
 
         [ConditionalFact]
-        [QuarantinedTest("https://github.com/dotnet/aspnetcore/issues/31404")]
         public async Task ClosesAfterDataSent()
         {
             var bodyReceived = CreateTaskCompletionSource();
-- 
GitLab