From a21ae5b03ce158fa34479d84366b4031d0deb3db Mon Sep 17 00:00:00 2001 From: Dmitry Batkovich Date: Mon, 22 Mar 2021 18:38:33 +0300 Subject: [PATCH] javac index: do not use read-action in myOpenCloseLock otherwise it leads to deadlocks on index#close() GitOrigin-RevId: fc8af15bb71d20dcf70a1587a66d4e05c1fbc300 --- .../CompilerReferenceServiceBase.java | 31 ++++++++++++++----- .../backwardRefs/DirtyScopeHolder.java | 30 +++++------------- 2 files changed, 32 insertions(+), 29 deletions(-) diff --git a/java/compiler/impl/src/com/intellij/compiler/backwardRefs/CompilerReferenceServiceBase.java b/java/compiler/impl/src/com/intellij/compiler/backwardRefs/CompilerReferenceServiceBase.java index 3976ad40fb21..9ade5e00347d 100644 --- a/java/compiler/impl/src/com/intellij/compiler/backwardRefs/CompilerReferenceServiceBase.java +++ b/java/compiler/impl/src/com/intellij/compiler/backwardRefs/CompilerReferenceServiceBase.java @@ -17,6 +17,7 @@ import com.intellij.openapi.diagnostic.Logger; import com.intellij.openapi.fileEditor.FileDocumentManager; import com.intellij.openapi.fileTypes.FileType; import com.intellij.openapi.module.Module; +import com.intellij.openapi.module.ModuleManager; import com.intellij.openapi.progress.ProcessCanceledException; import com.intellij.openapi.project.Project; import com.intellij.openapi.roots.ProjectFileIndex; @@ -39,6 +40,7 @@ import com.intellij.psi.util.PsiModificationTracker; import com.intellij.psi.util.PsiUtilCore; import com.intellij.util.containers.CollectionFactory; import com.intellij.util.containers.ConcurrentFactoryMap; +import com.intellij.util.containers.ContainerUtil; import com.intellij.util.indexing.StorageException; import com.intellij.util.messages.MessageBusConnection; import it.unimi.dsi.fastutil.ints.IntCollection; @@ -406,16 +408,27 @@ public abstract class CompilerReferenceServiceBase compiledModules = null; + if (reason == IndexOpenReason.COMPILATION_FINISHED) { + compiledModules = ReadAction.nonBlocking(() -> { + if (myProject.isDisposed()) { + return null; + } + final ModuleManager moduleManager = ModuleManager.getInstance(myProject); + return ContainerUtil.map(myDirtyScopeHolder.getCompilationAffectedModules(), moduleManager::findModuleByName); + }).executeSynchronously(); + } + myCompilationCount.increment(); myOpenCloseLock.lock(); try { try { - switch (reason) { - case UP_TO_DATE_CACHE: - myDirtyScopeHolder.upToDateChecked(true); - break; - case COMPILATION_FINISHED: - myDirtyScopeHolder.compilerActivityFinished(); + if (reason == IndexOpenReason.COMPILATION_FINISHED) { + myDirtyScopeHolder.compilerActivityFinished(compiledModules); + } + else if (reason == IndexOpenReason.UP_TO_DATE_CACHE) { + myDirtyScopeHolder.upToDateCheckFinished(Module.EMPTY_ARRAY); } } catch (RuntimeException e) { @@ -433,12 +446,16 @@ public abstract class CompilerReferenceServiceBase myProject.isDisposed() + ? null + : ModuleManager.getInstance(myProject).getModules()); myOpenCloseLock.lock(); try { if (decrementBuildCount) { --myActiveBuilds; } - myDirtyScopeHolder.upToDateChecked(false); + if (modules == null) return; + myDirtyScopeHolder.upToDateCheckFinished(modules); } finally { myOpenCloseLock.unlock(); } diff --git a/java/compiler/impl/src/com/intellij/compiler/backwardRefs/DirtyScopeHolder.java b/java/compiler/impl/src/com/intellij/compiler/backwardRefs/DirtyScopeHolder.java index 7395960157c9..03c5311d5973 100644 --- a/java/compiler/impl/src/com/intellij/compiler/backwardRefs/DirtyScopeHolder.java +++ b/java/compiler/impl/src/com/intellij/compiler/backwardRefs/DirtyScopeHolder.java @@ -109,34 +109,20 @@ public class DirtyScopeHolder extends UserDataHolderBase implements AsyncFileLis } } - public void upToDateChecked(boolean isUpToDate) { - final Module[] modules = ReadAction.compute(() -> { - final Project project = myService.getProject(); - if (project.isDisposed()) { - return null; - } - return ModuleManager.getInstance(project).getModules(); - }); - if (modules == null) return; + void upToDateCheckFinished(Module @NotNull [] modules) { compilationFinished(() -> { - if (!isUpToDate) { - ContainerUtil.addAll(myVFSChangedModules, modules); - } + ContainerUtil.addAll(myVFSChangedModules, modules); }); } - void compilerActivityFinished() { - final List compiledModules = ReadAction.compute(() -> { - final Project project = myService.getProject(); - if (project.isDisposed()) { - return null; - } - final ModuleManager moduleManager = ModuleManager.getInstance(myService.getProject()); - return ContainerUtil.map(myCompilationAffectedModules, moduleManager::findModuleByName); - }); + @NotNull Set getCompilationAffectedModules() { + return myCompilationAffectedModules; + } + + void compilerActivityFinished(List compiledModules) { compilationFinished(() -> { if (compiledModules == null) return; - myVFSChangedModules.removeAll(compiledModules); + compiledModules.forEach(myVFSChangedModules::remove); }); }