From c3d3296b60ce2be3300f0742221fca5eca5a14aa Mon Sep 17 00:00:00 2001 From: Anton Leherbauer Date: Thu, 12 May 2011 13:41:58 +0000 Subject: [PATCH] Bug 343538 - Index not updated when complete folder deleted --- .../internal/index/tests/IndexBugsTests.java | 85 ++++++++++++++++++- .../internal/core/model/DeltaProcessor.java | 43 ++++------ .../core/pdom/indexer/DeltaAnalyzer.java | 17 ++-- 3 files changed, 109 insertions(+), 36 deletions(-) diff --git a/core/org.eclipse.cdt.core.tests/parser/org/eclipse/cdt/internal/index/tests/IndexBugsTests.java b/core/org.eclipse.cdt.core.tests/parser/org/eclipse/cdt/internal/index/tests/IndexBugsTests.java index e5488f1d415..9ff17488f06 100644 --- a/core/org.eclipse.cdt.core.tests/parser/org/eclipse/cdt/internal/index/tests/IndexBugsTests.java +++ b/core/org.eclipse.cdt.core.tests/parser/org/eclipse/cdt/internal/index/tests/IndexBugsTests.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2006, 2010 Wind River Systems, Inc. and others. + * Copyright (c) 2006, 2011 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 @@ -17,6 +17,8 @@ import java.io.File; import java.io.IOException; import java.io.InputStream; import java.lang.reflect.Field; +import java.util.HashSet; +import java.util.Set; import java.util.regex.Pattern; import junit.framework.TestSuite; @@ -89,10 +91,18 @@ import org.eclipse.core.resources.IFolder; import org.eclipse.core.resources.IProject; import org.eclipse.core.resources.IProjectDescription; import org.eclipse.core.resources.IResource; +import org.eclipse.core.resources.IResourceVisitor; +import org.eclipse.core.resources.IWorkspace; +import org.eclipse.core.resources.ResourcesPlugin; +import org.eclipse.core.resources.WorkspaceJob; import org.eclipse.core.runtime.CoreException; import org.eclipse.core.runtime.IPath; +import org.eclipse.core.runtime.IProgressMonitor; +import org.eclipse.core.runtime.IStatus; import org.eclipse.core.runtime.NullProgressMonitor; import org.eclipse.core.runtime.Path; +import org.eclipse.core.runtime.Status; +import org.eclipse.core.runtime.jobs.Job; public class IndexBugsTests extends BaseTestCase { private static final int INDEX_WAIT_TIME = 8000; @@ -2317,4 +2327,77 @@ public class IndexBugsTests extends BaseTestCase { assertTrue(offset1 != offset2); } + + public void testUpdateOnFolderRemove_343538() throws Exception { + IIndexBinding[] r; + + final IProject prj = fCProject.getProject(); + final IFolder root= prj.getFolder("root"); + root.create(true, false, null); + assertTrue(root.exists()); + IFolder child1 = root.getFolder("child1"); + child1.create(true, false, null); + assertTrue(child1.exists()); + IFolder child2 = root.getFolder("child2"); + child2.create(true, false, null); + assertTrue(child2.exists()); + + TestSourceReader.createFile(child1, "a.c", "void bug343538() {}"); + TestSourceReader.createFile(child2, "b.c", "void bug343538();"); + waitForIndexer(fCProject); + + final IIndex index= CCorePlugin.getIndexManager().getIndex(fCProject); + index.acquireReadLock(); + try { + r = index.findBindings("bug343538".toCharArray(), IndexFilter.ALL, null); + assertEquals(1, r.length); + IIndexName[] names = index.findNames(r[0], IIndex.FIND_DECLARATIONS_DEFINITIONS); + assertEquals(2, names.length); + } finally { + index.releaseReadLock(); + } + + // Collect files and folders + final Set files = new HashSet(); + final Set folders = new HashSet(); + folders.add(root); + root.accept(new IResourceVisitor() { + public boolean visit(final IResource resource) throws CoreException { + if (resource instanceof IFile) { + files.add((IFile) resource); + } else if (resource instanceof IFolder) { + folders.add((IFolder) resource); + } + return true; + } + }); + + Job job = new WorkspaceJob("Delete folder") { + @Override + public IStatus runInWorkspace(final IProgressMonitor monitor) throws CoreException { + IWorkspace ws = ResourcesPlugin.getWorkspace(); + ws.delete(files.toArray(new IResource[files.size()]), IResource.FORCE, null); + ws.delete(folders.toArray(new IResource[folders.size()]), IResource.FORCE, null); + return Status.OK_STATUS; + } + }; + job.schedule(); + job.join(); + Thread.sleep(1000); + waitForIndexer(fCProject); + + index.acquireReadLock(); + try { + r = index.findBindings("bug343538".toCharArray(), IndexFilter.ALL, null); + if (r.length == 1) { + IIndexName[] names = index.findNames(r[0], IIndex.FIND_DECLARATIONS_DEFINITIONS); + assertEquals(0, names.length); + } else { + assertEquals(0, r.length); + } + } finally { + index.releaseReadLock(); + } + } + } \ No newline at end of file diff --git a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/DeltaProcessor.java b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/DeltaProcessor.java index b91c40f18df..5275241ab9d 100644 --- a/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/DeltaProcessor.java +++ b/core/org.eclipse.cdt.core/model/org/eclipse/cdt/internal/core/model/DeltaProcessor.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2002, 2010 IBM Corporation and others. + * Copyright (c) 2002, 2011 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 @@ -423,25 +423,21 @@ final class DeltaProcessor { * relevant CModels. */ public ICElementDelta[] processResourceDelta(IResourceDelta changes) { - - try { - ICElement root = CModelManager.getDefault().getCModel(); - // get the workspace delta, and start processing there. - IResourceDelta[] deltas = changes.getAffectedChildren(); - ICElementDelta[] translatedDeltas = new CElementDelta[deltas.length]; - //System.out.println("delta.length: " + deltas.length); - for (int i = 0; i < deltas.length; i++) { - IResourceDelta delta = deltas[i]; - fCurrentDelta = new CElementDelta(root); - traverseDelta(root, delta); // traverse delta - translatedDeltas[i] = fCurrentDelta; - } - ICElementDelta[] filteredDeltas= filterRealDeltas(translatedDeltas); - // release deltas - fCurrentDelta= null; - return filteredDeltas; - } finally { + ICElement root = CModelManager.getDefault().getCModel(); + // get the workspace delta, and start processing there. + IResourceDelta[] deltas = changes.getAffectedChildren(); + ICElementDelta[] translatedDeltas = new CElementDelta[deltas.length]; + //System.out.println("delta.length: " + deltas.length); + for (int i = 0; i < deltas.length; i++) { + IResourceDelta delta = deltas[i]; + fCurrentDelta = new CElementDelta(root); + traverseDelta(root, delta); // traverse delta + translatedDeltas[i] = fCurrentDelta; } + ICElementDelta[] filteredDeltas= filterRealDeltas(translatedDeltas); + // release deltas + fCurrentDelta= null; + return filteredDeltas; } /** @@ -457,12 +453,9 @@ final class DeltaProcessor { IResource resource = delta.getResource(); ICElement current = createElement(resource); updateChildren = updateCurrentDeltaAndIndex(current, delta); - if (current == null) { + if (current == null || current instanceof ICContainer) { if (parent != null) - nonCResourcesChanged(parent, delta); - } else if (current instanceof ISourceRoot) { - if (parent != null) - nonCResourcesChanged(parent, delta); + nonCResourcesChanged(parent, delta); } else if (current instanceof ICProject) { ICProject cprj = (ICProject)current; CModel cModel = CModelManager.getDefault().getCModel(); @@ -487,7 +480,7 @@ final class DeltaProcessor { * @param delta */ protected void nonCResourcesChanged(ICElement parent, IResourceDelta delta) throws CModelException { - if (parent instanceof Openable && ((Openable)parent).isOpen()) { + if (parent instanceof Openable && ((Openable)parent).isOpen()) { CElementInfo info = ((Openable)parent).getElementInfo(); switch (parent.getElementType()) { case ICElement.C_MODEL: diff --git a/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/pdom/indexer/DeltaAnalyzer.java b/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/pdom/indexer/DeltaAnalyzer.java index ea96c54b8d7..ea1993788ce 100644 --- a/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/pdom/indexer/DeltaAnalyzer.java +++ b/core/org.eclipse.cdt.core/parser/org/eclipse/cdt/internal/core/pdom/indexer/DeltaAnalyzer.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2007, 2010 Wind River Systems, Inc. and others. + * Copyright (c) 2007, 2011 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 @@ -51,11 +51,11 @@ public class DeltaAnalyzer { } final ICElement element = delta.getElement(); - handled.add(element.getResource()); switch (element.getElementType()) { case ICElement.C_UNIT: ITranslationUnit tu = (ITranslationUnit)element; if (!tu.isWorkingCopy()) { + handled.add(element.getResource()); switch (delta.getKind()) { case ICElementDelta.CHANGED: if ((flags & ICElementDelta.F_CONTENT) != 0) { @@ -74,22 +74,21 @@ public class DeltaAnalyzer { case ICElement.C_CCONTAINER: ICContainer folder= (ICContainer) element; if (delta.getKind() == ICElementDelta.ADDED) { + handled.add(element.getResource()); collectSources(folder, fChanged); } break; } if (!sSuppressPotentialTUs) { - // If the cmodel delta does not have children, also look at the children of the - // resource delta. - final boolean checkChildren = !hasChildren; + // Always look at the children of the resource delta (bug 343538) final IResourceDelta[] rDeltas= delta.getResourceDeltas(); - processResourceDelta(rDeltas, element, handled, checkChildren); + processResourceDelta(rDeltas, element, handled); } } public void processResourceDelta(final IResourceDelta[] rDeltas, final ICElement element, - Set handled, boolean checkChildren) { + Set handled) { if (rDeltas != null) { for (IResourceDelta rd: rDeltas) { final int rdkind = rd.getKind(); @@ -108,9 +107,7 @@ public class DeltaAnalyzer { } } } - if (rdkind == IResourceDelta.CHANGED && checkChildren) { - processResourceDelta(rd.getAffectedChildren(), element, handled, checkChildren); - } + processResourceDelta(rd.getAffectedChildren(IResourceDelta.CHANGED | IResourceDelta.REMOVED), element, handled); } } }