From 4b11fb634b4218de216e31cdccc55ebefee29946 Mon Sep 17 00:00:00 2001 From: Mikhail Pyltsin Date: Thu, 24 Apr 2025 20:37:43 +0200 Subject: [PATCH] [java] IJ-CR-159341 IDEA-370304 "Go to Declaration and Usages" seems to leak memory in both IntelliJ 2024.2 and 2024.3 (a lot of memory used by java PSI) - move `USE_WEAK_FILE_SCOPE` to `GlobalSearchScope` - IJ-CR-159341 (cherry picked from commit 1e049676158a010d82ac528a15328ea717ba4681) GitOrigin-RevId: 74c5c4e70f02a3c5b159aff1aa7048daf29bb2d6 --- .../intellij/psi/impl/PsiDiamondTypeUtil.java | 4 +-- .../file/impl/ResolveScopeManagerImpl.java | 23 ++-------------- .../psi/search/GlobalSearchScope.java | 26 ++++++++++++++----- .../psi/impl/ResolveScopeManager.java | 12 --------- 4 files changed, 24 insertions(+), 41 deletions(-) diff --git a/java/java-psi-impl/src/com/intellij/psi/impl/PsiDiamondTypeUtil.java b/java/java-psi-impl/src/com/intellij/psi/impl/PsiDiamondTypeUtil.java index 0a001b16f90a..56cebbbb5fdc 100644 --- a/java/java-psi-impl/src/com/intellij/psi/impl/PsiDiamondTypeUtil.java +++ b/java/java-psi-impl/src/com/intellij/psi/impl/PsiDiamondTypeUtil.java @@ -9,6 +9,7 @@ import com.intellij.psi.*; import com.intellij.psi.augment.PsiAugmentProvider; import com.intellij.psi.codeStyle.CodeStyleManager; import com.intellij.psi.infos.MethodCandidateInfo; +import com.intellij.psi.search.GlobalSearchScope; import com.intellij.psi.util.PsiTreeUtil; import com.intellij.psi.util.PsiTypesUtil; import com.intellij.psi.util.PsiUtil; @@ -202,8 +203,7 @@ public final class PsiDiamondTypeUtil { } if (copy != null && copy.getContainingFile() != null) { - ResolveScopeManager resolveScopeManager = ResolveScopeManager.getInstance(context.getProject()); - resolveScopeManager.markFileForWeakScope(copy.getContainingFile().getViewProvider().getVirtualFile()); + GlobalSearchScope.markFileForWeakScope(copy.getContainingFile().getViewProvider().getVirtualFile()); } final PsiCallExpression exprCopy = PsiTreeUtil.getParentOfType(copy, PsiCallExpression.class, false); if (context instanceof PsiMethodReferenceExpression) { diff --git a/platform/analysis-impl/src/com/intellij/psi/impl/file/impl/ResolveScopeManagerImpl.java b/platform/analysis-impl/src/com/intellij/psi/impl/file/impl/ResolveScopeManagerImpl.java index bc96515be391..1a0e421c5116 100644 --- a/platform/analysis-impl/src/com/intellij/psi/impl/file/impl/ResolveScopeManagerImpl.java +++ b/platform/analysis-impl/src/com/intellij/psi/impl/file/impl/ResolveScopeManagerImpl.java @@ -1,10 +1,7 @@ // Copyright 2000-2024 JetBrains s.r.o. and contributors. Use of this source code is governed by the Apache 2.0 license. package com.intellij.psi.impl.file.impl; -import com.intellij.codeInsight.multiverse.CodeInsightContext; -import com.intellij.codeInsight.multiverse.CodeInsightContextKt; -import com.intellij.codeInsight.multiverse.FileViewProviderUtil; -import com.intellij.codeInsight.multiverse.ModuleContext; +import com.intellij.codeInsight.multiverse.*; import com.intellij.ide.scratch.ScratchUtil; import com.intellij.injected.editor.VirtualFileWindow; import com.intellij.openapi.Disposable; @@ -17,7 +14,6 @@ import com.intellij.openapi.roots.ProjectFileIndex; import com.intellij.openapi.roots.ProjectRootManager; import com.intellij.openapi.roots.TestSourcesFilter; import com.intellij.openapi.roots.impl.LibraryScopeCache; -import com.intellij.openapi.util.Key; import com.intellij.openapi.util.Pair; import com.intellij.openapi.vfs.VirtualFile; import com.intellij.openapi.vfs.VirtualFileUtil; @@ -32,7 +28,6 @@ import com.intellij.util.containers.CollectionFactory; import com.intellij.util.containers.ConcurrentFactoryMap; import com.intellij.util.indexing.AdditionalIndexableFileSet; import com.intellij.workspaceModel.core.fileIndex.WorkspaceFileIndex; -import org.jetbrains.annotations.ApiStatus; import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; @@ -49,8 +44,6 @@ final class ResolveScopeManagerImpl extends ResolveScopeManager implements Dispo private final Map, GlobalSearchScope> myDefaultResolveScopesCache; private final AdditionalIndexableFileSet myAdditionalIndexableFileSet; - private static final Key USE_WEAK_FILE_SCOPE = Key.create("virtual.file.use.weak.scope"); - ResolveScopeManagerImpl(Project project) { myProject = project; myProjectRootManager = ProjectRootManager.getInstance(project); @@ -91,12 +84,7 @@ final class ResolveScopeManagerImpl extends ResolveScopeManager implements Dispo } } if (original != null && !scope.contains(key.first)) { - if (key.first.getUserData(USE_WEAK_FILE_SCOPE) == Boolean.TRUE) { - scope = scope.union(GlobalSearchScope.fileWeakScope(myProject, key.first, null)); - } - else { - scope = scope.union(GlobalSearchScope.fileScope(myProject, key.first)); - } + scope = scope.union(GlobalSearchScope.fileScope(myProject, key.first)); } return scope; } @@ -242,13 +230,6 @@ final class ResolveScopeManagerImpl extends ResolveScopeManager implements Dispo return projectFileIndex.getModuleForFile(notNullVFile); } - @ApiStatus.Experimental - @ApiStatus.Internal - @Override - public void markFileForWeakScope(@NotNull VirtualFile file) { - file.putUserData(USE_WEAK_FILE_SCOPE, Boolean.TRUE); - } - @Override public void dispose() { diff --git a/platform/core-api/src/com/intellij/psi/search/GlobalSearchScope.java b/platform/core-api/src/com/intellij/psi/search/GlobalSearchScope.java index 69f21ed73e9f..b5aff1dea4a8 100644 --- a/platform/core-api/src/com/intellij/psi/search/GlobalSearchScope.java +++ b/platform/core-api/src/com/intellij/psi/search/GlobalSearchScope.java @@ -6,6 +6,7 @@ import com.intellij.openapi.fileTypes.FileType; import com.intellij.openapi.module.Module; import com.intellij.openapi.module.UnloadedModuleDescription; import com.intellij.openapi.project.Project; +import com.intellij.openapi.util.Key; import com.intellij.openapi.util.text.StringUtil; import com.intellij.openapi.vfs.VfsUtilCore; import com.intellij.openapi.vfs.VirtualFile; @@ -28,6 +29,7 @@ import java.util.function.Supplier; public abstract class GlobalSearchScope extends SearchScope implements ProjectAwareFileFilter { public static final GlobalSearchScope[] EMPTY_ARRAY = new GlobalSearchScope[0]; private final Project myProject; + private static final Key USE_WEAK_FILE_SCOPE = Key.create("virtual.file.use.weak.scope"); protected GlobalSearchScope(@Nullable Project project) { myProject = project; @@ -244,15 +246,15 @@ public abstract class GlobalSearchScope extends SearchScope implements ProjectAw } @Contract(pure = true) - public static @NotNull GlobalSearchScope fileScope(@NotNull Project project, @Nullable VirtualFile virtualFile, final @Nullable @Nls String displayName) { + public static @NotNull GlobalSearchScope fileScope(@NotNull Project project, + @Nullable VirtualFile virtualFile, + final @Nullable @Nls String displayName) { + if (virtualFile != null && virtualFile.getUserData(USE_WEAK_FILE_SCOPE) == Boolean.TRUE) { + return new FileWeakScope(project, virtualFile, displayName); + } return new FileScope(project, virtualFile, displayName); } - @ApiStatus.Internal - @Contract(pure = true) - public static @NotNull GlobalSearchScope fileWeakScope(@NotNull Project project, @NotNull VirtualFile virtualFile, final @Nullable @Nls String displayName) { - return new FileWeakScope(project, virtualFile, displayName); - } /** * Please consider using {@link #filesWithLibrariesScope} or {@link #filesWithoutLibrariesScope} for optimization @@ -318,6 +320,18 @@ public abstract class GlobalSearchScope extends SearchScope implements ProjectAw return new FileTypeRestrictionScope(scope, fileTypes); } + /** + * Marks a specified file to use a weak file scope. This is useful for modifying + * the scoping mechanism of a file to ensure it is treated under weaker constraints + * than the default resolve scope. It can be used to improve memory consumption. + * + * @param file the virtual file to be marked for weak scope; must not be null + */ + @ApiStatus.Internal + public static void markFileForWeakScope(@NotNull VirtualFile file) { + file.putUserData(USE_WEAK_FILE_SCOPE, Boolean.TRUE); + } + private static class EmptyScope extends GlobalSearchScope { @Override public boolean contains(@NotNull VirtualFile file) { diff --git a/platform/core-impl/src/com/intellij/psi/impl/ResolveScopeManager.java b/platform/core-impl/src/com/intellij/psi/impl/ResolveScopeManager.java index 1bdb9d2fec11..f540def3c469 100644 --- a/platform/core-impl/src/com/intellij/psi/impl/ResolveScopeManager.java +++ b/platform/core-impl/src/com/intellij/psi/impl/ResolveScopeManager.java @@ -6,7 +6,6 @@ import com.intellij.openapi.vfs.VirtualFile; import com.intellij.psi.PsiElement; import com.intellij.psi.PsiFile; import com.intellij.psi.search.GlobalSearchScope; -import org.jetbrains.annotations.ApiStatus; import org.jetbrains.annotations.NotNull; @@ -32,15 +31,4 @@ public abstract class ResolveScopeManager { } return getInstance(element.getProject()).getResolveScope(element); } - - /** - * Marks a specified file to use a weak file scope. This is useful for modifying - * the scoping mechanism of a file to ensure it is treated under weaker constraints - * than the default resolve scope. It can be used to improve memory consumption. - * - * @param file the virtual file to be marked for weak scope; must not be null - */ - @ApiStatus.Experimental - @ApiStatus.Internal - public void markFileForWeakScope(@NotNull VirtualFile file){} }