diff options
author | Eugene Tarassov | 2016-03-30 21:43:02 +0000 |
---|---|---|
committer | Eugene Tarassov | 2016-03-30 21:43:02 +0000 |
commit | d681442db7aca29479d8dc7f62086723a1b336be (patch) | |
tree | 854e4f02b3db5e0f1428929602e6af98dfc5811a | |
parent | 15cb01e9fe90b9202bc2e1164fca44fadd813298 (diff) | |
download | org.eclipse.tcf-d681442db7aca29479d8dc7f62086723a1b336be.tar.gz org.eclipse.tcf-d681442db7aca29479d8dc7f62086723a1b336be.tar.xz org.eclipse.tcf-d681442db7aca29479d8dc7f62086723a1b336be.zip |
TCF Debugger: added preference option to allow hover popup when application is running
6 files changed, 134 insertions, 60 deletions
diff --git a/plugins/org.eclipse.tcf.cdt.ui/src/org/eclipse/tcf/internal/cdt/ui/hover/TCFDebugTextHover.java b/plugins/org.eclipse.tcf.cdt.ui/src/org/eclipse/tcf/internal/cdt/ui/hover/TCFDebugTextHover.java index c014ba010..207f20b7e 100644 --- a/plugins/org.eclipse.tcf.cdt.ui/src/org/eclipse/tcf/internal/cdt/ui/hover/TCFDebugTextHover.java +++ b/plugins/org.eclipse.tcf.cdt.ui/src/org/eclipse/tcf/internal/cdt/ui/hover/TCFDebugTextHover.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2010, 2014 Wind River Systems, Inc. and others. + * Copyright (c) 2010, 2016 Wind River Systems, Inc. and others. * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at @@ -21,6 +21,7 @@ import org.eclipse.jface.text.IRegion; import org.eclipse.jface.text.ITextHoverExtension2; import org.eclipse.jface.text.ITextViewer; import org.eclipse.swt.widgets.Shell; +import org.eclipse.tcf.internal.debug.model.TCFContextState; import org.eclipse.tcf.internal.debug.ui.model.TCFChildren; import org.eclipse.tcf.internal.debug.ui.model.TCFChildrenStackTrace; import org.eclipse.tcf.internal.debug.ui.model.TCFNode; @@ -44,6 +45,9 @@ import org.eclipse.tcf.util.TCFTask; */ public class TCFDebugTextHover extends AbstractDebugTextHover implements ITextHoverExtension2 { + private TCFNode node; + private boolean running; + @Override public IInformationControlCreator getHoverControlCreator() { if (useExpressionExplorer()) { @@ -66,25 +70,91 @@ public class TCFDebugTextHover extends AbstractDebugTextHover implements ITextHo return true; } - public Object getHoverInfo2(ITextViewer textViewer, IRegion hoverRegion) { - if (!useExpressionExplorer()) return getHoverInfo(textViewer, hoverRegion); - final TCFNodeStackFrame activeFrame = getActiveFrame(); - if (activeFrame == null) return null; - final String text = getExpressionText(textViewer, hoverRegion); + private boolean getNode(TCFNode selection, Runnable done) { + node = null; + running = false; + TCFNodeStackFrame frame = null; + TCFNodeExecContext exe = null; + if (selection instanceof TCFNodeStackFrame) { + frame = (TCFNodeStackFrame)selection; + exe = (TCFNodeExecContext)frame.getParent(); + } + else if (selection instanceof TCFNodeExecContext) { + exe = (TCFNodeExecContext)selection; + } + else { + return true; + } + TCFDataCache<TCFContextState> state_cache = exe.getState(); + if (!state_cache.validate(done)) return false; + TCFContextState state_data = state_cache.getData(); + if (state_data == null || !state_data.is_suspended) { + if (exe.getModel().getHoverWhileRunning()) { + running = true; + node = exe; + } + } + else { + if (frame == null) { + TCFChildrenStackTrace stack = exe.getStackTrace(); + if (!stack.validate(done)) return false; + frame = stack.getTopFrame(); + } + if (frame != null && !frame.isEmulated()) node = frame; + } + return true; + } + + @Override + protected boolean canEvaluate() { + IAdaptable context = getSelectionAdaptable(); + if (context == null) return false; + final TCFNode selection = context.getAdapter(TCFNode.class); + if (selection == null) return false; + try { + return new TCFTask<Boolean>(selection.getChannel()) { + public void run() { + if (!getNode(selection, this)) return; + done(node != null); + } + }.get(); + } + catch (Exception x) { + // Problem in Eclipse 3.7: + // TextViewerHoverManager calls Thread.interrupt(), + // but it fails to handle InterruptedException. + // We have to catch and ignore the exception. + } + return false; + } + + public Object getHoverInfo2(ITextViewer viewer, IRegion region) { + if (!useExpressionExplorer()) return getHoverInfo(viewer, region); + IAdaptable context = getSelectionAdaptable(); + if (context == null) return null; + final TCFNode selection = context.getAdapter(TCFNode.class); + if (selection == null) return null; + final String text = getExpressionText(viewer, region); if (text == null || text.length() == 0) return null; try { - return new TCFTask<TCFNode>(activeFrame.getChannel()) { + return new TCFTask<Object>(selection.getChannel()) { public void run() { - TCFNode evalContext = activeFrame.isEmulated() ? activeFrame.getParent() : activeFrame; - TCFChildren cache = evalContext.getModel().getHoverExpressionCache(evalContext, text); - if (!cache.validate(this)) return; - Map<String,TCFNode> nodes = cache.getData(); - if (nodes != null) { - for (TCFNode node : nodes.values()) { - TCFDataCache<IExpressions.Value> value = ((TCFNodeExpression)node).getValue(); - if (!value.validate(this)) return; - if (value.getData() != null) { - done(node.getParent()); + if (!getNode(selection, this)) return; + if (node != null) { + TCFChildren cache = node.getModel().getHoverExpressionCache(node, text); + if (!cache.validate(this)) return; + Map<String,TCFNode> nodes = cache.getData(); + if (nodes != null) { + boolean ok = false; + for (TCFNode n : nodes.values()) { + TCFNodeExpression expr = (TCFNodeExpression)n; + if (running) expr.update(this); + TCFDataCache<IExpressions.Value> value = expr.getValue(); + if (!value.validate(this)) return; + if (value.getData() != null) ok = true; + } + if (ok) { + done(node); return; } } @@ -103,52 +173,24 @@ public class TCFDebugTextHover extends AbstractDebugTextHover implements ITextHo } @Override - protected boolean canEvaluate() { - return getActiveFrame() != null; - } - - private TCFNodeStackFrame getActiveFrame() { - IAdaptable context = getSelectionAdaptable(); - if (context instanceof TCFNodeStackFrame) return (TCFNodeStackFrame) context; - if (context instanceof TCFNodeExecContext) { - try { - final TCFNodeExecContext exe = (TCFNodeExecContext) context; - return new TCFTask<TCFNodeStackFrame>(exe.getChannel()) { - public void run() { - TCFChildrenStackTrace stack = exe.getStackTrace(); - if (!stack.validate(this)) return; - done(stack.getTopFrame()); - } - }.get(); - } - catch (Exception x) { - // Problem in Eclipse 3.7: - // TextViewerHoverManager calls Thread.interrupt(), - // but it fails to handle InterruptedException. - // We have to catch and ignore the exception. - return null; - } - } - return null; - } - - @Override protected String evaluateExpression(final String expression) { - final TCFNodeStackFrame activeFrame = getActiveFrame(); - if (activeFrame == null) return null; - final IChannel channel = activeFrame.getChannel(); + IAdaptable context = getSelectionAdaptable(); + if (context == null) return null; + final TCFNode selection = context.getAdapter(TCFNode.class); + if (selection == null) return null; + final IChannel channel = selection.getChannel(); return new TCFTask<String>(channel) { public void run() { - final IExpressions exprSvc = channel.getRemoteService(IExpressions.class); - if (exprSvc != null) { - TCFNode evalContext = activeFrame.isEmulated() ? activeFrame.getParent() : activeFrame; - exprSvc.create(evalContext.getID(), null, expression, new DoneCreate() { + final IExpressions service = channel.getRemoteService(IExpressions.class); + if (!getNode(selection, this)) return; + if (service != null && node != null) { + service.create(node.getID(), null, expression, new DoneCreate() { public void doneCreate(IToken token, Exception error, final Expression context) { if (error == null) { - exprSvc.evaluate(context.getID(), new DoneEvaluate() { + service.evaluate(context.getID(), new DoneEvaluate() { public void doneEvaluate(IToken token, Exception error, Value value) { done(error == null && value != null ? getValueText(value) : null); - exprSvc.dispose(context.getID(), new DoneDispose() { + service.dispose(context.getID(), new DoneDispose() { public void doneDispose(IToken token, Exception error) { // no-op } diff --git a/plugins/org.eclipse.tcf.debug.ui/src/org/eclipse/tcf/internal/debug/ui/model/TCFModel.java b/plugins/org.eclipse.tcf.debug.ui/src/org/eclipse/tcf/internal/debug/ui/model/TCFModel.java index 66c5cd9a4..61e1daea9 100644 --- a/plugins/org.eclipse.tcf.debug.ui/src/org/eclipse/tcf/internal/debug/ui/model/TCFModel.java +++ b/plugins/org.eclipse.tcf.debug.ui/src/org/eclipse/tcf/internal/debug/ui/model/TCFModel.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2007, 2015 Wind River Systems, Inc. and others. + * Copyright (c) 2007, 2016 Wind River Systems, Inc. and others. * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at @@ -237,6 +237,7 @@ public class TCFModel implements ITCFModel, IElementContentProvider, IElementLab private boolean delay_children_list_updates; private boolean auto_children_list_updates; private boolean show_full_error_reports; + private boolean hover_while_running; private boolean qualified_type_names_enabled; private boolean filter_variants_by_discriminant; @@ -748,6 +749,7 @@ public class TCFModel implements ITCFModel, IElementContentProvider, IElementLab auto_children_list_updates = prefs_store.getBoolean(TCFPreferences.PREF_AUTO_CHILDREN_LIST_UPDATES); delay_children_list_updates = prefs_store.getBoolean(TCFPreferences.PREF_DELAY_CHILDREN_LIST_UPDATES); show_full_error_reports = prefs_store.getBoolean(TCFPreferences.PREF_FULL_ERROR_REPORTS); + hover_while_running = prefs_store.getBoolean(TCFPreferences.PREF_HOVER_WHILE_RUNNING); qualified_type_names_enabled = prefs_store.getBoolean(TCFPreferences.PREF_SHOW_QUALIFIED_TYPE_NAMES); filter_variants_by_discriminant = prefs_store.getBoolean(TCFPreferences.PREF_FILTER_VARIANTS_BY_DISCRIMINANT); final boolean affectsExpressionsOnly = event != null && ( @@ -1099,6 +1101,10 @@ public class TCFModel implements ITCFModel, IElementContentProvider, IElementLab return show_full_error_reports; } + public boolean getHoverWhileRunning() { + return hover_while_running; + } + void onProxyInstalled(TCFModelProxy mp) { IPresentationContext pc = mp.getPresentationContext(); model_proxies.add(mp); diff --git a/plugins/org.eclipse.tcf.debug.ui/src/org/eclipse/tcf/internal/debug/ui/model/TCFNodeExpression.java b/plugins/org.eclipse.tcf.debug.ui/src/org/eclipse/tcf/internal/debug/ui/model/TCFNodeExpression.java index 6405a7d7b..aac000a57 100644 --- a/plugins/org.eclipse.tcf.debug.ui/src/org/eclipse/tcf/internal/debug/ui/model/TCFNodeExpression.java +++ b/plugins/org.eclipse.tcf.debug.ui/src/org/eclipse/tcf/internal/debug/ui/model/TCFNodeExpression.java @@ -85,6 +85,7 @@ public class TCFNodeExpression extends TCFNode implements IElementEditor, ICastT private byte[] parent_value; private String remote_expression_id; private IExpression platform_expression; + private Object update_generation; private static int expr_cnt; @@ -699,7 +700,22 @@ public class TCFNodeExpression extends TCFNode implements IElementEditor, ICastT } } + public void update(Object generation) { + if (update_generation == generation) return; + prev_value = null; + update_generation = generation; + if (rem_expression.isValid() && rem_expression.getError() != null) rem_expression.reset(); + type.reset(); + type_name.reset(); + value.reset(); + string.reset(); + for (ITCFPrettyExpressionProvider p : TCFPrettyExpressionProvider.getProviders()) p.cancel(this); + children.onSuspended(false); + resetBaseText(); + } + void onSuspended(boolean func_call) { + update_generation = null; if (!func_call) { prev_value = next_value; type.reset(); diff --git a/plugins/org.eclipse.tcf.debug.ui/src/org/eclipse/tcf/internal/debug/ui/preferences/TCFDebugPreferencePage.java b/plugins/org.eclipse.tcf.debug.ui/src/org/eclipse/tcf/internal/debug/ui/preferences/TCFDebugPreferencePage.java index e6b531ef2..3a112560c 100644 --- a/plugins/org.eclipse.tcf.debug.ui/src/org/eclipse/tcf/internal/debug/ui/preferences/TCFDebugPreferencePage.java +++ b/plugins/org.eclipse.tcf.debug.ui/src/org/eclipse/tcf/internal/debug/ui/preferences/TCFDebugPreferencePage.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2011, 2013 Wind River Systems, Inc. and others. + * Copyright (c) 2011, 2016 Wind River Systems, Inc. and others. * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at @@ -180,6 +180,14 @@ public class TCFDebugPreferencePage extends FieldEditorPreferencePage implements fullErrorReports.fillIntoGrid(group, 3); addField(fullErrorReports); + BooleanFieldEditor hoverWhileRunning = new BooleanFieldEditor( + TCFPreferences.PREF_HOVER_WHILE_RUNNING, + "Allow inspection of a variable by hovering over it even when application is running", + group); + + hoverWhileRunning.fillIntoGrid(group, 3); + addField(hoverWhileRunning); + group.setLayout(layout); } } diff --git a/plugins/org.eclipse.tcf.debug.ui/src/org/eclipse/tcf/internal/debug/ui/preferences/TCFPreferences.java b/plugins/org.eclipse.tcf.debug.ui/src/org/eclipse/tcf/internal/debug/ui/preferences/TCFPreferences.java index 072a3be44..f21f97341 100644 --- a/plugins/org.eclipse.tcf.debug.ui/src/org/eclipse/tcf/internal/debug/ui/preferences/TCFPreferences.java +++ b/plugins/org.eclipse.tcf.debug.ui/src/org/eclipse/tcf/internal/debug/ui/preferences/TCFPreferences.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2011, 2015 Wind River Systems, Inc. and others. + * Copyright (c) 2011, 2016 Wind River Systems, Inc. and others. * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at @@ -30,6 +30,7 @@ public class TCFPreferences { PREF_AUTO_CHILDREN_LIST_UPDATES = "AutoChildrenListUpdates", PREF_DELAY_CHILDREN_LIST_UPDATES = "DelayChildrenListUpdates", PREF_FULL_ERROR_REPORTS = "FullErrorReports", + PREF_HOVER_WHILE_RUNNING = "HoverWhileRunning", PREF_SHOW_QUALIFIED_TYPE_NAMES = "ShowQualifiedTypeNames", PREF_FILTER_VARIANTS_BY_DISCRIMINANT = "FilterVariantsByDiscriminant"; diff --git a/plugins/org.eclipse.tcf.debug.ui/src/org/eclipse/tcf/internal/debug/ui/preferences/TCFPreferencesInitializer.java b/plugins/org.eclipse.tcf.debug.ui/src/org/eclipse/tcf/internal/debug/ui/preferences/TCFPreferencesInitializer.java index 662a50aca..3328eabd2 100644 --- a/plugins/org.eclipse.tcf.debug.ui/src/org/eclipse/tcf/internal/debug/ui/preferences/TCFPreferencesInitializer.java +++ b/plugins/org.eclipse.tcf.debug.ui/src/org/eclipse/tcf/internal/debug/ui/preferences/TCFPreferencesInitializer.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2011, 2015 Wind River Systems, Inc. and others. + * Copyright (c) 2011, 2016 Wind River Systems, Inc. and others. * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at @@ -33,6 +33,7 @@ public class TCFPreferencesInitializer extends AbstractPreferenceInitializer { prefs.setDefault(TCFPreferences.PREF_AUTO_CHILDREN_LIST_UPDATES, true); prefs.setDefault(TCFPreferences.PREF_DELAY_CHILDREN_LIST_UPDATES, false); prefs.setDefault(TCFPreferences.PREF_FULL_ERROR_REPORTS, false); + prefs.setDefault(TCFPreferences.PREF_HOVER_WHILE_RUNNING, false); prefs.setDefault(TCFPreferences.PREF_SHOW_QUALIFIED_TYPE_NAMES, false); prefs.setDefault(TCFPreferences.PREF_FILTER_VARIANTS_BY_DISCRIMINANT, false); } |