diff --git a/core/org.eclipse.cdt.core.tests/model/org/eclipse/cdt/core/model/tests/AllCoreTests.java b/core/org.eclipse.cdt.core.tests/model/org/eclipse/cdt/core/model/tests/AllCoreTests.java index db5170e8ac0..ea99f47ce41 100644 --- a/core/org.eclipse.cdt.core.tests/model/org/eclipse/cdt/core/model/tests/AllCoreTests.java +++ b/core/org.eclipse.cdt.core.tests/model/org/eclipse/cdt/core/model/tests/AllCoreTests.java @@ -40,6 +40,8 @@ public class AllCoreTests { // each class being tested suite.addTest(AllLanguageInterfaceTests.suite()); suite.addTest(CModelTests.suite()); + suite.addTest(CModelElementsTests.suite()); + suite.addTest(CModelIdentifierTests.suite()); suite.addTest(CModelExceptionTest.suite()); suite.addTest(FlagTests.suite()); suite.addTest(ArchiveTests.suite()); diff --git a/core/org.eclipse.cdt.core.tests/model/org/eclipse/cdt/core/model/tests/CModelIdentifierTests.java b/core/org.eclipse.cdt.core.tests/model/org/eclipse/cdt/core/model/tests/CModelIdentifierTests.java new file mode 100644 index 00000000000..e1f01d7c1ce --- /dev/null +++ b/core/org.eclipse.cdt.core.tests/model/org/eclipse/cdt/core/model/tests/CModelIdentifierTests.java @@ -0,0 +1,114 @@ +/******************************************************************************* + * Copyright (c) 2008 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 + * http://www.eclipse.org/legal/epl-v10.html + * + * Contributors: + * Anton Leherbauer (Wind River Systems) - initial API and implementation + *******************************************************************************/ + +package org.eclipse.cdt.core.model.tests; + +import java.io.FileInputStream; +import java.io.FileNotFoundException; +import java.util.ArrayList; +import java.util.List; + +import junit.framework.Test; + +import org.eclipse.cdt.core.CCorePlugin; +import org.eclipse.cdt.core.dom.IPDOMManager; +import org.eclipse.cdt.core.model.CoreModel; +import org.eclipse.cdt.core.model.ICElement; +import org.eclipse.cdt.core.model.ICElementVisitor; +import org.eclipse.cdt.core.model.ICProject; +import org.eclipse.cdt.core.model.ITranslationUnit; +import org.eclipse.cdt.core.testplugin.CProjectHelper; +import org.eclipse.cdt.core.testplugin.CTestPlugin; +import org.eclipse.cdt.core.testplugin.util.BaseTestCase; +import org.eclipse.core.resources.IFile; +import org.eclipse.core.runtime.CoreException; +import org.eclipse.core.runtime.NullProgressMonitor; +import org.eclipse.core.runtime.Path; + +/** + * Tests for CModel identifier API. + * + * @see ICElement#getHandleIdentier() + * @see CoreModel.create(String) + * + * @since 5.0 + */ +public class CModelIdentifierTests extends BaseTestCase { + + public static Test suite() { + return BaseTestCase.suite(CModelIdentifierTests.class); + } + + private ICProject fCProject; + private IFile fHeaderFile; + + protected void setUp() throws Exception { + // reusing project setup from CModelElementsTests + NullProgressMonitor monitor= new NullProgressMonitor(); + fCProject= CProjectHelper.createCCProject("CModelIdentifierTests", "bin", IPDOMManager.ID_FAST_INDEXER); + fHeaderFile = fCProject.getProject().getFile("CModelIdentifierTests.h"); + if (!fHeaderFile.exists()) { + try{ + FileInputStream fileIn = new FileInputStream( + CTestPlugin.getDefault().getFileInPlugin(new Path("resources/cfiles/CModelElementsTestStart.h"))); + fHeaderFile.create(fileIn,false, monitor); + } catch (CoreException e) { + e.printStackTrace(); + } catch (FileNotFoundException e) { + e.printStackTrace(); + } + } + CCorePlugin.getIndexManager().joinIndexer(10000, new NullProgressMonitor()); + } + + protected void tearDown() { + CProjectHelper.delete(fCProject); + } + + public void testIdentiferConsistency() throws Exception { + ITranslationUnit tu = (ITranslationUnit)CoreModel.getDefault().create(fHeaderFile); + + final String cModelIdentifier= tu.getCModel().getHandleIdentifier(); + assertNotNull(cModelIdentifier); + assertEquals(tu.getCModel(), CoreModel.create(cModelIdentifier)); + + final String cProjectIdentifier= tu.getCProject().getHandleIdentifier(); + assertNotNull(cProjectIdentifier); + assertEquals(tu.getCProject(), CoreModel.create(cProjectIdentifier)); + + final String tUnitIdentifier= tu.getHandleIdentifier(); + assertNotNull(tUnitIdentifier); + assertEquals(tu, CoreModel.create(tUnitIdentifier)); + + final List elements= new ArrayList(); + final List identifiers= new ArrayList(); + ICElementVisitor visitor= new ICElementVisitor() { + public boolean visit(ICElement element) throws CoreException { + elements.add(element); + identifiers.add(element.getHandleIdentifier()); + return true; + }}; + tu.accept(visitor); + + assertEquals(elements.size(), identifiers.size()); + int size= elements.size(); + for (int i = 0; i < size; i++) { + ICElement expected= (ICElement) elements.get(i); + String identifier= (String) identifiers.get(i); + assertNotNull("Could not create identifier for element: "+ expected, identifier); + ICElement actual= CoreModel.create(identifier); + assertNotNull("Cannot create element '" + expected + "' from identifier: "+identifier, actual); + assertEquals(expected.getElementName(), actual.getElementName()); + assertEquals(expected.getElementType(), actual.getElementType()); + assertEquals(expected, actual); + } + } +} diff --git a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/core/model/CoreModel.java b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/core/model/CoreModel.java index 9bfd5824abc..58358b12c8a 100644 --- a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/core/model/CoreModel.java +++ b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/core/model/CoreModel.java @@ -40,6 +40,7 @@ import org.eclipse.cdt.internal.core.model.ProjectEntry; import org.eclipse.cdt.internal.core.model.SourceEntry; import org.eclipse.cdt.internal.core.settings.model.CLanguageSettingCache; import org.eclipse.cdt.internal.core.settings.model.CProjectDescriptionManager; +import org.eclipse.cdt.internal.core.util.MementoTokenizer; import org.eclipse.core.resources.IFile; import org.eclipse.core.resources.IFolder; import org.eclipse.core.resources.IProject; @@ -51,6 +52,7 @@ import org.eclipse.core.resources.ResourcesPlugin; import org.eclipse.core.runtime.CoreException; import org.eclipse.core.runtime.IPath; import org.eclipse.core.runtime.IProgressMonitor; +import org.eclipse.core.runtime.Plugin; import org.eclipse.core.runtime.content.IContentType; import org.eclipse.core.runtime.jobs.ISchedulingRule; @@ -79,6 +81,24 @@ public class CoreModel { return manager.createTranslationUnitFrom(cproject, path); } + /** + * Returns the C model element corresponding to the given handle identifier + * generated by ICElement.getHandleIdentifier(), or + * null if unable to create the associated element. + * + * @param handleIdentifier the given handle identifier + * @return the C element corresponding to the handle identifier + * + * @since 5.0 + */ + public static ICElement create(String handleIdentifier) { + if (handleIdentifier == null) { + return null; + } + MementoTokenizer memento = new MementoTokenizer(handleIdentifier); + return manager.getCModel().getHandleFromMemento(memento); + } + /** * Creates an ICElement form and IFile. Returns null if not found. */ diff --git a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/core/model/ICElement.java b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/core/model/ICElement.java index 9dc22dd559e..9963020c566 100644 --- a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/core/model/ICElement.java +++ b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/core/model/ICElement.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2000, 2007 QNX Software Systems and others. + * Copyright (c) 2000, 2008 QNX Software Systems 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 @@ -8,6 +8,7 @@ * Contributors: * QNX Software Systems - Initial API and implementation * Markus Schorn (Wind River Systems) + * Anton Leherbauer (Wind River Systems) *******************************************************************************/ package org.eclipse.cdt.core.model; @@ -413,4 +414,19 @@ public interface ICElement extends IAdaptable { * @throws CModelException */ void accept(ICElementVisitor visitor) throws CoreException; + + + /** + * Returns a string representation of this element handle. The format of + * the string is not specified; however, the identifier is stable across + * workspace sessions, and can be used to recreate this handle via the + * CoreModel.create(String) method. + * + * @return the string handle identifier + * @see CoreModel#create(java.lang.String) + * + * @since 5.0 + */ + String getHandleIdentifier(); + } diff --git a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/Archive.java b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/Archive.java index 045332cbe9c..9da6f64580d 100644 --- a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/Archive.java +++ b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/Archive.java @@ -21,8 +21,10 @@ import org.eclipse.cdt.core.model.IArchive; import org.eclipse.cdt.core.model.IBinary; import org.eclipse.cdt.core.model.ICElement; import org.eclipse.cdt.core.model.ICProject; +import org.eclipse.cdt.internal.core.util.MementoTokenizer; import org.eclipse.core.resources.IFile; import org.eclipse.core.resources.IResource; +import org.eclipse.core.runtime.Assert; import org.eclipse.core.runtime.IPath; import org.eclipse.core.runtime.IProgressMonitor; @@ -118,4 +120,20 @@ public class Archive extends Openable implements IArchive { super.closing(info); } + @Override + public ICElement getHandleFromMemento(String token, MementoTokenizer memento) { + return null; + } + + @Override + public void getHandleMemento(StringBuilder buff) { + ((CElement)getParent()).getHandleMemento(buff); + } + + @Override + protected char getHandleMementoDelimiter() { + Assert.isTrue(false, "Should not be called"); //$NON-NLS-1$ + return 0; + } + } diff --git a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/ArchiveContainer.java b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/ArchiveContainer.java index ed1c39e1693..cafc06fc329 100644 --- a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/ArchiveContainer.java +++ b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/ArchiveContainer.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2000, 2006 QNX Software Systems and others. + * Copyright (c) 2000, 2008 QNX Software Systems 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 @@ -7,6 +7,7 @@ * * Contributors: * QNX Software Systems - Initial API and implementation + * Anton Leherbauer (Wind River Systems) *******************************************************************************/ package org.eclipse.cdt.internal.core.model; @@ -17,7 +18,9 @@ import org.eclipse.cdt.core.model.CModelException; import org.eclipse.cdt.core.model.IArchive; import org.eclipse.cdt.core.model.IArchiveContainer; import org.eclipse.cdt.core.model.ICElement; +import org.eclipse.cdt.internal.core.util.MementoTokenizer; import org.eclipse.core.resources.IResource; +import org.eclipse.core.runtime.Assert; import org.eclipse.core.runtime.IProgressMonitor; public class ArchiveContainer extends Openable implements IArchiveContainer { @@ -48,4 +51,20 @@ public class ArchiveContainer extends Openable implements IArchiveContainer { return true; } + @Override + public ICElement getHandleFromMemento(String token, MementoTokenizer memento) { + return null; + } + + @Override + public void getHandleMemento(StringBuilder buff) { + ((CElement)getParent()).getHandleMemento(buff); + } + + @Override + protected char getHandleMementoDelimiter() { + Assert.isTrue(false, "Should not be called"); //$NON-NLS-1$ + return 0; + } + } diff --git a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/Binary.java b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/Binary.java index a37abddd235..9bc4d1a53ed 100644 --- a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/Binary.java +++ b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/Binary.java @@ -35,9 +35,11 @@ import org.eclipse.cdt.core.model.IBinary; import org.eclipse.cdt.core.model.IBuffer; import org.eclipse.cdt.core.model.ICElement; import org.eclipse.cdt.core.model.ICProject; +import org.eclipse.cdt.internal.core.util.MementoTokenizer; import org.eclipse.core.resources.IFile; import org.eclipse.core.resources.IResource; import org.eclipse.core.resources.ResourcesPlugin; +import org.eclipse.core.runtime.Assert; import org.eclipse.core.runtime.IPath; import org.eclipse.core.runtime.IProgressMonitor; import org.eclipse.core.runtime.Path; @@ -514,4 +516,21 @@ public class Binary extends Openable implements IBinary { public boolean showInBinaryContainer() { return showInBinaryContainer; } + + @Override + public ICElement getHandleFromMemento(String token, MementoTokenizer memento) { + return null; + } + + @Override + public void getHandleMemento(StringBuilder buff) { + ((CElement)getParent()).getHandleMemento(buff); + } + + @Override + protected char getHandleMementoDelimiter() { + Assert.isTrue(false, "Should not be called"); //$NON-NLS-1$ + return 0; + } + } diff --git a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/BinaryContainer.java b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/BinaryContainer.java index 915aa438a61..bdbdd6cc737 100644 --- a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/BinaryContainer.java +++ b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/BinaryContainer.java @@ -19,7 +19,9 @@ import org.eclipse.cdt.core.model.CModelException; import org.eclipse.cdt.core.model.IBinary; import org.eclipse.cdt.core.model.IBinaryContainer; import org.eclipse.cdt.core.model.ICElement; +import org.eclipse.cdt.internal.core.util.MementoTokenizer; import org.eclipse.core.resources.IResource; +import org.eclipse.core.runtime.Assert; import org.eclipse.core.runtime.IProgressMonitor; public class BinaryContainer extends Openable implements IBinaryContainer { @@ -66,4 +68,20 @@ public class BinaryContainer extends Openable implements IBinaryContainer { return true; } + @Override + public ICElement getHandleFromMemento(String token, MementoTokenizer memento) { + return null; + } + + @Override + public void getHandleMemento(StringBuilder buff) { + ((CElement)getParent()).getHandleMemento(buff); + } + + @Override + protected char getHandleMementoDelimiter() { + Assert.isTrue(false, "Should not be called"); //$NON-NLS-1$ + return 0; + } + } diff --git a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/BinaryElement.java b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/BinaryElement.java index cc4065ce98a..88cacc6fb84 100644 --- a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/BinaryElement.java +++ b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/BinaryElement.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2000, 2006 QNX Software Systems and others. + * Copyright (c) 2000, 2008 QNX Software Systems 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 @@ -7,6 +7,7 @@ * * Contributors: * QNX Software Systems - Initial API and implementation + * Anton Leherbauer (Wind River Systems) *******************************************************************************/ package org.eclipse.cdt.internal.core.model; @@ -24,8 +25,10 @@ import org.eclipse.cdt.core.model.ISourceManipulation; import org.eclipse.cdt.core.model.ISourceRange; import org.eclipse.cdt.core.model.ISourceReference; import org.eclipse.cdt.core.model.ITranslationUnit; +import org.eclipse.cdt.internal.core.util.MementoTokenizer; import org.eclipse.core.resources.IFile; import org.eclipse.core.resources.IResource; +import org.eclipse.core.runtime.Assert; import org.eclipse.core.runtime.IPath; import org.eclipse.core.runtime.IProgressMonitor; import org.eclipse.core.runtime.Path; @@ -247,4 +250,20 @@ public class BinaryElement extends CElement implements IBinaryElement, ISourceMa protected void generateInfos(Object info, Map newElements, IProgressMonitor monitor) throws CModelException { } + @Override + public ICElement getHandleFromMemento(String token, MementoTokenizer memento) { + return null; + } + + @Override + public void getHandleMemento(StringBuilder buff) { + ((CElement)getParent()).getHandleMemento(buff); + } + + @Override + protected char getHandleMementoDelimiter() { + Assert.isTrue(false, "Should not be called"); //$NON-NLS-1$ + return 0; + } + } diff --git a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/BinaryModule.java b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/BinaryModule.java index 828fa62e73c..2cf00c80ee1 100644 --- a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/BinaryModule.java +++ b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/BinaryModule.java @@ -19,8 +19,10 @@ import org.eclipse.cdt.core.model.IBinary; import org.eclipse.cdt.core.model.IBinaryElement; import org.eclipse.cdt.core.model.IBinaryModule; import org.eclipse.cdt.core.model.ICElement; +import org.eclipse.cdt.internal.core.util.MementoTokenizer; import org.eclipse.core.resources.IResource; import org.eclipse.core.resources.IWorkspaceRoot; +import org.eclipse.core.runtime.Assert; import org.eclipse.core.runtime.IPath; import org.eclipse.core.runtime.IProgressMonitor; @@ -99,4 +101,20 @@ public class BinaryModule extends Parent implements IBinaryModule { newElements.put(this, info); } + @Override + public ICElement getHandleFromMemento(String token, MementoTokenizer memento) { + return null; + } + + @Override + public void getHandleMemento(StringBuilder buff) { + ((CElement)getParent()).getHandleMemento(buff); + } + + @Override + protected char getHandleMementoDelimiter() { + Assert.isTrue(false, "Should not be called"); //$NON-NLS-1$ + return 0; + } + } diff --git a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/CContainer.java b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/CContainer.java index ffdecd2c410..3a84513cc2b 100644 --- a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/CContainer.java +++ b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/CContainer.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2000, 2007 QNX Software Systems and others. + * Copyright (c) 2000, 2008 QNX Software Systems 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 @@ -7,6 +7,7 @@ * * Contributors: * QNX Software Systems - Initial API and implementation + * Anton Leherbauer (Wind River Systems) *******************************************************************************/ package org.eclipse.cdt.internal.core.model; @@ -15,8 +16,8 @@ import java.util.List; import java.util.Map; import org.eclipse.cdt.core.IBinaryParser; -import org.eclipse.cdt.core.IBinaryParser.IBinaryFile; import org.eclipse.cdt.core.IBinaryParser.IBinaryArchive; +import org.eclipse.cdt.core.IBinaryParser.IBinaryFile; import org.eclipse.cdt.core.IBinaryParser.IBinaryObject; import org.eclipse.cdt.core.model.CModelException; import org.eclipse.cdt.core.model.CoreModel; @@ -27,6 +28,7 @@ import org.eclipse.cdt.core.model.ICElement; import org.eclipse.cdt.core.model.ICProject; import org.eclipse.cdt.core.model.ISourceRoot; import org.eclipse.cdt.core.model.ITranslationUnit; +import org.eclipse.cdt.internal.core.util.MementoTokenizer; import org.eclipse.core.resources.IContainer; import org.eclipse.core.resources.IFile; import org.eclipse.core.resources.IFolder; @@ -268,4 +270,24 @@ public class CContainer extends Openable implements ICContainer { } return celement; } + + @Override + public ICElement getHandleFromMemento(String token, MementoTokenizer memento) { + switch (token.charAt(0)) { + case CEM_TRANSLATIONUNIT: + if (!memento.hasMoreTokens()) return this; + String tuName = memento.nextToken(); + CElement tu = (CElement) getTranslationUnit(tuName); + if (tu != null) { + return tu.getHandleFromMemento(memento); + } + } + return null; + } + + @Override + protected char getHandleMementoDelimiter() { + return CElement.CEM_SOURCEFOLDER; + } + } diff --git a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/CElement.java b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/CElement.java index 70a85b95544..0133771b3f3 100644 --- a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/CElement.java +++ b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/CElement.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2000, 2006 QNX Software Systems and others. + * Copyright (c) 2000, 2008 QNX Software Systems 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 @@ -8,6 +8,7 @@ * Contributors: * QNX Software Systems - Initial API and implementation * Markus Schorn (Wind River Systems) + * Anton Leherbauer (Wind River Systems) *******************************************************************************/ package org.eclipse.cdt.internal.core.model; @@ -31,6 +32,7 @@ import org.eclipse.cdt.core.model.ISourceRange; import org.eclipse.cdt.core.model.ISourceReference; import org.eclipse.cdt.core.model.ISourceRoot; import org.eclipse.cdt.core.model.IWorkingCopy; +import org.eclipse.cdt.internal.core.util.MementoTokenizer; import org.eclipse.core.resources.IResource; import org.eclipse.core.resources.ResourceAttributes; import org.eclipse.core.runtime.CoreException; @@ -39,8 +41,22 @@ import org.eclipse.core.runtime.IProgressMonitor; import org.eclipse.core.runtime.Path; import org.eclipse.core.runtime.PlatformObject; +/** + * TLETODO Document CElement. + * + * @since 5.0 + */ public abstract class CElement extends PlatformObject implements ICElement { + public static final char CEM_ESCAPE = '\\'; + public static final char CEM_CPROJECT = '='; + public static final char CEM_SOURCEROOT = '/'; + public static final char CEM_SOURCEFOLDER = '<'; + public static final char CEM_TRANSLATIONUNIT = '{'; + public static final char CEM_SOURCEELEMENT = '['; + public static final char CEM_PARAMETER = '('; + public static final char CEM_ELEMENTTYPE = '#'; + protected static final CElement[] NO_ELEMENTS = new CElement[0]; protected int fType; @@ -508,4 +524,82 @@ public abstract class CElement extends PlatformObject implements ICElement { } } + /* + * @see org.eclipse.cdt.core.model.ICElement#getHandleIdentifier() + */ + public String getHandleIdentifier() { + return getHandleMemento(); + } + + /** + * Builds a string representation of this element. + * + * @return the string representation + */ + public String getHandleMemento(){ + StringBuilder buff = new StringBuilder(); + getHandleMemento(buff); + return buff.toString(); + } + + /** + * Append this elements memento string to the given buffer. + * + * @param buff the buffer building the memento string + */ + public void getHandleMemento(StringBuilder buff) { + ((CElement)getParent()).getHandleMemento(buff); + buff.append(getHandleMementoDelimiter()); + escapeMementoName(buff, getElementName()); + } + + /** + * Returns the char that marks the start of this handles + * contribution to a memento. + */ + protected abstract char getHandleMementoDelimiter(); + + /** + * Creates a C element handle from the given memento. + * + * @param memento the memento tokenizer + */ + public ICElement getHandleFromMemento(MementoTokenizer memento) { + if (!memento.hasMoreTokens()) return this; + String token = memento.nextToken(); + return getHandleFromMemento(token, memento); + } + + /** + * Creates a C element handle from the given memento. + * The given token is the current delimiter indicating the type of the next token(s). + * + * @param token the curren memento token + * @param memento the memento tokenizer + */ + public abstract ICElement getHandleFromMemento(String token, MementoTokenizer memento); + + /** + * Escape special characters in the given name and append the result to buffer. + * + * @param buffer the buffer to build the memento string + * @param mementoName the name to escape + */ + public static void escapeMementoName(StringBuilder buffer, String mementoName) { + for (int i = 0, length = mementoName.length(); i < length; i++) { + char character = mementoName.charAt(i); + switch (character) { + case CEM_ESCAPE: + case CEM_CPROJECT: + case CEM_TRANSLATIONUNIT: + case CEM_SOURCEROOT: + case CEM_SOURCEFOLDER: + case CEM_SOURCEELEMENT: + case CEM_ELEMENTTYPE: + case CEM_PARAMETER: + buffer.append(CEM_ESCAPE); + } + buffer.append(character); + } + } } diff --git a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/CModel.java b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/CModel.java index f0b4a388d9b..853fef2a18b 100644 --- a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/CModel.java +++ b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/CModel.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2000, 2005 QNX Software Systems and others. + * Copyright (c) 2000, 2008 QNX Software Systems 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 @@ -7,6 +7,7 @@ * * Contributors: * QNX Software Systems - Initial API and implementation + * Anton Leherbauer (Wind River Systems) *******************************************************************************/ package org.eclipse.cdt.internal.core.model; @@ -19,6 +20,7 @@ import org.eclipse.cdt.core.model.CoreModel; import org.eclipse.cdt.core.model.ICElement; import org.eclipse.cdt.core.model.ICModel; import org.eclipse.cdt.core.model.ICProject; +import org.eclipse.cdt.internal.core.util.MementoTokenizer; import org.eclipse.core.resources.IFile; import org.eclipse.core.resources.IFolder; import org.eclipse.core.resources.IProject; @@ -26,6 +28,7 @@ import org.eclipse.core.resources.IResource; import org.eclipse.core.resources.IWorkspace; import org.eclipse.core.resources.IWorkspaceRoot; import org.eclipse.core.resources.ResourcesPlugin; +import org.eclipse.core.runtime.Assert; import org.eclipse.core.runtime.IProgressMonitor; public class CModel extends Openable implements ICModel { @@ -218,4 +221,29 @@ public class CModel extends Openable implements ICModel { return true; } + @Override + public ICElement getHandleFromMemento(String token, MementoTokenizer memento) { + switch (token.charAt(0)) { + case CEM_CPROJECT: + if (!memento.hasMoreTokens()) return this; + String projectName = memento.nextToken(); + CElement project = (CElement)getCProject(projectName); + if (project != null) { + return project.getHandleFromMemento(memento); + } + } + return null; + } + + @Override + public void getHandleMemento(StringBuilder buff) { + buff.append(getElementName()); + } + + @Override + protected char getHandleMementoDelimiter(){ + Assert.isTrue(false, "Should not be called"); //$NON-NLS-1$ + return 0; + } + } diff --git a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/CProject.java b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/CProject.java index 13bf4d2ac48..bfedb1f9e71 100644 --- a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/CProject.java +++ b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/CProject.java @@ -48,12 +48,14 @@ import org.eclipse.cdt.core.settings.model.ICConfigurationDescription; import org.eclipse.cdt.core.settings.model.ICProjectDescription; import org.eclipse.cdt.core.settings.model.ICSourceEntry; import org.eclipse.cdt.internal.core.settings.model.CProjectDescriptionManager; +import org.eclipse.cdt.internal.core.util.MementoTokenizer; import org.eclipse.core.resources.IProject; import org.eclipse.core.resources.IResource; import org.eclipse.core.resources.ProjectScope; import org.eclipse.core.runtime.CoreException; import org.eclipse.core.runtime.IPath; import org.eclipse.core.runtime.IProgressMonitor; +import org.eclipse.core.runtime.Path; import org.eclipse.core.runtime.Preferences; import org.eclipse.core.runtime.QualifiedName; import org.eclipse.core.runtime.preferences.IEclipsePreferences; @@ -741,4 +743,58 @@ public class CProject extends Openable implements ICProject { } } + @Override + public ICElement getHandleFromMemento(String token, MementoTokenizer memento) { + switch (token.charAt(0)) { + case CEM_SOURCEROOT: + IPath rootPath = Path.EMPTY; + token = null; + while (memento.hasMoreTokens()) { + token = memento.nextToken(); + char firstChar = token.charAt(0); + if (firstChar != CEM_SOURCEFOLDER && firstChar != CEM_TRANSLATIONUNIT) { + rootPath.append(token); + token= null; + } else { + break; + } + } + if (!rootPath.isAbsolute()) { + rootPath= getProject().getFullPath().append(rootPath); + } + CElement root = (CElement)findSourceRoot(rootPath); + if (root != null) { + if (token != null) { + return root.getHandleFromMemento(token, memento); + } else { + return root.getHandleFromMemento(memento); + } + } + break; + case CEM_TRANSLATIONUNIT: + if (!memento.hasMoreTokens()) return this; + String tuName = memento.nextToken(); + final IPath path= Path.fromPortableString(tuName); + CElement tu= null; + try { + tu= (CElement) findElement(path); + } catch (CModelException exc) { + CCorePlugin.log(exc); + } + if (tu == null) { + tu= (CElement) CoreModel.getDefault().createTranslationUnitFrom(this, path); + } + if (tu != null) { + return tu.getHandleFromMemento(memento); + } + break; + } + return null; + } + + @Override + protected char getHandleMementoDelimiter() { + return CEM_CPROJECT; + } + } diff --git a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/FunctionDeclaration.java b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/FunctionDeclaration.java index 7de25d219ea..3222e218f10 100644 --- a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/FunctionDeclaration.java +++ b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/FunctionDeclaration.java @@ -1,13 +1,14 @@ /******************************************************************************* - * Copyright (c) 2002, 2006 IBM Corporation and others. + * Copyright (c) 2002, 2008 IBM Corporation 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: - * Rational Software - Initial API and implementation - * Markus Schorn (Wind River Systems) + * Rational Software - Initial API and implementation + * Markus Schorn (Wind River Systems) + * Anton Leherbauer (Wind River Systems) *******************************************************************************/ package org.eclipse.cdt.internal.core.model; @@ -167,4 +168,13 @@ public class FunctionDeclaration extends SourceManipulation implements IFunction getFunctionInfo().setVolatile(isVolatile); } + @Override + public void getHandleMemento(StringBuilder buff) { + super.getHandleMemento(buff); + for (int i = 0; i < fParameterTypes.length; i++) { + buff.append(CEM_PARAMETER); + escapeMementoName(buff, fParameterTypes[i]); + } + } + } diff --git a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/IncludeReference.java b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/IncludeReference.java index a98dd587c3a..1c31ce53326 100644 --- a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/IncludeReference.java +++ b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/IncludeReference.java @@ -24,9 +24,11 @@ import org.eclipse.cdt.core.model.ICElement; import org.eclipse.cdt.core.model.ICProject; import org.eclipse.cdt.core.model.IIncludeEntry; import org.eclipse.cdt.core.model.IIncludeReference; +import org.eclipse.cdt.internal.core.util.MementoTokenizer; import org.eclipse.cdt.utils.PathUtil; import org.eclipse.core.filesystem.URIUtil; import org.eclipse.core.resources.IResource; +import org.eclipse.core.runtime.Assert; import org.eclipse.core.runtime.IPath; import org.eclipse.core.runtime.IProgressMonitor; import org.eclipse.core.runtime.Path; @@ -145,4 +147,21 @@ public class IncludeReference extends Openable implements IIncludeReference { public IPath getPath() { return fPath; } + + @Override + public ICElement getHandleFromMemento(String token, MementoTokenizer memento) { + return null; + } + + @Override + public void getHandleMemento(StringBuilder buff) { + ((CElement)getParent()).getHandleMemento(buff); + } + + @Override + protected char getHandleMementoDelimiter() { + Assert.isTrue(false, "Should not be called"); //$NON-NLS-1$ + return 0; + } + } diff --git a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/LibraryReference.java b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/LibraryReference.java index ed9a0209c67..93a60a1b094 100644 --- a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/LibraryReference.java +++ b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/LibraryReference.java @@ -1,19 +1,14 @@ /******************************************************************************* - * Copyright (c) 2002, 2006 QNX Software Systems and others. + * Copyright (c) 2002, 2008 QNX Software Systems 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: - * QNX Software Systems - Initial API and implementation + * QNX Software Systems - Initial API and implementation + * Anton Leherbauer (Wind River Systems) *******************************************************************************/ -/* - * Created on Apr 2, 2003 - * - * To change this generated comment go to - * Window>Preferences>Java>Code Generation>Code Template - */ package org.eclipse.cdt.internal.core.model; import java.util.Map; @@ -22,7 +17,9 @@ import org.eclipse.cdt.core.model.CModelException; import org.eclipse.cdt.core.model.ICElement; import org.eclipse.cdt.core.model.ILibraryEntry; import org.eclipse.cdt.core.model.ILibraryReference; +import org.eclipse.cdt.internal.core.util.MementoTokenizer; import org.eclipse.core.resources.IResource; +import org.eclipse.core.runtime.Assert; import org.eclipse.core.runtime.IPath; import org.eclipse.core.runtime.IProgressMonitor; @@ -72,4 +69,20 @@ public class LibraryReference extends Parent implements ILibraryReference { protected void generateInfos(Object info, Map newElements, IProgressMonitor monitor) throws CModelException { } + @Override + public ICElement getHandleFromMemento(String token, MementoTokenizer memento) { + return null; + } + + @Override + public void getHandleMemento(StringBuilder buff) { + ((CElement)getParent()).getHandleMemento(buff); + } + + @Override + protected char getHandleMementoDelimiter() { + Assert.isTrue(false, "Should not be called"); //$NON-NLS-1$ + return 0; + } + } diff --git a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/SourceManipulation.java b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/SourceManipulation.java index 794178f8f10..d1540c97885 100644 --- a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/SourceManipulation.java +++ b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/SourceManipulation.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2000, 2007 QNX Software Systems and others. + * Copyright (c) 2000, 2008 QNX Software Systems 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 @@ -7,19 +7,27 @@ * * Contributors: * QNX Software Systems - Initial API and implementation + * Anton Leherbauer (Wind River Systems) *******************************************************************************/ package org.eclipse.cdt.internal.core.model; +import java.util.ArrayList; +import java.util.Arrays; +import java.util.List; import java.util.Map; +import org.eclipse.cdt.core.CCorePlugin; import org.eclipse.cdt.core.model.CModelException; import org.eclipse.cdt.core.model.ICElement; +import org.eclipse.cdt.core.model.IFunctionDeclaration; import org.eclipse.cdt.core.model.IOpenable; import org.eclipse.cdt.core.model.ISourceManipulation; import org.eclipse.cdt.core.model.ISourceRange; import org.eclipse.cdt.core.model.ISourceReference; +import org.eclipse.cdt.core.model.ITemplate; import org.eclipse.cdt.core.model.ITranslationUnit; +import org.eclipse.cdt.internal.core.util.MementoTokenizer; import org.eclipse.core.resources.IResource; import org.eclipse.core.runtime.IProgressMonitor; @@ -176,7 +184,7 @@ public class SourceManipulation extends Parent implements ISourceManipulation, I } /* - * @see JavaElement#generateInfos + * @see CElement#generateInfos */ protected void generateInfos(Object info, Map newElements, IProgressMonitor pm) throws CModelException { Openable openableParent = (Openable)getOpenableParent(); @@ -215,4 +223,125 @@ public class SourceManipulation extends Parent implements ISourceManipulation, I } } + /* + * @see CElement + */ + public ICElement getHandleFromMemento(String token, MementoTokenizer memento) { + switch (token.charAt(0)) { + case CEM_SOURCEELEMENT: + if (!memento.hasMoreTokens()) return this; + token= memento.nextToken(); + // element name + final String elementName; + if (token.charAt(0) != CEM_ELEMENTTYPE) { + elementName= token; + token= memento.nextToken(); + } else { + // anonymous + elementName= ""; //$NON-NLS-1$ + } + // element type + assert token.charAt(0) == CEM_ELEMENTTYPE; + String typeString= memento.nextToken(); + int elementType; + try { + elementType= Integer.parseInt(typeString); + } catch (NumberFormatException nfe) { + CCorePlugin.log(nfe); + return null; + } + token= null; + // optional: parameters + String[] mementoParams= {}; + if (memento.hasMoreTokens()) { + List params= new ArrayList(); + do { + token= memento.nextToken(); + if (token.charAt(0) != CEM_PARAMETER) { + break; + } + params.add(memento.nextToken()); + token= null; + } while (memento.hasMoreTokens()); + mementoParams= params.toArray(new String[params.size()]); + } + CElement element= null; + ICElement[] children; + try { + children= getChildren(); + } catch (CModelException exc) { + CCorePlugin.log(exc); + return null; + } + switch (elementType) { + case ICElement.C_FUNCTION: + case ICElement.C_FUNCTION_DECLARATION: + case ICElement.C_METHOD: + case ICElement.C_METHOD_DECLARATION: + case ICElement.C_TEMPLATE_FUNCTION: + case ICElement.C_TEMPLATE_FUNCTION_DECLARATION: + case ICElement.C_TEMPLATE_METHOD: + case ICElement.C_TEMPLATE_METHOD_DECLARATION: + for (int i = 0; i < children.length; i++) { + if (elementType == children[i].getElementType() + && elementName.equals(children[i].getElementName())) { + assert children[i] instanceof IFunctionDeclaration; + String[] functionParams= ((IFunctionDeclaration)children[i]).getParameterTypes(); + if (Arrays.equals(functionParams, mementoParams)) { + element= (CElement) children[i]; + break; + } + } + } + break; + case ICElement.C_TEMPLATE_CLASS: + case ICElement.C_TEMPLATE_STRUCT: + case ICElement.C_TEMPLATE_UNION: + for (int i = 0; i < children.length; i++) { + if (elementType == children[i].getElementType() + && elementName.equals(children[i].getElementName())) { + assert children[i] instanceof ITemplate; + String[] templateParams= ((ITemplate)children[i]).getTemplateParameterTypes(); + if (Arrays.equals(templateParams, mementoParams)) { + element= (CElement) children[i]; + break; + } + } + } + break; + default: + for (int i = 0; i < children.length; i++) { + if (elementType == children[i].getElementType() + && elementName.equals(children[i].getElementName())) { + element= (CElement) children[i]; + break; + } + } + break; + } + if (element != null) { + if (token != null) { + return element.getHandleFromMemento(token, memento); + } else { + return element.getHandleFromMemento(memento); + } + } + } + return null; + } + + @Override + public void getHandleMemento(StringBuilder buff) { + ((CElement)getParent()).getHandleMemento(buff); + buff.append(getHandleMementoDelimiter()); + escapeMementoName(buff, getElementName()); + buff.append(CEM_ELEMENTTYPE); + buff.append(Integer.toString(getElementType())); + } + + @Override + protected char getHandleMementoDelimiter() { + return CElement.CEM_SOURCEELEMENT; + } + } diff --git a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/SourceRoot.java b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/SourceRoot.java index f0f8549e02d..1e69711047b 100644 --- a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/SourceRoot.java +++ b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/SourceRoot.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2000, 2007 QNX Software Systems and others. + * Copyright (c) 2000, 2008 QNX Software Systems 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 @@ -7,6 +7,7 @@ * * Contributors: * QNX Software Systems - Initial API and implementation + * Anton Leherbauer (Wind River Systems) *******************************************************************************/ package org.eclipse.cdt.internal.core.model; @@ -16,8 +17,10 @@ import org.eclipse.cdt.core.model.CoreModelUtil; import org.eclipse.cdt.core.model.ICElement; import org.eclipse.cdt.core.model.ISourceRoot; import org.eclipse.cdt.core.settings.model.ICSourceEntry; +import org.eclipse.cdt.internal.core.util.MementoTokenizer; import org.eclipse.core.resources.IResource; import org.eclipse.core.runtime.IPath; +import org.eclipse.core.runtime.Path; /** * SourceRoot @@ -69,4 +72,62 @@ public class SourceRoot extends CContainer implements ISourceRoot { return false; } + /* + * @see CElement + */ + public ICElement getHandleFromMemento(String token, MementoTokenizer memento) { + switch (token.charAt(0)) { + case CEM_SOURCEFOLDER: + String name; + if (memento.hasMoreTokens()) { + name = memento.nextToken(); + char firstChar = name.charAt(0); + if (firstChar == CEM_TRANSLATIONUNIT) { + token = name; + name = ""; //$NON-NLS-1$ + } else { + token = null; + } + } else { + name = ""; //$NON-NLS-1$ + token = null; + } + CElement folder = (CElement)getCContainer(name); + if (token == null) { + return folder.getHandleFromMemento(memento); + } else { + return folder.getHandleFromMemento(token, memento); + } + case CEM_TRANSLATIONUNIT: + return super.getHandleFromMemento(token, memento); + } + return null; + } + /** + * @see CElement#getHandleMemento(StringBuilder) + */ + public void getHandleMemento(StringBuilder buff) { + IPath path; + IResource underlyingResource = getResource(); + if (underlyingResource != null) { + if (getResource().getProject().equals(getCProject().getProject())) { + path = underlyingResource.getProjectRelativePath(); + } else { + path = underlyingResource.getFullPath(); + } + } else { + path= Path.EMPTY; + } + ((CElement)getParent()).getHandleMemento(buff); + buff.append(getHandleMementoDelimiter()); + escapeMementoName(buff, path.toString()); + } + + /** + * @see CElement#getHandleMemento() + */ + protected char getHandleMementoDelimiter() { + return CElement.CEM_SOURCEROOT; + } + } diff --git a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/StructureTemplate.java b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/StructureTemplate.java index d7fe03d3433..c47057b70e3 100644 --- a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/StructureTemplate.java +++ b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/StructureTemplate.java @@ -1,12 +1,13 @@ /******************************************************************************* - * Copyright (c) 2002, 2005 IBM Corporation and others. + * Copyright (c) 2002, 2008 IBM Corporation 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: - * Rational Software - Initial API and implementation + * Rational Software - Initial API and implementation + * Anton Leherbauer (Wind River Systems) *******************************************************************************/ package org.eclipse.cdt.internal.core.model; @@ -52,4 +53,16 @@ public class StructureTemplate extends Structure implements IStructureTemplate { return fTemplate.getTemplateSignature(); } + @Override + public void getHandleMemento(StringBuilder buff) { + super.getHandleMemento(buff); + if (fTemplate.getNumberOfTemplateParameters() > 0) { + final String[] parameterTypes= fTemplate.getTemplateParameterTypes(); + for (int i = 0; i < parameterTypes.length; i++) { + buff.append(CEM_PARAMETER); + escapeMementoName(buff, parameterTypes[i]); + } + } + } + } diff --git a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/StructureTemplateDeclaration.java b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/StructureTemplateDeclaration.java index 051aec7d60b..f3ba748418f 100644 --- a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/StructureTemplateDeclaration.java +++ b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/StructureTemplateDeclaration.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2005 QnX Software Systems and others. + * Copyright (c) 2005, 2008 QnX Software Systems 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 @@ -7,6 +7,7 @@ * * Contributors: * Qnx Software Systems - initial API and implementation + * Anton Leherbauer (Wind River Systems) *******************************************************************************/ package org.eclipse.cdt.internal.core.model; @@ -40,4 +41,16 @@ public class StructureTemplateDeclaration extends StructureDeclaration implement return fTemplate.getNumberOfTemplateParameters(); } + @Override + public void getHandleMemento(StringBuilder buff) { + super.getHandleMemento(buff); + if (fTemplate.getNumberOfTemplateParameters() > 0) { + final String[] parameterTypes= fTemplate.getTemplateParameterTypes(); + for (int i = 0; i < parameterTypes.length; i++) { + buff.append(CEM_PARAMETER); + escapeMementoName(buff, parameterTypes[i]); + } + } + } + } diff --git a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/TranslationUnit.java b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/TranslationUnit.java index 9c8a4278e35..6f04ab921ed 100644 --- a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/TranslationUnit.java +++ b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/TranslationUnit.java @@ -19,9 +19,11 @@ import java.io.IOException; import java.io.InputStream; import java.net.URI; import java.util.ArrayList; +import java.util.Arrays; import java.util.HashMap; import java.util.HashSet; import java.util.Iterator; +import java.util.List; import java.util.Map; import org.eclipse.cdt.core.CCorePlugin; @@ -42,6 +44,7 @@ import org.eclipse.cdt.core.model.IBuffer; import org.eclipse.cdt.core.model.ICElement; import org.eclipse.cdt.core.model.ICProject; import org.eclipse.cdt.core.model.IContributedModelBuilder; +import org.eclipse.cdt.core.model.IFunctionDeclaration; import org.eclipse.cdt.core.model.IInclude; import org.eclipse.cdt.core.model.ILanguage; import org.eclipse.cdt.core.model.INamespace; @@ -49,6 +52,7 @@ import org.eclipse.cdt.core.model.IParent; import org.eclipse.cdt.core.model.IProblemRequestor; import org.eclipse.cdt.core.model.ISourceRange; import org.eclipse.cdt.core.model.ISourceReference; +import org.eclipse.cdt.core.model.ITemplate; import org.eclipse.cdt.core.model.ITranslationUnit; import org.eclipse.cdt.core.model.IUsing; import org.eclipse.cdt.core.model.IWorkingCopy; @@ -64,6 +68,7 @@ import org.eclipse.cdt.internal.core.dom.NullCodeReaderFactory; import org.eclipse.cdt.internal.core.dom.SavedCodeReaderFactory; import org.eclipse.cdt.internal.core.index.IndexBasedCodeReaderFactory; import org.eclipse.cdt.internal.core.pdom.indexer.ProjectIndexerInputAdapter; +import org.eclipse.cdt.internal.core.util.MementoTokenizer; import org.eclipse.core.filesystem.EFS; import org.eclipse.core.filesystem.IFileInfo; import org.eclipse.core.filesystem.IFileStore; @@ -956,4 +961,128 @@ public class TranslationUnit extends Openable implements ITranslationUnit { return super.getPath(); } + @Override + public ICElement getHandleFromMemento(String token, MementoTokenizer memento) { + switch (token.charAt(0)) { + case CEM_SOURCEELEMENT: + if (!memento.hasMoreTokens()) return this; + token= memento.nextToken(); + // element name + final String elementName; + if (token.charAt(0) != CEM_ELEMENTTYPE) { + elementName= token; + token= memento.nextToken(); + } else { + // anonymous + elementName= ""; //$NON-NLS-1$ + } + // element type + assert token.charAt(0) == CEM_ELEMENTTYPE; + String typeString= memento.nextToken(); + int elementType; + try { + elementType= Integer.parseInt(typeString); + } catch (NumberFormatException nfe) { + CCorePlugin.log(nfe); + return null; + } + token= null; + // optional: parameters + String[] mementoParams= {}; + if (memento.hasMoreTokens()) { + List params= new ArrayList(); + do { + token= memento.nextToken(); + if (token.charAt(0) != CEM_PARAMETER) { + break; + } + params.add(memento.nextToken()); + token= null; + } while (memento.hasMoreTokens()); + mementoParams= params.toArray(new String[params.size()]); + } + CElement element= null; + ICElement[] children; + try { + children= getChildren(); + } catch (CModelException exc) { + CCorePlugin.log(exc); + return null; + } + switch (elementType) { + case ICElement.C_FUNCTION: + case ICElement.C_FUNCTION_DECLARATION: + case ICElement.C_METHOD: + case ICElement.C_METHOD_DECLARATION: + case ICElement.C_TEMPLATE_FUNCTION: + case ICElement.C_TEMPLATE_FUNCTION_DECLARATION: + case ICElement.C_TEMPLATE_METHOD: + case ICElement.C_TEMPLATE_METHOD_DECLARATION: + // search for matching function + for (int i = 0; i < children.length; i++) { + if (elementType == children[i].getElementType() + && elementName.equals(children[i].getElementName())) { + assert children[i] instanceof IFunctionDeclaration; + String[] functionParams= ((IFunctionDeclaration)children[i]).getParameterTypes(); + if (Arrays.equals(functionParams, mementoParams)) { + element= (CElement) children[i]; + break; + } + } + } + break; + case ICElement.C_TEMPLATE_CLASS: + case ICElement.C_TEMPLATE_STRUCT: + case ICElement.C_TEMPLATE_UNION: + // search for matching template type + for (int i = 0; i < children.length; i++) { + if (elementType == children[i].getElementType() + && elementName.equals(children[i].getElementName())) { + assert children[i] instanceof ITemplate; + String[] templateParams= ((ITemplate)children[i]).getTemplateParameterTypes(); + if (Arrays.equals(templateParams, mementoParams)) { + element= (CElement) children[i]; + break; + } + } + } + break; + default: + // search for matching element + for (int i = 0; i < children.length; i++) { + if (elementType == children[i].getElementType() + && elementName.equals(children[i].getElementName())) { + element= (CElement) children[i]; + break; + } + } + break; + } + if (element != null) { + if (token != null) { + return element.getHandleFromMemento(token, memento); + } else { + return element.getHandleFromMemento(memento); + } + } + } + return null; + } + + @Override + public void getHandleMemento(StringBuilder buff) { + if (getResource() == null) { + ((CElement)getCProject()).getHandleMemento(buff); + buff.append(getHandleMementoDelimiter()); + escapeMementoName(buff, getPath().toPortableString()); + } else { + super.getHandleMemento(buff); + } + } + + @Override + protected char getHandleMementoDelimiter() { + return CElement.CEM_TRANSLATIONUNIT; + } + } diff --git a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/ext/CElementHandle.java b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/ext/CElementHandle.java index 8cb5cc78ffe..fc549228c72 100644 --- a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/ext/CElementHandle.java +++ b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/ext/CElementHandle.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2006, 2007 Wind River Systems, Inc. and others. + * Copyright (c) 2006, 2008 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 @@ -7,6 +7,7 @@ * * Contributors: * Markus Schorn - initial API and implementation + * Anton Leherbauer (Wind River Systems) *******************************************************************************/ package org.eclipse.cdt.internal.core.model.ext; @@ -293,4 +294,39 @@ abstract class CElementHandle implements ICElementHandle, ISourceReference { } return ASTAccessVisibility.PUBLIC; } + + /** + * @see ICElement + */ + public String getHandleIdentifier() { + return getHandleMemento(); + } + + public String getHandleMemento(){ + StringBuilder buff = new StringBuilder(); + getHandleMemento(buff); + return buff.toString(); + } + + protected void getHandleMemento(StringBuilder buff) { + final ICElement parent= getParent(); + if (parent instanceof CElement) { + ((CElement)parent).getHandleMemento(buff); + } else if (parent instanceof CElementHandle) { + ((CElementHandle)parent).getHandleMemento(buff); + } + buff.append(getHandleMementoDelimiter()); + CElement.escapeMementoName(buff, getElementName()); + buff.append(CElement.CEM_ELEMENTTYPE); + buff.append(Integer.toString(getElementType())); + } + + /** + * Returns the char that marks the start of this handles + * contribution to a memento. + */ + protected char getHandleMementoDelimiter() { + return CElement.CEM_SOURCEELEMENT; + } + } diff --git a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/ext/FunctionDeclarationHandle.java b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/ext/FunctionDeclarationHandle.java index 2576a3acdab..6aa39b806ef 100644 --- a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/ext/FunctionDeclarationHandle.java +++ b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/ext/FunctionDeclarationHandle.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2006, 2007 Wind River Systems, Inc. and others. + * Copyright (c) 2006, 2008 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 @@ -7,6 +7,7 @@ * * Contributors: * Markus Schorn - initial API and implementation + * Anton Leherbauer (Wind River Systems) *******************************************************************************/ package org.eclipse.cdt.internal.core.model.ext; @@ -17,6 +18,7 @@ import org.eclipse.cdt.core.dom.ast.IFunction; import org.eclipse.cdt.core.model.CModelException; import org.eclipse.cdt.core.model.ICElement; import org.eclipse.cdt.core.model.IFunctionDeclaration; +import org.eclipse.cdt.internal.core.model.CElement; import org.eclipse.cdt.internal.core.model.FunctionDeclaration; public class FunctionDeclarationHandle extends CElementHandle implements org.eclipse.cdt.core.model.IFunctionDeclaration { @@ -61,4 +63,13 @@ public class FunctionDeclarationHandle extends CElementHandle implements org.ecl public boolean isStatic() throws CModelException { return fIsStatic; } + + public void getHandleMemento(StringBuilder buff) { + super.getHandleMemento(buff); + for (int i = 0; i < fParameterTypes.length; i++) { + buff.append(CElement.CEM_PARAMETER); + CElement.escapeMementoName(buff, fParameterTypes[i]); + } + } + } diff --git a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/ext/MethodDeclarationHandle.java b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/ext/MethodDeclarationHandle.java index fe1a029d59c..4da108c6b46 100644 --- a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/ext/MethodDeclarationHandle.java +++ b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/ext/MethodDeclarationHandle.java @@ -19,6 +19,7 @@ import org.eclipse.cdt.core.model.CModelException; import org.eclipse.cdt.core.model.ICElement; import org.eclipse.cdt.core.model.IMethodDeclaration; import org.eclipse.cdt.core.parser.ast.ASTAccessVisibility; +import org.eclipse.cdt.internal.core.model.CElement; import org.eclipse.cdt.internal.core.model.FunctionDeclaration; import org.eclipse.cdt.internal.core.model.MethodDeclaration; @@ -82,4 +83,12 @@ public class MethodDeclarationHandle extends CElementHandle implements IMethodDe public boolean isDestructor() throws CModelException { return fIsDestructor; } + + public void getHandleMemento(StringBuilder buff) { + super.getHandleMemento(buff); + for (int i = 0; i < fParameterTypes.length; i++) { + buff.append(CElement.CEM_PARAMETER); + CElement.escapeMementoName(buff, fParameterTypes[i]); + } + } } diff --git a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/ext/StructureTemplateHandle.java b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/ext/StructureTemplateHandle.java index 18bff3dcf8e..8c9bf34bbde 100644 --- a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/ext/StructureTemplateHandle.java +++ b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/ext/StructureTemplateHandle.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2007 Wind River Systems, Inc. and others. + * Copyright (c) 2007, 2008 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 @@ -7,6 +7,7 @@ * * Contributors: * Markus Schorn - initial API and implementation + * Anton Leherbauer (Wind River Systems) *******************************************************************************/ package org.eclipse.cdt.internal.core.model.ext; @@ -18,6 +19,7 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateParameter; import org.eclipse.cdt.core.model.CModelException; import org.eclipse.cdt.core.model.ICElement; import org.eclipse.cdt.core.model.IStructureTemplate; +import org.eclipse.cdt.internal.core.model.CElement; import org.eclipse.cdt.internal.core.model.Template; public class StructureTemplateHandle extends StructureHandle implements IStructureTemplate { @@ -50,4 +52,15 @@ public class StructureTemplateHandle extends StructureHandle implements IStructu public String getTemplateSignature() throws CModelException { return fTemplate.getTemplateSignature(); } + + public void getHandleMemento(StringBuilder buff) { + super.getHandleMemento(buff); + if (fTemplate.getNumberOfTemplateParameters() > 0) { + final String[] parameterTypes= fTemplate.getTemplateParameterTypes(); + for (int i = 0; i < parameterTypes.length; i++) { + buff.append(CElement.CEM_PARAMETER); + CElement.escapeMementoName(buff, parameterTypes[i]); + } + } + } } diff --git a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/util/MementoTokenizer.java b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/util/MementoTokenizer.java new file mode 100644 index 00000000000..37342dd2de7 --- /dev/null +++ b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/util/MementoTokenizer.java @@ -0,0 +1,94 @@ +/******************************************************************************* + * Copyright (c) 2004, 2008 IBM Corporation 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: + * IBM Corporation - initial API and implementation + * Anton Leherbauer (Wind River Systems) + *******************************************************************************/ +package org.eclipse.cdt.internal.core.util; + +import org.eclipse.cdt.internal.core.model.CElement; + + +/** + * A tokenizer to decipher a C element memento string. + * + * @since 5.0 + */ +public class MementoTokenizer { + private static final String CPROJECT = Character.toString(CElement.CEM_CPROJECT); + private static final String SOURCEROOT = Character.toString(CElement.CEM_SOURCEROOT); + private static final String SOURCEFOLDER = Character.toString(CElement.CEM_SOURCEFOLDER); + private static final String TRANSLATIONUNIT = Character.toString(CElement.CEM_TRANSLATIONUNIT); + private static final String SOURCEELEMENT = Character.toString(CElement.CEM_SOURCEELEMENT); + private static final String ELEMENTTYPE = Character.toString(CElement.CEM_ELEMENTTYPE); + private static final String PARAMETER = Character.toString(CElement.CEM_PARAMETER); + + private final char[] memento; + private final int length; + private int index = 0; + + public MementoTokenizer(String memento) { + this.memento = memento.toCharArray(); + this.length = this.memento.length; + } + + public boolean hasMoreTokens() { + return this.index < this.length; + } + + public String nextToken() { + int start = this.index; + StringBuilder buffer = null; + switch (this.memento[this.index++]) { + case CElement.CEM_ESCAPE: + buffer = new StringBuilder(); + buffer.append(this.memento[this.index]); + start = ++this.index; + break; + case CElement.CEM_CPROJECT: + return CPROJECT; + case CElement.CEM_SOURCEROOT: + return SOURCEROOT; + case CElement.CEM_SOURCEFOLDER: + return SOURCEFOLDER; + case CElement.CEM_TRANSLATIONUNIT: + return TRANSLATIONUNIT; + case CElement.CEM_SOURCEELEMENT: + return SOURCEELEMENT; + case CElement.CEM_ELEMENTTYPE: + return ELEMENTTYPE; + case CElement.CEM_PARAMETER: + return PARAMETER; + } + loop: while (this.index < this.length) { + switch (this.memento[this.index]) { + case CElement.CEM_ESCAPE: + if (buffer == null) buffer = new StringBuilder(); + buffer.append(this.memento, start, this.index - start); + start = ++this.index; + break; + case CElement.CEM_CPROJECT: + case CElement.CEM_TRANSLATIONUNIT: + case CElement.CEM_SOURCEROOT: + case CElement.CEM_SOURCEFOLDER: + case CElement.CEM_SOURCEELEMENT: + case CElement.CEM_ELEMENTTYPE: + case CElement.CEM_PARAMETER: + break loop; + } + this.index++; + } + if (buffer != null) { + buffer.append(this.memento, start, this.index - start); + return buffer.toString(); + } else { + return new String(this.memento, start, this.index - start); + } + } + +}