Download
Getting Started
Members
Projects
Community
Marketplace
Events
Planet Eclipse
Newsletter
Videos
Participate
Report a Bug
Forums
Mailing Lists
Wiki
IRC
How to Contribute
Working Groups
Automotive
Internet of Things
LocationTech
Long-Term Support
PolarSys
Science
OpenMDM
More
Community
Marketplace
Events
Planet Eclipse
Newsletter
Videos
Participate
Report a Bug
Forums
Mailing Lists
Wiki
IRC
How to Contribute
Working Groups
Automotive
Internet of Things
LocationTech
Long-Term Support
PolarSys
Science
OpenMDM
Toggle navigation
Bugzilla – Attachment 130342 Details for
Bug 233643
API builder performance bad for incremental build
Home
|
New
|
Browse
|
Search
|
[?]
|
Reports
|
Requests
|
Help
|
Log In
[x]
|
Terms of Use
|
Copyright Agent
[patch]
updated fix
233643C.patch (text/plain), 75.46 KB, created by
Michael Rennie
on 2009-03-30 23:47:27 EDT
(
hide
)
Description:
updated fix
Filename:
MIME Type:
Creator:
Michael Rennie
Created:
2009-03-30 23:47:27 EDT
Size:
75.46 KB
patch
obsolete
>### Eclipse Workspace Patch 1.0 >#P org.eclipse.pde.api.tools.tests >Index: src/org/eclipse/pde/api/tools/builder/tests/usage/DependentUsageTests.java >=================================================================== >RCS file: /cvsroot/eclipse/pde/apitools/org.eclipse.pde.api.tools.tests/src/org/eclipse/pde/api/tools/builder/tests/usage/DependentUsageTests.java,v >retrieving revision 1.1 >diff -u -r1.1 DependentUsageTests.java >--- src/org/eclipse/pde/api/tools/builder/tests/usage/DependentUsageTests.java 24 Mar 2009 21:14:12 -0000 1.1 >+++ src/org/eclipse/pde/api/tools/builder/tests/usage/DependentUsageTests.java 31 Mar 2009 03:38:31 -0000 >@@ -363,4 +363,68 @@ > setExpectedMessageArgs(new String[][] {{"interref", "test8"}}); > deployTest("test8", XYZ_PATH, I_PATH, "interref.java", addtag); > } >+ >+ /** >+ * Tests adding @noextend AND @noinstantiate tags to a class known to be used >+ * by another bundle >+ * >+ * Uses test9.java and classref.java >+ */ >+ public void testAddExtendInstantiateRestriction() throws Exception { >+ test9(true); >+ } >+ >+ /** >+ * Tests removing @noextend AND @noinstantiate tags to a class known to be used >+ * by another bundle >+ * >+ * Uses test9.java and classref.java >+ */ >+ public void testRemoveExtendInstantiateRestriction() throws Exception { >+ test9(false); >+ } >+ >+ private void test9(boolean addtag) throws Exception { >+ setExpectedProblemIds(new int[] { >+ ApiProblemFactory.createProblemId(IApiProblem.CATEGORY_USAGE, IElementDescriptor.TYPE, IApiProblem.ILLEGAL_EXTEND, IApiProblem.NO_FLAGS), >+ ApiProblemFactory.createProblemId(IApiProblem.CATEGORY_USAGE, IElementDescriptor.TYPE, IApiProblem.ILLEGAL_INSTANTIATE, IApiProblem.NO_FLAGS) >+ }); >+ setExpectedMessageArgs(new String[][] { >+ {"classref", "test9"}, >+ {"classref", "test9"} >+ }); >+ deployTest("test9", XYZ_PATH, C_PATH, "classref.java", addtag); >+ } >+ >+ /** >+ * Tests adding @noextend AND @noimplement tags to an interface known to be used >+ * by another bundle >+ * >+ * Uses test10.java and interref.java >+ */ >+ public void testAddExtendImplementRestriction() throws Exception { >+ test10(true); >+ } >+ >+ /** >+ * Tests removing @noextend AND @noimplement tags to an interface known to be used >+ * by another bundle >+ * >+ * Uses test10.java and interref.java >+ */ >+ public void testRemoveExtendImplementRestriction() throws Exception { >+ test10(false); >+ } >+ >+ private void test10(boolean addtag) throws Exception { >+ setExpectedProblemIds(new int[] { >+ ApiProblemFactory.createProblemId(IApiProblem.CATEGORY_USAGE, IElementDescriptor.TYPE, IApiProblem.ILLEGAL_EXTEND, IApiProblem.NO_FLAGS), >+ ApiProblemFactory.createProblemId(IApiProblem.CATEGORY_USAGE, IElementDescriptor.TYPE, IApiProblem.ILLEGAL_IMPLEMENT, IApiProblem.NO_FLAGS) >+ }); >+ setExpectedMessageArgs(new String[][] { >+ {"interref", "test10"}, >+ {"interref", "clazz"} >+ }); >+ deployTest("test10", XYZ_PATH, I_PATH, "interref.java", addtag); >+ } > } >Index: test-builder/usage/dependent/test10/test10.java >=================================================================== >RCS file: test-builder/usage/dependent/test10/test10.java >diff -N test-builder/usage/dependent/test10/test10.java >--- /dev/null 1 Jan 1970 00:00:00 -0000 >+++ test-builder/usage/dependent/test10/test10.java 1 Jan 1970 00:00:00 -0000 >@@ -0,0 +1,23 @@ >+/******************************************************************************* >+ * Copyright (c) 2009 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 >+ *******************************************************************************/ >+package x.y.z; >+ >+import i.interref; >+ >+/** >+ * >+ */ >+public interface test10 extends interref { >+ >+} >+class clazz implements interref { >+ >+} >Index: test-builder/usage/dependent/test10/withouttag/interref.java >=================================================================== >RCS file: test-builder/usage/dependent/test10/withouttag/interref.java >diff -N test-builder/usage/dependent/test10/withouttag/interref.java >--- /dev/null 1 Jan 1970 00:00:00 -0000 >+++ test-builder/usage/dependent/test10/withouttag/interref.java 1 Jan 1970 00:00:00 -0000 >@@ -0,0 +1,18 @@ >+/******************************************************************************* >+ * Copyright (c) 2009 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 >+ *******************************************************************************/ >+package i; >+ >+/** >+ * >+ */ >+public interface interref { >+ >+} >Index: test-builder/usage/dependent/test9/withtag/classref.java >=================================================================== >RCS file: test-builder/usage/dependent/test9/withtag/classref.java >diff -N test-builder/usage/dependent/test9/withtag/classref.java >--- /dev/null 1 Jan 1970 00:00:00 -0000 >+++ test-builder/usage/dependent/test9/withtag/classref.java 1 Jan 1970 00:00:00 -0000 >@@ -0,0 +1,19 @@ >+/******************************************************************************* >+ * Copyright (c) 2009 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 >+ *******************************************************************************/ >+package c; >+ >+/** >+ * @noextend >+ * @noinstantiate >+ */ >+public class classref { >+ >+} >Index: test-builder/usage/dependent/test9/test9.java >=================================================================== >RCS file: test-builder/usage/dependent/test9/test9.java >diff -N test-builder/usage/dependent/test9/test9.java >--- /dev/null 1 Jan 1970 00:00:00 -0000 >+++ test-builder/usage/dependent/test9/test9.java 1 Jan 1970 00:00:00 -0000 >@@ -0,0 +1,21 @@ >+/******************************************************************************* >+ * Copyright (c) 2009 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 >+ *******************************************************************************/ >+package x.y.z; >+ >+import c.classref; >+ >+/** >+ * >+ */ >+public class test9 extends classref { >+ >+ classref ref = new classref(); >+} >Index: test-builder/usage/dependent/test10/withtag/interref.java >=================================================================== >RCS file: test-builder/usage/dependent/test10/withtag/interref.java >diff -N test-builder/usage/dependent/test10/withtag/interref.java >--- /dev/null 1 Jan 1970 00:00:00 -0000 >+++ test-builder/usage/dependent/test10/withtag/interref.java 1 Jan 1970 00:00:00 -0000 >@@ -0,0 +1,19 @@ >+/******************************************************************************* >+ * Copyright (c) 2009 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 >+ *******************************************************************************/ >+package i; >+ >+/** >+ * @noextend >+ * @noimplement >+ */ >+public interface interref { >+ >+} >Index: test-builder/usage/dependent/test9/withouttag/classref.java >=================================================================== >RCS file: test-builder/usage/dependent/test9/withouttag/classref.java >diff -N test-builder/usage/dependent/test9/withouttag/classref.java >--- /dev/null 1 Jan 1970 00:00:00 -0000 >+++ test-builder/usage/dependent/test9/withouttag/classref.java 1 Jan 1970 00:00:00 -0000 >@@ -0,0 +1,18 @@ >+/******************************************************************************* >+ * Copyright (c) 2009 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 >+ *******************************************************************************/ >+package c; >+ >+/** >+ * >+ */ >+public class classref { >+ >+} >#P org.eclipse.pde.api.tools >Index: src/org/eclipse/pde/api/tools/internal/builder/BaseApiAnalyzer.java >=================================================================== >RCS file: /cvsroot/eclipse/pde/apitools/org.eclipse.pde.api.tools/src/org/eclipse/pde/api/tools/internal/builder/BaseApiAnalyzer.java,v >retrieving revision 1.91 >diff -u -r1.91 BaseApiAnalyzer.java >--- src/org/eclipse/pde/api/tools/internal/builder/BaseApiAnalyzer.java 16 Mar 2009 14:19:51 -0000 1.91 >+++ src/org/eclipse/pde/api/tools/internal/builder/BaseApiAnalyzer.java 31 Mar 2009 03:38:36 -0000 >@@ -301,7 +301,7 @@ > } > } > if (changedTypes != null) { >- // check the ones not already checked as part of typenames check >+ // check the ones not already checked as part of type names check > for (int i = 0; i < changedTypes.length; i++) { > String typeName = changedTypes[i]; > if (typeNamesSet == null || !typeNamesSet.remove(typeName)) { >@@ -1550,7 +1550,7 @@ > Util.EMPTY_STRING); > } > } >- // analyse version of required components >+ // analyze version of required components > ReexportedBundleVersionInfo info = null; > if (problem != null) { > switch (problem.getKind()) { >@@ -1580,7 +1580,7 @@ > } > break; > case IApiProblem.MINOR_VERSION_CHANGE : >- // check if there is a version change required due to reexported bundles >+ // check if there is a version change required due to re-exported bundles > info = checkBundleVersionsOfReexportedBundles(reference, component); > if (info != null) { > switch(info.kind) { >@@ -1602,7 +1602,7 @@ > } > break; > case IApiProblem.MINOR_VERSION_CHANGE_NO_NEW_API : >- // check if there is a version change required due to reexported bundles >+ // check if there is a version change required due to re-exported bundles > info = checkBundleVersionsOfReexportedBundles(reference, component); > if (info != null) { > switch(info.kind) { >Index: src/org/eclipse/pde/api/tools/internal/builder/BuilderMessages.java >=================================================================== >RCS file: /cvsroot/eclipse/pde/apitools/org.eclipse.pde.api.tools/src/org/eclipse/pde/api/tools/internal/builder/BuilderMessages.java,v >retrieving revision 1.32 >diff -u -r1.32 BuilderMessages.java >--- src/org/eclipse/pde/api/tools/internal/builder/BuilderMessages.java 7 Jan 2009 19:29:01 -0000 1.32 >+++ src/org/eclipse/pde/api/tools/internal/builder/BuilderMessages.java 31 Mar 2009 03:38:36 -0000 >@@ -20,6 +20,7 @@ > public static String checking_api_usage; > > public static String AbstractTypeLeakDetector_vis_type_has_no_api_description; >+ public static String ApiAnalysisBuilder_builder_for_project; > public static String ApiAnalysisBuilder_finding_affected_source_files; > public static String ApiAnalysisBuilder_initializing_analyzer; > public static String ApiProblemFactory_problem_message_not_found; >@@ -32,7 +33,6 @@ > public static String build_wrongFileFormat; > public static String build_saveStateComplete; > public static String build_cannotSaveState; >- public static String IllegalExtendsProblemDetector_an_anonymous_declaration; > public static String undefinedRange; > public static String reportUnsatisfiedConstraint; > >Index: src/org/eclipse/pde/api/tools/internal/builder/ApiAnalysisBuilder.java >=================================================================== >RCS file: /cvsroot/eclipse/pde/apitools/org.eclipse.pde.api.tools/src/org/eclipse/pde/api/tools/internal/builder/ApiAnalysisBuilder.java,v >retrieving revision 1.97 >diff -u -r1.97 ApiAnalysisBuilder.java >--- src/org/eclipse/pde/api/tools/internal/builder/ApiAnalysisBuilder.java 24 Mar 2009 18:50:44 -0000 1.97 >+++ src/org/eclipse/pde/api/tools/internal/builder/ApiAnalysisBuilder.java 31 Mar 2009 03:38:35 -0000 >@@ -22,18 +22,14 @@ > import java.util.Date; > import java.util.HashMap; > import java.util.HashSet; >-import java.util.Iterator; >-import java.util.List; > import java.util.Map; > import java.util.Set; > import java.util.jar.JarFile; > >-import org.eclipse.core.resources.IFile; > import org.eclipse.core.resources.IMarker; > import org.eclipse.core.resources.IProject; > import org.eclipse.core.resources.IResource; > import org.eclipse.core.resources.IResourceDelta; >-import org.eclipse.core.resources.IResourceDeltaVisitor; > import org.eclipse.core.resources.IWorkspaceRoot; > import org.eclipse.core.resources.IncrementalProjectBuilder; > import org.eclipse.core.resources.ResourcesPlugin; >@@ -41,7 +37,6 @@ > 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.OperationCanceledException; > import org.eclipse.core.runtime.Path; > import org.eclipse.core.runtime.Platform; >@@ -49,16 +44,9 @@ > import org.eclipse.core.runtime.SubMonitor; > import org.eclipse.jdt.core.IClasspathAttribute; > import org.eclipse.jdt.core.IClasspathEntry; >-import org.eclipse.jdt.core.ICompilationUnit; >-import org.eclipse.jdt.core.IJavaElement; > import org.eclipse.jdt.core.IJavaProject; >-import org.eclipse.jdt.core.IType; > import org.eclipse.jdt.core.JavaCore; > import org.eclipse.jdt.core.JavaModelException; >-import org.eclipse.jdt.internal.core.JavaModelManager; >-import org.eclipse.jdt.internal.core.builder.ReferenceCollection; >-import org.eclipse.jdt.internal.core.builder.State; >-import org.eclipse.jdt.internal.core.builder.StringSet; > import org.eclipse.osgi.service.resolver.BundleDescription; > import org.eclipse.osgi.util.NLS; > import org.eclipse.pde.api.tools.internal.ApiDescriptionManager; >@@ -82,93 +70,30 @@ > */ > public class ApiAnalysisBuilder extends IncrementalProjectBuilder { > /** >- * Visits a resource delta to determine if the changes have been made that might required a rebuild: >- * - modification to the manifest file >- * - removal of the .api_filter file >- */ >- class ResourceDeltaVisitor implements IResourceDeltaVisitor { >- IProject[] projects; >- public ResourceDeltaVisitor(IProject[] projects) { >- this.projects = projects; >- } >- private boolean fRequireFullBuild = false; >- >- /** >- * Returns whether a full build should be run. >- * >- * @return whether a full build should be run >- */ >- boolean shouldRunFullBuild() { >- return fRequireFullBuild; >- } >- >- /* (non-Javadoc) >- * @see org.eclipse.core.resources.IResourceDeltaVisitor#visit(org.eclipse.core.resources.IResourceDelta) >- */ >- public boolean visit(IResourceDelta delta) throws CoreException { >- switch (delta.getResource().getType()) { >- case IResource.ROOT: >- case IResource.PROJECT: >- return !fRequireFullBuild; >- case IResource.FOLDER: >- return !fRequireFullBuild; >- case IResource.FILE: >- if (delta.getResource().getProjectRelativePath().equals(MANIFEST_PATH)) { >- fRequireFullBuild = true; >- break; >- } >- IResource resource = delta.getResource(); >- String fileName = resource.getName(); >- if (Util.isClassFile(fileName)) { >- findAffectedSourceFiles(delta); >- } else if (Util.isJavaFileName(fileName)) { >- IProject project = resource.getProject(); >- if (fCurrentProject.equals(project)) { >- if (delta.getKind() == IResourceDelta.ADDED) { >- fAddedRemovedDeltas.add(delta); >- } >- fTypesToCheck.add(resource); >- } else if (this.projects != null) { >- loop: for (int i = 0, max = this.projects.length; i < max; i++) { >- if (this.projects[i].equals(project)) { >- fTypesToCheck.add(resource); >- break loop; >- } >- } >- } >- } else if (!fRequireFullBuild && IApiCoreConstants.API_FILTERS_XML_NAME.equals(fileName)) { >- switch(delta.getKind()) { >- case IResourceDelta.REMOVED : >- case IResourceDelta.REPLACED : >- case IResourceDelta.CHANGED : >- case IResourceDelta.ADDED : >- fRequireFullBuild = true; >- } >- } >- } >- return false; >- } >- } >- /** > * Constant used for controlling tracing in the API tool builder > */ >- private static boolean DEBUG = Util.DEBUG; >+ static boolean DEBUG = Util.DEBUG; > > /** > * Project relative path to the manifest file. > */ >- private static final IPath MANIFEST_PATH = new Path(JarFile.MANIFEST_NAME); >+ static final IPath MANIFEST_PATH = new Path(JarFile.MANIFEST_NAME); > > /** >- * Internal flag used to determine what created the marker, as there is overlap for reference kinds and deltas >+ * Project relative path to the .api_filters file > */ >- public static final int REF_TYPE_FLAG = 0; >+ static final IPath FILTER_PATH = new Path(".settings").append(IApiCoreConstants.API_FILTERS_XML_NAME); //$NON-NLS-1$ >+ >+ /** >+ * Empty listing of projects to be returned by the builder if there is nothing to do >+ */ >+ static final IProject[] NO_PROJECTS = new IProject[0]; > > /** > * Constant representing the name of the 'source' attribute on API tooling markers. > * Value is <code>Api Tooling</code> > */ >- public static final String SOURCE = "Api Tooling"; //$NON-NLS-1$ >+ static final String SOURCE = "Api Tooling"; //$NON-NLS-1$ > > /** > * Method used for initializing tracing in the API tool builder >@@ -176,51 +101,33 @@ > public static void setDebug(boolean debugValue) { > DEBUG = debugValue || Util.DEBUG; > } >+ > /** > * The current project for which this builder was defined > */ >- private IProject fCurrentProject = null; >+ private IProject currentproject = null; > > /** > * The API analyzer for this builder > */ >- private IApiAnalyzer fAnalyzer = null; >+ private IApiAnalyzer analyzer = null; > > /** > * Maps prerequisite projects to their output location(s) > */ >- private HashMap fProjectToOutputLocations = new HashMap(); >- >- /** >- * List of type names to lookup for each project context to find dependents of >- */ >- private StringSet fTypes = new StringSet(3); >- >- /** >- * List of package names to qualify type names >- */ >- private StringSet fPackages = new StringSet(3); >- >- /** >- * The type that we want to check for API problems >- */ >- private HashSet fTypesToCheck = new HashSet(); >- /** >- * The set of added/removed deltas that come directly from the builder resource delta >- */ >- private HashSet fAddedRemovedDeltas = new HashSet(5); >+ private HashMap projecttooutputlocations = new HashMap(); > > /** > * Current build state > */ >- private BuildState fBuildState; >+ private BuildState buildstate = null; > > /** > * Cleans up markers associated with API tooling on the given resource. > * > * @param resource > */ >- public static void cleanupMarkers(IResource resource) { >+ void cleanupMarkers(IResource resource) { > cleanupUsageMarkers(resource); > cleanupCompatibilityMarkers(resource); > cleanupUnsupportedTagMarkers(resource); >@@ -230,7 +137,7 @@ > * Cleans up unsupported Javadoc tag markers on the specified resource > * @param resource > */ >- private static void cleanupUnsupportedTagMarkers(IResource resource) { >+ void cleanupUnsupportedTagMarkers(IResource resource) { > try { > if(DEBUG) { > System.out.println("cleaning unsupported tag problems"); //$NON-NLS-1$ >@@ -245,7 +152,7 @@ > * Cleans up only API compatibility markers on the given {@link IResource} > * @param resource the given resource > */ >- private static void cleanupCompatibilityMarkers(IResource resource) { >+ void cleanupCompatibilityMarkers(IResource resource) { > try { > if (resource != null && resource.isAccessible()) { > resource.deleteMarkers(IApiMarkerConstants.COMPATIBILITY_PROBLEM_MARKER, false, IResource.DEPTH_INFINITE); >@@ -266,7 +173,7 @@ > * cleans up only API usage markers from the given {@link IResource} > * @param resource > */ >- private static void cleanupUsageMarkers(IResource resource) { >+ void cleanupUsageMarkers(IResource resource) { > try { > if (resource != null && resource.isAccessible()) { > resource.deleteMarkers(IApiMarkerConstants.API_USAGE_PROBLEM_MARKER, false, IResource.DEPTH_INFINITE); >@@ -276,39 +183,16 @@ > } > } > >- /** >- * Adds a type to search for dependents of in considered projects for an incremental build >- * >- * @param path >- */ >- private void addDependentsOf(IPath path) { >- // the qualifiedStrings are of the form 'p1/p2' & the simpleStrings are just 'X' >- path = path.setDevice(null); >- String packageName = path.removeLastSegments(1).toString(); >- String typeName = path.lastSegment(); >- int memberIndex = typeName.indexOf('$'); >- if (memberIndex > 0) { >- typeName = typeName.substring(0, memberIndex); >- } >- if (fTypes.add(typeName) && fPackages.add(packageName) && DEBUG) { >- System.out.println(" will look for dependents of " + typeName + " in " + packageName); //$NON-NLS-1$ //$NON-NLS-2$ >- } >- } >- > /* (non-Javadoc) > * @see org.eclipse.core.resources.IncrementalProjectBuilder#build(int, java.util.Map, org.eclipse.core.runtime.IProgressMonitor) > */ > protected IProject[] build(int kind, Map args, IProgressMonitor monitor) throws CoreException { >- fCurrentProject = getProject(); >- fAnalyzer = getAnalyzer(); >- if (fCurrentProject == null || >- !fCurrentProject.isAccessible() || >- !fCurrentProject.hasNature(ApiPlugin.NATURE_ID) || >- hasBeenBuilt(fCurrentProject)) { >- return new IProject[0]; >+ this.currentproject = getProject(); >+ if (!this.currentproject.isAccessible() || !this.currentproject.hasNature(ApiPlugin.NATURE_ID) || hasBeenBuilt(this.currentproject)) { >+ return NO_PROJECTS; > } > if (DEBUG) { >- System.out.println("\nStarting build of " + fCurrentProject.getName() + " @ " + new Date(System.currentTimeMillis())); //$NON-NLS-1$ //$NON-NLS-2$ >+ System.out.println("\nStarting build of " + this.currentproject.getName() + " @ " + new Date(System.currentTimeMillis())); //$NON-NLS-1$ //$NON-NLS-2$ > } > updateMonitor(monitor, 0); > SubMonitor localMonitor = SubMonitor.convert(monitor, BuilderMessages.api_analysis_builder, 2); >@@ -325,64 +209,43 @@ > } > case AUTO_BUILD : > case INCREMENTAL_BUILD : { >- IResourceDelta[] deltas = getDeltas(projects); >- boolean shouldRunFullBuild = false; >- fBuildState = getLastBuiltState(fCurrentProject); >- if (fBuildState == null) { >+ this.buildstate = getLastBuiltState(currentproject); >+ if (this.buildstate == null) { > buildAll(baseline, localMonitor.newChild(1)); >- } else if (worthDoingFullBuild(projects)) { >+ break; >+ } >+ else if(worthDoingFullBuild(projects)) { > buildAll(baseline, localMonitor.newChild(1)); >- } else { >- IProject[] reexportedProjects = null; >- String[] projectNames = this.fBuildState.getReexportedComponents(); >- int length = projectNames.length; >- if (length != 0) { >- List allProjects = new ArrayList(); >- IWorkspaceRoot root = ResourcesPlugin.getWorkspace().getRoot(); >- for (int i = 0, max = projectNames.length; i < max; i++) { >- String projectName = projectNames[i]; >- IProject project = root.getProject(projectName); >- if (project.isAccessible()) { >- // select only projects that don't exist in the reference baseline >- if (baseline != null && baseline.getApiComponent(projectName) == null) { >- allProjects.add(project); >- } >- } >- } >- if (allProjects.size() != 0) { >- reexportedProjects = new IProject[allProjects.size()]; >- allProjects.toArray(reexportedProjects); >- } >- } >- ResourceDeltaVisitor visitor = new ResourceDeltaVisitor(reexportedProjects); >+ } >+ IResourceDelta[] deltas = getDeltas(projects); >+ if(deltas.length < 1) { >+ buildAll(baseline, localMonitor.newChild(1)); >+ } >+ else { >+ IResourceDelta manifest = null; >+ IResourceDelta filters = null; > for (int i = 0; i < deltas.length; i++) { >- deltas[i].accept(visitor); >- if (visitor.shouldRunFullBuild()) { >- shouldRunFullBuild = true; >+ manifest = deltas[i].findMember(MANIFEST_PATH); >+ if(manifest != null) { > break; > } >- } >- if (shouldRunFullBuild) { >- if (DEBUG) { >- System.out.println("Performing full build since MANIFEST.MF was modified"); //$NON-NLS-1$ >+ filters = deltas[i].findMember(FILTER_PATH); >+ if(filters != null){ >+ break; > } >- buildAll(baseline, localMonitor.newChild(1)); >- } else if (deltas.length == 0) { >+ } >+ if (manifest != null || filters != null) { > if (DEBUG) { >- System.out.println("Performing full build since deltas are missing after incremental request"); //$NON-NLS-1$ >- } >+ System.out.println("Performing full build since MANIFEST.MF or .api_filters was modified"); //$NON-NLS-1$ >+ } > buildAll(baseline, localMonitor.newChild(1)); >- } else { >- State state = (State)JavaModelManager.getJavaModelManager().getLastBuiltState(fCurrentProject, new NullProgressMonitor()); >- if (state == null) { >- buildAll(baseline, localMonitor.newChild(1)); >- } else { >- build(state, baseline, localMonitor.newChild(1)); >- } >+ } >+ else { >+ IncrementalApiBuilder builder = new IncrementalApiBuilder(this); >+ builder.build(baseline, deltas, this.buildstate, localMonitor.newChild(1)); > } > } >- break; >- } >+ } > } > updateMonitor(monitor, 0); > } catch(CoreException e) { >@@ -392,38 +255,36 @@ > } > ApiPlugin.log(e); > } finally { >- fTypes.clear(); >- fPackages.clear(); >- fTypesToCheck.clear(); >- fAddedRemovedDeltas.clear(); >- fProjectToOutputLocations.clear(); > updateMonitor(monitor, 0); >- fAnalyzer.dispose(); >+ if(this.analyzer != null) { >+ this.analyzer.dispose(); >+ this.analyzer = null; >+ } > if(baseline != null) { > baseline.close(); > } > if(monitor != null) { > monitor.done(); > } >- if (fBuildState != null) { >+ if (this.buildstate != null) { > for(int i = 0, max = projects.length; i < max; i++) { > IProject project = projects[i]; > if (Util.isApiProject(project)) { >- fBuildState.addApiToolingDependentProject(project.getName()); >+ this.buildstate.addApiToolingDependentProject(project.getName()); > } > } >- saveBuiltState(fCurrentProject, fBuildState); >- fBuildState = null; >+ saveBuiltState(this.currentproject, this.buildstate); >+ this.buildstate = null; > } > } > if (DEBUG) { >- System.out.println("Finished build of " + fCurrentProject.getName() + " @ " + new Date(System.currentTimeMillis())); //$NON-NLS-1$ //$NON-NLS-2$ >+ System.out.println("Finished build of " + this.currentproject.getName() + " @ " + new Date(System.currentTimeMillis())); //$NON-NLS-1$ //$NON-NLS-2$ > } > return projects; > } > > private boolean worthDoingFullBuild(IProject[] projects) { >- Set apiToolingDependentProjects = fBuildState.getApiToolingDependentProjects(); >+ Set apiToolingDependentProjects = this.buildstate.getApiToolingDependentProjects(); > for (int i = 0, max = projects.length; i < max; i++) { > IProject currentProject = projects[i]; > if (Util.isApiProject(currentProject)) { >@@ -437,18 +298,19 @@ > } > return false; > } >+ > /** > * Performs a full build for the project > * @param monitor > */ >- private void buildAll(IApiBaseline baseline, IProgressMonitor monitor) throws CoreException { >+ void buildAll(IApiBaseline baseline, IProgressMonitor monitor) throws CoreException { > IApiBaseline wsprofile = null; > try { > clearLastState(); >- fBuildState = new BuildState(); >+ this.buildstate = new BuildState(); > SubMonitor localMonitor = SubMonitor.convert(monitor, BuilderMessages.api_analysis_on_0, 4); >- localMonitor.subTask(NLS.bind(BuilderMessages.ApiAnalysisBuilder_initializing_analyzer, fCurrentProject.getName())); >- cleanupMarkers(fCurrentProject); >+ localMonitor.subTask(NLS.bind(BuilderMessages.ApiAnalysisBuilder_initializing_analyzer, currentproject.getName())); >+ cleanupMarkers(this.currentproject); > IPluginModelBase currentModel = getCurrentModel(); > if (currentModel != null) { > localMonitor.subTask(BuilderMessages.building_workspace_profile); >@@ -464,7 +326,7 @@ > // Compatibility checks > IApiComponent apiComponent = wsprofile.getApiComponent(id); > if(apiComponent != null) { >- fAnalyzer.analyzeComponent(fBuildState, null, null, baseline, apiComponent, null, null, localMonitor.newChild(1)); >+ getAnalyzer().analyzeComponent(this.buildstate, null, null, baseline, apiComponent, null, null, localMonitor.newChild(1)); > updateMonitor(localMonitor, 1); > createMarkers(); > updateMonitor(localMonitor, 1); >@@ -488,13 +350,13 @@ > */ > protected void createMarkers() { > try { >- fCurrentProject.deleteMarkers(IApiMarkerConstants.VERSION_NUMBERING_PROBLEM_MARKER, true, IResource.DEPTH_INFINITE); >- fCurrentProject.deleteMarkers(IApiMarkerConstants.DEFAULT_API_BASELINE_PROBLEM_MARKER, true, IResource.DEPTH_ZERO); >- fCurrentProject.deleteMarkers(IApiMarkerConstants.API_COMPONENT_RESOLUTION_PROBLEM_MARKER, true, IResource.DEPTH_ZERO); >+ this.currentproject.deleteMarkers(IApiMarkerConstants.VERSION_NUMBERING_PROBLEM_MARKER, true, IResource.DEPTH_INFINITE); >+ this.currentproject.deleteMarkers(IApiMarkerConstants.DEFAULT_API_BASELINE_PROBLEM_MARKER, true, IResource.DEPTH_ZERO); >+ this.currentproject.deleteMarkers(IApiMarkerConstants.API_COMPONENT_RESOLUTION_PROBLEM_MARKER, true, IResource.DEPTH_ZERO); > } catch (CoreException e) { > ApiPlugin.log(e); > } >- IApiProblem[] problems = fAnalyzer.getProblems(); >+ IApiProblem[] problems = getAnalyzer().getProblems(); > String type = null; > for(int i = 0; i < problems.length; i++) { > int category = problems[i].getCategory(); >@@ -578,7 +440,7 @@ > IApiMarkerConstants.MARKER_ATTR_PROBLEM_ID}, > new Object[] { > problem.getMessage(), >- new Integer(ApiPlugin.getDefault().getSeverityLevel(ApiProblemFactory.getProblemSeverityId(problem), this.fCurrentProject)), >+ new Integer(ApiPlugin.getDefault().getSeverityLevel(ApiProblemFactory.getProblemSeverityId(problem), this.currentproject)), > new Integer(line), > new Integer(problem.getCharStart()), > new Integer(problem.getCharEnd()), >@@ -620,7 +482,7 @@ > if (resourcePath == null) { > return null; > } >- IResource resource = fCurrentProject.findMember(new Path(resourcePath)); >+ IResource resource = currentproject.findMember(new Path(resourcePath)); > if(resource == null) { > return null; > } >@@ -654,7 +516,7 @@ > * @param ticks > * @throws OperationCanceledException > */ >- private void updateMonitor(IProgressMonitor monitor, int ticks) throws OperationCanceledException { >+ void updateMonitor(IProgressMonitor monitor, int ticks) throws OperationCanceledException { > if(monitor != null) { > monitor.worked(ticks); > if (monitor.isCanceled()) { >@@ -663,232 +525,21 @@ > } > } > >- /** >- * Builds an API delta using the default profile (from the workspace settings and the current >- * workspace profile >- * @param state >- * @param monitor >- */ >- private void build(final State state, IApiBaseline baseline, IProgressMonitor monitor) throws CoreException { >- IApiBaseline wsprofile = null; >- SubMonitor localMonitor = SubMonitor.convert(monitor, BuilderMessages.api_analysis_on_0, 6); >- try { >- clearLastState(); // so if the build fails, a full build will be triggered >- localMonitor.subTask(NLS.bind(BuilderMessages.ApiAnalysisBuilder_finding_affected_source_files, fCurrentProject.getName())); >- updateMonitor(localMonitor, 0); >- collectAffectedSourceFiles(state, fTypesToCheck); >- updateMonitor(localMonitor, 1); >- final int typesToCheckSize = fTypesToCheck.size(); >- if (typesToCheckSize != 0) { >- IPluginModelBase currentModel = getCurrentModel(); >- if (currentModel != null) { >- wsprofile = getWorkspaceProfile(); >- if (wsprofile == null) { >- if (DEBUG) { >- System.err.println("Could not retrieve a workspace profile"); //$NON-NLS-1$ >- } >- return; >- } >- String id = currentModel.getBundleDescription().getSymbolicName(); >- IApiComponent apiComponent = wsprofile.getApiComponent(id); >- if(apiComponent == null) { >- return; >- } >- List tnames = new ArrayList(typesToCheckSize), >- cnames = new ArrayList(typesToCheckSize); >- collectAllQualifiedNames(fTypesToCheck, tnames, cnames, localMonitor.newChild(1)); >- updateMonitor(localMonitor, 1); >- fAnalyzer.analyzeComponent(fBuildState, >- null, >- null, >- baseline, >- apiComponent, >- (String[])tnames.toArray(new String[tnames.size()]), >- (String[])cnames.toArray(new String[cnames.size()]), >- localMonitor.newChild(1)); >- updateMonitor(localMonitor, 1); >- createMarkers(); >- updateMonitor(localMonitor, 1); >- } >- } >- } >- finally { >- if(wsprofile != null) { >- wsprofile.close(); >- } >- if(!localMonitor.isCanceled()) { >- localMonitor.done(); >- } >- } >- } >- >- /** >- * Returns an array of type names, and cleans up markers for the specified resource >- * @param alltypes the listing of {@link IFile}s to get qualified names from >- * @param changedtypes the listing of {@link IFile}s that have actually changed (from the {@link IResourceDelta} >- * @param tnames the list to collect all type names into (including inner member names) >- * @param cnames the list to collect the changed type names into >- * @param monitor >- */ >- private void collectAllQualifiedNames(final HashSet alltypes, List tnames, List cnames, final IProgressMonitor monitor) { >- IType[] types = null; >- IFile file = null; >- for (Iterator iterator = alltypes.iterator(); iterator.hasNext(); ) { >- file = (IFile) iterator.next(); >- ICompilationUnit unit = (ICompilationUnit) JavaCore.create(file); >- if(!unit.exists()) { >- continue; >- } >- IType type = unit.findPrimaryType(); >- if(type == null) { >- continue; >- } >- updateMonitor(monitor, 0); >- cleanupUnsupportedTagMarkers(file); >- updateMonitor(monitor, 0); >- cleanupCompatibilityMarkers(file); >- updateMonitor(monitor, 0); >- cnames.add(type.getFullyQualifiedName()); >- try { >- cleanupUsageMarkers(file); >- updateMonitor(monitor, 0); >- types = unit.getAllTypes(); >- String tname = null; >- for (int i = 0; i < types.length; i++) { >- IType type2 = types[i]; >- if (type2.isMember()) { >- tname = type2.getFullyQualifiedName('$'); >- } else { >- tname = type2.getFullyQualifiedName(); >- } >- tnames.add(tname); >- } >- } catch (JavaModelException e) { >- ApiPlugin.log(e.getStatus()); >- } >- updateMonitor(monitor, 0); >- } >- // inject removed types inside changed type names so that we can properly detect type removal >- for (Iterator iterator = this.fAddedRemovedDeltas.iterator(); iterator.hasNext(); ) { >- IResourceDelta delta = (IResourceDelta) iterator.next(); >- if (delta.getKind() != IResourceDelta.REMOVED) continue; >- IResource resource = delta.getResource(); >- IPath typePath = resolveJavaPathFromResource(resource); >- if(typePath == null) { >- continue; >- } >- // record removed type names (package + type) >- StringBuffer buffer = new StringBuffer(); >- String[] segments = typePath.segments(); >- for (int i = 0, max = segments.length; i < max; i++) { >- if (i > 0) { >- buffer.append('.'); >- } >- buffer.append(segments[i]); >- } >- cnames.add(String.valueOf(buffer)); >- } >- // clean up markers on added deltas >- if (!this.fAddedRemovedDeltas.isEmpty()) { >- IResource manifestFile = Util.getManifestFile(this.fCurrentProject); >- if (manifestFile != null) { >- try { >- IMarker[] markers = manifestFile.findMarkers(IApiMarkerConstants.COMPATIBILITY_PROBLEM_MARKER, false, IResource.DEPTH_INFINITE); >- for (int i = 0, max = markers.length; i < max; i++) { >- IMarker marker = markers[i]; >- String typeName = marker.getAttribute(IApiMarkerConstants.MARKER_ATTR_PROBLEM_TYPE_NAME, null); >- if (typeName != null) { >- for (Iterator iterator = this.fAddedRemovedDeltas.iterator(); iterator.hasNext(); ) { >- IResourceDelta delta = (IResourceDelta) iterator.next(); >- if (delta.getKind() != IResourceDelta.ADDED) continue; >- ICompilationUnit unit = (ICompilationUnit) JavaCore.create(delta.getResource()); >- if(!unit.exists()) { >- continue; >- } >- IType type = unit.findPrimaryType(); >- if(type == null) { >- continue; >- } >- if (typeName.equals(type.getFullyQualifiedName())) { >- marker.delete(); >- return; >- } else { >- // check secondary types >- try { >- types = unit.getAllTypes(); >- for (int j = 0; j < types.length; j++) { >- IType type2 = types[i]; >- String fullyQualifiedName = null; >- if (type2.isMember()) { >- fullyQualifiedName = type2.getFullyQualifiedName('$'); >- } else { >- fullyQualifiedName = type2.getFullyQualifiedName(); >- } >- if (typeName.equals(fullyQualifiedName)) { >- marker.delete(); >- return; >- } >- } >- } catch (JavaModelException e) { >- ApiPlugin.log(e.getStatus()); >- } >- } >- } >- } >- } >- } catch (CoreException e) { >- ApiPlugin.log(e.getStatus()); >- } >- } >- } >- IResource resource = fCurrentProject.findMember(MANIFEST_PATH); >- if (resource != null) { >- try { >- IMarker[] markers = resource.findMarkers(IApiMarkerConstants.COMPATIBILITY_PROBLEM_MARKER, false, IResource.DEPTH_ZERO); >- loop: for (int i = 0, max = markers.length; i < max; i++) { >- IMarker marker = markers[i]; >- String typeNameFromMarker = Util.getTypeNameFromMarker(marker); >- for (Iterator iterator = tnames.iterator(); iterator.hasNext(); ) { >- String typeName = (String) iterator.next(); >- if (typeName.equals(typeNameFromMarker)) { >- marker.delete(); >- continue loop; >- } >- } >- } >- markers = resource.findMarkers(IApiMarkerConstants.SINCE_TAGS_PROBLEM_MARKER, false, IResource.DEPTH_ZERO); >- loop: for (int i = 0, max = markers.length; i < max; i++) { >- IMarker marker = markers[i]; >- String typeNameFromMarker = Util.getTypeNameFromMarker(marker); >- for (Iterator iterator = tnames.iterator(); iterator.hasNext(); ) { >- String typeName = (String) iterator.next(); >- if (typeName.equals(typeNameFromMarker)) { >- marker.delete(); >- continue loop; >- } >- } >- } >- } catch (CoreException e) { >- ApiPlugin.log(e); >- } >- } >- } >- > /* (non-Javadoc) > * @see org.eclipse.core.resources.IncrementalProjectBuilder#clean(org.eclipse.core.runtime.IProgressMonitor) > */ > protected void clean(IProgressMonitor monitor) throws CoreException { >- fCurrentProject = getProject(); >- SubMonitor localmonitor = SubMonitor.convert(monitor, MessageFormat.format(BuilderMessages.CleaningAPIDescription, new String[] {fCurrentProject.getName()}), 2); >+ this.currentproject = getProject(); >+ SubMonitor localmonitor = SubMonitor.convert(monitor, MessageFormat.format(BuilderMessages.CleaningAPIDescription, new String[] {this.currentproject.getName()}), 2); > try { > // clean up all existing markers >- cleanupUsageMarkers(fCurrentProject); >- cleanupCompatibilityMarkers(fCurrentProject); >- cleanupUnsupportedTagMarkers(fCurrentProject); >- fCurrentProject.deleteMarkers(IApiMarkerConstants.UNUSED_FILTER_PROBLEM_MARKER, false, IResource.DEPTH_INFINITE); >+ cleanupUsageMarkers(this.currentproject); >+ cleanupCompatibilityMarkers(this.currentproject); >+ cleanupUnsupportedTagMarkers(this.currentproject); >+ this.currentproject.deleteMarkers(IApiMarkerConstants.UNUSED_FILTER_PROBLEM_MARKER, false, IResource.DEPTH_INFINITE); > updateMonitor(localmonitor, 1); > //clean up the .api_settings >- cleanupApiDescription(fCurrentProject); >+ cleanupApiDescription(this.currentproject); > updateMonitor(localmonitor, 1); > } > finally { >@@ -906,93 +557,13 @@ > ApiDescriptionManager.getDefault().clean(JavaCore.create(project), true, true); > } > } >- /** >- * Collects the complete set of affected source files from the current project context based on the current JDT build state. >- * >- * @param state >- */ >- private void collectAffectedSourceFiles(State state, Set typesToCheck) { >- // the qualifiedStrings are of the form 'p1/p2' & the simpleStrings are just 'X' >- char[][][] internedQualifiedNames = ReferenceCollection.internQualifiedNames(fPackages); >- // if a well known qualified name was found then we can skip over these >- if (internedQualifiedNames.length < fPackages.elementSize) { >- internedQualifiedNames = null; >- } >- char[][] internedSimpleNames = ReferenceCollection.internSimpleNames(fTypes, true); >- // if a well known name was found then we can skip over these >- if (internedSimpleNames.length < fTypes.elementSize) { >- internedSimpleNames = null; >- } >- Object[] keyTable = state.getReferences().keyTable; >- Object[] valueTable = state.getReferences().valueTable; >- next : for (int i = 0, l = valueTable.length; i < l; i++) { >- String typeLocator = (String) keyTable[i]; >- if (typeLocator != null) { >- ReferenceCollection refs = (ReferenceCollection) valueTable[i]; >- if (refs.includes(internedQualifiedNames, internedSimpleNames, null)) { >- IFile file = fCurrentProject.getFile(typeLocator); >- if (file == null) { >- continue next; >- } >- if (DEBUG) { >- System.out.println(" adding affected source file " + typeLocator); //$NON-NLS-1$ >- } >- typesToCheck.add(file); >- } >- } >- } >- } >- > >- >- /** >- * Finds affected source files for a resource that has changed that either contains class files or is itself a class file >- * @param binaryDelta >- */ >- private void findAffectedSourceFiles(IResourceDelta binaryDelta) { >- IResource resource = binaryDelta.getResource(); >- if(resource.getType() == IResource.FILE) { >- if (Util.isClassFile(resource.getName())) { >- switch (binaryDelta.getKind()) { >- case IResourceDelta.REMOVED : >- fAddedRemovedDeltas.add(binaryDelta); >- //$FALL-THROUGH$ >- case IResourceDelta.ADDED : { >- IPath typePath = resolveJavaPathFromResource(resource); >- if(typePath == null) { >- return; >- } >- if (DEBUG) { >- System.out.println("Found added/removed class file " + typePath); //$NON-NLS-1$ >- } >- addDependentsOf(typePath); >- return; >- } >- case IResourceDelta.CHANGED : { >- if ((binaryDelta.getFlags() & IResourceDelta.CONTENT) == 0) { >- return; // skip it since it really isn't changed >- } >- IPath typePath = resolveJavaPathFromResource(resource); >- if(typePath == null) { >- return; >- } >- if (DEBUG) { >- System.out.println("Found changed class file " + typePath); //$NON-NLS-1$ >- } >- addDependentsOf(typePath); >- } >- } >- return; >- } >- } >- } >- > /** > * @return the current {@link IPluginModelBase} based on the current project for this builder > */ >- private IPluginModelBase getCurrentModel() { >+ IPluginModelBase getCurrentModel() { > IPluginModelBase[] workspaceModels = PluginRegistry.getWorkspaceModels(); >- IPath location = fCurrentProject.getLocation(); >+ IPath location = this.currentproject.getLocation(); > IPluginModelBase currentModel = null; > BundleDescription desc = null; > loop: for (int i = 0, max = workspaceModels.length; i < max; i++) { >@@ -1018,10 +589,10 @@ > */ > private IResourceDelta[] getDeltas(IProject[] projects) { > if(DEBUG) { >- System.out.println("Searching for deltas for build of project: "+fCurrentProject.getName()); //$NON-NLS-1$ >+ System.out.println("Searching for deltas for build of project: "+this.currentproject.getName()); //$NON-NLS-1$ > } > ArrayList deltas = new ArrayList(); >- IResourceDelta delta = getDelta(fCurrentProject); >+ IResourceDelta delta = getDelta(this.currentproject); > if(delta != null) { > if (DEBUG) { > System.out.println("Found a delta: " + delta); //$NON-NLS-1$ >@@ -1041,11 +612,14 @@ > } > > /** >- * Returns the API analyzer to use with this instance of the builder >+ * Returns the API analyzer to use with this instance of the builder > * @return the API analyzer to use > */ >- protected IApiAnalyzer getAnalyzer() { >- return new BaseApiAnalyzer(); >+ protected synchronized IApiAnalyzer getAnalyzer() { >+ if(this.analyzer == null) { >+ this.analyzer = new BaseApiAnalyzer(); >+ } >+ return this.analyzer; > } > > /** >@@ -1056,15 +630,15 @@ > */ > private IProject[] getRequiredProjects(boolean includebinaries) throws CoreException { > IWorkspaceRoot workspaceRoot = ResourcesPlugin.getWorkspace().getRoot(); >- if (fCurrentProject == null || workspaceRoot == null) { >+ if (this.currentproject == null || workspaceRoot == null) { > return new IProject[0]; > } > ArrayList projects = new ArrayList(); > try { >- IJavaProject javaProject = JavaCore.create(fCurrentProject); >+ IJavaProject javaProject = JavaCore.create(this.currentproject); > HashSet blocations = new HashSet(); > blocations.add(javaProject.getOutputLocation()); >- fProjectToOutputLocations.put(fCurrentProject, blocations); >+ projecttooutputlocations.put(this.currentproject, blocations); > IClasspathEntry[] entries = javaProject.getResolvedClasspath(true); > for (int i = 0, l = entries.length; i < l; i++) { > IClasspathEntry entry = entries[i]; >@@ -1112,7 +686,7 @@ > } > } > } >- fProjectToOutputLocations.put(p, bins); >+ this.projecttooutputlocations.put(p, bins); > } > } > } >@@ -1128,9 +702,19 @@ > /** > * @return the workspace {@link IApiProfile} > */ >- private IApiBaseline getWorkspaceProfile() throws CoreException { >+ IApiBaseline getWorkspaceProfile() throws CoreException { > return ApiPlugin.getDefault().getApiBaselineManager().getWorkspaceBaseline(); > } >+ >+ /** >+ * Returns the output paths of the given project or <code>null</code> if none have been computed >+ * @param project >+ * @return the output paths for the given project or <code>null</code> >+ */ >+ HashSet getProjectOutputPaths(IProject project) { >+ return (HashSet) this.projecttooutputlocations.get(project); >+ } >+ > /** > * Returns is the given classpath entry is optional or not > * @param entry >@@ -1145,39 +729,12 @@ > } > return false; > } >- >- /** >- * Resolves the java path from the given resource >- * @param resource >- * @return the resolved path or <code>null</code> if the resource is not part of the java model >- */ >- private IPath resolveJavaPathFromResource(IResource resource) { >- IJavaElement element = JavaCore.create(resource); >- if(element != null) { >- switch(element.getElementType()) { >- case IJavaElement.CLASS_FILE: { >- org.eclipse.jdt.core.IClassFile classfile = (org.eclipse.jdt.core.IClassFile) element; >- IType type = classfile.getType(); >- HashSet paths = (HashSet) fProjectToOutputLocations.get(resource.getProject()); >- IPath prefix = null; >- for(Iterator iter = paths.iterator(); iter.hasNext();) { >- prefix = (IPath) iter.next(); >- if(prefix.isPrefixOf(type.getPath())) { >- return type.getPath().removeFirstSegments(prefix.segmentCount()).removeFileExtension(); >- } >- } >- break; >- } >- } >- } >- return null; >- } > > /* (non-Javadoc) > * @see java.lang.Object#toString() > */ > public String toString() { >- return "Builder for project: ["+fCurrentProject.getName()+"]"; //$NON-NLS-1$ //$NON-NLS-2$ >+ return NLS.bind(BuilderMessages.ApiAnalysisBuilder_builder_for_project, this.currentproject.getName()); > } > > /** >@@ -1194,7 +751,7 @@ > /** > * Reads the build state for the relevant project. > */ >- protected static BuildState readState(IProject project) throws CoreException { >+ static BuildState readState(IProject project) throws CoreException { > File file = getSerializationFile(project); > if (file != null && file.exists()) { > try { >@@ -1245,7 +802,7 @@ > /** > * Returns the File to use for saving and restoring the last built state for the given project. > */ >- private static File getSerializationFile(IProject project) { >+ static File getSerializationFile(IProject project) { > if (!project.exists()) { > return null; > } >@@ -1259,7 +816,7 @@ > * @param state > * @throws CoreException > */ >- private static void saveBuiltState(IProject project, BuildState state) throws CoreException { >+ static void saveBuiltState(IProject project, BuildState state) throws CoreException { > if (DEBUG) { > System.out.println("Saving build state for project: "+project.getName()); //$NON-NLS-1$ > } >@@ -1305,7 +862,7 @@ > * Clears the last build state by setting it to <code>null</code> > * @throws CoreException > */ >- private void clearLastState() throws CoreException { >- setLastBuiltState(fCurrentProject, null); >+ void clearLastState() throws CoreException { >+ setLastBuiltState(this.currentproject, null); > } > } >Index: src/org/eclipse/pde/api/tools/internal/builder/buildermessages.properties >=================================================================== >RCS file: /cvsroot/eclipse/pde/apitools/org.eclipse.pde.api.tools/src/org/eclipse/pde/api/tools/internal/builder/buildermessages.properties,v >retrieving revision 1.44 >diff -u -r1.44 buildermessages.properties >--- src/org/eclipse/pde/api/tools/internal/builder/buildermessages.properties 7 Jan 2009 19:29:01 -0000 1.44 >+++ src/org/eclipse/pde/api/tools/internal/builder/buildermessages.properties 31 Mar 2009 03:38:36 -0000 >@@ -13,6 +13,7 @@ > building_workspace_profile=Building workspace API profile > checking_api_usage=Checking API use of ''{0}'' > AbstractTypeLeakDetector_vis_type_has_no_api_description=Visible type {0} has no API description >+ApiAnalysisBuilder_builder_for_project=Builder for project: [{0}] > ApiAnalysisBuilder_finding_affected_source_files=Finding affected source in ''{0}'' > ApiAnalysisBuilder_initializing_analyzer=Initializing analyzer for ''{0}'' > ApiProblemFactory_problem_message_not_found=Message not found for id: {0} >@@ -25,7 +26,6 @@ > build_saveStateComplete = Saved in {0} ms > build_wrongFileFormat = Wrong file format > build_cannotSaveState = Error saving last build state for project {0} >-IllegalExtendsProblemDetector_an_anonymous_declaration=An anonymous declaration > ReferenceAnalyzer_analyzing_api_checking_use=Analyzing API: Checking API use > ReferenceAnalyzer_analyzing_api=Analyzing API > ReferenceAnalyzer_api_analysis_error=API analysis error >Index: src/org/eclipse/pde/api/tools/internal/ApiBaselineManager.java >=================================================================== >RCS file: /cvsroot/eclipse/pde/apitools/org.eclipse.pde.api.tools/src/org/eclipse/pde/api/tools/internal/ApiBaselineManager.java,v >retrieving revision 1.7 >diff -u -r1.7 ApiBaselineManager.java >--- src/org/eclipse/pde/api/tools/internal/ApiBaselineManager.java 26 Mar 2009 18:43:54 -0000 1.7 >+++ src/org/eclipse/pde/api/tools/internal/ApiBaselineManager.java 31 Mar 2009 03:38:35 -0000 >@@ -56,7 +56,6 @@ > import org.eclipse.jdt.core.IPackageFragment; > import org.eclipse.jdt.core.IPackageFragmentRoot; > import org.eclipse.jdt.core.JavaCore; >-import org.eclipse.pde.api.tools.internal.builder.ApiAnalysisBuilder; > import org.eclipse.pde.api.tools.internal.model.ApiBaseline; > import org.eclipse.pde.api.tools.internal.model.ApiModelFactory; > import org.eclipse.pde.api.tools.internal.model.StubApiComponent; >@@ -888,7 +887,6 @@ > IJavaProject jp = JavaCore.create(project); > if (jp.exists()) { > ApiDescriptionManager.getDefault().clean(jp, true, true); >- ApiAnalysisBuilder.cleanupMarkers(resource); > } > } > } catch (CoreException e) { >Index: src/org/eclipse/pde/api/tools/internal/ApiDescriptionManager.java >=================================================================== >RCS file: /cvsroot/eclipse/pde/apitools/org.eclipse.pde.api.tools/src/org/eclipse/pde/api/tools/internal/ApiDescriptionManager.java,v >retrieving revision 1.22 >diff -u -r1.22 ApiDescriptionManager.java >--- src/org/eclipse/pde/api/tools/internal/ApiDescriptionManager.java 24 Mar 2009 18:50:44 -0000 1.22 >+++ src/org/eclipse/pde/api/tools/internal/ApiDescriptionManager.java 31 Mar 2009 03:38:35 -0000 >@@ -139,8 +139,8 @@ > * Cleans the API description for the given project. > * > * @param project >- * @param whether to delete the file on disk >- * @param whether to remove the cached API description >+ * @param delete whether to delete the file on disk >+ * @param remove whether to remove the cached API description > */ > public synchronized void clean(IJavaProject project, boolean delete, boolean remove) { > ProjectApiDescription desc = null; >@@ -261,7 +261,8 @@ > switch (delta.getKind()) { > case IJavaElementDelta.CHANGED: { > if ((flags & IJavaElementDelta.F_CONTENT) != 0 >- || (flags & IJavaElementDelta.F_FINE_GRAINED) != 0) { >+ || (flags & IJavaElementDelta.F_FINE_GRAINED) != 0 >+ || (flags & IJavaElementDelta.F_PRIMARY_RESOURCE) != 0){ > if (proj != null) { > projectChanged(proj); > return true; >@@ -502,6 +503,5 @@ > private static void abort(String message, Throwable exception) throws CoreException { > IStatus status = new Status(IStatus.ERROR, ApiPlugin.PLUGIN_ID, message, exception); > throw new CoreException(status); >- } >- >+ } > } >Index: src/org/eclipse/pde/api/tools/internal/CompilationUnit.java >=================================================================== >RCS file: /cvsroot/eclipse/pde/apitools/org.eclipse.pde.api.tools/src/org/eclipse/pde/api/tools/internal/CompilationUnit.java,v >retrieving revision 1.3 >diff -u -r1.3 CompilationUnit.java >--- src/org/eclipse/pde/api/tools/internal/CompilationUnit.java 21 Feb 2008 20:32:15 -0000 1.3 >+++ src/org/eclipse/pde/api/tools/internal/CompilationUnit.java 31 Mar 2009 03:38:35 -0000 >@@ -75,4 +75,11 @@ > } > return new FileInputStream(new File(filepath)); > } >+ >+ /* (non-Javadoc) >+ * @see java.lang.Object#toString() >+ */ >+ public String toString() { >+ return getName(); >+ } > } >Index: src/org/eclipse/pde/api/tools/internal/builder/IncrementalApiBuilder.java >=================================================================== >RCS file: src/org/eclipse/pde/api/tools/internal/builder/IncrementalApiBuilder.java >diff -N src/org/eclipse/pde/api/tools/internal/builder/IncrementalApiBuilder.java >--- /dev/null 1 Jan 1970 00:00:00 -0000 >+++ src/org/eclipse/pde/api/tools/internal/builder/IncrementalApiBuilder.java 1 Jan 1970 00:00:00 -0000 >@@ -0,0 +1,523 @@ >+/******************************************************************************* >+ * Copyright (c) 2009 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 >+ *******************************************************************************/ >+package org.eclipse.pde.api.tools.internal.builder; >+ >+import java.util.ArrayList; >+import java.util.HashSet; >+import java.util.Iterator; >+import java.util.List; >+import java.util.Set; >+ >+import org.eclipse.core.resources.IFile; >+import org.eclipse.core.resources.IMarker; >+import org.eclipse.core.resources.IProject; >+import org.eclipse.core.resources.IResource; >+import org.eclipse.core.resources.IResourceDelta; >+import org.eclipse.core.resources.IResourceDeltaVisitor; >+import org.eclipse.core.resources.IWorkspaceRoot; >+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.SubMonitor; >+import org.eclipse.jdt.core.ICompilationUnit; >+import org.eclipse.jdt.core.IJavaElement; >+import org.eclipse.jdt.core.IType; >+import org.eclipse.jdt.core.JavaCore; >+import org.eclipse.jdt.core.JavaModelException; >+import org.eclipse.jdt.internal.core.JavaModelManager; >+import org.eclipse.jdt.internal.core.builder.ReferenceCollection; >+import org.eclipse.jdt.internal.core.builder.State; >+import org.eclipse.jdt.internal.core.builder.StringSet; >+import org.eclipse.osgi.util.NLS; >+import org.eclipse.pde.api.tools.internal.provisional.ApiPlugin; >+import org.eclipse.pde.api.tools.internal.provisional.IApiMarkerConstants; >+import org.eclipse.pde.api.tools.internal.provisional.model.IApiBaseline; >+import org.eclipse.pde.api.tools.internal.provisional.model.IApiComponent; >+import org.eclipse.pde.api.tools.internal.util.Util; >+import org.eclipse.pde.core.plugin.IPluginModelBase; >+ >+/** >+ * Used to incrementally build changed Java types >+ * >+ * @since 3.5 >+ */ >+public class IncrementalApiBuilder { >+ >+ /** >+ * Visits a resource delta to collect changes that need to be built >+ */ >+ class ResourceDeltaVisitor implements IResourceDeltaVisitor { >+ HashSet projects = null; >+ IProject project = null; >+ >+ /** >+ * Constructor >+ * @param project >+ * @param projects >+ */ >+ public ResourceDeltaVisitor(IProject project, HashSet projects) { >+ this.project = project; >+ this.projects = projects; >+ } >+ /* (non-Javadoc) >+ * @see org.eclipse.core.resources.IResourceDeltaVisitor#visit(org.eclipse.core.resources.IResourceDelta) >+ */ >+ public boolean visit(IResourceDelta delta) throws CoreException { >+ switch (delta.getResource().getType()) { >+ case IResource.ROOT: >+ case IResource.PROJECT: >+ case IResource.FOLDER: { >+ return true; >+ } >+ case IResource.FILE: { >+ IResource resource = delta.getResource(); >+ String fileName = resource.getName(); >+ if (Util.isClassFile(fileName)) { >+ findAffectedSourceFiles(delta); >+ } else if (Util.isJavaFileName(fileName)) { >+ IProject project = resource.getProject(); >+ if (this.project.equals(project)) { >+ if (delta.getKind() == IResourceDelta.ADDED) { >+ IncrementalApiBuilder.this.addremovedeltas.add(delta); >+ } >+ IncrementalApiBuilder.this.changedtypes.add(resource); >+ } >+ else if (this.projects != null && this.projects.contains(project)) { >+ IncrementalApiBuilder.this.changedtypes.add(resource); >+ } >+ } >+ } >+ } >+ return false; >+ } >+ } >+ >+ ApiAnalysisBuilder builder = null; >+ //IProject project = null; >+ HashSet changedtypes = new HashSet(16); >+ HashSet addremovedeltas = new HashSet(8); >+ StringSet typenames = new StringSet(16); >+ StringSet packages = new StringSet(16); >+ >+ >+ /** >+ * Constructor >+ * @param project the current project context being built >+ * @param delta the {@link IResourceDelta} from the build framework >+ * @param buildstate the current build state from the {@link org.eclipse.jdt.internal.core.builder.JavaBuilder} >+ */ >+ public IncrementalApiBuilder(ApiAnalysisBuilder builder) { >+ this.builder = builder; >+ } >+ >+ /** >+ * Incrementally builds using the {@link org.eclipse.pde.api.tools.internal.provisional.builder.IApiAnalyzer} >+ * from the given {@link ApiAnalysisBuilder} >+ * >+ * @param baseline >+ * @param deltas >+ * @param monitor >+ * @throws CoreException >+ */ >+ public void build(IApiBaseline baseline, IResourceDelta[] deltas, BuildState buildstate, IProgressMonitor monitor) throws CoreException { >+ IProject project = this.builder.getProject(); >+ SubMonitor localmonitor = SubMonitor.convert(monitor, NLS.bind("API analysis: Incrementally building... {0}", project), 10); >+ try { >+ State state = (State)JavaModelManager.getJavaModelManager().getLastBuiltState(project, localmonitor.newChild(1)); >+ if(state == null) { >+ this.builder.buildAll(baseline, localmonitor); >+ return; >+ } >+ String[] projectNames = buildstate.getReexportedComponents(); >+ HashSet depprojects = null; >+ if (projectNames.length != 0) { >+ depprojects = new HashSet(); >+ IWorkspaceRoot root = ResourcesPlugin.getWorkspace().getRoot(); >+ IProject pj = null; >+ for (int i = 0, max = projectNames.length; i < max; i++) { >+ pj = root.getProject(projectNames[i]); >+ if (pj.isAccessible()) { >+ // select only projects that don't exist in the reference baseline >+ if (baseline != null && baseline.getApiComponent(projectNames[i]) == null) { >+ depprojects.add(pj); >+ } >+ } >+ } >+ } >+ ResourceDeltaVisitor visitor = new ResourceDeltaVisitor(project, depprojects); >+ for (int i = 0; i < deltas.length; i++) { >+ deltas[i].accept(visitor); >+ } >+ build(project, state, baseline, buildstate, localmonitor.newChild(1)); >+ } >+ finally { >+ if(!localmonitor.isCanceled()) { >+ localmonitor.done(); >+ } >+ this.changedtypes.clear(); >+ this.addremovedeltas.clear(); >+ this.typenames.clear(); >+ this.packages.clear(); >+ } >+ } >+ >+ /** >+ * Builds an API delta using the default profile (from the workspace settings and the current >+ * @param project >+ * workspace profile >+ * @param state >+ * @param monitor >+ */ >+ private void build(final IProject project, final State state, IApiBaseline baseline, BuildState buildstate, IProgressMonitor monitor) throws CoreException { >+ IApiBaseline wsprofile = null; >+ try { >+ // clear the old state so a full build will occur if this one is cancelled or terminates prematurely >+ this.builder.clearLastState(); >+ SubMonitor localmonitor = SubMonitor.convert(monitor, BuilderMessages.api_analysis_on_0, 1); >+ collectAffectedSourceFiles(project, state, this.changedtypes); >+ int typesize = this.changedtypes.size(); >+ this.builder.updateMonitor(localmonitor, 1); >+ localmonitor.setWorkRemaining(1+(typesize != 0 ? 5 : 0)); >+ localmonitor.subTask(NLS.bind(BuilderMessages.ApiAnalysisBuilder_finding_affected_source_files, project.getName())); >+ this.builder.updateMonitor(localmonitor, 0); >+ if (typesize != 0) { >+ IPluginModelBase currentModel = this.builder.getCurrentModel(); >+ if (currentModel != null) { >+ wsprofile = this.builder.getWorkspaceProfile(); >+ if (wsprofile == null) { >+ if (ApiAnalysisBuilder.DEBUG) { >+ System.err.println("Could not retrieve a workspace profile"); //$NON-NLS-1$ >+ } >+ return; >+ } >+ String id = currentModel.getBundleDescription().getSymbolicName(); >+ IApiComponent comp = wsprofile.getApiComponent(id); >+ if(comp == null) { >+ return; >+ } >+ List tnames = new ArrayList(typesize), >+ cnames = new ArrayList(typesize); >+ collectAllQualifiedNames(project, this.changedtypes, tnames, cnames, localmonitor.newChild(1)); >+ this.builder.updateMonitor(localmonitor, 1); >+ this.builder.getAnalyzer().analyzeComponent(buildstate, >+ null, >+ null, >+ baseline, >+ comp, >+ (String[])tnames.toArray(new String[tnames.size()]), >+ (String[])cnames.toArray(new String[cnames.size()]), >+ localmonitor.newChild(1)); >+ this.builder.updateMonitor(localmonitor, 1); >+ this.builder.createMarkers(); >+ this.builder.updateMonitor(localmonitor, 1); >+ } >+ } >+ } >+ finally { >+ if(wsprofile != null) { >+ wsprofile.close(); >+ } >+ if(monitor != null) { >+ monitor.done(); >+ } >+ } >+ } >+ >+ /** >+ * Collects the complete set of affected source files from the current project context based on the current JDT build state. >+ * >+ * @param project >+ * @param state >+ * @param typesToCheck >+ */ >+ private void collectAffectedSourceFiles(final IProject project, State state, Set typesToCheck) { >+ // the qualifiedStrings are of the form 'p1/p2' & the simpleStrings are just 'X' >+ char[][][] internedQualifiedNames = ReferenceCollection.internQualifiedNames(this.packages); >+ // if a well known qualified name was found then we can skip over these >+ if (internedQualifiedNames.length < this.packages.elementSize) { >+ internedQualifiedNames = null; >+ } >+ char[][] internedSimpleNames = ReferenceCollection.internSimpleNames(this.typenames, true); >+ // if a well known name was found then we can skip over these >+ if (internedSimpleNames.length < this.typenames.elementSize) { >+ internedSimpleNames = null; >+ } >+ Object[] keyTable = state.getReferences().keyTable; >+ Object[] valueTable = state.getReferences().valueTable; >+ IFile file = null; >+ String typeLocator = null; >+ next : for (int i = 0, l = valueTable.length; i < l; i++) { >+ typeLocator = (String) keyTable[i]; >+ if (typeLocator != null) { >+ ReferenceCollection refs = (ReferenceCollection) valueTable[i]; >+ if (refs.includes(internedQualifiedNames, internedSimpleNames, null)) { >+ file = project.getFile(typeLocator); >+ if (file == null) { >+ continue next; >+ } >+ if (ApiAnalysisBuilder.DEBUG) { >+ System.out.println(" adding affected source file " + typeLocator); //$NON-NLS-1$ >+ } >+ typesToCheck.add(file); >+ } >+ } >+ } >+ } >+ >+ /** >+ * Finds affected source files for a resource that has changed that either contains class files or is itself a class file >+ * @param binaryDelta >+ */ >+ private void findAffectedSourceFiles(IResourceDelta binaryDelta) { >+ IResource resource = binaryDelta.getResource(); >+ if(resource.getType() == IResource.FILE) { >+ if (Util.isClassFile(resource.getName())) { >+ switch (binaryDelta.getKind()) { >+ case IResourceDelta.REMOVED : >+ this.addremovedeltas.add(binaryDelta); >+ //$FALL-THROUGH$ >+ case IResourceDelta.ADDED : { >+ IPath typePath = resolveJavaPathFromResource(resource); >+ if(typePath == null) { >+ return; >+ } >+ if (ApiAnalysisBuilder.DEBUG) { >+ System.out.println("Found added/removed class file " + typePath); //$NON-NLS-1$ >+ } >+ addDependentsOf(typePath); >+ return; >+ } >+ case IResourceDelta.CHANGED : { >+ if ((binaryDelta.getFlags() & IResourceDelta.CONTENT) == 0) { >+ return; // skip it since it really isn't changed >+ } >+ IPath typePath = resolveJavaPathFromResource(resource); >+ if(typePath == null) { >+ return; >+ } >+ if (ApiAnalysisBuilder.DEBUG) { >+ System.out.println("Found changed class file " + typePath); //$NON-NLS-1$ >+ } >+ addDependentsOf(typePath); >+ } >+ } >+ return; >+ } >+ } >+ } >+ >+ /** >+ * Adds a type to search for dependents of in considered projects for an incremental build >+ * >+ * @param path >+ */ >+ void addDependentsOf(IPath path) { >+ // the qualifiedStrings are of the form 'p1/p2' & the simpleStrings are just 'X' >+ path = path.setDevice(null); >+ String packageName = path.removeLastSegments(1).toString(); >+ String typeName = path.lastSegment(); >+ int memberIndex = typeName.indexOf('$'); >+ if (memberIndex > 0) { >+ typeName = typeName.substring(0, memberIndex); >+ } >+ if (this.typenames.add(typeName) && this.packages.add(packageName) && ApiAnalysisBuilder.DEBUG) { >+ System.out.println(" will look for dependents of " + typeName + " in " + packageName); //$NON-NLS-1$ //$NON-NLS-2$ >+ } >+ } >+ >+ /** >+ * Returns an array of type names, and cleans up markers for the specified resource >+ * @param alltypes the listing of {@link IFile}s to get qualified names from >+ * @param changedtypes the listing of {@link IFile}s that have actually changed (from the {@link IResourceDelta} >+ * @param tnames the list to collect all type names into (including inner member names) >+ * @param cnames the list to collect the changed type names into >+ * @param monitor >+ */ >+ private void collectAllQualifiedNames(final IProject project, final HashSet alltypes, List tnames, List cnames, final IProgressMonitor monitor) { >+ IType[] types = null; >+ IFile file = null; >+ for (Iterator iterator = alltypes.iterator(); iterator.hasNext(); ) { >+ file = (IFile) iterator.next(); >+ ICompilationUnit unit = (ICompilationUnit) JavaCore.create(file); >+ if(!unit.exists()) { >+ continue; >+ } >+ IType type = unit.findPrimaryType(); >+ if(type == null) { >+ continue; >+ } >+ this.builder.updateMonitor(monitor, 0); >+ this.builder.cleanupUnsupportedTagMarkers(file); >+ this.builder.updateMonitor(monitor, 0); >+ this.builder.cleanupCompatibilityMarkers(file); >+ this.builder.updateMonitor(monitor, 0); >+ cnames.add(type.getFullyQualifiedName()); >+ try { >+ this.builder.cleanupUsageMarkers(file); >+ this.builder.updateMonitor(monitor, 0); >+ types = unit.getAllTypes(); >+ String tname = null; >+ for (int i = 0; i < types.length; i++) { >+ IType type2 = types[i]; >+ if (type2.isMember()) { >+ tname = type2.getFullyQualifiedName('$'); >+ } else { >+ tname = type2.getFullyQualifiedName(); >+ } >+ tnames.add(tname); >+ } >+ } catch (JavaModelException e) { >+ ApiPlugin.log(e.getStatus()); >+ } >+ this.builder.updateMonitor(monitor, 0); >+ } >+ // inject removed types inside changed type names so that we can properly detect type removal >+ IResourceDelta delta = null; >+ for (Iterator iterator = this.addremovedeltas.iterator(); iterator.hasNext(); ) { >+ delta = (IResourceDelta) iterator.next(); >+ if (delta.getKind() != IResourceDelta.REMOVED) { >+ continue; >+ } >+ IResource resource = delta.getResource(); >+ IPath typePath = resolveJavaPathFromResource(resource); >+ if(typePath == null) { >+ continue; >+ } >+ // record removed type names (package + type) >+ StringBuffer buffer = new StringBuffer(); >+ String[] segments = typePath.segments(); >+ for (int i = 0, max = segments.length; i < max; i++) { >+ if (i > 0) { >+ buffer.append('.'); >+ } >+ buffer.append(segments[i]); >+ } >+ cnames.add(String.valueOf(buffer)); >+ } >+ // clean up markers on added deltas >+ if (!this.addremovedeltas.isEmpty()) { >+ IResource manifestFile = Util.getManifestFile(project); >+ if (manifestFile != null) { >+ try { >+ IMarker[] markers = manifestFile.findMarkers(IApiMarkerConstants.COMPATIBILITY_PROBLEM_MARKER, false, IResource.DEPTH_INFINITE); >+ for (int i = 0, max = markers.length; i < max; i++) { >+ IMarker marker = markers[i]; >+ String typeName = marker.getAttribute(IApiMarkerConstants.MARKER_ATTR_PROBLEM_TYPE_NAME, null); >+ if (typeName != null) { >+ for (Iterator iterator = this.addremovedeltas.iterator(); iterator.hasNext(); ) { >+ delta = (IResourceDelta) iterator.next(); >+ if (delta.getKind() != IResourceDelta.ADDED) { >+ continue; >+ } >+ ICompilationUnit unit = (ICompilationUnit) JavaCore.create(delta.getResource()); >+ if(!unit.exists()) { >+ continue; >+ } >+ IType type = unit.findPrimaryType(); >+ if(type == null) { >+ continue; >+ } >+ if (typeName.equals(type.getFullyQualifiedName())) { >+ marker.delete(); >+ return; >+ } else { >+ // check secondary types >+ try { >+ types = unit.getAllTypes(); >+ for (int j = 0; j < types.length; j++) { >+ IType type2 = types[i]; >+ String fullyQualifiedName = null; >+ if (type2.isMember()) { >+ fullyQualifiedName = type2.getFullyQualifiedName('$'); >+ } else { >+ fullyQualifiedName = type2.getFullyQualifiedName(); >+ } >+ if (typeName.equals(fullyQualifiedName)) { >+ marker.delete(); >+ return; >+ } >+ } >+ } catch (JavaModelException e) { >+ ApiPlugin.log(e.getStatus()); >+ } >+ } >+ } >+ } >+ } >+ } catch (CoreException e) { >+ ApiPlugin.log(e.getStatus()); >+ } >+ } >+ } >+ IResource resource = project.findMember(ApiAnalysisBuilder.MANIFEST_PATH); >+ if (resource != null) { >+ try { >+ IMarker[] markers = resource.findMarkers(IApiMarkerConstants.COMPATIBILITY_PROBLEM_MARKER, false, IResource.DEPTH_ZERO); >+ loop: for (int i = 0, max = markers.length; i < max; i++) { >+ IMarker marker = markers[i]; >+ String typeNameFromMarker = Util.getTypeNameFromMarker(marker); >+ for (Iterator iterator = tnames.iterator(); iterator.hasNext(); ) { >+ String typeName = (String) iterator.next(); >+ if (typeName.equals(typeNameFromMarker)) { >+ marker.delete(); >+ continue loop; >+ } >+ } >+ } >+ markers = resource.findMarkers(IApiMarkerConstants.SINCE_TAGS_PROBLEM_MARKER, false, IResource.DEPTH_ZERO); >+ loop: for (int i = 0, max = markers.length; i < max; i++) { >+ IMarker marker = markers[i]; >+ String typeNameFromMarker = Util.getTypeNameFromMarker(marker); >+ for (Iterator iterator = tnames.iterator(); iterator.hasNext(); ) { >+ String typeName = (String) iterator.next(); >+ if (typeName.equals(typeNameFromMarker)) { >+ marker.delete(); >+ continue loop; >+ } >+ } >+ } >+ } catch (CoreException e) { >+ ApiPlugin.log(e); >+ } >+ } >+ } >+ >+ /** >+ * Resolves the java path from the given resource >+ * @param resource >+ * @return the resolved path or <code>null</code> if the resource is not part of the java model >+ */ >+ IPath resolveJavaPathFromResource(IResource resource) { >+ IJavaElement element = JavaCore.create(resource); >+ if(element != null) { >+ switch(element.getElementType()) { >+ case IJavaElement.CLASS_FILE: { >+ org.eclipse.jdt.core.IClassFile classfile = (org.eclipse.jdt.core.IClassFile) element; >+ IType type = classfile.getType(); >+ HashSet paths = this.builder.getProjectOutputPaths(resource.getProject()); >+ if(paths == null) { >+ return null; >+ } >+ IPath prefix = null; >+ for(Iterator iter = paths.iterator(); iter.hasNext();) { >+ prefix = (IPath) iter.next(); >+ if(prefix.isPrefixOf(type.getPath())) { >+ return type.getPath().removeFirstSegments(prefix.segmentCount()).removeFileExtension(); >+ } >+ } >+ break; >+ } >+ } >+ } >+ return null; >+ } >+}
You cannot view the attachment while viewing its details because your browser does not support IFRAMEs.
View the attachment on a separate page
.
View Attachment As Diff
View Attachment As Raw
Actions:
View
|
Diff
Attachments on
bug 233643
:
101805
|
126467
|
126895
|
127856
|
130342
|
130743
|
130860
|
131061
|
153351
|
155857