VS hangs: project options reactor reads the caret through UI-thread COM while the UI thread waits for the reactor
Chưa có ai nhận issue này.
Đánh giá
- Độ khó
- 4/5
- Thời gian dự kiến
- 3-5 ngày
- Mức phù hợp với người mới
- 48/100
- Loại issue
- Lỗi
- Độ rõ ràng
- Khá rõ ràng
- Mức độ hoạt động
- Sôi nổi
- Công nghệ
- fsharp
- Lĩnh vực
- devtools
Hướng nghiên cứu
Bắt đầu trong Common/Extensions.fs và LanguageService/FSharpProjectOptionsManager.fs, lần theo FSharpProjectOptionsReactor.textViewAndCaret qua getProjectOptionsFromScript. Kiểm tra cách ScriptClosure.resolveDependencyManagerSources sử dụng caret và cách các tệp .fs không phải script đăng ký nhận IVsTextViewEvents. Hoàn thành khi reactor không bao giờ chờ UI thread và các tệp không phải script không yêu cầu dữ liệu caret.
Do mô hình lập chỉ mục viết ra từ nội dung của issue.
Mô tả
Visual Studio can hang for good when the project options reactor computes options for a document in F# Miscellaneous Files or for a script while the UI thread synchronously waits for those options. The reactor asks the UI thread for the caret, and the UI thread is blocked waiting for the reactor.
The caret lookup came with #18393, which gave GetProjectOptionsFromScript a caret so that a #r "nuget: …" line is not resolved while it is still being typed (#18231).
Repro steps
Caught once in the debugger, not reproduced on demand. The window is any synchronous UI-thread wait on project options for such a document while the reactor is busy with it. Here it was:
- A solution restored with an F# document tab whose project is not loaded, so the file opened in F# Miscellaneous Files, with breakpoints set in it.
- An extension's
QueryStatusasked the not-yet-loaded frame for its text view, which forcedEnsureDocumentFrameLoaded. - Showing the frame made the debugger validate the breakpoint locations on the UI thread.
Actual behavior
Project options reactor thread:
Microsoft.VisualStudio.Services.VsTask.InternalGetResult
Microsoft.VisualStudio.Shell.ServiceProvider.QueryService
Microsoft.VisualStudio.Shell.ServiceProvider.GetService
Extensions.Document.TryGetIVsTextView Common/Extensions.fs
Extensions.Document.TryGetTextViewAndCaretPos Common/Extensions.fs
FSharpProjectOptionsReactor.textViewAndCaret LanguageService/FSharpProjectOptionsManager.fs
FSharpProjectOptionsReactor.getProjectOptionsFromScript
… tryComputeOptionsBySingleScriptOrFile, started from the reactor's MailboxProcessor loop
UI thread:
Microsoft.VisualStudio.Threading.JoinableTaskFactory.WaitSynchronouslyCore
Microsoft.VisualStudio.Threading.JoinableTask.CompleteOnCurrentThread
AbstractLanguageService<FSharpPackage, FSharpLanguageService>.VsLanguageDebugInfo.ValidateBreakpointLocation
Microsoft.VisualStudio.Platform.WindowManagement.Rdt.NotifyOnBeforeShow
WindowFrame.NotifyFrameShowing / ShowInternal / Show / TryReplacePlaceholderView
WindowFrame.LoadDocumentFrameInternalAsync
WindowFrame.EnsureDocumentFrameLoaded / GetProperty
… an extension's IOleCommandTarget.QueryStatus asking for the active text view
ValidateBreakpointLocation goes through F# breakpoint resolution to the parse results and so to the reactor, which sits on the first stack. ServiceProvider.GlobalProvider.GetService called off the UI thread needs the UI thread, and so do the RDT, IVsTextManager.GetActiveView, IVsTextView.GetCaretPos and the IVsTextViewEvents connection point that follow it. The reactor is a MailboxProcessor, so its work is not joined to the JoinableTask the UI thread waits for, and JTF.Run never runs the request. Switching the reactor to the UI thread with SwitchToMainThreadAsync would hang the same way.
The document here was a plain .fs file, for which the caret is useless: ScriptClosure.resolveDependencyManagerSources is its only reader, and only scripts have #r "nuget: …" lines. The same path also subscribed to IVsTextViewEvents for every such .fs file and recomputed script options on every caret line change.
Expected behavior
The reactor never waits for the UI thread: the UI thread publishes the caret, the reactor reads it, and files that are not scripts do not look for it at all.
Related information
- Windows 11, Visual Studio 18 Insiders, experimental instance
- The code path is unchanged on
main
- Ngôn ngữ chính
- F#
- Star
- 4.3k
- Fork
- 877
- Merge trung bình
- 6 ngày 11 giờ
- Pull request đã merge (30 ngày)
- 150
Hướng dẫn đóng góp
Bắt đầu từ đâu
- Đọc hết issue, rồi đọc hướng dẫn đóng góp của dự án.
- Bình luận trên issue rằng bạn sẽ nhận — tránh hai người làm cùng một việc.
- Fork repository và làm thay đổi trên một nhánh.
- Mở pull request có tham chiếu số hiệu của issue.
Issue khác của dotnet/fsharp
-
Needs-Triage
Độ khó 1/5 Dưới một giờ Mức phù hợp với người mới 90/100
-
Needs-Triage
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 78/100
-
Bug Needs-Triage
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 78/100
-
agentic-workflows
Độ khó 4/5 3-5 ngày Mức phù hợp với người mới 45/100
-
Needs-Triage vs-insertion
Độ khó 5/5 Hơn một tuần Mức phù hợp với người mới 1/100
Tất cả issue của dotnet/fsharp
Issue tương tự
-
[Bug] reef-hermes tells me to resume with hermes --resume, which does not work from my shell Đang mởarea: harness bug status: needs-triage
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 75/100
Human-Agent-Society/reef#625 ·
-
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 75/100
vercel-labs/just-bash#464 ·
-
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 70/100
-
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 75/100
-
Độ khó 2/5 1-3 giờ Mức phù hợp với người mới 75/100