From d45fb3f67233cd3567a43aa47d7da10021231ed1 Mon Sep 17 00:00:00 2001 From: "Egor.Ushakov" Date: Fri, 14 Nov 2014 21:02:10 +0300 Subject: [PATCH] inline debugger: fixed slow variables tree update due to lots of sourcePosition requests in the debugger thread, also do not show fields values at the declaration for not "this" objects --- .../debugger/engine/JavaStackFrame.java | 36 +------------------ .../intellij/debugger/engine/JavaValue.java | 7 ++++ .../debugger/impl/DebuggerContextUtil.java | 4 +-- .../debugger/impl/DebuggerUtilsEx.java | 34 +++++++++++++++++- .../impl/IdentifierHighlighterPass.java | 20 ++++++----- .../frame/XInlineSourcePosition.java | 22 ++++++++++++ .../frame/XNearestSourcePosition.java | 2 +- .../xdebugger/impl/ui/tree/XDebuggerTree.java | 25 +------------ .../impl/ui/tree/nodes/XValueNodeImpl.java | 9 +++-- 9 files changed, 84 insertions(+), 75 deletions(-) create mode 100644 platform/xdebugger-api/src/com/intellij/xdebugger/frame/XInlineSourcePosition.java diff --git a/java/debugger/impl/src/com/intellij/debugger/engine/JavaStackFrame.java b/java/debugger/impl/src/com/intellij/debugger/engine/JavaStackFrame.java index 463243a0d419..913f64ead071 100644 --- a/java/debugger/impl/src/com/intellij/debugger/engine/JavaStackFrame.java +++ b/java/debugger/impl/src/com/intellij/debugger/engine/JavaStackFrame.java @@ -34,19 +34,15 @@ import com.intellij.debugger.ui.tree.render.ClassRenderer; import com.intellij.debugger.ui.tree.render.DescriptorLabelListener; import com.intellij.openapi.application.ApplicationManager; import com.intellij.openapi.diagnostic.Logger; -import com.intellij.openapi.project.Project; import com.intellij.openapi.util.Computable; import com.intellij.openapi.util.Pair; import com.intellij.openapi.util.text.StringUtil; -import com.intellij.openapi.vfs.VirtualFile; -import com.intellij.pom.Navigatable; import com.intellij.ui.ColoredTextContainer; import com.intellij.xdebugger.XDebugSession; import com.intellij.xdebugger.XSourcePosition; import com.intellij.xdebugger.evaluation.XDebuggerEvaluator; import com.intellij.xdebugger.frame.*; import com.intellij.xdebugger.frame.presentation.XValuePresentation; -import com.intellij.xdebugger.impl.XSourcePositionImpl; import com.intellij.xdebugger.impl.ui.XDebuggerUIConstants; import com.intellij.xdebugger.settings.XDebuggerSettingsManager; import com.sun.jdi.*; @@ -89,7 +85,7 @@ public class JavaStackFrame extends XStackFrame { myEqualityObject = update ? NodeManagerImpl.getContextKeyForFrame(myDescriptor.getFrameProxy()) : null; myDebugProcess = ((DebugProcessImpl)descriptor.getDebugProcess()); myNodeManager = myDebugProcess.getXdebugProcess().getNodeManager(); - myXSourcePosition = myDescriptor.getSourcePosition() != null ? new JavaXSourcePosition(myDescriptor.getSourcePosition()) : null; + myXSourcePosition = myDescriptor.getSourcePosition() != null ? DebuggerUtilsEx.toXSourcePosition(myDescriptor.getSourcePosition()) : null; } @NotNull @@ -401,34 +397,4 @@ public class JavaStackFrame extends XStackFrame { return "JavaFrame position unknown"; } } - - private static class JavaXSourcePosition implements XSourcePosition { - private final SourcePosition mySourcePosition; - - public JavaXSourcePosition(@NotNull SourcePosition sourcePosition) { - mySourcePosition = sourcePosition; - } - - @Override - public int getLine() { - return mySourcePosition.getLine(); - } - - @Override - public int getOffset() { - return mySourcePosition.getOffset(); - } - - @NotNull - @Override - public VirtualFile getFile() { - return mySourcePosition.getFile().getVirtualFile(); - } - - @NotNull - @Override - public Navigatable createNavigatable(@NotNull Project project) { - return XSourcePositionImpl.createOpenFileDescriptor(project, this); - } - } } diff --git a/java/debugger/impl/src/com/intellij/debugger/engine/JavaValue.java b/java/debugger/impl/src/com/intellij/debugger/engine/JavaValue.java index 43232ce3fd2d..12cafe763fe0 100644 --- a/java/debugger/impl/src/com/intellij/debugger/engine/JavaValue.java +++ b/java/debugger/impl/src/com/intellij/debugger/engine/JavaValue.java @@ -377,9 +377,16 @@ public class JavaValue extends XNamedValue implements NodeDescriptorProvider, XV @Override public void computeSourcePosition(@NotNull final XNavigatable navigatable) { + if (navigatable instanceof XInlineSourcePosition && !(navigatable instanceof XNearestSourcePosition) + && !(myValueDescriptor instanceof ThisDescriptorImpl || myValueDescriptor instanceof LocalVariableDescriptor)) { + return; + } myEvaluationContext.getManagerThread().schedule(new SuspendContextCommandImpl(myEvaluationContext.getSuspendContext()) { @Override public Priority getPriority() { + if (navigatable instanceof XInlineSourcePosition) { + return Priority.LOW; + } return Priority.NORMAL; } diff --git a/java/debugger/impl/src/com/intellij/debugger/impl/DebuggerContextUtil.java b/java/debugger/impl/src/com/intellij/debugger/impl/DebuggerContextUtil.java index c24a33742986..92e983253c54 100644 --- a/java/debugger/impl/src/com/intellij/debugger/impl/DebuggerContextUtil.java +++ b/java/debugger/impl/src/com/intellij/debugger/impl/DebuggerContextUtil.java @@ -80,7 +80,7 @@ public class DebuggerContextUtil { //final Editor editor = fileEditor instanceof TextEditorImpl ? ((TextEditorImpl)fileEditor).getEditor() : null; if (editor != null && position != null && file.getVirtualFile().equals(position.getFile())) { - final Couple> usages = IdentifierHighlighterPass.getHighlightUsages(psi, file); + final Couple> usages = IdentifierHighlighterPass.getHighlightUsages(psi, file, false); final List ranges = new ArrayList(); ranges.addAll(usages.first); ranges.addAll(usages.second); @@ -104,6 +104,6 @@ public class DebuggerContextUtil { catch (Exception ignore) { } } - return SourcePosition.createFromOffset(file, psi.getTextOffset()); + return null; } } diff --git a/java/debugger/impl/src/com/intellij/debugger/impl/DebuggerUtilsEx.java b/java/debugger/impl/src/com/intellij/debugger/impl/DebuggerUtilsEx.java index ae6bb5dd7b27..c4721ce254a9 100644 --- a/java/debugger/impl/src/com/intellij/debugger/impl/DebuggerUtilsEx.java +++ b/java/debugger/impl/src/com/intellij/debugger/impl/DebuggerUtilsEx.java @@ -42,6 +42,8 @@ import com.intellij.openapi.fileTypes.StdFileTypes; import com.intellij.openapi.project.Project; import com.intellij.openapi.util.*; import com.intellij.openapi.util.text.StringUtil; +import com.intellij.openapi.vfs.VirtualFile; +import com.intellij.pom.Navigatable; import com.intellij.psi.*; import com.intellij.psi.codeStyle.CodeStyleSettingsManager; import com.intellij.ui.classFilter.ClassFilter; @@ -631,6 +633,36 @@ public abstract class DebuggerUtilsEx extends DebuggerUtils { @Nullable public static XSourcePosition toXSourcePosition(@NotNull SourcePosition position) { - return XSourcePositionImpl.create(position.getFile().getVirtualFile(), position.getLine()); + return new JavaXSourcePosition(position); + } + + private static class JavaXSourcePosition implements XSourcePosition { + private final SourcePosition mySourcePosition; + + public JavaXSourcePosition(@NotNull SourcePosition sourcePosition) { + mySourcePosition = sourcePosition; + } + + @Override + public int getLine() { + return mySourcePosition.getLine(); + } + + @Override + public int getOffset() { + return mySourcePosition.getOffset(); + } + + @NotNull + @Override + public VirtualFile getFile() { + return mySourcePosition.getFile().getVirtualFile(); + } + + @NotNull + @Override + public Navigatable createNavigatable(@NotNull Project project) { + return XSourcePositionImpl.createOpenFileDescriptor(project, this); + } } } diff --git a/platform/lang-impl/src/com/intellij/codeInsight/daemon/impl/IdentifierHighlighterPass.java b/platform/lang-impl/src/com/intellij/codeInsight/daemon/impl/IdentifierHighlighterPass.java index 91c3f140ed68..1ac3921c9b9a 100644 --- a/platform/lang-impl/src/com/intellij/codeInsight/daemon/impl/IdentifierHighlighterPass.java +++ b/platform/lang-impl/src/com/intellij/codeInsight/daemon/impl/IdentifierHighlighterPass.java @@ -123,7 +123,7 @@ public class IdentifierHighlighterPass extends TextEditorHighlightingPass { * @param psiFile psi file for element * @return a pair where first element is read usages and second is write usages */ - public static Couple> getHighlightUsages(@NotNull PsiElement target, PsiFile psiFile) { + public static Couple> getHighlightUsages(@NotNull PsiElement target, PsiFile psiFile, boolean withDecls) { Collection readRanges = new ArrayList(); Collection writeRanges = new ArrayList(); final ReadWriteAccessDetector detector = ReadWriteAccessDetector.findDetector(target); @@ -143,13 +143,15 @@ public class IdentifierHighlighterPass extends TextEditorHighlightingPass { } } - final TextRange declRange = HighlightUsagesHandler.getNameIdentifierRange(psiFile, target); - if (declRange != null) { - if (detector != null && detector.isDeclarationWriteAccess(target)) { - writeRanges.add(declRange); - } - else { - readRanges.add(declRange); + if (withDecls) { + final TextRange declRange = HighlightUsagesHandler.getNameIdentifierRange(psiFile, target); + if (declRange != null) { + if (detector != null && detector.isDeclarationWriteAccess(target)) { + writeRanges.add(declRange); + } + else { + readRanges.add(declRange); + } } } @@ -157,7 +159,7 @@ public class IdentifierHighlighterPass extends TextEditorHighlightingPass { } private void highlightTargetUsages(@NotNull PsiElement target) { - final Couple> usages = getHighlightUsages(target, myFile); + final Couple> usages = getHighlightUsages(target, myFile, true); myReadAccessRanges.addAll(usages.first); myWriteAccessRanges.addAll(usages.second); } diff --git a/platform/xdebugger-api/src/com/intellij/xdebugger/frame/XInlineSourcePosition.java b/platform/xdebugger-api/src/com/intellij/xdebugger/frame/XInlineSourcePosition.java new file mode 100644 index 000000000000..ff9bc065cac5 --- /dev/null +++ b/platform/xdebugger-api/src/com/intellij/xdebugger/frame/XInlineSourcePosition.java @@ -0,0 +1,22 @@ +/* + * Copyright 2000-2014 JetBrains s.r.o. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package com.intellij.xdebugger.frame; + +/** + * @author egor + */ +public interface XInlineSourcePosition extends XNavigatable { +} diff --git a/platform/xdebugger-api/src/com/intellij/xdebugger/frame/XNearestSourcePosition.java b/platform/xdebugger-api/src/com/intellij/xdebugger/frame/XNearestSourcePosition.java index 87abf3da3b21..9b223851ee03 100644 --- a/platform/xdebugger-api/src/com/intellij/xdebugger/frame/XNearestSourcePosition.java +++ b/platform/xdebugger-api/src/com/intellij/xdebugger/frame/XNearestSourcePosition.java @@ -18,5 +18,5 @@ package com.intellij.xdebugger.frame; /** * @author Konstantin Bulenkov */ -public interface XNearestSourcePosition extends XNavigatable { +public interface XNearestSourcePosition extends XInlineSourcePosition { } diff --git a/platform/xdebugger-impl/src/com/intellij/xdebugger/impl/ui/tree/XDebuggerTree.java b/platform/xdebugger-impl/src/com/intellij/xdebugger/impl/ui/tree/XDebuggerTree.java index feb62d3c03df..303293d5a3ab 100644 --- a/platform/xdebugger-impl/src/com/intellij/xdebugger/impl/ui/tree/XDebuggerTree.java +++ b/platform/xdebugger-impl/src/com/intellij/xdebugger/impl/ui/tree/XDebuggerTree.java @@ -37,7 +37,6 @@ import com.intellij.util.containers.Convertor; import com.intellij.util.containers.TransferToEDTQueue; import com.intellij.util.ui.TextTransferable; import com.intellij.util.ui.UIUtil; -import com.intellij.util.ui.tree.TreeModelAdapter; import com.intellij.xdebugger.XSourcePosition; import com.intellij.xdebugger.evaluation.XDebuggerEditorsProvider; import com.intellij.xdebugger.frame.XDebuggerTreeNodeHyperlink; @@ -49,7 +48,6 @@ import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; import javax.swing.*; -import javax.swing.event.TreeModelEvent; import javax.swing.tree.DefaultTreeModel; import javax.swing.tree.TreeNode; import javax.swing.tree.TreePath; @@ -155,27 +153,6 @@ public class XDebuggerTree extends DnDAwareTree implements DataProvider, Disposa myEditorsProvider = editorsProvider; mySourcePosition = sourcePosition; myTreeModel = new DefaultTreeModel(null); - myTreeModel.addTreeModelListener(new TreeModelAdapter() { - @Override - public void treeNodesChanged(TreeModelEvent e) { - updateEditor(); - } - - @Override - public void treeNodesInserted(TreeModelEvent e) { - updateEditor(); - } - - @Override - public void treeNodesRemoved(TreeModelEvent e) { - updateEditor(); - } - - @Override - public void treeStructureChanged(TreeModelEvent e) { - updateEditor(); - } - }); setModel(myTreeModel); setCellRenderer(new XDebuggerTreeRenderer()); new TreeLinkMouseListener(new XDebuggerTreeRenderer()) { @@ -226,7 +203,7 @@ public class XDebuggerTree extends DnDAwareTree implements DataProvider, Disposa setTransferHandler(DEFAULT_TRANSFER_HANDLER); } - private void updateEditor() { + public void updateEditor() { myAlarm.cancelAndRequest(); } diff --git a/platform/xdebugger-impl/src/com/intellij/xdebugger/impl/ui/tree/nodes/XValueNodeImpl.java b/platform/xdebugger-impl/src/com/intellij/xdebugger/impl/ui/tree/nodes/XValueNodeImpl.java index 6f911b28cd68..992371f8ff7e 100644 --- a/platform/xdebugger-impl/src/com/intellij/xdebugger/impl/ui/tree/nodes/XValueNodeImpl.java +++ b/platform/xdebugger-impl/src/com/intellij/xdebugger/impl/ui/tree/nodes/XValueNodeImpl.java @@ -18,6 +18,7 @@ package com.intellij.xdebugger.impl.ui.tree.nodes; import com.intellij.openapi.application.ApplicationManager; import com.intellij.openapi.editor.Document; import com.intellij.openapi.fileEditor.FileDocumentManager; +import com.intellij.openapi.util.Comparing; import com.intellij.openapi.util.Pair; import com.intellij.openapi.util.registry.Registry; import com.intellij.openapi.util.text.StringUtil; @@ -137,8 +138,8 @@ public class XValueNodeImpl extends XValueContainerNode implements XValu try { final XDebugSession session = XDebugView.getSession(getTree()); if (session != null) { - final XSourcePosition position = session.getCurrentPosition(); - if (position != null) { + final XSourcePosition debuggerPosition = session.getCurrentPosition(); + if (debuggerPosition != null) { final XInlineDebuggerDataCallback callback = new XInlineDebuggerDataCallback() { @Override public void computed(@NotNull VirtualFile file, @NotNull Document document, int line) { @@ -156,11 +157,12 @@ public class XValueNodeImpl extends XValueContainerNode implements XValu if (old != null) { presentations.addAll(old); } + myTree.updateEditor(); } }; if (getValueContainer().computeInlineDebuggerData(callback) == ThreeState.UNSURE) { - class ValueDeclaration implements XNavigatable { + class ValueDeclaration implements XInlineSourcePosition { @Override public void setSourcePosition(@Nullable XSourcePosition sourcePosition) { final Map, Set> map = @@ -168,6 +170,7 @@ public class XValueNodeImpl extends XValueContainerNode implements XValu final Map timestamps = myTree.getProject().getUserData(XVariablesView.DEBUG_VARIABLES_TIMESTAMPS); if (map == null || timestamps == null || sourcePosition == null) return; VirtualFile file = sourcePosition.getFile(); + if (!Comparing.equal(debuggerPosition.getFile(), sourcePosition.getFile())) return; final Document doc = FileDocumentManager.getInstance().getDocument(file); if (doc == null) return; int line = sourcePosition.getLine();