Skip to main content
aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--core/org.eclipse.cdt.core/parser/org/eclipse/cdt/core/index/IIndexSymbols.java43
-rw-r--r--core/org.eclipse.cdt.core/parser/org/eclipse/cdt/core/index/IPDOMASTProcessor.java44
-rw-r--r--core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/pdom/AbstractIndexerTask.java16
-rw-r--r--core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/pdom/PDOMASTProcessorDesc.java141
-rw-r--r--core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/pdom/PDOMASTProcessorManager.java52
-rw-r--r--core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/pdom/PDOMWriter.java134
-rw-r--r--core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/pdom/dom/PDOMLinkage.java12
-rwxr-xr-xcore/org.eclipse.cdt.core/plugin.properties1
-rw-r--r--core/org.eclipse.cdt.core/plugin.xml1
-rw-r--r--core/org.eclipse.cdt.core/schema/PDOMASTProcessor.exsd131
10 files changed, 516 insertions, 59 deletions
diff --git a/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/core/index/IIndexSymbols.java b/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/core/index/IIndexSymbols.java
new file mode 100644
index 00000000000..d8516d0e04e
--- /dev/null
+++ b/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/core/index/IIndexSymbols.java
@@ -0,0 +1,43 @@
+package org.eclipse.cdt.core.index;
+
+import org.eclipse.cdt.core.dom.ast.IASTName;
+import org.eclipse.cdt.core.dom.ast.IASTPreprocessorIncludeStatement;
+import org.eclipse.cdt.core.dom.ast.IASTPreprocessorStatement;
+
+/**
+ * A container for symbols that should be added to a linkage in the persisted index. Contributors
+ * of the org.eclipse.cdt.core.PDOMASTProcessor extension-point are provided the opportunity
+ * to process the parsed AST translation units. Elements of interest are added to an
+ * implementation of this interface.
+ *
+ * @since 5.6
+ * @noimplement This interface is not intended to be implemented by clients.
+ * @noextend This interface is not intended to be extended by clients.
+ */
+public interface IIndexSymbols {
+ /**
+ * Return true if the map contains no symbols and false otherwise.
+ */
+ public boolean isEmpty();
+
+ /**
+ * Adds an IASTName along with an optional referencing IASTName to the map. The names
+ * will be associated with the optional owning include statement.
+ *
+ * @param owner The optional include statement that provides context for the given
+ * names. Can be null.
+ * @param name The name that is being added to the map, cannot be null.
+ * @param caller The optional name that references the name being added. Can be null.
+ */
+ public void add(IASTPreprocessorIncludeStatement owner, IASTName name, IASTName caller);
+
+ /**
+ * Creates an association from the caller include statement to the owning context.
+ */
+ public void add(IASTPreprocessorIncludeStatement owner, IASTPreprocessorIncludeStatement caller);
+
+ /**
+ * Creates an association from the caller preprocessor statement to the owning context.
+ */
+ public void add(IASTPreprocessorIncludeStatement owner, IASTPreprocessorStatement caller);
+}
diff --git a/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/core/index/IPDOMASTProcessor.java b/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/core/index/IPDOMASTProcessor.java
new file mode 100644
index 00000000000..6390d24d336
--- /dev/null
+++ b/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/core/index/IPDOMASTProcessor.java
@@ -0,0 +1,44 @@
+package org.eclipse.cdt.core.index;
+
+import org.eclipse.cdt.core.dom.ILinkage;
+import org.eclipse.cdt.core.dom.ast.IASTTranslationUnit;
+import org.eclipse.cdt.internal.core.pdom.dom.IPDOMLinkageFactory;
+import org.eclipse.core.runtime.CoreException;
+
+/**
+ * The PDOMASTProcessor extension point allows contributors to the org.eclipse.cdt.core.PDOMASTProcessor
+ * extension-point to store their own information in the persisted index. The intent is for
+ * contributors to define their own ILinkage to avoid managing conflicts with the storage format
+ * for existing Linkages.
+ * <p>
+ * NOTE: The existing org.eclipse.cdt.core.language extension-point, allows new pdomLinkageFactories
+ * to be added. However, the {@link IPDOMLinkageFactory} interface which must be implemented is
+ * in an internal package.
+ *
+ * @since 5.6
+ * @noimplement Clients should extend {@link IPDOMASTProcessor.Abstract}.
+ */
+public interface IPDOMASTProcessor {
+ /**
+ * Process the input ast by adding significant symbols to the given output map. Return the
+ * linkage id that should be used to store the result, or {@link ILinkage#NO_LINKAGE_ID} if
+ * the AST contained nothing of significance to this processor.
+ *
+ * @param ast The input AST to be processed.
+ * @param symbols The output map of significant symbols.
+ * @return The linkage-id in which to store the symbols or {@link ILinkage#NO_LINKAGE_ID}
+ * if the AST contained nothing of significance.
+ */
+ public int process(IASTTranslationUnit ast, IIndexSymbols symbols) throws CoreException;
+
+ /**
+ * An abstract class that should be extended by contributors of the extension-point. Extending
+ * this class means that contributors will get default implementations for future additions.
+ */
+ public static abstract class Abstract implements IPDOMASTProcessor {
+ @Override
+ public int process(IASTTranslationUnit ast, IIndexSymbols symbols) throws CoreException {
+ return ILinkage.NO_LINKAGE_ID;
+ }
+ }
+}
diff --git a/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/pdom/AbstractIndexerTask.java b/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/pdom/AbstractIndexerTask.java
index d509b6b16e1..b44872ece24 100644
--- a/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/pdom/AbstractIndexerTask.java
+++ b/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/pdom/AbstractIndexerTask.java
@@ -28,6 +28,7 @@ import java.util.Map;
import java.util.Set;
import org.eclipse.cdt.core.CCorePlugin;
+import org.eclipse.cdt.core.dom.ILinkage;
import org.eclipse.cdt.core.dom.IPDOMIndexerTask;
import org.eclipse.cdt.core.dom.ast.IASTPreprocessorIncludeStatement;
import org.eclipse.cdt.core.dom.ast.IASTTranslationUnit;
@@ -39,6 +40,7 @@ import org.eclipse.cdt.core.index.IIndexFileLocation;
import org.eclipse.cdt.core.index.IIndexInclude;
import org.eclipse.cdt.core.index.IIndexMacro;
import org.eclipse.cdt.core.index.IIndexManager;
+import org.eclipse.cdt.core.index.IPDOMASTProcessor;
import org.eclipse.cdt.core.index.IndexLocationFactory;
import org.eclipse.cdt.core.model.AbstractLanguage;
import org.eclipse.cdt.core.model.ILanguage;
@@ -1196,7 +1198,19 @@ public abstract class AbstractIndexerTask extends PDOMWriter {
FileInAST[] fileKeys= orderedFileKeys.toArray(new FileInAST[orderedFileKeys.size()]);
try {
- addSymbols(ast, fileKeys, fIndex, false, ctx, fTodoTaskUpdater, pm);
+ // The default processing is handled by the indexer task.
+ PDOMWriter.Data data = new PDOMWriter.Data(ast, fileKeys, fIndex);
+ int storageLinkageID = process(ast, data);
+ if (storageLinkageID != ILinkage.NO_LINKAGE_ID)
+ addSymbols(data, storageLinkageID, ctx, fTodoTaskUpdater, pm);
+
+ // Contributed processors now have an opportunity to examine the AST.
+ for(IPDOMASTProcessor processor : PDOMASTProcessorManager.getProcessors(ast)) {
+ data = new PDOMWriter.Data(ast, fileKeys, fIndex);
+ storageLinkageID = processor.process(ast, data);
+ if (storageLinkageID != ILinkage.NO_LINKAGE_ID)
+ addSymbols(data, storageLinkageID, ctx, fTodoTaskUpdater, pm);
+ }
} catch (CoreException e) {
// Avoid parsing files again, that caused an exception to be thrown.
withdrawRequests(linkageID, fileKeys);
diff --git a/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/pdom/PDOMASTProcessorDesc.java b/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/pdom/PDOMASTProcessorDesc.java
new file mode 100644
index 00000000000..a614f44e4d8
--- /dev/null
+++ b/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/pdom/PDOMASTProcessorDesc.java
@@ -0,0 +1,141 @@
+package org.eclipse.cdt.internal.core.pdom;
+
+import java.util.Arrays;
+
+import org.eclipse.cdt.core.CCorePlugin;
+import org.eclipse.cdt.core.dom.ast.IASTTranslationUnit;
+import org.eclipse.cdt.core.index.IPDOMASTProcessor;
+import org.eclipse.cdt.core.model.ICProject;
+import org.eclipse.cdt.core.model.ILanguage;
+import org.eclipse.cdt.core.model.ITranslationUnit;
+import org.eclipse.core.expressions.EvaluationContext;
+import org.eclipse.core.expressions.EvaluationResult;
+import org.eclipse.core.expressions.Expression;
+import org.eclipse.core.expressions.ExpressionConverter;
+import org.eclipse.core.expressions.ExpressionTagNames;
+import org.eclipse.core.resources.IProject;
+import org.eclipse.core.runtime.CoreException;
+import org.eclipse.core.runtime.IConfigurationElement;
+
+/**
+ * Internal container for extensions of org.eclipse.cdt.core.PDOMASTProcessor. The implementation
+ * of the processor is instantiated only after checking the enablement expression (if present) for
+ * the given AST translation unit. This avoids activating the contributing plugin until it is
+ * actually needed.
+ */
+public class PDOMASTProcessorDesc {
+ private static final String Attr_Class = "class"; //$NON-NLS-1$
+
+ private final IConfigurationElement element;
+ private final Expression enablementExpression;
+ private Boolean fStatus = null;
+
+ private String id;
+ private IPDOMASTProcessor processor;
+
+ private static final String VAR_PROJECTNATURES = "projectNatures"; //$NON-NLS-1$
+ private static final String VAR_LANGUAGEID = "languageId"; //$NON-NLS-1$
+
+ /**
+ * An empty implementation of the processor used as a placeholder in descriptors that are unable
+ * to load the contributed class.
+ */
+ private static final IPDOMASTProcessor NULL_PROCESSOR = new IPDOMASTProcessor.Abstract() {
+ };
+
+ public PDOMASTProcessorDesc(IConfigurationElement element) {
+ this.element = element;
+
+ Expression expr = null;
+ IConfigurationElement[] children = element.getChildren(ExpressionTagNames.ENABLEMENT);
+ switch (children.length) {
+ case 0:
+ fStatus = Boolean.TRUE;
+ break;
+ case 1:
+ try {
+ ExpressionConverter parser = ExpressionConverter.getDefault();
+ expr = parser.perform(children[0]);
+ } catch (CoreException e) {
+ CCorePlugin.log("Error in enablement expression of " + id, e); //$NON-NLS-1$
+ }
+ break;
+ default:
+ CCorePlugin.log("Too many enablement expressions for " + id); //$NON-NLS-1$
+ fStatus = Boolean.FALSE;
+ break;
+ }
+ enablementExpression = expr;
+ }
+
+ private boolean matches(ITranslationUnit tu) {
+ // If the enablement expression is missing or structurally invalid, then return immediately
+ if (fStatus != null)
+ return fStatus.booleanValue();
+
+ // If there is no tu, then the enablement expression cannot be evaluated, assume that all
+ // taggers are needed
+ if (tu == null)
+ return true;
+
+ if (enablementExpression != null)
+ try {
+ IProject project = null;
+ ICProject cProject = tu.getCProject();
+ if (cProject != null)
+ project = cProject.getProject();
+
+ EvaluationContext evalContext = new EvaluationContext(null, project);
+
+ // if the project is not accessible, then only taggers that don't care about it will
+ // get a chance to run
+ if (project != null) {
+ String[] natures = project.getDescription().getNatureIds();
+ evalContext.addVariable(VAR_PROJECTNATURES, Arrays.asList(natures));
+ }
+
+ ILanguage language = tu.getLanguage();
+ if (language != null)
+ evalContext.addVariable(VAR_LANGUAGEID, language.getId());
+
+ return enablementExpression.evaluate(evalContext) == EvaluationResult.TRUE;
+ } catch (CoreException e) {
+ CCorePlugin.log("Error while evaluating enablement expression for " + id, e); //$NON-NLS-1$
+ }
+
+ fStatus = Boolean.FALSE;
+ return false;
+ }
+
+ private IPDOMASTProcessor getProcessor() {
+ if (processor == null)
+ synchronized (this) {
+ if (processor == null) {
+ try {
+ processor = (IPDOMASTProcessor) element.createExecutableExtension(Attr_Class);
+ } catch (CoreException e) {
+ String id = element.getDeclaringExtension().getNamespaceIdentifier() + '.'
+ + element.getDeclaringExtension().getSimpleIdentifier();
+ CCorePlugin.log("Error in class attribute of " + id, e); //$NON-NLS-1$
+
+ // mark the tagger with an empty implementation to prevent future load attempts
+ processor = NULL_PROCESSOR;
+ }
+ }
+ }
+
+ return processor;
+ }
+
+ // Activates the plugin if needed.
+ public IPDOMASTProcessor getProcessorFor(IASTTranslationUnit ast) {
+ // If there isn't an ast with an AST-TU accessible, then there is no way to defer processing,
+ // just return the processor and let it try to sort things out. E.g., this happens for built-in
+ // things.
+ if (ast == null)
+ return getProcessor();
+
+ // Otherwise evaluate the enablement expression for this TU
+ return matches(ast.getOriginatingTranslationUnit()) ? getProcessor() : null;
+ }
+}
diff --git a/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/pdom/PDOMASTProcessorManager.java b/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/pdom/PDOMASTProcessorManager.java
new file mode 100644
index 00000000000..945e9b81258
--- /dev/null
+++ b/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/pdom/PDOMASTProcessorManager.java
@@ -0,0 +1,52 @@
+package org.eclipse.cdt.internal.core.pdom;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.List;
+
+import org.eclipse.cdt.core.CCorePlugin;
+import org.eclipse.cdt.core.dom.ast.IASTTranslationUnit;
+import org.eclipse.cdt.core.index.IPDOMASTProcessor;
+import org.eclipse.core.runtime.IConfigurationElement;
+import org.eclipse.core.runtime.Platform;
+
+/**
+ * An internal manager for the org.eclipse.cdt.core.PDOMASTProcessor extension-point.
+ *
+ * @see #getProcessors(IASTTranslationUnit)
+ */
+public class PDOMASTProcessorManager {
+
+ private static final String EXTENSION_POINT = "PDOMASTProcessor"; //$NON-NLS-1$
+
+ private static final List<PDOMASTProcessorDesc> processors = new ArrayList<PDOMASTProcessorDesc>();
+ static {
+ // Load the extensions
+ IConfigurationElement[] elements
+ = Platform.getExtensionRegistry().getConfigurationElementsFor(CCorePlugin.PLUGIN_ID, EXTENSION_POINT);
+ for (IConfigurationElement element : elements)
+ processors.add(new PDOMASTProcessorDesc(element));
+ }
+
+ private PDOMASTProcessorManager() {
+ }
+
+ /**
+ * Returns a list of the contributed PDOMASTProcessors that should be used with the
+ * specific AST. Does not return null.
+ */
+ public static List<IPDOMASTProcessor> getProcessors(IASTTranslationUnit ast) {
+ List<IPDOMASTProcessor> list = null;
+
+ for (PDOMASTProcessorDesc desc : processors) {
+ IPDOMASTProcessor processor = desc.getProcessorFor(ast);
+ if (processor != null) {
+ if (list == null)
+ list = new ArrayList<IPDOMASTProcessor>();
+ list.add(processor);
+ }
+ }
+
+ return list == null ? Collections.<IPDOMASTProcessor>emptyList() : list;
+ }
+}
diff --git a/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/pdom/PDOMWriter.java b/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/pdom/PDOMWriter.java
index 2f78c6eaa0c..69ffd2aba2e 100644
--- a/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/pdom/PDOMWriter.java
+++ b/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/pdom/PDOMWriter.java
@@ -21,6 +21,7 @@ import java.util.Map;
import java.util.Set;
import org.eclipse.cdt.core.CCorePlugin;
+import org.eclipse.cdt.core.dom.ILinkage;
import org.eclipse.cdt.core.dom.ast.IASTDeclSpecifier;
import org.eclipse.cdt.core.dom.ast.IASTFileLocation;
import org.eclipse.cdt.core.dom.ast.IASTName;
@@ -48,6 +49,8 @@ import org.eclipse.cdt.core.dom.ast.cpp.ICPPTemplateParameter;
import org.eclipse.cdt.core.index.IIndexFile;
import org.eclipse.cdt.core.index.IIndexFileLocation;
import org.eclipse.cdt.core.index.IIndexInclude;
+import org.eclipse.cdt.core.index.IIndexSymbols;
+import org.eclipse.cdt.core.index.IPDOMASTProcessor;
import org.eclipse.cdt.core.parser.FileContent;
import org.eclipse.cdt.core.parser.IProblem;
import org.eclipse.cdt.core.parser.ISignificantMacros;
@@ -72,7 +75,7 @@ import org.eclipse.osgi.util.NLS;
* Abstract class to write information from AST.
* @since 4.0
*/
-abstract public class PDOMWriter {
+abstract public class PDOMWriter implements IPDOMASTProcessor {
private static final boolean REPORT_UNKNOWN_BUILTINS = false;
public static class FileInAST {
@@ -135,7 +138,7 @@ abstract public class PDOMWriter {
final ArrayList<IASTPreprocessorIncludeStatement> fIncludes= new ArrayList<IASTPreprocessorIncludeStatement>();
}
- private static class Data {
+ protected static class Data implements IIndexSymbols {
final IASTTranslationUnit fAST;
final FileInAST[] fSelectedFiles;
final IWritableIndex fIndex;
@@ -147,6 +150,44 @@ abstract public class PDOMWriter {
fAST= ast;
fSelectedFiles= selectedFiles;
fIndex= index;
+
+ for(FileInAST file : selectedFiles)
+ fSymbolMap.put(file.includeStatement, new Symbols());
+ }
+
+ @Override
+ public boolean isEmpty() {
+ if (fSymbolMap.isEmpty())
+ return true;
+
+ for (Symbols symbols : fSymbolMap.values())
+ if (!symbols.fNames.isEmpty()
+ || !symbols.fIncludes.isEmpty()
+ || !symbols.fMacros.isEmpty())
+ return false;
+
+ return true;
+ }
+
+ @Override
+ public void add(IASTPreprocessorIncludeStatement owner, IASTName name, IASTName caller) {
+ Symbols lists= fSymbolMap.get(owner);
+ if (lists != null)
+ lists.fNames.add(new IASTName[]{ name, caller });
+ }
+
+ @Override
+ public void add(IASTPreprocessorIncludeStatement owner, IASTPreprocessorIncludeStatement thing) {
+ Symbols lists= fSymbolMap.get(owner);
+ if (lists != null)
+ lists.fIncludes.add(thing);
+ }
+
+ @Override
+ public void add(IASTPreprocessorIncludeStatement owner, IASTPreprocessorStatement thing) {
+ Symbols lists= fSymbolMap.get(owner);
+ if (lists != null)
+ lists.fMacros.add(thing);
}
}
@@ -203,50 +244,45 @@ abstract public class PDOMWriter {
}
/**
- * Extracts symbols from the given AST and adds them to the index.
- *
+ * Extracts symbols from the given AST and adds them to the index. Ignores Data maps that are
+ * empty and ones where storageLinkageID == {@link ILinkage#NO_LINKAGE_ID}.
+ * <p>
* When flushIndex is set to <code>false</code>, you must make sure to flush
* the index after your last write operation.
*/
- final protected void addSymbols(IASTTranslationUnit ast, FileInAST[] selectedFiles,
- IWritableIndex index, boolean flushIndex, FileContext ctx,
- ITodoTaskUpdater taskUpdater, IProgressMonitor pm) throws InterruptedException,
+ final protected void addSymbols(Data data, int storageLinkageID, FileContext ctx, ITodoTaskUpdater taskUpdater, IProgressMonitor pm) throws InterruptedException,
CoreException {
+ if (data.isEmpty()
+ || storageLinkageID == ILinkage.NO_LINKAGE_ID)
+ return;
+
if (fShowProblems) {
fShowInclusionProblems= true;
fShowScannerProblems= true;
fShowSyntaxProblems= true;
}
- Data data= new Data(ast, selectedFiles, index);
- for (FileInAST file : selectedFiles) {
- data.fSymbolMap.put(file.includeStatement, new Symbols());
- }
-
- // Extract symbols from AST.
- extractSymbols(data);
-
// Name resolution.
resolveNames(data, pm);
// Index update.
- storeSymbolsInIndex(data, ctx, flushIndex, pm);
+ storeSymbolsInIndex(data, storageLinkageID, ctx, pm);
// Tasks update.
if (taskUpdater != null) {
Set<IIndexFileLocation> locations= new HashSet<IIndexFileLocation>();
- for (FileInAST file : selectedFiles) {
+ for (FileInAST file : data.fSelectedFiles) {
locations.add(file.fileContentKey.getLocation());
}
- taskUpdater.updateTasks(ast.getComments(), locations.toArray(new IIndexFileLocation[locations.size()]));
+ taskUpdater.updateTasks(data.fAST.getComments(), locations.toArray(new IIndexFileLocation[locations.size()]));
}
if (!data.fStati.isEmpty()) {
List<IStatus> stati = data.fStati;
String path= null;
- if (selectedFiles.length > 0) {
- path= selectedFiles[selectedFiles.length - 1].fileContentKey.getLocation().getURI().getPath();
+ if (data.fSelectedFiles.length > 0) {
+ path= data.fSelectedFiles[data.fSelectedFiles.length - 1].fileContentKey.getLocation().getURI().getPath();
} else {
- path= ast.getFilePath().toString();
+ path= data.fAST.getFilePath().toString();
}
String msg= NLS.bind(Messages.PDOMWriter_errorWhileParsing, path);
if (stati.size() == 1) {
@@ -262,10 +298,9 @@ abstract public class PDOMWriter {
}
}
- private void storeSymbolsInIndex(final Data data, FileContext ctx, boolean flushIndex, IProgressMonitor pm)
+ private void storeSymbolsInIndex(final Data data, int storageLinkageID, FileContext ctx, IProgressMonitor pm)
throws InterruptedException, CoreException {
final IIndexFragmentFile newFile= ctx == null ? null : ctx.fNewFile;
- final int linkageID= data.fAST.getLinkage().getLinkageID();
for (int i= 0; i < data.fSelectedFiles.length; i++) {
if (pm.isCanceled())
return;
@@ -276,13 +311,13 @@ abstract public class PDOMWriter {
trace("Indexer: adding " + fileInAST.fileContentKey.getLocation().getURI()); //$NON-NLS-1$
}
Throwable th= null;
- YieldableIndexLock lock = new YieldableIndexLock(data.fIndex, flushIndex);
+ YieldableIndexLock lock = new YieldableIndexLock(data.fIndex, false);
lock.acquire();
try {
final boolean isReplacement= ctx != null && fileInAST.includeStatement == null;
IIndexFragmentFile ifile= null;
if (!isReplacement || newFile == null) {
- ifile= storeFileInIndex(data, fileInAST, linkageID, lock);
+ ifile= storeFileInIndex(data, fileInAST, storageLinkageID, lock);
reportFileWrittenToIndex(fileInAST, ifile);
}
@@ -389,9 +424,17 @@ abstract public class PDOMWriter {
fStatistics.fResolutionTime += System.currentTimeMillis() - start;
}
- private void extractSymbols(Data data) throws CoreException {
+ @Override
+ public int process(final IASTTranslationUnit ast, final IIndexSymbols symbols) throws CoreException {
+ if (!(symbols instanceof Data)) {
+ // TODO Fix this case -- the old implementation relies on the symbol map being exactly
+ // as expected.
+ CCorePlugin.log(IStatus.ERROR, "Default processor must receive expected Data type"); //$NON-NLS-1$
+ return ILinkage.NO_LINKAGE_ID;
+ }
+
int unresolvedIncludes= 0;
- final IASTTranslationUnit ast = data.fAST;
+ Data data = (Data) symbols;
final Map<IASTPreprocessorIncludeStatement, Symbols> symbolMap = data.fSymbolMap;
IASTPreprocessorStatement[] stmts = ast.getAllPreprocessorStatements();
@@ -404,7 +447,7 @@ abstract public class PDOMWriter {
IASTPreprocessorIncludeStatement owner = astLoc.getContextInclusionStatement();
final boolean updateSource= symbolMap.containsKey(owner);
if (updateSource) {
- addToMap(symbolMap, owner, include);
+ symbols.add(owner, include);
}
if (include.isActive()) {
if (!include.isResolved()) {
@@ -421,7 +464,7 @@ abstract public class PDOMWriter {
IASTFileLocation sourceLoc = stmt.getFileLocation();
if (sourceLoc != null) { // skip built-ins and command line macros
IASTPreprocessorIncludeStatement owner = sourceLoc.getContextInclusionStatement();
- addToMap(symbolMap, owner, stmt);
+ symbols.add(owner, stmt);
}
}
}
@@ -444,7 +487,7 @@ abstract public class PDOMWriter {
IASTFileLocation nameLoc = name.getFileLocation();
if (nameLoc != null) {
IASTPreprocessorIncludeStatement owner= nameLoc.getContextInclusionStatement();
- addToMap(symbolMap, owner, new IASTName[] { name, caller });
+ symbols.add(owner, name, caller);
}
}
}
@@ -459,7 +502,7 @@ abstract public class PDOMWriter {
IASTFileLocation nameLoc = name.getFileLocation();
if (nameLoc != null) {
IASTPreprocessorIncludeStatement owner= nameLoc.getContextInclusionStatement();
- addToMap(symbolMap, owner, new IASTName[] { name, null });
+ symbols.add(owner, name, null);
}
}
}
@@ -484,6 +527,8 @@ abstract public class PDOMWriter {
reportProblem(problem);
}
}
+
+ return ast.getLinkage().getLinkageID();
}
protected final boolean isRequiredReference(IASTName name) {
@@ -516,26 +561,7 @@ abstract public class PDOMWriter {
return false;
}
- private void addToMap(Map<IASTPreprocessorIncludeStatement, Symbols> symbolMap, IASTPreprocessorIncludeStatement owner, IASTName[] thing) {
- Symbols lists= symbolMap.get(owner);
- if (lists != null)
- lists.fNames.add(thing);
- }
-
- private void addToMap(Map<IASTPreprocessorIncludeStatement, Symbols> symbolMap, IASTPreprocessorIncludeStatement owner, IASTPreprocessorIncludeStatement thing) {
- Symbols lists= symbolMap.get(owner);
- if (lists != null)
- lists.fIncludes.add(thing);
- }
-
- private void addToMap(Map<IASTPreprocessorIncludeStatement, Symbols> symbolMap,
- IASTPreprocessorIncludeStatement owner, IASTPreprocessorStatement thing) {
- Symbols lists= symbolMap.get(owner);
- if (lists != null)
- lists.fMacros.add(thing);
- }
-
- private IIndexFragmentFile storeFileInIndex(Data data, FileInAST astFile, int linkageID,
+ private IIndexFragmentFile storeFileInIndex(Data data, FileInAST astFile, int storageLinkageID,
YieldableIndexLock lock) throws CoreException, InterruptedException {
final IWritableIndex index = data.fIndex;
IIndexFragmentFile file;
@@ -548,8 +574,8 @@ abstract public class PDOMWriter {
IIndexFileLocation location = fileKey.getLocation();
ISignificantMacros significantMacros = fileKey.getSignificantMacros();
- IIndexFragmentFile oldFile = index.getWritableFile(linkageID, location, significantMacros);
- file= index.addUncommittedFile(linkageID, location, significantMacros);
+ IIndexFragmentFile oldFile = index.getWritableFile(storageLinkageID, location, significantMacros);
+ file= index.addUncommittedFile(storageLinkageID, location, significantMacros);
try {
boolean pragmaOnce= owner != null ? owner.hasPragmaOnceSemantics() : data.fAST.hasPragmaOnceSemantics();
file.setPragmaOnceSemantics(pragmaOnce);
@@ -584,7 +610,7 @@ abstract public class PDOMWriter {
}
}
IncludeInformation[] includeInfoArray= includeInfos.toArray(new IncludeInformation[includeInfos.size()]);
- index.setFileContent(file, linkageID, includeInfoArray, macros, names, fResolver, lock);
+ index.setFileContent(file, storageLinkageID, includeInfoArray, macros, names, fResolver, lock);
}
file.setTimestamp(astFile.hasError ? 0 : astFile.timestamp);
file.setSourceReadTime(astFile.sourceReadTime);
diff --git a/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/pdom/dom/PDOMLinkage.java b/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/pdom/dom/PDOMLinkage.java
index b6e2d68c186..c5d8997fc73 100644
--- a/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/pdom/dom/PDOMLinkage.java
+++ b/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/pdom/dom/PDOMLinkage.java
@@ -56,8 +56,12 @@ import org.eclipse.core.runtime.CoreException;
import org.eclipse.core.runtime.IProgressMonitor;
/**
- * This class represents a collection of symbols that can be linked together at
- * link time. These are generally global symbols specific to a given language.
+ * The top-level node in the PDOM storage format. A linkage is a collection of nodes
+ * that can be linked with references. Several linkages can be created for an input
+ * AST.
+ *
+ * TODO Move this to a public interface and discuss the extension point (that already
+ * exists).
*/
public abstract class PDOMLinkage extends PDOMNamedNode implements IIndexLinkage, IIndexBindingConstants {
// Record offsets.
@@ -84,13 +88,13 @@ public abstract class PDOMLinkage extends PDOMNamedNode implements IIndexLinkage
fDatabase= pdom.getDB();
}
- protected PDOMLinkage(PDOM pdom, String languageId, char[] name) throws CoreException {
+ protected PDOMLinkage(PDOM pdom, String linkageID, char[] name) throws CoreException {
super(pdom.getDB(), name);
final Database db= pdom.getDB();
fPDOM= pdom;
fDatabase= db;
- db.putRecPtr(record + ID_OFFSET, db.newString(languageId).getRecord());
+ db.putRecPtr(record + ID_OFFSET, db.newString(linkageID).getRecord());
pdom.insertLinkage(this);
}
diff --git a/core/org.eclipse.cdt.core/plugin.properties b/core/org.eclipse.cdt.core/plugin.properties
index e6208db94b6..f06189e829e 100755
--- a/core/org.eclipse.cdt.core/plugin.properties
+++ b/core/org.eclipse.cdt.core/plugin.properties
@@ -122,6 +122,7 @@ projectConverter.name = Project converter
CIndex.name = C/C++ Index
externalSettingsProvider.name = External Settings provider
tagger.name = Parser Node Tagger Extension Point
+PDOMASTProcessor.name = PDOM AST Processor Extension Point
GeneratePDOMApplication.name = GeneratePDOM
defaultProvider.name = Default Provider
templatesExtensionPoint.name = Templates Extension point
diff --git a/core/org.eclipse.cdt.core/plugin.xml b/core/org.eclipse.cdt.core/plugin.xml
index 0d4bbd6b960..3d6764c38ec 100644
--- a/core/org.eclipse.cdt.core/plugin.xml
+++ b/core/org.eclipse.cdt.core/plugin.xml
@@ -43,6 +43,7 @@
<extension-point id="CIndex" name="%CIndex.name" schema="schema/CIndex.exsd"/>
<extension-point id="externalSettingsProvider" name="%externalSettingsProvider.name" schema="schema/externalSettingsProvider.exsd"/>
<extension-point id="tagger" name="%tagger.name" schema="schema/tagger.exsd"/>
+ <extension-point id="PDOMASTProcessor" name="%PDOMASTProcessor.name" schema="schema/PDOMASTProcessor.exsd"/>
<!-- =================================================================================== -->
<!-- CProjectDescriptionStorage provides addition types of project description storage -->
<!-- =================================================================================== -->
diff --git a/core/org.eclipse.cdt.core/schema/PDOMASTProcessor.exsd b/core/org.eclipse.cdt.core/schema/PDOMASTProcessor.exsd
new file mode 100644
index 00000000000..fb087747692
--- /dev/null
+++ b/core/org.eclipse.cdt.core/schema/PDOMASTProcessor.exsd
@@ -0,0 +1,131 @@
+<?xml version='1.0' encoding='UTF-8'?>
+<!-- Schema file written by PDE -->
+<schema targetNamespace="org.eclipse.cdt.core" xmlns="http://www.w3.org/2001/XMLSchema">
+<annotation>
+ <appInfo>
+ <meta.schema plugin="org.eclipse.cdt.core" id="PDOMASTProcessor" name="PDOM AST Processor"/>
+ </appInfo>
+ <documentation>
+ This extension point allows extensions to contribute to the information that is written to the .pdom file. After the AST has been parsed, all contributors are provided a chance to process the AST&apos;s translation units while the .pdom is being updated.
+ </documentation>
+ </annotation>
+
+ <include schemaLocation="schema://org.eclipse.core.expressions/schema/expressionLanguage.exsd"/>
+
+ <element name="extension">
+ <annotation>
+ <appInfo>
+ <meta.element />
+ </appInfo>
+ </annotation>
+ <complexType>
+ <sequence>
+ <element ref="processor" minOccurs="1" maxOccurs="unbounded"/>
+ </sequence>
+ <attribute name="point" type="string" use="required">
+ <annotation>
+ <documentation>
+ a fully qualified identifier of the target extension point
+ </documentation>
+ </annotation>
+ </attribute>
+ <attribute name="id" type="string">
+ <annotation>
+ <documentation>
+ an optional identifier of the extension instance
+ </documentation>
+ </annotation>
+ </attribute>
+ <attribute name="name" type="string">
+ <annotation>
+ <documentation>
+ an optional name of the extension instance
+ </documentation>
+ <appInfo>
+ <meta.attribute translatable="true"/>
+ </appInfo>
+ </annotation>
+ </attribute>
+ </complexType>
+ </element>
+
+ <element name="processor">
+ <complexType>
+ <sequence>
+ <element ref="enablement" minOccurs="0" maxOccurs="1"/>
+ </sequence>
+ <attribute name="class" type="string" use="required">
+ <annotation>
+ <documentation>
+
+ </documentation>
+ <appInfo>
+ <meta.attribute kind="java" basedOn=":org.eclipse.cdt.core.index.IPDOMASTProcessor"/>
+ </appInfo>
+ </annotation>
+ </attribute>
+ </complexType>
+ </element>
+
+ <annotation>
+ <appInfo>
+ <meta.section type="since"/>
+ </appInfo>
+ <documentation>
+ 8.3
+ </documentation>
+ </annotation>
+
+ <annotation>
+ <appInfo>
+ <meta.section type="examples"/>
+ </appInfo>
+ <documentation>
+ The following is an example of a Tagger contribution:
+&lt;p&gt;
+&lt;pre&gt;
+&lt;extension
+ point=&quot;org.eclipse.cdt.core.PDOMASTProcessor&quot;
+ id=&quot;example&quot;
+ name=&quot;Example PDOM AST Processor&quot;&gt;
+ &lt;bindingTagger
+ local-id=&quot;my-processor&quot;
+ class=&quot;com.example.internal.ExamplePDOMASTProcessor&quot;&gt;
+ &lt;enablement&gt;
+ &lt;with variable=&quot;projectNatures&quot;&gt;
+ &lt;iterate operator=&quot;or&quot;&gt;
+ &lt;equals value=&quot;com.example.my-nature&quot;/&gt;
+ &lt;/iterate&gt;
+ &lt;/with&gt;
+ &lt;/enablement&gt;
+ &lt;/bindingTagger&gt;
+&lt;/extension&gt;
+&lt;/pre&gt;
+&lt;/p&gt;
+ </documentation>
+ </annotation>
+
+ <annotation>
+ <appInfo>
+ <meta.section type="apiInfo"/>
+ </appInfo>
+ <documentation>
+ The contributed class must implement &lt;code&gt;org.eclipse.cdt.core.index.IPDOMASTProcessor&lt;/code&gt; interface.
+ </documentation>
+ </annotation>
+
+
+ <annotation>
+ <appInfo>
+ <meta.section type="copyright"/>
+ </appInfo>
+ <documentation>
+ Copyright (c) 2013 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
+ </documentation>
+ </annotation>
+
+</schema>

Back to the top