Fix deadlock in GOAWAY_Received_RelievesConnectionBackpressure (#2724)

This commit is contained in:
Stephen Halter 2018-07-16 10:55:09 -07:00 committed by GitHub
parent 429bcfe216
commit 5f065b6670
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
1 changed files with 11 additions and 20 deletions

View File

@ -131,14 +131,23 @@ namespace Microsoft.AspNetCore.Server.Kestrel.Core.Tests
public Http2ConnectionTests()
{
var inlineSchedulingPipeOptions = new PipeOptions(
// Always dispatch test code back to the ThreadPool. This prevents deadlocks caused by continuing
// Http2Connection.ProcessRequestsAsync() loop with writer locks acquired. Run product code inline to make
// it easier to verify request frames are processed correctly immediately after sending the them.
var inputPipeOptions = new PipeOptions(
pool: _memoryPool,
readerScheduler: PipeScheduler.Inline,
writerScheduler: PipeScheduler.ThreadPool,
useSynchronizationContext: false
);
var outputPipeOptions = new PipeOptions(
pool: _memoryPool,
readerScheduler: PipeScheduler.ThreadPool,
writerScheduler: PipeScheduler.Inline,
useSynchronizationContext: false
);
_pair = DuplexPipe.CreateConnectionPair(inlineSchedulingPipeOptions, inlineSchedulingPipeOptions);
_pair = DuplexPipe.CreateConnectionPair(inputPipeOptions, outputPipeOptions);
_noopApplication = context => Task.CompletedTask;
@ -488,12 +497,6 @@ namespace Microsoft.AspNetCore.Server.Kestrel.Core.Tests
withFlags: (byte)Http2DataFrameFlags.END_STREAM,
withStreamId: 3);
// Ensure that Http2FrameWriter._writeLock isn't acquired when completing the frame processing loop.
// Otherwise there's a deadlock where Http2OutputProducer.Abort() being called from the frame processing
// loop blocks waiting Http2OutputProducer.Dispose() being called from the stream processing loop to
// acquire the _writeLock.
await ThreadPoolAwaitable.Instance;
await StopConnectionAsync(expectedLastStreamId: 3, ignoreNonGoAwayFrames: false);
Assert.Equal(stream1DataFrame1.DataPayload, _helloBytes);
@ -565,12 +568,6 @@ namespace Microsoft.AspNetCore.Server.Kestrel.Core.Tests
withFlags: (byte)Http2DataFrameFlags.END_STREAM,
withStreamId: 1);
// Ensure that Http2FrameWriter._writeLock isn't acquired when completing the frame processing loop.
// Otherwise there's a deadlock where Http2OutputProducer.Abort() being called from the frame processing
// loop blocks waiting Http2OutputProducer.Dispose() being called from the stream processing loop to
// acquire the _writeLock.
await ThreadPoolAwaitable.Instance;
await StopConnectionAsync(expectedLastStreamId: 3, ignoreNonGoAwayFrames: false);
}
@ -868,12 +865,6 @@ namespace Microsoft.AspNetCore.Server.Kestrel.Core.Tests
withFlags: (byte)Http2DataFrameFlags.END_STREAM,
withStreamId: 1);
// Ensure that Http2FrameWriter._writeLock isn't acquired when completing the frame processing loop.
// Otherwise there's a deadlock where Http2OutputProducer.Abort() being called from the frame processing
// loop blocks waiting Http2OutputProducer.Dispose() being called from the stream processing loop to
// acquire the _writeLock.
await ThreadPoolAwaitable.Instance;
await StopConnectionAsync(expectedLastStreamId: 3, ignoreNonGoAwayFrames: false);
await WaitForAllStreamsAsync();
}