diff options
Diffstat (limited to 'eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/internal/build/builders/PreCompilerBuilder.java')
-rw-r--r-- | eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/internal/build/builders/PreCompilerBuilder.java | 1401 |
1 files changed, 0 insertions, 1401 deletions
diff --git a/eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/internal/build/builders/PreCompilerBuilder.java b/eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/internal/build/builders/PreCompilerBuilder.java deleted file mode 100644 index 0d9ee4897..000000000 --- a/eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/internal/build/builders/PreCompilerBuilder.java +++ /dev/null @@ -1,1401 +0,0 @@ -/* - * Copyright (C) 2007 The Android Open Source Project - * - * Licensed under the Eclipse Public License, Version 1.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.eclipse.org/org/documents/epl-v10.php - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package com.android.ide.eclipse.adt.internal.build.builders; - -import com.android.SdkConstants; -import com.android.annotations.NonNull; -import com.android.annotations.Nullable; -import com.android.ide.common.xml.ManifestData; -import com.android.ide.eclipse.adt.AdtConstants; -import com.android.ide.eclipse.adt.AdtPlugin; -import com.android.ide.eclipse.adt.internal.build.AaptParser; -import com.android.ide.eclipse.adt.internal.build.AidlProcessor; -import com.android.ide.eclipse.adt.internal.build.Messages; -import com.android.ide.eclipse.adt.internal.build.RenderScriptLauncher; -import com.android.ide.eclipse.adt.internal.build.RsSourceChangeHandler; -import com.android.ide.eclipse.adt.internal.build.SourceProcessor; -import com.android.ide.eclipse.adt.internal.build.builders.BaseBuilder.AbortBuildException; -import com.android.ide.eclipse.adt.internal.lint.EclipseLintClient; -import com.android.ide.eclipse.adt.internal.preferences.AdtPrefs; -import com.android.ide.eclipse.adt.internal.preferences.AdtPrefs.BuildVerbosity; -import com.android.ide.eclipse.adt.internal.project.AndroidManifestHelper; -import com.android.ide.eclipse.adt.internal.project.BaseProjectHelper; -import com.android.ide.eclipse.adt.internal.project.FixLaunchConfig; -import com.android.ide.eclipse.adt.internal.project.ProjectHelper; -import com.android.ide.eclipse.adt.internal.project.XmlErrorHandler.BasicXmlErrorListener; -import com.android.ide.eclipse.adt.internal.resources.manager.IdeScanningContext; -import com.android.ide.eclipse.adt.internal.resources.manager.ProjectResources; -import com.android.ide.eclipse.adt.internal.resources.manager.ResourceManager; -import com.android.ide.eclipse.adt.internal.sdk.AdtManifestMergeCallback; -import com.android.ide.eclipse.adt.internal.sdk.ProjectState; -import com.android.ide.eclipse.adt.internal.sdk.Sdk; -import com.android.ide.eclipse.adt.io.IFileWrapper; -import com.android.ide.eclipse.adt.io.IFolderWrapper; -import com.android.io.StreamException; -import com.android.manifmerger.ManifestMerger; -import com.android.manifmerger.MergerLog; -import com.android.sdklib.AndroidVersion; -import com.android.sdklib.BuildToolInfo; -import com.android.sdklib.IAndroidTarget; -import com.android.sdklib.build.RenderScriptChecker; -import com.android.sdklib.build.RenderScriptProcessor; -import com.android.sdklib.internal.build.BuildConfigGenerator; -import com.android.sdklib.internal.build.SymbolLoader; -import com.android.sdklib.internal.build.SymbolWriter; -import com.android.sdklib.internal.project.ProjectProperties; -import com.android.sdklib.io.FileOp; -import com.android.sdklib.repository.FullRevision; -import com.android.utils.ILogger; -import com.android.utils.Pair; -import com.android.xml.AndroidManifest; -import com.google.common.collect.ArrayListMultimap; -import com.google.common.collect.Lists; -import com.google.common.collect.Multimap; - -import org.eclipse.core.resources.IFile; -import org.eclipse.core.resources.IFolder; -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.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.IStatus; -import org.eclipse.core.runtime.NullProgressMonitor; -import org.eclipse.core.runtime.Path; -import org.eclipse.jdt.core.IJavaProject; -import org.eclipse.jdt.core.JavaCore; -import org.xml.sax.SAXException; - -import java.io.File; -import java.io.IOException; -import java.util.ArrayList; -import java.util.Collection; -import java.util.List; -import java.util.Map; - -import javax.xml.parsers.ParserConfigurationException; - -/** - * Pre Java Compiler. - * This incremental builder performs 2 tasks: - * <ul> - * <li>compiles the resources located in the res/ folder, along with the - * AndroidManifest.xml file into the R.java class.</li> - * <li>compiles any .aidl files into a corresponding java file.</li> - * </ul> - * - */ -public class PreCompilerBuilder extends BaseBuilder { - - /** This ID is used in plugin.xml and in each project's .project file. - * It cannot be changed even if the class is renamed/moved */ - public static final String ID = "com.android.ide.eclipse.adt.PreCompilerBuilder"; //$NON-NLS-1$ - - /** Flag to pass to PreCompiler builder that the build is a release build. - */ - public final static String RELEASE_REQUESTED = "android.releaseBuild"; //$NON-NLS-1$ - - private static final String PROPERTY_PACKAGE = "manifestPackage"; //$NON-NLS-1$ - private static final String PROPERTY_MERGE_MANIFEST = "mergeManifest"; //$NON-NLS-1$ - private static final String PROPERTY_COMPILE_RESOURCES = "compileResources"; //$NON-NLS-1$ - private static final String PROPERTY_COMPILE_BUILDCONFIG = "createBuildConfig"; //$NON-NLS-1$ - private static final String PROPERTY_BUILDCONFIG_MODE = "buildConfigMode"; //$NON-NLS-1$ - - private static final boolean MANIFEST_MERGER_ENABLED_DEFAULT = false; - private static final String MANIFEST_MERGER_PROPERTY = "manifestmerger.enabled"; //$NON-NLS-1$ - - /** Merge Manifest Flag. Computed from resource delta, reset after action is taken. - * Stored persistently in the project. */ - private boolean mMustMergeManifest = false; - /** Resource compilation Flag. Computed from resource delta, reset after action is taken. - * Stored persistently in the project. */ - private boolean mMustCompileResources = false; - /** BuildConfig Flag. Computed from resource delta, reset after action is taken. - * Stored persistently in the project. */ - private boolean mMustCreateBuildConfig = false; - /** BuildConfig last more Flag. Computed from resource delta, reset after action is taken. - * Stored persistently in the project. */ - private boolean mLastBuildConfigMode; - - /** cache of the java package defined in the manifest */ - private String mManifestPackage; - - /** Output folder for generated Java File. Created on the Builder init - * @see #startupOnInitialize() - */ - private IFolder mGenFolder; - - /** - * Progress monitor used at the end of every build to refresh the content of the 'gen' folder - * and set the generated files as derived. - */ - private DerivedProgressMonitor mDerivedProgressMonitor; - - private AidlProcessor mAidlProcessor; - private RsSourceChangeHandler mRenderScriptSourceChangeHandler; - - /** - * Progress monitor waiting the end of the process to set a persistent value - * in a file. This is typically used in conjunction with <code>IResource.refresh()</code>, - * since this call is asynchronous, and we need to wait for it to finish for the file - * to be known by eclipse, before we can call <code>resource.setPersistentProperty</code> on - * a new file. - */ - private static class DerivedProgressMonitor implements IProgressMonitor { - private boolean mCancelled = false; - private boolean mDone = false; - private final IFolder mGenFolder; - - public DerivedProgressMonitor(IFolder genFolder) { - mGenFolder = genFolder; - } - - void reset() { - mDone = false; - } - - @Override - public void beginTask(String name, int totalWork) { - } - - @Override - public void done() { - if (mDone == false) { - mDone = true; - processChildrenOf(mGenFolder); - } - } - - private void processChildrenOf(IFolder folder) { - IResource[] list; - try { - list = folder.members(); - } catch (CoreException e) { - return; - } - - for (IResource member : list) { - if (member.exists()) { - if (member.getType() == IResource.FOLDER) { - processChildrenOf((IFolder) member); - } - - try { - member.setDerived(true, new NullProgressMonitor()); - } catch (CoreException e) { - // This really shouldn't happen since we check that the resource - // exist. - // Worst case scenario, the resource isn't marked as derived. - } - } - } - } - - @Override - public void internalWorked(double work) { - } - - @Override - public boolean isCanceled() { - return mCancelled; - } - - @Override - public void setCanceled(boolean value) { - mCancelled = value; - } - - @Override - public void setTaskName(String name) { - } - - @Override - public void subTask(String name) { - } - - @Override - public void worked(int work) { - } - } - - public PreCompilerBuilder() { - super(); - } - - // build() returns a list of project from which this project depends for future compilation. - @Override - protected IProject[] build( - int kind, - @SuppressWarnings("rawtypes") Map args, - IProgressMonitor monitor) - throws CoreException { - // get a project object - IProject project = getProject(); - - if (DEBUG_LOG) { - AdtPlugin.log(IStatus.INFO, "%s BUILD(PRE)", project.getName()); - } - - // For the PreCompiler, only the library projects are considered Referenced projects, - // as only those projects have an impact on what is generated by this builder. - IProject[] result = null; - - IFolder resOutFolder = null; - - try { - assert mDerivedProgressMonitor != null; - - mDerivedProgressMonitor.reset(); - - // get the project info - ProjectState projectState = Sdk.getProjectState(project); - - // this can happen if the project has no project.properties. - if (projectState == null) { - return null; - } - - boolean isLibrary = projectState.isLibrary(); - - IAndroidTarget projectTarget = projectState.getTarget(); - - // get the libraries - List<IProject> libProjects = projectState.getFullLibraryProjects(); - result = libProjects.toArray(new IProject[libProjects.size()]); - - IJavaProject javaProject = JavaCore.create(project); - - // Top level check to make sure the build can move forward. - abortOnBadSetup(javaProject, projectState); - - // now we need to get the classpath list - List<IPath> sourceFolderPathList = BaseProjectHelper.getSourceClasspaths(javaProject); - - IFolder androidOutputFolder = BaseProjectHelper.getAndroidOutputFolder(project); - - resOutFolder = getResOutFolder(androidOutputFolder); - - setupSourceProcessors(javaProject, projectState, sourceFolderPathList, - androidOutputFolder); - - PreCompilerDeltaVisitor dv = null; - String javaPackage = null; - String minSdkVersion = null; - - if (kind == FULL_BUILD) { - AdtPlugin.printBuildToConsole(BuildVerbosity.VERBOSE, project, - Messages.Start_Full_Pre_Compiler); - - if (DEBUG_LOG) { - AdtPlugin.log(IStatus.INFO, "%s full build!", project.getName()); - } - - // do some clean up. - doClean(project, monitor); - - mMustMergeManifest = true; - mMustCompileResources = true; - mMustCreateBuildConfig = true; - - mAidlProcessor.prepareFullBuild(project); - mRenderScriptSourceChangeHandler.prepareFullBuild(); - } else { - AdtPlugin.printBuildToConsole(BuildVerbosity.VERBOSE, project, - Messages.Start_Inc_Pre_Compiler); - - // Go through the resources and see if something changed. - // Even if the mCompileResources flag is true from a previously aborted - // build, we need to go through the Resource delta to get a possible - // list of aidl files to compile/remove. - IResourceDelta delta = getDelta(project); - if (delta == null) { - mMustCompileResources = true; - - mAidlProcessor.prepareFullBuild(project); - mRenderScriptSourceChangeHandler.prepareFullBuild(); - } else { - dv = new PreCompilerDeltaVisitor(this, sourceFolderPathList, - mAidlProcessor.getChangeHandler(), - mRenderScriptSourceChangeHandler); - delta.accept(dv); - - // Check to see if Manifest.xml, Manifest.java, or R.java have changed: - mMustCompileResources |= dv.getCompileResources(); - mMustMergeManifest |= dv.hasManifestChanged(); - - // Notify the ResourceManager: - ResourceManager resManager = ResourceManager.getInstance(); - - if (ResourceManager.isAutoBuilding()) { - ProjectResources projectResources = resManager.getProjectResources(project); - - IdeScanningContext context = new IdeScanningContext(projectResources, - project, true); - - boolean wasCleared = projectResources.ensureInitialized(); - - if (!wasCleared) { - resManager.processDelta(delta, context); - } - - // Check whether this project or its dependencies (libraries) have - // resources that need compilation - if (wasCleared || context.needsFullAapt()) { - mMustCompileResources = true; - - // Must also call markAaptRequested on the project to not just - // store "aapt required" on this project, but also on any projects - // depending on this project if it's a library project - ResourceManager.markAaptRequested(project); - } - - // Update error markers in the source editor - if (!mMustCompileResources) { - context.updateMarkers(false /* async */); - } - } // else: already processed the deltas in ResourceManager's IRawDeltaListener - - mAidlProcessor.doneVisiting(project); - - // get the java package from the visitor - javaPackage = dv.getManifestPackage(); - minSdkVersion = dv.getMinSdkVersion(); - } - } - - // Has anyone marked this project as needing aapt? Typically done when - // one of the library projects this project depends on has changed - mMustCompileResources |= ResourceManager.isAaptRequested(project); - - // if the main manifest didn't change, then we check for the library - // ones (will trigger manifest merging too) - if (libProjects.size() > 0) { - for (IProject libProject : libProjects) { - IResourceDelta delta = getDelta(libProject); - if (delta != null) { - PatternBasedDeltaVisitor visitor = new PatternBasedDeltaVisitor( - project, libProject, - "PRE:LibManifest"); //$NON-NLS-1$ - visitor.addSet(ChangedFileSetHelper.MANIFEST); - - ChangedFileSet textSymbolCFS = null; - if (isLibrary == false) { - textSymbolCFS = ChangedFileSetHelper.getTextSymbols( - libProject); - visitor.addSet(textSymbolCFS); - } - - delta.accept(visitor); - - mMustMergeManifest |= visitor.checkSet(ChangedFileSetHelper.MANIFEST); - - if (textSymbolCFS != null) { - mMustCompileResources |= visitor.checkSet(textSymbolCFS); - } - - // no need to test others if we have all flags at true. - if (mMustMergeManifest && - (mMustCompileResources || textSymbolCFS == null)) { - break; - } - } - } - } - - // store the build status in the persistent storage - saveProjectBooleanProperty(PROPERTY_MERGE_MANIFEST, mMustMergeManifest); - saveProjectBooleanProperty(PROPERTY_COMPILE_RESOURCES, mMustCompileResources); - saveProjectBooleanProperty(PROPERTY_COMPILE_BUILDCONFIG, mMustCreateBuildConfig); - - // if there was some XML errors, we just return w/o doing - // anything since we've put some markers in the files anyway. - if (dv != null && dv.mXmlError) { - AdtPlugin.printErrorToConsole(project, Messages.Xml_Error); - - return result; - } - - if (projectState.getRenderScriptSupportMode()) { - FullRevision minBuildToolsRev = new FullRevision(19,0,3); - if (mBuildToolInfo.getRevision().compareTo(minBuildToolsRev) == -1) { - String msg = "RenderScript support mode requires Build-Tools 19.0.3 or later."; - AdtPlugin.printErrorToConsole(project, msg); - markProject(AdtConstants.MARKER_ADT, msg, IMarker.SEVERITY_ERROR); - - return result; - } - } - - // get the manifest file - IFile manifestFile = ProjectHelper.getManifest(project); - - if (manifestFile == null) { - String msg = String.format(Messages.s_File_Missing, - SdkConstants.FN_ANDROID_MANIFEST_XML); - AdtPlugin.printErrorToConsole(project, msg); - markProject(AdtConstants.MARKER_ADT, msg, IMarker.SEVERITY_ERROR); - - return result; - - // TODO: document whether code below that uses manifest (which is now guaranteed - // to be null) will actually be executed or not. - } - - // lets check the XML of the manifest first, if that hasn't been done by the - // resource delta visitor yet. - if (dv == null || dv.getCheckedManifestXml() == false) { - BasicXmlErrorListener errorListener = new BasicXmlErrorListener(); - try { - ManifestData parser = AndroidManifestHelper.parseUnchecked( - new IFileWrapper(manifestFile), - true /*gather data*/, - errorListener); - - if (errorListener.mHasXmlError == true) { - // There was an error in the manifest, its file has been marked - // by the XmlErrorHandler. The stopBuild() call below will abort - // this with an exception. - String msg = String.format(Messages.s_Contains_Xml_Error, - SdkConstants.FN_ANDROID_MANIFEST_XML); - AdtPlugin.printBuildToConsole(BuildVerbosity.VERBOSE, project, msg); - markProject(AdtConstants.MARKER_ADT, msg, IMarker.SEVERITY_ERROR); - - return result; - } - - // Get the java package from the parser. - // This can be null if the parsing failed because the resource is out of sync, - // in which case the error will already have been logged anyway. - if (parser != null) { - javaPackage = parser.getPackage(); - minSdkVersion = parser.getMinSdkVersionString(); - } - } catch (StreamException e) { - handleStreamException(e); - - return result; - } catch (ParserConfigurationException e) { - String msg = String.format( - "Bad parser configuration for %s: %s", - manifestFile.getFullPath(), - e.getMessage()); - - handleException(e, msg); - return result; - - } catch (SAXException e) { - String msg = String.format( - "Parser exception for %s: %s", - manifestFile.getFullPath(), - e.getMessage()); - - handleException(e, msg); - return result; - } catch (IOException e) { - String msg = String.format( - "I/O error for %s: %s", - manifestFile.getFullPath(), - e.getMessage()); - - handleException(e, msg); - return result; - } - } - - int minSdkValue = -1; - - if (minSdkVersion != null) { - try { - minSdkValue = Integer.parseInt(minSdkVersion); - } catch (NumberFormatException e) { - // it's ok, it means minSdkVersion contains a (hopefully) valid codename. - } - - AndroidVersion targetVersion = projectTarget.getVersion(); - - // remove earlier marker from the manifest - removeMarkersFromResource(manifestFile, AdtConstants.MARKER_ADT); - - if (minSdkValue != -1) { - String codename = targetVersion.getCodename(); - if (codename != null) { - // integer minSdk when the target is a preview => fatal error - String msg = String.format( - "Platform %1$s is a preview and requires application manifest to set %2$s to '%1$s'", - codename, AndroidManifest.ATTRIBUTE_MIN_SDK_VERSION); - AdtPlugin.printErrorToConsole(project, msg); - BaseProjectHelper.markResource(manifestFile, AdtConstants.MARKER_ADT, - msg, IMarker.SEVERITY_ERROR); - return result; - } else if (minSdkValue > targetVersion.getApiLevel()) { - // integer minSdk is too high for the target => warning - String msg = String.format( - "Attribute %1$s (%2$d) is higher than the project target API level (%3$d)", - AndroidManifest.ATTRIBUTE_MIN_SDK_VERSION, - minSdkValue, targetVersion.getApiLevel()); - AdtPlugin.printBuildToConsole(BuildVerbosity.VERBOSE, project, msg); - BaseProjectHelper.markResource(manifestFile, AdtConstants.MARKER_ADT, - msg, IMarker.SEVERITY_WARNING); - } - } else { - // looks like the min sdk is a codename, check it matches the codename - // of the platform - String codename = targetVersion.getCodename(); - if (codename == null) { - // platform is not a preview => fatal error - String msg = String.format( - "Manifest attribute '%1$s' is set to '%2$s'. Integer is expected.", - AndroidManifest.ATTRIBUTE_MIN_SDK_VERSION, minSdkVersion); - AdtPlugin.printErrorToConsole(project, msg); - BaseProjectHelper.markResource(manifestFile, AdtConstants.MARKER_ADT, - msg, IMarker.SEVERITY_ERROR); - return result; - } else if (codename.equals(minSdkVersion) == false) { - // platform and manifest codenames don't match => fatal error. - String msg = String.format( - "Value of manifest attribute '%1$s' does not match platform codename '%2$s'", - AndroidManifest.ATTRIBUTE_MIN_SDK_VERSION, codename); - AdtPlugin.printErrorToConsole(project, msg); - BaseProjectHelper.markResource(manifestFile, AdtConstants.MARKER_ADT, - msg, IMarker.SEVERITY_ERROR); - return result; - } - - // if we get there, the minSdkVersion is a codename matching the target - // platform codename. In this case we set minSdkValue to the previous API - // level, as it's used by source processors. - minSdkValue = targetVersion.getApiLevel(); - } - } else if (projectTarget.getVersion().isPreview()) { - // else the minSdkVersion is not set but we are using a preview target. - // Display an error - String codename = projectTarget.getVersion().getCodename(); - String msg = String.format( - "Platform %1$s is a preview and requires application manifests to set %2$s to '%1$s'", - codename, AndroidManifest.ATTRIBUTE_MIN_SDK_VERSION); - AdtPlugin.printErrorToConsole(project, msg); - BaseProjectHelper.markResource(manifestFile, AdtConstants.MARKER_ADT, msg, - IMarker.SEVERITY_ERROR); - return result; - } - - if (javaPackage == null || javaPackage.length() == 0) { - // looks like the AndroidManifest file isn't valid. - String msg = String.format(Messages.s_Doesnt_Declare_Package_Error, - SdkConstants.FN_ANDROID_MANIFEST_XML); - AdtPlugin.printErrorToConsole(project, msg); - BaseProjectHelper.markResource(manifestFile, AdtConstants.MARKER_ADT, - msg, IMarker.SEVERITY_ERROR); - - return result; - } else if (javaPackage.indexOf('.') == -1) { - // The application package name does not contain 2+ segments! - String msg = String.format( - "Application package '%1$s' must have a minimum of 2 segments.", - SdkConstants.FN_ANDROID_MANIFEST_XML); - AdtPlugin.printErrorToConsole(project, msg); - BaseProjectHelper.markResource(manifestFile, AdtConstants.MARKER_ADT, - msg, IMarker.SEVERITY_ERROR); - - return result; - } - - // at this point we have the java package. We need to make sure it's not a different - // package than the previous one that were built. - if (javaPackage.equals(mManifestPackage) == false) { - // The manifest package has changed, the user may want to update - // the launch configuration - if (mManifestPackage != null) { - AdtPlugin.printBuildToConsole(BuildVerbosity.VERBOSE, project, - Messages.Checking_Package_Change); - - FixLaunchConfig flc = new FixLaunchConfig(project, mManifestPackage, - javaPackage); - flc.start(); - } - - // record the new manifest package, and save it. - mManifestPackage = javaPackage; - saveProjectStringProperty(PROPERTY_PACKAGE, mManifestPackage); - - // force a clean - doClean(project, monitor); - mMustMergeManifest = true; - mMustCompileResources = true; - mMustCreateBuildConfig = true; - mAidlProcessor.prepareFullBuild(project); - mRenderScriptSourceChangeHandler.prepareFullBuild(); - - saveProjectBooleanProperty(PROPERTY_MERGE_MANIFEST, mMustMergeManifest); - saveProjectBooleanProperty(PROPERTY_COMPILE_RESOURCES, mMustCompileResources); - saveProjectBooleanProperty(PROPERTY_COMPILE_BUILDCONFIG, mMustCreateBuildConfig); - } - - try { - handleBuildConfig(args); - } catch (IOException e) { - handleException(e, "Failed to create BuildConfig class"); - return result; - } - - // merge the manifest - if (mMustMergeManifest) { - boolean enabled = MANIFEST_MERGER_ENABLED_DEFAULT; - String propValue = projectState.getProperty(MANIFEST_MERGER_PROPERTY); - if (propValue != null) { - enabled = Boolean.valueOf(propValue); - } - - if (mergeManifest(androidOutputFolder, libProjects, enabled) == false) { - return result; - } - } - - List<File> libProjectsOut = new ArrayList<File>(libProjects.size()); - for (IProject libProject : libProjects) { - libProjectsOut.add( - BaseProjectHelper.getAndroidOutputFolder(libProject) - .getLocation().toFile()); - } - - // run the source processors - int processorStatus = SourceProcessor.COMPILE_STATUS_NONE; - - - try { - processorStatus |= mAidlProcessor.compileFiles(this, - project, projectTarget, sourceFolderPathList, - libProjectsOut, monitor); - } catch (Throwable t) { - handleException(t, "Failed to run aidl. Check workspace log for detail."); - return result; - } - - try { - processorStatus |= compileRs(minSdkValue, projectState, androidOutputFolder, - resOutFolder, monitor); - } catch (Throwable t) { - handleException(t, "Failed to run renderscript. Check workspace log for detail."); - return result; - } - - // if a processor created some resources file, force recompilation of the resources. - if ((processorStatus & SourceProcessor.COMPILE_STATUS_RES) != 0) { - mMustCompileResources = true; - // save the current state before attempting the compilation - saveProjectBooleanProperty(PROPERTY_COMPILE_RESOURCES, mMustCompileResources); - } - - // handle the resources, after the processors are run since some (renderscript) - // generate resources. - boolean compiledTheResources = mMustCompileResources; - if (mMustCompileResources) { - if (DEBUG_LOG) { - AdtPlugin.log(IStatus.INFO, "%s compiling resources!", project.getName()); - } - - IFile proguardFile = null; - if (projectState.getProperty(ProjectProperties.PROPERTY_PROGUARD_CONFIG) != null) { - proguardFile = androidOutputFolder.getFile(AdtConstants.FN_AAPT_PROGUARD); - } - - handleResources(project, javaPackage, projectTarget, manifestFile, resOutFolder, - libProjects, isLibrary, proguardFile); - } - - if (processorStatus == SourceProcessor.COMPILE_STATUS_NONE && - compiledTheResources == false) { - AdtPlugin.printBuildToConsole(BuildVerbosity.VERBOSE, project, - Messages.Nothing_To_Compile); - } - } catch (AbortBuildException e) { - return result; - } finally { - // refresh the 'gen' source folder. Once this is done with the custom progress - // monitor to mark all new files as derived - mGenFolder.refreshLocal(IResource.DEPTH_INFINITE, mDerivedProgressMonitor); - if (resOutFolder != null) { - resOutFolder.refreshLocal(IResource.DEPTH_INFINITE, mDerivedProgressMonitor); - } - } - - return result; - } - - private IFolder getResOutFolder(IFolder androidOutputFolder) { - return androidOutputFolder.getFolder(AdtConstants.WS_BIN_RELATIVE_BC); - } - - @Override - protected void clean(IProgressMonitor monitor) throws CoreException { - super.clean(monitor); - - if (DEBUG_LOG) { - AdtPlugin.log(IStatus.INFO, "%s CLEAN(PRE)", getProject().getName()); - } - - doClean(getProject(), monitor); - if (mGenFolder != null) { - mGenFolder.refreshLocal(IResource.DEPTH_INFINITE, monitor); - } - } - - private void doClean(IProject project, IProgressMonitor monitor) throws CoreException { - AdtPlugin.printBuildToConsole(BuildVerbosity.VERBOSE, project, - Messages.Removing_Generated_Classes); - - // remove all the derived resources from the 'gen' source folder. - if (mGenFolder != null && mGenFolder.exists()) { - // gen folder should not be derived, but previous version could set it to derived - // so we make sure this isn't the case (or it'll get deleted by the clean) - mGenFolder.setDerived(false, monitor); - - removeDerivedResources(mGenFolder, monitor); - } - - // Clear the project of the generic markers - removeMarkersFromContainer(project, AdtConstants.MARKER_AAPT_COMPILE); - removeMarkersFromContainer(project, AdtConstants.MARKER_XML); - removeMarkersFromContainer(project, AdtConstants.MARKER_AIDL); - removeMarkersFromContainer(project, AdtConstants.MARKER_RENDERSCRIPT); - removeMarkersFromContainer(project, AdtConstants.MARKER_MANIFMERGER); - removeMarkersFromContainer(project, AdtConstants.MARKER_ANDROID); - - // Also clean up lint - EclipseLintClient.clearMarkers(project); - - // clean the project repo - ProjectResources res = ResourceManager.getInstance().getProjectResources(project); - res.clear(); - } - - @Override - protected void startupOnInitialize() { - try { - super.startupOnInitialize(); - - IProject project = getProject(); - - // load the previous IFolder and java package. - mManifestPackage = loadProjectStringProperty(PROPERTY_PACKAGE); - - // get the source folder in which all the Java files are created - mGenFolder = project.getFolder(SdkConstants.FD_GEN_SOURCES); - mDerivedProgressMonitor = new DerivedProgressMonitor(mGenFolder); - - // Load the current compile flags. We ask for true if not found to force a recompile. - mMustMergeManifest = loadProjectBooleanProperty(PROPERTY_MERGE_MANIFEST, true); - mMustCompileResources = loadProjectBooleanProperty(PROPERTY_COMPILE_RESOURCES, true); - mMustCreateBuildConfig = loadProjectBooleanProperty(PROPERTY_COMPILE_BUILDCONFIG, true); - Boolean v = ProjectHelper.loadBooleanProperty(project, PROPERTY_BUILDCONFIG_MODE); - if (v == null) { - // no previous build config mode? force regenerate - mMustCreateBuildConfig = true; - } else { - mLastBuildConfigMode = v; - } - - } catch (Throwable throwable) { - AdtPlugin.log(throwable, "Failed to finish PrecompilerBuilder#startupOnInitialize()"); - } - } - - private void setupSourceProcessors(@NonNull IJavaProject javaProject, - @NonNull ProjectState projectState, - @NonNull List<IPath> sourceFolderPathList, - @NonNull IFolder androidOutputFolder) { - if (mAidlProcessor == null) { - mAidlProcessor = new AidlProcessor(javaProject, mBuildToolInfo, mGenFolder); - } else { - mAidlProcessor.setBuildToolInfo(mBuildToolInfo); - } - - List<File> sourceFolders = Lists.newArrayListWithCapacity(sourceFolderPathList.size()); - IWorkspaceRoot root = ResourcesPlugin.getWorkspace().getRoot(); - - for (IPath path : sourceFolderPathList) { - IResource resource = root.findMember(path); - if (resource != null && resource.exists() && resource.getType() == IResource.FOLDER) { - IPath fullPath = resource.getLocation(); - if (fullPath != null) { - sourceFolders.add(fullPath.toFile()); - } - } - } - - RenderScriptChecker checker = new RenderScriptChecker(sourceFolders, - androidOutputFolder.getLocation().toFile()); - mRenderScriptSourceChangeHandler = new RsSourceChangeHandler(checker); - } - - private int compileRs(int minSdkValue, - @NonNull ProjectState projectState, - @NonNull IFolder androidOutputFolder, - @NonNull IFolder resOutFolder, - @NonNull IProgressMonitor monitor) - throws IOException, InterruptedException { - if (!mRenderScriptSourceChangeHandler.mustCompile()) { - return SourceProcessor.COMPILE_STATUS_NONE; - } - - RenderScriptChecker checker = mRenderScriptSourceChangeHandler.getChecker(); - - List<File> inputs = checker.findInputFiles(); - List<File> importFolders = checker.getSourceFolders(); - File buildFolder = androidOutputFolder.getLocation().toFile(); - - - // get the renderscript target - int rsTarget = minSdkValue == -1 ? 11 : minSdkValue; - String rsTargetStr = projectState.getProperty(ProjectProperties.PROPERTY_RS_TARGET); - if (rsTargetStr != null) { - try { - rsTarget = Integer.parseInt(rsTargetStr); - } catch (NumberFormatException e) { - handleException(e, String.format( - "Property %s is not an integer.", - ProjectProperties.PROPERTY_RS_TARGET)); - return SourceProcessor.COMPILE_STATUS_NONE; - } - } - - RenderScriptProcessor processor = new RenderScriptProcessor( - inputs, - importFolders, - buildFolder, - mGenFolder.getLocation().toFile(), - resOutFolder.getLocation().toFile(), - new File(buildFolder, SdkConstants.FD_RS_OBJ), - new File(buildFolder, SdkConstants.FD_RS_LIBS), - mBuildToolInfo, - rsTarget, - false /*debugBuild, always false for now*/, - 3, - projectState.getRenderScriptSupportMode()); - - // clean old dependency files fiest - checker.cleanDependencies(); - - // then clean old output files - processor.cleanOldOutput(checker.getOldOutputs()); - - RenderScriptLauncher launcher = new RenderScriptLauncher( - getProject(), - mGenFolder, - resOutFolder, - monitor, - AdtPrefs.getPrefs().getBuildVerbosity() == BuildVerbosity.VERBOSE /*verbose*/); - - // and run the build - processor.build(launcher); - - return SourceProcessor.COMPILE_STATUS_CODE | SourceProcessor.COMPILE_STATUS_RES; - } - - @SuppressWarnings("deprecation") - private void handleBuildConfig(@SuppressWarnings("rawtypes") Map args) - throws IOException, CoreException { - boolean debugMode = !args.containsKey(RELEASE_REQUESTED); - - BuildConfigGenerator generator = new BuildConfigGenerator( - mGenFolder.getLocation().toOSString(), mManifestPackage, debugMode); - - if (mMustCreateBuildConfig == false) { - // check the file is present. - IFolder folder = getGenManifestPackageFolder(); - if (folder.exists(new Path(BuildConfigGenerator.BUILD_CONFIG_NAME)) == false) { - mMustCreateBuildConfig = true; - AdtPlugin.printBuildToConsole(BuildVerbosity.VERBOSE, getProject(), - String.format("Class %1$s is missing!", - BuildConfigGenerator.BUILD_CONFIG_NAME)); - } else if (debugMode != mLastBuildConfigMode) { - // else if the build mode changed, force creation - mMustCreateBuildConfig = true; - AdtPlugin.printBuildToConsole(BuildVerbosity.VERBOSE, getProject(), - String.format("Different build mode, must update %1$s!", - BuildConfigGenerator.BUILD_CONFIG_NAME)); - } - } - - if (mMustCreateBuildConfig) { - if (DEBUG_LOG) { - AdtPlugin.log(IStatus.INFO, "%s generating BuilderConfig!", getProject().getName()); - } - - AdtPlugin.printBuildToConsole(BuildVerbosity.VERBOSE, getProject(), - String.format("Generating %1$s...", BuildConfigGenerator.BUILD_CONFIG_NAME)); - generator.generate(); - - mMustCreateBuildConfig = false; - saveProjectBooleanProperty(PROPERTY_COMPILE_BUILDCONFIG, mMustCreateBuildConfig); - saveProjectBooleanProperty(PROPERTY_BUILDCONFIG_MODE, mLastBuildConfigMode = debugMode); - } - } - - private boolean mergeManifest(IFolder androidOutFolder, List<IProject> libProjects, - boolean enabled) throws CoreException { - if (DEBUG_LOG) { - AdtPlugin.log(IStatus.INFO, "%s merging manifests!", getProject().getName()); - } - - IFile outFile = androidOutFolder.getFile(SdkConstants.FN_ANDROID_MANIFEST_XML); - IFile manifest = getProject().getFile(SdkConstants.FN_ANDROID_MANIFEST_XML); - - // remove existing markers from the manifest. - // FIXME: only remove from manifest once the markers are put there. - removeMarkersFromResource(getProject(), AdtConstants.MARKER_MANIFMERGER); - - // If the merging is not enabled or if there's no library then we simply copy the - // manifest over. - if (enabled == false || libProjects.size() == 0) { - try { - new FileOp().copyFile(manifest.getLocation().toFile(), - outFile.getLocation().toFile()); - - outFile.refreshLocal(IResource.DEPTH_INFINITE, mDerivedProgressMonitor); - - saveProjectBooleanProperty(PROPERTY_MERGE_MANIFEST, mMustMergeManifest = false); - } catch (IOException e) { - handleException(e, "Failed to copy Manifest"); - return false; - } - } else { - final ArrayList<String> errors = new ArrayList<String>(); - - // TODO change MergerLog.wrapSdkLog by a custom IMergerLog that will create - // and maintain error markers. - ManifestMerger merger = new ManifestMerger( - MergerLog.wrapSdkLog(new ILogger() { - @Override - public void warning(@NonNull String warningFormat, Object... args) { - AdtPlugin.printToConsole(getProject(), String.format(warningFormat, args)); - } - - @Override - public void info(@NonNull String msgFormat, Object... args) { - AdtPlugin.printToConsole(getProject(), String.format(msgFormat, args)); - } - - @Override - public void verbose(@NonNull String msgFormat, Object... args) { - info(msgFormat, args); - } - - @Override - public void error(@Nullable Throwable t, @Nullable String errorFormat, - Object... args) { - errors.add(String.format(errorFormat, args)); - } - }), - new AdtManifestMergeCallback()); - - File[] libManifests = new File[libProjects.size()]; - int libIndex = 0; - for (IProject lib : libProjects) { - libManifests[libIndex++] = lib.getFile(SdkConstants.FN_ANDROID_MANIFEST_XML) - .getLocation().toFile(); - } - - if (merger.process( - outFile.getLocation().toFile(), - manifest.getLocation().toFile(), - libManifests, - null /*injectAttributes*/, null /*packageOverride*/) == false) { - if (errors.size() > 1) { - StringBuilder sb = new StringBuilder(); - for (String s : errors) { - sb.append(s).append('\n'); - } - - markProject(AdtConstants.MARKER_MANIFMERGER, sb.toString(), - IMarker.SEVERITY_ERROR); - - } else if (errors.size() == 1) { - markProject(AdtConstants.MARKER_MANIFMERGER, errors.get(0), - IMarker.SEVERITY_ERROR); - } else { - markProject(AdtConstants.MARKER_MANIFMERGER, "Unknown error merging manifest", - IMarker.SEVERITY_ERROR); - } - return false; - } - - outFile.refreshLocal(IResource.DEPTH_INFINITE, mDerivedProgressMonitor); - saveProjectBooleanProperty(PROPERTY_MERGE_MANIFEST, mMustMergeManifest = false); - } - - return true; - } - - /** - * Handles resource changes and regenerate whatever files need regenerating. - * @param project the main project - * @param javaPackage the app package for the main project - * @param projectTarget the target of the main project - * @param manifest the {@link IFile} representing the project manifest - * @param libProjects the library dependencies - * @param isLibrary if the project is a library project - * @throws CoreException - * @throws AbortBuildException - */ - private void handleResources(IProject project, String javaPackage, IAndroidTarget projectTarget, - IFile manifest, IFolder resOutFolder, List<IProject> libProjects, boolean isLibrary, - IFile proguardFile) throws CoreException, AbortBuildException { - // get the resource folder - IFolder resFolder = project.getFolder(AdtConstants.WS_RESOURCES); - - // get the file system path - IPath outputLocation = mGenFolder.getLocation(); - IPath resLocation = resFolder.getLocation(); - IPath manifestLocation = manifest == null ? null : manifest.getLocation(); - - // those locations have to exist for us to do something! - if (outputLocation != null && resLocation != null - && manifestLocation != null) { - String osOutputPath = outputLocation.toOSString(); - String osResPath = resLocation.toOSString(); - String osManifestPath = manifestLocation.toOSString(); - - // remove the aapt markers - removeMarkersFromResource(manifest, AdtConstants.MARKER_AAPT_COMPILE); - removeMarkersFromContainer(resFolder, AdtConstants.MARKER_AAPT_COMPILE); - - AdtPlugin.printBuildToConsole(BuildVerbosity.VERBOSE, project, - Messages.Preparing_Generated_Files); - - // we need to figure out where to store the R class. - // get the parent folder for R.java and update mManifestPackageSourceFolder - IFolder mainPackageFolder = getGenManifestPackageFolder(); - - // handle libraries - ArrayList<IFolder> libResFolders = Lists.newArrayList(); - ArrayList<Pair<File, String>> libRFiles = Lists.newArrayList(); - if (libProjects != null) { - for (IProject lib : libProjects) { - IFolder libResFolder = lib.getFolder(SdkConstants.FD_RES); - if (libResFolder.exists()) { - libResFolders.add(libResFolder); - } - - try { - // get the package of the library, and if it's different form the - // main project, generate the R class for it too. - String libJavaPackage = AndroidManifest.getPackage(new IFolderWrapper(lib)); - if (libJavaPackage.equals(javaPackage) == false) { - - IFolder libOutput = BaseProjectHelper.getAndroidOutputFolder(lib); - File libOutputFolder = libOutput.getLocation().toFile(); - - libRFiles.add(Pair.of( - new File(libOutputFolder, "R.txt"), - libJavaPackage)); - - } - } catch (Exception e) { - } - } - } - - String proguardFilePath = proguardFile != null ? - proguardFile.getLocation().toOSString(): null; - - File resOutFile = resOutFolder.getLocation().toFile(); - String resOutPath = resOutFile.isDirectory() ? resOutFile.getAbsolutePath() : null; - - execAapt(project, projectTarget, osOutputPath, resOutPath, osResPath, osManifestPath, - mainPackageFolder, libResFolders, libRFiles, isLibrary, proguardFilePath); - } - } - - /** - * Executes AAPT to generate R.java/Manifest.java - * @param project the main project - * @param projectTarget the main project target - * @param osOutputPath the OS output path for the generated file. This is the source folder, not - * the package folder. - * @param osResPath the OS path to the res folder for the main project - * @param osManifestPath the OS path to the manifest of the main project - * @param packageFolder the IFolder that will contain the generated file. Unlike - * <var>osOutputPath</var> this is the direct parent of the generated files. - * If <var>customJavaPackage</var> is not null, this must match the new destination triggered - * by its value. - * @param libResFolders the list of res folders for the library. - * @param libRFiles a list of R files for the libraries. - * @param isLibrary if the project is a library project - * @param proguardFile an optional path to store proguard information - * @throws AbortBuildException - */ - @SuppressWarnings("deprecation") - private void execAapt(IProject project, IAndroidTarget projectTarget, String osOutputPath, - String osBcOutPath, String osResPath, String osManifestPath, IFolder packageFolder, - ArrayList<IFolder> libResFolders, List<Pair<File, String>> libRFiles, - boolean isLibrary, String proguardFile) - throws AbortBuildException { - - // We actually need to delete the manifest.java as it may become empty and - // in this case aapt doesn't generate an empty one, but instead doesn't - // touch it. - IFile manifestJavaFile = packageFolder.getFile(SdkConstants.FN_MANIFEST_CLASS); - manifestJavaFile.getLocation().toFile().delete(); - - // launch aapt: create the command line - ArrayList<String> array = new ArrayList<String>(); - - String aaptPath = mBuildToolInfo.getPath(BuildToolInfo.PathId.AAPT); - - array.add(aaptPath); - array.add("package"); //$NON-NLS-1$ - array.add("-m"); //$NON-NLS-1$ - if (AdtPrefs.getPrefs().getBuildVerbosity() == BuildVerbosity.VERBOSE) { - array.add("-v"); //$NON-NLS-1$ - } - - if (isLibrary) { - array.add("--non-constant-id"); //$NON-NLS-1$ - } - - if (libResFolders.size() > 0) { - array.add("--auto-add-overlay"); //$NON-NLS-1$ - } - - // If a library or has libraries, generate a text version of the R symbols. - File outputFolder = BaseProjectHelper.getAndroidOutputFolder(project).getLocation() - .toFile(); - - if (isLibrary || !libRFiles.isEmpty()) { - array.add("--output-text-symbols"); //$NON-NLS-1$ - array.add(outputFolder.getAbsolutePath()); - } - - array.add("-J"); //$NON-NLS-1$ - array.add(osOutputPath); - array.add("-M"); //$NON-NLS-1$ - array.add(osManifestPath); - if (osBcOutPath != null) { - array.add("-S"); //$NON-NLS-1$ - array.add(osBcOutPath); - } - array.add("-S"); //$NON-NLS-1$ - array.add(osResPath); - for (IFolder libResFolder : libResFolders) { - array.add("-S"); //$NON-NLS-1$ - array.add(libResFolder.getLocation().toOSString()); - } - - array.add("-I"); //$NON-NLS-1$ - array.add(projectTarget.getPath(IAndroidTarget.ANDROID_JAR)); - - // use the proguard file - if (proguardFile != null && proguardFile.length() > 0) { - array.add("-G"); - array.add(proguardFile); - } - - if (AdtPrefs.getPrefs().getBuildVerbosity() == BuildVerbosity.VERBOSE) { - StringBuilder sb = new StringBuilder(); - for (String c : array) { - sb.append(c); - sb.append(' '); - } - String cmd_line = sb.toString(); - AdtPlugin.printToConsole(project, cmd_line); - } - - // launch - try { - // launch the command line process - Process process = Runtime.getRuntime().exec( - array.toArray(new String[array.size()])); - - // list to store each line of stderr - ArrayList<String> stdErr = new ArrayList<String>(); - - // get the output and return code from the process - int returnCode = grabProcessOutput(process, stdErr); - - // attempt to parse the error output - boolean parsingError = AaptParser.parseOutput(stdErr, project); - - // if we couldn't parse the output we display it in the console. - if (parsingError) { - if (returnCode != 0) { - AdtPlugin.printErrorToConsole(project, stdErr.toArray()); - } else { - AdtPlugin.printBuildToConsole(BuildVerbosity.NORMAL, - project, stdErr.toArray()); - } - } - - if (returnCode != 0) { - // if the exec failed, and we couldn't parse the error output - // (and therefore not all files that should have been marked, - // were marked), we put a generic marker on the project and abort. - if (parsingError) { - markProject(AdtConstants.MARKER_ADT, - Messages.Unparsed_AAPT_Errors, IMarker.SEVERITY_ERROR); - } else if (stdErr.size() == 0) { - // no parsing error because sdterr was empty. We still need to put - // a marker otherwise there's no user visible feedback. - markProject(AdtConstants.MARKER_ADT, - String.format(Messages.AAPT_Exec_Error_d, returnCode), - IMarker.SEVERITY_ERROR); - } - - AdtPlugin.printBuildToConsole(BuildVerbosity.VERBOSE, project, - Messages.AAPT_Error); - - // abort if exec failed. - throw new AbortBuildException(); - } - - // now if the project has libraries, R needs to be created for each libraries - // unless this is a library. - if (isLibrary == false && !libRFiles.isEmpty()) { - File rFile = new File(outputFolder, SdkConstants.FN_RESOURCE_TEXT); - // if the project has no resources, the file could not exist. - if (rFile.isFile()) { - // Load the full symbols from the full R.txt file. - SymbolLoader fullSymbolValues = new SymbolLoader(rFile); - fullSymbolValues.load(); - - Multimap<String, SymbolLoader> libMap = ArrayListMultimap.create(); - - // First pass processing the libraries, collecting them by packageName, - // and ignoring the ones that have the same package name as the application - // (since that R class was already created). - - for (Pair<File, String> lib : libRFiles) { - String libPackage = lib.getSecond(); - File rText = lib.getFirst(); - - if (rText.isFile()) { - // load the lib symbols - SymbolLoader libSymbols = new SymbolLoader(rText); - libSymbols.load(); - - // store these symbols by associating them with the package name. - libMap.put(libPackage, libSymbols); - } - } - - // now loop on all the package names, merge all the symbols to write, - // and write them - for (String packageName : libMap.keySet()) { - Collection<SymbolLoader> symbols = libMap.get(packageName); - - SymbolWriter writer = new SymbolWriter(osOutputPath, packageName, - fullSymbolValues); - for (SymbolLoader symbolLoader : symbols) { - writer.addSymbolsToWrite(symbolLoader); - } - writer.write(); - } - } - } - - } catch (IOException e1) { - // something happen while executing the process, - // mark the project and exit - String msg; - String path = array.get(0); - if (!new File(path).exists()) { - msg = String.format(Messages.AAPT_Exec_Error_s, path); - } else { - String description = e1.getLocalizedMessage(); - if (e1.getCause() != null && e1.getCause() != e1) { - description = description + ": " + e1.getCause().getLocalizedMessage(); - } - msg = String.format(Messages.AAPT_Exec_Error_Other_s, description); - } - - markProject(AdtConstants.MARKER_ADT, msg, IMarker.SEVERITY_ERROR); - - // Add workaround for the Linux problem described here: - // http://developer.android.com/sdk/installing.html#troubleshooting - // There are various posts on StackOverflow elsewhere where people are asking - // about aapt failing to run, so even though this is documented in the - // Troubleshooting section add an error message to help with this - // scenario. - if (SdkConstants.CURRENT_PLATFORM == SdkConstants.PLATFORM_LINUX - && System.getProperty("os.arch").endsWith("64") //$NON-NLS-1$ //$NON-NLS-2$ - && new File(aaptPath).exists() - && new File("/usr/bin/apt-get").exists()) { //$NON-NLS-1$ - markProject(AdtConstants.MARKER_ADT, - "Hint: On 64-bit systems, make sure the 32-bit libraries are installed: \"sudo apt-get install ia32-libs\" or on some systems, \"sudo apt-get install lib32z1\"", - IMarker.SEVERITY_ERROR); - // Note - this uses SEVERITY_ERROR even though it's really SEVERITY_INFO because - // we want this error message to show up adjacent to the aapt error message - // (and Eclipse sorts by priority) - } - - // This interrupts the build. - throw new AbortBuildException(); - } catch (InterruptedException e) { - // we got interrupted waiting for the process to end... - // mark the project and exit - String msg = String.format(Messages.AAPT_Exec_Error_s, array.get(0)); - markProject(AdtConstants.MARKER_ADT, msg, IMarker.SEVERITY_ERROR); - - // This interrupts the build. - throw new AbortBuildException(); - } finally { - // we've at least attempted to run aapt, save the fact that we don't have to - // run it again, unless there's a new resource change. - saveProjectBooleanProperty(PROPERTY_COMPILE_RESOURCES, - mMustCompileResources = false); - ResourceManager.clearAaptRequest(project); - } - } - - /** - * Creates a relative {@link IPath} from a java package. - * @param javaPackageName the java package. - */ - private IPath getJavaPackagePath(String javaPackageName) { - // convert the java package into path - String[] segments = javaPackageName.split(AdtConstants.RE_DOT); - - StringBuilder path = new StringBuilder(); - for (String s : segments) { - path.append(AdtConstants.WS_SEP_CHAR); - path.append(s); - } - - return new Path(path.toString()); - } - - /** - * Returns an {@link IFolder} (located inside the 'gen' source folder), that matches the - * package defined in the manifest. This {@link IFolder} may not actually exist - * (aapt will create it anyway). - * @return the {@link IFolder} that will contain the R class or null if - * the folder was not found. - * @throws CoreException - */ - private IFolder getGenManifestPackageFolder() throws CoreException { - // get the path for the package - IPath packagePath = getJavaPackagePath(mManifestPackage); - - // get a folder for this path under the 'gen' source folder, and return it. - // This IFolder may not reference an actual existing folder. - return mGenFolder.getFolder(packagePath); - } -} |