mirror of
https://github.com/eclipse-cdt/cdt
synced 2025-04-22 06:02:11 +02:00
Postpone build container creation to build start. Fixes possible Eclipse freeze. (#433)
The creation of the build container for Core Build projects is postponed to the start of the build process. StandardBuildConfiguration getBuildContainer and setBuildContainer have been cleaned up. CBuildConfiguration creation is started via CBuildConfigurationManager.getBuildConfiguration(IBuildConfiguration) which holds a lock on the HashMap 'configs'. Creation of StandardBuildConfiguration triggered, via applyProperties and getBuildContainer(), a Folder.create which loops back to CBuildConfigurationManager.getBuildConfiguration(). For detailed traces see https://github.com/eclipse-cdt/cdt/issues/424 Fixes #424
This commit is contained in:
parent
44dc9d7cd7
commit
8a8b94bfbb
3 changed files with 72 additions and 34 deletions
|
@ -2,7 +2,7 @@ Manifest-Version: 1.0
|
||||||
Bundle-ManifestVersion: 2
|
Bundle-ManifestVersion: 2
|
||||||
Bundle-Name: %pluginName
|
Bundle-Name: %pluginName
|
||||||
Bundle-SymbolicName: org.eclipse.cdt.core; singleton:=true
|
Bundle-SymbolicName: org.eclipse.cdt.core; singleton:=true
|
||||||
Bundle-Version: 8.2.100.qualifier
|
Bundle-Version: 8.2.200.qualifier
|
||||||
Bundle-Activator: org.eclipse.cdt.core.CCorePlugin
|
Bundle-Activator: org.eclipse.cdt.core.CCorePlugin
|
||||||
Bundle-Vendor: %providerName
|
Bundle-Vendor: %providerName
|
||||||
Bundle-Localization: plugin
|
Bundle-Localization: plugin
|
||||||
|
|
|
@ -232,20 +232,49 @@ public abstract class CBuildConfiguration extends PlatformObject implements ICBu
|
||||||
return toolChain != null ? toolChain.getBinaryParserIds() : List.of(CCorePlugin.DEFAULT_BINARY_PARSER_UNIQ_ID);
|
return toolChain != null ? toolChain.getBinaryParserIds() : List.of(CCorePlugin.DEFAULT_BINARY_PARSER_UNIQ_ID);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create build container if it doesn't exist yet.
|
||||||
|
*
|
||||||
|
* For a {@link StandardBuildConfiguration} the container can be the project or
|
||||||
|
* a folder. For all other Core Build configurations it is a folder.
|
||||||
|
*
|
||||||
|
* @param container Container where build is executed.
|
||||||
|
* @param monitor
|
||||||
|
* @throws CoreException
|
||||||
|
*/
|
||||||
|
/*
|
||||||
|
* Container creation is done at the start of the build process. Folder creation
|
||||||
|
* during the creation of a Core Build Configuration can lead to a loop back to
|
||||||
|
* CBuildConfigurationManager.getBuildConfiguration() that makes Eclipse freeze.
|
||||||
|
* This was seen with StandardBuildConfiguration when it created the build
|
||||||
|
* container. Folder.create got triggered via applyProperties() and
|
||||||
|
* getBuildContainer(). See https://github.com/eclipse-cdt/cdt/issues/424
|
||||||
|
*/
|
||||||
|
private void createBuildContainer(IContainer container, IProgressMonitor monitor) throws CoreException {
|
||||||
|
if (!(container instanceof IProject) && !container.exists()) {
|
||||||
|
IContainer parent = container.getParent();
|
||||||
|
if (!(parent instanceof IProject) && !parent.exists()) {
|
||||||
|
createBuildContainer(parent, monitor);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (container instanceof IFolder) {
|
||||||
|
((IFolder) container).create(IResource.FORCE | IResource.DERIVED, true, monitor);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Only the StandardBuildConfiguration has an option in the launch configuration
|
||||||
|
* to change the build container to the project root. For as long as the
|
||||||
|
* StandardBuildConfiguration is the only one there is no need to make the
|
||||||
|
* folder name a project property for all types. StandardBuildConfiguration has
|
||||||
|
* its own getBuildContainer() override.
|
||||||
|
*/
|
||||||
public IContainer getBuildContainer() throws CoreException {
|
public IContainer getBuildContainer() throws CoreException {
|
||||||
// TODO make the name of this folder a project property
|
|
||||||
IProject project = getProject();
|
IProject project = getProject();
|
||||||
IFolder buildRootFolder = project.getFolder("build"); //$NON-NLS-1$
|
IFolder buildRootFolder = project.getFolder("build"); //$NON-NLS-1$
|
||||||
IFolder buildFolder = buildRootFolder.getFolder(name);
|
IFolder buildFolder = buildRootFolder.getFolder(name);
|
||||||
|
|
||||||
IProgressMonitor monitor = new NullProgressMonitor();
|
|
||||||
if (!buildRootFolder.exists()) {
|
|
||||||
buildRootFolder.create(IResource.FORCE | IResource.DERIVED, true, monitor);
|
|
||||||
}
|
|
||||||
if (!buildFolder.exists()) {
|
|
||||||
buildFolder.create(IResource.FORCE | IResource.DERIVED, true, monitor);
|
|
||||||
}
|
|
||||||
|
|
||||||
return buildFolder;
|
return buildFolder;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -521,6 +550,9 @@ public abstract class CBuildConfiguration extends PlatformObject implements ICBu
|
||||||
IConsole console, IProgressMonitor monitor) throws IOException, CoreException {
|
IConsole console, IProgressMonitor monitor) throws IOException, CoreException {
|
||||||
Process process = null;
|
Process process = null;
|
||||||
IToolChain tc = getToolChain();
|
IToolChain tc = getToolChain();
|
||||||
|
|
||||||
|
createBuildContainer(getBuildContainer(), monitor);
|
||||||
|
|
||||||
if (tc instanceof IToolChain2) {
|
if (tc instanceof IToolChain2) {
|
||||||
process = ((IToolChain2) tc).startBuildProcess(this, commands, buildDirectory.toString(), envVars, console,
|
process = ((IToolChain2) tc).startBuildProcess(this, commands, buildDirectory.toString(), envVars, console,
|
||||||
monitor);
|
monitor);
|
||||||
|
|
|
@ -84,16 +84,20 @@ public class StandardBuildConfiguration extends CBuildConfiguration {
|
||||||
setupEnvVars();
|
setupEnvVars();
|
||||||
}
|
}
|
||||||
|
|
||||||
private void applyProperties() {
|
private IContainer getContainer(String containerPath) {
|
||||||
String container = getProperty(BUILD_CONTAINER);
|
if (containerPath != null && !containerPath.trim().isEmpty()) {
|
||||||
if (container != null && !container.trim().isEmpty()) {
|
IPath containerLoc = new org.eclipse.core.runtime.Path(containerPath);
|
||||||
IPath containerLoc = new org.eclipse.core.runtime.Path(container);
|
|
||||||
if (containerLoc.segmentCount() == 1) {
|
if (containerLoc.segmentCount() == 1) {
|
||||||
buildContainer = ResourcesPlugin.getWorkspace().getRoot().getProject(containerLoc.segment(0));
|
return ResourcesPlugin.getWorkspace().getRoot().getProject(containerLoc.segment(0));
|
||||||
} else {
|
} else {
|
||||||
buildContainer = ResourcesPlugin.getWorkspace().getRoot().getFolder(containerLoc);
|
return ResourcesPlugin.getWorkspace().getRoot().getFolder(containerLoc);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
private void applyProperties() {
|
||||||
|
setBuildContainer(getProperty(BUILD_CONTAINER));
|
||||||
|
|
||||||
String buildCmd = getProperty(BUILD_COMMAND);
|
String buildCmd = getProperty(BUILD_COMMAND);
|
||||||
if (buildCmd != null && !buildCmd.trim().isEmpty()) {
|
if (buildCmd != null && !buildCmd.trim().isEmpty()) {
|
||||||
|
@ -137,9 +141,26 @@ public class StandardBuildConfiguration extends CBuildConfiguration {
|
||||||
return envVars;
|
return envVars;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set the build container based on the full path starting from workspace root.
|
||||||
|
*
|
||||||
|
* @param containerPath Path from workspace root.
|
||||||
|
*/
|
||||||
|
private void setBuildContainer(String containerPath) {
|
||||||
|
IContainer container = null;
|
||||||
|
if (containerPath != null && !containerPath.trim().isEmpty()) {
|
||||||
|
container = getContainer(containerPath);
|
||||||
|
}
|
||||||
|
setBuildContainer(container);
|
||||||
|
}
|
||||||
|
|
||||||
public void setBuildContainer(IContainer buildContainer) {
|
public void setBuildContainer(IContainer buildContainer) {
|
||||||
this.buildContainer = buildContainer;
|
this.buildContainer = buildContainer;
|
||||||
setProperty(BUILD_CONTAINER, buildContainer.getFullPath().toString());
|
if (buildContainer == null) {
|
||||||
|
setProperty(BUILD_CONTAINER, ""); // overwrite old property value.
|
||||||
|
} else {
|
||||||
|
setProperty(BUILD_CONTAINER, buildContainer.getFullPath().toString());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void setBuildCommand(String[] buildCommand) {
|
public void setBuildCommand(String[] buildCommand) {
|
||||||
|
@ -162,27 +183,12 @@ public class StandardBuildConfiguration extends CBuildConfiguration {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void createBuildContainer(IContainer container, IProgressMonitor monitor) throws CoreException {
|
|
||||||
IContainer parent = container.getParent();
|
|
||||||
if (!(parent instanceof IProject) && !parent.exists()) {
|
|
||||||
createBuildContainer(parent, monitor);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (container instanceof IFolder) {
|
|
||||||
((IFolder) container).create(IResource.FORCE | IResource.DERIVED, true, monitor);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public IContainer getBuildContainer() throws CoreException {
|
public IContainer getBuildContainer() throws CoreException {
|
||||||
if (buildContainer == null) {
|
if (buildContainer == null) {
|
||||||
return super.getBuildContainer();
|
setBuildContainer(getDefaultBuildContainer());
|
||||||
} else {
|
|
||||||
if (!(buildContainer instanceof IProject) && !buildContainer.exists()) {
|
|
||||||
createBuildContainer(buildContainer, new NullProgressMonitor());
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
return buildContainer != null ? buildContainer : super.getBuildContainer();
|
return buildContainer;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
Loading…
Add table
Reference in a new issue