提交 f3a55ed2 编写于 作者: S Sam Harwell

Apply a hang mitigating timeout to WaitForAllAsyncOperations

上级 8ef458b2
......@@ -2,6 +2,8 @@
using System;
using System.Composition;
using System.Threading;
using System.Threading.Tasks;
using System.Windows.Threading;
using Microsoft.CodeAnalysis.Shared.TestHooks;
using Roslyn.Utilities;
......@@ -35,7 +37,7 @@ public void WaitForAsyncOperations(string featureName, bool waitForWorkspaceFirs
var waitTask = featureWaiter.CreateWaitTask();
WaitForTask(waitTask);
WaitForTask(waitTask, CancellationToken.None);
// Debugging trick: don't let the listeners collection get optimized away during execution.
// This means if the process is killed during integration tests and the test was waiting, you can
......@@ -45,6 +47,11 @@ public void WaitForAsyncOperations(string featureName, bool waitForWorkspaceFirs
}
public void WaitForAllAsyncOperations(params string[] featureNames)
{
WaitForAllAsyncOperations(TimeSpan.FromMilliseconds(-1), featureNames);
}
public void WaitForAllAsyncOperations(TimeSpan timeout, params string[] featureNames)
{
var task = _provider.WaitAllAsync(
featureNames,
......@@ -52,7 +59,17 @@ public void WaitForAllAsyncOperations(params string[] featureNames)
eventProcessingAction: () => Dispatcher.CurrentDispatcher.Invoke(() => { }, DispatcherPriority.ApplicationIdle));
#pragma warning restore VSTHRD001 // Avoid legacy thread switching APIs
WaitForTask(task);
if (timeout == TimeSpan.FromMilliseconds(-1))
{
WaitForTask(task, CancellationToken.None);
}
else
{
using (var cancellationTokenSource = new CancellationTokenSource(timeout))
{
WaitForTask(task, cancellationTokenSource.Token);
}
}
}
public void EnableActiveTokenTracking(bool enable)
......@@ -65,9 +82,9 @@ public void Enable(bool enable)
AsynchronousOperationListenerProvider.Enable(enable);
}
private void WaitForTask(System.Threading.Tasks.Task task)
private void WaitForTask(Task task, CancellationToken cancellationToken)
{
while (!task.Wait(100))
while (!task.Wait(100, cancellationToken))
{
// set breakpoint here when debugging
var tokens = _provider.GetTokens();
......@@ -76,7 +93,7 @@ private void WaitForTask(System.Threading.Tasks.Task task)
// make sure pending task that require UI threads to finish as well.
#pragma warning disable VSTHRD001 // Avoid legacy thread switching APIs
Dispatcher.CurrentDispatcher.Invoke(() => { }, DispatcherPriority.ApplicationIdle);
Dispatcher.CurrentDispatcher.Invoke(() => { }, DispatcherPriority.ApplicationIdle, cancellationToken);
#pragma warning restore VSTHRD001 // Avoid legacy thread switching APIs
}
}
......
......@@ -210,6 +210,7 @@ class C
// Wait for CodingConventions library events to propagate to the workspace
VisualStudio.WaitForApplicationIdle(CancellationToken.None);
VisualStudio.Workspace.WaitForAllAsyncOperations(
Helper.HangMitigatingTimeout,
FeatureAttribute.Workspace,
FeatureAttribute.SolutionCrawler,
FeatureAttribute.DiagnosticService);
......@@ -233,6 +234,7 @@ class C
// Wait for CodingConventions library events to propagate to the workspace
VisualStudio.WaitForApplicationIdle(CancellationToken.None);
VisualStudio.Workspace.WaitForAllAsyncOperations(
Helper.HangMitigatingTimeout,
FeatureAttribute.Workspace,
FeatureAttribute.SolutionCrawler,
FeatureAttribute.DiagnosticService);
......
......@@ -314,6 +314,7 @@ public int X1
*/
VisualStudio.Workspace.WaitForAllAsyncOperations(
Helper.HangMitigatingTimeout,
FeatureAttribute.Workspace,
FeatureAttribute.SolutionCrawler,
FeatureAttribute.DiagnosticService);
......@@ -337,6 +338,7 @@ public int X1
// Wait for CodingConventions library events to propagate to the workspace
VisualStudio.WaitForApplicationIdle(CancellationToken.None);
VisualStudio.Workspace.WaitForAllAsyncOperations(
Helper.HangMitigatingTimeout,
FeatureAttribute.Workspace,
FeatureAttribute.SolutionCrawler,
FeatureAttribute.DiagnosticService);
......@@ -354,6 +356,7 @@ public int X1
// Wait for CodingConventions library events to propagate to the workspace
VisualStudio.WaitForApplicationIdle(CancellationToken.None);
VisualStudio.Workspace.WaitForAllAsyncOperations(
Helper.HangMitigatingTimeout,
FeatureAttribute.Workspace,
FeatureAttribute.SolutionCrawler,
FeatureAttribute.DiagnosticService);
......
......@@ -104,6 +104,7 @@ private void Verify(string marker, ImmutableArray<TextSpan> expectedCount)
{
VisualStudio.Editor.PlaceCaret(marker, charsOffset: -1);
VisualStudio.Workspace.WaitForAllAsyncOperations(
Helper.HangMitigatingTimeout,
FeatureAttribute.Workspace,
FeatureAttribute.SolutionCrawler,
FeatureAttribute.DiagnosticService,
......
......@@ -86,6 +86,7 @@ private void Verify(string marker, IDictionary<string, ImmutableArray<TextSpan>>
{
VisualStudio.Editor.PlaceCaret(marker, charsOffset: -1);
VisualStudio.Workspace.WaitForAllAsyncOperations(
Helper.HangMitigatingTimeout,
FeatureAttribute.Workspace,
FeatureAttribute.SolutionCrawler,
FeatureAttribute.DiagnosticService,
......@@ -109,6 +110,7 @@ private void VerifyNone(string marker)
{
VisualStudio.Editor.PlaceCaret(marker, charsOffset: -1);
VisualStudio.Workspace.WaitForAllAsyncOperations(
Helper.HangMitigatingTimeout,
FeatureAttribute.Workspace,
FeatureAttribute.SolutionCrawler,
FeatureAttribute.DiagnosticService,
......
......@@ -40,6 +40,7 @@ private void Verify(string marker, int expectedCount)
{
VisualStudio.Editor.PlaceCaret(marker, charsOffset: -1);
VisualStudio.Workspace.WaitForAllAsyncOperations(
Helper.HangMitigatingTimeout,
FeatureAttribute.Workspace,
FeatureAttribute.SolutionCrawler,
FeatureAttribute.DiagnosticService,
......
......@@ -46,6 +46,7 @@ private void Verify(string marker, IDictionary<string, ImmutableArray<TextSpan>>
{
VisualStudio.Editor.PlaceCaret(marker, charsOffset: -1);
VisualStudio.Workspace.WaitForAllAsyncOperations(
Helper.HangMitigatingTimeout,
FeatureAttribute.Workspace,
FeatureAttribute.SolutionCrawler,
FeatureAttribute.DiagnosticService,
......@@ -61,6 +62,7 @@ private void VerifyNone(string marker)
{
VisualStudio.Editor.PlaceCaret(marker, charsOffset: -1);
VisualStudio.Workspace.WaitForAllAsyncOperations(
Helper.HangMitigatingTimeout,
FeatureAttribute.Workspace,
FeatureAttribute.SolutionCrawler,
FeatureAttribute.DiagnosticService,
......
......@@ -123,8 +123,8 @@ private static TestingOnly_WaitingService GetWaitingService()
public void WaitForAsyncOperations(string featuresToWaitFor, bool waitForWorkspaceFirst = true)
=> GetWaitingService().WaitForAsyncOperations(featuresToWaitFor, waitForWorkspaceFirst);
public void WaitForAllAsyncOperations(params string[] featureNames)
=> GetWaitingService().WaitForAllAsyncOperations(featureNames);
public void WaitForAllAsyncOperations(TimeSpan timeout, params string[] featureNames)
=> GetWaitingService().WaitForAllAsyncOperations(timeout, featureNames);
private static void LoadRoslynPackage()
{
......
......@@ -50,8 +50,8 @@ public void SetOption(string optionName, string feature, object value)
public void WaitForAsyncOperations(string featuresToWaitFor, bool waitForWorkspaceFirst = true)
=> _inProc.WaitForAsyncOperations(featuresToWaitFor, waitForWorkspaceFirst);
public void WaitForAllAsyncOperations(params string[] featureNames)
=> _inProc.WaitForAllAsyncOperations(featureNames);
public void WaitForAllAsyncOperations(TimeSpan timeout, params string[] featureNames)
=> _inProc.WaitForAllAsyncOperations(timeout, featureNames);
public void CleanUpWorkspace()
=> _inProc.CleanUpWorkspace();
......
......@@ -194,7 +194,7 @@ public void CleanUp()
Workspace.CleanUpWaitingService();
Workspace.CleanUpWorkspace();
SolutionExplorer.CleanUpOpenSolution();
Workspace.WaitForAllAsyncOperations();
Workspace.WaitForAllAsyncOperations(Helper.HangMitigatingTimeout);
// Close any windows leftover from previous (failed) tests
InteractiveWindow.CloseInteractiveWindow();
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册