diff --git a/debug/org.eclipse.cdt.debug.core/src/org/eclipse/cdt/debug/internal/core/sourcelookup/CSourceNotFoundElement.java b/debug/org.eclipse.cdt.debug.core/src/org/eclipse/cdt/debug/internal/core/sourcelookup/CSourceNotFoundElement.java index 3fa97b0a60e..8134264cb0a 100644 --- a/debug/org.eclipse.cdt.debug.core/src/org/eclipse/cdt/debug/internal/core/sourcelookup/CSourceNotFoundElement.java +++ b/debug/org.eclipse.cdt.debug.core/src/org/eclipse/cdt/debug/internal/core/sourcelookup/CSourceNotFoundElement.java @@ -46,4 +46,12 @@ public class CSourceNotFoundElement { return file; } + public String getDescription() { + ICSourceNotFoundDescription description = (ICSourceNotFoundDescription) element.getAdapter(ICSourceNotFoundDescription.class); + if (description != null) + return description.getDescription(); + else + return element.toString(); + } + } diff --git a/debug/org.eclipse.cdt.debug.core/src/org/eclipse/cdt/debug/internal/core/sourcelookup/ICSourceNotFoundDescription.java b/debug/org.eclipse.cdt.debug.core/src/org/eclipse/cdt/debug/internal/core/sourcelookup/ICSourceNotFoundDescription.java new file mode 100644 index 00000000000..d5a49fea2c5 --- /dev/null +++ b/debug/org.eclipse.cdt.debug.core/src/org/eclipse/cdt/debug/internal/core/sourcelookup/ICSourceNotFoundDescription.java @@ -0,0 +1,32 @@ +/******************************************************************************* + * Copyright (c) 2010 Nokia 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 + * http://www.eclipse.org/legal/epl-v10.html + * + * Contributors: + * Nokia - initial API and implementation + *******************************************************************************/ + +package org.eclipse.cdt.debug.internal.core.sourcelookup; + + +/** + * This interface is used to provide a description of a debug element, + * usually a stack frame, when no source can be located for it. + * An instance is usually provided by an adapter. + */ +public interface ICSourceNotFoundDescription { + + /** + * Returns a description of the debug element suitable for + * use by the CSourceNotFoundEditor. This description is then + * used by the editor to inform the user when describing what + * it can't locate source for. + * + * @return the description of the debug element. + */ + String getDescription(); + +} diff --git a/debug/org.eclipse.cdt.debug.ui/src/org/eclipse/cdt/debug/internal/ui/sourcelookup/CSourceNotFoundEditor.java b/debug/org.eclipse.cdt.debug.ui/src/org/eclipse/cdt/debug/internal/ui/sourcelookup/CSourceNotFoundEditor.java index 423c3086f9a..b3f5e02f7a4 100644 --- a/debug/org.eclipse.cdt.debug.ui/src/org/eclipse/cdt/debug/internal/ui/sourcelookup/CSourceNotFoundEditor.java +++ b/debug/org.eclipse.cdt.debug.ui/src/org/eclipse/cdt/debug/internal/ui/sourcelookup/CSourceNotFoundEditor.java @@ -21,6 +21,7 @@ import org.eclipse.cdt.debug.core.CDebugCorePlugin; import org.eclipse.cdt.debug.core.sourcelookup.MappingSourceContainer; import org.eclipse.cdt.debug.internal.core.sourcelookup.CSourceLookupDirector; import org.eclipse.cdt.debug.internal.core.sourcelookup.CSourceNotFoundElement; +import org.eclipse.cdt.debug.internal.core.sourcelookup.ICSourceNotFoundDescription; import org.eclipse.cdt.debug.internal.core.sourcelookup.MapEntrySourceContainer; import org.eclipse.cdt.debug.internal.ui.ICDebugHelpContextIds; import org.eclipse.cdt.internal.core.model.ExternalTranslationUnit; @@ -130,7 +131,13 @@ public class CSourceNotFoundEditor extends CommonSourceNotFoundEditor { else { if (context == null) return super.getText(); - return MessageFormat.format(SourceLookupUIMessages.getString( "CSourceNotFoundEditor.3" ), new String[] { context.toString() }); //$NON-NLS-1$ + String contextDescription; + ICSourceNotFoundDescription description = (ICSourceNotFoundDescription) context.getAdapter(ICSourceNotFoundDescription.class); + if (description != null) + contextDescription = description.getDescription(); + else + contextDescription = context.toString(); + return MessageFormat.format(SourceLookupUIMessages.getString( "CSourceNotFoundEditor.3" ), new String[] { contextDescription }); //$NON-NLS-1$ } } diff --git a/debug/org.eclipse.cdt.debug.ui/src/org/eclipse/cdt/debug/internal/ui/sourcelookup/CSourceNotFoundEditorInput.java b/debug/org.eclipse.cdt.debug.ui/src/org/eclipse/cdt/debug/internal/ui/sourcelookup/CSourceNotFoundEditorInput.java index 4042f6e4b1e..267f2491a72 100644 --- a/debug/org.eclipse.cdt.debug.ui/src/org/eclipse/cdt/debug/internal/ui/sourcelookup/CSourceNotFoundEditorInput.java +++ b/debug/org.eclipse.cdt.debug.ui/src/org/eclipse/cdt/debug/internal/ui/sourcelookup/CSourceNotFoundEditorInput.java @@ -11,6 +11,7 @@ package org.eclipse.cdt.debug.internal.ui.sourcelookup; +import org.eclipse.cdt.debug.internal.core.sourcelookup.CSourceNotFoundElement; import org.eclipse.debug.ui.sourcelookup.CommonSourceNotFoundEditorInput; public class CSourceNotFoundEditorInput extends CommonSourceNotFoundEditorInput { @@ -19,4 +20,11 @@ public class CSourceNotFoundEditorInput extends CommonSourceNotFoundEditorInput super(artifact); } + @Override + public String getName() { + if (getArtifact() instanceof CSourceNotFoundElement) + return ((CSourceNotFoundElement)getArtifact()).getDescription(); + return super.getName(); + } + } diff --git a/dsf/org.eclipse.cdt.dsf.ui/src/org/eclipse/cdt/dsf/debug/internal/ui/CSourceNotFoundDescriptionFactory.java b/dsf/org.eclipse.cdt.dsf.ui/src/org/eclipse/cdt/dsf/debug/internal/ui/CSourceNotFoundDescriptionFactory.java new file mode 100644 index 00000000000..a3dbecf4338 --- /dev/null +++ b/dsf/org.eclipse.cdt.dsf.ui/src/org/eclipse/cdt/dsf/debug/internal/ui/CSourceNotFoundDescriptionFactory.java @@ -0,0 +1,156 @@ +/******************************************************************************* + * Copyright (c) 2010 Nokia 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 + * http://www.eclipse.org/legal/epl-v10.html + * + * Contributors: + * Nokia - initial API and implementation + *******************************************************************************/ +package org.eclipse.cdt.dsf.debug.internal.ui; + +import java.util.HashMap; + +import org.eclipse.cdt.core.IAddress; +import org.eclipse.cdt.debug.internal.core.sourcelookup.ICSourceNotFoundDescription; +import org.eclipse.cdt.dsf.concurrent.DataRequestMonitor; +import org.eclipse.cdt.dsf.concurrent.Query; +import org.eclipse.cdt.dsf.debug.service.IStack; +import org.eclipse.cdt.dsf.debug.service.IStack.IFrameDMContext; +import org.eclipse.cdt.dsf.debug.service.IStack.IFrameDMData; +import org.eclipse.cdt.dsf.debug.ui.viewmodel.launch.ILaunchVMConstants; +import org.eclipse.cdt.dsf.debug.ui.viewmodel.launch.MessagesForLaunchVM; +import org.eclipse.cdt.dsf.internal.ui.DsfUIPlugin; +import org.eclipse.cdt.dsf.service.DsfServicesTracker; +import org.eclipse.cdt.dsf.service.DsfSession; +import org.eclipse.core.runtime.IAdapterFactory; + +import com.ibm.icu.text.MessageFormat; + +/** + * This factory provides an instance of ICSourceNotFoundDescription that + * can generate a description of a IFrameDMContext. + * + */ +public class CSourceNotFoundDescriptionFactory implements IAdapterFactory { + + @SuppressWarnings("rawtypes") + public Object getAdapter(Object adaptableObject, Class adapterType) { + if (adapterType.equals(ICSourceNotFoundDescription.class) && + adaptableObject instanceof IFrameDMContext) + { + final IFrameDMContext frameDMC = (IFrameDMContext) adaptableObject; + return new ICSourceNotFoundDescription() { + + public String getDescription() { + Query query = new Query() { + @Override + protected void execute(DataRequestMonitor rm) { + DsfServicesTracker tracker = + new DsfServicesTracker(DsfUIPlugin.getBundleContext(), frameDMC.getSessionId()); + + IStack stack = tracker.getService(IStack.class); + if (stack != null) { + stack.getFrameData(frameDMC, rm); + } else { + rm.setData(null); + rm.done(); + } + tracker.dispose(); + } + }; + DsfSession.getSession(frameDMC.getSessionId()).getExecutor().execute(query); + try { + IFrameDMData dmData = query.get(); + return getFrameDescription(dmData); + } catch (Exception e) { + return frameDMC.toString(); + } + }}; + } + return null; + } + + @SuppressWarnings("rawtypes") + public Class[] getAdapterList() { + return new Class[] { ICSourceNotFoundDescription.class }; + } + + /** Creates a brief description of stack frame data. + * Based on code in StackFrameVMNode. + * @param frame + * @return the frame description + */ + private static String getFrameDescription(IStack.IFrameDMData frame) + { + String formatString = ""; //$NON-NLS-1$ + String[] propertyNames = null; + HashMap properties = new HashMap(); + fillFrameDataProperties(properties, frame); + + Integer line = (Integer)properties.get(ILaunchVMConstants.PROP_FRAME_LINE); + String file = (String)properties.get(ILaunchVMConstants.PROP_FRAME_FILE); + String function = (String)properties.get(ILaunchVMConstants.PROP_FRAME_FUNCTION); + String module = (String)properties.get(ILaunchVMConstants.PROP_FRAME_MODULE); + if (line != null && line >= 0 && file != null && file.length() > 0) + { + formatString = MessagesForLaunchVM.StackFramesVMNode_No_columns__text_format; + propertyNames = new String[] { + ILaunchVMConstants.PROP_FRAME_ADDRESS, + ILaunchVMConstants.PROP_FRAME_FUNCTION, + ILaunchVMConstants.PROP_FRAME_FILE, + ILaunchVMConstants.PROP_FRAME_LINE, + ILaunchVMConstants.PROP_FRAME_COLUMN, + ILaunchVMConstants.PROP_FRAME_MODULE}; + } + else if (function != null && function.length() > 0 && module != null && module.length() > 0) + { + formatString = MessagesForLaunchVM.StackFramesVMNode_No_columns__No_line__text_format; + propertyNames = new String[] { + ILaunchVMConstants.PROP_FRAME_ADDRESS, + ILaunchVMConstants.PROP_FRAME_FUNCTION, + ILaunchVMConstants.PROP_FRAME_MODULE}; + } + else if (module != null && module.length() > 0) + { + formatString = MessagesForLaunchVM.StackFramesVMNode_No_columns__No_function__text_format; + propertyNames = new String[] { + ILaunchVMConstants.PROP_FRAME_ADDRESS, + ILaunchVMConstants.PROP_FRAME_MODULE}; + } + else if (function != null && function.length() > 0) + { + formatString = MessagesForLaunchVM.StackFramesVMNode_No_columns__No_module__text_format; + propertyNames = new String[] { + ILaunchVMConstants.PROP_FRAME_ADDRESS, + ILaunchVMConstants.PROP_FRAME_FUNCTION}; + } + else + { + formatString = MessagesForLaunchVM.StackFramesVMNode_No_columns__Address_only__text_format; + propertyNames = new String[] { + ILaunchVMConstants.PROP_FRAME_ADDRESS}; + } + + Object[] propertyValues = new Object[propertyNames.length]; + for (int i = 0; i < propertyNames.length; i++) { + propertyValues[i] = properties.get(propertyNames[i]); + } + + return new MessageFormat(formatString).format(propertyValues, new StringBuffer(), null).toString(); + } + + private static void fillFrameDataProperties(java.util.Map properties, IFrameDMData data) { + IAddress address = data.getAddress(); + if (address != null) { + properties.put(ILaunchVMConstants.PROP_FRAME_ADDRESS, "0x" + address.toString(16)); //$NON-NLS-1$ + } + properties.put(ILaunchVMConstants.PROP_FRAME_FILE, data.getFile()); + properties.put(ILaunchVMConstants.PROP_FRAME_FUNCTION, data.getFunction()); + properties.put(ILaunchVMConstants.PROP_FRAME_LINE, data.getLine()); + properties.put(ILaunchVMConstants.PROP_FRAME_COLUMN, data.getColumn()); + properties.put(ILaunchVMConstants.PROP_FRAME_MODULE, data.getModule()); + } + +} diff --git a/dsf/org.eclipse.cdt.dsf.ui/src/org/eclipse/cdt/dsf/internal/ui/DsfUIPlugin.java b/dsf/org.eclipse.cdt.dsf.ui/src/org/eclipse/cdt/dsf/internal/ui/DsfUIPlugin.java index 58e7fa37723..8716b0be978 100644 --- a/dsf/org.eclipse.cdt.dsf.ui/src/org/eclipse/cdt/dsf/internal/ui/DsfUIPlugin.java +++ b/dsf/org.eclipse.cdt.dsf.ui/src/org/eclipse/cdt/dsf/internal/ui/DsfUIPlugin.java @@ -11,8 +11,10 @@ package org.eclipse.cdt.dsf.internal.ui; import org.eclipse.cdt.dsf.concurrent.IDsfStatusConstants; +import org.eclipse.cdt.dsf.debug.internal.ui.CSourceNotFoundDescriptionFactory; import org.eclipse.cdt.dsf.debug.internal.ui.disassembly.DisassemblyBackendDsfFactory; import org.eclipse.cdt.dsf.debug.internal.ui.disassembly.model.SourceDocumentProvider; +import org.eclipse.cdt.dsf.debug.service.IStack.IFrameDMContext; import org.eclipse.cdt.dsf.debug.ui.DsfDebugUITools; import org.eclipse.cdt.dsf.ui.viewmodel.datamodel.IDMVMContext; import org.eclipse.core.runtime.IStatus; @@ -62,6 +64,9 @@ public class DsfUIPlugin extends AbstractUIPlugin { // Register the DSF backend for our disassembly view (the CDT debug UI // plugin registers the CDI one) Platform.getAdapterManager().registerAdapters(new DisassemblyBackendDsfFactory(), IDMVMContext.class); + // Register the factory that provides descriptions of stack frames + // to the CSourceNotFoundEditor. + Platform.getAdapterManager().registerAdapters(new CSourceNotFoundDescriptionFactory(), IFrameDMContext.class); DsfDebugUITools.enableActivity("org.eclipse.cdt.debug.ui.cdtActivity", true); //$NON-NLS-1$ }