public static async Task <RemoteHostClient?> CreateAsync( Workspace workspace, CancellationToken cancellationToken) { try { using (Logger.LogBlock(FunctionId.ServiceHubRemoteHostClient_CreateAsync, cancellationToken)) { var primary = new HubClient("ManagedLanguage.IDE.RemoteHostClient"); var timeout = TimeSpan.FromMilliseconds(workspace.Options.GetOption(RemoteHostOptions.RequestServiceTimeoutInMS)); // Retry (with timeout) until we can connect to RemoteHost (service hub process). // we are seeing cases where we failed to connect to service hub process when a machine is under heavy load. // (see https://devdiv.visualstudio.com/DevDiv/_workitems/edit/481103 as one of example) var instance = await Connections.RetryRemoteCallAsync <IOException, ServiceHubRemoteHostClient>( workspace, () => CreateWorkerAsync(workspace, primary, timeout, cancellationToken), timeout, cancellationToken).ConfigureAwait(false); instance.Started(); // return instance return(instance); } } catch (SoftCrashException) { // at this point, we should have shown info bar (RemoteHostCrashInfoBar.ShowInfoBar) to users // returning null here will disable OOP for this VS session. // * Note * this is not trying to recover the exception. but giving users to time // to clean up before restart VS return(null); } }
public static async Task <Stream> RequestServiceAsync( Workspace workspace, HubClient client, string serviceName, HostGroup hostGroup, CancellationToken cancellationToken) { const string LogMessage = "Unexpected exception from HubClient"; var descriptor = new ServiceDescriptor(serviceName) { HostGroup = hostGroup }; try { return(await client.RequestServiceAsync(descriptor, cancellationToken).ConfigureAwait(false)); } catch (Exception e) when(ReportNonFatalWatson(e, cancellationToken)) { // TODO: Once https://devdiv.visualstudio.com/DevDiv/_workitems/edit/1040692. // ServiceHub may throw non-cancellation exceptions if it is called after VS started to shut down, // even if our cancellation token is signaled. Cancel the operation and do not report an error in these cases. // // If ServiceHub did not throw non-cancellation exceptions when cancellation token is signaled, // we can assume that these exceptions indicate a failure and should be reported to the user. cancellationToken.ThrowIfCancellationRequested(); client.Logger.TraceEvent(TraceEventType.Error, 1, $"{LogMessage}: {e}"); RemoteHostCrashInfoBar.ShowInfoBar(workspace, e); // TODO: Propagate the original exception (see https://github.com/dotnet/roslyn/issues/40476) throw new SoftCrashException(LogMessage, e, cancellationToken); }
public override bool TryGetWorkspace(ITextBuffer textBuffer, out Workspace workspace) { if (textBuffer == null) { throw new ArgumentNullException(nameof(textBuffer)); } // We do a best effort approach in this method to get the workspace that belongs to the TextBuffer. // Below we try and find the project and then the solution that contains the given text buffer. If // we're able to find both the project and solution then we use the solution to look up the corresponding // Workspace using MonoDevelops TypeSystemService. var hostProject = (DotNetProject)_projectService.GetHostProject(textBuffer); if (hostProject == null) { // Does not have a host project. workspace = null; return(false); } var hostSolution = hostProject.ParentSolution; if (hostSolution == null) { // Project does not have a solution workspace = null; return(false); } return(TryGetWorkspace(hostSolution, out workspace)); }
public RoslynMetadataProviderStub(DTE dte) { var solutionPath = dte.Solution.FullName; var msBuildWorkspace = MSBuildWorkspace.Create(); // ReSharper disable once UnusedVariable var solution = msBuildWorkspace.OpenSolutionAsync(solutionPath).Result; this.workspace = msBuildWorkspace; }
public RoslynProviderStub() { //var componentModel = ServiceProvider.GlobalProvider.GetService(typeof(SComponentModel)) as IComponentModel; //this.workspace = componentModel.GetService<VisualStudioWorkspace>(); var solutionPath = @"C:\Dev\Typewriter\Typewriter\Typewriter.sln"; var msBuildWorkspace = MSBuildWorkspace.Create(); var solution = msBuildWorkspace.OpenSolutionAsync(solutionPath).Result; this.workspace = msBuildWorkspace; }
public static async Task <RemoteHostClient?> CreateAsync(Workspace workspace, CancellationToken cancellationToken) { using (Logger.LogBlock(FunctionId.ServiceHubRemoteHostClient_CreateAsync, cancellationToken)) { var enableConnectionPool = workspace.Options.GetOption(RemoteHostOptions.EnableConnectionPool); var maxConnection = workspace.Options.GetOption(RemoteHostOptions.MaxPoolConnection); // let each client to have unique id so that we can distinguish different clients when service is restarted var clientId = CreateClientId(Process.GetCurrentProcess().Id.ToString()); var hostGroup = new HostGroup(clientId); var hubClient = new HubClient("ManagedLanguage.IDE.RemoteHostClient"); // use the hub client logger for unexpected exceptions from devenv as well, so we have complete information in the log: WatsonReporter.InitializeLogger(hubClient.Logger); // Create the RemotableDataJsonRpc before we create the remote host: this call implicitly sets up the remote IExperimentationService so that will be available for later calls var snapshotServiceStream = await RequestServiceAsync(workspace, hubClient, WellKnownServiceHubServices.SnapshotService, hostGroup, cancellationToken).ConfigureAwait(false); var remoteHostStream = await RequestServiceAsync(workspace, hubClient, WellKnownRemoteHostServices.RemoteHostService, hostGroup, cancellationToken).ConfigureAwait(false); var remotableDataRpc = new RemotableDataJsonRpc(workspace, hubClient.Logger, snapshotServiceStream); var connectionManager = new ConnectionManager(workspace, hubClient, hostGroup, enableConnectionPool, maxConnection, new ReferenceCountedDisposable <RemotableDataJsonRpc>(remotableDataRpc)); var client = new ServiceHubRemoteHostClient(workspace, hubClient.Logger, connectionManager, remoteHostStream); var uiCultureLCID = CultureInfo.CurrentUICulture.LCID; var cultureLCID = CultureInfo.CurrentCulture.LCID; bool success = false; try { // initialize the remote service _ = await client._endPoint.InvokeAsync <string>( nameof(IRemoteHostService.Connect), new object[] { clientId, uiCultureLCID, cultureLCID, TelemetryService.DefaultSession.SerializeSettings() }, cancellationToken).ConfigureAwait(false); success = true; } finally { if (!success) { client.Dispose(); } } client.Started(); return(client); } }
public static async Task <ServiceHubRemoteHostClient> CreateWorkerAsync(Workspace workspace, HubClient primary, TimeSpan timeout, CancellationToken cancellationToken) { ServiceHubRemoteHostClient?client = null; try { // let each client to have unique id so that we can distinguish different clients when service is restarted var current = CreateClientId(Process.GetCurrentProcess().Id.ToString()); var hostGroup = new HostGroup(current); // Create the RemotableDataJsonRpc before we create the remote host: this call implicitly sets up the remote IExperimentationService so that will be available for later calls var remotableDataRpc = new RemotableDataJsonRpc( workspace, primary.Logger, await Connections.RequestServiceAsync(workspace, primary, WellKnownServiceHubServices.SnapshotService, hostGroup, timeout, cancellationToken).ConfigureAwait(false)); var remoteHostStream = await Connections.RequestServiceAsync(workspace, primary, WellKnownRemoteHostServices.RemoteHostService, hostGroup, timeout, cancellationToken).ConfigureAwait(false); var enableConnectionPool = workspace.Options.GetOption(RemoteHostOptions.EnableConnectionPool); var maxConnection = workspace.Options.GetOption(RemoteHostOptions.MaxPoolConnection); var connectionManager = new ConnectionManager(primary, hostGroup, enableConnectionPool, maxConnection, timeout, new ReferenceCountedDisposable <RemotableDataJsonRpc>(remotableDataRpc)); client = new ServiceHubRemoteHostClient(workspace, primary.Logger, connectionManager, remoteHostStream); var uiCultureLCID = CultureInfo.CurrentUICulture.LCID; var cultureLCID = CultureInfo.CurrentCulture.LCID; // make sure connection is done right var host = await client._rpc.InvokeWithCancellationAsync <string>( nameof(IRemoteHostService.Connect), new object[] { current, uiCultureLCID, cultureLCID, TelemetryService.DefaultSession.SerializeSettings() }, cancellationToken).ConfigureAwait(false); return(client); } catch (ConnectionLostException ex) { RemoteHostCrashInfoBar.ShowInfoBar(workspace, ex); Shutdown(client, ex, cancellationToken); // dont crash VS because OOP is failed to start. we will show info bar telling users to restart // but never physically crash VS. throw new SoftCrashException("Connection Lost", ex, cancellationToken); } catch (Exception ex) { Shutdown(client, ex, cancellationToken); throw; }
public RoslynMetadataProviderStub(DTE dte) { var solutionPath = dte.Solution.FullName; var msBuildWorkspace = MSBuildWorkspace.Create(); msBuildWorkspace.OpenSolutionAsync(solutionPath).GetAwaiter().GetResult(); // ReSharper disable once UnusedVariable //ThreadHelper.JoinableTaskFactory.RunAsync(async () => //{ // await msBuildWorkspace.OpenSolutionAsync(solutionPath); //}).Join(); this.workspace = msBuildWorkspace; }
private ServiceHubRemoteHostClient( Workspace workspace, TraceSource logger, ConnectionManager connectionManager, Stream stream) : base(workspace) { _shutdownCancellationTokenSource = new CancellationTokenSource(); _connectionManager = connectionManager; _endPoint = new RemoteEndPoint(stream, logger, incomingCallTarget: this); _endPoint.Disconnected += OnDisconnected; _endPoint.UnexpectedExceptionThrown += OnUnexpectedExceptionThrown; _endPoint.StartListening(); }
internal static void InformDocumentOpen(Microsoft.CodeAnalysis.Workspace ws, Microsoft.CodeAnalysis.DocumentId analysisDocument, TextEditor editor, DocumentContext context) { if (ws == null) { throw new ArgumentNullException(nameof(ws)); } if (analysisDocument == null) { throw new ArgumentNullException(nameof(analysisDocument)); } if (editor == null) { throw new ArgumentNullException(nameof(editor)); } ((MonoDevelopWorkspace)ws).InformDocumentOpen(analysisDocument, editor, context); }
public override bool TryGetWorkspace(ITextBuffer textBuffer, out Workspace workspace) { if (textBuffer == null) { throw new ArgumentNullException(nameof(textBuffer)); } // We do a best effort approach in this method to get the workspace that belongs to the TextBuffer. // Below we try and find the project and then the solution that contains the given text buffer. If // we're able to find both the project and solution then we use the solution to look up the corresponding // Workspace using MonoDevelops TypeSystemService. var hostProject = (DotNetProject)_projectService.GetHostProject(textBuffer); if (hostProject == null) { // Does not have a host project. workspace = null; return(false); } var hostSolution = hostProject.ParentSolution; if (hostSolution == null) { // Project does not have a solution workspace = null; return(false); } workspace = TypeSystemService.GetWorkspace(hostSolution); // Workspace cannot be null at this point. If TypeSystemService.GetWorkspace isn't able to find a corresponding // workspace it returns an empty workspace. Therefore, in order to see if we have a valid workspace we need to // cross-check it against the list of active non-empty workspaces. if (!TypeSystemService.AllWorkspaces.Contains(workspace)) { // We were returned the empty workspace which is equivalent to us not finding a valid workspace for our text buffer. workspace = null; return(false); } return(true); }
private ServiceHubRemoteHostClient( Workspace workspace, TraceSource logger, ConnectionManager connectionManager, Stream stream) : base(workspace) { _shutdownCancellationTokenSource = new CancellationTokenSource(); _connectionManager = connectionManager; _rpc = stream.CreateStreamJsonRpc(target: this, logger); // handle disconnected situation _rpc.Disconnected += OnRpcDisconnected; _rpc.StartListening(); }
public override bool TryGetWorkspace(Solution solution, out Workspace workspace) { if (solution == null) { throw new ArgumentNullException(nameof(solution)); } workspace = TypeSystemService.GetWorkspace(solution); // Workspace cannot be null at this point. If TypeSystemService.GetWorkspace isn't able to find a corresponding // workspace it returns an empty workspace. Therefore, in order to see if we have a valid workspace we need to // cross-check it against the list of active non-empty workspaces. if (!TypeSystemService.AllWorkspaces.Contains(workspace)) { // We were returned the empty workspace which is equivalent to us not finding a valid workspace for our text buffer. workspace = null; return(false); } return(true); }
public RoslynContextActionProvider(Microsoft.CodeAnalysis.Workspace workspace, ICodeFixService codeFixService) { _codeFixService = codeFixService; _workspace = workspace; }
public static async Task <RemoteHostClient?> CreateAsync(Workspace workspace, CancellationToken cancellationToken) { using (Logger.LogBlock(FunctionId.ServiceHubRemoteHostClient_CreateAsync, cancellationToken)) { var timeout = TimeSpan.FromMilliseconds(workspace.Options.GetOption(RemoteHostOptions.RequestServiceTimeoutInMS)); var enableConnectionPool = workspace.Options.GetOption(RemoteHostOptions.EnableConnectionPool); var maxConnection = workspace.Options.GetOption(RemoteHostOptions.MaxPoolConnection); // let each client to have unique id so that we can distinguish different clients when service is restarted var clientId = CreateClientId(Process.GetCurrentProcess().Id.ToString()); var hostGroup = new HostGroup(clientId); var primary = new HubClient("ManagedLanguage.IDE.RemoteHostClient"); ServiceHubRemoteHostClient?client = null; try { // Create the RemotableDataJsonRpc before we create the remote host: this call implicitly sets up the remote IExperimentationService so that will be available for later calls var snapshotServiceStream = await Connections.RequestServiceAsync(workspace, primary, WellKnownServiceHubServices.SnapshotService, hostGroup, timeout, cancellationToken).ConfigureAwait(false); var remoteHostStream = await Connections.RequestServiceAsync(workspace, primary, WellKnownRemoteHostServices.RemoteHostService, hostGroup, timeout, cancellationToken).ConfigureAwait(false); var remotableDataRpc = new RemotableDataJsonRpc(workspace, primary.Logger, snapshotServiceStream); var connectionManager = new ConnectionManager(primary, hostGroup, enableConnectionPool, maxConnection, timeout, new ReferenceCountedDisposable <RemotableDataJsonRpc>(remotableDataRpc)); client = new ServiceHubRemoteHostClient(workspace, primary.Logger, connectionManager, remoteHostStream); var uiCultureLCID = CultureInfo.CurrentUICulture.LCID; var cultureLCID = CultureInfo.CurrentCulture.LCID; // make sure connection is done right var host = await client._rpc.InvokeWithCancellationAsync <string>( nameof(IRemoteHostService.Connect), new object[] { clientId, uiCultureLCID, cultureLCID, TelemetryService.DefaultSession.SerializeSettings() }, cancellationToken).ConfigureAwait(false); client.Started(); return(client); } catch (ConnectionLostException ex) { RemoteHostCrashInfoBar.ShowInfoBar(workspace, ex); Shutdown(ex); // dont crash VS because OOP is failed to start. we will show info bar telling users to restart // but never physically crash VS. return(null); } catch (SoftCrashException ex) { Shutdown(ex); // at this point, we should have shown info bar (RemoteHostCrashInfoBar.ShowInfoBar) to users // returning null here will disable OOP for this VS session. // * Note * this is not trying to recover the exception. but giving users to time // to clean up before restart VS return(null); } catch (Exception ex) { Shutdown(ex); throw; } void Shutdown(Exception ex) { // make sure we shutdown client if initializing client has failed. client?.Shutdown(); // translate to our own cancellation if it is raised. cancellationToken.ThrowIfCancellationRequested(); // otherwise, report watson ex.ReportServiceHubNFW("ServiceHub creation failed"); } } }
internal static void InformDocumentOpen(Microsoft.CodeAnalysis.Workspace ws, Microsoft.CodeAnalysis.DocumentId analysisDocument, TextEditor editor) { ((MonoDevelopWorkspace)ws).InformDocumentOpen(analysisDocument, editor); }
public RoslynMetadataProvider() { var componentModel = ServiceProvider.GlobalProvider.GetService(typeof(SComponentModel)) as IComponentModel; this.workspace = componentModel.GetService<VisualStudioWorkspace>(); }
public RoslynContextActionProvider(Microsoft.CodeAnalysis.Workspace workspace) { _workspace = workspace; }
public abstract bool TryGetWorkspace(Solution solution, out Workspace workspace);