Skip to content

internal/lsp: fix deadlocks loading lots of files at once #129

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

Closed
wants to merge 1 commit into from

Conversation

muirdm
Copy link
Contributor

@muirdm muirdm commented Jul 3, 2019

The first deadlock involved differing mutex acquisition order in two
code paths:

  1. loadParseTypecheck() holds the "mcache" mutex then eventually
    acquires the "handleMu" file mutex.
  2. (*goFile).invalidateContent() acquires the "handleMu" mutex first and
    then the "mcache" mutex.

Fix by changing the acquisition order in invalidateContent().

The second deadlock involved the file watcher. The two code paths
involved were:

  1. (*goFile).GetPackages() holds the view mutex and eventually calls
    (*WatchMap).Watch, which acquires the watcher mutex.
  2. (*session).openOverlay acquires the watcher mutex as it triggers a
    file's callbacks, and then the callback
    "(*goFile).invalidateContent" acquires the view mutex.

Fix by not holding the watcher mutex as we invoke the callbacks.

Fixes golang/go#32910

The first deadlock involved differing mutex acquisition order in two
code paths:

1. loadParseTypecheck() holds the "mcache" mutex then eventually
   acquires the "handleMu" file mutex.
2. (*goFile).invalidateContent() acquires the "handleMu" mutex first and
   then the "mcache" mutex.

Fix by changing the acquisition order in invalidateContent().

The second deadlock involved the file watcher. The two code paths
involved were:

1. (*goFile).GetPackages() holds the view mutex and eventually gets
   (*WatchMap).Watch, which acquires the watcher mutex.
2. (*session).openOverlay acquires the watcher mutex as it triggers a
   file's callbacks, and then the callback
   "(*goFile).invalidateContent" acquires the vie mutex.

Fix by not holding the watcher mutex as we invoke the callbacks.
@gopherbot
Copy link
Contributor

This PR (HEAD: 04944fa) has been imported to Gerrit for code review.

Please visit https://go-review.googlesource.com/c/tools/+/184880 to see it.

Tip: You can toggle comments from me using the comments slash command (e.g. /comments off)
See the Wiki page for more info

@gopherbot
Copy link
Contributor

Message from Rebecca Stambler:

Patch Set 2: Code-Review+2


Please don’t reply on this GitHub thread. Visit golang.org/cl/184880.
After addressing review feedback, remember to publish your drafts!

@gopherbot
Copy link
Contributor

Message from Rebecca Stambler:

Patch Set 2: Run-TryBot+1

Thank you!


Please don’t reply on this GitHub thread. Visit golang.org/cl/184880.
After addressing review feedback, remember to publish your drafts!

@gopherbot
Copy link
Contributor

Message from Gobot Gobot:

Patch Set 2:

TryBots beginning. Status page: https://farmer.golang.org/try?commit=59c25da1


Please don’t reply on this GitHub thread. Visit golang.org/cl/184880.
After addressing review feedback, remember to publish your drafts!

@gopherbot
Copy link
Contributor

Message from Gobot Gobot:

Patch Set 2: TryBot-Result+1

TryBots are happy.


Please don’t reply on this GitHub thread. Visit golang.org/cl/184880.
After addressing review feedback, remember to publish your drafts!

gopherbot pushed a commit that referenced this pull request Jul 3, 2019
The first deadlock involved differing mutex acquisition order in two
code paths:

1. loadParseTypecheck() holds the "mcache" mutex then eventually
   acquires the "handleMu" file mutex.
2. (*goFile).invalidateContent() acquires the "handleMu" mutex first and
   then the "mcache" mutex.

Fix by changing the acquisition order in invalidateContent().

The second deadlock involved the file watcher. The two code paths
involved were:

1. (*goFile).GetPackages() holds the view mutex and eventually calls
   (*WatchMap).Watch, which acquires the watcher mutex.
2. (*session).openOverlay acquires the watcher mutex as it triggers a
   file's callbacks, and then the callback
   "(*goFile).invalidateContent" acquires the view mutex.

Fix by not holding the watcher mutex as we invoke the callbacks.

Fixes golang/go#32910

Change-Id: I9d060e0d80fd86a317a1d6c7aaa736a8ce10bd07
GitHub-Last-Rev: 04944fa
GitHub-Pull-Request: #129
Reviewed-on: https://go-review.googlesource.com/c/tools/+/184880
Reviewed-by: Rebecca Stambler <[email protected]>
Run-TryBot: Rebecca Stambler <[email protected]>
TryBot-Result: Gobot Gobot <[email protected]>
@gopherbot
Copy link
Contributor

This PR is being closed because golang.org/cl/184880 has been merged.

@gopherbot gopherbot closed this Jul 3, 2019
movie-travel-code pushed a commit to movie-travel-code/tools that referenced this pull request Jul 11, 2019
The first deadlock involved differing mutex acquisition order in two
code paths:

1. loadParseTypecheck() holds the "mcache" mutex then eventually
   acquires the "handleMu" file mutex.
2. (*goFile).invalidateContent() acquires the "handleMu" mutex first and
   then the "mcache" mutex.

Fix by changing the acquisition order in invalidateContent().

The second deadlock involved the file watcher. The two code paths
involved were:

1. (*goFile).GetPackages() holds the view mutex and eventually calls
   (*WatchMap).Watch, which acquires the watcher mutex.
2. (*session).openOverlay acquires the watcher mutex as it triggers a
   file's callbacks, and then the callback
   "(*goFile).invalidateContent" acquires the view mutex.

Fix by not holding the watcher mutex as we invoke the callbacks.

Fixes golang/go#32910

Change-Id: I9d060e0d80fd86a317a1d6c7aaa736a8ce10bd07
GitHub-Last-Rev: 04944fa
GitHub-Pull-Request: golang#129
Reviewed-on: https://go-review.googlesource.com/c/tools/+/184880
Reviewed-by: Rebecca Stambler <[email protected]>
Run-TryBot: Rebecca Stambler <[email protected]>
TryBot-Result: Gobot Gobot <[email protected]>
bsponge added a commit to bsponge/tools that referenced this pull request Sep 30, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

Successfully merging this pull request may close these issues.

x/tools/gopls: deadlock opening many files at once
3 participants