1
0
Fork 0
mirror of https://github.com/eclipse-cdt/cdt synced 2025-04-29 19:45:01 +02:00

CModelBuilder and scalability problems

This commit is contained in:
Hoda Amer 2004-04-12 15:23:23 +00:00
parent 54490364bb
commit 9e4f258b9a
11 changed files with 75 additions and 143 deletions

View file

@ -1,3 +1,8 @@
2004-04-12 Hoda Amer
CModelBuilder and scalability problems: Building the CModel takes a long time
when translation unit has lots of children (25,000 children taking ~ 45 sec to build model).
Revising Parent.addChild() and TranslationUnit.removeChildren() (now 25,000 children taking ~ 160 ms).
2004-04-07 David Inglis
Fixed event problem

View file

@ -213,9 +213,7 @@ public class CContainer extends Openable implements ICContainer {
//e.printStackTrace();
throw new CModelException(e);
}
ICElement[] children = new ICElement[vChildren.size()];
vChildren.toArray(children);
info.setChildren(children);
info.setChildren(vChildren);
if (info instanceof CContainerInfo) {
((CContainerInfo) info).setNonCResources(null);
}

View file

@ -6,6 +6,8 @@ package org.eclipse.cdt.internal.core.model;
*/
import java.io.File;
import java.util.ArrayList;
import java.util.List;
import org.eclipse.cdt.core.model.ICElement;
import org.eclipse.core.resources.IResource;
@ -16,11 +18,6 @@ import org.eclipse.core.resources.IResource;
*/
class CElementInfo {
/**
* Shared empty collection used for efficiency.
*/
static Object[] NO_NON_C_RESOURCES = new Object[] {};
protected CElement element;
/**
@ -28,12 +25,7 @@ class CElementInfo {
* object. This is an empty array if this element has
* no children.
*/
protected ICElement[] fChildren;
/**
* Shared empty collection used for efficiency.
*/
protected static ICElement[] fgEmptyChildren = new ICElement[]{};
protected List fChildren;
/**
* Is the structure of this element known
@ -45,7 +37,7 @@ class CElementInfo {
protected CElementInfo(CElement element) {
this.element = element;
fChildren = fgEmptyChildren;
fChildren = new ArrayList();
}
protected CElement getElement() {
@ -53,41 +45,21 @@ class CElementInfo {
}
protected void addChild(ICElement child) {
if (fChildren == fgEmptyChildren) {
setChildren(new ICElement[] {child});
} else {
if (!includesChild(child)) {
setChildren(growAndAddToArray(fChildren, child));
}
}
fChildren.add(child);
}
protected ICElement[] getChildren() {
return fChildren;
ICElement[] array= new ICElement[fChildren.size()];
return (ICElement[]) fChildren.toArray( array );
}
/**
* Adds the new element to a new array that contains all of the elements of the old array.
* Returns the new array.
*/
protected ICElement[] growAndAddToArray(ICElement[] array, ICElement addition) {
ICElement[] old = array;
array = new ICElement[old.length + 1];
System.arraycopy(old, 0, array, 0, old.length);
array[old.length] = addition;
return array;
}
/**
* Returns <code>true</code> if this child is in my children collection
*/
protected boolean includesChild(ICElement child) {
for (int i= 0; i < fChildren.length; i++) {
if (fChildren[i].equals(child)) {
return true;
}
}
protected boolean includesChild(ICElement child) {
if(fChildren.contains(child))
return true;
return false;
}
@ -98,42 +70,20 @@ class CElementInfo {
return fIsStructureKnown;
}
/**
* Returns an array with all the same elements as the specified array except for
* the element to remove. Assumes that the deletion is contained in the array.
*/
protected ICElement[] removeAndShrinkArray(ICElement[] array, ICElement deletion) {
ICElement[] old = array;
array = new ICElement[old.length - 1];
int j = 0;
for (int i = 0; i < old.length; i++) {
if (!old[i].equals(deletion)) {
array[j] = old[i];
} else {
System.arraycopy(old, i + 1, array, j, old.length - (i + 1));
return array;
}
j++;
}
return array;
}
protected void removeChild(ICElement child) {
if (includesChild(child)) {
setChildren(removeAndShrinkArray(fChildren, child));
}
fChildren.remove(child);
}
protected void removeChildren () {
fChildren = fgEmptyChildren;
fChildren.clear();
}
protected void setChildren(ICElement[] children) {
fChildren = children;
protected void setChildren(List children) {
fChildren.addAll(children);
}
protected boolean hasChildren() {
return fChildren.length > 0;
return fChildren.size() > 0;
}
protected void setChanged() {

View file

@ -70,7 +70,7 @@ public class CModelBuilder {
private IASTCompilationUnit compilationUnit;
// indicator if the unit has parse errors
private boolean hasNoErrors = false;
public CModelBuilder(org.eclipse.cdt.internal.core.model.TranslationUnit tu) {
this.translationUnit = tu ;
this.newElements = new HashMap();
@ -150,6 +150,7 @@ public class CModelBuilder {
public Map parse(boolean quickParseMode) throws Exception {
long startTime = System.currentTimeMillis();
try
{
compilationUnit = parse( translationUnit, quickParseMode, true);
@ -160,7 +161,9 @@ public class CModelBuilder {
Util.debugLog( "Parse Exception in CModelBuilder", IDebugLogConstants.MODEL ); //$NON-NLS-1$
//e.printStackTrace();
}
long startTime = System.currentTimeMillis();
Util.debugLog("CModel parsing: "+ ( System.currentTimeMillis() - startTime ) + "ms", IDebugLogConstants.MODEL); //$NON-NLS-1$ //$NON-NLS-2$
startTime = System.currentTimeMillis();
try
{
generateModelElements();
@ -170,13 +173,12 @@ public class CModelBuilder {
catch( NullPointerException npe )
{
Util.debugLog( "NullPointer exception in CModelBuilder", IDebugLogConstants.MODEL); //$NON-NLS-1$
//npe.printStackTrace();
}
// For the debuglog to take place, you have to call
// Util.setDebugging(true);
// Or set debug to true in the core plugin preference
Util.debugLog("CModel build: "+ ( System.currentTimeMillis() - startTime ) + "ms", IDebugLogConstants.MODEL); //$NON-NLS-1$ //$NON-NLS-2$
Util.debugLog("CModel building: "+ ( System.currentTimeMillis() - startTime ) + "ms", IDebugLogConstants.MODEL); //$NON-NLS-1$ //$NON-NLS-2$
return this.newElements;
}
@ -344,6 +346,7 @@ public class CModelBuilder {
element.setLines( macro.getStartingLine(), macro.getEndingLine() );
this.newElements.put(element, element.getElementInfo());
return element;
}
private Namespace createNamespace(Parent parent, IASTNamespaceDefinition nsDef){
@ -656,4 +659,10 @@ public class CModelBuilder {
return element;
}
/**
* @return Returns the newElements.
*/
public Map getNewElements() {
return newElements;
}
}

View file

@ -41,7 +41,7 @@ public class CModelInfo extends OpenableInfo {
}
}
if (index == 0) {
return NO_NON_C_RESOURCES;
return new Object[] {}; // NO_NON_C_RESOURCES
}
if (index < length) {
System.arraycopy(nonCProjects, 0, nonCProjects = new Object[index], 0, index);

View file

@ -4,6 +4,9 @@ package org.eclipse.cdt.internal.core.model;
* (c) Copyright QNX Software Systems Ltd. 2002.
* All Rights Reserved.
*/
import java.util.ArrayList;
import java.util.List;
import org.eclipse.cdt.core.CCorePlugin;
import org.eclipse.cdt.core.model.ICElement;
import org.eclipse.cdt.core.model.ICModelStatus;
@ -24,7 +27,7 @@ public class CModelStatus extends Status implements ICModelStatus, ICModelStatus
* The elements related to the failure, or <code>null</code>
* if no elements are involved.
*/
protected ICElement[] fElements = new ICElement[0];
protected List fElements = new ArrayList();
/**
* The path related to the failure, or <code>null</code>
* if no path is involved.
@ -59,7 +62,7 @@ public class CModelStatus extends Status implements ICModelStatus, ICModelStatus
*/
public CModelStatus(int code) {
super(ERROR, CCorePlugin.PLUGIN_ID, code, "CModelStatus", null); //$NON-NLS-1$
fElements= CElementInfo.fgEmptyChildren;
fElements.clear();
}
/**
@ -68,7 +71,8 @@ public class CModelStatus extends Status implements ICModelStatus, ICModelStatus
*/
public CModelStatus(int code, ICElement[] elements) {
super(ERROR, CCorePlugin.PLUGIN_ID, code, "CModelStatus", null); //$NON-NLS-1$
fElements= elements;
for(int i=0; i<elements.length; ++i)
fElements.add(elements[i]);
fPath= null;
}
@ -81,7 +85,7 @@ public class CModelStatus extends Status implements ICModelStatus, ICModelStatus
public CModelStatus(int severity, int code, String string) {
super(severity, CCorePlugin.PLUGIN_ID, code, "CModelStatus", null); //$NON-NLS-1$
fElements= CElementInfo.fgEmptyChildren;
fElements.clear();
fPath= null;
fString = string;
}
@ -91,7 +95,7 @@ public class CModelStatus extends Status implements ICModelStatus, ICModelStatus
*/
public CModelStatus(int code, Throwable throwable) {
super(ERROR, CCorePlugin.PLUGIN_ID, code, "CModelStatus", throwable); //$NON-NLS-1$
fElements= CElementInfo.fgEmptyChildren;
fElements.clear();
}
/**
@ -99,7 +103,7 @@ public class CModelStatus extends Status implements ICModelStatus, ICModelStatus
*/
public CModelStatus(int code, IPath path) {
super(ERROR, CCorePlugin.PLUGIN_ID, code, "CModelStatus", null); //$NON-NLS-1$
fElements= CElementInfo.fgEmptyChildren;
fElements.clear();
fPath= path;
}
@ -150,7 +154,7 @@ public class CModelStatus extends Status implements ICModelStatus, ICModelStatus
* @see ICModelStatus
*/
public ICElement[] getElements() {
return fElements;
return (ICElement[])fElements.toArray(new ICElement[fElements.size()]);
}
/**

View file

@ -10,6 +10,7 @@ import java.util.ArrayList;
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.CCProjectNature;
@ -425,8 +426,6 @@ public class CProject extends Openable implements ICProject {
System.arraycopy(children, 0, roots, 0, length);
return roots;
//return computeSourceRoots();
}
/**
@ -441,10 +440,10 @@ public class CProject extends Openable implements ICProject {
if (pinfo.sourceRoots != null) {
roots = pinfo.sourceRoots;
} else {
roots = pinfo.sourceRoots = computeSourceRoots();
roots = pinfo.sourceRoots = (ISourceRoot[])computeSourceRoots().toArray(new ISourceRoot[computeSourceRoots().size()]);
}
} else {
roots = computeSourceRoots();
roots = (ISourceRoot[])computeSourceRoots().toArray(new ISourceRoot[computeSourceRoots().size()]);
}
return roots;
}
@ -535,7 +534,7 @@ public class CProject extends Openable implements ICProject {
return validInfo;
}
protected ISourceRoot[] computeSourceRoots() throws CModelException {
protected List computeSourceRoots() throws CModelException {
IPathEntry[] entries = getResolvedPathEntries();
ArrayList list = new ArrayList(entries.length);
for (int i = 0; i < entries.length; i++) {
@ -547,9 +546,7 @@ public class CProject extends Openable implements ICProject {
}
}
}
ISourceRoot[] roots = new ISourceRoot[list.size()];
list.toArray(roots);
return roots;
return list;
}
protected boolean computeSourceRoots(OpenableInfo info, IResource res) throws CModelException {

View file

@ -114,9 +114,7 @@ public class IncludeReference extends Openable implements IIncludeReference {
}
}
}
ICElement[] children = new ICElement[vChildren.size()];
vChildren.toArray(children);
info.setChildren(children);
info.setChildren(vChildren);
return true;
}

View file

@ -78,9 +78,7 @@ public class SourceRoot extends CContainer implements ISourceRoot {
//e.printStackTrace();
throw new CModelException(e);
}
ICElement[] children = new ICElement[vChildren.size()];
vChildren.toArray(children);
info.setChildren(children);
info.setChildren(vChildren);
if (info instanceof CContainerInfo) {
((CContainerInfo) info).setNonCResources(null);
}

View file

@ -11,20 +11,24 @@ import java.util.Iterator;
import java.util.Map;
import org.eclipse.cdt.core.CCorePlugin;
import org.eclipse.cdt.core.model.*;
import org.eclipse.cdt.core.model.CModelException;
import org.eclipse.cdt.core.model.IBuffer;
import org.eclipse.cdt.core.model.ICElement;
import org.eclipse.cdt.core.model.IInclude;
import org.eclipse.cdt.core.model.IParent;
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.core.model.IUsing;
import org.eclipse.cdt.core.model.IWorkingCopy;
import org.eclipse.core.resources.IFile;
import org.eclipse.core.resources.IResource;
import org.eclipse.core.runtime.IPath;
import org.eclipse.core.runtime.IProgressMonitor;
import org.eclipse.core.runtime.IStatus;
import org.eclipse.core.runtime.Status;
import org.eclipse.core.runtime.jobs.Job;
/**
* @see ITranslationUnit
@ -473,19 +477,28 @@ public class TranslationUnit extends Openable implements ITranslationUnit {
* Parse the buffer contents of this element.
*/
public Map parse(){
removeChildren(this);
final CModelBuilder modelBuilder = new CModelBuilder(this);
final boolean quickParseMode = ! (CCorePlugin.getDefault().useStructuralParseMode());
try {
removeChildren();
CModelBuilder modelBuilder = new CModelBuilder(this);
boolean quickParseMode = ! (CCorePlugin.getDefault().useStructuralParseMode());
return modelBuilder.parse(quickParseMode);
return modelBuilder.parse(quickParseMode);
} catch (Exception e) {
// FIXME: use the debug log for this exception.
//System.out.println(e);
// use the debug log for this exception.
Util.debugLog( "Exception in CModelBuilder", IDebugLogConstants.MODEL); //$NON-NLS-1$
return null;
}
}
}
public void removeChildren(ICElement element){
if (element instanceof Parent){
Parent parent = (Parent) element;
ICElement[] children = parent.getChildren();
for(int i =0; i< children.length; ++i){
removeChildren(children[i]);
}
parent.removeChildren();
}
}
}

View file

@ -5,7 +5,6 @@ package org.eclipse.cdt.internal.core.model;
* All Rights Reserved.
*/
import org.eclipse.cdt.core.model.ICElement;
import org.eclipse.cdt.core.model.ISourceRange;
import org.eclipse.core.runtime.IPath;
@ -24,45 +23,6 @@ class TranslationUnitInfo extends OpenableInfo {
super(element);
}
protected boolean hasChildren() {
return true;
}
protected ICElement [] getChildren() {
// CHECKPOINT: replacing the parsing done here before
return fChildren;
}
/*
protected Map parse(InputStream in, boolean requiresLineNumbers) {
try {
removeChildren();
if (CCorePlugin.getDefault().useNewParser()) {
// new parser
CModelBuilder modelBuilder = new CModelBuilder((TranslationUnit)getElement());
return (modelBuilder.parse(requiresLineNumbers));
} else {
// cdt 1.0 parser
ModelBuilder modelBuilder= new ModelBuilder((TranslationUnit)getElement());
CStructurizer.getCStructurizer().parse(modelBuilder, in);
return null;
}
} catch (Exception e) {
System.out.println(e);
return null;
}
}
protected Map parse(String buf, boolean requiresLineNumbers) {
// CHECKPOINT: Parsing a string using the StringBufferInputStream
// FIXME: quick fix for the IBinary which uses fake translationUnit
if (buf != null) {
StringBufferInputStream in = new StringBufferInputStream (buf);
return (parse (in, requiresLineNumbers));
}
return null;
}
*/
/* Overide the SourceManipulation for the range. */
protected ISourceRange getSourceRange() {
IPath location = ((TranslationUnit)getElement()).getLocation();