-
Notifications
You must be signed in to change notification settings - Fork 764
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Debug Session stuck for attach remote with Go Debugging on Theia #740
Comments
@quoctruong @polinasok Thanks for inspecting the case thoroughly.
Shouldn't we just fix this part - if we see the delve is in running state and the |
@hyangah @polinasok Correctness-wise, I think Performance-wise, |
This issue is not unique to Theia. I am able to reproduce this problem locally with just vscode on my mac.
Launch with
You can also start the program separate and use Debug configuration:
|
Please also note that the problem does NOT occur if the editor has a breakpoint before the debug session is started. Then as part of the initialization sequence there will be a This might explain why we are not seeing more user complaints for this issue. Users are likely to set all their breakpoints before starting a debug session that will not stop on entry. |
About explicit calls to If the debugger is not running in multi-client mode, we don't need to call this because we always have accurate state from the context and the various calls that we issue to dlv that return state. We can check if we are in this position, with RPCServer.IsMulticlient. In multi-client mode, things get more complicated. We might be connecting to halted or running dlv and must check which one with an explicit call to |
@polinasok Thank you for the follow up. About the |
@quoctruong Agree that optimizing |
Want to add that stackTraceRequest when it cannot be sent to running delve should return an error, so the next waterfall request doesn't kick in. Otherwise, we would need to put another guard for this in ScopesRequest. |
Change https://golang.org/cl/257337 mentions this issue: |
Repro:
--continue
and--accept-multiclient
mode.Why this happens
Important Caveats
continueRequestRunning
to keep track of whether Delve is in a running state or not.Theia's and Delve's Sequence of Events
To understand the root cause, we need to go through the sequences of events from both Theia and Delve's perspective. Note the bolded part as that is crucial to understanding the problem. I also skipped some initial calls when initializing Delve (getVersion). Special thanks to @polinasok for helping debugging the issue and very helpful and detailed discussion of different scenarios.
Initializing Sequence (Not important)
Theia -> DAP: Sends
InitializeRequest
to VSCode Go's Debug Adapter Protocol (DAP) to initialize.Theia <- DAP: Receives a successful response from DAP.
Theia -> DAP: Sends
SetBreakpointsRequest
to DAP to set breakpoints if there are any (also sendssetFunctionBreakpoints
andsetExceptionBreakpoints
if applicable). // <==== this does make a difference - please see explanation belowTheia <- DAP: Receives successful response(s) for those events from DAP.
Post-Initializing Sequence
Theia -> DAP Sends
configurationDoneRequest
to DAP to indicate the end of the configuration.DAP -> Delve: Sends asynchronous call to get Delve's state.
DAP <- Delve: Receives Delve's state and sees that it is running because we started Delve with
--continue
switch. Since this is the case, the code doesn't callthis.continue()
function and this meansthis.continueRequestRunning
is still set tofalse
.Theia <- DAP: Receives response from DAP for the configurationDoneRequest.
Theia -> DAP: Sends
ThreadsRequest
to DAP.DAP -> Delve: Since DAP sees that
this.continueRequestRunning
is still false, DAP thinks that Delve is not in a running state and so it sends a non-asynchronous (BLOCKING) callListGoroutines
to Delve. Since Delve is in a running state, it won't return this call until it changes its state to Halted. However, sinceListGoroutines
is a BLOCKING call, no other requests will get through, including the request to Halt Delve.Theia -> DAP: Sends
setBreakpointsRequest
to DAP, which will not go through.As soon as we fix ThreadsRequest() to bypass the blocking call, the same issue occurs with the next call in the request waterfall to StackTraceRequest()
Remedy
this.continueRequestRunning
, we should issue a non-blocking async call to get Delve's state instead and only fall back tothis.continueRequestRunning
if the call fails.ThreadsRequest
andStacktraceRequest
, we need to make sure Delve's is in a halted state. Otherwise, we are not stopped at a breakpoint and should send back the dummy thread or empty response.The text was updated successfully, but these errors were encountered: