package org.eclipse.jdt.internal.core.builder;
import org.eclipse.core.resources.*;
import org.eclipse.core.runtime.*;
import org.eclipse.jdt.core.*;
import org.eclipse.jdt.core.compiler.*;
import org.eclipse.jdt.internal.compiler.util.SimpleLookupTable;
import org.eclipse.jdt.internal.core.*;
import org.eclipse.jdt.internal.core.util.Messages;
import org.eclipse.jdt.internal.core.util.Util;
import java.io.*;
import java.util.*;
@SuppressWarnings({"rawtypes", "unchecked"})
public class JavaBuilder extends IncrementalProjectBuilder {
IProject currentProject;
JavaProject javaProject;
IWorkspaceRoot workspaceRoot;
CompilationParticipant[] participants;
NameEnvironment nameEnvironment;
NameEnvironment testNameEnvironment;
SimpleLookupTable binaryLocationsPerProject;
public State lastState;
BuildNotifier notifier;
char[][] ;
String[] ;
public static final String SOURCE_ID = "JDT";
public static boolean DEBUG = false;
public static boolean SHOW_STATS = false;
private static final boolean DISABLE_AUTO_BUILDING_ON_SETTINGS_CHANGE = Boolean.getBoolean("org.eclipse.disableAutoBuildOnSettingsChange");
private static final IPath JDT_CORE_SETTINGS_PATH = Path.fromPortableString(JavaProject.DEFAULT_PREFERENCES_DIRNAME + IPath.SEPARATOR + JavaProject.JAVA_CORE_PREFS_FILE);
static LinkedHashSet<String> builtProjects;
public static IMarker[] getProblemsFor(IResource resource) {
try {
if (resource != null && resource.exists()) {
IMarker[] markers = resource.findMarkers(IJavaModelMarker.JAVA_MODEL_PROBLEM_MARKER, false, IResource.DEPTH_INFINITE);
Set markerTypes = JavaModelManager.getJavaModelManager().compilationParticipants.managedMarkerTypes();
if (markerTypes.isEmpty()) return markers;
ArrayList markerList = new ArrayList(5);
for (int i = 0, length = markers.length; i < length; i++) {
markerList.add(markers[i]);
}
Iterator iterator = markerTypes.iterator();
while (iterator.hasNext()) {
markers = resource.findMarkers((String) iterator.next(), false, IResource.DEPTH_INFINITE);
for (int i = 0, length = markers.length; i < length; i++) {
markerList.add(markers[i]);
}
}
IMarker[] result;
markerList.toArray(result = new IMarker[markerList.size()]);
return result;
}
} catch (CoreException e) {
}
return new IMarker[0];
}
public static IMarker[] getTasksFor(IResource resource) {
try {
if (resource != null && resource.exists())
return resource.findMarkers(IJavaModelMarker.TASK_MARKER, false, IResource.DEPTH_INFINITE);
} catch (CoreException e) {
}
return new IMarker[0];
}
public static void buildStarting() {
}
public static void buildFinished() {
BuildNotifier.resetProblemCounters();
}
public static void removeProblemsFor(IResource resource) {
try {
if (resource != null && resource.exists()) {
resource.deleteMarkers(IJavaModelMarker.JAVA_MODEL_PROBLEM_MARKER, false, IResource.DEPTH_INFINITE);
Set markerTypes = JavaModelManager.getJavaModelManager().compilationParticipants.managedMarkerTypes();
if (markerTypes.size() == 0) return;
Iterator iterator = markerTypes.iterator();
while (iterator.hasNext())
resource.deleteMarkers((String) iterator.next(), false, IResource.DEPTH_INFINITE);
}
} catch (CoreException e) {
}
}
public static void removeTasksFor(IResource resource) {
try {
if (resource != null && resource.exists())
resource.deleteMarkers(IJavaModelMarker.TASK_MARKER, false, IResource.DEPTH_INFINITE);
} catch (CoreException e) {
}
}
public static void removeProblemsAndTasksFor(IResource resource) {
try {
if (resource != null && resource.exists()) {
resource.deleteMarkers(IJavaModelMarker.JAVA_MODEL_PROBLEM_MARKER, false, IResource.DEPTH_INFINITE);
resource.deleteMarkers(IJavaModelMarker.TASK_MARKER, false, IResource.DEPTH_INFINITE);
Set markerTypes = JavaModelManager.getJavaModelManager().compilationParticipants.managedMarkerTypes();
if (markerTypes.size() == 0) return;
Iterator iterator = markerTypes.iterator();
while (iterator.hasNext())
resource.deleteMarkers((String) iterator.next(), false, IResource.DEPTH_INFINITE);
}
} catch (CoreException e) {
}
}
public static State readState(IProject project, DataInputStream in) throws IOException, CoreException {
return State.read(project, in);
}
public static void writeState(Object state, DataOutputStream out) throws IOException {
((State) state).write(out);
}
@Override
protected IProject[] build(int kind, Map ignored, IProgressMonitor monitor) throws CoreException {
this.currentProject = getProject();
if (this.currentProject == null || !this.currentProject.isAccessible()) return new IProject[0];
if (DEBUG)
System.out.println("\nJavaBuilder: Starting build of " + this.currentProject.getName()
+ " @ " + new Date(System.currentTimeMillis()));
this.notifier = new BuildNotifier(monitor, this.currentProject);
this.notifier.begin();
boolean ok = false;
try {
this.notifier.checkCancel();
kind = initializeBuilder(kind, true);
if (isWorthBuilding()) {
if (kind == FULL_BUILD) {
if (DEBUG)
System.out.println("JavaBuilder: Performing full build as requested");
buildAll();
} else {
if ((this.lastState = getLastState(this.currentProject)) == null) {
if (DEBUG)
System.out.println("JavaBuilder: Performing full build since last saved state was not found");
buildAll();
} else if (hasClasspathChanged()) {
if (DEBUG)
System.out.println("JavaBuilder: Performing full build since classpath has changed");
buildAll();
} else if (this.nameEnvironment.sourceLocations.length > 0 || this.testNameEnvironment.sourceLocations.length > 0) {
SimpleLookupTable deltas = findDeltas();
if (deltas == null) {
if (DEBUG)
System.out.println("JavaBuilder: Performing full build since deltas are missing after incremental request");
buildAll();
} else if (deltas.elementSize > 0) {
if (hasJdtCoreSettingsChange(deltas) && !DISABLE_AUTO_BUILDING_ON_SETTINGS_CHANGE) {
if (DEBUG)
System.out.println("JavaBuilder: Performing full build since project settings have changed");
buildAll();
} else {
buildDeltas(deltas);
}
} else if (DEBUG) {
System.out.println("JavaBuilder: Nothing to build since deltas were empty");
}
} else {
if (hasStructuralDelta()) {
if (DEBUG)
System.out.println("JavaBuilder: Performing full build since there are structural deltas");
buildAll();
} else {
if (DEBUG)
System.out.println("JavaBuilder: Nothing to build since there are no source folders and no deltas");
this.lastState.tagAsNoopBuild();
}
}
}
ok = true;
}
} catch (CoreException e) {
Util.log(e, "JavaBuilder handling CoreException while building: " + this.currentProject.getName());
createInconsistentBuildMarker(e);
} catch (ImageBuilderInternalException e) {
Util.log(e.getThrowable(), "JavaBuilder handling ImageBuilderInternalException while building: " + this.currentProject.getName());
createInconsistentBuildMarker(e.coreException);
} catch (MissingSourceFileException e) {
if (DEBUG)
System.out.println(Messages.bind(Messages.build_missingSourceFile, e.missingSourceFile));
removeProblemsAndTasksFor(this.currentProject);
IMarker marker = this.currentProject.createMarker(IJavaModelMarker.JAVA_MODEL_PROBLEM_MARKER);
marker.setAttributes(
new String[] {IMarker.MESSAGE, IMarker.SEVERITY, IMarker.SOURCE_ID},
new Object[] {
Messages.bind(Messages.build_missingSourceFile, e.missingSourceFile),
Integer.valueOf(IMarker.SEVERITY_ERROR),
JavaBuilder.SOURCE_ID
}
);
} finally {
for (int i = 0, l = this.participants == null ? 0 : this.participants.length; i < l; i++)
this.participants[i].buildFinished(this.javaProject);
if (!ok)
clearLastState();
this.notifier.done();
cleanup();
}
IProject[] requiredProjects = getRequiredProjects(true);
if (DEBUG)
System.out.println("JavaBuilder: Finished build of " + this.currentProject.getName()
+ " @ " + new Date(System.currentTimeMillis()) + "\n");
return requiredProjects;
}
private void buildAll() {
this.notifier.checkCancel();
this.notifier.subTask(Messages.bind(Messages.build_preparingBuild, this.currentProject.getName()));
if (DEBUG && this.lastState != null)
System.out.println("JavaBuilder: Clearing last state : " + this.lastState);
clearLastState();
BatchImageBuilder imageBuilder = new BatchImageBuilder(this, true, CompilationGroup.MAIN);
BatchImageBuilder testImageBuilder = new BatchImageBuilder(imageBuilder, true, CompilationGroup.TEST);
imageBuilder.build();
if (testImageBuilder.sourceLocations.length > 0) {
testImageBuilder.build();
} else {
testImageBuilder.cleanUp();
}
recordNewState(imageBuilder.newState);
}
private void buildDeltas(SimpleLookupTable deltas) {
this.notifier.checkCancel();
this.notifier.subTask(Messages.bind(Messages.build_preparingBuild, this.currentProject.getName()));
if (DEBUG && this.lastState != null)
System.out.println("JavaBuilder: Clearing last state : " + this.lastState);
clearLastState();
IncrementalImageBuilder imageBuilder = new IncrementalImageBuilder(this);
if (imageBuilder.build(deltas)) {
recordNewState(imageBuilder.newState);
} else {
if (DEBUG)
System.out.println("JavaBuilder: Performing full build since incremental build failed");
buildAll();
}
}
@Override
protected void clean(IProgressMonitor monitor) throws CoreException {
this.currentProject = getProject();
if (this.currentProject == null || !this.currentProject.isAccessible()) return;
if (DEBUG)
System.out.println("\nJavaBuilder: Cleaning " + this.currentProject.getName()
+ " @ " + new Date(System.currentTimeMillis()));
this.notifier = new BuildNotifier(monitor, this.currentProject);
this.notifier.begin();
try {
this.notifier.checkCancel();
initializeBuilder(CLEAN_BUILD, true);
if (DEBUG)
System.out.println("JavaBuilder: Clearing last state as part of clean : " + this.lastState);
clearLastState();
removeProblemsAndTasksFor(this.currentProject);
new BatchImageBuilder(this, false, CompilationGroup.MAIN).cleanOutputFolders(false);
new BatchImageBuilder(this, false, CompilationGroup.TEST).cleanOutputFolders(false);
} catch (CoreException e) {
Util.log(e, "JavaBuilder handling CoreException while cleaning: " + this.currentProject.getName());
createInconsistentBuildMarker(e);
} finally {
this.notifier.done();
cleanup();
}
if (DEBUG)
System.out.println("JavaBuilder: Finished cleaning " + this.currentProject.getName()
+ " @ " + new Date(System.currentTimeMillis()));
}
private void createInconsistentBuildMarker(CoreException coreException) throws CoreException {
String message = null;
IStatus status = coreException.getStatus();
if (status.isMultiStatus()) {
IStatus[] children = status.getChildren();
if (children != null && children.length > 0)
message = children[0].getMessage();
}
if (message == null)
message = coreException.getMessage();
IMarker marker = this.currentProject.createMarker(IJavaModelMarker.JAVA_MODEL_PROBLEM_MARKER);
marker.setAttributes(
new String[] {IMarker.MESSAGE, IMarker.SEVERITY, IJavaModelMarker.CATEGORY_ID, IMarker.SOURCE_ID},
new Object[] {
Messages.bind(Messages.build_inconsistentProject, message),
Integer.valueOf(IMarker.SEVERITY_ERROR),
Integer.valueOf(CategorizedProblem.CAT_BUILDPATH),
JavaBuilder.SOURCE_ID
}
);
}
private void cleanup() {
this.participants = null;
if(this.nameEnvironment != null) {
this.nameEnvironment.cleanup();
this.nameEnvironment = null;
}
if(this.testNameEnvironment != null) {
this.testNameEnvironment.cleanup();
this.testNameEnvironment = null;
}
this.binaryLocationsPerProject = null;
this.lastState = null;
this.notifier = null;
this.extraResourceFileFilters = null;
this.extraResourceFolderFilters = null;
}
private void clearLastState() {
JavaModelManager.getJavaModelManager().setLastBuiltState(this.currentProject, null);
}
boolean (IResource resource) {
if (this.extraResourceFileFilters != null) {
char[] name = resource.getName().toCharArray();
for (int i = 0, l = this.extraResourceFileFilters.length; i < l; i++)
if (CharOperation.match(this.extraResourceFileFilters[i], name, true))
return true;
}
if (this.extraResourceFolderFilters != null) {
IPath path = resource.getProjectRelativePath();
String pathName = path.toString();
int count = path.segmentCount();
if (resource.getType() == IResource.FILE) count--;
for (int i = 0, l = this.extraResourceFolderFilters.length; i < l; i++)
if (pathName.indexOf(this.extraResourceFolderFilters[i]) != -1)
for (int j = 0; j < count; j++)
if (this.extraResourceFolderFilters[i].equals(path.segment(j)))
return true;
}
return false;
}
private SimpleLookupTable findDeltas() {
this.notifier.subTask(Messages.bind(Messages.build_readingDelta, this.currentProject.getName()));
IResourceDelta delta = getDelta(this.currentProject);
SimpleLookupTable deltas = new SimpleLookupTable(3);
if (delta != null) {
if (delta.getKind() != IResourceDelta.NO_CHANGE) {
if (DEBUG)
System.out.println("JavaBuilder: Found source delta for: " + this.currentProject.getName());
deltas.put(this.currentProject, delta);
}
} else {
if (DEBUG)
System.out.println("JavaBuilder: Missing delta for: " + this.currentProject.getName());
this.notifier.subTask("");
return null;
}
Object[] keyTable = this.binaryLocationsPerProject.keyTable;
Object[] valueTable = this.binaryLocationsPerProject.valueTable;
nextProject : for (int i = 0, l = keyTable.length; i < l; i++) {
IProject p = (IProject) keyTable[i];
if (p != null && p != this.currentProject) {
State s = getLastState(p);
if (!this.lastState.wasStructurallyChanged(p, s)) {
if (s.wasNoopBuild())
continue nextProject;
ClasspathLocation[] classFoldersAndJars = (ClasspathLocation[]) valueTable[i];
boolean canSkip = true;
for (int j = 0, m = classFoldersAndJars.length; j < m; j++) {
if (classFoldersAndJars[j].isOutputFolder())
classFoldersAndJars[j] = null;
else
canSkip = false;
}
if (canSkip) continue nextProject;
}
this.notifier.subTask(Messages.bind(Messages.build_readingDelta, p.getName()));
delta = getDelta(p);
if (delta != null) {
if (delta.getKind() != IResourceDelta.NO_CHANGE) {
if (DEBUG)
System.out.println("JavaBuilder: Found binary delta for: " + p.getName());
deltas.put(p, delta);
}
} else {
if (DEBUG)
System.out.println("JavaBuilder: Missing delta for: " + p.getName());
this.notifier.subTask("");
return null;
}
}
}
this.notifier.subTask("");
return deltas;
}
public State getLastState(IProject project) {
return (State) JavaModelManager.getJavaModelManager().getLastBuiltState(project, this.notifier.monitor);
}
private IProject[] getRequiredProjects(boolean includeBinaryPrerequisites) {
if (this.javaProject == null || this.workspaceRoot == null) return new IProject[0];
LinkedHashSet<IProject> projects = new LinkedHashSet<>();
ExternalFoldersManager externalFoldersManager = JavaModelManager.getExternalManager();
try {
IClasspathEntry[] entries = this.javaProject.getExpandedClasspath();
for (int i = 0, l = entries.length; i < l; i++) {
IClasspathEntry entry = entries[i];
IPath path = entry.getPath();
IProject p = null;
switch (entry.getEntryKind()) {
case IClasspathEntry.CPE_PROJECT :
p = this.workspaceRoot.getProject(path.lastSegment());
if (((ClasspathEntry) entry).isOptional() && !JavaProject.hasJavaNature(p))
p = null;
break;
case IClasspathEntry.CPE_LIBRARY :
if (includeBinaryPrerequisites && path.segmentCount() > 0) {
IResource resource = this.workspaceRoot.findMember(path.segment(0));
if (resource instanceof IProject) {
p = (IProject) resource;
} else {
resource = externalFoldersManager.getFolder(path);
if (resource != null)
p = resource.getProject();
}
}
}
if (p != null && !projects.contains(p))
projects.add(p);
}
} catch(JavaModelException e) {
return new IProject[0];
}
IProject[] result = new IProject[projects.size()];
projects.toArray(result);
return result;
}
boolean hasBuildpathErrors() throws CoreException {
IMarker[] markers = this.currentProject.findMarkers(IJavaModelMarker.JAVA_MODEL_PROBLEM_MARKER, false, IResource.DEPTH_ZERO);
for (int i = 0, l = markers.length; i < l; i++)
if (markers[i].getAttribute(IJavaModelMarker.CATEGORY_ID, -1) == CategorizedProblem.CAT_BUILDPATH)
return true;
return false;
}
private boolean hasJdtCoreSettingsChange(SimpleLookupTable deltas) {
Object resourceDelta = deltas.get(this.currentProject);
if (resourceDelta instanceof IResourceDelta) {
return ((IResourceDelta) resourceDelta).findMember(JDT_CORE_SETTINGS_PATH) != null;
}
return false;
}
private boolean hasClasspathChanged() {
return hasClasspathChanged(CompilationGroup.MAIN) || hasClasspathChanged(CompilationGroup.TEST);
}
private boolean hasClasspathChanged(CompilationGroup compilationGroup) {
ClasspathMultiDirectory[] newSourceLocations = (compilationGroup == CompilationGroup.MAIN ? this.nameEnvironment : this.testNameEnvironment).sourceLocations;
ClasspathMultiDirectory[] oldSourceLocations = compilationGroup == CompilationGroup.MAIN ? this.lastState.sourceLocations : this.lastState.testSourceLocations;
int newLength = newSourceLocations.length;
int oldLength = oldSourceLocations.length;
int n, o;
for (n = o = 0; n < newLength && o < oldLength; n++, o++) {
if (newSourceLocations[n].equals(oldSourceLocations[o])) continue;
try {
if (newSourceLocations[n].sourceFolder.members().length == 0) {
o--;
continue;
} else if (this.lastState.isSourceFolderEmpty(oldSourceLocations[o].sourceFolder)) {
n--;
continue;
}
} catch (CoreException ignore) {
}
if (DEBUG) {
System.out.println("JavaBuilder: New location: " + newSourceLocations[n] + "\n!= old location: " + oldSourceLocations[o]);
printLocations(newSourceLocations, oldSourceLocations);
}
return true;
}
while (n < newLength) {
try {
if (newSourceLocations[n].sourceFolder.members().length == 0) {
n++;
continue;
}
} catch (CoreException ignore) {
}
if (DEBUG) {
System.out.println("JavaBuilder: Added non-empty source folder");
printLocations(newSourceLocations, oldSourceLocations);
}
return true;
}
while (o < oldLength) {
if (this.lastState.isSourceFolderEmpty(oldSourceLocations[o].sourceFolder)) {
o++;
continue;
}
if (DEBUG) {
System.out.println("JavaBuilder: Removed non-empty source folder");
printLocations(newSourceLocations, oldSourceLocations);
}
return true;
}
ClasspathLocation[] newBinaryLocations = (compilationGroup == CompilationGroup.MAIN ? this.nameEnvironment : this.testNameEnvironment).binaryLocations;
ClasspathLocation[] oldBinaryLocations = compilationGroup == CompilationGroup.MAIN ? this.lastState.binaryLocations : this.lastState.testBinaryLocations;
newLength = newBinaryLocations.length;
oldLength = oldBinaryLocations.length;
for (n = o = 0; n < newLength && o < oldLength; n++, o++) {
if (newBinaryLocations[n].equals(oldBinaryLocations[o])) continue;
if (DEBUG) {
System.out.println("JavaBuilder: New location: " + newBinaryLocations[n] + "\n!= old location: " + oldBinaryLocations[o]);
printLocations(newBinaryLocations, oldBinaryLocations);
}
return true;
}
if (n < newLength || o < oldLength) {
if (DEBUG) {
System.out.println("JavaBuilder: Number of binary folders/jar files has changed:");
printLocations(newBinaryLocations, oldBinaryLocations);
}
return true;
}
return false;
}
private boolean hasJavaBuilder(IProject project) throws CoreException {
ICommand[] buildCommands = project.getDescription().getBuildSpec();
for (int i = 0, l = buildCommands.length; i < l; i++)
if (buildCommands[i].getBuilderName().equals(JavaCore.BUILDER_ID))
return true;
return false;
}
private boolean hasStructuralDelta() {
IResourceDelta delta = getDelta(this.currentProject);
if (delta != null && delta.getKind() != IResourceDelta.NO_CHANGE) {
ClasspathLocation[] classFoldersAndJars = (ClasspathLocation[]) this.binaryLocationsPerProject.get(this.currentProject);
if (classFoldersAndJars != null) {
for (int i = 0, l = classFoldersAndJars.length; i < l; i++) {
ClasspathLocation classFolderOrJar = classFoldersAndJars[i];
if (classFolderOrJar != null) {
IPath p = classFolderOrJar.getProjectRelativePath();
if (p != null) {
IResourceDelta binaryDelta = delta.findMember(p);
if (binaryDelta != null && binaryDelta.getKind() != IResourceDelta.NO_CHANGE)
return true;
}
}
}
}
}
return false;
}
private int initializeBuilder(int kind, boolean forBuild) throws CoreException {
this.javaProject = (JavaProject) JavaCore.create(this.currentProject);
this.workspaceRoot = this.currentProject.getWorkspace().getRoot();
if (forBuild) {
this.participants = JavaModelManager.getJavaModelManager().compilationParticipants.getCompilationParticipants(this.javaProject);
if (this.participants != null)
for (int i = 0, l = this.participants.length; i < l; i++)
if (this.participants[i].aboutToBuild(this.javaProject) == CompilationParticipant.NEEDS_FULL_BUILD)
kind = FULL_BUILD;
String projectName = this.currentProject.getName();
if (builtProjects == null || builtProjects.contains(projectName)) {
builtProjects = new LinkedHashSet();
}
builtProjects.add(projectName);
}
this.binaryLocationsPerProject = new SimpleLookupTable(3);
this.nameEnvironment = new NameEnvironment(this.workspaceRoot, this.javaProject, this.binaryLocationsPerProject, this.notifier, CompilationGroup.MAIN);
this.testNameEnvironment = new NameEnvironment(this.workspaceRoot, this.javaProject, this.binaryLocationsPerProject, this.notifier, CompilationGroup.TEST);
if (forBuild) {
String filterSequence = this.javaProject.getOption(JavaCore.CORE_JAVA_BUILD_RESOURCE_COPY_FILTER, true);
char[][] filters = filterSequence != null && filterSequence.length() > 0
? CharOperation.splitAndTrimOn(',', filterSequence.toCharArray())
: null;
if (filters == null) {
this.extraResourceFileFilters = null;
this.extraResourceFolderFilters = null;
} else {
int fileCount = 0, folderCount = 0;
for (int i = 0, l = filters.length; i < l; i++) {
char[] f = filters[i];
if (f.length == 0) continue;
if (f[f.length - 1] == '/') folderCount++; else fileCount++;
}
this.extraResourceFileFilters = new char[fileCount][];
this.extraResourceFolderFilters = new String[folderCount];
for (int i = 0, l = filters.length; i < l; i++) {
char[] f = filters[i];
if (f.length == 0) continue;
if (f[f.length - 1] == '/')
this.extraResourceFolderFilters[--folderCount] = new String(f, 0, f.length - 1);
else
this.extraResourceFileFilters[--fileCount] = f;
}
}
}
return kind;
}
private boolean isClasspathBroken(JavaProject jProj, boolean tryRepair) throws CoreException {
IMarker[] markers = jProj.getProject().findMarkers(IJavaModelMarker.BUILDPATH_PROBLEM_MARKER, false, IResource.DEPTH_ZERO);
for (int i = 0, l = markers.length; i < l; i++) {
if (markers[i].getAttribute(IMarker.SEVERITY, -1) == IMarker.SEVERITY_ERROR) {
if (tryRepair) {
Object code = markers[i].getAttribute(IJavaModelMarker.ID);
if (code instanceof Integer && ((Integer)code) == IJavaModelStatusConstants.CP_INVALID_EXTERNAL_ANNOTATION_PATH) {
new ClasspathValidation(jProj).validate();
return isClasspathBroken(jProj, false);
}
}
return true;
}
}
return false;
}
private boolean isWorthBuilding() throws CoreException {
boolean abortBuilds =
JavaCore.ABORT.equals(this.javaProject.getOption(JavaCore.CORE_JAVA_BUILD_INVALID_CLASSPATH, true));
if (!abortBuilds) {
if (DEBUG)
System.out.println("JavaBuilder: Ignoring invalid classpath");
return true;
}
if (isClasspathBroken(this.javaProject, true)) {
if (DEBUG)
System.out.println("JavaBuilder: Aborted build because project has classpath errors (incomplete or involved in cycle)");
removeProblemsAndTasksFor(this.currentProject);
IMarker marker = this.currentProject.createMarker(IJavaModelMarker.JAVA_MODEL_PROBLEM_MARKER);
marker.setAttributes(
new String[] {IMarker.MESSAGE, IMarker.SEVERITY, IJavaModelMarker.CATEGORY_ID, IMarker.SOURCE_ID},
new Object[] {
Messages.build_abortDueToClasspathProblems,
Integer.valueOf(IMarker.SEVERITY_ERROR),
Integer.valueOf(CategorizedProblem.CAT_BUILDPATH),
JavaBuilder.SOURCE_ID
}
);
return false;
}
if (JavaCore.WARNING.equals(this.javaProject.getOption(JavaCore.CORE_INCOMPLETE_CLASSPATH, true)))
return true;
IProject[] requiredProjects = getRequiredProjects(false);
for (int i = 0, l = requiredProjects.length; i < l; i++) {
IProject p = requiredProjects[i];
if (getLastState(p) == null) {
JavaProject prereq = (JavaProject) JavaCore.create(p);
if (prereq.hasCycleMarker() && JavaCore.WARNING.equals(this.javaProject.getOption(JavaCore.CORE_CIRCULAR_CLASSPATH, true))) {
if (DEBUG)
System.out.println("JavaBuilder: Continued to build even though prereq project " + p.getName()
+ " was not built since its part of a cycle");
continue;
}
if (!hasJavaBuilder(p)) {
if (DEBUG)
System.out.println("JavaBuilder: Continued to build even though prereq project " + p.getName()
+ " is not built by JavaBuilder");
continue;
}
if (DEBUG)
System.out.println("JavaBuilder: Aborted build because prereq project " + p.getName()
+ " was not built");
removeProblemsAndTasksFor(this.currentProject);
IMarker marker = this.currentProject.createMarker(IJavaModelMarker.JAVA_MODEL_PROBLEM_MARKER);
marker.setAttributes(
new String[] {IMarker.MESSAGE, IMarker.SEVERITY, IJavaModelMarker.CATEGORY_ID, IMarker.SOURCE_ID},
new Object[] {
isClasspathBroken(prereq, true)
? Messages.bind(Messages.build_prereqProjectHasClasspathProblems, p.getName())
: Messages.bind(Messages.build_prereqProjectMustBeRebuilt, p.getName()),
Integer.valueOf(IMarker.SEVERITY_ERROR),
Integer.valueOf(CategorizedProblem.CAT_BUILDPATH),
JavaBuilder.SOURCE_ID
}
);
return false;
}
}
return true;
}
void mustPropagateStructuralChanges() {
LinkedHashSet cycleParticipants = new LinkedHashSet(3);
this.javaProject.updateCycleParticipants(new ArrayList(), cycleParticipants, new HashMap<>(), this.workspaceRoot, new HashSet(3), null);
IPath currentPath = this.javaProject.getPath();
Iterator i= cycleParticipants.iterator();
while (i.hasNext()) {
IPath participantPath = (IPath) i.next();
if (participantPath != currentPath) {
IProject project = this.workspaceRoot.getProject(participantPath.segment(0));
if (hasBeenBuilt(project)) {
if (DEBUG)
System.out.println("JavaBuilder: Requesting another build iteration since cycle participant " + project.getName()
+ " has not yet seen some structural changes");
needRebuild();
return;
}
}
}
}
private void printLocations(ClasspathLocation[] newLocations, ClasspathLocation[] oldLocations) {
System.out.println("JavaBuilder: New locations:");
for (int i = 0, length = newLocations.length; i < length; i++)
System.out.println(" " + newLocations[i].debugPathString());
System.out.println("JavaBuilder: Old locations:");
for (int i = 0, length = oldLocations.length; i < length; i++)
System.out.println(" " + oldLocations[i].debugPathString());
}
private void recordNewState(State state) {
Object[] keyTable = this.binaryLocationsPerProject.keyTable;
for (int i = 0, l = keyTable.length; i < l; i++) {
IProject prereqProject = (IProject) keyTable[i];
if (prereqProject != null && prereqProject != this.currentProject)
state.recordStructuralDependency(prereqProject, getLastState(prereqProject));
}
if (DEBUG)
System.out.println("JavaBuilder: Recording new state : " + state);
JavaModelManager.getJavaModelManager().setLastBuiltState(this.currentProject, state);
}
@Override
public String toString() {
return this.currentProject == null
? "JavaBuilder for unknown project"
: "JavaBuilder for " + this.currentProject.getName();
}
}