diff options
author | Raphael Moll <ralf@android.com> | 2013-01-15 19:53:50 -0800 |
---|---|---|
committer | Raphael Moll <ralf@android.com> | 2013-01-16 11:10:06 -0800 |
commit | fd30096196e3747986bdf8a95cc7713dd6e0b239 (patch) | |
tree | 93fa4530e6a759f7c5e6b9630015f4011e644d74 /sdkmanager/libs | |
parent | 20d8d91c41d05b1f5e73a04a2992448a12b82f7b (diff) | |
download | sdk-fd30096196e3747986bdf8a95cc7713dd6e0b239.zip sdk-fd30096196e3747986bdf8a95cc7713dd6e0b239.tar.gz sdk-fd30096196e3747986bdf8a95cc7713dd6e0b239.tar.bz2 |
SDK: use prebuilts/devtools for sdklib
Change-Id: I55c69a46fb7fa21701025f2df4e4fcc3bfd3ef96
Diffstat (limited to 'sdkmanager/libs')
205 files changed, 11 insertions, 52617 deletions
diff --git a/sdkmanager/libs/sdklib/Android.mk b/sdkmanager/libs/sdklib/Android.mk index e5e1a27..dfd3fcb 100644 --- a/sdkmanager/libs/sdklib/Android.mk +++ b/sdkmanager/libs/sdklib/Android.mk @@ -12,15 +12,18 @@ # 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. -# + LOCAL_PATH := $(call my-dir) include $(CLEAR_VARS) -LOCAL_SRC_FILES := $(call all-java-files-under, src/main/java) -LOCAL_JAVA_RESOURCE_DIRS := src/main/java - -LOCAL_JAR_MANIFEST := manifest.txt +# The sdklib code has moved to tools/base/sdklib. +# The rule below uses the prebuilt sdklib.jar if found. +# +# If you want to run the tests, cd to tools/base +# and run ./gradlew :sdklib:test +LOCAL_MODULE := sdklib +LOCAL_MODULE_TAGS := optional # IMPORTANT: if you add a new dependency here, please make sure # to also check the following files: # sdkmanager/sdklib/manifest.txt @@ -38,21 +41,8 @@ LOCAL_JAVA_LIBRARIES := \ mkidentity-prebuilt \ layoutlib_api -LOCAL_MODULE := sdklib - -include $(BUILD_HOST_JAVA_LIBRARY) - - -# Build tests -include $(CLEAR_VARS) - -# Only compile source java files in this lib. -LOCAL_SRC_FILES := $(call all-java-files-under, src/test/java) -LOCAL_JAVA_RESOURCE_DIRS := src/test/java - -LOCAL_MODULE := sdklib-tests -LOCAL_MODULE_TAGS := optional +LOCAL_PREBUILT_JAVA_LIBRARIES := \ + ../../../../prebuilts/devtools/$(LOCAL_MODULE)/$(LOCAL_MODULE)$(COMMON_JAVA_PACKAGE_SUFFIX) -LOCAL_JAVA_LIBRARIES := sdklib junit dvlib-tests +include $(BUILD_HOST_PREBUILT) -include $(BUILD_HOST_JAVA_LIBRARY) diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/AddOnTarget.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/AddOnTarget.java deleted file mode 100644 index 12d4a49..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/AddOnTarget.java +++ /dev/null @@ -1,462 +0,0 @@ -/* - * Copyright (C) 2008 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib; - -import com.android.SdkConstants; - -import java.io.File; -import java.io.FileFilter; -import java.util.Arrays; -import java.util.HashSet; -import java.util.Map; -import java.util.Map.Entry; - -/** - * Represents an add-on target in the SDK. - * An add-on extends a standard {@link PlatformTarget}. - */ -final class AddOnTarget implements IAndroidTarget { - /** - * String to compute hash for add-on targets. - * Format is vendor:name:apiVersion - * */ - private final static String ADD_ON_FORMAT = "%s:%s:%s"; //$NON-NLS-1$ - - private final static class OptionalLibrary implements IOptionalLibrary { - private final String mJarName; - private final String mJarPath; - private final String mName; - private final String mDescription; - - OptionalLibrary(String jarName, String jarPath, String name, String description) { - mJarName = jarName; - mJarPath = jarPath; - mName = name; - mDescription = description; - } - - @Override - public String getJarName() { - return mJarName; - } - - @Override - public String getJarPath() { - return mJarPath; - } - - @Override - public String getName() { - return mName; - } - - @Override - public String getDescription() { - return mDescription; - } - } - - private final String mLocation; - private final PlatformTarget mBasePlatform; - private final String mName; - private final ISystemImage[] mSystemImages; - private final String mVendor; - private final int mRevision; - private final String mDescription; - private final boolean mHasRenderingLibrary; - private final boolean mHasRenderingResources; - - private String[] mSkins; - private String mDefaultSkin; - private IOptionalLibrary[] mLibraries; - private int mVendorId = NO_USB_ID; - - /** - * Creates a new add-on - * @param location the OS path location of the add-on - * @param name the name of the add-on - * @param vendor the vendor name of the add-on - * @param revision the revision of the add-on - * @param description the add-on description - * @param systemImages list of supported system images. Can be null or empty. - * @param libMap A map containing the optional libraries. The map key is the fully-qualified - * library name. The value is a 2 string array with the .jar filename, and the description. - * @param hasRenderingLibrary whether the addon has a custom layoutlib.jar - * @param hasRenderingResources whether the add has custom framework resources. - * @param basePlatform the platform the add-on is extending. - */ - AddOnTarget( - String location, - String name, - String vendor, - int revision, - String description, - ISystemImage[] systemImages, - Map<String, String[]> libMap, - boolean hasRenderingLibrary, - boolean hasRenderingResources, - PlatformTarget basePlatform) { - if (location.endsWith(File.separator) == false) { - location = location + File.separator; - } - - mLocation = location; - mName = name; - mVendor = vendor; - mRevision = revision; - mDescription = description; - mHasRenderingLibrary = hasRenderingLibrary; - mHasRenderingResources = hasRenderingResources; - mBasePlatform = basePlatform; - - // If the add-on does not have any system-image of its own, the list here - // is empty and it's up to the callers to query the parent platform. - mSystemImages = systemImages == null ? new ISystemImage[0] : systemImages; - Arrays.sort(mSystemImages); - - // handle the optional libraries. - if (libMap != null) { - mLibraries = new IOptionalLibrary[libMap.size()]; - int index = 0; - for (Entry<String, String[]> entry : libMap.entrySet()) { - String jarFile = entry.getValue()[0]; - String desc = entry.getValue()[1]; - mLibraries[index++] = new OptionalLibrary(jarFile, - mLocation + SdkConstants.OS_ADDON_LIBS_FOLDER + jarFile, - entry.getKey(), desc); - } - } - } - - @Override - public String getLocation() { - return mLocation; - } - - @Override - public String getName() { - return mName; - } - - @Override - public ISystemImage getSystemImage(String abiType) { - for (ISystemImage sysImg : mSystemImages) { - if (sysImg.getAbiType().equals(abiType)) { - return sysImg; - } - } - return null; - } - - @Override - public ISystemImage[] getSystemImages() { - return mSystemImages; - } - - @Override - public String getVendor() { - return mVendor; - } - - @Override - public String getFullName() { - return String.format("%1$s (%2$s)", mName, mVendor); - } - - @Override - public String getClasspathName() { - return String.format("%1$s [%2$s]", mName, mBasePlatform.getClasspathName()); - } - - @Override - public String getShortClasspathName() { - return String.format("%1$s [%2$s]", mName, mBasePlatform.getVersionName()); - } - - @Override - public String getDescription() { - return mDescription; - } - - @Override - public AndroidVersion getVersion() { - // this is always defined by the base platform - return mBasePlatform.getVersion(); - } - - @Override - public String getVersionName() { - return mBasePlatform.getVersionName(); - } - - @Override - public int getRevision() { - return mRevision; - } - - @Override - public boolean isPlatform() { - return false; - } - - @Override - public IAndroidTarget getParent() { - return mBasePlatform; - } - - @Override - public String getPath(int pathId) { - switch (pathId) { - case SKINS: - return mLocation + SdkConstants.OS_SKINS_FOLDER; - case DOCS: - return mLocation + SdkConstants.FD_DOCS + File.separator - + SdkConstants.FD_DOCS_REFERENCE; - - case LAYOUT_LIB: - if (mHasRenderingLibrary) { - return mLocation + SdkConstants.FD_DATA + File.separator - + SdkConstants.FN_LAYOUTLIB_JAR; - } - return mBasePlatform.getPath(pathId); - - case RESOURCES: - if (mHasRenderingResources) { - return mLocation + SdkConstants.FD_DATA + File.separator - + SdkConstants.FD_RES; - } - return mBasePlatform.getPath(pathId); - - case FONTS: - if (mHasRenderingResources) { - return mLocation + SdkConstants.FD_DATA + File.separator - + SdkConstants.FD_FONTS; - } - return mBasePlatform.getPath(pathId); - - case SAMPLES: - // only return the add-on samples folder if there is actually a sample (or more) - File sampleLoc = new File(mLocation, SdkConstants.FD_SAMPLES); - if (sampleLoc.isDirectory()) { - File[] files = sampleLoc.listFiles(new FileFilter() { - @Override - public boolean accept(File pathname) { - return pathname.isDirectory(); - } - - }); - if (files != null && files.length > 0) { - return sampleLoc.getAbsolutePath(); - } - } - //$FALL-THROUGH$ - default : - return mBasePlatform.getPath(pathId); - } - } - - @Override - public boolean hasRenderingLibrary() { - return mHasRenderingLibrary || mHasRenderingResources; - } - - @Override - public String[] getSkins() { - return mSkins; - } - - @Override - public String getDefaultSkin() { - return mDefaultSkin; - } - - @Override - public IOptionalLibrary[] getOptionalLibraries() { - return mLibraries; - } - - /** - * Returns the list of libraries of the underlying platform. - * - * {@inheritDoc} - */ - @Override - public String[] getPlatformLibraries() { - return mBasePlatform.getPlatformLibraries(); - } - - @Override - public String getProperty(String name) { - return mBasePlatform.getProperty(name); - } - - @Override - public Integer getProperty(String name, Integer defaultValue) { - return mBasePlatform.getProperty(name, defaultValue); - } - - @Override - public Boolean getProperty(String name, Boolean defaultValue) { - return mBasePlatform.getProperty(name, defaultValue); - } - - @Override - public Map<String, String> getProperties() { - return mBasePlatform.getProperties(); - } - - @Override - public int getUsbVendorId() { - return mVendorId; - } - - @Override - public boolean canRunOn(IAndroidTarget target) { - // basic test - if (target == this) { - return true; - } - - /* - * The method javadoc indicates: - * Returns whether the given target is compatible with the receiver. - * <p/>A target is considered compatible if applications developed for the receiver can - * run on the given target. - */ - - // The receiver is an add-on. There are 2 big use cases: The add-on has libraries - // or the add-on doesn't (in which case we consider it a platform). - if (mLibraries == null || mLibraries.length == 0) { - return mBasePlatform.canRunOn(target); - } else { - // the only targets that can run the receiver are the same add-on in the same or later - // versions. - // first check: vendor/name - if (mVendor.equals(target.getVendor()) == false || - mName.equals(target.getName()) == false) { - return false; - } - - // now check the version. At this point since we checked the add-on part, - // we can revert to the basic check on version/codename which are done by the - // base platform already. - return mBasePlatform.canRunOn(target); - } - - } - - @Override - public String hashString() { - return String.format(ADD_ON_FORMAT, mVendor, mName, - mBasePlatform.getVersion().getApiString()); - } - - @Override - public int hashCode() { - return hashString().hashCode(); - } - - @Override - public boolean equals(Object obj) { - if (obj instanceof AddOnTarget) { - AddOnTarget addon = (AddOnTarget)obj; - - return mVendor.equals(addon.mVendor) && mName.equals(addon.mName) && - mBasePlatform.getVersion().equals(addon.mBasePlatform.getVersion()); - } - - return false; - } - - /* - * Order by API level (preview/n count as between n and n+1). - * At the same API level, order as: Platform first, then add-on ordered by vendor and then name - * (non-Javadoc) - * @see java.lang.Comparable#compareTo(java.lang.Object) - */ - @Override - public int compareTo(IAndroidTarget target) { - // quick check. - if (this == target) { - return 0; - } - - int versionDiff = getVersion().compareTo(target.getVersion()); - - // only if the version are the same do we care about platform/add-ons. - if (versionDiff == 0) { - // platforms go before add-ons. - if (target.isPlatform()) { - return +1; - } else { - AddOnTarget targetAddOn = (AddOnTarget)target; - - // both are add-ons of the same version. Compare per vendor then by name - int vendorDiff = mVendor.compareTo(targetAddOn.mVendor); - if (vendorDiff == 0) { - return mName.compareTo(targetAddOn.mName); - } else { - return vendorDiff; - } - } - - } - - return versionDiff; - } - - /** - * Returns a string representation suitable for debugging. - * The representation is not intended for display to the user. - * - * The representation is also purposely compact. It does not describe _all_ the properties - * of the target, only a few key ones. - * - * @see #getDescription() - */ - @Override - public String toString() { - return String.format("AddonTarget %1$s rev %2$d (based on %3$s)", //$NON-NLS-1$ - getVersion(), - getRevision(), - getParent().toString()); - } - - // ---- local methods. - - void setSkins(String[] skins, String defaultSkin) { - mDefaultSkin = defaultSkin; - - // we mix the add-on and base platform skins - HashSet<String> skinSet = new HashSet<String>(); - skinSet.addAll(Arrays.asList(skins)); - skinSet.addAll(Arrays.asList(mBasePlatform.getSkins())); - - mSkins = skinSet.toArray(new String[skinSet.size()]); - } - - /** - * Sets the USB vendor id in the add-on. - */ - void setUsbVendorId(int vendorId) { - if (vendorId == 0) { - throw new IllegalArgumentException( "VendorId must be > 0"); - } - - mVendorId = vendorId; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/AndroidVersion.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/AndroidVersion.java deleted file mode 100644 index 44ffa63..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/AndroidVersion.java +++ /dev/null @@ -1,326 +0,0 @@ -/* - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib; - -import com.android.SdkConstants; -import com.android.annotations.Nullable; -import com.android.sdklib.repository.PkgProps; - -import java.util.Properties; - -/** - * Represents the version of a target or device. - * <p/> - * A version is defined by an API level and an optional code name. - * <ul><li>Release versions of the Android platform are identified by their API level (integer), - * (technically the code name for release version is "REL" but this class will return - * <code>null<code> instead.)</li> - * <li>Preview versions of the platform are identified by a code name. Their API level - * is usually set to the value of the previous platform.</li></ul> - * <p/> - * While this class contains both values, its goal is to abstract them, so that code comparing 2+ - * versions doesn't have to deal with the logic of handle both values. - * <p/> - * There are some cases where ones may want to access the values directly. This can be done - * with {@link #getApiLevel()} and {@link #getCodename()}. - * <p/> - * For generic UI display of the API version, {@link #getApiString()} is to be used. - */ -public final class AndroidVersion implements Comparable<AndroidVersion> { - - private final int mApiLevel; - private final String mCodename; - - /** - * Thrown when an {@link AndroidVersion} object could not be created. - * @see AndroidVersion#AndroidVersion(Properties) - */ - public final static class AndroidVersionException extends Exception { - private static final long serialVersionUID = 1L; - - AndroidVersionException(String message, Throwable cause) { - super(message, cause); - } - } - - /** - * Creates an {@link AndroidVersion} with the given api level and codename. - * Codename should be null for a release version, otherwise it's a preview codename. - */ - public AndroidVersion(int apiLevel, String codename) { - mApiLevel = apiLevel; - mCodename = sanitizeCodename(codename); - } - - /** - * Creates an {@link AndroidVersion} from {@link Properties}, with default values if the - * {@link Properties} object doesn't contain the expected values. - * <p/>The {@link Properties} is expected to have been filled with - * {@link #saveProperties(Properties)}. - */ - public AndroidVersion(Properties properties, int defaultApiLevel, String defaultCodeName) { - if (properties == null) { - mApiLevel = defaultApiLevel; - mCodename = sanitizeCodename(defaultCodeName); - } else { - mApiLevel = Integer.parseInt(properties.getProperty(PkgProps.VERSION_API_LEVEL, - Integer.toString(defaultApiLevel))); - mCodename = sanitizeCodename( - properties.getProperty(PkgProps.VERSION_CODENAME, defaultCodeName)); - } - } - - /** - * Creates an {@link AndroidVersion} from {@link Properties}. The properties must contain - * android version information, or an exception will be thrown. - * @throws AndroidVersionException if no Android version information have been found - * - * @see #saveProperties(Properties) - */ - public AndroidVersion(Properties properties) throws AndroidVersionException { - Exception error = null; - - String apiLevel = properties.getProperty(PkgProps.VERSION_API_LEVEL, null/*defaultValue*/); - if (apiLevel != null) { - try { - mApiLevel = Integer.parseInt(apiLevel); - mCodename = sanitizeCodename(properties.getProperty(PkgProps.VERSION_CODENAME, - null/*defaultValue*/)); - return; - } catch (NumberFormatException e) { - error = e; - } - } - - // reaching here means the Properties object did not contain the apiLevel which is required. - throw new AndroidVersionException(PkgProps.VERSION_API_LEVEL + " not found!", error); - } - - public void saveProperties(Properties props) { - props.setProperty(PkgProps.VERSION_API_LEVEL, Integer.toString(mApiLevel)); - if (mCodename != null) { - props.setProperty(PkgProps.VERSION_CODENAME, mCodename); - } - } - - /** - * Returns the api level as an integer. - * <p/>For target that are in preview mode, this can be superseded by - * {@link #getCodename()}. - * <p/>To display the API level in the UI, use {@link #getApiString()}, which will use the - * codename if applicable. - * @see #getCodename() - * @see #getApiString() - */ - public int getApiLevel() { - return mApiLevel; - } - - /** - * Returns the version code name if applicable, null otherwise. - * <p/>If the codename is non null, then the API level should be ignored, and this should be - * used as a unique identifier of the target instead. - */ - public String getCodename() { - return mCodename; - } - - /** - * Returns a string representing the API level and/or the code name. - */ - public String getApiString() { - if (mCodename != null) { - return mCodename; - } - - return Integer.toString(mApiLevel); - } - - /** - * Returns whether or not the version is a preview version. - */ - public boolean isPreview() { - return mCodename != null; - } - - /** - * Checks whether a device running a version similar to the receiver can run a project compiled - * for the given <var>version</var>. - * <p/> - * Be aware that this is not a perfect test, as other properties could break compatibility - * despite this method returning true. For a more comprehensive test, see - * {@link IAndroidTarget#canRunOn(IAndroidTarget)}. - * <p/> - * Nevertheless, when testing if an application can run on a device (where there is no - * access to the list of optional libraries), this method can give a good indication of whether - * there is a chance the application could run, or if there's a direct incompatibility. - */ - public boolean canRun(AndroidVersion appVersion) { - // if the application is compiled for a preview version, the device must be running exactly - // the same. - if (appVersion.mCodename != null) { - return appVersion.mCodename.equals(mCodename); - } - - // otherwise, we check the api level (note that a device running a preview version - // will have the api level of the previous platform). - return mApiLevel >= appVersion.mApiLevel; - } - - /** - * Returns <code>true</code> if the AndroidVersion is an API level equals to - * <var>apiLevel</var>. - */ - public boolean equals(int apiLevel) { - return mCodename == null && apiLevel == mApiLevel; - } - - /** - * Compares the receiver with either an {@link AndroidVersion} object or a {@link String} - * object. - * <p/>If <var>obj</var> is a {@link String}, then the method will first check if it's a string - * representation of a number, in which case it'll compare it to the api level. Otherwise, it'll - * compare it against the code name. - * <p/>For all other type of object give as parameter, this method will return - * <code>false</code>. - */ - @Override - public boolean equals(Object obj) { - if (obj instanceof AndroidVersion) { - AndroidVersion version = (AndroidVersion)obj; - - if (mCodename == null) { - return version.mCodename == null && - mApiLevel == version.mApiLevel; - } else { - return mCodename.equals(version.mCodename) && - mApiLevel == version.mApiLevel; - } - - } else if (obj instanceof String) { - // if we have a code name, this must match. - if (mCodename != null) { - return mCodename.equals(obj); - } - - // else we try to convert to a int and compare to the api level - try { - int value = Integer.parseInt((String)obj); - return value == mApiLevel; - } catch (NumberFormatException e) { - // not a number? we'll return false below. - } - } - - return false; - } - - @Override - public int hashCode() { - if (mCodename != null) { - return mCodename.hashCode(); - } - - // there may be some collisions between the hashcode of the codename and the api level - // but it's acceptable. - return mApiLevel; - } - - /** - * Returns a string with the API Level and optional codename. - * Useful for debugging. - * For display purpose, please use {@link #getApiString()} instead. - */ - @Override - public String toString() { - String s = String.format("API %1$d", mApiLevel); //$NON-NLS-1$ - if (isPreview()) { - s += String.format(", %1$s preview", mCodename); //$NON-NLS-1$ - } - return s; - } - - /** - * Compares this object with the specified object for order. Returns a - * negative integer, zero, or a positive integer as this object is less - * than, equal to, or greater than the specified object. - * - * @param o the Object to be compared. - * @return a negative integer, zero, or a positive integer as this object is - * less than, equal to, or greater than the specified object. - */ - @Override - public int compareTo(AndroidVersion o) { - return compareTo(o.mApiLevel, o.mCodename); - } - - public int compareTo(int apiLevel, String codename) { - if (mCodename == null) { - if (codename == null) { - return mApiLevel - apiLevel; - } else { - if (mApiLevel == apiLevel) { - return -1; // same api level but argument is a preview for next version - } - - return mApiLevel - apiLevel; - } - } else { - // 'this' is a preview - if (mApiLevel == apiLevel) { - if (codename == null) { - return +1; - } else { - return mCodename.compareTo(codename); // strange case where the 2 previews - // have different codename? - } - } else { - return mApiLevel - apiLevel; - } - } - } - - /** - * Compares this version with the specified API and returns true if this version - * is greater or equal than the requested API -- that is the current version is a - * suitable min-api-level for the argument API. - */ - public boolean isGreaterOrEqualThan(int api) { - return compareTo(api, null /*codename*/) >= 0; - } - - /** - * Sanitizes the codename string according to the following rules: - * - A codename should be {@code null} for a release version or it should be a non-empty - * string for an actual preview. - * - In input, spacing is trimmed since it is irrelevant. - * - An empty string or the special codename "REL" means a release version - * and is converted to {@code null}. - * - * @param codename A possible-null codename. - * @return Null for a release version or a non-empty codename. - */ - private @Nullable String sanitizeCodename(@Nullable String codename) { - if (codename != null) { - codename = codename.trim(); - if (codename.length() == 0 || SdkConstants.CODENAME_RELEASE.equals(codename)) { - codename = null; - } - } - return codename; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/IAndroidTarget.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/IAndroidTarget.java deleted file mode 100644 index 18577cf..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/IAndroidTarget.java +++ /dev/null @@ -1,288 +0,0 @@ -/* - * Copyright (C) 2008 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib; - -import java.util.Map; - - - -/** - * A version of Android that applications can target when building. - */ -public interface IAndroidTarget extends Comparable<IAndroidTarget> { - - /** - * Prefix used to build hash strings for platform targets - * @see SdkManager#getTargetFromHashString(String) - */ - public static final String PLATFORM_HASH_PREFIX = "android-"; - - /** OS Path to the "android.jar" file. */ - public final static int ANDROID_JAR = 1; - /** OS Path to the "framework.aidl" file. */ - public final static int ANDROID_AIDL = 2; - /** OS Path to the "samples" folder which contains sample projects. */ - public final static int SAMPLES = 4; - /** OS Path to the "skins" folder which contains the emulator skins. */ - public final static int SKINS = 5; - /** OS Path to the "templates" folder which contains the templates for new projects. */ - public final static int TEMPLATES = 6; - /** OS Path to the "data" folder which contains data & libraries for the SDK tools. */ - public final static int DATA = 7; - /** OS Path to the "attrs.xml" file. */ - public final static int ATTRIBUTES = 8; - /** OS Path to the "attrs_manifest.xml" file. */ - public final static int MANIFEST_ATTRIBUTES = 9; - /** OS Path to the "data/layoutlib.jar" library. */ - public final static int LAYOUT_LIB = 10; - /** OS Path to the "data/res" folder. */ - public final static int RESOURCES = 11; - /** OS Path to the "data/fonts" folder. */ - public final static int FONTS = 12; - /** OS Path to the "data/widgets.txt" file. */ - public final static int WIDGETS = 13; - /** OS Path to the "data/activity_actions.txt" file. */ - public final static int ACTIONS_ACTIVITY = 14; - /** OS Path to the "data/broadcast_actions.txt" file. */ - public final static int ACTIONS_BROADCAST = 15; - /** OS Path to the "data/service_actions.txt" file. */ - public final static int ACTIONS_SERVICE = 16; - /** OS Path to the "data/categories.txt" file. */ - public final static int CATEGORIES = 17; - /** OS Path to the "sources" folder. */ - public final static int SOURCES = 18; - /** OS Path to the target specific docs */ - public final static int DOCS = 19; - /** OS Path to the target's version of the aapt tool. - * This is deprecated as aapt is now in the platform tools and not in the platform. */ - @Deprecated - public final static int AAPT = 20; - /** OS Path to the target's version of the aidl tool. - * This is deprecated as aidl is now in the platform tools and not in the platform. */ - @Deprecated - public final static int AIDL = 21; - /** OS Path to the target's version of the dx too.<br> - * This is deprecated as dx is now in the platform tools and not in the platform. */ - @Deprecated - public final static int DX = 22; - /** OS Path to the target's version of the dx.jar file.<br> - * This is deprecated as dx.jar is now in the platform tools and not in the platform. */ - @Deprecated - public final static int DX_JAR = 23; - /** OS Path to the "ant" folder which contains the ant build rules (ver 2 and above) */ - public final static int ANT = 24; - /** OS Path to the Renderscript include folder. - * This is deprecated as this is now in the platform tools and not in the platform. */ - @Deprecated - public final static int ANDROID_RS = 25; - /** OS Path to the Renderscript(clang) include folder. - * This is deprecated as this is now in the platform tools and not in the platform. */ - @Deprecated - public final static int ANDROID_RS_CLANG = 26; - /** OS Path to the "uiautomator.jar" file. */ - public final static int UI_AUTOMATOR_JAR = 27; - - /** - * Return value for {@link #getUsbVendorId()} meaning no USB vendor IDs are defined by the - * Android target. - */ - public final static int NO_USB_ID = 0; - - /** An optional library provided by an Android Target */ - public interface IOptionalLibrary { - /** The name of the library, as used in the manifest (<uses-library>). */ - String getName(); - /** The file name of the jar file. */ - String getJarName(); - /** Absolute OS path to the jar file. */ - String getJarPath(); - /** Description of the library. */ - String getDescription(); - } - - /** - * Returns the target location. - */ - String getLocation(); - - /** - * Returns the name of the vendor of the target. - */ - String getVendor(); - - /** - * Returns the name of the target. - */ - String getName(); - - /** - * Returns the full name of the target, possibly including vendor name. - */ - String getFullName(); - - /** - * Returns the name to be displayed when representing all the libraries this target contains. - */ - String getClasspathName(); - - /** - * Returns the name to be displayed when representing all the libraries this target contains. - */ - String getShortClasspathName(); - - /** - * Returns the description of the target. - */ - String getDescription(); - - /** - * Returns the version of the target. This is guaranteed to be non-null. - */ - AndroidVersion getVersion(); - - /** - * Returns the platform version as a readable string. - */ - public String getVersionName(); - - /** Returns the revision number for the target. */ - int getRevision(); - - /** - * Returns true if the target is a standard Android platform. - */ - boolean isPlatform(); - - /** - * Returns the parent target. This is likely to only be non <code>null</code> if - * {@link #isPlatform()} returns <code>false</code> - */ - IAndroidTarget getParent(); - - /** - * Returns the path of a platform component. - * @param pathId the id representing the path to return. Any of the constants defined in the - * {@link IAndroidTarget} interface can be used. - */ - String getPath(int pathId); - - /** - * Returns whether the target is able to render layouts. - */ - boolean hasRenderingLibrary(); - - /** - * Returns the available skins for this target. - */ - String[] getSkins(); - - /** - * Returns the default skin for this target. - */ - String getDefaultSkin(); - - /** - * Returns the available optional libraries for this target. - * @return an array of optional libraries or <code>null</code> if there is none. - */ - IOptionalLibrary[] getOptionalLibraries(); - - /** - * Returns the list of libraries available for a given platform. - * - * @return an array of libraries provided by the platform or <code>null</code> if there is none. - */ - String[] getPlatformLibraries(); - - /** - * Return the value of a given property for this target. - * @return the property value or <code>null</code> if it was not found. - */ - String getProperty(String name); - - /** - * Returns the value of a given property for this target as an Integer value. - * <p/> If the value is missing or is not an integer, the method will return the given default - * value. - * @param name the name of the property to return - * @param defaultValue the default value to return. - * - * @see Integer#decode(String) - */ - Integer getProperty(String name, Integer defaultValue); - - /** - * Returns the value of a given property for this target as a Boolean value. - * <p/> If the value is missing or is not an boolean, the method will return the given default - * value. - * - * @param name the name of the property to return - * @param defaultValue the default value to return. - * - * @see Boolean#valueOf(String) - */ - - Boolean getProperty(String name, Boolean defaultValue); - - /** - * Returns all the properties associated with this target. This can be null if the target has - * no properties. - */ - Map<String, String> getProperties(); - - /** - * Returns the USB Vendor ID for the vendor of this target. - * <p/>If the target defines no USB Vendor ID, then the method return 0. - */ - int getUsbVendorId(); - - /** - * Returns an array of system images for this target. - * The array can be empty but not null. - */ - public ISystemImage[] getSystemImages(); - - /** - * Returns the system image information for the given {@code abiType}. - * - * @param abiType An ABI type string. - * @return An existing {@link ISystemImage} for the requested {@code abiType} - * or null if none exists for this type. - */ - public ISystemImage getSystemImage(String abiType); - - /** - * Returns whether the given target is compatible with the receiver. - * <p/> - * This means that a project using the receiver's target can run on the given target. - * <br/> - * Example: - * <pre> - * CupcakeTarget.canRunOn(DonutTarget) == true - * </pre>. - * - * @param target the IAndroidTarget to test. - */ - boolean canRunOn(IAndroidTarget target); - - /** - * Returns a string able to uniquely identify a target. - * Typically the target will encode information such as api level, whether it's a platform - * or add-on, and if it's an add-on vendor and add-on name. - */ - String hashString(); -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/ISystemImage.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/ISystemImage.java deleted file mode 100755 index 7a69030..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/ISystemImage.java +++ /dev/null @@ -1,71 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib; - -import com.android.SdkConstants; - -import java.io.File; - - -/** - * Describes a system image as used by an {@link IAndroidTarget}. - * A system image has an installation path, a location type and an ABI type. - */ -public interface ISystemImage extends Comparable<ISystemImage> { - - /** Indicates the type of location for the system image folder in the SDK. */ - public enum LocationType { - /** - * The system image is located in the legacy platform's {@link SdkConstants#FD_IMAGES} - * folder. - * <p/> - * Used by both platform and add-ons. - */ - IN_PLATFORM_LEGACY, - - /** - * The system image is located in a sub-directory of the platform's - * {@link SdkConstants#FD_IMAGES} folder, allowing for multiple system - * images within the platform. - * <p/> - * Used by both platform and add-ons. - */ - IN_PLATFORM_SUBFOLDER, - - /** - * The system image is located in the new SDK's {@link SdkConstants#FD_SYSTEM_IMAGES} - * folder. Supported as of Tools R14 and Repository XSD version 5. - * <p/> - * Used <em>only</em> by both platform. This is not supported for add-ons yet. - */ - IN_SYSTEM_IMAGE, - } - - /** Returns the actual location of an installed system image. */ - public abstract File getLocation(); - - /** Indicates the location strategy for this system image in the SDK. */ - public abstract LocationType getLocationType(); - - /** - * Returns the ABI type. For example, one of {@link SdkConstants#ABI_ARMEABI}, - * {@link SdkConstants#ABI_ARMEABI_V7A}, {@link SdkConstants#ABI_INTEL_ATOM} or - * {@link SdkConstants#ABI_MIPS}. - * Cannot be null nor empty. - */ - public abstract String getAbiType(); -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/PlatformTarget.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/PlatformTarget.java deleted file mode 100644 index 7c2b4aa..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/PlatformTarget.java +++ /dev/null @@ -1,427 +0,0 @@ -/* - * Copyright (C) 2008 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib; - -import com.android.SdkConstants; -import com.android.sdklib.SdkManager.LayoutlibVersion; -import com.android.sdklib.util.SparseArray; - -import java.io.File; -import java.util.Arrays; -import java.util.Collections; -import java.util.Map; - -/** - * Represents a platform target in the SDK. - */ -final class PlatformTarget implements IAndroidTarget { - /** String used to get a hash to the platform target */ - private final static String PLATFORM_HASH = "android-%s"; - - private final static String PLATFORM_VENDOR = "Android Open Source Project"; - - private final static String PLATFORM_NAME = "Android %s"; - private final static String PLATFORM_NAME_PREVIEW = "Android %s (Preview)"; - - /** the OS path to the root folder of the platform component. */ - private final String mRootFolderOsPath; - private final String mName; - private final AndroidVersion mVersion; - private final String mVersionName; - private final int mRevision; - private final Map<String, String> mProperties; - private final SparseArray<String> mPaths = new SparseArray<String>(); - private String[] mSkins; - private final ISystemImage[] mSystemImages; - private final LayoutlibVersion mLayoutlibVersion; - - /** - * Creates a Platform target. - * - * @param sdkOsPath the root folder of the SDK - * @param platformOSPath the root folder of the platform component - * @param apiVersion the API Level + codename. - * @param versionName the version name of the platform. - * @param revision the revision of the platform component. - * @param layoutlibVersion The {@link LayoutlibVersion}. May be null. - * @param systemImages list of supported system images - * @param properties the platform properties - */ - @SuppressWarnings("deprecation") - PlatformTarget( - String sdkOsPath, - String platformOSPath, - AndroidVersion apiVersion, - String versionName, - int revision, - LayoutlibVersion layoutlibVersion, - ISystemImage[] systemImages, - Map<String, String> properties) { - if (platformOSPath.endsWith(File.separator) == false) { - platformOSPath = platformOSPath + File.separator; - } - mRootFolderOsPath = platformOSPath; - mProperties = Collections.unmodifiableMap(properties); - mVersion = apiVersion; - mVersionName = versionName; - mRevision = revision; - mLayoutlibVersion = layoutlibVersion; - mSystemImages = systemImages == null ? new ISystemImage[0] : systemImages; - Arrays.sort(mSystemImages); - - if (mVersion.isPreview()) { - mName = String.format(PLATFORM_NAME_PREVIEW, mVersionName); - } else { - mName = String.format(PLATFORM_NAME, mVersionName); - } - - // pre-build the path to the platform components - mPaths.put(ANDROID_JAR, mRootFolderOsPath + SdkConstants.FN_FRAMEWORK_LIBRARY); - mPaths.put(UI_AUTOMATOR_JAR, mRootFolderOsPath + SdkConstants.FN_UI_AUTOMATOR_LIBRARY); - mPaths.put(SOURCES, mRootFolderOsPath + SdkConstants.FD_ANDROID_SOURCES); - mPaths.put(ANDROID_AIDL, mRootFolderOsPath + SdkConstants.FN_FRAMEWORK_AIDL); - mPaths.put(SAMPLES, mRootFolderOsPath + SdkConstants.OS_PLATFORM_SAMPLES_FOLDER); - mPaths.put(SKINS, mRootFolderOsPath + SdkConstants.OS_SKINS_FOLDER); - mPaths.put(TEMPLATES, mRootFolderOsPath + SdkConstants.OS_PLATFORM_TEMPLATES_FOLDER); - mPaths.put(DATA, mRootFolderOsPath + SdkConstants.OS_PLATFORM_DATA_FOLDER); - mPaths.put(ATTRIBUTES, mRootFolderOsPath + SdkConstants.OS_PLATFORM_ATTRS_XML); - mPaths.put(MANIFEST_ATTRIBUTES, - mRootFolderOsPath + SdkConstants.OS_PLATFORM_ATTRS_MANIFEST_XML); - mPaths.put(RESOURCES, mRootFolderOsPath + SdkConstants.OS_PLATFORM_RESOURCES_FOLDER); - mPaths.put(FONTS, mRootFolderOsPath + SdkConstants.OS_PLATFORM_FONTS_FOLDER); - mPaths.put(LAYOUT_LIB, mRootFolderOsPath + SdkConstants.OS_PLATFORM_DATA_FOLDER + - SdkConstants.FN_LAYOUTLIB_JAR); - mPaths.put(WIDGETS, mRootFolderOsPath + SdkConstants.OS_PLATFORM_DATA_FOLDER + - SdkConstants.FN_WIDGETS); - mPaths.put(ACTIONS_ACTIVITY, mRootFolderOsPath + SdkConstants.OS_PLATFORM_DATA_FOLDER + - SdkConstants.FN_INTENT_ACTIONS_ACTIVITY); - mPaths.put(ACTIONS_BROADCAST, mRootFolderOsPath + SdkConstants.OS_PLATFORM_DATA_FOLDER + - SdkConstants.FN_INTENT_ACTIONS_BROADCAST); - mPaths.put(ACTIONS_SERVICE, mRootFolderOsPath + SdkConstants.OS_PLATFORM_DATA_FOLDER + - SdkConstants.FN_INTENT_ACTIONS_SERVICE); - mPaths.put(CATEGORIES, mRootFolderOsPath + SdkConstants.OS_PLATFORM_DATA_FOLDER + - SdkConstants.FN_INTENT_CATEGORIES); - mPaths.put(ANT, mRootFolderOsPath + SdkConstants.OS_PLATFORM_ANT_FOLDER); - - // location for aapt, aidl, dx is now in the platform-tools folder. - mPaths.put(AAPT, sdkOsPath + SdkConstants.OS_SDK_PLATFORM_TOOLS_FOLDER + - SdkConstants.FN_AAPT); - mPaths.put(AIDL, sdkOsPath + SdkConstants.OS_SDK_PLATFORM_TOOLS_FOLDER + - SdkConstants.FN_AIDL); - mPaths.put(DX, sdkOsPath + SdkConstants.OS_SDK_PLATFORM_TOOLS_FOLDER + - SdkConstants.FN_DX); - mPaths.put(DX_JAR, sdkOsPath + SdkConstants.OS_SDK_PLATFORM_TOOLS_LIB_FOLDER + - SdkConstants.FN_DX_JAR); - mPaths.put(ANDROID_RS, sdkOsPath + SdkConstants.OS_SDK_PLATFORM_TOOLS_FOLDER + - SdkConstants.OS_FRAMEWORK_RS); - mPaths.put(ANDROID_RS_CLANG, sdkOsPath + SdkConstants.OS_SDK_PLATFORM_TOOLS_FOLDER + - SdkConstants.OS_FRAMEWORK_RS_CLANG); - } - - /** - * Returns the {@link LayoutlibVersion}. May be null. - */ - public LayoutlibVersion getLayoutlibVersion() { - return mLayoutlibVersion; - } - - @Override - public ISystemImage getSystemImage(String abiType) { - for (ISystemImage sysImg : mSystemImages) { - if (sysImg.getAbiType().equals(abiType)) { - return sysImg; - } - } - return null; - } - - @Override - public ISystemImage[] getSystemImages() { - return mSystemImages; - } - - @Override - public String getLocation() { - return mRootFolderOsPath; - } - - /** - * {@inheritDoc} - * <p/> - * For Platform, the vendor name is always "Android". - * - * @see com.android.sdklib.IAndroidTarget#getVendor() - */ - @Override - public String getVendor() { - return PLATFORM_VENDOR; - } - - @Override - public String getName() { - return mName; - } - - @Override - public String getFullName() { - return mName; - } - - @Override - public String getClasspathName() { - return mName; - } - - @Override - public String getShortClasspathName() { - return mName; - } - - /* - * (non-Javadoc) - * - * Description for the Android platform is dynamically generated. - * - * @see com.android.sdklib.IAndroidTarget#getDescription() - */ - @Override - public String getDescription() { - return String.format("Standard Android platform %s", mVersionName); - } - - @Override - public AndroidVersion getVersion() { - return mVersion; - } - - @Override - public String getVersionName() { - return mVersionName; - } - - @Override - public int getRevision() { - return mRevision; - } - - @Override - public boolean isPlatform() { - return true; - } - - @Override - public IAndroidTarget getParent() { - return null; - } - - @Override - public String getPath(int pathId) { - return mPaths.get(pathId); - } - - /** - * Returns whether the target is able to render layouts. This is always true for platforms. - */ - @Override - public boolean hasRenderingLibrary() { - return true; - } - - - @Override - public String[] getSkins() { - return mSkins; - } - - @Override - public String getDefaultSkin() { - // only one skin? easy. - if (mSkins.length == 1) { - return mSkins[0]; - } - - // look for the skin name in the platform props - String skinName = mProperties.get(SdkConstants.PROP_SDK_DEFAULT_SKIN); - if (skinName != null) { - return skinName; - } - - // otherwise try to find a good default. - if (mVersion.getApiLevel() >= 4) { - // at this time, this is the default skin for all older platforms that had 2+ skins. - return "WVGA800"; - } - - return "HVGA"; // this is for 1.5 and earlier. - } - - /** - * Always returns null, as a standard platform ha no optional libraries. - * - * {@inheritDoc} - * @see com.android.sdklib.IAndroidTarget#getOptionalLibraries() - */ - @Override - public IOptionalLibrary[] getOptionalLibraries() { - return null; - } - - /** - * Currently always return a fixed list with "android.test.runner" in it. - * <p/> - * TODO change the fixed library list to be build-dependent later. - * {@inheritDoc} - */ - @Override - public String[] getPlatformLibraries() { - return new String[] { SdkConstants.ANDROID_TEST_RUNNER_LIB }; - } - - /** - * The platform has no USB Vendor Id: always return {@link IAndroidTarget#NO_USB_ID}. - * {@inheritDoc} - */ - @Override - public int getUsbVendorId() { - return NO_USB_ID; - } - - @Override - public boolean canRunOn(IAndroidTarget target) { - // basic test - if (target == this) { - return true; - } - - // if the platform has a codename (ie it's a preview of an upcoming platform), then - // both platforms must be exactly identical. - if (mVersion.getCodename() != null) { - return mVersion.equals(target.getVersion()); - } - - // target is compatible wit the receiver as long as its api version number is greater or - // equal. - return target.getVersion().getApiLevel() >= mVersion.getApiLevel(); - } - - @Override - public String hashString() { - return String.format(PLATFORM_HASH, mVersion.getApiString()); - } - - @Override - public int hashCode() { - return hashString().hashCode(); - } - - @Override - public boolean equals(Object obj) { - if (obj instanceof PlatformTarget) { - PlatformTarget platform = (PlatformTarget)obj; - - return mVersion.equals(platform.getVersion()); - } - - return false; - } - - /* - * Order by API level (preview/n count as between n and n+1). - * At the same API level, order as: Platform first, then add-on ordered by vendor and then name - * (non-Javadoc) - * @see java.lang.Comparable#compareTo(java.lang.Object) - */ - @Override - public int compareTo(IAndroidTarget target) { - // quick check. - if (this == target) { - return 0; - } - - int versionDiff = mVersion.compareTo(target.getVersion()); - - // only if the version are the same do we care about add-ons. - if (versionDiff == 0) { - // platforms go before add-ons. - if (target.isPlatform() == false) { - return -1; - } - } - - return versionDiff; - } - - /** - * Returns a string representation suitable for debugging. - * The representation is not intended for display to the user. - * - * The representation is also purposely compact. It does not describe _all_ the properties - * of the target, only a few key ones. - * - * @see #getDescription() - */ - @Override - public String toString() { - return String.format("PlatformTarget %1$s rev %2$d", //$NON-NLS-1$ - getVersion(), - getRevision()); - } - - @Override - public String getProperty(String name) { - return mProperties.get(name); - } - - @Override - public Integer getProperty(String name, Integer defaultValue) { - try { - String value = getProperty(name); - if (value != null) { - return Integer.decode(value); - } - } catch (NumberFormatException e) { - // ignore, return default value; - } - - return defaultValue; - } - - @Override - public Boolean getProperty(String name, Boolean defaultValue) { - String value = getProperty(name); - if (value != null) { - return Boolean.valueOf(value); - } - - return defaultValue; - } - - @Override - public Map<String, String> getProperties() { - return mProperties; // mProperties is unmodifiable. - } - - // ---- platform only methods. - - void setSkins(String[] skins) { - mSkins = skins; - } - - void setSamplesPath(String osLocation) { - mPaths.put(SAMPLES, osLocation); - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/SdkManager.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/SdkManager.java deleted file mode 100644 index 0bca185..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/SdkManager.java +++ /dev/null @@ -1,1368 +0,0 @@ -/* - * Copyright (C) 2008 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib; - -import com.android.SdkConstants; -import com.android.annotations.NonNull; -import com.android.annotations.Nullable; -import com.android.annotations.VisibleForTesting; -import com.android.annotations.VisibleForTesting.Visibility; -import com.android.io.FileWrapper; -import com.android.prefs.AndroidLocation; -import com.android.prefs.AndroidLocation.AndroidLocationException; -import com.android.sdklib.AndroidVersion.AndroidVersionException; -import com.android.sdklib.ISystemImage.LocationType; -import com.android.sdklib.internal.project.ProjectProperties; -import com.android.sdklib.internal.repository.LocalSdkParser; -import com.android.sdklib.internal.repository.NullTaskMonitor; -import com.android.sdklib.internal.repository.archives.Archive; -import com.android.sdklib.internal.repository.packages.ExtraPackage; -import com.android.sdklib.internal.repository.packages.Package; -import com.android.sdklib.internal.repository.packages.PlatformToolPackage; -import com.android.sdklib.repository.PkgProps; -import com.android.utils.ILogger; -import com.android.utils.NullLogger; -import com.android.utils.Pair; - -import java.io.File; -import java.io.FileInputStream; -import java.io.FileNotFoundException; -import java.io.FileWriter; -import java.io.IOException; -import java.util.ArrayList; -import java.util.Collections; -import java.util.HashMap; -import java.util.HashSet; -import java.util.Map; -import java.util.Properties; -import java.util.Set; -import java.util.TreeMap; -import java.util.TreeSet; -import java.util.regex.Matcher; -import java.util.regex.Pattern; -import java.util.zip.Adler32; - -/** - * The SDK manager parses the SDK folder and gives access to the content. - * @see PlatformTarget - * @see AddOnTarget - */ -public class SdkManager { - - private static final boolean DEBUG = System.getenv("SDKMAN_DEBUG") != null; //$NON-NLS-1$ - - public final static String PROP_VERSION_SDK = "ro.build.version.sdk"; //$NON-NLS-1$ - public final static String PROP_VERSION_CODENAME = "ro.build.version.codename"; //$NON-NLS-1$ - public final static String PROP_VERSION_RELEASE = "ro.build.version.release"; //$NON-NLS-1$ - - public final static String ADDON_NAME = "name"; //$NON-NLS-1$ - public final static String ADDON_VENDOR = "vendor"; //$NON-NLS-1$ - public final static String ADDON_API = "api"; //$NON-NLS-1$ - public final static String ADDON_DESCRIPTION = "description"; //$NON-NLS-1$ - public final static String ADDON_LIBRARIES = "libraries"; //$NON-NLS-1$ - public final static String ADDON_DEFAULT_SKIN = "skin"; //$NON-NLS-1$ - public final static String ADDON_USB_VENDOR = "usb-vendor"; //$NON-NLS-1$ - public final static String ADDON_REVISION = "revision"; //$NON-NLS-1$ - public final static String ADDON_REVISION_OLD = "version"; //$NON-NLS-1$ - - - private final static Pattern PATTERN_LIB_DATA = Pattern.compile( - "^([a-zA-Z0-9._-]+\\.jar);(.*)$", Pattern.CASE_INSENSITIVE); //$NON-NLS-1$ - - // usb ids are 16-bit hexadecimal values. - private final static Pattern PATTERN_USB_IDS = Pattern.compile( - "^0x[a-f0-9]{4}$", Pattern.CASE_INSENSITIVE); //$NON-NLS-1$ - - /** List of items in the platform to check when parsing it. These paths are relative to the - * platform root folder. */ - private final static String[] sPlatformContentList = new String[] { - SdkConstants.FN_FRAMEWORK_LIBRARY, - SdkConstants.FN_FRAMEWORK_AIDL, - }; - - /** Preference file containing the usb ids for adb */ - private final static String ADB_INI_FILE = "adb_usb.ini"; //$NON-NLS-1$ - //0--------90--------90--------90--------90--------90--------90--------90--------9 - private final static String ADB_INI_HEADER = - "# ANDROID 3RD PARTY USB VENDOR ID LIST -- DO NOT EDIT.\n" + //$NON-NLS-1$ - "# USE 'android update adb' TO GENERATE.\n" + //$NON-NLS-1$ - "# 1 USB VENDOR ID PER LINE.\n"; //$NON-NLS-1$ - - /** The location of the SDK as an OS path */ - private final String mOsSdkPath; - /** Valid targets that have been loaded. Can be empty but not null. */ - private IAndroidTarget[] mTargets = new IAndroidTarget[0]; - /** A map to keep information on directories to see if they change later. */ - private final Map<File, DirInfo> mTargetDirs = new HashMap<File, SdkManager.DirInfo>(); - - /** - * Create a new {@link SdkManager} instance. - * External users should use {@link #createManager(String, ILogger)}. - * - * @param osSdkPath the location of the SDK. - */ - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected SdkManager(String osSdkPath) { - mOsSdkPath = osSdkPath; - } - - /** - * Creates an {@link SdkManager} for a given sdk location. - * @param osSdkPath the location of the SDK. - * @param log the ILogger object receiving warning/error from the parsing. Cannot be null. - * @return the created {@link SdkManager} or null if the location is not valid. - */ - public static SdkManager createManager(String osSdkPath, ILogger log) { - try { - SdkManager manager = new SdkManager(osSdkPath); - manager.reloadSdk(log); - - return manager; - } catch (IllegalArgumentException e) { - log.error(e, "Error parsing the sdk."); - } - - return null; - } - - /** - * Reloads the content of the SDK. - * - * @param log the ILogger object receiving warning/error from the parsing. Cannot be null. - */ - public void reloadSdk(ILogger log) { - // get the current target list. - mTargetDirs.clear(); - ArrayList<IAndroidTarget> targets = new ArrayList<IAndroidTarget>(); - loadPlatforms(mOsSdkPath, targets, mTargetDirs, log); - loadAddOns(mOsSdkPath, targets, mTargetDirs, log); - - // For now replace the old list with the new one. - // In the future we may want to keep the current objects, so that ADT doesn't have to deal - // with new IAndroidTarget objects when a target didn't actually change. - - // sort the targets/add-ons - Collections.sort(targets); - setTargets(targets.toArray(new IAndroidTarget[targets.size()])); - - // load the samples, after the targets have been set. - initializeSamplePaths(log); - } - - /** - * Checks whether any of the SDK platforms/add-ons have changed on-disk - * since we last loaded the SDK. This does not reload the SDK nor does it - * change the underlying targets. - * - * @return True if at least one directory or source.prop has changed. - */ - public boolean hasChanged() { - Set<File> visited = new HashSet<File>(); - boolean changed = false; - - File platformFolder = new File(mOsSdkPath, SdkConstants.FD_PLATFORMS); - if (platformFolder.isDirectory()) { - File[] platforms = platformFolder.listFiles(); - if (platforms != null) { - for (File platform : platforms) { - if (!platform.isDirectory()) { - continue; - } - visited.add(platform); - DirInfo dirInfo = mTargetDirs.get(platform); - if (dirInfo == null) { - // This is a new platform directory. - changed = true; - } else { - changed = dirInfo.hasChanged(); - } - if (changed) { - if (DEBUG) { - System.out.println("SDK changed due to " + //$NON-NLS-1$ - (dirInfo != null ? dirInfo.toString() : platform.getPath())); - } - } - } - } - } - - File addonFolder = new File(mOsSdkPath, SdkConstants.FD_ADDONS); - - if (!changed && addonFolder.isDirectory()) { - File[] addons = addonFolder.listFiles(); - if (addons != null) { - for (File addon : addons) { - if (!addon.isDirectory()) { - continue; - } - visited.add(addon); - DirInfo dirInfo = mTargetDirs.get(addon); - if (dirInfo == null) { - // This is a new add-on directory. - changed = true; - } else { - changed = dirInfo.hasChanged(); - } - if (changed) { - if (DEBUG) { - System.out.println("SDK changed due to " + //$NON-NLS-1$ - (dirInfo != null ? dirInfo.toString() : addon.getPath())); - } - } - } - } - } - - if (!changed) { - // Check whether some pre-existing target directories have vanished. - for (File previousDir : mTargetDirs.keySet()) { - if (!visited.contains(previousDir)) { - // This directory is no longer present. - changed = true; - if (DEBUG) { - System.out.println("SDK changed: " + //$NON-NLS-1$ - previousDir.getPath() + " removed"); //$NON-NLS-1$ - } - break; - } - } - } - - return changed; - } - - /** - * Returns the location of the SDK. - */ - public String getLocation() { - return mOsSdkPath; - } - - /** - * Returns the targets that are available in the SDK. - * <p/> - * The array can be empty but not null. - */ - public IAndroidTarget[] getTargets() { - return mTargets; - } - - /** - * Sets the targets that are available in the SDK. - * <p/> - * The array can be empty but not null. - */ - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected void setTargets(IAndroidTarget[] targets) { - assert targets != null; - mTargets = targets; - } - - /** - * Returns a target from a hash that was generated by {@link IAndroidTarget#hashString()}. - * - * @param hash the {@link IAndroidTarget} hash string. - * @return The matching {@link IAndroidTarget} or null. - */ - public IAndroidTarget getTargetFromHashString(String hash) { - if (hash != null) { - for (IAndroidTarget target : mTargets) { - if (hash.equals(target.hashString())) { - return target; - } - } - } - - return null; - } - - /** - * Updates adb with the USB devices declared in the SDK add-ons. - * @throws AndroidLocationException - * @throws IOException - */ - public void updateAdb() throws AndroidLocationException, IOException { - FileWriter writer = null; - try { - // get the android prefs location to know where to write the file. - File adbIni = new File(AndroidLocation.getFolder(), ADB_INI_FILE); - writer = new FileWriter(adbIni); - - // first, put all the vendor id in an HashSet to remove duplicate. - HashSet<Integer> set = new HashSet<Integer>(); - IAndroidTarget[] targets = getTargets(); - for (IAndroidTarget target : targets) { - if (target.getUsbVendorId() != IAndroidTarget.NO_USB_ID) { - set.add(target.getUsbVendorId()); - } - } - - // write file header. - writer.write(ADB_INI_HEADER); - - // now write the Id in a text file, one per line. - for (Integer i : set) { - writer.write(String.format("0x%04x\n", i)); //$NON-NLS-1$ - } - } finally { - if (writer != null) { - writer.close(); - } - } - } - - /** - * Returns the greatest {@link LayoutlibVersion} found amongst all platform - * targets currently loaded in the SDK. - * <p/> - * We only started recording Layoutlib Versions recently in the platform meta data - * so it's possible to have an SDK with many platforms loaded but no layoutlib - * version defined. - * - * @return The greatest {@link LayoutlibVersion} or null if none is found. - * @deprecated This does NOT solve the right problem and will be changed later. - */ - @Deprecated - public LayoutlibVersion getMaxLayoutlibVersion() { - LayoutlibVersion maxVersion = null; - - for (IAndroidTarget target : getTargets()) { - if (target instanceof PlatformTarget) { - LayoutlibVersion lv = ((PlatformTarget) target).getLayoutlibVersion(); - if (lv != null) { - if (maxVersion == null || lv.compareTo(maxVersion) > 0) { - maxVersion = lv; - } - } - } - } - - return maxVersion; - } - - /** - * Returns a map of the <em>root samples directories</em> located in the SDK/extras packages. - * No guarantee is made that the extras' samples directory actually contain any valid samples. - * The only guarantee is that the root samples directory actually exists. - * The map is { File: Samples root directory => String: Extra package display name. } - * - * @return A non-null possibly empty map of extra samples directories and their associated - * extra package display name. - */ - public @NonNull Map<File, String> getExtraSamples() { - LocalSdkParser parser = new LocalSdkParser(); - Package[] packages = parser.parseSdk(mOsSdkPath, - this, - LocalSdkParser.PARSE_EXTRAS, - new NullTaskMonitor(NullLogger.getLogger())); - - Map<File, String> samples = new HashMap<File, String>(); - - for (Package pkg : packages) { - if (pkg instanceof ExtraPackage && pkg.isLocal()) { - // isLocal()==true implies there's a single locally-installed archive. - assert pkg.getArchives() != null && pkg.getArchives().length == 1; - Archive a = pkg.getArchives()[0]; - assert a != null; - File path = new File(a.getLocalOsPath(), SdkConstants.FD_SAMPLES); - if (path.isDirectory()) { - samples.put(path, pkg.getListDescription()); - continue; - } - // Some old-style extras simply have a single "sample" directory. - // Accept it if it contains an AndroidManifest.xml. - path = new File(a.getLocalOsPath(), SdkConstants.FD_SAMPLE); - if (path.isDirectory() && - new File(path, SdkConstants.FN_ANDROID_MANIFEST_XML).isFile()) { - samples.put(path, pkg.getListDescription()); - } - } - } - - return samples; - } - - /** - * Returns a map of all the extras found in the <em>local</em> SDK with their major revision. - * <p/> - * Map keys are in the form "vendor-id/path-id". These ids uniquely identify an extra package. - * The version is the incremental integer major revision of the package. - * - * @return A non-null possibly empty map of { string "vendor/path" => integer major revision } - */ - public @NonNull Map<String, Integer> getExtrasVersions() { - LocalSdkParser parser = new LocalSdkParser(); - Package[] packages = parser.parseSdk(mOsSdkPath, - this, - LocalSdkParser.PARSE_EXTRAS, - new NullTaskMonitor(NullLogger.getLogger())); - - Map<String, Integer> extraVersions = new TreeMap<String, Integer>(); - - for (Package pkg : packages) { - if (pkg instanceof ExtraPackage && pkg.isLocal()) { - ExtraPackage ep = (ExtraPackage) pkg; - String vendor = ep.getVendorId(); - String path = ep.getPath(); - int majorRev = ep.getRevision().getMajor(); - - extraVersions.put(vendor + '/' + path, majorRev); - } - } - - return extraVersions; - } - - /** Returns the platform tools version if installed, null otherwise. */ - public @Nullable String getPlatformToolsVersion() { - LocalSdkParser parser = new LocalSdkParser(); - Package[] packages = parser.parseSdk(mOsSdkPath, this, LocalSdkParser.PARSE_PLATFORM_TOOLS, - new NullTaskMonitor(NullLogger.getLogger())); - - for (Package pkg : packages) { - if (pkg instanceof PlatformToolPackage && pkg.isLocal()) { - return pkg.getRevision().toShortString(); - } - } - - return null; - } - - - // -------- private methods ---------- - - /** - * Loads the Platforms from the SDK. - * Creates the "platforms" folder if necessary. - * - * @param sdkOsPath Location of the SDK - * @param targets the list to fill with the platforms. - * @param dirInfos a map to keep information on directories to see if they change later. - * @param log the ILogger object receiving warning/error from the parsing. Cannot be null. - * @throws RuntimeException when the "platforms" folder is missing and cannot be created. - */ - private static void loadPlatforms( - String sdkOsPath, - ArrayList<IAndroidTarget> targets, - Map<File, DirInfo> dirInfos, ILogger log) { - File platformFolder = new File(sdkOsPath, SdkConstants.FD_PLATFORMS); - - if (platformFolder.isDirectory()) { - File[] platforms = platformFolder.listFiles(); - - for (File platform : platforms) { - PlatformTarget target = null; - if (platform.isDirectory()) { - target = loadPlatform(sdkOsPath, platform, log); - if (target != null) { - targets.add(target); - } - // Remember we visited this file/directory, - // even if we failed to load anything from it. - dirInfos.put(platform, new DirInfo(platform)); - } else { - log.warning("Ignoring platform '%1$s', not a folder.", platform.getName()); - } - } - - return; - } - - // Try to create it or complain if something else is in the way. - if (!platformFolder.exists()) { - if (!platformFolder.mkdir()) { - throw new RuntimeException( - String.format("Failed to create %1$s.", - platformFolder.getAbsolutePath())); - } - } else { - throw new RuntimeException( - String.format("%1$s is not a folder.", - platformFolder.getAbsolutePath())); - } - } - - /** - * Loads a specific Platform at a given location. - * @param sdkOsPath Location of the SDK - * @param platformFolder the root folder of the platform. - * @param log the ILogger object receiving warning/error from the parsing. Cannot be null. - */ - private static PlatformTarget loadPlatform( - String sdkOsPath, - File platformFolder, - ILogger log) { - FileWrapper buildProp = new FileWrapper(platformFolder, SdkConstants.FN_BUILD_PROP); - FileWrapper sourcePropFile = new FileWrapper(platformFolder, SdkConstants.FN_SOURCE_PROP); - - if (buildProp.isFile() && sourcePropFile.isFile()) { - Map<String, String> platformProp = new HashMap<String, String>(); - - // add all the property files - Map<String, String> map = ProjectProperties.parsePropertyFile(buildProp, log); - if (map != null) { - platformProp.putAll(map); - } - - map = ProjectProperties.parsePropertyFile(sourcePropFile, log); - if (map != null) { - platformProp.putAll(map); - } - - FileWrapper sdkPropFile = new FileWrapper(platformFolder, SdkConstants.FN_SDK_PROP); - if (sdkPropFile.isFile()) { // obsolete platforms don't have this. - map = ProjectProperties.parsePropertyFile(sdkPropFile, log); - if (map != null) { - platformProp.putAll(map); - } - } - - // look for some specific values in the map. - - // api level - int apiNumber; - String stringValue = platformProp.get(PROP_VERSION_SDK); - if (stringValue == null) { - log.warning( - "Ignoring platform '%1$s': %2$s is missing from '%3$s'", - platformFolder.getName(), PROP_VERSION_SDK, - SdkConstants.FN_BUILD_PROP); - return null; - } else { - try { - apiNumber = Integer.parseInt(stringValue); - } catch (NumberFormatException e) { - // looks like apiNumber does not parse to a number. - // Ignore this platform. - log.warning( - "Ignoring platform '%1$s': %2$s is not a valid number in %3$s.", - platformFolder.getName(), PROP_VERSION_SDK, - SdkConstants.FN_BUILD_PROP); - return null; - } - } - - // Codename must be either null or a platform codename. - // REL means it's a release version and therefore the codename should be null. - AndroidVersion apiVersion = - new AndroidVersion(apiNumber, platformProp.get(PROP_VERSION_CODENAME)); - - // version string - String apiName = platformProp.get(PkgProps.PLATFORM_VERSION); - if (apiName == null) { - apiName = platformProp.get(PROP_VERSION_RELEASE); - } - if (apiName == null) { - log.warning( - "Ignoring platform '%1$s': %2$s is missing from '%3$s'", - platformFolder.getName(), PROP_VERSION_RELEASE, - SdkConstants.FN_BUILD_PROP); - return null; - } - - // platform rev number & layoutlib version are extracted from the source.properties - // saved by the SDK Manager when installing the package. - - int revision = 1; - LayoutlibVersion layoutlibVersion = null; - try { - revision = Integer.parseInt(platformProp.get(PkgProps.PKG_REVISION)); - } catch (NumberFormatException e) { - // do nothing, we'll keep the default value of 1. - } - - try { - String propApi = platformProp.get(PkgProps.LAYOUTLIB_API); - String propRev = platformProp.get(PkgProps.LAYOUTLIB_REV); - int llApi = propApi == null ? LayoutlibVersion.NOT_SPECIFIED : - Integer.parseInt(propApi); - int llRev = propRev == null ? LayoutlibVersion.NOT_SPECIFIED : - Integer.parseInt(propRev); - if (llApi > LayoutlibVersion.NOT_SPECIFIED && - llRev >= LayoutlibVersion.NOT_SPECIFIED) { - layoutlibVersion = new LayoutlibVersion(llApi, llRev); - } - } catch (NumberFormatException e) { - // do nothing, we'll ignore the layoutlib version if it's invalid - } - - // api number and name look valid, perform a few more checks - if (checkPlatformContent(platformFolder, log) == false) { - return null; - } - - ISystemImage[] systemImages = - getPlatformSystemImages(sdkOsPath, platformFolder, apiVersion); - - // create the target. - PlatformTarget target = new PlatformTarget( - sdkOsPath, - platformFolder.getAbsolutePath(), - apiVersion, - apiName, - revision, - layoutlibVersion, - systemImages, - platformProp); - - // need to parse the skins. - String[] skins = parseSkinFolder(target.getPath(IAndroidTarget.SKINS)); - target.setSkins(skins); - - return target; - } else { - log.warning("Ignoring platform '%1$s': %2$s is missing.", //$NON-NLS-1$ - platformFolder.getName(), - SdkConstants.FN_BUILD_PROP); - } - - return null; - } - - /** - * Get all the system images supported by an add-on target. - * For an add-on, we first look for sub-folders in the addon/images directory. - * If none are found but the directory exists and is not empty, assume it's a legacy - * arm eabi system image. - * <p/> - * Note that it's OK for an add-on to have no system-images at all, since it can always - * rely on the ones from its base platform. - * - * @param root Root of the add-on target being loaded. - * @return an array of ISystemImage containing all the system images for the target. - * The list can be empty. - */ - private static ISystemImage[] getAddonSystemImages(File root) { - Set<ISystemImage> found = new TreeSet<ISystemImage>(); - - root = new File(root, SdkConstants.OS_IMAGES_FOLDER); - File[] files = root.listFiles(); - boolean hasImgFiles = false; - - if (files != null) { - // Look for sub-directories - for (File file : files) { - if (file.isDirectory()) { - found.add(new SystemImage( - file, - LocationType.IN_PLATFORM_SUBFOLDER, - file.getName())); - } else if (!hasImgFiles && file.isFile()) { - if (file.getName().endsWith(".img")) { //$NON-NLS-1$ - hasImgFiles = true; - } - } - } - } - - if (found.size() == 0 && hasImgFiles && root.isDirectory()) { - // We found no sub-folder system images but it looks like the top directory - // has some img files in it. It must be a legacy ARM EABI system image folder. - found.add(new SystemImage( - root, - LocationType.IN_PLATFORM_LEGACY, - SdkConstants.ABI_ARMEABI)); - } - - return found.toArray(new ISystemImage[found.size()]); - } - - /** - * Get all the system images supported by a platform target. - * For a platform, we first look in the new sdk/system-images folders then we - * look for sub-folders in the platform/images directory and/or the one legacy - * folder. - * If any given API appears twice or more, the first occurrence wins. - * - * @param sdkOsPath The path to the SDK. - * @param root Root of the platform target being loaded. - * @param version API level + codename of platform being loaded. - * @return an array of ISystemImage containing all the system images for the target. - * The list can be empty. - */ - private static ISystemImage[] getPlatformSystemImages( - String sdkOsPath, - File root, - AndroidVersion version) { - Set<ISystemImage> found = new TreeSet<ISystemImage>(); - Set<String> abiFound = new HashSet<String>(); - - // First look in the SDK/system-image/platform-n/abi folders. - // We require/enforce the system image to have a valid properties file. - // The actual directory names are irrelevant. - // If we find multiple occurrences of the same platform/abi, the first one read wins. - - File[] firstLevelFiles = new File(sdkOsPath, SdkConstants.FD_SYSTEM_IMAGES).listFiles(); - if (firstLevelFiles != null) { - for (File firstLevel : firstLevelFiles) { - File[] secondLevelFiles = firstLevel.listFiles(); - if (secondLevelFiles != null) { - for (File secondLevel : secondLevelFiles) { - try { - File propFile = new File(secondLevel, SdkConstants.FN_SOURCE_PROP); - Properties props = new Properties(); - FileInputStream fis = null; - try { - fis = new FileInputStream(propFile); - props.load(fis); - } finally { - if (fis != null) { - fis.close(); - } - } - - AndroidVersion propsVersion = new AndroidVersion(props); - if (!propsVersion.equals(version)) { - continue; - } - - String abi = props.getProperty(PkgProps.SYS_IMG_ABI); - if (abi != null && !abiFound.contains(abi)) { - found.add(new SystemImage( - secondLevel, - LocationType.IN_SYSTEM_IMAGE, - abi)); - abiFound.add(abi); - } - } catch (Exception ignore) { - } - } - } - } - } - - // Then look in either the platform/images/abi or the legacy folder - root = new File(root, SdkConstants.OS_IMAGES_FOLDER); - File[] files = root.listFiles(); - boolean useLegacy = true; - boolean hasImgFiles = false; - - if (files != null) { - // Look for sub-directories - for (File file : files) { - if (file.isDirectory()) { - useLegacy = false; - String abi = file.getName(); - if (!abiFound.contains(abi)) { - found.add(new SystemImage( - file, - LocationType.IN_PLATFORM_SUBFOLDER, - abi)); - abiFound.add(abi); - } - } else if (!hasImgFiles && file.isFile()) { - if (file.getName().endsWith(".img")) { //$NON-NLS-1$ - hasImgFiles = true; - } - } - } - } - - if (useLegacy && hasImgFiles && root.isDirectory() && - !abiFound.contains(SdkConstants.ABI_ARMEABI)) { - // We found no sub-folder system images but it looks like the top directory - // has some img files in it. It must be a legacy ARM EABI system image folder. - found.add(new SystemImage( - root, - LocationType.IN_PLATFORM_LEGACY, - SdkConstants.ABI_ARMEABI)); - } - - return found.toArray(new ISystemImage[found.size()]); - } - - /** - * Loads the Add-on from the SDK. - * Creates the "add-ons" folder if necessary. - * - * @param osSdkPath Location of the SDK - * @param targets the list to fill with the add-ons. - * @param dirInfos a map to keep information on directories to see if they change later. - * @param log the ILogger object receiving warning/error from the parsing. Cannot be null. - * @throws RuntimeException when the "add-ons" folder is missing and cannot be created. - */ - private static void loadAddOns( - String osSdkPath, - ArrayList<IAndroidTarget> targets, - Map<File, DirInfo> dirInfos, ILogger log) { - File addonFolder = new File(osSdkPath, SdkConstants.FD_ADDONS); - - if (addonFolder.isDirectory()) { - File[] addons = addonFolder.listFiles(); - - IAndroidTarget[] targetList = targets.toArray(new IAndroidTarget[targets.size()]); - - if (addons != null) { - for (File addon : addons) { - // Add-ons have to be folders. Ignore files and no need to warn about them. - AddOnTarget target = null; - if (addon.isDirectory()) { - target = loadAddon(addon, targetList, log); - if (target != null) { - targets.add(target); - } - // Remember we visited this file/directory, - // even if we failed to load anything from it. - dirInfos.put(addon, new DirInfo(addon)); - } - } - } - - return; - } - - // Try to create it or complain if something else is in the way. - if (!addonFolder.exists()) { - if (!addonFolder.mkdir()) { - throw new RuntimeException( - String.format("Failed to create %1$s.", - addonFolder.getAbsolutePath())); - } - } else { - throw new RuntimeException( - String.format("%1$s is not a folder.", - addonFolder.getAbsolutePath())); - } - } - - /** - * Loads a specific Add-on at a given location. - * @param addonDir the location of the add-on directory. - * @param targetList The list of Android target that were already loaded from the SDK. - * @param log the ILogger object receiving warning/error from the parsing. Cannot be null. - */ - private static AddOnTarget loadAddon(File addonDir, - IAndroidTarget[] targetList, - ILogger log) { - - // Parse the addon properties to ensure we can load it. - Pair<Map<String, String>, String> infos = parseAddonProperties(addonDir, targetList, log); - - Map<String, String> propertyMap = infos.getFirst(); - String error = infos.getSecond(); - - if (error != null) { - log.warning("Ignoring add-on '%1$s': %2$s", addonDir.getName(), error); - return null; - } - - // Since error==null we're not supposed to encounter any issues loading this add-on. - try { - assert propertyMap != null; - - String api = propertyMap.get(ADDON_API); - String name = propertyMap.get(ADDON_NAME); - String vendor = propertyMap.get(ADDON_VENDOR); - - assert api != null; - assert name != null; - assert vendor != null; - - PlatformTarget baseTarget = null; - - // Look for a platform that has a matching api level or codename. - for (IAndroidTarget target : targetList) { - if (target.isPlatform() && target.getVersion().equals(api)) { - baseTarget = (PlatformTarget)target; - break; - } - } - - assert baseTarget != null; - - // get the optional description - String description = propertyMap.get(ADDON_DESCRIPTION); - - // get the add-on revision - int revisionValue = 1; - String revision = propertyMap.get(ADDON_REVISION); - if (revision == null) { - revision = propertyMap.get(ADDON_REVISION_OLD); - } - if (revision != null) { - revisionValue = Integer.parseInt(revision); - } - - // get the optional libraries - String librariesValue = propertyMap.get(ADDON_LIBRARIES); - Map<String, String[]> libMap = null; - - if (librariesValue != null) { - librariesValue = librariesValue.trim(); - if (librariesValue.length() > 0) { - // split in the string into the libraries name - String[] libraries = librariesValue.split(";"); //$NON-NLS-1$ - if (libraries.length > 0) { - libMap = new HashMap<String, String[]>(); - for (String libName : libraries) { - libName = libName.trim(); - - // get the library data from the properties - String libData = propertyMap.get(libName); - - if (libData != null) { - // split the jar file from the description - Matcher m = PATTERN_LIB_DATA.matcher(libData); - if (m.matches()) { - libMap.put(libName, new String[] { - m.group(1), m.group(2) }); - } else { - log.warning( - "Ignoring library '%1$s', property value has wrong format\n\t%2$s", - libName, libData); - } - } else { - log.warning( - "Ignoring library '%1$s', missing property value", - libName, libData); - } - } - } - } - } - - // get the abi list. - ISystemImage[] systemImages = getAddonSystemImages(addonDir); - - // check whether the add-on provides its own rendering info/library. - boolean hasRenderingLibrary = false; - boolean hasRenderingResources = false; - - File dataFolder = new File(addonDir, SdkConstants.FD_DATA); - if (dataFolder.isDirectory()) { - hasRenderingLibrary = new File(dataFolder, SdkConstants.FN_LAYOUTLIB_JAR).isFile(); - hasRenderingResources = new File(dataFolder, SdkConstants.FD_RES).isDirectory() && - new File(dataFolder, SdkConstants.FD_FONTS).isDirectory(); - } - - AddOnTarget target = new AddOnTarget(addonDir.getAbsolutePath(), name, vendor, - revisionValue, description, systemImages, libMap, - hasRenderingLibrary, hasRenderingResources,baseTarget); - - // need to parse the skins. - String[] skins = parseSkinFolder(target.getPath(IAndroidTarget.SKINS)); - - // get the default skin, or take it from the base platform if needed. - String defaultSkin = propertyMap.get(ADDON_DEFAULT_SKIN); - if (defaultSkin == null) { - if (skins.length == 1) { - defaultSkin = skins[0]; - } else { - defaultSkin = baseTarget.getDefaultSkin(); - } - } - - // get the USB ID (if available) - int usbVendorId = convertId(propertyMap.get(ADDON_USB_VENDOR)); - if (usbVendorId != IAndroidTarget.NO_USB_ID) { - target.setUsbVendorId(usbVendorId); - } - - target.setSkins(skins, defaultSkin); - - return target; - } - catch (Exception e) { - log.warning("Ignoring add-on '%1$s': error %2$s.", - addonDir.getName(), e.toString()); - } - - return null; - } - - /** - * Parses the add-on properties and decodes any error that occurs when loading an addon. - * - * @param addonDir the location of the addon directory. - * @param targetList The list of Android target that were already loaded from the SDK. - * @param log the ILogger object receiving warning/error from the parsing. Cannot be null. - * @return A pair with the property map and an error string. Both can be null but not at the - * same time. If a non-null error is present then the property map must be ignored. The error - * should be translatable as it might show up in the SdkManager UI. - */ - public static Pair<Map<String, String>, String> parseAddonProperties( - File addonDir, - IAndroidTarget[] targetList, - ILogger log) { - Map<String, String> propertyMap = null; - String error = null; - - FileWrapper addOnManifest = new FileWrapper(addonDir, SdkConstants.FN_MANIFEST_INI); - - do { - if (!addOnManifest.isFile()) { - error = String.format("File not found: %1$s", SdkConstants.FN_MANIFEST_INI); - break; - } - - propertyMap = ProjectProperties.parsePropertyFile(addOnManifest, log); - if (propertyMap == null) { - error = String.format("Failed to parse properties from %1$s", - SdkConstants.FN_MANIFEST_INI); - break; - } - - // look for some specific values in the map. - // we require name, vendor, and api - String name = propertyMap.get(ADDON_NAME); - if (name == null) { - error = addonManifestWarning(ADDON_NAME); - break; - } - - String vendor = propertyMap.get(ADDON_VENDOR); - if (vendor == null) { - error = addonManifestWarning(ADDON_VENDOR); - break; - } - - String api = propertyMap.get(ADDON_API); - PlatformTarget baseTarget = null; - if (api == null) { - error = addonManifestWarning(ADDON_API); - break; - } - - // Look for a platform that has a matching api level or codename. - for (IAndroidTarget target : targetList) { - if (target.isPlatform() && target.getVersion().equals(api)) { - baseTarget = (PlatformTarget)target; - break; - } - } - - if (baseTarget == null) { - error = String.format("Unable to find base platform with API level '%1$s'", api); - break; - } - - // get the add-on revision - String revision = propertyMap.get(ADDON_REVISION); - if (revision == null) { - revision = propertyMap.get(ADDON_REVISION_OLD); - } - if (revision != null) { - try { - Integer.parseInt(revision); - } catch (NumberFormatException e) { - // looks like revision does not parse to a number. - error = String.format("%1$s is not a valid number in %2$s.", - ADDON_REVISION, SdkConstants.FN_BUILD_PROP); - break; - } - } - - } while(false); - - return Pair.of(propertyMap, error); - } - - /** - * Converts a string representation of an hexadecimal ID into an int. - * @param value the string to convert. - * @return the int value, or {@link IAndroidTarget#NO_USB_ID} if the convertion failed. - */ - private static int convertId(String value) { - if (value != null && value.length() > 0) { - if (PATTERN_USB_IDS.matcher(value).matches()) { - String v = value.substring(2); - try { - return Integer.parseInt(v, 16); - } catch (NumberFormatException e) { - // this shouldn't happen since we check the pattern above, but this is safer. - // the method will return 0 below. - } - } - } - - return IAndroidTarget.NO_USB_ID; - } - - /** - * Prepares a warning about the addon being ignored due to a missing manifest value. - * This string will show up in the SdkManager UI. - * - * @param valueName The missing manifest value, for display. - */ - private static String addonManifestWarning(String valueName) { - return String.format("'%1$s' is missing from %2$s.", - valueName, SdkConstants.FN_MANIFEST_INI); - } - - /** - * Checks the given platform has all the required files, and returns true if they are all - * present. - * <p/>This checks the presence of the following files: android.jar, framework.aidl, aapt(.exe), - * aidl(.exe), dx(.bat), and dx.jar - * - * @param platform The folder containing the platform. - * @param log Logger. Cannot be null. - */ - private static boolean checkPlatformContent(File platform, ILogger log) { - for (String relativePath : sPlatformContentList) { - File f = new File(platform, relativePath); - if (!f.exists()) { - log.warning( - "Ignoring platform '%1$s': %2$s is missing.", //$NON-NLS-1$ - platform.getName(), relativePath); - return false; - } - } - return true; - } - - - - /** - * Parses the skin folder and builds the skin list. - * @param osPath The path of the skin root folder. - */ - private static String[] parseSkinFolder(String osPath) { - File skinRootFolder = new File(osPath); - - if (skinRootFolder.isDirectory()) { - ArrayList<String> skinList = new ArrayList<String>(); - - File[] files = skinRootFolder.listFiles(); - - for (File skinFolder : files) { - if (skinFolder.isDirectory()) { - // check for layout file - File layout = new File(skinFolder, SdkConstants.FN_SKIN_LAYOUT); - - if (layout.isFile()) { - // for now we don't parse the content of the layout and - // simply add the directory to the list. - skinList.add(skinFolder.getName()); - } - } - } - - return skinList.toArray(new String[skinList.size()]); - } - - return new String[0]; - } - - /** - * Initialize the sample folders for all known targets (platforms and addons). - * <p/> - * Samples used to be located at SDK/Target/samples. We then changed this to - * have a separate SDK/samples/samples-API directory. This parses either directories - * and sets the targets' sample path accordingly. - * - * @param log Logger. Cannot be null. - */ - private void initializeSamplePaths(ILogger log) { - File sampleFolder = new File(mOsSdkPath, SdkConstants.FD_SAMPLES); - if (sampleFolder.isDirectory()) { - File[] platforms = sampleFolder.listFiles(); - - for (File platform : platforms) { - if (platform.isDirectory()) { - // load the source.properties file and get an AndroidVersion object from it. - AndroidVersion version = getSamplesVersion(platform, log); - - if (version != null) { - // locate the platform matching this version - for (IAndroidTarget target : mTargets) { - if (target.isPlatform() && target.getVersion().equals(version)) { - ((PlatformTarget)target).setSamplesPath(platform.getAbsolutePath()); - break; - } - } - } - } - } - } - } - - /** - * Returns the {@link AndroidVersion} of the sample in the given folder. - * - * @param folder The sample's folder. - * @param log Logger for errors. Cannot be null. - * @return An {@link AndroidVersion} or null on error. - */ - private AndroidVersion getSamplesVersion(File folder, ILogger log) { - File sourceProp = new File(folder, SdkConstants.FN_SOURCE_PROP); - try { - Properties p = new Properties(); - FileInputStream fis = null; - try { - fis = new FileInputStream(sourceProp); - p.load(fis); - } finally { - if (fis != null) { - fis.close(); - } - } - - return new AndroidVersion(p); - } catch (FileNotFoundException e) { - log.warning("Ignoring sample '%1$s': does not contain %2$s.", //$NON-NLS-1$ - folder.getName(), SdkConstants.FN_SOURCE_PROP); - } catch (IOException e) { - log.warning("Ignoring sample '%1$s': failed reading %2$s.", //$NON-NLS-1$ - folder.getName(), SdkConstants.FN_SOURCE_PROP); - } catch (AndroidVersionException e) { - log.warning("Ignoring sample '%1$s': no android version found in %2$s.", //$NON-NLS-1$ - folder.getName(), SdkConstants.FN_SOURCE_PROP); - } - - return null; - } - - // ------------- - - public static class LayoutlibVersion implements Comparable<LayoutlibVersion> { - private final int mApi; - private final int mRevision; - - public static final int NOT_SPECIFIED = 0; - - public LayoutlibVersion(int api, int revision) { - mApi = api; - mRevision = revision; - } - - public int getApi() { - return mApi; - } - - public int getRevision() { - return mRevision; - } - - @Override - public int compareTo(LayoutlibVersion rhs) { - boolean useRev = this.mRevision > NOT_SPECIFIED && rhs.mRevision > NOT_SPECIFIED; - int lhsValue = (this.mApi << 16) + (useRev ? this.mRevision : 0); - int rhsValue = (rhs.mApi << 16) + (useRev ? rhs.mRevision : 0); - return lhsValue - rhsValue; - } - } - - // ------------- - - private static class DirInfo { - private final @NonNull File mDir; - private final long mDirModifiedTS; - private final long mPropsModifedTS; - private final long mPropsChecksum; - - /** - * Creates a new immutable {@link DirInfo}. - * - * @param dir The platform/addon directory of the target. It should be a directory. - */ - public DirInfo(@NonNull File dir) { - mDir = dir; - mDirModifiedTS = dir.lastModified(); - - // Capture some info about the source.properties file if it exists. - // We use propsModifedTS == 0 to mean there is no props file. - long propsChecksum = 0; - long propsModifedTS = 0; - File props = new File(dir, SdkConstants.FN_SOURCE_PROP); - if (props.isFile()) { - propsModifedTS = props.lastModified(); - propsChecksum = getFileChecksum(props); - } - mPropsModifedTS = propsModifedTS; - mPropsChecksum = propsChecksum; - } - - /** - * Checks whether the directory/source.properties attributes have changed. - * - * @return True if the directory modified timestampd or - * its source.property files have changed. - */ - public boolean hasChanged() { - // Does platform directory still exist? - if (!mDir.isDirectory()) { - return true; - } - // Has platform directory modified-timestamp changed? - if (mDirModifiedTS != mDir.lastModified()) { - return true; - } - - File props = new File(mDir, SdkConstants.FN_SOURCE_PROP); - - // The directory did not have a props file if target was null or - // if mPropsModifedTS is 0. - boolean hadProps = mPropsModifedTS != 0; - - // Was there a props file and it vanished, or there wasn't and there's one now? - if (hadProps != props.isFile()) { - return true; - } - - if (hadProps) { - // Has source.props file modified-timestampd changed? - if (mPropsModifedTS != props.lastModified()) { - return true; - } - // Had the content of source.props changed? - if (mPropsChecksum != getFileChecksum(props)) { - return true; - } - } - - return false; - } - - /** - * Computes an adler32 checksum (source.props are small files, so this - * should be OK with an acceptable collision rate.) - */ - private static long getFileChecksum(File file) { - FileInputStream fis = null; - try { - fis = new FileInputStream(file); - Adler32 a = new Adler32(); - byte[] buf = new byte[1024]; - int n; - while ((n = fis.read(buf)) > 0) { - a.update(buf, 0, n); - } - return a.getValue(); - } catch (Exception ignore) { - } finally { - try { - if (fis != null) { - fis.close(); - } - } catch(Exception ignore) {}; - } - return 0; - } - - /** Returns a visual representation of this object for debugging. */ - @Override - public String toString() { - String s = String.format("<DirInfo %1$s TS=%2$d", mDir, mDirModifiedTS); //$NON-NLS-1$ - if (mPropsModifedTS != 0) { - s += String.format(" | Props TS=%1$d, Chksum=%2$s", //$NON-NLS-1$ - mPropsModifedTS, mPropsChecksum); - } - return s + ">"; //$NON-NLS-1$ - } - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/SystemImage.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/SystemImage.java deleted file mode 100755 index afc11c7..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/SystemImage.java +++ /dev/null @@ -1,172 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib; - -import com.android.SdkConstants; -import com.android.sdklib.io.FileOp; - -import java.io.File; -import java.util.Locale; - - -/** - * Describes a system image as used by an {@link IAndroidTarget}. - * A system image has an installation path, a location type and an ABI type. - */ -public class SystemImage implements ISystemImage { - - public static final String ANDROID_PREFIX = "android-"; //$NON-NLS-1$ - - private final LocationType mLocationtype; - private final String mAbiType; - private final File mLocation; - - /** - * Creates a {@link SystemImage} description for an existing system image folder. - * - * @param location The location of an installed system image. - * @param locationType Where the system image folder is located for this ABI. - * @param abiType The ABI type. For example, one of {@link SdkConstants#ABI_ARMEABI}, - * {@link SdkConstants#ABI_ARMEABI_V7A}, {@link SdkConstants#ABI_INTEL_ATOM} or - * {@link SdkConstants#ABI_MIPS}. - */ - public SystemImage(File location, LocationType locationType, String abiType) { - mLocation = location; - mLocationtype = locationType; - mAbiType = abiType; - } - - /** - * Creates a {@link SystemImage} description for a non-existing system image folder. - * The actual location is computed based on the {@code locationtype}. - * - * @param sdkManager The current SDK manager. - * @param locationType Where the system image folder is located for this ABI. - * @param abiType The ABI type. For example, one of {@link SdkConstants#ABI_ARMEABI}, - * {@link SdkConstants#ABI_ARMEABI_V7A}, {@link SdkConstants#ABI_INTEL_ATOM} or - * {@link SdkConstants#ABI_MIPS}. - * @throws IllegalArgumentException if the {@code target} used for - * {@link ISystemImage.LocationType#IN_SYSTEM_IMAGE} is not a {@link PlatformTarget}. - */ - public SystemImage( - SdkManager sdkManager, - IAndroidTarget target, - LocationType locationType, - String abiType) { - mLocationtype = locationType; - mAbiType = abiType; - - File location = null; - switch(locationType) { - case IN_PLATFORM_LEGACY: - location = new File(target.getLocation(), SdkConstants.OS_IMAGES_FOLDER); - break; - - case IN_PLATFORM_SUBFOLDER: - location = FileOp.append(target.getLocation(), SdkConstants.OS_IMAGES_FOLDER, abiType); - break; - - case IN_SYSTEM_IMAGE: - if (!target.isPlatform()) { - throw new IllegalArgumentException( - "Add-ons do not support the system-image location type"); //$NON-NLS-1$ - } - - location = getCanonicalFolder(sdkManager.getLocation(), target.getVersion(), abiType); - break; - default: - // This is not supposed to happen unless LocationType is - // extended without adjusting this code. - assert false : "SystemImage used with an incorrect locationType"; //$NON-NLS-1$ - } - mLocation = location; - } - - /** - * Static helper method that returns the canonical path for a system-image that uses - * the {@link ISystemImage.LocationType#IN_SYSTEM_IMAGE} location type. - * <p/> - * Such an image is located in {@code SDK/system-images/android-N/abiType}. - * For this reason this method requires the root SDK as well as the platform and the ABI type. - * - * @param sdkOsPath The OS path to the SDK. - * @param platformVersion The platform version. - * @param abiType An optional ABI type. If null, the parent directory is returned. - * @return A file that represents the location of the canonical system-image folder - * for this configuration. - */ - public static File getCanonicalFolder( - String sdkOsPath, - AndroidVersion platformVersion, - String abiType) { - File root = FileOp.append( - sdkOsPath, - SdkConstants.FD_SYSTEM_IMAGES, - ANDROID_PREFIX + platformVersion.getApiString()); - if (abiType == null) { - return root; - } else { - return FileOp.append(root, abiType); - } - } - - /** Returns the actual location of an installed system image. */ - @Override - public File getLocation() { - return mLocation; - } - - /** Indicates the location strategy for this system image in the SDK. */ - @Override - public LocationType getLocationType() { - return mLocationtype; - } - - /** - * Returns the ABI type. For example, one of {@link SdkConstants#ABI_ARMEABI}, - * {@link SdkConstants#ABI_ARMEABI_V7A}, {@link SdkConstants#ABI_INTEL_ATOM} or - * {@link SdkConstants#ABI_MIPS}. - * Cannot be null nor empty. - */ - @Override - public String getAbiType() { - return mAbiType; - } - - @Override - public int compareTo(ISystemImage other) { - // Sort by ABI name only. This is what matters from a user point of view. - return this.getAbiType().compareToIgnoreCase(other.getAbiType()); - } - - /** - * Generates a string representation suitable for debug purposes. - * The string is not intended to be displayed to the user. - * - * {@inheritDoc} - */ - @Override - public String toString() { - return String.format("SystemImage ABI=%s, location %s='%s'", //$NON-NLS-1$ - mAbiType, - mLocationtype.toString().replace('_', ' ').toLowerCase(Locale.US), - mLocation - ); - } - - -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/build/ApkBuilder.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/build/ApkBuilder.java deleted file mode 100644 index d499feb..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/build/ApkBuilder.java +++ /dev/null @@ -1,1000 +0,0 @@ -/* - * Copyright (C) 2010 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.build; - -import com.android.SdkConstants; -import com.android.sdklib.internal.build.DebugKeyProvider; -import com.android.sdklib.internal.build.DebugKeyProvider.IKeyGenOutput; -import com.android.sdklib.internal.build.DebugKeyProvider.KeytoolException; -import com.android.sdklib.internal.build.SignedJarBuilder; -import com.android.sdklib.internal.build.SignedJarBuilder.IZipEntryFilter; - -import java.io.File; -import java.io.FileInputStream; -import java.io.FileNotFoundException; -import java.io.FileOutputStream; -import java.io.IOException; -import java.io.PrintStream; -import java.security.PrivateKey; -import java.security.cert.X509Certificate; -import java.text.DateFormat; -import java.util.ArrayList; -import java.util.Date; -import java.util.HashMap; -import java.util.List; -import java.util.regex.Pattern; - -/** - * Class making the final apk packaging. - * The inputs are: - * - packaged resources (output of aapt) - * - code file (ouput of dx) - * - Java resources coming from the project, its libraries, and its jar files - * - Native libraries from the project or its library. - * - */ -public final class ApkBuilder implements IArchiveBuilder { - - private final static Pattern PATTERN_NATIVELIB_EXT = Pattern.compile("^.+\\.so$", - Pattern.CASE_INSENSITIVE); - private final static Pattern PATTERN_BITCODELIB_EXT = Pattern.compile("^.+\\.bc$", - Pattern.CASE_INSENSITIVE); - - /** - * A No-op zip filter. It's used to detect conflicts. - * - */ - private final class NullZipFilter implements IZipEntryFilter { - private File mInputFile; - - void reset(File inputFile) { - mInputFile = inputFile; - } - - @Override - public boolean checkEntry(String archivePath) throws ZipAbortException { - verbosePrintln("=> %s", archivePath); - - File duplicate = checkFileForDuplicate(archivePath); - if (duplicate != null) { - throw new DuplicateFileException(archivePath, duplicate, mInputFile); - } else { - mAddedFiles.put(archivePath, mInputFile); - } - - return true; - } - } - - /** - * Custom {@link IZipEntryFilter} to filter out everything that is not a standard java - * resources, and also record whether the zip file contains native libraries. - * <p/>Used in {@link SignedJarBuilder#writeZip(java.io.InputStream, IZipEntryFilter)} when - * we only want the java resources from external jars. - */ - private final class JavaAndNativeResourceFilter implements IZipEntryFilter { - private final List<String> mNativeLibs = new ArrayList<String>(); - private boolean mNativeLibsConflict = false; - private File mInputFile; - - @Override - public boolean checkEntry(String archivePath) throws ZipAbortException { - // split the path into segments. - String[] segments = archivePath.split("/"); - - // empty path? skip to next entry. - if (segments.length == 0) { - return false; - } - - // Check each folders to make sure they should be included. - // Folders like CVS, .svn, etc.. should already have been excluded from the - // jar file, but we need to exclude some other folder (like /META-INF) so - // we check anyway. - for (int i = 0 ; i < segments.length - 1; i++) { - if (checkFolderForPackaging(segments[i]) == false) { - return false; - } - } - - // get the file name from the path - String fileName = segments[segments.length-1]; - - boolean check = checkFileForPackaging(fileName); - - // only do additional checks if the file passes the default checks. - if (check) { - verbosePrintln("=> %s", archivePath); - - File duplicate = checkFileForDuplicate(archivePath); - if (duplicate != null) { - throw new DuplicateFileException(archivePath, duplicate, mInputFile); - } else { - mAddedFiles.put(archivePath, mInputFile); - } - - if (archivePath.endsWith(".so") || archivePath.endsWith(".bc")) { - mNativeLibs.add(archivePath); - - // only .so located in lib/ will interfere with the installation - if (archivePath.startsWith(SdkConstants.FD_APK_NATIVE_LIBS + "/")) { - mNativeLibsConflict = true; - } - } else if (archivePath.endsWith(".jnilib")) { - mNativeLibs.add(archivePath); - } - } - - return check; - } - - List<String> getNativeLibs() { - return mNativeLibs; - } - - boolean getNativeLibsConflict() { - return mNativeLibsConflict; - } - - void reset(File inputFile) { - mInputFile = inputFile; - mNativeLibs.clear(); - mNativeLibsConflict = false; - } - } - - private File mApkFile; - private File mResFile; - private File mDexFile; - private PrintStream mVerboseStream; - private SignedJarBuilder mBuilder; - private boolean mDebugMode = false; - private boolean mIsSealed = false; - - private final NullZipFilter mNullFilter = new NullZipFilter(); - private final JavaAndNativeResourceFilter mFilter = new JavaAndNativeResourceFilter(); - private final HashMap<String, File> mAddedFiles = new HashMap<String, File>(); - - /** - * Status for the addition of a jar file resources into the APK. - * This indicates possible issues with native library inside the jar file. - */ - public interface JarStatus { - /** - * Returns the list of native libraries found in the jar file. - */ - List<String> getNativeLibs(); - - /** - * Returns whether some of those libraries were located in the location that Android - * expects its native libraries. - */ - boolean hasNativeLibsConflicts(); - - } - - /** Internal implementation of {@link JarStatus}. */ - private final static class JarStatusImpl implements JarStatus { - public final List<String> mLibs; - public final boolean mNativeLibsConflict; - - private JarStatusImpl(List<String> libs, boolean nativeLibsConflict) { - mLibs = libs; - mNativeLibsConflict = nativeLibsConflict; - } - - @Override - public List<String> getNativeLibs() { - return mLibs; - } - - @Override - public boolean hasNativeLibsConflicts() { - return mNativeLibsConflict; - } - } - - /** - * Signing information. - * - * Both the {@link PrivateKey} and the {@link X509Certificate} are guaranteed to be non-null. - * - */ - public final static class SigningInfo { - public final PrivateKey key; - public final X509Certificate certificate; - - private SigningInfo(PrivateKey key, X509Certificate certificate) { - if (key == null || certificate == null) { - throw new IllegalArgumentException("key and certificate cannot be null"); - } - this.key = key; - this.certificate = certificate; - } - } - - /** - * Returns the key and certificate from a given debug store. - * - * It is expected that the store password is 'android' and the key alias and password are - * 'androiddebugkey' and 'android' respectively. - * - * @param storeOsPath the OS path to the debug store. - * @param verboseStream an option {@link PrintStream} to display verbose information - * @return they key and certificate in a {@link SigningInfo} object or null. - * @throws ApkCreationException - */ - public static SigningInfo getDebugKey(String storeOsPath, final PrintStream verboseStream) - throws ApkCreationException { - try { - if (storeOsPath != null) { - File storeFile = new File(storeOsPath); - try { - checkInputFile(storeFile); - } catch (FileNotFoundException e) { - // ignore these since the debug store can be created on the fly anyway. - } - - // get the debug key - if (verboseStream != null) { - verboseStream.println(String.format("Using keystore: %s", storeOsPath)); - } - - IKeyGenOutput keygenOutput = null; - if (verboseStream != null) { - keygenOutput = new IKeyGenOutput() { - @Override - public void out(String message) { - verboseStream.println(message); - } - - @Override - public void err(String message) { - verboseStream.println(message); - } - }; - } - - DebugKeyProvider keyProvider = new DebugKeyProvider( - storeOsPath, null /*store type*/, keygenOutput); - - PrivateKey key = keyProvider.getDebugKey(); - X509Certificate certificate = (X509Certificate)keyProvider.getCertificate(); - - if (key == null) { - throw new ApkCreationException("Unable to get debug signature key"); - } - - // compare the certificate expiration date - if (certificate != null && certificate.getNotAfter().compareTo(new Date()) < 0) { - // TODO, regenerate a new one. - throw new ApkCreationException("Debug Certificate expired on " + - DateFormat.getInstance().format(certificate.getNotAfter())); - } - - return new SigningInfo(key, certificate); - } else { - return null; - } - } catch (KeytoolException e) { - if (e.getJavaHome() == null) { - throw new ApkCreationException(e.getMessage() + - "\nJAVA_HOME seems undefined, setting it will help locating keytool automatically\n" + - "You can also manually execute the following command\n:" + - e.getCommandLine(), e); - } else { - throw new ApkCreationException(e.getMessage() + - "\nJAVA_HOME is set to: " + e.getJavaHome() + - "\nUpdate it if necessary, or manually execute the following command:\n" + - e.getCommandLine(), e); - } - } catch (ApkCreationException e) { - throw e; - } catch (Exception e) { - throw new ApkCreationException(e); - } - } - - /** - * Creates a new instance. - * - * This creates a new builder that will create the specified output file, using the two - * mandatory given input files. - * - * An optional debug keystore can be provided. If set, it is expected that the store password - * is 'android' and the key alias and password are 'androiddebugkey' and 'android'. - * - * An optional {@link PrintStream} can also be provided for verbose output. If null, there will - * be no output. - * - * @param apkOsPath the OS path of the file to create. - * @param resOsPath the OS path of the packaged resource file. - * @param dexOsPath the OS path of the dex file. This can be null for apk with no code. - * @param verboseStream the stream to which verbose output should go. If null, verbose mode - * is not enabled. - * @throws ApkCreationException - */ - public ApkBuilder(String apkOsPath, String resOsPath, String dexOsPath, String storeOsPath, - PrintStream verboseStream) throws ApkCreationException { - this(new File(apkOsPath), - new File(resOsPath), - dexOsPath != null ? new File(dexOsPath) : null, - storeOsPath, - verboseStream); - } - - /** - * Creates a new instance. - * - * This creates a new builder that will create the specified output file, using the two - * mandatory given input files. - * - * Optional {@link PrivateKey} and {@link X509Certificate} can be provided to sign the APK. - * - * An optional {@link PrintStream} can also be provided for verbose output. If null, there will - * be no output. - * - * @param apkOsPath the OS path of the file to create. - * @param resOsPath the OS path of the packaged resource file. - * @param dexOsPath the OS path of the dex file. This can be null for apk with no code. - * @param key the private key used to sign the package. Can be null. - * @param certificate the certificate used to sign the package. Can be null. - * @param verboseStream the stream to which verbose output should go. If null, verbose mode - * is not enabled. - * @throws ApkCreationException - */ - public ApkBuilder(String apkOsPath, String resOsPath, String dexOsPath, PrivateKey key, - X509Certificate certificate, PrintStream verboseStream) throws ApkCreationException { - this(new File(apkOsPath), - new File(resOsPath), - dexOsPath != null ? new File(dexOsPath) : null, - key, certificate, - verboseStream); - } - - /** - * Creates a new instance. - * - * This creates a new builder that will create the specified output file, using the two - * mandatory given input files. - * - * An optional debug keystore can be provided. If set, it is expected that the store password - * is 'android' and the key alias and password are 'androiddebugkey' and 'android'. - * - * An optional {@link PrintStream} can also be provided for verbose output. If null, there will - * be no output. - * - * @param apkFile the file to create - * @param resFile the file representing the packaged resource file. - * @param dexFile the file representing the dex file. This can be null for apk with no code. - * @param debugStoreOsPath the OS path to the debug keystore, if needed or null. - * @param verboseStream the stream to which verbose output should go. If null, verbose mode - * is not enabled. - * @throws ApkCreationException - */ - public ApkBuilder(File apkFile, File resFile, File dexFile, String debugStoreOsPath, - final PrintStream verboseStream) throws ApkCreationException { - - SigningInfo info = getDebugKey(debugStoreOsPath, verboseStream); - if (info != null) { - init(apkFile, resFile, dexFile, info.key, info.certificate, verboseStream); - } else { - init(apkFile, resFile, dexFile, null /*key*/, null/*certificate*/, verboseStream); - } - } - - /** - * Creates a new instance. - * - * This creates a new builder that will create the specified output file, using the two - * mandatory given input files. - * - * Optional {@link PrivateKey} and {@link X509Certificate} can be provided to sign the APK. - * - * An optional {@link PrintStream} can also be provided for verbose output. If null, there will - * be no output. - * - * @param apkFile the file to create - * @param resFile the file representing the packaged resource file. - * @param dexFile the file representing the dex file. This can be null for apk with no code. - * @param key the private key used to sign the package. Can be null. - * @param certificate the certificate used to sign the package. Can be null. - * @param verboseStream the stream to which verbose output should go. If null, verbose mode - * is not enabled. - * @throws ApkCreationException - */ - public ApkBuilder(File apkFile, File resFile, File dexFile, PrivateKey key, - X509Certificate certificate, PrintStream verboseStream) throws ApkCreationException { - init(apkFile, resFile, dexFile, key, certificate, verboseStream); - } - - - /** - * Constructor init method. - * - * @see #ApkBuilder(File, File, File, String, PrintStream) - * @see #ApkBuilder(String, String, String, String, PrintStream) - * @see #ApkBuilder(File, File, File, PrivateKey, X509Certificate, PrintStream) - */ - private void init(File apkFile, File resFile, File dexFile, PrivateKey key, - X509Certificate certificate, PrintStream verboseStream) throws ApkCreationException { - - try { - checkOutputFile(mApkFile = apkFile); - checkInputFile(mResFile = resFile); - if (dexFile != null) { - checkInputFile(mDexFile = dexFile); - } else { - mDexFile = null; - } - mVerboseStream = verboseStream; - - mBuilder = new SignedJarBuilder( - new FileOutputStream(mApkFile, false /* append */), key, - certificate); - - verbosePrintln("Packaging %s", mApkFile.getName()); - - // add the resources - addZipFile(mResFile); - - // add the class dex file at the root of the apk - if (mDexFile != null) { - addFile(mDexFile, SdkConstants.FN_APK_CLASSES_DEX); - } - - } catch (ApkCreationException e) { - if (mBuilder != null) { - mBuilder.cleanUp(); - } - throw e; - } catch (Exception e) { - if (mBuilder != null) { - mBuilder.cleanUp(); - } - throw new ApkCreationException(e); - } - } - - /** - * Sets the debug mode. In debug mode, when native libraries are present, the packaging - * will also include one or more copies of gdbserver in the final APK file. - * - * These are used for debugging native code, to ensure that gdbserver is accessible to the - * application. - * - * There will be one version of gdbserver for each ABI supported by the application. - * - * the gbdserver files are placed in the libs/abi/ folders automatically by the NDK. - * - * @param debugMode the debug mode flag. - */ - public void setDebugMode(boolean debugMode) { - mDebugMode = debugMode; - } - - /** - * Adds a file to the APK at a given path - * @param file the file to add - * @param archivePath the path of the file inside the APK archive. - * @throws ApkCreationException if an error occurred - * @throws SealedApkException if the APK is already sealed. - * @throws DuplicateFileException if a file conflicts with another already added to the APK - * at the same location inside the APK archive. - */ - @Override - public void addFile(File file, String archivePath) throws ApkCreationException, - SealedApkException, DuplicateFileException { - if (mIsSealed) { - throw new SealedApkException("APK is already sealed"); - } - - try { - doAddFile(file, archivePath); - } catch (DuplicateFileException e) { - mBuilder.cleanUp(); - throw e; - } catch (Exception e) { - mBuilder.cleanUp(); - throw new ApkCreationException(e, "Failed to add %s", file); - } - } - - /** - * Adds the content from a zip file. - * All file keep the same path inside the archive. - * @param zipFile the zip File. - * @throws ApkCreationException if an error occurred - * @throws SealedApkException if the APK is already sealed. - * @throws DuplicateFileException if a file conflicts with another already added to the APK - * at the same location inside the APK archive. - */ - public void addZipFile(File zipFile) throws ApkCreationException, SealedApkException, - DuplicateFileException { - if (mIsSealed) { - throw new SealedApkException("APK is already sealed"); - } - - try { - verbosePrintln("%s:", zipFile); - - // reset the filter with this input. - mNullFilter.reset(zipFile); - - // ask the builder to add the content of the file. - FileInputStream fis = new FileInputStream(zipFile); - mBuilder.writeZip(fis, mNullFilter); - fis.close(); - } catch (DuplicateFileException e) { - mBuilder.cleanUp(); - throw e; - } catch (Exception e) { - mBuilder.cleanUp(); - throw new ApkCreationException(e, "Failed to add %s", zipFile); - } - } - - /** - * Adds the resources from a jar file. - * @param jarFile the jar File. - * @return a {@link JarStatus} object indicating if native libraries where found in - * the jar file. - * @throws ApkCreationException if an error occurred - * @throws SealedApkException if the APK is already sealed. - * @throws DuplicateFileException if a file conflicts with another already added to the APK - * at the same location inside the APK archive. - */ - public JarStatus addResourcesFromJar(File jarFile) throws ApkCreationException, - SealedApkException, DuplicateFileException { - if (mIsSealed) { - throw new SealedApkException("APK is already sealed"); - } - - try { - verbosePrintln("%s:", jarFile); - - // reset the filter with this input. - mFilter.reset(jarFile); - - // ask the builder to add the content of the file, filtered to only let through - // the java resources. - FileInputStream fis = new FileInputStream(jarFile); - mBuilder.writeZip(fis, mFilter); - fis.close(); - - // check if native libraries were found in the external library. This should - // constitutes an error or warning depending on if they are in lib/ - return new JarStatusImpl(mFilter.getNativeLibs(), mFilter.getNativeLibsConflict()); - } catch (DuplicateFileException e) { - mBuilder.cleanUp(); - throw e; - } catch (Exception e) { - mBuilder.cleanUp(); - throw new ApkCreationException(e, "Failed to add %s", jarFile); - } - } - - /** - * Adds the resources from a source folder. - * @param sourceFolder the source folder. - * @throws ApkCreationException if an error occurred - * @throws SealedApkException if the APK is already sealed. - * @throws DuplicateFileException if a file conflicts with another already added to the APK - * at the same location inside the APK archive. - */ - public void addSourceFolder(File sourceFolder) throws ApkCreationException, SealedApkException, - DuplicateFileException { - if (mIsSealed) { - throw new SealedApkException("APK is already sealed"); - } - - addSourceFolder(this, sourceFolder); - } - - /** - * Adds the resources from a source folder to a given {@link IArchiveBuilder} - * @param sourceFolder the source folder. - * @throws ApkCreationException if an error occurred - * @throws DuplicateFileException if a file conflicts with another already added to the APK - * at the same location inside the APK archive. - */ - public static void addSourceFolder(IArchiveBuilder builder, File sourceFolder) - throws ApkCreationException, DuplicateFileException { - if (sourceFolder.isDirectory()) { - try { - // file is a directory, process its content. - File[] files = sourceFolder.listFiles(); - for (File file : files) { - processFileForResource(builder, file, null); - } - } catch (DuplicateFileException e) { - throw e; - } catch (Exception e) { - throw new ApkCreationException(e, "Failed to add %s", sourceFolder); - } - } else { - // not a directory? check if it's a file or doesn't exist - if (sourceFolder.exists()) { - throw new ApkCreationException("%s is not a folder", sourceFolder); - } else { - throw new ApkCreationException("%s does not exist", sourceFolder); - } - } - } - - /** - * Adds the native libraries from the top native folder. - * The content of this folder must be the various ABI folders. - * - * This may or may not copy gdbserver into the apk based on whether the debug mode is set. - * - * @param nativeFolder the native folder. - * - * @throws ApkCreationException if an error occurred - * @throws SealedApkException if the APK is already sealed. - * @throws DuplicateFileException if a file conflicts with another already added to the APK - * at the same location inside the APK archive. - * - * @see #setDebugMode(boolean) - */ - public void addNativeLibraries(File nativeFolder) - throws ApkCreationException, SealedApkException, DuplicateFileException { - if (mIsSealed) { - throw new SealedApkException("APK is already sealed"); - } - - if (nativeFolder.isDirectory() == false) { - // not a directory? check if it's a file or doesn't exist - if (nativeFolder.exists()) { - throw new ApkCreationException("%s is not a folder", nativeFolder); - } else { - throw new ApkCreationException("%s does not exist", nativeFolder); - } - } - - File[] abiList = nativeFolder.listFiles(); - - verbosePrintln("Native folder: %s", nativeFolder); - - if (abiList != null) { - for (File abi : abiList) { - if (abi.isDirectory()) { // ignore files - - File[] libs = abi.listFiles(); - if (libs != null) { - for (File lib : libs) { - // only consider files that are .so or, if in debug mode, that - // are gdbserver executables - if (lib.isFile() && - (PATTERN_NATIVELIB_EXT.matcher(lib.getName()).matches() || - PATTERN_BITCODELIB_EXT.matcher(lib.getName()).matches() || - (mDebugMode && - SdkConstants.FN_GDBSERVER.equals( - lib.getName())))) { - String path = - SdkConstants.FD_APK_NATIVE_LIBS + "/" + - abi.getName() + "/" + lib.getName(); - - try { - doAddFile(lib, path); - } catch (IOException e) { - mBuilder.cleanUp(); - throw new ApkCreationException(e, "Failed to add %s", lib); - } - } - } - } - } - } - } - } - - public void addNativeLibraries(List<FileEntry> entries) throws SealedApkException, - DuplicateFileException, ApkCreationException { - if (mIsSealed) { - throw new SealedApkException("APK is already sealed"); - } - - for (FileEntry entry : entries) { - try { - doAddFile(entry.mFile, entry.mPath); - } catch (IOException e) { - mBuilder.cleanUp(); - throw new ApkCreationException(e, "Failed to add %s", entry.mFile); - } - } - } - - public static final class FileEntry { - public final File mFile; - public final String mPath; - - FileEntry(File file, String path) { - mFile = file; - mPath = path; - } - } - - public static List<FileEntry> getNativeFiles(File nativeFolder, boolean debugMode) - throws ApkCreationException { - - if (nativeFolder.isDirectory() == false) { - // not a directory? check if it's a file or doesn't exist - if (nativeFolder.exists()) { - throw new ApkCreationException("%s is not a folder", nativeFolder); - } else { - throw new ApkCreationException("%s does not exist", nativeFolder); - } - } - - List<FileEntry> files = new ArrayList<FileEntry>(); - - File[] abiList = nativeFolder.listFiles(); - - if (abiList != null) { - for (File abi : abiList) { - if (abi.isDirectory()) { // ignore files - - File[] libs = abi.listFiles(); - if (libs != null) { - for (File lib : libs) { - // only consider files that are .so or, if in debug mode, that - // are gdbserver executables - if (lib.isFile() && - (PATTERN_NATIVELIB_EXT.matcher(lib.getName()).matches() || - PATTERN_BITCODELIB_EXT.matcher(lib.getName()).matches() || - (debugMode && - SdkConstants.FN_GDBSERVER.equals( - lib.getName())))) { - String path = - SdkConstants.FD_APK_NATIVE_LIBS + "/" + - abi.getName() + "/" + lib.getName(); - - files.add(new FileEntry(lib, path)); - } - } - } - } - } - } - - return files; - } - - - - /** - * Seals the APK, and signs it if necessary. - * @throws ApkCreationException - * @throws ApkCreationException if an error occurred - * @throws SealedApkException if the APK is already sealed. - */ - public void sealApk() throws ApkCreationException, SealedApkException { - if (mIsSealed) { - throw new SealedApkException("APK is already sealed"); - } - - // close and sign the application package. - try { - mBuilder.close(); - mIsSealed = true; - } catch (Exception e) { - throw new ApkCreationException(e, "Failed to seal APK"); - } finally { - mBuilder.cleanUp(); - } - } - - /** - * Output a given message if the verbose mode is enabled. - * @param format the format string for {@link String#format(String, Object...)} - * @param args the string arguments - */ - private void verbosePrintln(String format, Object... args) { - if (mVerboseStream != null) { - mVerboseStream.println(String.format(format, args)); - } - } - - private void doAddFile(File file, String archivePath) throws DuplicateFileException, - IOException { - verbosePrintln("%1$s => %2$s", file, archivePath); - - File duplicate = checkFileForDuplicate(archivePath); - if (duplicate != null) { - throw new DuplicateFileException(archivePath, duplicate, file); - } - - mAddedFiles.put(archivePath, file); - mBuilder.writeFile(file, archivePath); - } - - /** - * Processes a {@link File} that could be an APK {@link File}, or a folder containing - * java resources. - * - * @param file the {@link File} to process. - * @param path the relative path of this file to the source folder. - * Can be <code>null</code> to identify a root file. - * @throws IOException - * @throws DuplicateFileException if a file conflicts with another already added - * to the APK at the same location inside the APK archive. - * @throws SealedApkException if the APK is already sealed. - * @throws ApkCreationException if an error occurred - */ - private static void processFileForResource(IArchiveBuilder builder, File file, String path) - throws IOException, DuplicateFileException, ApkCreationException, SealedApkException { - if (file.isDirectory()) { - // a directory? we check it - if (checkFolderForPackaging(file.getName())) { - // if it's valid, we append its name to the current path. - if (path == null) { - path = file.getName(); - } else { - path = path + "/" + file.getName(); - } - - // and process its content. - File[] files = file.listFiles(); - for (File contentFile : files) { - processFileForResource(builder, contentFile, path); - } - } - } else { - // a file? we check it to make sure it should be added - if (checkFileForPackaging(file.getName())) { - // we append its name to the current path - if (path == null) { - path = file.getName(); - } else { - path = path + "/" + file.getName(); - } - - // and add it to the apk - builder.addFile(file, path); - } - } - } - - /** - * Checks if the given path in the APK archive has not already been used and if it has been, - * then returns a {@link File} object for the source of the duplicate - * @param archivePath the archive path to test. - * @return A File object of either a file at the same location or an archive that contains a - * file that was put at the same location. - */ - private File checkFileForDuplicate(String archivePath) { - return mAddedFiles.get(archivePath); - } - - /** - * Checks an output {@link File} object. - * This checks the following: - * - the file is not an existing directory. - * - if the file exists, that it can be modified. - * - if it doesn't exists, that a new file can be created. - * @param file the File to check - * @throws ApkCreationException If the check fails - */ - private void checkOutputFile(File file) throws ApkCreationException { - if (file.isDirectory()) { - throw new ApkCreationException("%s is a directory!", file); - } - - if (file.exists()) { // will be a file in this case. - if (file.canWrite() == false) { - throw new ApkCreationException("Cannot write %s", file); - } - } else { - try { - if (file.createNewFile() == false) { - throw new ApkCreationException("Failed to create %s", file); - } - } catch (IOException e) { - throw new ApkCreationException( - "Failed to create '%1$ss': %2$s", file, e.getMessage()); - } - } - } - - /** - * Checks an input {@link File} object. - * This checks the following: - * - the file is not an existing directory. - * - that the file exists (if <var>throwIfDoesntExist</var> is <code>false</code>) and can - * be read. - * @param file the File to check - * @throws FileNotFoundException if the file is not here. - * @throws ApkCreationException If the file is a folder or a file that cannot be read. - */ - private static void checkInputFile(File file) throws FileNotFoundException, ApkCreationException { - if (file.isDirectory()) { - throw new ApkCreationException("%s is a directory!", file); - } - - if (file.exists()) { - if (file.canRead() == false) { - throw new ApkCreationException("Cannot read %s", file); - } - } else { - throw new FileNotFoundException(String.format("%s does not exist", file)); - } - } - - public static String getDebugKeystore() throws ApkCreationException { - try { - return DebugKeyProvider.getDefaultKeyStoreOsPath(); - } catch (Exception e) { - throw new ApkCreationException(e, e.getMessage()); - } - } - - /** - * Checks whether a folder and its content is valid for packaging into the .apk as - * standard Java resource. - * @param folderName the name of the folder. - */ - public static boolean checkFolderForPackaging(String folderName) { - return folderName.equalsIgnoreCase("CVS") == false && - folderName.equalsIgnoreCase(".svn") == false && - folderName.equalsIgnoreCase("SCCS") == false && - folderName.equalsIgnoreCase("META-INF") == false && - folderName.startsWith("_") == false; - } - - /** - * Checks a file to make sure it should be packaged as standard resources. - * @param fileName the name of the file (including extension) - * @return true if the file should be packaged as standard java resources. - */ - public static boolean checkFileForPackaging(String fileName) { - String[] fileSegments = fileName.split("\\."); - String fileExt = ""; - if (fileSegments.length > 1) { - fileExt = fileSegments[fileSegments.length-1]; - } - - return checkFileForPackaging(fileName, fileExt); - } - - /** - * Checks a file to make sure it should be packaged as standard resources. - * @param fileName the name of the file (including extension) - * @param extension the extension of the file (excluding '.') - * @return true if the file should be packaged as standard java resources. - */ - public static boolean checkFileForPackaging(String fileName, String extension) { - // ignore hidden files and backup files - if (fileName.charAt(0) == '.' || fileName.charAt(fileName.length()-1) == '~') { - return false; - } - - return "aidl".equalsIgnoreCase(extension) == false && // Aidl files - "rs".equalsIgnoreCase(extension) == false && // RenderScript files - "rsh".equalsIgnoreCase(extension) == false && // RenderScript header files - "d".equalsIgnoreCase(extension) == false && // Dependency files - "java".equalsIgnoreCase(extension) == false && // Java files - "scala".equalsIgnoreCase(extension) == false && // Scala files - "class".equalsIgnoreCase(extension) == false && // Java class files - "scc".equalsIgnoreCase(extension) == false && // VisualSourceSafe - "swp".equalsIgnoreCase(extension) == false && // vi swap file - "thumbs.db".equalsIgnoreCase(fileName) == false && // image index file - "picasa.ini".equalsIgnoreCase(fileName) == false && // image index file - "package.html".equalsIgnoreCase(fileName) == false && // Javadoc - "overview.html".equalsIgnoreCase(fileName) == false; // Javadoc - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/build/ApkBuilderMain.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/build/ApkBuilderMain.java deleted file mode 100644 index 805b74a..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/build/ApkBuilderMain.java +++ /dev/null @@ -1,228 +0,0 @@ -/* - * Copyright (C) 2008 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.build; - - -import java.io.File; -import java.io.FilenameFilter; -import java.util.ArrayList; -import java.util.regex.Pattern; - - -/** - * Command line APK builder with signing support. - */ -public final class ApkBuilderMain { - - private final static Pattern PATTERN_JAR_EXT = Pattern.compile("^.+\\.jar$", - Pattern.CASE_INSENSITIVE); - - /** - * Main method. This is meant to be called from the command line through an exec. - * <p/>WARNING: this will call {@link System#exit(int)} if anything goes wrong. - * @param args command line arguments. - */ - public static void main(String[] args) { - if (args.length < 1) { - printUsageAndQuit(); - } - - System.err.println("\nTHIS TOOL IS DEPRECATED. See --help for more information.\n"); - - try { - File outApk = new File(args[0]); - - File dexFile = null; - ArrayList<File> zipArchives = new ArrayList<File>(); - ArrayList<File> sourceFolders = new ArrayList<File>(); - ArrayList<File> jarFiles = new ArrayList<File>(); - ArrayList<File> nativeFolders = new ArrayList<File>(); - - boolean verbose = false; - boolean signed = true; - boolean debug = false; - - int index = 1; - do { - String argument = args[index++]; - - if ("-v".equals(argument)) { - verbose = true; - - } else if ("-d".equals(argument)) { - debug = true; - - } else if ("-u".equals(argument)) { - signed = false; - - } else if ("-z".equals(argument)) { - // quick check on the next argument. - if (index == args.length) { - printAndExit("Missing value for -z"); - } - - zipArchives.add(new File(args[index++])); - } else if ("-f". equals(argument)) { - if (dexFile != null) { - // can't have more than one dex file. - printAndExit("Can't have more than one dex file (-f)"); - } - // quick check on the next argument. - if (index == args.length) { - printAndExit("Missing value for -f"); - } - - dexFile = new File(args[index++]); - } else if ("-rf". equals(argument)) { - // quick check on the next argument. - if (index == args.length) { - printAndExit("Missing value for -rf"); - } - - sourceFolders.add(new File(args[index++])); - } else if ("-rj". equals(argument)) { - // quick check on the next argument. - if (index == args.length) { - printAndExit("Missing value for -rj"); - } - - jarFiles.add(new File(args[index++])); - } else if ("-nf".equals(argument)) { - // quick check on the next argument. - if (index == args.length) { - printAndExit("Missing value for -nf"); - } - - nativeFolders.add(new File(args[index++])); - } else if ("-storetype".equals(argument)) { - // quick check on the next argument. - if (index == args.length) { - printAndExit("Missing value for -storetype"); - } - - // FIXME - } else { - printAndExit("Unknown argument: " + argument); - } - } while (index < args.length); - - if (zipArchives.size() == 0) { - printAndExit("No zip archive, there must be one for the resources"); - } - - // create the builder with the basic files. - ApkBuilder builder = new ApkBuilder(outApk, zipArchives.get(0), dexFile, - signed ? ApkBuilder.getDebugKeystore() : null, - verbose ? System.out : null); - builder.setDebugMode(debug); - - // add the rest of the files. - // first zip Archive was used in the constructor. - for (int i = 1 ; i < zipArchives.size() ; i++) { - builder.addZipFile(zipArchives.get(i)); - } - - for (File sourceFolder : sourceFolders) { - builder.addSourceFolder(sourceFolder); - } - - for (File jarFile : jarFiles) { - if (jarFile.isDirectory()) { - String[] filenames = jarFile.list(new FilenameFilter() { - @Override - public boolean accept(File dir, String name) { - return PATTERN_JAR_EXT.matcher(name).matches(); - } - }); - - for (String filename : filenames) { - builder.addResourcesFromJar(new File(jarFile, filename)); - } - } else { - builder.addResourcesFromJar(jarFile); - } - } - - for (File nativeFolder : nativeFolders) { - builder.addNativeLibraries(nativeFolder); - } - - // seal the apk - builder.sealApk(); - - - } catch (ApkCreationException e) { - printAndExit(e.getMessage()); - } catch (DuplicateFileException e) { - printAndExit(String.format( - "Found duplicate file for APK: %1$s\nOrigin 1: %2$s\nOrigin 2: %3$s", - e.getArchivePath(), e.getFile1(), e.getFile2())); - } catch (SealedApkException e) { - printAndExit(e.getMessage()); - } catch (Exception e) { - e.printStackTrace(); - } - } - - private static void printUsageAndQuit() { - // 80 cols marker: 01234567890123456789012345678901234567890123456789012345678901234567890123456789 - System.err.println("\n\n<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<"); - System.err.println("THIS TOOL IS DEPRECATED and may stop working at any time!\n"); - System.err.println("If you wish to use apkbuilder for a custom build system, please look at the"); - System.err.println("com.android.sdklib.build.ApkBuilder which provides support for"); - System.err.println("recent build improvements including library projects."); - System.err.println(">>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>\n\n"); - System.err.println("A command line tool to package an Android application from various sources."); - System.err.println("Usage: apkbuilder <out archive> [-v][-u][-storetype STORE_TYPE] [-z inputzip]"); - System.err.println(" [-f inputfile] [-rf input-folder] [-rj -input-path]"); - System.err.println(""); - System.err.println(" -v Verbose."); - System.err.println(" -d Debug Mode: Includes debug files in the APK file."); - System.err.println(" -u Creates an unsigned package."); - System.err.println(" -storetype Forces the KeyStore type. If ommited the default is used."); - System.err.println(""); - System.err.println(" -z Followed by the path to a zip archive."); - System.err.println(" Adds the content of the application package."); - System.err.println(""); - System.err.println(" -f Followed by the path to a file."); - System.err.println(" Adds the file to the application package."); - System.err.println(""); - System.err.println(" -rf Followed by the path to a source folder."); - System.err.println(" Adds the java resources found in that folder to the application"); - System.err.println(" package, while keeping their path relative to the source folder."); - System.err.println(""); - System.err.println(" -rj Followed by the path to a jar file or a folder containing"); - System.err.println(" jar files."); - System.err.println(" Adds the java resources found in the jar file(s) to the application"); - System.err.println(" package."); - System.err.println(""); - System.err.println(" -nf Followed by the root folder containing native libraries to"); - System.err.println(" include in the application package."); - - System.exit(1); - } - - private static void printAndExit(String... messages) { - for (String message : messages) { - System.err.println(message); - } - System.exit(1); - } - - private ApkBuilderMain() { - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/build/ApkCreationException.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/build/ApkCreationException.java deleted file mode 100644 index 2379915..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/build/ApkCreationException.java +++ /dev/null @@ -1,36 +0,0 @@ -/* - * Copyright (C) 2010 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.build; - -/** - * An exception thrown during packaging of an APK file. - */ -public final class ApkCreationException extends Exception { - private static final long serialVersionUID = 1L; - - public ApkCreationException(String format, Object... args) { - super(String.format(format, args)); - } - - public ApkCreationException(Throwable cause, String format, Object... args) { - super(String.format(format, args), cause); - } - - public ApkCreationException(Throwable cause) { - super(cause); - } -}
\ No newline at end of file diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/build/DuplicateFileException.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/build/DuplicateFileException.java deleted file mode 100644 index ba53ba3..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/build/DuplicateFileException.java +++ /dev/null @@ -1,55 +0,0 @@ -/* - * Copyright (C) 2010 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.build; - -import com.android.sdklib.internal.build.SignedJarBuilder.IZipEntryFilter.ZipAbortException; - -import java.io.File; - -/** - * An exception thrown during packaging of an APK file. - */ -public final class DuplicateFileException extends ZipAbortException { - private static final long serialVersionUID = 1L; - private final String mArchivePath; - private final File mFile1; - private final File mFile2; - - public DuplicateFileException(String archivePath, File file1, File file2) { - super(); - mArchivePath = archivePath; - mFile1 = file1; - mFile2 = file2; - } - - public String getArchivePath() { - return mArchivePath; - } - - public File getFile1() { - return mFile1; - } - - public File getFile2() { - return mFile2; - } - - @Override - public String getMessage() { - return "Duplicate files at the same path inside the APK"; - } -}
\ No newline at end of file diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/build/IArchiveBuilder.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/build/IArchiveBuilder.java deleted file mode 100644 index e2230e9..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/build/IArchiveBuilder.java +++ /dev/null @@ -1,35 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.build; - -import java.io.File; - -public interface IArchiveBuilder { - - /** - * Adds a file to the archive at a given path - * @param file the file to add - * @param archivePath the path of the file inside the APK archive. - * @throws ApkCreationException if an error occurred - * @throws SealedApkException if the APK is already sealed. - * @throws DuplicateFileException if a file conflicts with another already added to the APK - * at the same location inside the APK archive. - */ - void addFile(File file, String archivePath) throws ApkCreationException, - SealedApkException, DuplicateFileException; - -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/build/JarListSanitizer.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/build/JarListSanitizer.java deleted file mode 100644 index 4d1dcdb..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/build/JarListSanitizer.java +++ /dev/null @@ -1,479 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.build; - -import java.io.BufferedReader; -import java.io.File; -import java.io.FileInputStream; -import java.io.FileNotFoundException; -import java.io.FileOutputStream; -import java.io.IOException; -import java.io.InputStreamReader; -import java.io.OutputStreamWriter; -import java.io.PrintStream; -import java.io.UnsupportedEncodingException; -import java.security.MessageDigest; -import java.util.ArrayList; -import java.util.Collection; -import java.util.Formatter; -import java.util.HashMap; -import java.util.List; -import java.util.Map; -import java.util.Map.Entry; -import java.util.regex.Matcher; -import java.util.regex.Pattern; - -/** - * A Class to handle a list of jar files, finding and removing duplicates. - * - * Right now duplicates are based on: - * - same filename - * - same length - * - same content: using sha1 comparison. - * - * The length/sha1 are kept in a cache and only updated if the library is changed. - */ -public class JarListSanitizer { - - private static final byte[] sBuffer = new byte[4096]; - private static final String CACHE_FILENAME = "jarlist.cache"; - private static final Pattern READ_PATTERN = Pattern.compile("^(\\d+) (\\d+) ([0-9a-f]+) (.+)$"); - - /** - * Simple class holding the data regarding a jar dependency. - * - */ - private static final class JarEntity { - private final File mFile; - private final long mLastModified; - private long mLength; - private String mSha1; - - /** - * Creates an entity from cached data. - * @param path the file path - * @param lastModified when it was last modified - * @param length its length - * @param sha1 its sha1 - */ - private JarEntity(String path, long lastModified, long length, String sha1) { - mFile = new File(path); - mLastModified = lastModified; - mLength = length; - mSha1 = sha1; - } - - /** - * Creates an entity from a {@link File}. - * @param file the file. - */ - private JarEntity(File file) { - mFile = file; - mLastModified = file.lastModified(); - mLength = file.length(); - } - - /** - * Checks whether the {@link File#lastModified()} matches the cached value. If not, length - * is updated and the sha1 is reset (but not recomputed, this is done on demand). - * @return return whether the file was changed. - */ - private boolean checkValidity() { - if (mLastModified != mFile.lastModified()) { - mLength = mFile.length(); - mSha1 = null; - return true; - } - - return false; - } - - private File getFile() { - return mFile; - } - - private long getLastModified() { - return mLastModified; - } - - private long getLength() { - return mLength; - } - - /** - * Returns the file's sha1, computing it if necessary. - * @return the sha1 - * @throws Sha1Exception - */ - private String getSha1() throws Sha1Exception { - if (mSha1 == null) { - mSha1 = JarListSanitizer.getSha1(mFile); - } - return mSha1; - } - - private boolean hasSha1() { - return mSha1 != null; - } - } - - /** - * Exception used to indicate the sanitized list of jar dependency cannot be computed due - * to inconsistency in duplicate jar files. - */ - public static final class DifferentLibException extends Exception { - private static final long serialVersionUID = 1L; - private final String[] mDetails; - - public DifferentLibException(String message, String[] details) { - super(message); - mDetails = details; - } - - public String[] getDetails() { - return mDetails; - } - } - - /** - * Exception to indicate a failure to check a jar file's content. - */ - public static final class Sha1Exception extends Exception { - private static final long serialVersionUID = 1L; - private final File mJarFile; - - public Sha1Exception(File jarFile, Throwable cause) { - super(cause); - mJarFile = jarFile; - } - - public File getJarFile() { - return mJarFile; - } - } - - private final File mOut; - private final PrintStream mOutStream; - - /** - * Creates a sanitizer. - * @param out the project output where the cache is to be stored. - */ - public JarListSanitizer(File out) { - mOut = out; - mOutStream = System.out; - } - - public JarListSanitizer(File out, PrintStream outStream) { - mOut = out; - mOutStream = outStream; - } - - /** - * Sanitize a given list of files - * @param files the list to sanitize - * @return a new list containing no duplicates. - * @throws DifferentLibException - * @throws Sha1Exception - */ - public List<File> sanitize(Collection<File> files) throws DifferentLibException, Sha1Exception { - List<File> results = new ArrayList<File>(); - - // get the cache list. - Map<String, JarEntity> jarList = getCachedJarList(); - - boolean updateJarList = false; - - // clean it up of removed files. - // use results as a temp storage to store the files to remove as we go through the map. - for (JarEntity entity : jarList.values()) { - if (entity.getFile().exists() == false) { - results.add(entity.getFile()); - } - } - - // the actual clean up. - if (results.size() > 0) { - for (File f : results) { - jarList.remove(f.getAbsolutePath()); - } - - results.clear(); - updateJarList = true; - } - - Map<String, List<JarEntity>> nameMap = new HashMap<String, List<JarEntity>>(); - - // update the current jar list if needed, while building a 2ndary map based on - // filename only. - for (File file : files) { - String path = file.getAbsolutePath(); - JarEntity entity = jarList.get(path); - - if (entity == null) { - entity = new JarEntity(file); - jarList.put(path, entity); - updateJarList = true; - } else { - updateJarList |= entity.checkValidity(); - } - - String filename = file.getName(); - List<JarEntity> nameList = nameMap.get(filename); - if (nameList == null) { - nameList = new ArrayList<JarEntity>(); - nameMap.put(filename, nameList); - } - nameList.add(entity); - } - - try { - // now look for dups. Each name list can have more than one file but they must - // have the same size/sha1 - for (Entry<String, List<JarEntity>> entry : nameMap.entrySet()) { - List<JarEntity> list = entry.getValue(); - checkEntities(entry.getKey(), list); - - // if we are here, there's no issue. Add the first of the list to the results. - results.add(list.get(0).getFile()); - } - - // special case for android-support-v4/13 - checkSupportLibs(nameMap, results); - } finally { - if (updateJarList) { - writeJarList(nameMap); - } - } - - return results; - } - - /** - * Checks whether a given list of duplicates can be replaced by a single one. - * @param filename the filename of the files - * @param list the list of dup files - * @throws DifferentLibException - * @throws Sha1Exception - */ - private void checkEntities(String filename, List<JarEntity> list) - throws DifferentLibException, Sha1Exception { - if (list.size() == 1) { - return; - } - - JarEntity baseEntity = list.get(0); - long baseLength = baseEntity.getLength(); - String baseSha1 = baseEntity.getSha1(); - - final int count = list.size(); - for (int i = 1; i < count ; i++) { - JarEntity entity = list.get(i); - if (entity.getLength() != baseLength || entity.getSha1().equals(baseSha1) == false) { - throw new DifferentLibException("Jar mismatch! Fix your dependencies", - getEntityDetails(filename, list)); - } - - } - } - - /** - * Checks for present of both support libraries in v4 and v13. If both are detected, - * v4 is removed from <var>results</var> - * @param nameMap the list of jar as a map of (filename, list of files). - * @param results the current list of jar file set to be used. it's already been cleaned of - * duplicates. - */ - private void checkSupportLibs(Map<String, List<JarEntity>> nameMap, List<File> results) { - List<JarEntity> v4 = nameMap.get("android-support-v4.jar"); - List<JarEntity> v13 = nameMap.get("android-support-v13.jar"); - - if (v13 != null && v4 != null) { - mOutStream.println("WARNING: Found both android-support-v4 and android-support-v13 in the dependency list."); - mOutStream.println("Because v13 includes v4, using only v13."); - results.remove(v4.get(0).getFile()); - } - } - - private Map<String, JarEntity> getCachedJarList() { - Map<String, JarEntity> cache = new HashMap<String, JarListSanitizer.JarEntity>(); - - File cacheFile = new File(mOut, CACHE_FILENAME); - if (cacheFile.exists() == false) { - return cache; - } - - BufferedReader reader = null; - try { - reader = new BufferedReader(new InputStreamReader(new FileInputStream(cacheFile), - "UTF-8")); - - String line = null; - while ((line = reader.readLine()) != null) { - // skip comments - if (line.charAt(0) == '#') { - continue; - } - - // get the data with a regexp - Matcher m = READ_PATTERN.matcher(line); - if (m.matches()) { - String path = m.group(4); - - JarEntity entity = new JarEntity( - path, - Long.parseLong(m.group(1)), - Long.parseLong(m.group(2)), - m.group(3)); - - cache.put(path, entity); - } - } - - } catch (FileNotFoundException e) { - // won't happen, we check up front. - } catch (UnsupportedEncodingException e) { - // shouldn't happen, but if it does, we just won't have a cache. - } catch (IOException e) { - // shouldn't happen, but if it does, we just won't have a cache. - } finally { - if (reader != null) { - try { - reader.close(); - } catch (IOException e) { - } - } - } - - return cache; - } - - private void writeJarList(Map<String, List<JarEntity>> nameMap) { - File cacheFile = new File(mOut, CACHE_FILENAME); - OutputStreamWriter writer = null; - try { - writer = new OutputStreamWriter( - new FileOutputStream(cacheFile), "UTF-8"); - - writer.write("# cache for current jar dependecy. DO NOT EDIT.\n"); - writer.write("# format is <lastModified> <length> <SHA-1> <path>\n"); - writer.write("# Encoding is UTF-8\n"); - - for (List<JarEntity> list : nameMap.values()) { - // clean up the list of files that don't have a sha1. - for (int i = 0 ; i < list.size() ; ) { - JarEntity entity = list.get(i); - if (entity.hasSha1()) { - i++; - } else { - list.remove(i); - } - } - - if (list.size() > 1) { - for (JarEntity entity : list) { - writer.write(String.format("%d %d %s %s\n", - entity.getLastModified(), - entity.getLength(), - entity.getSha1(), - entity.getFile().getAbsolutePath())); - } - } - } - } catch (IOException e) { - mOutStream.println("WARNING: unable to write jarlist cache file " + - cacheFile.getAbsolutePath()); - } catch (Sha1Exception e) { - // shouldn't happen here since we check that the sha1 is present first, meaning it's - // already been computing. - } finally { - if (writer != null) { - try { - writer.close(); - } catch (IOException e) { - } - } - } - } - - private String[] getEntityDetails(String filename, List<JarEntity> list) throws Sha1Exception { - ArrayList<String> result = new ArrayList<String>(); - result.add( - String.format("Found %d versions of %s in the dependency list,", - list.size(), filename)); - result.add("but not all the versions are identical (check is based on SHA-1 only at this time)."); - result.add("All versions of the libraries must be the same at this time."); - result.add("Versions found are:"); - for (JarEntity entity : list) { - result.add("Path: " + entity.getFile().getAbsolutePath()); - result.add("\tLength: " + entity.getLength()); - result.add("\tSHA-1: " + entity.getSha1()); - } - - return result.toArray(new String[result.size()]); - } - - /** - * Computes the sha1 of a file and returns it. - * @param f the file to compute the sha1 for. - * @return the sha1 value - * @throws Sha1Exception if the sha1 value cannot be computed. - */ - private static String getSha1(File f) throws Sha1Exception { - synchronized (sBuffer) { - FileInputStream fis = null; - try { - MessageDigest md = MessageDigest.getInstance("SHA-1"); - - fis = new FileInputStream(f); - while (true) { - int length = fis.read(sBuffer); - if (length > 0) { - md.update(sBuffer, 0, length); - } else { - break; - } - } - - return byteArray2Hex(md.digest()); - - } catch (Exception e) { - throw new Sha1Exception(f, e); - } finally { - if (fis != null) { - try { - fis.close(); - } catch (IOException e) { - // ignore - } - } - } - } - } - - private static String byteArray2Hex(final byte[] hash) { - Formatter formatter = new Formatter(); - try { - for (byte b : hash) { - formatter.format("%02x", b); - } - return formatter.toString(); - } finally { - formatter.close(); - } - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/build/SealedApkException.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/build/SealedApkException.java deleted file mode 100644 index 97f03bd..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/build/SealedApkException.java +++ /dev/null @@ -1,36 +0,0 @@ -/* - * Copyright (C) 2010 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.build; - -/** - * An exception thrown when trying to add files to a sealed APK. - */ -public final class SealedApkException extends Exception { - private static final long serialVersionUID = 1L; - - public SealedApkException(String format, Object... args) { - super(String.format(format, args)); - } - - public SealedApkException(Throwable cause, String format, Object... args) { - super(String.format(format, args), cause); - } - - public SealedApkException(Throwable cause) { - super(cause); - } -}
\ No newline at end of file diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Abi.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Abi.java deleted file mode 100644 index 080ae75..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Abi.java +++ /dev/null @@ -1,46 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.devices; - -import com.android.SdkConstants; - -public enum Abi { - ARMEABI(SdkConstants.ABI_ARMEABI), - ARMEABI_V7A(SdkConstants.ABI_ARMEABI_V7A), - X86(SdkConstants.ABI_INTEL_ATOM), - MIPS(SdkConstants.ABI_MIPS); - - private final String mValue; - - private Abi(String value) { - mValue = value; - } - - public static Abi getEnum(String value) { - for (Abi a : values()) { - if (a.mValue.equals(value)) { - return a; - } - } - return null; - } - - @Override - public String toString() { - return mValue; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/BluetoothProfile.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/BluetoothProfile.java deleted file mode 100644 index 536dcd8..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/BluetoothProfile.java +++ /dev/null @@ -1,77 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.devices; - -public enum BluetoothProfile { - A2DP("A2DP"), - ATT("ATT"), - AVRCP("AVRCP"), - AVDTP("AVDTP"), - BIP("BIP"), - BPP("BPP"), - CIP("CIP"), - CTP("CTP"), - DIP("DIP"), - DUN("DUN"), - FAX("FAX"), - FTP("FTP"), - GAVDP("GAVDP"), - GAP("GAP"), - GATT("GATT"), - GOEP("GOEP"), - HCRP("HCRP"), - HDP("HDP"), - HFP("HFP"), - HID("HID"), - HSP("HSP"), - ICP("ICP"), - LAP("LAP"), - MAP("MAP"), - OPP("OPP"), - PAN("PAN"), - PBA("PBA"), - PBAP("PBAP"), - SPP("SPP"), - SDAP("SDAP"), - SAP("SAP"), - SIM("SIM"), - rSAP("rSAP"), - SYNCH("SYNCH"), - VDP("VDP"), - WAPB("WAPB"); - - - private final String mValue; - - private BluetoothProfile(String value) { - mValue = value; - } - - public static BluetoothProfile getEnum(String value) { - for (BluetoothProfile bp : values()) { - if (bp.mValue.equals(value)) { - return bp; - } - } - return null; - } - - @Override - public String toString() { - return mValue; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/ButtonType.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/ButtonType.java deleted file mode 100644 index 6776849..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/ButtonType.java +++ /dev/null @@ -1,55 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.devices; - -public enum ButtonType { - HARD("hard", "Hardware"), - SOFT("soft", "Software"); - - private final String mId; - private final String mDescription; - - /** - * Construct a {@link ButtonType}. - * - * @param id identifier for this button type. Persisted on disk when a user creates a device. - * @param desc User friendly description - */ - private ButtonType(String id, String desc) { - mId = id; - mDescription = desc; - } - - public static ButtonType getEnum(String value) { - for (ButtonType n : values()) { - if (n.mId.equals(value)) { - return n; - } - } - return null; - } - - @Override - public String toString() { - return mId; - } - - public String getDescription() { - return mDescription; - } - -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Camera.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Camera.java deleted file mode 100644 index d7d33fe..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Camera.java +++ /dev/null @@ -1,107 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.devices; - -public class Camera { - private CameraLocation mLocation; - private boolean mAutofocus; - private boolean mFlash; - - /** - * Creates a {@link Camera} with reasonable defaults. - * - * The resulting {@link Camera} with be on the {@link CameraLocation#BACK} with both autofocus - * and flash. - */ - public Camera() { - this(CameraLocation.BACK, true, true); - } - - /** - * Creates a new {@link Camera} which describes an on device camera and it's features. - * @param location The location of the {@link Camera} on the device. Either - * {@link CameraLocation#FRONT} or {@link CameraLocation#BACK}. - * @param autofocus Whether the {@link Camera} can auto-focus. - * @param flash Whether the {@link Camera} has flash. - */ - public Camera(CameraLocation location, boolean autofocus, boolean flash) { - mLocation = location; - mAutofocus = autofocus; - mFlash = flash; - } - - public CameraLocation getLocation() { - return mLocation; - } - - public void setLocation(CameraLocation cl) { - mLocation = cl; - } - - public boolean hasAutofocus() { - return mAutofocus; - } - - public void setAutofocus(boolean hasAutofocus) { - mAutofocus = hasAutofocus; - } - - public boolean hasFlash() { - return mFlash; - } - - public void setFlash(boolean flash) { - mFlash = flash; - } - - /** - * Returns a copy of the object that shares no state with it, - * but is initialized to equivalent values. - * - * @return A copy of the object. - */ - public Camera deepCopy() { - Camera c = new Camera(); - c.mLocation = mLocation; - c.mAutofocus = mAutofocus; - c.mFlash = mFlash; - return c; - } - - @Override - public boolean equals(Object o) { - if (o == this) { - return true; - } - if (!(o instanceof Camera)) { - return false; - } - Camera c = (Camera) o; - return mLocation == c.mLocation - && mAutofocus == c.hasAutofocus() - && mFlash == c.hasFlash(); - } - - @Override - public int hashCode() { - int hash = 17; - hash = 31 * hash + mLocation.ordinal(); - hash = 31 * hash + (mAutofocus ? 1 : 0); - hash = 31 * hash + (mFlash ? 1 : 0); - return hash; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/CameraLocation.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/CameraLocation.java deleted file mode 100644 index 9a8554d..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/CameraLocation.java +++ /dev/null @@ -1,42 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.devices; - -public enum CameraLocation { - FRONT("front"), - BACK("back"); - - private final String mValue; - - private CameraLocation(String value) { - mValue = value; - } - - public static CameraLocation getEnum(String value) { - for (CameraLocation l : values()) { - if (l.mValue.equals(value)) { - return l; - } - } - return null; - } - - @Override - public String toString() { - return mValue; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Device.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Device.java deleted file mode 100644 index 762597e..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Device.java +++ /dev/null @@ -1,295 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.devices; - -import com.android.dvlib.DeviceSchema; - -import java.util.ArrayList; -import java.util.Collection; -import java.util.Collections; -import java.util.List; - -/** - * Instances of this class contain the specifications for a device. Use the - * {@link Builder} class to construct a Device object, or the - * {@link DeviceParser} if constructing device objects from XML conforming to - * the {@link DeviceSchema} standards. - */ -public final class Device { - /** Name of the device */ - private final String mName; - /** Manufacturer of the device */ - private final String mManufacturer; - /** A list of software capabilities, one for each API level range */ - private final List<Software> mSoftware; - /** A list of phone states (landscape, portrait with keyboard out, etc.) */ - private final List<State> mState; - /** Meta information such as icon files and device frames */ - private final Meta mMeta; - /** Default state of the device */ - private final State mDefaultState; - - /** - * Returns the name of the {@link Device}. - * - * @return The name of the {@link Device}. - */ - public String getName() { - return mName; - } - - /** - * Returns the manufacturer of the {@link Device}. - * - * @return The name of the manufacturer of the {@link Device}. - */ - public String getManufacturer() { - return mManufacturer; - } - - /** - * Returns all of the {@link Software} configurations of the {@link Device}. - * - * @return A list of all the {@link Software} configurations. - */ - public List<Software> getAllSoftware() { - return mSoftware; - } - - /** - * Returns all of the {@link State}s the {@link Device} can be in. - * - * @return A list of all the {@link State}s. - */ - public List<State> getAllStates() { - return mState; - } - - /** - * Returns the default {@link Hardware} configuration for the device. This - * is really just a shortcut for getting the {@link Hardware} on the default - * {@link State} - * - * @return The default {@link Hardware} for the device. - */ - public Hardware getDefaultHardware() { - return mDefaultState.getHardware(); - } - - /** - * Returns the {@link Meta} object for the device, which contains meta - * information about the device, such as the location of icons. - * - * @return The {@link Meta} object for the {@link Device}. - */ - public Meta getMeta() { - return mMeta; - } - - /** - * Returns the default {@link State} of the {@link Device}. - * - * @return The default {@link State} of the {@link Device}. - */ - public State getDefaultState() { - return mDefaultState; - } - - /** - * Returns the software configuration for the given API version. - * - * @param apiVersion - * The API version requested. - * @return The Software instance for the requested API version or null if - * the API version is unsupported for this device. - */ - public Software getSoftware(int apiVersion) { - for (Software s : mSoftware) { - if (apiVersion >= s.getMinSdkLevel() && apiVersion <= s.getMaxSdkLevel()) { - return s; - } - } - return null; - } - - /** - * Returns the state of the device with the given name. - * - * @param name - * The name of the state requested. - * @return The State object requested or null if there's no state with the - * given name. - */ - public State getState(String name) { - for (State s : getAllStates()) { - if (s.getName().equals(name)) { - return s; - } - } - return null; - } - - public static class Builder { - private String mName; - private String mManufacturer; - private final List<Software> mSoftware = new ArrayList<Software>(); - private final List<State> mState = new ArrayList<State>(); - private Meta mMeta; - private State mDefaultState; - - public Builder() { } - - public Builder(Device d) { - mName = d.getName(); - mManufacturer = d.getManufacturer(); - for (Software s : d.getAllSoftware()) { - mSoftware.add(s.deepCopy()); - } - for (State s : d.getAllStates()) { - mState.add(s.deepCopy()); - } - mSoftware.addAll(d.getAllSoftware()); - mState.addAll(d.getAllStates()); - mMeta = d.getMeta(); - mDefaultState = d.getDefaultState(); - } - - public void setName(String name) { - mName = name; - } - - public void setManufacturer(String manufacturer) { - mManufacturer = manufacturer; - } - - public void addSoftware(Software sw) { - mSoftware.add(sw); - } - - public void addAllSoftware(Collection<? extends Software> sw) { - mSoftware.addAll(sw); - } - - public void addState(State state) { - mState.add(state); - } - - public void addAllState(Collection<? extends State> states) { - mState.addAll(states); - } - - /** - * Removes the first {@link State} with the given name - * @param stateName The name of the {@link State} to remove. - * @return Whether a {@link State} was removed or not. - */ - public boolean removeState(String stateName) { - for (int i = 0; i < mState.size(); i++) { - if (stateName != null && stateName.equals(mState.get(i).getName())) { - mState.remove(i); - return true; - } - } - return false; - } - - public void setMeta(Meta meta) { - mMeta = meta; - } - - public Device build() { - if (mSoftware.size() <= 0) { - throw generateBuildException("Device software not configured"); - } else if (mState.size() <= 0) { - throw generateBuildException("Device states not configured"); - } - - if (mMeta == null) { - mMeta = new Meta(); - } - for (State s : mState) { - if (s.isDefaultState()) { - mDefaultState = s; - break; - } - } - return new Device(this); - } - - private IllegalStateException generateBuildException(String err) { - String device = ""; - if (mManufacturer != null) { - device = mManufacturer + " "; - } - if (mName != null) { - device += mName; - } else { - device = "Unknown " + device +"Device"; - } - - return new IllegalStateException("Error building " + device + ": " +err); - } - } - - protected Device(Builder b) { - mName = b.mName; - mManufacturer = b.mManufacturer; - mSoftware = Collections.unmodifiableList(b.mSoftware); - mState = Collections.unmodifiableList(b.mState); - mMeta = b.mMeta; - mDefaultState = b.mDefaultState; - } - - @Override - public boolean equals(Object o) { - if (o == this) { - return true; - } - if (!(o instanceof Device)) { - return false; - } - Device d = (Device) o; - return mName.equals(d.getName()) - && mManufacturer.equals(d.getManufacturer()) - && mSoftware.equals(d.getAllSoftware()) - && mState.equals(d.getAllStates()) - && mMeta.equals(d.getMeta()) - && mDefaultState.equals(d.getDefaultState()); - } - - @Override - /** A hash that's stable across JVM instances */ - public int hashCode() { - int hash = 17; - if (mName != null) { - hash = 31 * hash + mName.hashCode(); - } - if (mManufacturer != null) { - hash = 31 * hash + mManufacturer.hashCode(); - } - hash = 31 * hash + mSoftware.hashCode(); - hash = 31 * hash + mState.hashCode(); - hash = 31 * hash + mMeta.hashCode(); - hash = 31 * hash + mDefaultState.hashCode(); - return hash; - } - - @Override - public String toString() { - return mName; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/DeviceManager.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/DeviceManager.java deleted file mode 100644 index c17a4df..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/DeviceManager.java +++ /dev/null @@ -1,548 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.devices; - -import com.android.SdkConstants; -import com.android.annotations.NonNull; -import com.android.annotations.Nullable; -import com.android.prefs.AndroidLocation; -import com.android.prefs.AndroidLocation.AndroidLocationException; -import com.android.resources.Keyboard; -import com.android.resources.KeyboardState; -import com.android.resources.Navigation; -import com.android.sdklib.internal.avd.AvdManager; -import com.android.sdklib.internal.avd.HardwareProperties; -import com.android.sdklib.repository.PkgProps; -import com.android.utils.ILogger; - -import org.xml.sax.SAXException; - -import java.io.BufferedReader; -import java.io.File; -import java.io.FileNotFoundException; -import java.io.FileOutputStream; -import java.io.FileReader; -import java.io.IOException; -import java.util.ArrayList; -import java.util.Collection; -import java.util.Collections; -import java.util.HashMap; -import java.util.Iterator; -import java.util.List; -import java.util.Map; -import java.util.Set; -import java.util.regex.Matcher; -import java.util.regex.Pattern; - -import javax.xml.parsers.ParserConfigurationException; -import javax.xml.transform.TransformerException; -import javax.xml.transform.TransformerFactoryConfigurationError; - -/** - * Manager class for interacting with {@link Device}s within the SDK - */ -public class DeviceManager { - - private static final String DEVICE_PROFILES_PROP = "DeviceProfiles"; - private static final Pattern PATH_PROPERTY_PATTERN = - Pattern.compile("^" + PkgProps.EXTRA_PATH + "=" + DEVICE_PROFILES_PROP + "$"); - private ILogger mLog; - private List<Device> mVendorDevices; - private List<Device> mUserDevices; - private List<Device> mDefaultDevices; - private final Object mLock = new Object(); - private final List<DevicesChangedListener> sListeners = - new ArrayList<DevicesChangedListener>(); - private final String mOsSdkPath; - - /** getDevices() flag to list user devices. */ - public static final int USER_DEVICES = 1; - /** getDevices() flag to list default devices. */ - public static final int DEFAULT_DEVICES = 2; - /** getDevices() flag to list vendor devices. */ - public static final int VENDOR_DEVICES = 4; - /** getDevices() flag to list all devices. */ - public static final int ALL_DEVICES = USER_DEVICES | DEFAULT_DEVICES | VENDOR_DEVICES; - - public static enum DeviceStatus { - /** - * The device exists unchanged from the given configuration - */ - EXISTS, - /** - * A device exists with the given name and manufacturer, but has a different configuration - */ - CHANGED, - /** - * There is no device with the given name and manufacturer - */ - MISSING; - } - - /** - * Creates a new instance of DeviceManager. - * - * @param osSdkPath Path to the current SDK. If null or invalid, vendor devices are ignored. - * @param log SDK logger instance. Should be non-null. - */ - public static DeviceManager createInstance(@Nullable String osSdkPath, @NonNull ILogger log) { - // TODO consider using a cache and reusing the same instance of the device manager - // for the same manager/log combo. - return new DeviceManager(osSdkPath, log); - } - - /** - * Creates a new instance of DeviceManager. - * - * @param osSdkPath Path to the current SDK. If null or invalid, vendor devices are ignored. - * @param log SDK logger instance. Should be non-null. - */ - private DeviceManager(@Nullable String osSdkPath, @NonNull ILogger log) { - mOsSdkPath = osSdkPath; - mLog = log; - } - - /** - * Interface implemented by objects which want to know when changes occur to the {@link Device} - * lists. - */ - public static interface DevicesChangedListener { - /** - * Called after one of the {@link Device} lists has been updated. - */ - public void onDevicesChanged(); - } - - /** - * Register a listener to be notified when the device lists are modified. - * - * @param listener The listener to add. Ignored if already registered. - */ - public void registerListener(DevicesChangedListener listener) { - if (listener != null) { - synchronized (sListeners) { - if (!sListeners.contains(listener)) { - sListeners.add(listener); - } - } - } - } - - /** - * Removes a listener from the notification list such that it will no longer receive - * notifications when modifications to the {@link Device} list occur. - * - * @param listener The listener to remove. - */ - public boolean unregisterListener(DevicesChangedListener listener) { - synchronized (sListeners) { - return sListeners.remove(listener); - } - } - - public DeviceStatus getDeviceStatus(String name, String manufacturer, int hashCode) { - Device d = getDevice(name, manufacturer); - if (d == null) { - return DeviceStatus.MISSING; - } else { - return d.hashCode() == hashCode ? DeviceStatus.EXISTS : DeviceStatus.CHANGED; - } - } - - public Device getDevice(String name, String manufacturer) { - initDevicesLists(); - for (List<?> devices : - new List<?>[] { mUserDevices, mDefaultDevices, mVendorDevices } ) { - if (devices != null) { - @SuppressWarnings("unchecked") List<Device> devicesList = (List<Device>) devices; - for (Device d : devicesList) { - if (d.getName().equals(name) && d.getManufacturer().equals(manufacturer)) { - return d; - } - } - } - } - return null; - } - - /** - * Returns the known {@link Device} list. - * - * @param deviceFilter A combination of USER_DEVICES, VENDOR_DEVICES and DEFAULT_DEVICES - * or the constant ALL_DEVICES. - * @return A copy of the list of {@link Device}s. Can be empty but not null. - */ - public List<Device> getDevices(int deviceFilter) { - initDevicesLists(); - List<Device> devices = new ArrayList<Device>(); - if (mUserDevices != null && (deviceFilter & USER_DEVICES) != 0) { - devices.addAll(mUserDevices); - } - if (mDefaultDevices != null && (deviceFilter & DEFAULT_DEVICES) != 0) { - devices.addAll(mDefaultDevices); - } - if (mVendorDevices != null && (deviceFilter & VENDOR_DEVICES) != 0) { - devices.addAll(mVendorDevices); - } - return Collections.unmodifiableList(devices); - } - - private void initDevicesLists() { - boolean changed = initDefaultDevices(); - changed |= initVendorDevices(); - changed |= initUserDevices(); - if (changed) { - notifyListeners(); - } - } - - /** - * Initializes the {@link Device}s packaged with the SDK. - * @return True if the list has changed. - */ - private boolean initDefaultDevices() { - synchronized (mLock) { - if (mDefaultDevices == null) { - try { - mDefaultDevices = DeviceParser.parse( - DeviceManager.class.getResourceAsStream(SdkConstants.FN_DEVICES_XML)); - return true; - } catch (IllegalStateException e) { - // The device builders can throw IllegalStateExceptions if - // build gets called before everything is properly setup - mLog.error(e, null); - mDefaultDevices = new ArrayList<Device>(); - } catch (Exception e) { - mLog.error(null, "Error reading default devices"); - mDefaultDevices = new ArrayList<Device>(); - } - } - } - return false; - } - - /** - * Initializes all vendor-provided {@link Device}s. - * @return True if the list has changed. - */ - private boolean initVendorDevices() { - synchronized (mLock) { - if (mVendorDevices == null) { - mVendorDevices = new ArrayList<Device>(); - - if (mOsSdkPath != null) { - // Load devices from tools folder - File toolsDevices = new File(mOsSdkPath, - SdkConstants.OS_SDK_TOOLS_LIB_FOLDER + - File.separator + - SdkConstants.FN_DEVICES_XML); - if (toolsDevices.isFile()) { - mVendorDevices.addAll(loadDevices(toolsDevices)); - } - - // Load devices from vendor extras - File extrasFolder = new File(mOsSdkPath, SdkConstants.FD_EXTRAS); - List<File> deviceDirs = getExtraDirs(extrasFolder); - for (File deviceDir : deviceDirs) { - File deviceXml = new File(deviceDir, SdkConstants.FN_DEVICES_XML); - if (deviceXml.isFile()) { - mVendorDevices.addAll(loadDevices(deviceXml)); - } - } - return true; - } - } - } - return false; - } - - /** - * Initializes all user-created {@link Device}s - * @return True if the list has changed. - */ - private boolean initUserDevices() { - synchronized (mLock) { - if (mUserDevices == null) { - // User devices should be saved out to - // $HOME/.android/devices.xml - mUserDevices = new ArrayList<Device>(); - File userDevicesFile = null; - try { - userDevicesFile = new File( - AndroidLocation.getFolder(), - SdkConstants.FN_DEVICES_XML); - if (userDevicesFile.exists()) { - mUserDevices.addAll(DeviceParser.parse(userDevicesFile)); - return true; - } - } catch (AndroidLocationException e) { - mLog.warning("Couldn't load user devices: %1$s", e.getMessage()); - } catch (SAXException e) { - // Probably an old config file which we don't want to overwrite. - if (userDevicesFile != null) { - String base = userDevicesFile.getAbsoluteFile() + ".old"; - File renamedConfig = new File(base); - int i = 0; - while (renamedConfig.exists()) { - renamedConfig = new File(base + '.' + (i++)); - } - mLog.error(null, "Error parsing %1$s, backing up to %2$s", - userDevicesFile.getAbsolutePath(), - renamedConfig.getAbsolutePath()); - userDevicesFile.renameTo(renamedConfig); - } - } catch (ParserConfigurationException e) { - mLog.error(null, "Error parsing %1$s", - userDevicesFile == null ? "(null)" : userDevicesFile.getAbsolutePath()); - } catch (IOException e) { - mLog.error(null, "Error parsing %1$s", - userDevicesFile == null ? "(null)" : userDevicesFile.getAbsolutePath()); - } - } - } - return false; - } - - public void addUserDevice(Device d) { - boolean changed = false; - synchronized (mLock) { - if (mUserDevices == null) { - initUserDevices(); - assert mUserDevices != null; - } - if (mUserDevices != null) { - mUserDevices.add(d); - } - changed = true; - } - if (changed) { - notifyListeners(); - } - } - - public void removeUserDevice(Device d) { - synchronized (mLock) { - if (mUserDevices == null) { - initUserDevices(); - assert mUserDevices != null; - } - if (mUserDevices != null) { - Iterator<Device> it = mUserDevices.iterator(); - while (it.hasNext()) { - Device userDevice = it.next(); - if (userDevice.getName().equals(d.getName()) - && userDevice.getManufacturer().equals(d.getManufacturer())) { - it.remove(); - notifyListeners(); - return; - } - - } - } - } - } - - public void replaceUserDevice(Device d) { - synchronized (mLock) { - if (mUserDevices == null) { - initUserDevices(); - } - removeUserDevice(d); - addUserDevice(d); - } - } - - /** - * Saves out the user devices to {@link SdkConstants#FN_DEVICES_XML} in - * {@link AndroidLocation#getFolder()}. - */ - public void saveUserDevices() { - if (mUserDevices == null) { - return; - } - - File userDevicesFile = null; - try { - userDevicesFile = new File(AndroidLocation.getFolder(), - SdkConstants.FN_DEVICES_XML); - } catch (AndroidLocationException e) { - mLog.warning("Couldn't find user directory: %1$s", e.getMessage()); - return; - } - - if (mUserDevices.size() == 0) { - userDevicesFile.delete(); - return; - } - - synchronized (mLock) { - if (mUserDevices.size() > 0) { - try { - DeviceWriter.writeToXml(new FileOutputStream(userDevicesFile), mUserDevices); - } catch (FileNotFoundException e) { - mLog.warning("Couldn't open file: %1$s", e.getMessage()); - } catch (ParserConfigurationException e) { - mLog.warning("Error writing file: %1$s", e.getMessage()); - } catch (TransformerFactoryConfigurationError e) { - mLog.warning("Error writing file: %1$s", e.getMessage()); - } catch (TransformerException e) { - mLog.warning("Error writing file: %1$s", e.getMessage()); - } - } - } - } - - /** - * Returns hardware properties (defined in hardware.ini) as a {@link Map}. - * - * @param s The {@link State} from which to derive the hardware properties. - * @return A {@link Map} of hardware properties. - */ - public static Map<String, String> getHardwareProperties(State s) { - Hardware hw = s.getHardware(); - Map<String, String> props = new HashMap<String, String>(); - props.put(HardwareProperties.HW_MAINKEYS, - getBooleanVal(hw.getButtonType().equals(ButtonType.HARD))); - props.put(HardwareProperties.HW_TRACKBALL, - getBooleanVal(hw.getNav().equals(Navigation.TRACKBALL))); - props.put(HardwareProperties.HW_KEYBOARD, - getBooleanVal(hw.getKeyboard().equals(Keyboard.QWERTY))); - props.put(HardwareProperties.HW_DPAD, - getBooleanVal(hw.getNav().equals(Navigation.DPAD))); - - Set<Sensor> sensors = hw.getSensors(); - props.put(HardwareProperties.HW_GPS, getBooleanVal(sensors.contains(Sensor.GPS))); - props.put(HardwareProperties.HW_BATTERY, - getBooleanVal(hw.getChargeType().equals(PowerType.BATTERY))); - props.put(HardwareProperties.HW_ACCELEROMETER, - getBooleanVal(sensors.contains(Sensor.ACCELEROMETER))); - props.put(HardwareProperties.HW_ORIENTATION_SENSOR, - getBooleanVal(sensors.contains(Sensor.GYROSCOPE))); - props.put(HardwareProperties.HW_AUDIO_INPUT, getBooleanVal(hw.hasMic())); - props.put(HardwareProperties.HW_SDCARD, getBooleanVal(hw.getRemovableStorage().size() > 0)); - props.put(HardwareProperties.HW_LCD_DENSITY, - Integer.toString(hw.getScreen().getPixelDensity().getDpiValue())); - props.put(HardwareProperties.HW_PROXIMITY_SENSOR, - getBooleanVal(sensors.contains(Sensor.PROXIMITY_SENSOR))); - return props; - } - - /** - * Returns the hardware properties defined in - * {@link AvdManager#HARDWARE_INI} as a {@link Map}. - * - * @param d The {@link Device} from which to derive the hardware properties. - * @return A {@link Map} of hardware properties. - */ - public static Map<String, String> getHardwareProperties(Device d) { - Map<String, String> props = getHardwareProperties(d.getDefaultState()); - for (State s : d.getAllStates()) { - if (s.getKeyState().equals(KeyboardState.HIDDEN)) { - props.put("hw.keyboard.lid", getBooleanVal(true)); - } - } - props.put(AvdManager.AVD_INI_DEVICE_HASH, Integer.toString(d.hashCode())); - props.put(AvdManager.AVD_INI_DEVICE_NAME, d.getName()); - props.put(AvdManager.AVD_INI_DEVICE_MANUFACTURER, d.getManufacturer()); - return props; - } - - /** - * Takes a boolean and returns the appropriate value for - * {@link HardwareProperties} - * - * @param bool The boolean value to turn into the appropriate - * {@link HardwareProperties} value. - * @return {@code HardwareProperties#BOOLEAN_VALUES[0]} if true, - * {@code HardwareProperties#BOOLEAN_VALUES[1]} otherwise. - */ - private static String getBooleanVal(boolean bool) { - if (bool) { - return HardwareProperties.BOOLEAN_VALUES[0]; - } - return HardwareProperties.BOOLEAN_VALUES[1]; - } - - private Collection<Device> loadDevices(File deviceXml) { - try { - return DeviceParser.parse(deviceXml); - } catch (SAXException e) { - mLog.error(null, "Error parsing %1$s", deviceXml.getAbsolutePath()); - } catch (ParserConfigurationException e) { - mLog.error(null, "Error parsing %1$s", deviceXml.getAbsolutePath()); - } catch (IOException e) { - mLog.error(null, "Error reading %1$s", deviceXml.getAbsolutePath()); - } catch (IllegalStateException e) { - // The device builders can throw IllegalStateExceptions if - // build gets called before everything is properly setup - mLog.error(e, null); - } - return new ArrayList<Device>(); - } - - private void notifyListeners() { - synchronized (sListeners) { - for (DevicesChangedListener listener : sListeners) { - listener.onDevicesChanged(); - } - } - } - - /* Returns all of DeviceProfiles in the extras/ folder */ - private List<File> getExtraDirs(File extrasFolder) { - List<File> extraDirs = new ArrayList<File>(); - // All OEM provided device profiles are in - // $SDK/extras/$VENDOR/$ITEM/devices.xml - if (extrasFolder != null && extrasFolder.isDirectory()) { - for (File vendor : extrasFolder.listFiles()) { - if (vendor.isDirectory()) { - for (File item : vendor.listFiles()) { - if (item.isDirectory() && isDevicesExtra(item)) { - extraDirs.add(item); - } - } - } - } - } - - return extraDirs; - } - - /* - * Returns whether a specific folder for a specific vendor is a - * DeviceProfiles folder - */ - private boolean isDevicesExtra(File item) { - File properties = new File(item, SdkConstants.FN_SOURCE_PROP); - try { - BufferedReader propertiesReader = new BufferedReader(new FileReader(properties)); - try { - String line; - while ((line = propertiesReader.readLine()) != null) { - Matcher m = PATH_PROPERTY_PATTERN.matcher(line); - if (m.matches()) { - return true; - } - } - } finally { - propertiesReader.close(); - } - } catch (IOException ignore) { - } - return false; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/DeviceParser.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/DeviceParser.java deleted file mode 100644 index dd63af2..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/DeviceParser.java +++ /dev/null @@ -1,373 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.devices; - -import com.android.annotations.Nullable; -import com.android.dvlib.DeviceSchema; -import com.android.resources.Density; -import com.android.resources.Keyboard; -import com.android.resources.KeyboardState; -import com.android.resources.Navigation; -import com.android.resources.NavigationState; -import com.android.resources.ScreenOrientation; -import com.android.resources.ScreenRatio; -import com.android.resources.ScreenSize; -import com.android.resources.TouchScreen; -import com.android.resources.UiMode; - -import org.xml.sax.Attributes; -import org.xml.sax.SAXException; -import org.xml.sax.SAXParseException; -import org.xml.sax.helpers.DefaultHandler; - -import java.awt.Point; -import java.io.File; -import java.io.IOException; -import java.io.InputStream; -import java.util.ArrayList; -import java.util.List; - -import javax.xml.parsers.ParserConfigurationException; -import javax.xml.parsers.SAXParser; -import javax.xml.parsers.SAXParserFactory; - -public class DeviceParser { - - private static class DeviceHandler extends DefaultHandler { - private final static String sSpaceRegex = "[\\s]+"; - private final List<Device> mDevices = new ArrayList<Device>(); - private final StringBuilder mStringAccumulator = new StringBuilder(); - private final File mParentFolder; - private Meta mMeta; - private Hardware mHardware; - private Software mSoftware; - private State mState; - private Device.Builder mBuilder; - private Camera mCamera; - private Storage.Unit mUnit; - - public DeviceHandler(@Nullable File parentFolder) { - mParentFolder = parentFolder; - } - - public List<Device> getDevices() { - return mDevices; - } - - @Override - public void startElement(String uri, String localName, String name, Attributes attributes) - throws SAXException { - - if (DeviceSchema.NODE_DEVICE.equals(localName)) { - // Reset everything - mMeta = null; - mHardware = null; - mSoftware = null; - mState = null; - mCamera = null; - mBuilder = new Device.Builder(); - } else if (DeviceSchema.NODE_META.equals(localName)) { - mMeta = new Meta(); - } else if (DeviceSchema.NODE_HARDWARE.equals(localName)) { - mHardware = new Hardware(); - } else if (DeviceSchema.NODE_SOFTWARE.equals(localName)) { - mSoftware = new Software(); - } else if (DeviceSchema.NODE_STATE.equals(localName)) { - mState = new State(); - // mState can embed a Hardware instance - mHardware = mHardware.deepCopy(); - String defaultState = attributes.getValue(DeviceSchema.ATTR_DEFAULT); - if ("true".equals(defaultState) || "1".equals(defaultState)) { - mState.setDefaultState(true); - } - mState.setName(attributes.getValue(DeviceSchema.ATTR_NAME).trim()); - } else if (DeviceSchema.NODE_CAMERA.equals(localName)) { - mCamera = new Camera(); - } else if (DeviceSchema.NODE_RAM.equals(localName) - || DeviceSchema.NODE_INTERNAL_STORAGE.equals(localName) - || DeviceSchema.NODE_REMOVABLE_STORAGE.equals(localName)) { - mUnit = Storage.Unit.getEnum(attributes.getValue(DeviceSchema.ATTR_UNIT)); - } else if (DeviceSchema.NODE_FRAME.equals(localName)) { - mMeta.setFrameOffsetLandscape(new Point()); - mMeta.setFrameOffsetPortrait(new Point()); - } else if (DeviceSchema.NODE_SCREEN.equals(localName)) { - mHardware.setScreen(new Screen()); - } - mStringAccumulator.setLength(0); - } - - @Override - public void characters(char[] ch, int start, int length) { - mStringAccumulator.append(ch, start, length); - } - - @Override - public void endElement(String uri, String localName, String name) throws SAXException { - if (DeviceSchema.NODE_DEVICE.equals(localName)) { - mDevices.add(mBuilder.build()); - } else if (DeviceSchema.NODE_NAME.equals(localName)) { - mBuilder.setName(getString(mStringAccumulator)); - } else if (DeviceSchema.NODE_MANUFACTURER.equals(localName)) { - mBuilder.setManufacturer(getString(mStringAccumulator)); - } else if (DeviceSchema.NODE_META.equals(localName)) { - mBuilder.setMeta(mMeta); - } else if (DeviceSchema.NODE_SOFTWARE.equals(localName)) { - mBuilder.addSoftware(mSoftware); - } else if (DeviceSchema.NODE_STATE.equals(localName)) { - mState.setHardware(mHardware); - mBuilder.addState(mState); - } else if (DeviceSchema.NODE_SIXTY_FOUR.equals(localName)) { - mMeta.setIconSixtyFour(new File(mParentFolder, getString(mStringAccumulator))); - } else if (DeviceSchema.NODE_SIXTEEN.equals(localName)) { - mMeta.setIconSixteen(new File(mParentFolder, getString(mStringAccumulator))); - } else if (DeviceSchema.NODE_PATH.equals(localName)) { - mMeta.setFrame(new File(mParentFolder, mStringAccumulator.toString().trim())); - } else if (DeviceSchema.NODE_PORTRAIT_X_OFFSET.equals(localName)) { - mMeta.getFrameOffsetPortrait().x = getInteger(mStringAccumulator); - } else if (DeviceSchema.NODE_PORTRAIT_Y_OFFSET.equals(localName)) { - mMeta.getFrameOffsetPortrait().y = getInteger(mStringAccumulator); - } else if (DeviceSchema.NODE_LANDSCAPE_X_OFFSET.equals(localName)) { - mMeta.getFrameOffsetLandscape().x = getInteger(mStringAccumulator); - } else if (DeviceSchema.NODE_LANDSCAPE_Y_OFFSET.equals(localName)) { - mMeta.getFrameOffsetLandscape().y = getInteger(mStringAccumulator); - } else if (DeviceSchema.NODE_SCREEN_SIZE.equals(localName)) { - mHardware.getScreen().setSize(ScreenSize.getEnum(getString(mStringAccumulator))); - } else if (DeviceSchema.NODE_DIAGONAL_LENGTH.equals(localName)) { - mHardware.getScreen().setDiagonalLength(getDouble(mStringAccumulator)); - } else if (DeviceSchema.NODE_PIXEL_DENSITY.equals(localName)) { - mHardware.getScreen().setPixelDensity( - Density.getEnum(getString(mStringAccumulator))); - } else if (DeviceSchema.NODE_SCREEN_RATIO.equals(localName)) { - mHardware.getScreen().setRatio( - ScreenRatio.getEnum(getString(mStringAccumulator))); - } else if (DeviceSchema.NODE_X_DIMENSION.equals(localName)) { - mHardware.getScreen().setXDimension(getInteger(mStringAccumulator)); - } else if (DeviceSchema.NODE_Y_DIMENSION.equals(localName)) { - mHardware.getScreen().setYDimension(getInteger(mStringAccumulator)); - } else if (DeviceSchema.NODE_XDPI.equals(localName)) { - mHardware.getScreen().setXdpi(getDouble(mStringAccumulator)); - } else if (DeviceSchema.NODE_YDPI.equals(localName)) { - mHardware.getScreen().setYdpi(getDouble(mStringAccumulator)); - } else if (DeviceSchema.NODE_MULTITOUCH.equals(localName)) { - mHardware.getScreen().setMultitouch( - Multitouch.getEnum(getString(mStringAccumulator))); - } else if (DeviceSchema.NODE_MECHANISM.equals(localName)) { - mHardware.getScreen().setMechanism( - TouchScreen.getEnum(getString(mStringAccumulator))); - } else if (DeviceSchema.NODE_SCREEN_TYPE.equals(localName)) { - mHardware.getScreen().setScreenType( - ScreenType.getEnum(getString(mStringAccumulator))); - } else if (DeviceSchema.NODE_NETWORKING.equals(localName)) { - for (String n : getStringList(mStringAccumulator)) { - Network net = Network.getEnum(n); - if (net != null) { - mHardware.addNetwork(net); - } - } - } else if (DeviceSchema.NODE_SENSORS.equals(localName)) { - for (String s : getStringList(mStringAccumulator)) { - Sensor sens = Sensor.getEnum(s); - if (sens != null) { - mHardware.addSensor(sens); - } - } - } else if (DeviceSchema.NODE_MIC.equals(localName)) { - mHardware.setHasMic(getBool(mStringAccumulator)); - } else if (DeviceSchema.NODE_CAMERA.equals(localName)) { - mHardware.addCamera(mCamera); - mCamera = null; - } else if (DeviceSchema.NODE_LOCATION.equals(localName)) { - mCamera.setLocation(CameraLocation.getEnum(getString(mStringAccumulator))); - } else if (DeviceSchema.NODE_AUTOFOCUS.equals(localName)) { - mCamera.setFlash(getBool(mStringAccumulator)); - } else if (DeviceSchema.NODE_FLASH.equals(localName)) { - mCamera.setFlash(getBool(mStringAccumulator)); - } else if (DeviceSchema.NODE_KEYBOARD.equals(localName)) { - mHardware.setKeyboard(Keyboard.getEnum(getString(mStringAccumulator))); - } else if (DeviceSchema.NODE_NAV.equals(localName)) { - mHardware.setNav(Navigation.getEnum(getString(mStringAccumulator))); - } else if (DeviceSchema.NODE_RAM.equals(localName)) { - int val = getInteger(mStringAccumulator); - mHardware.setRam(new Storage(val, mUnit)); - } else if (DeviceSchema.NODE_BUTTONS.equals(localName)) { - mHardware.setButtonType(ButtonType.getEnum(getString(mStringAccumulator))); - } else if (DeviceSchema.NODE_INTERNAL_STORAGE.equals(localName)) { - for (String s : getStringList(mStringAccumulator)) { - int val = Integer.parseInt(s); - mHardware.addInternalStorage(new Storage(val, mUnit)); - } - } else if (DeviceSchema.NODE_REMOVABLE_STORAGE.equals(localName)) { - for (String s : getStringList(mStringAccumulator)) { - if (s != null && !s.isEmpty()) { - int val = Integer.parseInt(s); - mHardware.addRemovableStorage(new Storage(val, mUnit)); - } - } - } else if (DeviceSchema.NODE_CPU.equals(localName)) { - mHardware.setCpu(getString(mStringAccumulator)); - } else if (DeviceSchema.NODE_GPU.equals(localName)) { - mHardware.setGpu(getString(mStringAccumulator)); - } else if (DeviceSchema.NODE_ABI.equals(localName)) { - for (String s : getStringList(mStringAccumulator)) { - Abi abi = Abi.getEnum(s); - if (abi != null) { - mHardware.addSupportedAbi(abi); - } - } - } else if (DeviceSchema.NODE_DOCK.equals(localName)) { - for (String s : getStringList(mStringAccumulator)) { - UiMode d = UiMode.getEnum(s); - if (d != null) { - mHardware.addSupportedUiMode(d); - } - } - } else if (DeviceSchema.NODE_POWER_TYPE.equals(localName)) { - mHardware.setChargeType(PowerType.getEnum(getString(mStringAccumulator))); - } else if (DeviceSchema.NODE_API_LEVEL.equals(localName)) { - String val = getString(mStringAccumulator); - // Can be one of 5 forms: - // 1 - // 1-2 - // 1- - // -2 - // - - int index; - if (val.charAt(0) == '-') { - if (val.length() == 1) { // - - mSoftware.setMinSdkLevel(0); - mSoftware.setMaxSdkLevel(Integer.MAX_VALUE); - } else { // -2 - // Remove the front dash and any whitespace between it - // and the upper bound. - val = val.substring(1).trim(); - mSoftware.setMinSdkLevel(0); - mSoftware.setMaxSdkLevel(Integer.parseInt(val)); - } - } else if ((index = val.indexOf('-')) > 0) { - if (index == val.length() - 1) { // 1- - // Strip the last dash and any whitespace between it and - // the lower bound. - val = val.substring(0, val.length() - 1).trim(); - mSoftware.setMinSdkLevel(Integer.parseInt(val)); - mSoftware.setMaxSdkLevel(Integer.MAX_VALUE); - } else { // 1-2 - String min = val.substring(0, index).trim(); - String max = val.substring(index + 1); - mSoftware.setMinSdkLevel(Integer.parseInt(min)); - mSoftware.setMaxSdkLevel(Integer.parseInt(max)); - } - } else { // 1 - int apiLevel = Integer.parseInt(val); - mSoftware.setMinSdkLevel(apiLevel); - mSoftware.setMaxSdkLevel(apiLevel); - } - } else if (DeviceSchema.NODE_LIVE_WALLPAPER_SUPPORT.equals(localName)) { - mSoftware.setLiveWallpaperSupport(getBool(mStringAccumulator)); - } else if (DeviceSchema.NODE_BLUETOOTH_PROFILES.equals(localName)) { - for (String s : getStringList(mStringAccumulator)) { - BluetoothProfile profile = BluetoothProfile.getEnum(s); - if (profile != null) { - mSoftware.addBluetoothProfile(profile); - } - } - } else if (DeviceSchema.NODE_GL_VERSION.equals(localName)) { - // Guaranteed to be in the form [\d]\.[\d] - mSoftware.setGlVersion(getString(mStringAccumulator)); - } else if (DeviceSchema.NODE_GL_EXTENSIONS.equals(localName)) { - mSoftware.addAllGlExtensions(getStringList(mStringAccumulator)); - } else if (DeviceSchema.NODE_DESCRIPTION.equals(localName)) { - mState.setDescription(getString(mStringAccumulator)); - } else if (DeviceSchema.NODE_SCREEN_ORIENTATION.equals(localName)) { - mState.setOrientation(ScreenOrientation.getEnum(getString(mStringAccumulator))); - } else if (DeviceSchema.NODE_KEYBOARD_STATE.equals(localName)) { - mState.setKeyState(KeyboardState.getEnum(getString(mStringAccumulator))); - } else if (DeviceSchema.NODE_NAV_STATE.equals(localName)) { - // We have an extra state in our XML for nonav that - // NavigationState doesn't contain - String navState = getString(mStringAccumulator); - if (navState.equals("nonav")) { - mState.setNavState(NavigationState.HIDDEN); - } else { - mState.setNavState(NavigationState.getEnum(getString(mStringAccumulator))); - } - } else if (DeviceSchema.NODE_STATUS_BAR.equals(localName)) { - mSoftware.setStatusBar(getBool(mStringAccumulator)); - } - } - - @Override - public void error(SAXParseException e) throws SAXParseException { - throw e; - } - - private List<String> getStringList(StringBuilder stringAccumulator) { - List<String> filteredStrings = new ArrayList<String>(); - for (String s : getString(mStringAccumulator).split(sSpaceRegex)) { - if (s != null && !s.isEmpty()) { - filteredStrings.add(s.trim()); - } - } - return filteredStrings; - } - - private Boolean getBool(StringBuilder stringAccumulator) { - String b = getString(stringAccumulator); - return b.equalsIgnoreCase("true") || b.equalsIgnoreCase("1"); - } - - private double getDouble(StringBuilder stringAccumulator) { - return Double.parseDouble(getString(stringAccumulator)); - } - - private String getString(StringBuilder stringAccumulator) { - return stringAccumulator.toString().trim(); - } - - private int getInteger(StringBuilder stringAccumulator) { - return Integer.parseInt(getString(stringAccumulator)); - } - - } - - private final static SAXParserFactory sParserFactory; - - static { - sParserFactory = SAXParserFactory.newInstance(); - sParserFactory.setNamespaceAware(true); - } - - public static List<Device> parse(File devicesFile) throws SAXException, - ParserConfigurationException, IOException { - SAXParser parser = getParser(); - DeviceHandler dHandler = new DeviceHandler(devicesFile.getAbsoluteFile().getParentFile()); - parser.parse(devicesFile, dHandler); - return dHandler.getDevices(); - } - - public static List<Device> parse(InputStream devices) throws SAXException, IOException, - ParserConfigurationException { - SAXParser parser = getParser(); - DeviceHandler dHandler = new DeviceHandler(null); - parser.parse(devices, dHandler); - return dHandler.getDevices(); - } - - private static SAXParser getParser() throws ParserConfigurationException, SAXException { - sParserFactory.setSchema(DeviceSchema.getSchema()); - return sParserFactory.newSAXParser(); - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/DeviceWriter.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/DeviceWriter.java deleted file mode 100644 index 11b1c6d..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/DeviceWriter.java +++ /dev/null @@ -1,296 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.devices; - -import com.android.SdkConstants; -import com.android.dvlib.DeviceSchema; -import com.android.resources.UiMode; - -import org.w3c.dom.Document; -import org.w3c.dom.Element; -import org.w3c.dom.Node; -import org.w3c.dom.NodeList; - -import java.awt.Point; -import java.io.OutputStream; -import java.util.Collection; -import java.util.Locale; - -import javax.xml.XMLConstants; -import javax.xml.parsers.DocumentBuilderFactory; -import javax.xml.parsers.ParserConfigurationException; -import javax.xml.transform.OutputKeys; -import javax.xml.transform.Transformer; -import javax.xml.transform.TransformerException; -import javax.xml.transform.TransformerFactory; -import javax.xml.transform.TransformerFactoryConfigurationError; -import javax.xml.transform.dom.DOMSource; -import javax.xml.transform.stream.StreamResult; - -public class DeviceWriter { - - public static final String LOCAL_NS = "d"; - public static final String PREFIX = LOCAL_NS + ":"; - - /** - * Writes the XML definition of the given {@link Collection} of {@link Device}s according to - * {@link SdkConstants#NS_DEVICES_XSD} to the {@link OutputStream}. - * Note that it is up to the caller to close the {@link OutputStream}. - * @param out The {@link OutputStream} to write the resulting XML to. - * @param devices The {@link Device}s from which to generate the XML. - * @throws ParserConfigurationException - * @throws TransformerFactoryConfigurationError - * @throws TransformerException - */ - public static void writeToXml(OutputStream out, Collection<Device> devices) throws - ParserConfigurationException, - TransformerFactoryConfigurationError, - TransformerException { - Document doc = DocumentBuilderFactory.newInstance().newDocumentBuilder().newDocument(); - Element root = doc.createElement(PREFIX + DeviceSchema.NODE_DEVICES); - root.setAttribute(XMLConstants.XMLNS_ATTRIBUTE + ":xsi", - XMLConstants.W3C_XML_SCHEMA_INSTANCE_NS_URI); - root.setAttribute(XMLConstants.XMLNS_ATTRIBUTE + ":" + LOCAL_NS, SdkConstants.NS_DEVICES_XSD); - doc.appendChild(root); - - for (Device device : devices) { - Element deviceNode = doc.createElement(PREFIX + DeviceSchema.NODE_DEVICE); - root.appendChild(deviceNode); - - Element name = doc.createElement(PREFIX + DeviceSchema.NODE_NAME); - name.appendChild(doc.createTextNode(device.getName())); - deviceNode.appendChild(name); - - Element manufacturer = doc.createElement(PREFIX + DeviceSchema.NODE_MANUFACTURER); - manufacturer.appendChild(doc.createTextNode(device.getManufacturer())); - deviceNode.appendChild(manufacturer); - - deviceNode.appendChild(generateMetaNode(device.getMeta(), doc)); - deviceNode.appendChild(generateHardwareNode(device.getDefaultHardware(), doc)); - for (Software sw : device.getAllSoftware()) { - deviceNode.appendChild(generateSoftwareNode(sw, doc)); - } - for (State s : device.getAllStates()) { - deviceNode.appendChild(generateStateNode(s, doc, device.getDefaultHardware())); - } - } - - Transformer tf = TransformerFactory.newInstance().newTransformer(); - tf.setOutputProperty(OutputKeys.INDENT, "yes"); - tf.setOutputProperty("{http://xml.apache.org/xslt}indent-amount", "2"); - DOMSource source = new DOMSource(doc); - StreamResult result = new StreamResult(out); - tf.transform(source, result); - } - - /* This returns the XML Element for the given instance of Meta */ - private static Node generateMetaNode(Meta meta, Document doc) { - Element m = doc.createElement(PREFIX + DeviceSchema.NODE_META); - if (meta.hasIconSixtyFour() || meta.hasIconSixteen()) { - Element icons = doc.createElement(PREFIX + DeviceSchema.NODE_ICONS); - m.appendChild(icons); - if (meta.hasIconSixtyFour()) { - addElement(doc, icons, DeviceSchema.NODE_SIXTY_FOUR, - meta.getIconSixtyFour().getPath()); - } - if (meta.hasIconSixteen()) { - addElement(doc, icons, DeviceSchema.NODE_SIXTEEN, meta.getIconSixteen().getPath()); - } - } - - if (meta.hasFrame()) { - Element frame = doc.createElement(PREFIX + DeviceSchema.NODE_FRAME); - addElement(doc, frame, DeviceSchema.NODE_PATH, meta.getFrame().getPath()); - Point offset = meta.getFrameOffsetPortrait(); - addElement(doc, frame, DeviceSchema.NODE_PORTRAIT_X_OFFSET, Integer.toString(offset.x)); - addElement(doc, frame, DeviceSchema.NODE_PORTRAIT_Y_OFFSET, Integer.toString(offset.y)); - offset = meta.getFrameOffsetLandscape(); - addElement(doc, frame, DeviceSchema.NODE_LANDSCAPE_X_OFFSET, - Integer.toString(offset.x)); - addElement(doc, frame, DeviceSchema.NODE_LANDSCAPE_Y_OFFSET, - Integer.toString(offset.y)); - } - - return m; - } - - /* This returns the XML Element for the given instance of Hardware */ - private static Element generateHardwareNode(Hardware hw, Document doc) { - Screen s = hw.getScreen(); - Element hardware = doc.createElement(PREFIX + DeviceSchema.NODE_HARDWARE); - Element screen = doc.createElement(PREFIX + DeviceSchema.NODE_SCREEN); - hardware.appendChild(screen); - - addElement(doc, screen, DeviceSchema.NODE_SCREEN_SIZE, s.getSize().getResourceValue()); - addElement(doc, screen, DeviceSchema.NODE_DIAGONAL_LENGTH, - String.format(Locale.US, "%.2f",s.getDiagonalLength())); - addElement(doc, screen, DeviceSchema.NODE_PIXEL_DENSITY, - s.getPixelDensity().getResourceValue()); - addElement(doc, screen, DeviceSchema.NODE_SCREEN_RATIO, s.getRatio().getResourceValue()); - - Element dimensions = doc.createElement(PREFIX + DeviceSchema.NODE_DIMENSIONS); - screen.appendChild(dimensions); - - addElement(doc, dimensions, DeviceSchema.NODE_X_DIMENSION, - Integer.toString(s.getXDimension())); - addElement(doc, dimensions, DeviceSchema.NODE_Y_DIMENSION, - Integer.toString(s.getYDimension())); - addElement(doc, screen, DeviceSchema.NODE_XDPI, String.format(Locale.US, - "%.2f", s.getXdpi())); - addElement(doc, screen, DeviceSchema.NODE_YDPI, String.format(Locale.US, - "%.2f", s.getYdpi())); - - Element touch = doc.createElement(PREFIX + DeviceSchema.NODE_TOUCH); - screen.appendChild(touch); - - addElement(doc, touch, DeviceSchema.NODE_MULTITOUCH, s.getMultitouch().toString()); - addElement(doc, touch, DeviceSchema.NODE_MECHANISM, s.getMechanism().getResourceValue()); - addElement(doc, touch, DeviceSchema.NODE_SCREEN_TYPE, s.getScreenType().toString()); - - addElement(doc, hardware, DeviceSchema.NODE_NETWORKING, hw.getNetworking()); - addElement(doc, hardware, DeviceSchema.NODE_SENSORS, hw.getSensors()); - addElement(doc, hardware, DeviceSchema.NODE_MIC, Boolean.toString(hw.hasMic())); - - for(Camera c : hw.getCameras()) { - Element camera = doc.createElement(PREFIX + DeviceSchema.NODE_CAMERA); - hardware.appendChild(camera); - addElement(doc, camera, DeviceSchema.NODE_LOCATION, c.getLocation().toString()); - addElement(doc, camera, DeviceSchema.NODE_AUTOFOCUS, - Boolean.toString(c.hasAutofocus())); - addElement(doc, camera, DeviceSchema.NODE_FLASH, Boolean.toString(c.hasFlash())); - } - - addElement(doc, hardware, DeviceSchema.NODE_KEYBOARD, hw.getKeyboard().getResourceValue()); - addElement(doc, hardware, DeviceSchema.NODE_NAV, hw.getNav().getResourceValue()); - - Storage.Unit unit = hw.getRam().getApproriateUnits(); - Element ram = addElement(doc, hardware, DeviceSchema.NODE_RAM, - Long.toString(hw.getRam().getSizeAsUnit(unit))); - ram.setAttribute(DeviceSchema.ATTR_UNIT, unit.toString()); - - addElement(doc, hardware, DeviceSchema.NODE_BUTTONS, hw.getButtonType().toString()); - addStorageElement(doc, hardware, DeviceSchema.NODE_INTERNAL_STORAGE, - hw.getInternalStorage()); - addStorageElement(doc, hardware, DeviceSchema.NODE_REMOVABLE_STORAGE, - hw.getRemovableStorage()); - addElement(doc, hardware, DeviceSchema.NODE_CPU, hw.getCpu()); - addElement(doc, hardware, DeviceSchema.NODE_GPU, hw.getGpu()); - addElement(doc, hardware, DeviceSchema.NODE_ABI, hw.getSupportedAbis()); - - StringBuilder sb = new StringBuilder(); - for (UiMode u : hw.getSupportedUiModes()) { - sb.append("\n" + u.getResourceValue()); - } - addElement(doc, hardware, DeviceSchema.NODE_DOCK, sb.toString()); - - addElement(doc, hardware, DeviceSchema.NODE_POWER_TYPE, hw.getChargeType().toString()); - - return hardware; - } - - /* This returns the XML Element for the given instance of Software */ - private static Element generateSoftwareNode(Software sw, Document doc) { - Element software = doc.createElement(PREFIX + DeviceSchema.NODE_SOFTWARE); - - String apiVersion = ""; - if (sw.getMinSdkLevel() != 0) { - apiVersion += Integer.toString(sw.getMinSdkLevel()); - } - apiVersion += "-"; - if (sw.getMaxSdkLevel() != Integer.MAX_VALUE) { - apiVersion += Integer.toString(sw.getMaxSdkLevel()); - } - addElement(doc, software, DeviceSchema.NODE_API_LEVEL, apiVersion); - addElement(doc, software, DeviceSchema.NODE_LIVE_WALLPAPER_SUPPORT, - Boolean.toString(sw.hasLiveWallpaperSupport())); - addElement(doc, software, DeviceSchema.NODE_BLUETOOTH_PROFILES, sw.getBluetoothProfiles()); - addElement(doc, software, DeviceSchema.NODE_GL_VERSION, sw.getGlVersion()); - addElement(doc, software, DeviceSchema.NODE_GL_EXTENSIONS, sw.getGlExtensions()); - addElement(doc, software, DeviceSchema.NODE_STATUS_BAR, - Boolean.toString(sw.hasStatusBar())); - - return software; - } - - /* This returns the XML Element for the given instance of State */ - private static Element generateStateNode(State s, Document doc, Hardware defaultHardware) { - Element state = doc.createElement(PREFIX + DeviceSchema.NODE_STATE); - state.setAttribute(DeviceSchema.ATTR_NAME, s.getName()); - if (s.isDefaultState()) { - state.setAttribute(DeviceSchema.ATTR_DEFAULT, Boolean.toString(s.isDefaultState())); - } - addElement(doc, state, DeviceSchema.NODE_DESCRIPTION, s.getDescription()); - addElement(doc, state, DeviceSchema.NODE_SCREEN_ORIENTATION, - s.getOrientation().getResourceValue()); - addElement(doc, state, DeviceSchema.NODE_KEYBOARD_STATE, - s.getKeyState().getResourceValue()); - addElement(doc, state, DeviceSchema.NODE_NAV_STATE, s.getNavState().getResourceValue()); - - // Only if the hardware is different do we want to append hardware values - if (!s.getHardware().equals(defaultHardware)){ - // TODO: Only append nodes which are different from the default hardware - Element hardware = generateHardwareNode(s.getHardware(), doc); - NodeList children = hardware.getChildNodes(); - for (int i = 0 ; i < children.getLength(); i++) { - Node child = children.item(i); - state.appendChild(child); - } - } - return state; - } - - private static Element addElement(Document doc, Element parent, String tag, String content) { - Element child = doc.createElement(PREFIX + tag); - child.appendChild(doc.createTextNode(content)); - parent.appendChild(child); - return child; - } - - private static Element addElement(Document doc, Element parent, String tag, - Collection<? extends Object> content) { - StringBuilder sb = new StringBuilder(); - for (Object o : content) { - sb.append("\n" + o.toString()); - } - return addElement(doc, parent, tag, sb.toString()); - } - - /* This adds generates the XML for a Collection<Storage> and appends it to the parent. Note - * that it picks the proper unit for the unit attribute and sets it on the node. - */ - private static Element addStorageElement(Document doc, Element parent, String tag, - Collection<Storage> content){ - Storage.Unit unit = Storage.Unit.TiB; - - // Get the lowest common unit (so if one piece of storage is 128KiB and another is 1MiB, - // use KiB for units) - for(Storage storage : content) { - if(storage.getApproriateUnits().getNumberOfBytes() < unit.getNumberOfBytes()) { - unit = storage.getApproriateUnits(); - } - } - - StringBuilder sb = new StringBuilder(); - for(Storage storage : content) { - sb.append("\n" + storage.getSizeAsUnit(unit)); - } - Element storage = addElement(doc, parent, tag, sb.toString()); - storage.setAttribute(DeviceSchema.ATTR_UNIT, unit.toString()); - return storage; - } - -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Hardware.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Hardware.java deleted file mode 100644 index b12f11d..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Hardware.java +++ /dev/null @@ -1,331 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.devices; - -import com.android.resources.Keyboard; -import com.android.resources.Navigation; -import com.android.resources.UiMode; - -import java.util.ArrayList; -import java.util.Collection; -import java.util.HashSet; -import java.util.List; -import java.util.Set; - -public class Hardware { - private Screen mScreen; - private Set<Network> mNetworking = new HashSet<Network>(); - private Set<Sensor> mSensors = new HashSet<Sensor>(); - private boolean mMic; - private List<Camera> mCameras = new ArrayList<Camera>(); - private Keyboard mKeyboard; - private Navigation mNav; - private Storage mRam; - private ButtonType mButtons; - private List<Storage> mInternalStorage = new ArrayList<Storage>(); - private List<Storage> mRemovableStorage = new ArrayList<Storage>(); - private String mCpu; - private String mGpu; - private Set<Abi> mAbis = new HashSet<Abi>(); - private Set<UiMode> mUiModes = new HashSet<UiMode>(); - private PowerType mPluggedIn; - - public Set<Network> getNetworking() { - return mNetworking; - } - - public void addNetwork(Network n) { - mNetworking.add(n); - } - - public void addAllNetworks(Collection<Network> ns) { - mNetworking.addAll(ns); - } - - public Set<Sensor> getSensors() { - return mSensors; - } - - public void addSensor(Sensor sensor) { - mSensors.add(sensor); - } - - public void addAllSensors(Collection<Sensor> sensors) { - mSensors.addAll(sensors); - } - - public boolean hasMic() { - return mMic; - } - - public void setHasMic(boolean hasMic) { - mMic = hasMic; - } - - public List<Camera> getCameras() { - return mCameras; - } - - public void addCamera(Camera c) { - mCameras.add(c); - } - - public void addAllCameras(Collection<Camera> cs) { - mCameras.addAll(cs); - } - - public Camera getCamera(int i) { - return mCameras.get(i); - } - - public Camera getCamera(CameraLocation location) { - for (Camera c : mCameras) { - if (location.equals(c.getLocation())) { - return c; - } - } - return null; - } - - public Keyboard getKeyboard() { - return mKeyboard; - } - - public void setKeyboard(Keyboard k) { - mKeyboard = k; - } - - public Navigation getNav() { - return mNav; - } - - public void setNav(Navigation n) { - mNav = n; - } - - public Storage getRam() { - return mRam; - } - - public void setRam(Storage ram) { - mRam = ram; - } - - public ButtonType getButtonType() { - return mButtons; - } - - public void setButtonType(ButtonType bt) { - mButtons = bt; - } - - public List<Storage> getInternalStorage() { - return mInternalStorage; - } - - public void addInternalStorage(Storage is) { - mInternalStorage.add(is); - } - - public void addAllInternalStorage(Collection<Storage> is) { - mInternalStorage.addAll(is); - } - - public List<Storage> getRemovableStorage() { - return mRemovableStorage; - } - - public void addRemovableStorage(Storage rs) { - mRemovableStorage.add(rs); - } - - public void addAllRemovableStorage(Collection<Storage> rs) { - mRemovableStorage.addAll(rs); - } - - public String getCpu() { - return mCpu; - } - - public void setCpu(String cpuName) { - mCpu = cpuName; - } - - public String getGpu() { - return mGpu; - } - - public void setGpu(String gpuName) { - mGpu = gpuName; - } - - public Set<Abi> getSupportedAbis() { - return mAbis; - } - - public void addSupportedAbi(Abi abi) { - mAbis.add(abi); - } - - public void addAllSupportedAbis(Collection<Abi> abis) { - mAbis.addAll(abis); - } - - public Set<UiMode> getSupportedUiModes() { - return mUiModes; - } - - public void addSupportedUiMode(UiMode uiMode) { - mUiModes.add(uiMode); - } - - public void addAllSupportedUiModes(Collection<UiMode> uiModes) { - mUiModes.addAll(uiModes); - } - - public PowerType getChargeType() { - return mPluggedIn; - } - - public void setChargeType(PowerType chargeType) { - mPluggedIn = chargeType; - } - - public Screen getScreen() { - return mScreen; - } - - public void setScreen(Screen s) { - mScreen = s; - } - - /** - * Returns a copy of the object that shares no state with it, - * but is initialized to equivalent values. - * - * @return A copy of the object. - */ - public Hardware deepCopy() { - Hardware hw = new Hardware(); - hw.mScreen = mScreen.deepCopy(); - hw.mNetworking = new HashSet<Network>(mNetworking); - hw.mSensors = new HashSet<Sensor>(mSensors); - // Get the constant boolean value - hw.mMic = mMic; - hw.mCameras = new ArrayList<Camera>(); - for (Camera c : mCameras) { - hw.mCameras.add(c.deepCopy()); - } - hw.mKeyboard = mKeyboard; - hw.mNav = mNav; - hw.mRam = mRam.deepCopy(); - hw.mButtons = mButtons; - hw.mInternalStorage = new ArrayList<Storage>(); - for (Storage s : mInternalStorage) { - hw.mInternalStorage.add(s.deepCopy()); - } - hw.mRemovableStorage = new ArrayList<Storage>(); - for (Storage s : mRemovableStorage) { - hw.mRemovableStorage.add(s.deepCopy()); - } - hw.mCpu = mCpu; - hw.mGpu = mGpu; - hw.mAbis = new HashSet<Abi>(mAbis); - hw.mUiModes = new HashSet<UiMode>(mUiModes); - hw.mPluggedIn = mPluggedIn; - return hw; - } - - @Override - public boolean equals(Object o) { - if (o == this) { - return true; - } - if (!(o instanceof Hardware)) { - return false; - } - Hardware hw = (Hardware) o; - return mScreen.equals(hw.getScreen()) - && mNetworking.equals(hw.getNetworking()) - && mSensors.equals(hw.getSensors()) - && mMic == hw.hasMic() - && mCameras.equals(hw.getCameras()) - && mKeyboard == hw.getKeyboard() - && mNav == hw.getNav() - && mRam.equals(hw.getRam()) - && mButtons == hw.getButtonType() - && mInternalStorage.equals(hw.getInternalStorage()) - && mRemovableStorage.equals(hw.getRemovableStorage()) - && mCpu.equals(hw.getCpu()) - && mGpu.equals(hw.getGpu()) - && mAbis.equals(hw.getSupportedAbis()) - && mUiModes.equals(hw.getSupportedUiModes()) - && mPluggedIn == hw.getChargeType(); - - } - - @Override - public int hashCode() { - int hash = 17; - hash = 31 * hash + mScreen.hashCode(); - - // Since sets have no defined order, we need to hash them in such a way that order doesn't - // matter. - int temp = 0; - for (Network n : mNetworking) { - temp |= 1 << n.ordinal(); - } - hash = 31 * hash + temp; - - temp = 0; - for (Sensor s : mSensors) { - temp |= 1 << s.ordinal(); - } - - hash = 31 * hash + temp; - hash = 31 * hash + (mMic ? 1 : 0); - hash = mCameras.hashCode(); - hash = 31 * hash + mKeyboard.ordinal(); - hash = 31 * hash + mNav.ordinal(); - hash = 31 * hash + mRam.hashCode(); - hash = 31 * hash + mButtons.ordinal(); - hash = 31 * hash + mInternalStorage.hashCode(); - hash = 31 * hash + mRemovableStorage.hashCode(); - - for (Character c : mCpu.toCharArray()) { - hash = 31 * hash + c; - } - - for (Character c : mGpu.toCharArray()) { - hash = 31 * hash + c; - } - - temp = 0; - for (Abi a : mAbis) { - temp |= 1 << a.ordinal(); - } - hash = 31 * hash + temp; - - temp = 0; - for (UiMode ui : mUiModes) { - temp |= 1 << ui.ordinal(); - } - hash = 31 * hash + temp; - - return hash; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Meta.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Meta.java deleted file mode 100644 index e69d2c3..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Meta.java +++ /dev/null @@ -1,167 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.devices; - -import java.awt.Point; -import java.io.File; - -public class Meta { - private File mIconSixtyFour; - private File mIconSixteen; - private File mFrame; - private Point mFrameOffsetLandscape; - private Point mFrameOffsetPortrait; - - public File getIconSixtyFour() { - return mIconSixtyFour; - } - - public void setIconSixtyFour(File iconSixtyFour) { - mIconSixtyFour = iconSixtyFour; - } - - public boolean hasIconSixtyFour() { - if (mIconSixtyFour != null && mIconSixtyFour.isFile()) { - return true; - } else { - return false; - } - } - - public File getIconSixteen() { - return mIconSixteen; - } - - public void setIconSixteen(File iconSixteen) { - mIconSixteen = iconSixteen; - } - - public boolean hasIconSixteen() { - if (mIconSixteen != null && mIconSixteen.isFile()) { - return true; - } else { - return false; - } - } - - public File getFrame() { - return mFrame; - } - - public void setFrame(File frame) { - mFrame = frame; - } - - public boolean hasFrame() { - if (mFrame != null && mFrame.isFile()) { - return true; - } else { - return false; - } - } - - public Point getFrameOffsetLandscape() { - return mFrameOffsetLandscape; - } - - public void setFrameOffsetLandscape(Point offset) { - mFrameOffsetLandscape = offset; - } - - public Point getFrameOffsetPortrait() { - return mFrameOffsetPortrait; - } - - public void setFrameOffsetPortrait(Point offset) { - mFrameOffsetPortrait = offset; - } - - @Override - public boolean equals(Object o) { - if (o == this) { - return true; - } - if (!(o instanceof Meta)) { - return false; - } - Meta m = (Meta) o; - - // Note that any of the fields of either object can be null - if (mIconSixtyFour != null && !mIconSixtyFour.equals(m.getIconSixtyFour())){ - return false; - } else if (m.getIconSixtyFour() != null && !m.getIconSixtyFour().equals(mIconSixtyFour)) { - return false; - } - - if (mIconSixteen != null && !mIconSixteen.equals(m.getIconSixteen())){ - return false; - } else if (m.getIconSixteen() != null && !m.getIconSixteen().equals(mIconSixteen)) { - return false; - } - - if (mFrame != null && !mFrame.equals(m.getFrame())) { - return false; - } else if (m.getFrame() != null && !m.getFrame().equals(mFrame)) { - return false; - } - - if (mFrameOffsetLandscape != null - && !mFrameOffsetLandscape.equals(m.getFrameOffsetLandscape())){ - return false; - } else if (m.getFrameOffsetLandscape() != null - && !m.getFrameOffsetLandscape().equals(mFrameOffsetLandscape)){ - return false; - } - - - if (mFrameOffsetPortrait != null - && !mFrameOffsetPortrait.equals(m.getFrameOffsetPortrait())){ - return false; - } else if (m.getFrameOffsetPortrait() != null - && !m.getFrameOffsetPortrait().equals(mFrameOffsetPortrait)){ - return false; - } - - return true; - } - - @Override - public int hashCode() { - int hash = 17; - if(mIconSixteen != null){ - String path = mIconSixteen.getAbsolutePath(); - hash = 31 * hash + path.hashCode(); - } - if(mIconSixtyFour != null){ - String path = mIconSixtyFour.getAbsolutePath(); - hash = 31 * hash + path.hashCode(); - } - if(mFrame != null){ - String path = mFrame.getAbsolutePath(); - hash = 31 * hash + path.hashCode(); - } - if(mFrameOffsetLandscape != null){ - hash = 31 * hash + mFrameOffsetLandscape.x; - hash = 31 * hash + mFrameOffsetLandscape.y; - } - if(mFrameOffsetPortrait != null){ - hash = 31 * hash + mFrameOffsetPortrait.x; - hash = 31 * hash + mFrameOffsetPortrait.y; - } - return hash; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Multitouch.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Multitouch.java deleted file mode 100644 index bfd4618..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Multitouch.java +++ /dev/null @@ -1,44 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.devices; - -public enum Multitouch { - NONE("none"), - BASIC("basic"), - DISTINCT("distinct"), - JAZZ_HANDS("jazz-hands"); - - private final String mValue; - - private Multitouch(String value){ - mValue = value; - } - - public static Multitouch getEnum(String val){ - for (Multitouch m : values()) { - if (m.mValue.equals(val)) { - return m; - } - } - return null; - } - - @Override - public String toString() { - return mValue; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Network.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Network.java deleted file mode 100644 index df84b44..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Network.java +++ /dev/null @@ -1,43 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.devices; - -public enum Network { - BLUETOOTH("Bluetooth"), - WIFI("Wifi"), - NFC("NFC"); - - private final String mValue; - - private Network(String value) { - mValue = value; - } - - public static Network getEnum(String value) { - for (Network n : values()) { - if (n.mValue.equals(value)) { - return n; - } - } - return null; - } - - @Override - public String toString(){ - return mValue; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/PowerType.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/PowerType.java deleted file mode 100644 index e38ba28..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/PowerType.java +++ /dev/null @@ -1,42 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.devices; - -public enum PowerType { - PLUGGEDIN("plugged-in"), - BATTERY("battery"); - - private final String mValue; - - private PowerType(String value) { - mValue = value; - } - - public static PowerType getEnum(String value) { - for (PowerType c : values()) { - if (c.mValue.equals(value)) { - return c; - } - } - return null; - } - - @Override - public String toString() { - return mValue; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Screen.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Screen.java deleted file mode 100644 index a7f4334..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Screen.java +++ /dev/null @@ -1,189 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.devices; - -import com.android.resources.Density; -import com.android.resources.ScreenRatio; -import com.android.resources.ScreenSize; -import com.android.resources.TouchScreen; - - -public class Screen { - private ScreenSize mScreenSize; - private double mDiagonalLength; - private Density mPixelDensity; - private ScreenRatio mScreenRatio; - private int mXDimension; - private int mYDimension; - private double mXdpi; - private double mYdpi; - private Multitouch mMultitouch; - private TouchScreen mMechanism; - private ScreenType mScreenType; - - public ScreenSize getSize() { - return mScreenSize; - } - - public void setSize(ScreenSize s) { - mScreenSize = s; - } - - public double getDiagonalLength() { - return mDiagonalLength; - } - - public void setDiagonalLength(double diagonalLength) { - mDiagonalLength = diagonalLength; - } - - public Density getPixelDensity() { - return mPixelDensity; - } - - public void setPixelDensity(Density pDensity) { - mPixelDensity = pDensity; - } - - public ScreenRatio getRatio() { - return mScreenRatio; - } - - public void setRatio(ScreenRatio ratio) { - mScreenRatio = ratio; - } - - public int getXDimension() { - return mXDimension; - } - - public void setXDimension(int xDimension) { - mXDimension = xDimension; - } - - public int getYDimension() { - return mYDimension; - } - - public void setYDimension(int yDimension) { - mYDimension = yDimension; - } - - public double getXdpi() { - return mXdpi; - } - - public void setXdpi(double xdpi) { - mXdpi = xdpi; - } - - public double getYdpi() { - return mYdpi; - } - - public void setYdpi(double ydpi) { - mYdpi = ydpi; - } - - public Multitouch getMultitouch() { - return mMultitouch; - } - - public void setMultitouch(Multitouch m) { - mMultitouch = m; - } - - public TouchScreen getMechanism() { - return mMechanism; - } - - public void setMechanism(TouchScreen mechanism) { - mMechanism = mechanism; - } - - public ScreenType getScreenType() { - return mScreenType; - } - - public void setScreenType(ScreenType screenType) { - mScreenType = screenType; - } - - /** - * Returns a copy of the object that shares no state with it, - * but is initialized to equivalent values. - * - * @return A copy of the object. - */ - public Screen deepCopy() { - Screen s = new Screen(); - s.mScreenSize = mScreenSize; - s.mDiagonalLength = mDiagonalLength; - s.mPixelDensity = mPixelDensity; - s.mScreenRatio = mScreenRatio; - s.mXDimension = mXDimension; - s.mYDimension = mYDimension; - s.mXdpi = mXdpi; - s.mYdpi = mYdpi; - s.mMultitouch = mMultitouch; - s.mMechanism = mMechanism; - s.mScreenType = mScreenType; - return s; - } - - @Override - public boolean equals(Object o) { - if (o == this) { - return true; - } - if (!(o instanceof Screen)) { - return false; - } - Screen s = (Screen) o; - return s.mScreenSize == mScreenSize - && s.mDiagonalLength == mDiagonalLength - && s.mPixelDensity == mPixelDensity - && s.mScreenRatio == mScreenRatio - && s.mXDimension == mXDimension - && s.mYDimension == mYDimension - && s.mXdpi == mXdpi - && s.mYdpi == mYdpi - && s.mMultitouch == mMultitouch - && s.mMechanism == mMechanism - && s.mScreenType == mScreenType; - } - - @Override - public int hashCode() { - int hash = 17; - hash = 31 * hash + mScreenSize.ordinal(); - long f = Double.doubleToLongBits(mDiagonalLength); - hash = 31 * hash + (int) (f ^ (f >>> 32)); - hash = 31 * hash + mPixelDensity.ordinal(); - hash = 31 * hash + mScreenRatio.ordinal(); - hash = 31 * hash + mXDimension; - hash = 31 * hash + mYDimension; - f = Double.doubleToLongBits(mXdpi); - hash = 31 * hash + (int) (f ^ (f >>> 32)); - f = Double.doubleToLongBits(mYdpi); - hash = 31 * hash + (int) (f ^ (f >>> 32)); - hash = 31 * hash + mMultitouch.ordinal(); - hash = 31 * hash + mMechanism.ordinal(); - hash = 31 * hash + mScreenType.ordinal(); - return hash; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/ScreenType.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/ScreenType.java deleted file mode 100644 index 21d6005..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/ScreenType.java +++ /dev/null @@ -1,43 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.devices; - -public enum ScreenType { - CAPACITIVE("capacitive"), - RESISTIVE("resistive"), - NOTOUCH("notouch"); - - private final String mValue; - - private ScreenType(String value) { - mValue = value; - } - - public static ScreenType getEnum(String value) { - for (ScreenType s : values()) { - if (s.mValue.equals(value)) { - return s; - } - } - return null; - } - - @Override - public String toString() { - return mValue; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Sensor.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Sensor.java deleted file mode 100644 index 3fc3e14..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Sensor.java +++ /dev/null @@ -1,47 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.devices; - -public enum Sensor { - ACCELEROMETER("Accelerometer"), - BAROMETER("Barometer"), - COMPASS("Compass"), - GPS("GPS"), - GYROSCOPE("Gyroscope"), - LIGHT_SENSOR("LightSensor"), - PROXIMITY_SENSOR("ProximitySensor"); - - private final String mValue; - - private Sensor(String value) { - mValue = value; - } - - public static Sensor getEnum(String value) { - for (Sensor s : values()) { - if (s.mValue.equals(value)) { - return s; - } - } - return null; - } - - @Override - public String toString(){ - return mValue; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Software.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Software.java deleted file mode 100644 index ac66a73..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Software.java +++ /dev/null @@ -1,148 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.devices; - -import java.util.Collection; -import java.util.LinkedHashSet; -import java.util.Set; - -public class Software { - private int mMinSdkLevel = 0; - private int mMaxSdkLevel = Integer.MAX_VALUE; - private boolean mLiveWallpaperSupport; - private Set<BluetoothProfile> mBluetoothProfiles = new LinkedHashSet<BluetoothProfile>(); - private String mGlVersion; - private Set<String> mGlExtensions = new LinkedHashSet<String>(); - private boolean mStatusBar; - - public int getMinSdkLevel() { - return mMinSdkLevel; - } - - public void setMinSdkLevel(int sdkLevel) { - mMinSdkLevel = sdkLevel; - } - - public int getMaxSdkLevel() { - return mMaxSdkLevel; - } - - public void setMaxSdkLevel(int sdkLevel) { - mMaxSdkLevel = sdkLevel; - } - - public boolean hasLiveWallpaperSupport() { - return mLiveWallpaperSupport; - } - - public void setLiveWallpaperSupport(boolean liveWallpaperSupport) { - mLiveWallpaperSupport = liveWallpaperSupport; - } - - public Set<BluetoothProfile> getBluetoothProfiles() { - return mBluetoothProfiles; - } - - public void addBluetoothProfile(BluetoothProfile bp) { - mBluetoothProfiles.add(bp); - } - - public void addAllBluetoothProfiles(Collection<BluetoothProfile> bps) { - mBluetoothProfiles.addAll(bps); - } - - public String getGlVersion() { - return mGlVersion; - } - - public void setGlVersion(String version) { - mGlVersion = version; - } - - public Set<String> getGlExtensions() { - return mGlExtensions; - } - - public void addGlExtension(String extension) { - mGlExtensions.add(extension); - } - - public void addAllGlExtensions(Collection<String> extensions) { - mGlExtensions.addAll(extensions); - } - - public void setStatusBar(boolean hasBar) { - mStatusBar = hasBar; - } - - public boolean hasStatusBar() { - return mStatusBar; - } - - public Software deepCopy() { - Software s = new Software(); - s.setMinSdkLevel(getMinSdkLevel()); - s.setMaxSdkLevel(getMaxSdkLevel()); - s.setLiveWallpaperSupport(hasLiveWallpaperSupport()); - s.addAllBluetoothProfiles(getBluetoothProfiles()); - s.setGlVersion(getGlVersion()); - s.addAllGlExtensions(getGlExtensions()); - s.setStatusBar(hasStatusBar()); - return s; - } - - @Override - public boolean equals(Object o) { - if (o == this) { - return true; - } - if (!(o instanceof Software)) { - return false; - } - - Software sw = (Software) o; - return mMinSdkLevel == sw.getMinSdkLevel() - && mMaxSdkLevel == sw.getMaxSdkLevel() - && mLiveWallpaperSupport == sw.hasLiveWallpaperSupport() - && mBluetoothProfiles.equals(sw.getBluetoothProfiles()) - && mGlVersion.equals(sw.getGlVersion()) - && mGlExtensions.equals(sw.getGlExtensions()) - && mStatusBar == sw.hasStatusBar(); - } - - @Override - /** A stable hash across JVM instances */ - public int hashCode() { - int hash = 17; - hash = 31 * hash + mMinSdkLevel; - hash = 31 * hash + mMaxSdkLevel; - hash = 31 * hash + (mLiveWallpaperSupport ? 1 : 0); - for (BluetoothProfile bp : mBluetoothProfiles) { - hash = 31 * hash + bp.ordinal(); - } - if (mGlVersion != null) { - hash = 31 * hash + mGlVersion.hashCode(); - } - for (String glExtension : mGlExtensions) { - if (glExtension != null) { - hash = 31 * hash + glExtension.hashCode(); - } - } - hash = 31 * hash + (mStatusBar ? 1 : 0); - return hash; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/State.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/State.java deleted file mode 100644 index 42c43e7..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/State.java +++ /dev/null @@ -1,145 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.devices; - -import com.android.resources.KeyboardState; -import com.android.resources.NavigationState; -import com.android.resources.ScreenOrientation; - -public class State { - private boolean mDefaultState; - private String mName; - private String mDescription; - private ScreenOrientation mOrientation; - private KeyboardState mKeyState; - private NavigationState mNavState; - private Hardware mHardwareOverride; - - public boolean isDefaultState() { - return mDefaultState; - } - - public void setDefaultState(boolean defaultState) { - mDefaultState = defaultState; - } - - public String getName() { - return mName; - } - - public void setName(String name) { - mName = name; - } - - public String getDescription() { - return mDescription; - } - - public void setDescription(String description) { - mDescription = description; - } - - public ScreenOrientation getOrientation() { - return mOrientation; - } - - public void setOrientation(ScreenOrientation orientation) { - mOrientation = orientation; - } - - public KeyboardState getKeyState() { - return mKeyState; - } - - public void setKeyState(KeyboardState keyState) { - mKeyState = keyState; - } - - public NavigationState getNavState() { - return mNavState; - } - - public void setNavState(NavigationState navState) { - mNavState = navState; - } - - public Hardware getHardware() { - return mHardwareOverride; - } - - public void setHardware(Hardware hw) { - mHardwareOverride = hw; - } - - /** - * Returns a copy of the object that shares no state with it, - * but is initialized to equivalent values. - * - * @return A copy of the object. - */ - public State deepCopy() { - State s = new State(); - s.setDefaultState(isDefaultState()); - s.setName(getName()); - s.setDescription(getDescription()); - s.setOrientation(getOrientation()); - s.setKeyState(getKeyState()); - s.setNavState(getNavState()); - s.setHardware(getHardware().deepCopy()); - return s; - } - - @Override - public boolean equals(Object o) { - if (o == this) { - return true; - } - if (!(o instanceof State)) { - return false; - } - State s = (State) o; - return mDefaultState == s.isDefaultState() - && mName.equals(s.getName()) - && mDescription.equals(s.getDescription()) - && mOrientation.equals(s.getOrientation()) - && mKeyState.equals(s.getKeyState()) - && mNavState.equals(s.getNavState()) - && mHardwareOverride.equals(s.getHardware()); - } - - @Override - public int hashCode() { - int hash = 17; - hash = 31 * hash + (mDefaultState ? 1 : 0); - if (mName != null) { - hash = 31 * hash + mName.hashCode(); - } - if (mDescription != null) { - hash = 31 * hash + mDescription.hashCode(); - } - hash = 31 * hash + mOrientation.ordinal(); - hash = 31 * hash + mKeyState.ordinal(); - hash = 31 * hash + mNavState.ordinal(); - hash = 31 * hash + mHardwareOverride.hashCode(); - return hash; - } - - @Override - public String toString() { - return mName; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Storage.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Storage.java deleted file mode 100644 index b30fe6e..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/Storage.java +++ /dev/null @@ -1,123 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.devices; - -public class Storage { - private long mNoBytes; - - public Storage(long amount, Unit unit){ - mNoBytes = amount * unit.getNumberOfBytes(); - } - - public Storage(long amount){ - this(amount, Unit.B); - } - - /** Returns the amount of storage represented, in Bytes */ - public long getSize() { - return getSizeAsUnit(Unit.B); - } - - public Storage deepCopy() { - return new Storage(mNoBytes); - } - - /** - * Return the amount of storage represented by the instance in the given unit - * @param unit The unit of the result. - * @return The size of the storage in the given unit. - */ - public long getSizeAsUnit(Unit unit) { - return mNoBytes / unit.getNumberOfBytes(); - } - - @Override - public boolean equals(Object o) { - if (o == this){ - return true; - } - - if (!(o instanceof Storage)) { - return false; - } - - Storage s = (Storage) o; - if (s.getSize() == this.getSize()) { - return true; - } else { - return false; - } - } - - @Override - public int hashCode() { - int result = 17; - return 31 * result + (int) (mNoBytes^(mNoBytes>>>32)); - } - - public enum Unit{ - B("B", 1), - KiB("KiB", 1024), - MiB("MiB", 1024 * 1024), - GiB("GiB", 1024 * 1024 * 1024), - TiB("TiB", 1024l * 1024l * 1024l * 1024l); - - private String mValue; - /** The number of bytes needed to have one of the given unit */ - private long mNoBytes; - - private Unit(String val, long noBytes) { - mValue = val; - mNoBytes = noBytes; - } - - public static Unit getEnum(String val) { - for(Unit v : values()){ - if(v.mValue.equals(val)) { - return v; - } - } - return null; - } - - public long getNumberOfBytes() { - return mNoBytes; - } - - @Override - public String toString() { - return mValue; - } - } - - /** - * Finds the largest {@link Unit} which can display the storage value as a positive integer - * with no loss of accuracy. - * @return The most appropriate {@link Unit}. - */ - public Unit getApproriateUnits() { - Unit optimalUnit = Unit.B; - for(Unit unit : Unit.values()) { - if(mNoBytes % unit.getNumberOfBytes() == 0) { - optimalUnit = unit; - } else { - break; - } - } - return optimalUnit; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/devices.xml b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/devices.xml deleted file mode 100644 index 9eacec2..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/devices/devices.xml +++ /dev/null @@ -1,1412 +0,0 @@ -<?xml version="1.0"?> -<d:devices - xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" - xmlns:d="http://schemas.android.com/sdk/devices/1"> - - <d:device> - <d:name> - 2.7in QVGA - </d:name> - <d:manufacturer> - Generic - </d:manufacturer> - <d:hardware> - <d:screen> - <d:screen-size>small</d:screen-size> - <d:diagonal-length>2.7</d:diagonal-length> - <d:pixel-density>ldpi</d:pixel-density> - <d:screen-ratio>notlong</d:screen-ratio> - <d:dimensions> - <d:x-dimension>240</d:x-dimension> - <d:y-dimension>320</d:y-dimension> - </d:dimensions> - <d:xdpi>145</d:xdpi> - <d:ydpi>145</d:ydpi> - <d:touch> - <d:multitouch>distinct</d:multitouch> - <d:mechanism>finger</d:mechanism> - <d:screen-type>capacitive</d:screen-type> - </d:touch> - </d:screen> - <d:networking> - Bluetooth - Wifi - NFC - </d:networking> - <d:sensors> - Accelerometer - Barometer - Gyroscope - Compass - GPS - ProximitySensor - </d:sensors> - <d:mic>true</d:mic> - <d:camera> - <d:location>back</d:location> - <d:autofocus>true</d:autofocus> - <d:flash>true</d:flash> - </d:camera> - <d:keyboard>nokeys</d:keyboard> - <d:nav>nonav</d:nav> - <d:ram unit="MiB">512</d:ram> - <d:buttons>hard</d:buttons> - <d:internal-storage unit="GiB">8</d:internal-storage> - <d:removable-storage unit="MiB"></d:removable-storage> - <d:cpu>OMAP 9001</d:cpu> - <d:gpu>Ultra Nexus 3D S++</d:gpu> - <d:abi> - armeabi - armeabi-v7a - mips - x86 - </d:abi> - <d:dock> - car - television - desk - </d:dock> - <d:power-type>battery</d:power-type> - </d:hardware> - - <d:software> - <d:api-level>-</d:api-level> - <d:live-wallpaper-support>true</d:live-wallpaper-support> - <d:bluetooth-profiles /> - <d:gl-version>2.1</d:gl-version> - <d:gl-extensions /> - <d:status-bar>true</d:status-bar> - </d:software> - - <d:state name="Portrait" default="true"> - <d:description>The phone in portrait view</d:description> - <d:screen-orientation>port</d:screen-orientation> - <d:keyboard-state>keyssoft</d:keyboard-state> - <d:nav-state>navhidden</d:nav-state> - </d:state> - <d:state name="Landscape"> - <d:description>The phone in landscape view</d:description> - <d:screen-orientation>land</d:screen-orientation> - <d:keyboard-state>keyssoft</d:keyboard-state> - <d:nav-state>navhidden</d:nav-state> - </d:state> - </d:device> - - <d:device> - <d:name> - 2.7in QVGA slider - </d:name> - <d:manufacturer> - Generic - </d:manufacturer> - <d:hardware> - <d:screen> - <d:screen-size>small</d:screen-size> - <d:diagonal-length>2.7</d:diagonal-length> - <d:pixel-density>ldpi</d:pixel-density> - <d:screen-ratio>notlong</d:screen-ratio> - <d:dimensions> - <d:x-dimension>240</d:x-dimension> - <d:y-dimension>320</d:y-dimension> - </d:dimensions> - <d:xdpi>145</d:xdpi> - <d:ydpi>145</d:ydpi> - <d:touch> - <d:multitouch>distinct</d:multitouch> - <d:mechanism>finger</d:mechanism> - <d:screen-type>capacitive</d:screen-type> - </d:touch> - </d:screen> - <d:networking> - Bluetooth - Wifi - NFC - </d:networking> - <d:sensors> - Accelerometer - Barometer - Gyroscope - Compass - GPS - ProximitySensor - </d:sensors> - <d:mic>true</d:mic> - <d:camera> - <d:location>back</d:location> - <d:autofocus>true</d:autofocus> - <d:flash>true</d:flash> - </d:camera> - <d:keyboard>qwerty</d:keyboard> - <d:nav>nonav</d:nav> - <d:ram unit="MiB">512</d:ram> - <d:buttons>hard</d:buttons> - <d:internal-storage unit="GiB">8</d:internal-storage> - <d:removable-storage unit="MiB"></d:removable-storage> - <d:cpu>OMAP 9001</d:cpu> - <d:gpu>Ultra Nexus 3D S++</d:gpu> - <d:abi> - armeabi - armeabi-v7a - mips - x86 - </d:abi> - <d:dock> - car - television - desk - </d:dock> - <d:power-type>battery</d:power-type> - </d:hardware> - - <d:software> - <d:api-level>-</d:api-level> - <d:live-wallpaper-support>true</d:live-wallpaper-support> - <d:bluetooth-profiles /> - <d:gl-version>2.1</d:gl-version> - <d:gl-extensions /> - <d:status-bar>true</d:status-bar> - </d:software> - - <d:state name="Portrait" default="true"> - <d:description>The phone in portrait view</d:description> - <d:screen-orientation>port</d:screen-orientation> - <d:keyboard-state>keyssoft</d:keyboard-state> - <d:nav-state>navhidden</d:nav-state> - </d:state> - <d:state name="Landscape, closed"> - <d:description>The phone in landscape view with the keyboard closed</d:description> - <d:screen-orientation>land</d:screen-orientation> - <d:keyboard-state>keyshidden</d:keyboard-state> - <d:nav-state>navhidden</d:nav-state> - </d:state> - <d:state name="Landscape, open"> - <d:description>The phone in landscape view with the keyboard open</d:description> - <d:screen-orientation>land</d:screen-orientation> - <d:keyboard-state>keysexposed</d:keyboard-state> - <d:nav-state>navexposed</d:nav-state> - </d:state> - </d:device> - - <d:device> - <d:name> - 3.2in HVGA slider (ADP1) - </d:name> - <d:manufacturer> - Generic - </d:manufacturer> - <d:hardware> - <d:screen> - <d:screen-size>normal</d:screen-size> - <d:diagonal-length>3.2</d:diagonal-length> - <d:pixel-density>mdpi</d:pixel-density> - <d:screen-ratio>notlong</d:screen-ratio> - <d:dimensions> - <d:x-dimension>320</d:x-dimension> - <d:y-dimension>480</d:y-dimension> - </d:dimensions> - <d:xdpi>180.6</d:xdpi> - <d:ydpi>182</d:ydpi> - <d:touch> - <d:multitouch>distinct</d:multitouch> - <d:mechanism>finger</d:mechanism> - <d:screen-type>capacitive</d:screen-type> - </d:touch> - </d:screen> - <d:networking> - Bluetooth - Wifi - NFC - </d:networking> - <d:sensors> - Accelerometer - Barometer - Gyroscope - Compass - GPS - ProximitySensor - </d:sensors> - <d:mic>true</d:mic> - <d:camera> - <d:location>back</d:location> - <d:autofocus>true</d:autofocus> - <d:flash>true</d:flash> - </d:camera> - <d:keyboard>qwerty</d:keyboard> - <d:nav>nonav</d:nav> - <d:ram unit="MiB">512</d:ram> - <d:buttons>hard</d:buttons> - <d:internal-storage unit="GiB">8</d:internal-storage> - <d:removable-storage unit="MiB"></d:removable-storage> - <d:cpu>OMAP 9001</d:cpu> - <d:gpu>Ultra Nexus 3D S++</d:gpu> - <d:abi> - armeabi - armeabi-v7a - mips - x86 - </d:abi> - <d:dock> - car - television - desk - </d:dock> - <d:power-type>battery</d:power-type> - </d:hardware> - - <d:software> - <d:api-level>-</d:api-level> - <d:live-wallpaper-support>true</d:live-wallpaper-support> - <d:bluetooth-profiles /> - <d:gl-version>2.1</d:gl-version> - <d:gl-extensions /> - <d:status-bar>true</d:status-bar> - </d:software> - - <d:state name="Portrait" default="true"> - <d:description>The phone in portrait view</d:description> - <d:screen-orientation>port</d:screen-orientation> - <d:keyboard-state>keyshidden</d:keyboard-state> - <d:nav-state>navhidden</d:nav-state> - </d:state> - <d:state name="Landscape, closed"> - <d:description>The phone in landscape view with the keyboard closed</d:description> - <d:screen-orientation>land</d:screen-orientation> - <d:keyboard-state>keyshidden</d:keyboard-state> - <d:nav-state>navhidden</d:nav-state> - </d:state> - <d:state name="Landscape, open"> - <d:description>The phone in landscape view with the keyboard open</d:description> - <d:screen-orientation>land</d:screen-orientation> - <d:keyboard-state>keysexposed</d:keyboard-state> - <d:nav-state>navexposed</d:nav-state> - </d:state> - </d:device> - - <d:device> - <d:name> - 3.2in QVGA (ADP2) - </d:name> - <d:manufacturer> - Generic - </d:manufacturer> - <d:hardware> - <d:screen> - <d:screen-size>normal</d:screen-size> - <d:diagonal-length>3.2</d:diagonal-length> - <d:pixel-density>mdpi</d:pixel-density> - <d:screen-ratio>notlong</d:screen-ratio> - <d:dimensions> - <d:x-dimension>320</d:x-dimension> - <d:y-dimension>480</d:y-dimension> - </d:dimensions> - <d:xdpi>180.6</d:xdpi> - <d:ydpi>182</d:ydpi> - <d:touch> - <d:multitouch>distinct</d:multitouch> - <d:mechanism>finger</d:mechanism> - <d:screen-type>capacitive</d:screen-type> - </d:touch> - </d:screen> - <d:networking> - Bluetooth - Wifi - NFC - </d:networking> - <d:sensors> - Accelerometer - Barometer - Gyroscope - Compass - GPS - ProximitySensor - </d:sensors> - <d:mic>true</d:mic> - <d:camera> - <d:location>back</d:location> - <d:autofocus>true</d:autofocus> - <d:flash>true</d:flash> - </d:camera> - <d:keyboard>nokeys</d:keyboard> - <d:nav>trackball</d:nav> - <d:ram unit="MiB">512</d:ram> - <d:buttons>hard</d:buttons> - <d:internal-storage unit="GiB">8</d:internal-storage> - <d:removable-storage unit="MiB"></d:removable-storage> - <d:cpu>OMAP 9001</d:cpu> - <d:gpu>Ultra Nexus 3D S++</d:gpu> - <d:abi> - armeabi - armeabi-v7a - mips - x86 - </d:abi> - <d:dock> - car - television - desk - </d:dock> - <d:power-type>battery</d:power-type> - </d:hardware> - - <d:software> - <d:api-level>-</d:api-level> - <d:live-wallpaper-support>true</d:live-wallpaper-support> - <d:bluetooth-profiles /> - <d:gl-version>2.1</d:gl-version> - <d:gl-extensions /> - <d:status-bar>true</d:status-bar> - </d:software> - - <d:state name="Portrait" default="true"> - <d:description>The phone in portrait view</d:description> - <d:screen-orientation>port</d:screen-orientation> - <d:keyboard-state>keyssoft</d:keyboard-state> - <d:nav-state>navexposed</d:nav-state> - </d:state> - <d:state name="Landscape"> - <d:description>The phone in landscape view</d:description> - <d:screen-orientation>land</d:screen-orientation> - <d:keyboard-state>keyssoft</d:keyboard-state> - <d:nav-state>navexposed</d:nav-state> - </d:state> - </d:device> - - <d:device> - <d:name> - 3.3in WQVGA - </d:name> - <d:manufacturer> - Generic - </d:manufacturer> - <d:hardware> - <d:screen> - <d:screen-size>normal</d:screen-size> - <d:diagonal-length>3.3</d:diagonal-length> - <d:pixel-density>ldpi</d:pixel-density> - <d:screen-ratio>long</d:screen-ratio> - <d:dimensions> - <d:x-dimension>240</d:x-dimension> - <d:y-dimension>400</d:y-dimension> - </d:dimensions> - <d:xdpi>141</d:xdpi> - <d:ydpi>141</d:ydpi> - <d:touch> - <d:multitouch>distinct</d:multitouch> - <d:mechanism>finger</d:mechanism> - <d:screen-type>capacitive</d:screen-type> - </d:touch> - </d:screen> - <d:networking> - Bluetooth - Wifi - NFC - </d:networking> - <d:sensors> - Accelerometer - Barometer - Gyroscope - Compass - GPS - ProximitySensor - </d:sensors> - <d:mic>true</d:mic> - <d:camera> - <d:location>back</d:location> - <d:autofocus>true</d:autofocus> - <d:flash>true</d:flash> - </d:camera> - <d:keyboard>nokeys</d:keyboard> - <d:nav>nonav</d:nav> - <d:ram unit="MiB">512</d:ram> - <d:buttons>hard</d:buttons> - <d:internal-storage unit="GiB">8</d:internal-storage> - <d:removable-storage unit="MiB"></d:removable-storage> - <d:cpu>OMAP 9001</d:cpu> - <d:gpu>Ultra Nexus 3D S++</d:gpu> - <d:abi> - armeabi - armeabi-v7a - mips - x86 - </d:abi> - <d:dock> - car - television - desk - </d:dock> - <d:power-type>battery</d:power-type> - </d:hardware> - - <d:software> - <d:api-level>-</d:api-level> - <d:live-wallpaper-support>true</d:live-wallpaper-support> - <d:bluetooth-profiles /> - <d:gl-version>2.1</d:gl-version> - <d:gl-extensions /> - <d:status-bar>true</d:status-bar> - </d:software> - - <d:state name="Portrait" default="true"> - <d:description>The phone in portrait view</d:description> - <d:screen-orientation>port</d:screen-orientation> - <d:keyboard-state>keyssoft</d:keyboard-state> - <d:nav-state>navhidden</d:nav-state> - </d:state> - <d:state name="Landscape"> - <d:description>The phone in landscape view</d:description> - <d:screen-orientation>land</d:screen-orientation> - <d:keyboard-state>keyssoft</d:keyboard-state> - <d:nav-state>navhidden</d:nav-state> - </d:state> - </d:device> - <d:device> - <d:name> - 3.4in WQVGA - </d:name> - <d:manufacturer> - Generic - </d:manufacturer> - <d:hardware> - <d:screen> - <d:screen-size>normal</d:screen-size> - <d:diagonal-length>3.4</d:diagonal-length> - <d:pixel-density>ldpi</d:pixel-density> - <d:screen-ratio>long</d:screen-ratio> - <d:dimensions> - <d:x-dimension>240</d:x-dimension> - <d:y-dimension>432</d:y-dimension> - </d:dimensions> - <d:xdpi>145</d:xdpi> - <d:ydpi>145</d:ydpi> - <d:touch> - <d:multitouch>distinct</d:multitouch> - <d:mechanism>finger</d:mechanism> - <d:screen-type>capacitive</d:screen-type> - </d:touch> - </d:screen> - <d:networking> - Bluetooth - Wifi - NFC - </d:networking> - <d:sensors> - Accelerometer - Barometer - Gyroscope - Compass - GPS - ProximitySensor - </d:sensors> - <d:mic>true</d:mic> - <d:camera> - <d:location>back</d:location> - <d:autofocus>true</d:autofocus> - <d:flash>true</d:flash> - </d:camera> - <d:keyboard>nokeys</d:keyboard> - <d:nav>nonav</d:nav> - <d:ram unit="MiB">512</d:ram> - <d:buttons>hard</d:buttons> - <d:internal-storage unit="GiB">8</d:internal-storage> - <d:removable-storage unit="MiB"></d:removable-storage> - <d:cpu>OMAP 9001</d:cpu> - <d:gpu>Ultra Nexus 3D S++</d:gpu> - <d:abi> - armeabi - armeabi-v7a - mips - x86 - </d:abi> - <d:dock> - car - television - desk - </d:dock> - <d:power-type>battery</d:power-type> - </d:hardware> - - <d:software> - <d:api-level>-</d:api-level> - <d:live-wallpaper-support>true</d:live-wallpaper-support> - <d:bluetooth-profiles /> - <d:gl-version>2.1</d:gl-version> - <d:gl-extensions /> - <d:status-bar>true</d:status-bar> - </d:software> - - <d:state name="Portrait" default="true"> - <d:description>The phone in portrait view</d:description> - <d:screen-orientation>port</d:screen-orientation> - <d:keyboard-state>keyssoft</d:keyboard-state> - <d:nav-state>navhidden</d:nav-state> - </d:state> - <d:state name="Landscape"> - <d:description>The phone in landscape view</d:description> - <d:screen-orientation>land</d:screen-orientation> - <d:keyboard-state>keyssoft</d:keyboard-state> - <d:nav-state>navhidden</d:nav-state> - </d:state> - </d:device> - - <d:device> - <d:name> - 3.7in WVGA (Nexus One) - </d:name> - <d:manufacturer> - Generic - </d:manufacturer> - <d:hardware> - <d:screen> - <d:screen-size>normal</d:screen-size> - <d:diagonal-length>3.4</d:diagonal-length> - <d:pixel-density>hdpi</d:pixel-density> - <d:screen-ratio>long</d:screen-ratio> - <d:dimensions> - <d:x-dimension>480</d:x-dimension> - <d:y-dimension>800</d:y-dimension> - </d:dimensions> - <d:xdpi>254</d:xdpi> - <d:ydpi>254</d:ydpi> - <d:touch> - <d:multitouch>distinct</d:multitouch> - <d:mechanism>finger</d:mechanism> - <d:screen-type>capacitive</d:screen-type> - </d:touch> - </d:screen> - <d:networking> - Bluetooth - Wifi - NFC - </d:networking> - <d:sensors> - Accelerometer - Barometer - Gyroscope - Compass - GPS - ProximitySensor - </d:sensors> - <d:mic>true</d:mic> - <d:camera> - <d:location>back</d:location> - <d:autofocus>true</d:autofocus> - <d:flash>true</d:flash> - </d:camera> - <d:keyboard>nokeys</d:keyboard> - <d:nav>trackball</d:nav> - <d:ram unit="MiB">512</d:ram> - <d:buttons>hard</d:buttons> - <d:internal-storage unit="GiB">8</d:internal-storage> - <d:removable-storage unit="MiB"></d:removable-storage> - <d:cpu>OMAP 9001</d:cpu> - <d:gpu>Ultra Nexus 3D S++</d:gpu> - <d:abi> - armeabi - armeabi-v7a - mips - x86 - </d:abi> - <d:dock> - car - television - desk - </d:dock> - <d:power-type>battery</d:power-type> - </d:hardware> - - <d:software> - <d:api-level>-</d:api-level> - <d:live-wallpaper-support>true</d:live-wallpaper-support> - <d:bluetooth-profiles /> - <d:gl-version>2.1</d:gl-version> - <d:gl-extensions /> - <d:status-bar>true</d:status-bar> - </d:software> - - <d:state name="Portrait" default="true"> - <d:description>The phone in portrait view</d:description> - <d:screen-orientation>port</d:screen-orientation> - <d:keyboard-state>keyssoft</d:keyboard-state> - <d:nav-state>navexposed</d:nav-state> - </d:state> - <d:state name="Landscape"> - <d:description>The phone in landscape view</d:description> - <d:screen-orientation>land</d:screen-orientation> - <d:keyboard-state>keyssoft</d:keyboard-state> - <d:nav-state>navexposed</d:nav-state> - </d:state> - </d:device> - - <d:device> - <d:name> - 3.7 FWVGA slider - </d:name> - <d:manufacturer> - Generic - </d:manufacturer> - <d:hardware> - <d:screen> - <d:screen-size>normal</d:screen-size> - <d:diagonal-length>3.7</d:diagonal-length> - <d:pixel-density>hdpi</d:pixel-density> - <d:screen-ratio>long</d:screen-ratio> - <d:dimensions> - <d:x-dimension>480</d:x-dimension> - <d:y-dimension>854</d:y-dimension> - </d:dimensions> - <d:xdpi>265</d:xdpi> - <d:ydpi>265</d:ydpi> - <d:touch> - <d:multitouch>distinct</d:multitouch> - <d:mechanism>finger</d:mechanism> - <d:screen-type>capacitive</d:screen-type> - </d:touch> - </d:screen> - <d:networking> - Bluetooth - Wifi - NFC - </d:networking> - <d:sensors> - Accelerometer - Barometer - Gyroscope - Compass - GPS - ProximitySensor - </d:sensors> - <d:mic>true</d:mic> - <d:camera> - <d:location>back</d:location> - <d:autofocus>true</d:autofocus> - <d:flash>true</d:flash> - </d:camera> - <d:keyboard>qwerty</d:keyboard> - <d:nav>nonav</d:nav> - <d:ram unit="MiB">512</d:ram> - <d:buttons>hard</d:buttons> - <d:internal-storage unit="GiB">8</d:internal-storage> - <d:removable-storage unit="MiB"></d:removable-storage> - <d:cpu>OMAP 9001</d:cpu> - <d:gpu>Ultra Nexus 3D S++</d:gpu> - <d:abi> - armeabi - armeabi-v7a - mips - x86 - </d:abi> - <d:dock> - car - television - desk - </d:dock> - <d:power-type>battery</d:power-type> - </d:hardware> - - <d:software> - <d:api-level>-</d:api-level> - <d:live-wallpaper-support>true</d:live-wallpaper-support> - <d:bluetooth-profiles /> - <d:gl-version>2.1</d:gl-version> - <d:gl-extensions /> - <d:status-bar>true</d:status-bar> - </d:software> - - <d:state name="Portrait" default="true"> - <d:description>The phone in portrait view</d:description> - <d:screen-orientation>port</d:screen-orientation> - <d:keyboard-state>keyshidden</d:keyboard-state> - <d:nav-state>navhidden</d:nav-state> - </d:state> - <d:state name="Landscape, closed"> - <d:description>The phone in landscape view with the keyboard closed</d:description> - <d:screen-orientation>land</d:screen-orientation> - <d:keyboard-state>keyshidden</d:keyboard-state> - <d:nav-state>navhidden</d:nav-state> - </d:state> - <d:state name="Landscape, open"> - <d:description>The phone in landscape view with the keyboard open</d:description> - <d:screen-orientation>land</d:screen-orientation> - <d:keyboard-state>keysexposed</d:keyboard-state> - <d:nav-state>navexposed</d:nav-state> - </d:state> - </d:device> - - <d:device> - <d:name> - 4in WVGA (Nexus S) - </d:name> - <d:manufacturer> - Generic - </d:manufacturer> - <d:hardware> - <d:screen> - <d:screen-size>normal</d:screen-size> - <d:diagonal-length>4.0</d:diagonal-length> - <d:pixel-density>hdpi</d:pixel-density> - <d:screen-ratio>long</d:screen-ratio> - <d:dimensions> - <d:x-dimension>480</d:x-dimension> - <d:y-dimension>800</d:y-dimension> - </d:dimensions> - <d:xdpi>235</d:xdpi> - <d:ydpi>235</d:ydpi> - <d:touch> - <d:multitouch>distinct</d:multitouch> - <d:mechanism>finger</d:mechanism> - <d:screen-type>capacitive</d:screen-type> - </d:touch> - </d:screen> - <d:networking> - Bluetooth - Wifi - NFC - </d:networking> - <d:sensors> - Accelerometer - Barometer - Gyroscope - Compass - GPS - ProximitySensor - </d:sensors> - <d:mic>true</d:mic> - <d:camera> - <d:location>back</d:location> - <d:autofocus>true</d:autofocus> - <d:flash>true</d:flash> - </d:camera> - <d:keyboard>nokeys</d:keyboard> - <d:nav>nonav</d:nav> - <d:ram unit="MiB">512</d:ram> - <d:buttons>hard</d:buttons> - <d:internal-storage unit="GiB">8</d:internal-storage> - <d:removable-storage unit="MiB"></d:removable-storage> - <d:cpu>OMAP 9001</d:cpu> - <d:gpu>Ultra Nexus 3D S++</d:gpu> - <d:abi> - armeabi - armeabi-v7a - mips - x86 - </d:abi> - <d:dock> - car - television - desk - </d:dock> - <d:power-type>battery</d:power-type> - </d:hardware> - - <d:software> - <d:api-level>-</d:api-level> - <d:live-wallpaper-support>true</d:live-wallpaper-support> - <d:bluetooth-profiles /> - <d:gl-version>2.1</d:gl-version> - <d:gl-extensions /> - <d:status-bar>true</d:status-bar> - </d:software> - - <d:state name="Portrait" default="true"> - <d:description>The phone in portrait view</d:description> - <d:screen-orientation>port</d:screen-orientation> - <d:keyboard-state>keyssoft</d:keyboard-state> - <d:nav-state>navhidden</d:nav-state> - </d:state> - <d:state name="Landscape"> - <d:description>The phone in landscape view</d:description> - <d:screen-orientation>land</d:screen-orientation> - <d:keyboard-state>keyssoft</d:keyboard-state> - <d:nav-state>navhidden</d:nav-state> - </d:state> - </d:device> - - <d:device> - <d:name> - 4.65in 720p (Galaxy Nexus) - </d:name> - <d:manufacturer> - Generic - </d:manufacturer> - <d:hardware> - <d:screen> - <d:screen-size>normal</d:screen-size> - <d:diagonal-length>4.65</d:diagonal-length> <!-- In inches --> - <d:pixel-density>xhdpi</d:pixel-density> - <d:screen-ratio>long</d:screen-ratio> - <d:dimensions> - <d:x-dimension>720</d:x-dimension> - <d:y-dimension>1280</d:y-dimension> - </d:dimensions> - <d:xdpi>316</d:xdpi> - <d:ydpi>316</d:ydpi> - <d:touch> - <d:multitouch>jazz-hands</d:multitouch> - <d:mechanism>finger</d:mechanism> - <d:screen-type>capacitive</d:screen-type> - </d:touch> - </d:screen> - <d:networking> - Bluetooth - Wifi - NFC - </d:networking> - <d:sensors> - Accelerometer - Barometer - Gyroscope - Compass - GPS - ProximitySensor - </d:sensors> - <d:mic>true</d:mic> - <d:camera> - <d:location>front</d:location> - <d:autofocus>true</d:autofocus> - <d:flash>false</d:flash> - </d:camera> - <d:camera> - <d:location>back</d:location> - <d:autofocus>true</d:autofocus> - <d:flash>true</d:flash> - </d:camera> - <d:keyboard>nokeys</d:keyboard> - <d:nav>nonav</d:nav> - <d:ram unit="GiB">1</d:ram> - <d:buttons>soft</d:buttons> - <d:internal-storage unit="GiB">16</d:internal-storage> - <d:removable-storage unit="KiB"></d:removable-storage> - <d:cpu>OMAP 4460</d:cpu> <!-- cpu type (Tegra3) freeform --> - <d:gpu>PowerVR SGX540</d:gpu> - <d:abi> - armeabi - armeabi-v7a - </d:abi> - <!--dock (car, desk, tv, none)--> - <d:dock> - car - desk - </d:dock> - <!-- plugged in (never, charge, always) --> - <d:power-type>battery</d:power-type> - </d:hardware> - <d:software> - <d:api-level>14-</d:api-level> - <d:live-wallpaper-support>true</d:live-wallpaper-support> - <d:bluetooth-profiles> - HSP - HFP - SPP - A2DP - AVRCP - OPP - PBAP - GAVDP - AVDTP - HID - HDP - PAN - </d:bluetooth-profiles> - <d:gl-version>2.0</d:gl-version> - <!-- - These can be gotten via - javax.microedition.khronos.opengles.GL10.glGetString(GL10.GL_EXTENSIONS); - --> - <d:gl-extensions> - GL_EXT_discard_framebuffer - GL_EXT_multi_draw_arrays - GL_EXT_shader_texture_lod - GL_EXT_texture_format_BGRA8888 - GL_IMG_multisampled_render_to_texture - GL_IMG_program_binary - GL_IMG_read_format - GL_IMG_shader_binary - GL_IMG_texture_compression_pvrtc - GL_IMG_texture_format_BGRA8888 - GL_IMG_texture_npot - GL_OES_compressed_ETC1_RGB8_texture - GL_OES_depth_texture - GL_OES_depth24 - GL_OES_EGL_image - GL_OES_EGL_image_external - GL_OES_egl_sync - GL_OES_element_index_uint - GL_OES_fragment_precision_high - GL_OES_get_program_binary - GL_OES_mapbuffer - GL_OES_packed_depth_stencil - GL_OES_required_internalformat - GL_OES_rgb8_rgba8 - GL_OES_standard_derivatives - GL_OES_texture_float - GL_OES_texture_half_float - GL_OES_vertex_array_object - GL_OES_vertex_half_float - </d:gl-extensions> - <d:status-bar>true</d:status-bar> - </d:software> - <d:state name="Portrait" default="true"> - <d:description>The phone in portrait view</d:description> - <d:screen-orientation>port</d:screen-orientation> - <d:keyboard-state>keyssoft</d:keyboard-state> - <d:nav-state>nonav</d:nav-state> - </d:state> - <d:state name="Landscape"> - <d:description>The phone in landscape view</d:description> - <d:screen-orientation>land</d:screen-orientation> - <d:keyboard-state>keyssoft</d:keyboard-state> - <d:nav-state>nonav</d:nav-state> - </d:state> - </d:device> - - <d:device> - <d:name> - 4.7in WXGA - </d:name> - <d:manufacturer> - Generic - </d:manufacturer> - <d:hardware> - <d:screen> - <d:screen-size>normal</d:screen-size> - <d:diagonal-length>4.7</d:diagonal-length> - <d:pixel-density>xhdpi</d:pixel-density> - <d:screen-ratio>long</d:screen-ratio> - <d:dimensions> - <d:x-dimension>1280</d:x-dimension> - <d:y-dimension>720</d:y-dimension> - </d:dimensions> - <d:xdpi>320</d:xdpi> - <d:ydpi>320</d:ydpi> - <d:touch> - <d:multitouch>distinct</d:multitouch> - <d:mechanism>finger</d:mechanism> - <d:screen-type>capacitive</d:screen-type> - </d:touch> - </d:screen> - <d:networking> - Bluetooth - Wifi - NFC - </d:networking> - <d:sensors> - Accelerometer - Barometer - Gyroscope - Compass - GPS - ProximitySensor - </d:sensors> - <d:mic>true</d:mic> - <d:camera> - <d:location>back</d:location> - <d:autofocus>true</d:autofocus> - <d:flash>true</d:flash> - </d:camera> - <d:keyboard>nokeys</d:keyboard> - <d:nav>nonav</d:nav> - <d:ram unit="MiB">512</d:ram> - <d:buttons>hard</d:buttons> - <d:internal-storage unit="GiB">8</d:internal-storage> - <d:removable-storage unit="MiB"></d:removable-storage> - <d:cpu>OMAP 9001</d:cpu> - <d:gpu>Ultra Nexus 3D S++</d:gpu> - <d:abi> - armeabi - armeabi-v7a - mips - x86 - </d:abi> - <d:dock> - car - television - desk - </d:dock> - <d:power-type>battery</d:power-type> - </d:hardware> - - <d:software> - <d:api-level>-</d:api-level> - <d:live-wallpaper-support>true</d:live-wallpaper-support> - <d:bluetooth-profiles /> - <d:gl-version>2.1</d:gl-version> - <d:gl-extensions /> - <d:status-bar>true</d:status-bar> - </d:software> - - <d:state name="Portrait" default="true"> - <d:description>The phone in portrait view</d:description> - <d:screen-orientation>port</d:screen-orientation> - <d:keyboard-state>keyssoft</d:keyboard-state> - <d:nav-state>navhidden</d:nav-state> - </d:state> - <d:state name="Landscape"> - <d:description>The phone in landscape view</d:description> - <d:screen-orientation>land</d:screen-orientation> - <d:keyboard-state>keyssoft</d:keyboard-state> - <d:nav-state>navhidden</d:nav-state> - </d:state> - </d:device> - - <d:device> - <d:name> - 5.1in WVGA - </d:name> - <d:manufacturer> - Generic - </d:manufacturer> - <d:hardware> - <d:screen> - <d:screen-size>large</d:screen-size> - <d:diagonal-length>5.1</d:diagonal-length> - <d:pixel-density>mdpi</d:pixel-density> - <d:screen-ratio>long</d:screen-ratio> - <d:dimensions> - <d:x-dimension>480</d:x-dimension> - <d:y-dimension>800</d:y-dimension> - </d:dimensions> - <d:xdpi>183</d:xdpi> - <d:ydpi>183</d:ydpi> - <d:touch> - <d:multitouch>distinct</d:multitouch> - <d:mechanism>finger</d:mechanism> - <d:screen-type>capacitive</d:screen-type> - </d:touch> - </d:screen> - <d:networking> - Bluetooth - Wifi - NFC - </d:networking> - <d:sensors> - Accelerometer - Barometer - Gyroscope - Compass - GPS - ProximitySensor - </d:sensors> - <d:mic>true</d:mic> - <d:camera> - <d:location>back</d:location> - <d:autofocus>true</d:autofocus> - <d:flash>true</d:flash> - </d:camera> - <d:keyboard>nokeys</d:keyboard> - <d:nav>nonav</d:nav> - <d:ram unit="MiB">512</d:ram> - <d:buttons>hard</d:buttons> - <d:internal-storage unit="GiB">8</d:internal-storage> - <d:removable-storage unit="MiB"></d:removable-storage> - <d:cpu>OMAP 9001</d:cpu> - <d:gpu>Ultra Nexus 3D S++</d:gpu> - <d:abi> - armeabi - armeabi-v7a - mips - x86 - </d:abi> - <d:dock> - car - television - desk - </d:dock> - <d:power-type>battery</d:power-type> - </d:hardware> - - <d:software> - <d:api-level>-</d:api-level> - <d:live-wallpaper-support>true</d:live-wallpaper-support> - <d:bluetooth-profiles /> - <d:gl-version>2.1</d:gl-version> - <d:gl-extensions /> - <d:status-bar>true</d:status-bar> - </d:software> - - <d:state name="Portrait" default="true"> - <d:description>The phone in portrait view</d:description> - <d:screen-orientation>port</d:screen-orientation> - <d:keyboard-state>keyssoft</d:keyboard-state> - <d:nav-state>navhidden</d:nav-state> - </d:state> - <d:state name="Landscape"> - <d:description>The phone in landscape view</d:description> - <d:screen-orientation>land</d:screen-orientation> - <d:keyboard-state>keyssoft</d:keyboard-state> - <d:nav-state>navhidden</d:nav-state> - </d:state> - </d:device> - - <d:device> - <d:name> - 5.4in FWVGA - </d:name> - <d:manufacturer> - Generic - </d:manufacturer> - <d:hardware> - <d:screen> - <d:screen-size>large</d:screen-size> - <d:diagonal-length>5.4</d:diagonal-length> - <d:pixel-density>mdpi</d:pixel-density> - <d:screen-ratio>long</d:screen-ratio> - <d:dimensions> - <d:x-dimension>480</d:x-dimension> - <d:y-dimension>854</d:y-dimension> - </d:dimensions> - <d:xdpi>181</d:xdpi> - <d:ydpi>181</d:ydpi> - <d:touch> - <d:multitouch>distinct</d:multitouch> - <d:mechanism>finger</d:mechanism> - <d:screen-type>capacitive</d:screen-type> - </d:touch> - </d:screen> - <d:networking> - Bluetooth - Wifi - NFC - </d:networking> - <d:sensors> - Accelerometer - Barometer - Gyroscope - Compass - GPS - ProximitySensor - </d:sensors> - <d:mic>true</d:mic> - <d:camera> - <d:location>back</d:location> - <d:autofocus>true</d:autofocus> - <d:flash>true</d:flash> - </d:camera> - <d:keyboard>nokeys</d:keyboard> - <d:nav>nonav</d:nav> - <d:ram unit="MiB">512</d:ram> - <d:buttons>hard</d:buttons> - <d:internal-storage unit="GiB">8</d:internal-storage> - <d:removable-storage unit="MiB"></d:removable-storage> - <d:cpu>OMAP 9001</d:cpu> - <d:gpu>Ultra Nexus 3D S++</d:gpu> - <d:abi> - armeabi - armeabi-v7a - mips - x86 - </d:abi> - <d:dock> - car - television - desk - </d:dock> - <d:power-type>battery</d:power-type> - </d:hardware> - - <d:software> - <d:api-level>-</d:api-level> - <d:live-wallpaper-support>true</d:live-wallpaper-support> - <d:bluetooth-profiles /> - <d:gl-version>2.1</d:gl-version> - <d:gl-extensions /> - <d:status-bar>true</d:status-bar> - </d:software> - - <d:state name="Portrait" default="true"> - <d:description>The phone in portrait view</d:description> - <d:screen-orientation>port</d:screen-orientation> - <d:keyboard-state>keyssoft</d:keyboard-state> - <d:nav-state>navhidden</d:nav-state> - </d:state> - <d:state name="Landscape"> - <d:description>The phone in landscape view</d:description> - <d:screen-orientation>land</d:screen-orientation> - <d:keyboard-state>keyssoft</d:keyboard-state> - <d:nav-state>navhidden</d:nav-state> - </d:state> - </d:device> - - <d:device> - <d:name> - 7in WSVGA (Tablet) - </d:name> - <d:manufacturer> - Generic - </d:manufacturer> - <d:hardware> - <d:screen> - <d:screen-size>large</d:screen-size> - <d:diagonal-length>7.0</d:diagonal-length> - <d:pixel-density>mdpi</d:pixel-density> - <d:screen-ratio>long</d:screen-ratio> - <d:dimensions> - <d:x-dimension>1024</d:x-dimension> - <d:y-dimension>600</d:y-dimension> - </d:dimensions> - <d:xdpi>169</d:xdpi> - <d:ydpi>169</d:ydpi> - <d:touch> - <d:multitouch>distinct</d:multitouch> - <d:mechanism>finger</d:mechanism> - <d:screen-type>capacitive</d:screen-type> - </d:touch> - </d:screen> - <d:networking> - Bluetooth - Wifi - NFC - </d:networking> - <d:sensors> - Accelerometer - Barometer - Gyroscope - Compass - GPS - ProximitySensor - </d:sensors> - <d:mic>true</d:mic> - <d:camera> - <d:location>front</d:location> - <d:autofocus>true</d:autofocus> - <d:flash>true</d:flash> - </d:camera> - <d:keyboard>nokeys</d:keyboard> - <d:nav>nonav</d:nav> - <d:ram unit="MiB">512</d:ram> - <d:buttons>soft</d:buttons> - <d:internal-storage unit="GiB">8</d:internal-storage> - <d:removable-storage unit="MiB"></d:removable-storage> - <d:cpu>OMAP 9001</d:cpu> - <d:gpu>Ultra Nexus 3D S++</d:gpu> - <d:abi> - armeabi - armeabi-v7a - mips - x86 - </d:abi> - <d:dock> - car - television - desk - </d:dock> - <d:power-type>battery</d:power-type> - </d:hardware> - - <d:software> - <d:api-level>-</d:api-level> - <d:live-wallpaper-support>true</d:live-wallpaper-support> - <d:bluetooth-profiles /> - <d:gl-version>2.1</d:gl-version> - <d:gl-extensions /> - <d:status-bar>true</d:status-bar> - </d:software> - - <d:state name="Portrait" default="true"> - <d:description>The phone in portrait view</d:description> - <d:screen-orientation>port</d:screen-orientation> - <d:keyboard-state>keyssoft</d:keyboard-state> - <d:nav-state>navhidden</d:nav-state> - </d:state> - <d:state name="Landscape"> - <d:description>The phone in landscape view</d:description> - <d:screen-orientation>land</d:screen-orientation> - <d:keyboard-state>keyssoft</d:keyboard-state> - <d:nav-state>navhidden</d:nav-state> - </d:state> - </d:device> - - - <d:device> - <d:name> - 10.1in WXGA (Tablet) - </d:name> - <d:manufacturer> - Generic - </d:manufacturer> - <d:hardware> - <d:screen> - <d:screen-size>xlarge</d:screen-size> - <d:diagonal-length>10.1</d:diagonal-length> - <d:pixel-density>mdpi</d:pixel-density> - <d:screen-ratio>long</d:screen-ratio> - <d:dimensions> - <d:x-dimension>1280</d:x-dimension> - <d:y-dimension>800</d:y-dimension> - </d:dimensions> - <d:xdpi>149</d:xdpi> - <d:ydpi>149</d:ydpi> - <d:touch> - <d:multitouch>distinct</d:multitouch> - <d:mechanism>finger</d:mechanism> - <d:screen-type>capacitive</d:screen-type> - </d:touch> - </d:screen> - <d:networking> - Bluetooth - Wifi - NFC - </d:networking> - <d:sensors> - Accelerometer - Barometer - Gyroscope - Compass - GPS - ProximitySensor - </d:sensors> - <d:mic>true</d:mic> - <d:camera> - <d:location>front</d:location> - <d:autofocus>true</d:autofocus> - <d:flash>true</d:flash> - </d:camera> - <d:camera> - <d:location>back</d:location> - <d:autofocus>true</d:autofocus> - <d:flash>true</d:flash> - </d:camera> - <d:keyboard>nokeys</d:keyboard> - <d:nav>nonav</d:nav> - <d:ram unit="MiB">512</d:ram> - <d:buttons>soft</d:buttons> - <d:internal-storage unit="GiB">8</d:internal-storage> - <d:removable-storage unit="MiB"></d:removable-storage> - <d:cpu>OMAP 9001</d:cpu> - <d:gpu>Ultra Nexus 3D S++</d:gpu> - <d:abi> - armeabi - armeabi-v7a - mips - x86 - </d:abi> - <d:dock> - car - television - desk - </d:dock> - <d:power-type>battery</d:power-type> - </d:hardware> - - <d:software> - <d:api-level>-</d:api-level> - <d:live-wallpaper-support>true</d:live-wallpaper-support> - <d:bluetooth-profiles /> - <d:gl-version>2.1</d:gl-version> - <d:gl-extensions /> - <d:status-bar>true</d:status-bar> - </d:software> - - <d:state name="Portrait" default="true"> - <d:description>The phone in portrait view</d:description> - <d:screen-orientation>port</d:screen-orientation> - <d:keyboard-state>keyssoft</d:keyboard-state> - <d:nav-state>navhidden</d:nav-state> - </d:state> - <d:state name="Landscape"> - <d:description>The phone in landscape view</d:description> - <d:screen-orientation>land</d:screen-orientation> - <d:keyboard-state>keyssoft</d:keyboard-state> - <d:nav-state>navhidden</d:nav-state> - </d:state> - </d:device> -</d:devices> diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/avd/AvdInfo.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/avd/AvdInfo.java deleted file mode 100755 index 83aa2ef..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/avd/AvdInfo.java +++ /dev/null @@ -1,350 +0,0 @@ -/* - * Copyright (C) 2008 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.avd; - -import com.android.SdkConstants; -import com.android.prefs.AndroidLocation.AndroidLocationException; -import com.android.sdklib.IAndroidTarget; -import com.android.sdklib.devices.Device; - -import java.io.File; -import java.util.Collections; -import java.util.Map; - -/** - * An immutable structure describing an Android Virtual Device. - */ -public final class AvdInfo implements Comparable<AvdInfo> { - - /** - * Status for an {@link AvdInfo}. Indicates whether or not this AVD is valid. - */ - public static enum AvdStatus { - /** No error */ - OK, - /** Missing 'path' property in the ini file */ - ERROR_PATH, - /** Missing config.ini file in the AVD data folder */ - ERROR_CONFIG, - /** Missing 'target' property in the ini file */ - ERROR_TARGET_HASH, - /** Target was not resolved from its hash */ - ERROR_TARGET, - /** Unable to parse config.ini */ - ERROR_PROPERTIES, - /** System Image folder in config.ini doesn't exist */ - ERROR_IMAGE_DIR, - /** The {@link Device} this AVD is based on has changed from its original configuration*/ - ERROR_DEVICE_CHANGED, - /** The {@link Device} this AVD is based on is no longer available */ - ERROR_DEVICE_MISSING; - } - - private final String mName; - private final File mIniFile; - private final String mFolderPath; - private final String mTargetHash; - private final IAndroidTarget mTarget; - private final String mAbiType; - /** An immutable map of properties. This must not be modified. Map can be empty. Never null. */ - private final Map<String, String> mProperties; - private final AvdStatus mStatus; - - /** - * Creates a new valid AVD info. Values are immutable. - * <p/> - * Such an AVD is available and can be used. - * The error string is set to null. - * - * @param name The name of the AVD (for display or reference) - * @param iniFile The path to the config.ini file - * @param folderPath The path to the data directory - * @param targetHash the target hash - * @param target The target. Can be null, if the target was not resolved. - * @param abiType Name of the abi. - * @param properties The property map. If null, an empty map will be created. - */ - public AvdInfo(String name, - File iniFile, - String folderPath, - String targetHash, - IAndroidTarget target, - String abiType, - Map<String, String> properties) { - this(name, iniFile, folderPath, targetHash, target, abiType, properties, AvdStatus.OK); - } - - /** - * Creates a new <em>invalid</em> AVD info. Values are immutable. - * <p/> - * Such an AVD is not complete and cannot be used. - * The error string must be non-null. - * - * @param name The name of the AVD (for display or reference) - * @param iniFile The path to the config.ini file - * @param folderPath The path to the data directory - * @param targetHash the target hash - * @param target The target. Can be null, if the target was not resolved. - * @param abiType Name of the abi. - * @param properties The property map. If null, an empty map will be created. - * @param status The {@link AvdStatus} of this AVD. Cannot be null. - */ - public AvdInfo(String name, - File iniFile, - String folderPath, - String targetHash, - IAndroidTarget target, - String abiType, - Map<String, String> properties, - AvdStatus status) { - mName = name; - mIniFile = iniFile; - mFolderPath = folderPath; - mTargetHash = targetHash; - mTarget = target; - mAbiType = abiType; - mProperties = properties == null ? Collections.<String, String>emptyMap() - : Collections.unmodifiableMap(properties); - mStatus = status; - } - - /** Returns the name of the AVD. */ - public String getName() { - return mName; - } - - /** Returns the path of the AVD data directory. */ - public String getDataFolderPath() { - return mFolderPath; - } - - /** Returns the processor type of the AVD. */ - public String getAbiType() { - return mAbiType; - } - - public String getCpuArch() { - String cpuArch = mProperties.get(AvdManager.AVD_INI_CPU_ARCH); - if (cpuArch != null) { - return cpuArch; - } - - // legacy - return SdkConstants.CPU_ARCH_ARM; - } - - public String getDeviceManufacturer() { - String deviceManufacturer = mProperties.get(AvdManager.AVD_INI_DEVICE_MANUFACTURER); - if (deviceManufacturer != null && !deviceManufacturer.isEmpty()) { - return deviceManufacturer; - } - - return ""; - } - - public String getDeviceName() { - String deviceName = mProperties.get(AvdManager.AVD_INI_DEVICE_NAME); - if (deviceName != null && !deviceName.isEmpty()) { - return deviceName; - } - - return ""; - } - - /** Convenience function to return a more user friendly name of the abi type. */ - public static String getPrettyAbiType(String raw) { - String s = null; - if (raw.equalsIgnoreCase(SdkConstants.ABI_ARMEABI)) { - s = "ARM (" + SdkConstants.ABI_ARMEABI + ")"; - - } else if (raw.equalsIgnoreCase(SdkConstants.ABI_ARMEABI_V7A)) { - s = "ARM (" + SdkConstants.ABI_ARMEABI_V7A + ")"; - - } else if (raw.equalsIgnoreCase(SdkConstants.ABI_INTEL_ATOM)) { - s = "Intel Atom (" + SdkConstants.ABI_INTEL_ATOM + ")"; - - } else if (raw.equalsIgnoreCase(SdkConstants.ABI_MIPS)) { - s = "MIPS (" + SdkConstants.ABI_MIPS + ")"; - - } else { - s = raw + " (" + raw + ")"; - } - return s; - } - - /** - * Returns the target hash string. - */ - public String getTargetHash() { - return mTargetHash; - } - - /** Returns the target of the AVD, or <code>null</code> if it has not been resolved. */ - public IAndroidTarget getTarget() { - return mTarget; - } - - /** Returns the {@link AvdStatus} of the receiver. */ - public AvdStatus getStatus() { - return mStatus; - } - - /** - * Helper method that returns the default AVD folder that would be used for a given - * AVD name <em>if and only if</em> the AVD was created with the default choice. - * <p/> - * Callers must NOT use this to "guess" the actual folder from an actual AVD since - * the purpose of the AVD .ini file is to be able to change this folder. Callers - * should however use this to create a new {@link AvdInfo} to setup its data folder - * to the default. - * <p/> - * The default is {@code getDefaultAvdFolder()/avdname.avd/}. - * <p/> - * For an actual existing AVD, callers must use {@link #getDataFolderPath()} instead. - * - * @param manager The AVD Manager, used to get the AVD storage path. - * @param avdName The name of the desired AVD. - * @throws AndroidLocationException if there's a problem getting android root directory. - */ - public static File getDefaultAvdFolder(AvdManager manager, String avdName) - throws AndroidLocationException { - return new File(manager.getBaseAvdFolder(), - avdName + AvdManager.AVD_FOLDER_EXTENSION); - } - - /** - * Helper method that returns the .ini {@link File} for a given AVD name. - * <p/> - * The default is {@code getDefaultAvdFolder()/avdname.ini}. - * - * @param manager The AVD Manager, used to get the AVD storage path. - * @param avdName The name of the desired AVD. - * @throws AndroidLocationException if there's a problem getting android root directory. - */ - public static File getDefaultIniFile(AvdManager manager, String avdName) - throws AndroidLocationException { - String avdRoot = manager.getBaseAvdFolder(); - return new File(avdRoot, avdName + AvdManager.INI_EXTENSION); - } - - /** - * Returns the .ini {@link File} for this AVD. - */ - public File getIniFile() { - return mIniFile; - } - - /** - * Helper method that returns the Config {@link File} for a given AVD name. - */ - public static File getConfigFile(String path) { - return new File(path, AvdManager.CONFIG_INI); - } - - /** - * Returns the Config {@link File} for this AVD. - */ - public File getConfigFile() { - return getConfigFile(mFolderPath); - } - - /** - * Returns an unmodifiable map of properties for the AVD. - * This can be empty but not null. - * Callers must NOT try to modify this immutable map. - */ - public Map<String, String> getProperties() { - return mProperties; - } - - /** - * Returns the error message for the AVD or <code>null</code> if {@link #getStatus()} - * returns {@link AvdStatus#OK} - */ - public String getErrorMessage() { - switch (mStatus) { - case ERROR_PATH: - return String.format("Missing AVD 'path' property in %1$s", getIniFile()); - case ERROR_CONFIG: - return String.format("Missing config.ini file in %1$s", mFolderPath); - case ERROR_TARGET_HASH: - return String.format("Missing 'target' property in %1$s", getIniFile()); - case ERROR_TARGET: - return String.format("Unknown target '%1$s' in %2$s", - mTargetHash, getIniFile()); - case ERROR_PROPERTIES: - return String.format("Failed to parse properties from %1$s", - getConfigFile()); - case ERROR_IMAGE_DIR: - return String.format( - "Invalid value in image.sysdir. Run 'android update avd -n %1$s'", - mName); - case ERROR_DEVICE_CHANGED: - return String.format("%1$s %2$s configuration has changed since AVD creation", - mProperties.get(AvdManager.AVD_INI_DEVICE_MANUFACTURER), - mProperties.get(AvdManager.AVD_INI_DEVICE_NAME)); - case ERROR_DEVICE_MISSING: - return String.format("%1$s %2$s no longer exists as a device", - mProperties.get(AvdManager.AVD_INI_DEVICE_MANUFACTURER), - mProperties.get(AvdManager.AVD_INI_DEVICE_NAME)); - case OK: - assert false; - return null; - } - - return null; - } - - /** - * Returns whether an emulator is currently running the AVD. - */ - public boolean isRunning() { - File f = new File(mFolderPath, "userdata-qemu.img.lock"); //$NON-NLS-1$ - return f.isFile(); - } - - /** - * Compares this object with the specified object for order. Returns a - * negative integer, zero, or a positive integer as this object is less - * than, equal to, or greater than the specified object. - * - * @param o the Object to be compared. - * @return a negative integer, zero, or a positive integer as this object is - * less than, equal to, or greater than the specified object. - */ - @Override - public int compareTo(AvdInfo o) { - // first handle possible missing targets (if the AVD failed to load for unresolved targets) - if (mTarget == null && o != null && o.mTarget == null) { - return 0; - } if (mTarget == null) { - return +1; - } else if (o == null || o.mTarget == null) { - return -1; - } - - // then compare the targets - int targetDiff = mTarget.compareTo(o.mTarget); - - if (targetDiff == 0) { - // same target? compare on the avd name - return mName.compareTo(o.mName); - } - - return targetDiff; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/avd/AvdManager.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/avd/AvdManager.java deleted file mode 100644 index eae4eea..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/avd/AvdManager.java +++ /dev/null @@ -1,1859 +0,0 @@ -/* - * Copyright (C) 2008 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.avd; - -import com.android.SdkConstants; -import com.android.annotations.NonNull; -import com.android.annotations.Nullable; -import com.android.io.FileWrapper; -import com.android.io.IAbstractFile; -import com.android.io.StreamException; -import com.android.prefs.AndroidLocation; -import com.android.prefs.AndroidLocation.AndroidLocationException; -import com.android.sdklib.IAndroidTarget; -import com.android.sdklib.ISystemImage; -import com.android.sdklib.SdkManager; -import com.android.sdklib.devices.DeviceManager; -import com.android.sdklib.devices.DeviceManager.DeviceStatus; -import com.android.sdklib.internal.avd.AvdInfo.AvdStatus; -import com.android.sdklib.internal.project.ProjectProperties; -import com.android.sdklib.util.GrabProcessOutput; -import com.android.sdklib.util.GrabProcessOutput.IProcessOutput; -import com.android.sdklib.util.GrabProcessOutput.Wait; -import com.android.utils.ILogger; -import com.android.utils.Pair; -import com.google.common.base.Charsets; -import com.google.common.io.Closeables; - -import java.io.BufferedReader; -import java.io.File; -import java.io.FileInputStream; -import java.io.FileNotFoundException; -import java.io.FileOutputStream; -import java.io.FileWriter; -import java.io.FilenameFilter; -import java.io.IOException; -import java.io.InputStreamReader; -import java.io.OutputStreamWriter; -import java.nio.charset.Charset; -import java.util.ArrayList; -import java.util.Collections; -import java.util.HashMap; -import java.util.Map; -import java.util.Map.Entry; -import java.util.WeakHashMap; -import java.util.regex.Matcher; -import java.util.regex.Pattern; - -/** - * Android Virtual Device Manager to manage AVDs. - */ -public class AvdManager { - - /** - * Exception thrown when something is wrong with a target path. - */ - private static final class InvalidTargetPathException extends Exception { - private static final long serialVersionUID = 1L; - - InvalidTargetPathException(String message) { - super(message); - } - } - - private final static Pattern INI_LINE_PATTERN = - Pattern.compile("^([a-zA-Z0-9._-]+)\\s*=\\s*(.*)\\s*$"); //$NON-NLS-1$ - - public static final String AVD_FOLDER_EXTENSION = ".avd"; //$NON-NLS-1$ - - /** Charset encoding used by the avd.ini/config.ini. */ - public static final String AVD_INI_ENCODING = "avd.ini.encoding"; //$NON-NLS-1$ - - /** - * The *absolute* path to the AVD folder (which contains the #CONFIG_INI file). - */ - public static final String AVD_INFO_ABS_PATH = "path"; //$NON-NLS-1$ - - /** - * The path to the AVD folder (which contains the #CONFIG_INI file) relative to - * the {@link AndroidLocation#FOLDER_DOT_ANDROID}. This information is written - * in the avd ini <b>only</b> if the AVD folder is located under the .android path - * (that is the relative that has no backward {@code ..} references). - */ - public static final String AVD_INFO_REL_PATH = "path.rel"; //$NON-NLS-1$ - - /** - * The {@link IAndroidTarget#hashString()} of the AVD. - */ - public static final String AVD_INFO_TARGET = "target"; //$NON-NLS-1$ - - /** - * AVD/config.ini key name representing the abi type of the specific avd - * - */ - public static final String AVD_INI_ABI_TYPE = "abi.type"; //$NON-NLS-1$ - - /** - * AVD/config.ini key name representing the CPU architecture of the specific avd - * - */ - public static final String AVD_INI_CPU_ARCH = "hw.cpu.arch"; //$NON-NLS-1$ - - /** - * AVD/config.ini key name representing the CPU architecture of the specific avd - * - */ - public static final String AVD_INI_CPU_MODEL = "hw.cpu.model"; //$NON-NLS-1$ - - /** - * AVD/config.ini key name representing the manufacturer of the device this avd was based on. - */ - public static final String AVD_INI_DEVICE_MANUFACTURER = "hw.device.manufacturer"; //$NON-NLS-1$ - - /** - * AVD/config.ini key name representing the name of the device this avd was based on. - */ - public static final String AVD_INI_DEVICE_NAME = "hw.device.name"; //$NON-NLS-1$ - - /** - * AVD/config.ini key name representing the SDK-relative path of the skin folder, if any, - * or a 320x480 like constant for a numeric skin size. - * - * @see #NUMERIC_SKIN_SIZE - */ - public static final String AVD_INI_SKIN_PATH = "skin.path"; //$NON-NLS-1$ - /** - * AVD/config.ini key name representing an UI name for the skin. - * This config key is ignored by the emulator. It is only used by the SDK manager or - * tools to give a friendlier name to the skin. - * If missing, use the {@link #AVD_INI_SKIN_PATH} key instead. - */ - public static final String AVD_INI_SKIN_NAME = "skin.name"; //$NON-NLS-1$ - - /** - * AVD/config.ini key name representing whether a dynamic skin should be displayed. - */ - public static final String AVD_INI_SKIN_DYNAMIC = "skin.dynamic"; //$NON-NLS-1$ - - /** - * AVD/config.ini key name representing the path to the sdcard file. - * If missing, the default name "sdcard.img" will be used for the sdcard, if there's such - * a file. - * - * @see #SDCARD_IMG - */ - public static final String AVD_INI_SDCARD_PATH = "sdcard.path"; //$NON-NLS-1$ - /** - * AVD/config.ini key name representing the size of the SD card. - * This property is for UI purposes only. It is not used by the emulator. - * - * @see #SDCARD_SIZE_PATTERN - * @see #parseSdcardSize(String, String[]) - */ - public static final String AVD_INI_SDCARD_SIZE = "sdcard.size"; //$NON-NLS-1$ - /** - * AVD/config.ini key name representing the first path where the emulator looks - * for system images. Typically this is the path to the add-on system image or - * the path to the platform system image if there's no add-on. - * <p/> - * The emulator looks at {@link #AVD_INI_IMAGES_1} before {@link #AVD_INI_IMAGES_2}. - */ - public static final String AVD_INI_IMAGES_1 = "image.sysdir.1"; //$NON-NLS-1$ - /** - * AVD/config.ini key name representing the second path where the emulator looks - * for system images. Typically this is the path to the platform system image. - * - * @see #AVD_INI_IMAGES_1 - */ - public static final String AVD_INI_IMAGES_2 = "image.sysdir.2"; //$NON-NLS-1$ - /** - * AVD/config.ini key name representing the presence of the snapshots file. - * This property is for UI purposes only. It is not used by the emulator. - * - * @see #SNAPSHOTS_IMG - */ - public static final String AVD_INI_SNAPSHOT_PRESENT = "snapshot.present"; //$NON-NLS-1$ - - /** - * AVD/config.ini key name representing whether hardware OpenGLES emulation is enabled - */ - public static final String AVD_INI_GPU_EMULATION = "hw.gpu.enabled"; //$NON-NLS-1$ - - /** - * AVD/config.ini key name representing how to emulate the front facing camera - */ - public static final String AVD_INI_CAMERA_FRONT = "hw.camera.front"; //$NON-NLS-1$ - - /** - * AVD/config.ini key name representing how to emulate the rear facing camera - */ - public static final String AVD_INI_CAMERA_BACK = "hw.camera.back"; //$NON-NLS-1$ - - /** - * AVD/config.ini key name representing the amount of RAM the emulated device should have - */ - public static final String AVD_INI_RAM_SIZE = "hw.ramSize"; - - /** - * AVD/config.ini key name representing the amount of memory available to applications by default - */ - public static final String AVD_INI_VM_HEAP_SIZE = "vm.heapSize"; - - /** - * AVD/config.ini key name representing the size of the data partition - */ - public static final String AVD_INI_DATA_PARTITION_SIZE = "disk.dataPartition.size"; - - /** - * AVD/config.ini key name representing the hash of the device this AVD is based on - */ - public static final String AVD_INI_DEVICE_HASH = "hw.device.hash"; - - /** - * Pattern to match pixel-sized skin "names", e.g. "320x480". - */ - public static final Pattern NUMERIC_SKIN_SIZE = Pattern.compile("([0-9]{2,})x([0-9]{2,})"); //$NON-NLS-1$ - - private static final String USERDATA_IMG = "userdata.img"; //$NON-NLS-1$ - static final String CONFIG_INI = "config.ini"; //$NON-NLS-1$ - private static final String SDCARD_IMG = "sdcard.img"; //$NON-NLS-1$ - private static final String SNAPSHOTS_IMG = "snapshots.img"; //$NON-NLS-1$ - - static final String INI_EXTENSION = ".ini"; //$NON-NLS-1$ - private static final Pattern INI_NAME_PATTERN = Pattern.compile("(.+)\\" + //$NON-NLS-1$ - INI_EXTENSION + "$", //$NON-NLS-1$ - Pattern.CASE_INSENSITIVE); - - private static final Pattern IMAGE_NAME_PATTERN = Pattern.compile("(.+)\\.img$", //$NON-NLS-1$ - Pattern.CASE_INSENSITIVE); - - /** - * Pattern for matching SD Card sizes, e.g. "4K" or "16M". - * Callers should use {@link #parseSdcardSize(String, String[])} instead of using this directly. - */ - private static final Pattern SDCARD_SIZE_PATTERN = Pattern.compile("(\\d+)([KMG])"); //$NON-NLS-1$ - - /** - * Minimal size of an SDCard image file in bytes. Currently 9 MiB. - */ - - public static final long SDCARD_MIN_BYTE_SIZE = 9<<20; - /** - * Maximal size of an SDCard image file in bytes. Currently 1023 GiB. - */ - public static final long SDCARD_MAX_BYTE_SIZE = 1023L<<30; - - /** The sdcard string represents a valid number but the size is outside of the allowed range. */ - public static final int SDCARD_SIZE_NOT_IN_RANGE = 0; - /** The sdcard string looks like a size number+suffix but the number failed to decode. */ - public static final int SDCARD_SIZE_INVALID = -1; - /** The sdcard string doesn't look like a size, it might be a path instead. */ - public static final int SDCARD_NOT_SIZE_PATTERN = -2; - - /** Regex used to validate characters that compose an AVD name. */ - public static final Pattern RE_AVD_NAME = Pattern.compile("[a-zA-Z0-9._-]+"); //$NON-NLS-1$ - - /** List of valid characters for an AVD name. Used for display purposes. */ - public static final String CHARS_AVD_NAME = "a-z A-Z 0-9 . _ -"; //$NON-NLS-1$ - - public static final String HARDWARE_INI = "hardware.ini"; //$NON-NLS-1$ - - /** - * Status returned by {@link AvdManager#isAvdNameConflicting(String)}. - */ - public static enum AvdConflict { - /** There is no known conflict for the given AVD name. */ - NO_CONFLICT, - /** The AVD name conflicts with an existing valid AVD. */ - CONFLICT_EXISTING_AVD, - /** The AVD name conflicts with an existing invalid AVD. */ - CONFLICT_INVALID_AVD, - /** - * The AVD name does not conflict with any known AVD however there are - * files or directory that would cause a conflict if this were to be created. - */ - CONFLICT_EXISTING_PATH, - } - - // A map where the keys are the locations of the SDK and the values are the corresponding - // AvdManagers. This prevents us from creating multiple AvdManagers for the same SDK and having - // them get out of sync. - private static final Map<String, AvdManager> mManagers = - Collections.synchronizedMap(new WeakHashMap<String, AvdManager>()); - - private final ArrayList<AvdInfo> mAllAvdList = new ArrayList<AvdInfo>(); - private AvdInfo[] mValidAvdList; - private AvdInfo[] mBrokenAvdList; - private final SdkManager mSdkManager; - - /** - * Creates an AVD Manager for a given SDK represented by a {@link SdkManager}. - * @param sdkManager The SDK. - * @param log The log object to receive the log of the initial loading of the AVDs. - * This log object is not kept by this instance of AvdManager and each - * method takes its own logger. The rationale is that the AvdManager - * might be called from a variety of context, each with different - * logging needs. Cannot be null. - * @throws AndroidLocationException - */ - protected AvdManager(SdkManager sdkManager, ILogger log) throws AndroidLocationException { - mSdkManager = sdkManager; - buildAvdList(mAllAvdList, log); - } - - public static AvdManager getInstance(SdkManager sdkManager, ILogger log) - throws AndroidLocationException { - synchronized(mManagers) { - AvdManager manager; - if ((manager = mManagers.get(sdkManager.getLocation())) != null) { - return manager; - } - manager = new AvdManager(sdkManager, log); - mManagers.put(sdkManager.getLocation(), manager); - return manager; - } - } - - /** - * Returns the base folder where AVDs are created. - * - * @throws AndroidLocationException - */ - public String getBaseAvdFolder() throws AndroidLocationException { - assert AndroidLocation.getFolder().endsWith(File.separator); - return AndroidLocation.getFolder() + AndroidLocation.FOLDER_AVD; - } - - /** - * Returns the {@link SdkManager} associated with the {@link AvdManager}. - */ - public SdkManager getSdkManager() { - return mSdkManager; - } - - /** - * Parse the sdcard string to decode the size. - * Returns: - * <ul> - * <li> The size in bytes > 0 if the sdcard string is a valid size in the allowed range. - * <li> {@link #SDCARD_SIZE_NOT_IN_RANGE} (0) - * if the sdcard string is a valid size NOT in the allowed range. - * <li> {@link #SDCARD_SIZE_INVALID} (-1) - * if the sdcard string is number that fails to parse correctly. - * <li> {@link #SDCARD_NOT_SIZE_PATTERN} (-2) - * if the sdcard string is not a number, in which case it's probably a file path. - * </ul> - * - * @param sdcard The sdcard string, which can be a file path, a size string or something else. - * @param parsedStrings If non-null, an array of 2 strings. The first string will be - * filled with the parsed numeric size and the second one will be filled with the - * parsed suffix. This is filled even if the returned size is deemed out of range or - * failed to parse. The values are null if the sdcard is not a size pattern. - * @return A size in byte if > 0, or {@link #SDCARD_SIZE_NOT_IN_RANGE}, - * {@link #SDCARD_SIZE_INVALID} or {@link #SDCARD_NOT_SIZE_PATTERN} as error codes. - */ - public static long parseSdcardSize(String sdcard, String[] parsedStrings) { - - if (parsedStrings != null) { - assert parsedStrings.length == 2; - parsedStrings[0] = null; - parsedStrings[1] = null; - } - - Matcher m = SDCARD_SIZE_PATTERN.matcher(sdcard); - if (m.matches()) { - if (parsedStrings != null) { - assert parsedStrings.length == 2; - parsedStrings[0] = m.group(1); - parsedStrings[1] = m.group(2); - } - - // get the sdcard values for checks - try { - long sdcardSize = Long.parseLong(m.group(1)); - - String sdcardSizeModifier = m.group(2); - if ("K".equals(sdcardSizeModifier)) { //$NON-NLS-1$ - sdcardSize <<= 10; - } else if ("M".equals(sdcardSizeModifier)) { //$NON-NLS-1$ - sdcardSize <<= 20; - } else if ("G".equals(sdcardSizeModifier)) { //$NON-NLS-1$ - sdcardSize <<= 30; - } - - if (sdcardSize < SDCARD_MIN_BYTE_SIZE || - sdcardSize > SDCARD_MAX_BYTE_SIZE) { - return SDCARD_SIZE_NOT_IN_RANGE; - } - - return sdcardSize; - } catch (NumberFormatException e) { - // This could happen if the number is too large to fit in a long. - return SDCARD_SIZE_INVALID; - } - } - - return SDCARD_NOT_SIZE_PATTERN; - } - - /** - * Returns all the existing AVDs. - * @return a newly allocated array containing all the AVDs. - */ - public AvdInfo[] getAllAvds() { - synchronized (mAllAvdList) { - return mAllAvdList.toArray(new AvdInfo[mAllAvdList.size()]); - } - } - - /** - * Returns all the valid AVDs. - * @return a newly allocated array containing all valid the AVDs. - */ - public AvdInfo[] getValidAvds() { - synchronized (mAllAvdList) { - if (mValidAvdList == null) { - ArrayList<AvdInfo> list = new ArrayList<AvdInfo>(); - for (AvdInfo avd : mAllAvdList) { - if (avd.getStatus() == AvdStatus.OK) { - list.add(avd); - } - } - - mValidAvdList = list.toArray(new AvdInfo[list.size()]); - } - return mValidAvdList; - } - } - - /** - * Returns all the broken AVDs. - * @return a newly allocated array containing all the broken AVDs. - */ - public AvdInfo[] getBrokenAvds() { - synchronized (mAllAvdList) { - if (mBrokenAvdList == null) { - ArrayList<AvdInfo> list = new ArrayList<AvdInfo>(); - for (AvdInfo avd : mAllAvdList) { - if (avd.getStatus() != AvdStatus.OK) { - list.add(avd); - } - } - mBrokenAvdList = list.toArray(new AvdInfo[list.size()]); - } - return mBrokenAvdList; - } - } - - /** - * Returns the {@link AvdInfo} matching the given <var>name</var>. - * <p/> - * The search is case-insensitive. - * - * @param name the name of the AVD to return - * @param validAvdOnly if <code>true</code>, only look through the list of valid AVDs. - * @return the matching AvdInfo or <code>null</code> if none were found. - */ - public AvdInfo getAvd(String name, boolean validAvdOnly) { - - boolean ignoreCase = SdkConstants.currentPlatform() == SdkConstants.PLATFORM_WINDOWS; - - if (validAvdOnly) { - for (AvdInfo info : getValidAvds()) { - String name2 = info.getName(); - if (name2.equals(name) || (ignoreCase && name2.equalsIgnoreCase(name))) { - return info; - } - } - } else { - synchronized (mAllAvdList) { - for (AvdInfo info : mAllAvdList) { - String name2 = info.getName(); - if (name2.equals(name) || (ignoreCase && name2.equalsIgnoreCase(name))) { - return info; - } - } - } - } - - return null; - } - - /** - * Returns whether this AVD name would generate a conflict. - * - * @param name the name of the AVD to return - * @return A pair of {@link AvdConflict} and the path or AVD name that conflicts. - */ - public Pair<AvdConflict, String> isAvdNameConflicting(String name) { - - boolean ignoreCase = SdkConstants.currentPlatform() == SdkConstants.PLATFORM_WINDOWS; - - // Check whether we have a conflict with an existing or invalid AVD - // known to the manager. - synchronized (mAllAvdList) { - for (AvdInfo info : mAllAvdList) { - String name2 = info.getName(); - if (name2.equals(name) || (ignoreCase && name2.equalsIgnoreCase(name))) { - if (info.getStatus() == AvdStatus.OK) { - return Pair.of(AvdConflict.CONFLICT_EXISTING_AVD, name2); - } else { - return Pair.of(AvdConflict.CONFLICT_INVALID_AVD, name2); - } - } - } - } - - // No conflict with known AVDs. - // Are some existing files/folders in the way of creating this AVD? - - try { - File file = AvdInfo.getDefaultIniFile(this, name); - if (file.exists()) { - return Pair.of(AvdConflict.CONFLICT_EXISTING_PATH, file.getPath()); - } - - file = AvdInfo.getDefaultAvdFolder(this, name); - if (file.exists()) { - return Pair.of(AvdConflict.CONFLICT_EXISTING_PATH, file.getPath()); - } - - } catch (AndroidLocationException e) { - // ignore - } - - - return Pair.of(AvdConflict.NO_CONFLICT, null); - } - - /** - * Reloads the AVD list. - * @param log the log object to receive action logs. Cannot be null. - * @throws AndroidLocationException if there was an error finding the location of the - * AVD folder. - */ - public void reloadAvds(ILogger log) throws AndroidLocationException { - // build the list in a temp list first, in case the method throws an exception. - // It's better than deleting the whole list before reading the new one. - ArrayList<AvdInfo> allList = new ArrayList<AvdInfo>(); - buildAvdList(allList, log); - - synchronized (mAllAvdList) { - mAllAvdList.clear(); - mAllAvdList.addAll(allList); - mValidAvdList = mBrokenAvdList = null; - } - } - - /** - * Creates a new AVD. It is expected that there is no existing AVD with this name already. - * - * @param avdFolder the data folder for the AVD. It will be created as needed. - * Unless you want to locate it in a specific directory, the ideal default is - * {@code AvdManager.AvdInfo.getAvdFolder}. - * @param avdName the name of the AVD - * @param target the target of the AVD - * @param abiType the abi type of the AVD - * @param skinName the name of the skin. Can be null. Must have been verified by caller. - * @param sdcard the parameter value for the sdCard. Can be null. This is either a path to - * an existing sdcard image or a sdcard size (\d+, \d+K, \dM). - * @param hardwareConfig the hardware setup for the AVD. Can be null to use defaults. - * @param createSnapshot If true copy a blank snapshot image into the AVD. - * @param removePrevious If true remove any previous files. - * @param editExisting If true, edit an existing AVD, changing only the minimum required. - * This won't remove files unless required or unless {@code removePrevious} is set. - * @param log the log object to receive action logs. Cannot be null. - * @return The new {@link AvdInfo} in case of success (which has just been added to the - * internal list) or null in case of failure. - */ - public AvdInfo createAvd( - File avdFolder, - String avdName, - IAndroidTarget target, - String abiType, - String skinName, - String sdcard, - Map<String,String> hardwareConfig, - boolean createSnapshot, - boolean removePrevious, - boolean editExisting, - ILogger log) { - if (log == null) { - throw new IllegalArgumentException("log cannot be null"); - } - - File iniFile = null; - boolean needCleanup = false; - try { - if (avdFolder.exists()) { - if (removePrevious) { - // AVD already exists and removePrevious is set, try to remove the - // directory's content first (but not the directory itself). - try { - deleteContentOf(avdFolder); - } catch (SecurityException e) { - log.error(e, "Failed to delete %1$s", avdFolder.getAbsolutePath()); - } - } else if (!editExisting) { - // AVD shouldn't already exist if removePrevious is false and - // we're not editing an existing AVD. - log.error(null, - "Folder %1$s is in the way. Use --force if you want to overwrite.", - avdFolder.getAbsolutePath()); - return null; - } - } else { - // create the AVD folder. - avdFolder.mkdir(); - // We're not editing an existing AVD. - editExisting = false; - } - - // actually write the ini file - iniFile = createAvdIniFile(avdName, avdFolder, target, removePrevious); - - // writes the userdata.img in it. - - File userdataSrc = null; - - // Look for a system image in the add-on. - // If we don't find one there, look in the base platform. - ISystemImage systemImage = target.getSystemImage(abiType); - - if (systemImage != null) { - File imageFolder = systemImage.getLocation(); - userdataSrc = new File(imageFolder, USERDATA_IMG); - } - - if ((userdataSrc == null || !userdataSrc.exists()) && !target.isPlatform()) { - // If we don't find a system-image in the add-on, look into the platform. - - systemImage = target.getParent().getSystemImage(abiType); - if (systemImage != null) { - File imageFolder = systemImage.getLocation(); - userdataSrc = new File(imageFolder, USERDATA_IMG); - } - } - - if (userdataSrc == null || !userdataSrc.exists()) { - log.error(null, - "Unable to find a '%1$s' file for ABI %2$s to copy into the AVD folder.", - USERDATA_IMG, - abiType); - needCleanup = true; - return null; - } - - File userdataDest = new File(avdFolder, USERDATA_IMG); - - copyImageFile(userdataSrc, userdataDest); - - if (userdataDest.exists() == false) { - log.error(null, "Unable to create '%1$s' file in the AVD folder.", - userdataDest); - needCleanup = true; - return null; - } - - // Config file. - HashMap<String, String> values = new HashMap<String, String>(); - - if (setImagePathProperties(target, abiType, values, log) == false) { - log.error(null, "Failed to set image path properties in the AVD folder."); - needCleanup = true; - return null; - } - - // Create the snapshot file - if (createSnapshot) { - File snapshotDest = new File(avdFolder, SNAPSHOTS_IMG); - if (snapshotDest.isFile() && editExisting) { - log.info("Snapshot image already present, was not changed.\n"); - - } else { - String toolsLib = mSdkManager.getLocation() + File.separator - + SdkConstants.OS_SDK_TOOLS_LIB_EMULATOR_FOLDER; - File snapshotBlank = new File(toolsLib, SNAPSHOTS_IMG); - if (snapshotBlank.exists() == false) { - log.error(null, - "Unable to find a '%2$s%1$s' file to copy into the AVD folder.", - SNAPSHOTS_IMG, toolsLib); - needCleanup = true; - return null; - } - - copyImageFile(snapshotBlank, snapshotDest); - } - values.put(AVD_INI_SNAPSHOT_PRESENT, "true"); - } - - // Now the abi type - values.put(AVD_INI_ABI_TYPE, abiType); - - // and the cpu arch. - if (SdkConstants.ABI_ARMEABI.equals(abiType)) { - values.put(AVD_INI_CPU_ARCH, SdkConstants.CPU_ARCH_ARM); - } else if (SdkConstants.ABI_ARMEABI_V7A.equals(abiType)) { - values.put(AVD_INI_CPU_ARCH, SdkConstants.CPU_ARCH_ARM); - values.put(AVD_INI_CPU_MODEL, SdkConstants.CPU_MODEL_CORTEX_A8); - } else if (SdkConstants.ABI_INTEL_ATOM.equals(abiType)) { - values.put(AVD_INI_CPU_ARCH, SdkConstants.CPU_ARCH_INTEL_ATOM); - } else if (SdkConstants.ABI_MIPS.equals(abiType)) { - values.put(AVD_INI_CPU_ARCH, SdkConstants.CPU_ARCH_MIPS); - } else { - log.error(null, - "ABI %1$s is not supported by this version of the SDK Tools", abiType); - needCleanup = true; - return null; - } - - // Now the skin. - if (skinName == null || skinName.length() == 0) { - skinName = target.getDefaultSkin(); - } - - if (NUMERIC_SKIN_SIZE.matcher(skinName).matches()) { - // Skin name is an actual screen resolution. - // Set skin.name for display purposes in the AVD manager and - // set skin.path for use by the emulator. - values.put(AVD_INI_SKIN_NAME, skinName); - values.put(AVD_INI_SKIN_PATH, skinName); - } else { - // get the path of the skin (relative to the SDK) - // assume skin name is valid - String skinPath = getSkinRelativePath(skinName, target, log); - if (skinPath == null) { - log.error(null, "Missing skinpath in the AVD folder."); - needCleanup = true; - return null; - } - - values.put(AVD_INI_SKIN_PATH, skinPath); - values.put(AVD_INI_SKIN_NAME, skinName); - } - - if (sdcard != null && sdcard.length() > 0) { - // Sdcard is possibly a size. In that case we create a file called 'sdcard.img' - // in the AVD folder, and do not put any value in config.ini. - - long sdcardSize = parseSdcardSize(sdcard, null/*parsedStrings*/); - - if (sdcardSize == SDCARD_SIZE_NOT_IN_RANGE) { - log.error(null, "SD Card size must be in the range 9 MiB..1023 GiB."); - needCleanup = true; - return null; - - } else if (sdcardSize == SDCARD_SIZE_INVALID) { - log.error(null, "Unable to parse SD Card size"); - needCleanup = true; - return null; - - } else if (sdcardSize == SDCARD_NOT_SIZE_PATTERN) { - File sdcardFile = new File(sdcard); - if (sdcardFile.isFile()) { - // sdcard value is an external sdcard, so we put its path into the config.ini - values.put(AVD_INI_SDCARD_PATH, sdcard); - } else { - log.error(null, "'%1$s' is not recognized as a valid sdcard value.\n" - + "Value should be:\n" + "1. path to an sdcard.\n" - + "2. size of the sdcard to create: <size>[K|M]", sdcard); - needCleanup = true; - return null; - } - } else { - // create the sdcard. - File sdcardFile = new File(avdFolder, SDCARD_IMG); - - boolean runMkSdcard = true; - if (sdcardFile.exists()) { - if (sdcardFile.length() == sdcardSize && editExisting) { - // There's already an sdcard file with the right size and we're - // not overriding it... so don't remove it. - runMkSdcard = false; - log.info("SD Card already present with same size, was not changed.\n"); - } - } - - if (runMkSdcard) { - String path = sdcardFile.getAbsolutePath(); - - // execute mksdcard with the proper parameters. - File toolsFolder = new File(mSdkManager.getLocation(), - SdkConstants.FD_TOOLS); - File mkSdCard = new File(toolsFolder, SdkConstants.mkSdCardCmdName()); - - if (mkSdCard.isFile() == false) { - log.error(null, "'%1$s' is missing from the SDK tools folder.", - mkSdCard.getName()); - needCleanup = true; - return null; - } - - if (createSdCard(mkSdCard.getAbsolutePath(), sdcard, path, log) == false) { - log.error(null, "Failed to create sdcard in the AVD folder."); - needCleanup = true; - return null; // mksdcard output has already been displayed, no need to - // output anything else. - } - } - - // add a property containing the size of the sdcard for display purpose - // only when the dev does 'android list avd' - values.put(AVD_INI_SDCARD_SIZE, sdcard); - } - } - - // add the hardware config to the config file. - // priority order is: - // - values provided by the user - // - values provided by the skin - // - values provided by the target (add-on only). - // In order to follow this priority, we'll add the lowest priority values first and then - // override by higher priority values. - // In the case of a platform with override values from the user, the skin value might - // already be there, but it's ok. - - HashMap<String, String> finalHardwareValues = new HashMap<String, String>(); - - FileWrapper targetHardwareFile = new FileWrapper(target.getLocation(), - AvdManager.HARDWARE_INI); - if (targetHardwareFile.isFile()) { - Map<String, String> targetHardwareConfig = ProjectProperties.parsePropertyFile( - targetHardwareFile, log); - - if (targetHardwareConfig != null) { - finalHardwareValues.putAll(targetHardwareConfig); - values.putAll(targetHardwareConfig); - } - } - - // get the hardware properties for this skin - File skinFolder = getSkinPath(skinName, target); - FileWrapper skinHardwareFile = new FileWrapper(skinFolder, AvdManager.HARDWARE_INI); - if (skinHardwareFile.isFile()) { - Map<String, String> skinHardwareConfig = ProjectProperties.parsePropertyFile( - skinHardwareFile, log); - - if (skinHardwareConfig != null) { - finalHardwareValues.putAll(skinHardwareConfig); - values.putAll(skinHardwareConfig); - } - } - - // finally put the hardware provided by the user. - if (hardwareConfig != null) { - finalHardwareValues.putAll(hardwareConfig); - values.putAll(hardwareConfig); - } - - File configIniFile = new File(avdFolder, CONFIG_INI); - writeIniFile(configIniFile, values); - - // Generate the log report first because we want to control where line breaks - // are located when generating the hardware config list. - StringBuilder report = new StringBuilder(); - - if (target.isPlatform()) { - if (editExisting) { - report.append(String.format("Updated AVD '%1$s' based on %2$s", - avdName, target.getName())); - } else { - report.append(String.format("Created AVD '%1$s' based on %2$s", - avdName, target.getName())); - } - } else { - if (editExisting) { - report.append(String.format("Updated AVD '%1$s' based on %2$s (%3$s)", avdName, - target.getName(), target.getVendor())); - } else { - report.append(String.format("Created AVD '%1$s' based on %2$s (%3$s)", avdName, - target.getName(), target.getVendor())); - } - } - report.append(String.format(", %s processor", AvdInfo.getPrettyAbiType(abiType))); - - // display the chosen hardware config - if (finalHardwareValues.size() > 0) { - report.append(",\nwith the following hardware config:\n"); - for (Entry<String, String> entry : finalHardwareValues.entrySet()) { - report.append(String.format("%s=%s\n",entry.getKey(), entry.getValue())); - } - } else { - report.append("\n"); - } - - log.info(report.toString()); - - // create the AvdInfo object, and add it to the list - AvdInfo newAvdInfo = new AvdInfo( - avdName, - iniFile, - avdFolder.getAbsolutePath(), - target.hashString(), - target, abiType, values); - - AvdInfo oldAvdInfo = getAvd(avdName, false /*validAvdOnly*/); - - synchronized (mAllAvdList) { - if (oldAvdInfo != null && (removePrevious || editExisting)) { - mAllAvdList.remove(oldAvdInfo); - } - mAllAvdList.add(newAvdInfo); - mValidAvdList = mBrokenAvdList = null; - } - - if ((removePrevious || editExisting) && - newAvdInfo != null && - oldAvdInfo != null && - !oldAvdInfo.getDataFolderPath().equals(newAvdInfo.getDataFolderPath())) { - log.warning("Removing previous AVD directory at %s", - oldAvdInfo.getDataFolderPath()); - // Remove the old data directory - File dir = new File(oldAvdInfo.getDataFolderPath()); - try { - deleteContentOf(dir); - dir.delete(); - } catch (SecurityException e) { - log.error(e, "Failed to delete %1$s", dir.getAbsolutePath()); - } - } - - return newAvdInfo; - } catch (AndroidLocationException e) { - log.error(e, null); - } catch (IOException e) { - log.error(e, null); - } catch (SecurityException e) { - log.error(e, null); - } finally { - if (needCleanup) { - if (iniFile != null && iniFile.exists()) { - iniFile.delete(); - } - - try { - deleteContentOf(avdFolder); - avdFolder.delete(); - } catch (SecurityException e) { - log.error(e, "Failed to delete %1$s", avdFolder.getAbsolutePath()); - } - } - } - - return null; - } - - /** - * Copy the nominated file to the given destination. - * - * @throws FileNotFoundException - * @throws IOException - */ - private void copyImageFile(File source, File destination) - throws FileNotFoundException, IOException { - FileInputStream fis = new FileInputStream(source); - FileOutputStream fos = new FileOutputStream(destination); - - byte[] buffer = new byte[4096]; - int count; - while ((count = fis.read(buffer)) != -1) { - fos.write(buffer, 0, count); - } - - fos.close(); - fis.close(); - } - - /** - * Returns the path to the target images folder as a relative path to the SDK, if the folder - * is not empty. If the image folder is empty or does not exist, <code>null</code> is returned. - * @throws InvalidTargetPathException if the target image folder is not in the current SDK. - */ - private String getImageRelativePath(IAndroidTarget target, String abiType) - throws InvalidTargetPathException { - - ISystemImage systemImage = target.getSystemImage(abiType); - if (systemImage == null) { - // ABI Type is unknown for target - return null; - } - - File folder = systemImage.getLocation(); - String imageFullPath = folder.getAbsolutePath(); - - // make this path relative to the SDK location - String sdkLocation = mSdkManager.getLocation(); - if (!imageFullPath.startsWith(sdkLocation)) { - // this really really should not happen. - assert false; - throw new InvalidTargetPathException("Target location is not inside the SDK."); - } - - if (folder.isDirectory()) { - String[] list = folder.list(new FilenameFilter() { - @Override - public boolean accept(File dir, String name) { - return IMAGE_NAME_PATTERN.matcher(name).matches(); - } - }); - - if (list.length > 0) { - // Remove the SDK root path, e.g. /sdk/dir1/dir2 => /dir1/dir2 - imageFullPath = imageFullPath.substring(sdkLocation.length()); - // The path is relative, so it must not start with a file separator - if (imageFullPath.charAt(0) == File.separatorChar) { - imageFullPath = imageFullPath.substring(1); - } - // For compatibility with previous versions, we denote folders - // by ending the path with file separator - if (!imageFullPath.endsWith(File.separator)) { - imageFullPath += File.separator; - } - - return imageFullPath; - } - } - - return null; - } - - /** - * Returns the path to the skin, as a relative path to the SDK. - * @param skinName The name of the skin to find. Case-sensitive. - * @param target The target where to find the skin. - * @param log the log object to receive action logs. Cannot be null. - */ - public String getSkinRelativePath(String skinName, IAndroidTarget target, ILogger log) { - if (log == null) { - throw new IllegalArgumentException("log cannot be null"); - } - - // first look to see if the skin is in the target - File skin = getSkinPath(skinName, target); - - // skin really does not exist! - if (skin.exists() == false) { - log.error(null, "Skin '%1$s' does not exist.", skinName); - return null; - } - - // get the skin path - String path = skin.getAbsolutePath(); - - // make this path relative to the SDK location - String sdkLocation = mSdkManager.getLocation(); - if (path.startsWith(sdkLocation) == false) { - // this really really should not happen. - log.error(null, "Target location is not inside the SDK."); - assert false; - return null; - } - - path = path.substring(sdkLocation.length()); - if (path.charAt(0) == File.separatorChar) { - path = path.substring(1); - } - return path; - } - - /** - * Returns the full absolute OS path to a skin specified by name for a given target. - * @param skinName The name of the skin to find. Case-sensitive. - * @param target The target where to find the skin. - * @return a {@link File} that may or may not actually exist. - */ - public File getSkinPath(String skinName, IAndroidTarget target) { - String path = target.getPath(IAndroidTarget.SKINS); - File skin = new File(path, skinName); - - if (skin.exists() == false && target.isPlatform() == false) { - target = target.getParent(); - - path = target.getPath(IAndroidTarget.SKINS); - skin = new File(path, skinName); - } - - return skin; - } - - /** - * Creates the ini file for an AVD. - * - * @param name of the AVD. - * @param avdFolder path for the data folder of the AVD. - * @param target of the AVD. - * @param removePrevious True if an existing ini file should be removed. - * @throws AndroidLocationException if there's a problem getting android root directory. - * @throws IOException if {@link File#getAbsolutePath()} fails. - */ - private File createAvdIniFile(String name, - File avdFolder, - IAndroidTarget target, - boolean removePrevious) - throws AndroidLocationException, IOException { - File iniFile = AvdInfo.getDefaultIniFile(this, name); - - if (removePrevious) { - if (iniFile.isFile()) { - iniFile.delete(); - } else if (iniFile.isDirectory()) { - deleteContentOf(iniFile); - iniFile.delete(); - } - } - - String absPath = avdFolder.getAbsolutePath(); - String relPath = null; - String androidPath = AndroidLocation.getFolder(); - if (absPath.startsWith(androidPath)) { - // Compute the AVD path relative to the android path. - assert androidPath.endsWith(File.separator); - relPath = absPath.substring(androidPath.length()); - } - - HashMap<String, String> values = new HashMap<String, String>(); - if (relPath != null) { - values.put(AVD_INFO_REL_PATH, relPath); - } - values.put(AVD_INFO_ABS_PATH, absPath); - values.put(AVD_INFO_TARGET, target.hashString()); - writeIniFile(iniFile, values); - - return iniFile; - } - - /** - * Creates the ini file for an AVD. - * - * @param info of the AVD. - * @throws AndroidLocationException if there's a problem getting android root directory. - * @throws IOException if {@link File#getAbsolutePath()} fails. - */ - private File createAvdIniFile(AvdInfo info) throws AndroidLocationException, IOException { - return createAvdIniFile(info.getName(), - new File(info.getDataFolderPath()), - info.getTarget(), - false /*removePrevious*/); - } - - /** - * Actually deletes the files of an existing AVD. - * <p/> - * This also remove it from the manager's list, The caller does not need to - * call {@link #removeAvd(AvdInfo)} afterwards. - * <p/> - * This method is designed to somehow work with an unavailable AVD, that is an AVD that - * could not be loaded due to some error. That means this method still tries to remove - * the AVD ini file or its folder if it can be found. An error will be output if any of - * these operations fail. - * - * @param avdInfo the information on the AVD to delete - * @param log the log object to receive action logs. Cannot be null. - * @return True if the AVD was deleted with no error. - */ - public boolean deleteAvd(AvdInfo avdInfo, ILogger log) { - try { - boolean error = false; - - File f = avdInfo.getIniFile(); - if (f != null && f.exists()) { - log.info("Deleting file %1$s\n", f.getCanonicalPath()); - if (!f.delete()) { - log.error(null, "Failed to delete %1$s\n", f.getCanonicalPath()); - error = true; - } - } - - String path = avdInfo.getDataFolderPath(); - if (path != null) { - f = new File(path); - if (f.exists()) { - log.info("Deleting folder %1$s\n", f.getCanonicalPath()); - if (deleteContentOf(f) == false || f.delete() == false) { - log.error(null, "Failed to delete %1$s\n", f.getCanonicalPath()); - error = true; - } - } - } - - removeAvd(avdInfo); - - if (error) { - log.info("\nAVD '%1$s' deleted with errors. See errors above.\n", - avdInfo.getName()); - } else { - log.info("\nAVD '%1$s' deleted.\n", avdInfo.getName()); - return true; - } - - } catch (IOException e) { - log.error(e, null); - } catch (SecurityException e) { - log.error(e, null); - } - return false; - } - - /** - * Moves and/or rename an existing AVD and its files. - * This also change it in the manager's list. - * <p/> - * The caller should make sure the name or path given are valid, do not exist and are - * actually different than current values. - * - * @param avdInfo the information on the AVD to move. - * @param newName the new name of the AVD if non null. - * @param paramFolderPath the new data folder if non null. - * @param log the log object to receive action logs. Cannot be null. - * @return True if the move succeeded or there was nothing to do. - * If false, this method will have had already output error in the log. - */ - public boolean moveAvd(AvdInfo avdInfo, String newName, String paramFolderPath, ILogger log) { - - try { - if (paramFolderPath != null) { - File f = new File(avdInfo.getDataFolderPath()); - log.warning("Moving '%1$s' to '%2$s'.", - avdInfo.getDataFolderPath(), - paramFolderPath); - if (!f.renameTo(new File(paramFolderPath))) { - log.error(null, "Failed to move '%1$s' to '%2$s'.", - avdInfo.getDataFolderPath(), paramFolderPath); - return false; - } - - // update AVD info - AvdInfo info = new AvdInfo( - avdInfo.getName(), - avdInfo.getIniFile(), - paramFolderPath, - avdInfo.getTargetHash(), - avdInfo.getTarget(), - avdInfo.getAbiType(), - avdInfo.getProperties()); - replaceAvd(avdInfo, info); - - // update the ini file - createAvdIniFile(info); - } - - if (newName != null) { - File oldIniFile = avdInfo.getIniFile(); - File newIniFile = AvdInfo.getDefaultIniFile(this, newName); - - log.warning("Moving '%1$s' to '%2$s'.", oldIniFile.getPath(), newIniFile.getPath()); - if (!oldIniFile.renameTo(newIniFile)) { - log.error(null, "Failed to move '%1$s' to '%2$s'.", - oldIniFile.getPath(), newIniFile.getPath()); - return false; - } - - // update AVD info - AvdInfo info = new AvdInfo( - newName, - avdInfo.getIniFile(), - avdInfo.getDataFolderPath(), - avdInfo.getTargetHash(), - avdInfo.getTarget(), - avdInfo.getAbiType(), - avdInfo.getProperties()); - replaceAvd(avdInfo, info); - } - - log.info("AVD '%1$s' moved.\n", avdInfo.getName()); - - } catch (AndroidLocationException e) { - log.error(e, null); - } catch (IOException e) { - log.error(e, null); - } - - // nothing to do or succeeded - return true; - } - - /** - * Helper method to recursively delete a folder's content (but not the folder itself). - * - * @throws SecurityException like {@link File#delete()} does if file/folder is not writable. - */ - private boolean deleteContentOf(File folder) throws SecurityException { - File[] files = folder.listFiles(); - if (files != null) { - for (File f : files) { - if (f.isDirectory()) { - if (deleteContentOf(f) == false) { - return false; - } - } - if (f.delete() == false) { - return false; - } - - } - } - - return true; - } - - /** - * Returns a list of files that are potential AVD ini files. - * <p/> - * This lists the $HOME/.android/avd/<name>.ini files. - * Such files are properties file than then indicate where the AVD folder is located. - * <p/> - * Note: the method is to be considered private. It is made protected so that - * unit tests can easily override the AVD root. - * - * @return A new {@link File} array or null. The array might be empty. - * @throws AndroidLocationException if there's a problem getting android root directory. - */ - private File[] buildAvdFilesList() throws AndroidLocationException { - File folder = new File(getBaseAvdFolder()); - - // ensure folder validity. - if (folder.isFile()) { - throw new AndroidLocationException( - String.format("%1$s is not a valid folder.", folder.getAbsolutePath())); - } else if (folder.exists() == false) { - // folder is not there, we create it and return - folder.mkdirs(); - return null; - } - - File[] avds = folder.listFiles(new FilenameFilter() { - @Override - public boolean accept(File parent, String name) { - if (INI_NAME_PATTERN.matcher(name).matches()) { - // check it's a file and not a folder - boolean isFile = new File(parent, name).isFile(); - return isFile; - } - - return false; - } - }); - - return avds; - } - - /** - * Computes the internal list of available AVDs - * @param allList the list to contain all the AVDs - * @param log the log object to receive action logs. Cannot be null. - * - * @throws AndroidLocationException if there's a problem getting android root directory. - */ - private void buildAvdList(ArrayList<AvdInfo> allList, ILogger log) - throws AndroidLocationException { - File[] avds = buildAvdFilesList(); - if (avds != null) { - for (File avd : avds) { - AvdInfo info = parseAvdInfo(avd, log); - if (info != null) { - allList.add(info); - } - } - } - } - - /** - * Parses an AVD .ini file to create an {@link AvdInfo}. - * - * @param iniPath The path to the AVD .ini file - * @param log the log object to receive action logs. Cannot be null. - * @return A new {@link AvdInfo} with an {@link AvdStatus} indicating whether this AVD is - * valid or not. - */ - private AvdInfo parseAvdInfo(File iniPath, ILogger log) { - Map<String, String> map = parseIniFile( - new FileWrapper(iniPath), - log); - - String avdPath = map.get(AVD_INFO_ABS_PATH); - String targetHash = map.get(AVD_INFO_TARGET); - - if (!(new File(avdPath).isDirectory())) { - // Try to fallback on the relative path, if present. - String relPath = map.get(AVD_INFO_REL_PATH); - if (relPath != null) { - try { - String androidPath = AndroidLocation.getFolder(); - File f = new File(androidPath, relPath); - if (f.isDirectory()) { - avdPath = f.getAbsolutePath(); - } - } catch (AndroidLocationException ignore) {} - } - } - - IAndroidTarget target = null; - FileWrapper configIniFile = null; - Map<String, String> properties = null; - - if (targetHash != null) { - target = mSdkManager.getTargetFromHashString(targetHash); - } - - // load the AVD properties. - if (avdPath != null) { - configIniFile = new FileWrapper(avdPath, CONFIG_INI); - } - - if (configIniFile != null) { - if (!configIniFile.isFile()) { - log.warning("Missing file '%1$s'.", configIniFile.getPath()); - } else { - properties = parseIniFile(configIniFile, log); - } - } - - // get name - String name = iniPath.getName(); - Matcher matcher = INI_NAME_PATTERN.matcher(iniPath.getName()); - if (matcher.matches()) { - name = matcher.group(1); - } - - // get abi type - String abiType = properties == null ? null : properties.get(AVD_INI_ABI_TYPE); - // for the avds created previously without enhancement, i.e. They are created based - // on previous API Levels. They are supposed to have ARM processor type - if (abiType == null) { - abiType = SdkConstants.ABI_ARMEABI; - } - - // check the image.sysdir are valid - boolean validImageSysdir = true; - if (properties != null) { - String imageSysDir = properties.get(AVD_INI_IMAGES_1); - if (imageSysDir != null) { - File f = new File(mSdkManager.getLocation() + File.separator + imageSysDir); - if (f.isDirectory() == false) { - validImageSysdir = false; - } else { - imageSysDir = properties.get(AVD_INI_IMAGES_2); - if (imageSysDir != null) { - f = new File(mSdkManager.getLocation() + File.separator + imageSysDir); - if (f.isDirectory() == false) { - validImageSysdir = false; - } - } - } - } - } - - // Get the device status if this AVD is associated with a device - DeviceStatus deviceStatus = null; - if (properties != null) { - String deviceName = properties.get(AVD_INI_DEVICE_NAME); - String deviceMfctr = properties.get(AVD_INI_DEVICE_MANUFACTURER); - String hash = properties.get(AVD_INI_DEVICE_HASH); - if (deviceName != null && deviceMfctr != null && hash != null) { - int deviceHash = Integer.parseInt(hash); - DeviceManager devMan = DeviceManager.createInstance(mSdkManager.getLocation(), log); - deviceStatus = devMan.getDeviceStatus(deviceName, deviceMfctr, deviceHash); - } - } - - - // TODO: What about missing sdcard, skins, etc? - - AvdStatus status; - - if (avdPath == null) { - status = AvdStatus.ERROR_PATH; - } else if (configIniFile == null) { - status = AvdStatus.ERROR_CONFIG; - } else if (targetHash == null) { - status = AvdStatus.ERROR_TARGET_HASH; - } else if (target == null) { - status = AvdStatus.ERROR_TARGET; - } else if (properties == null) { - status = AvdStatus.ERROR_PROPERTIES; - } else if (validImageSysdir == false) { - status = AvdStatus.ERROR_IMAGE_DIR; - } else if (deviceStatus == DeviceStatus.CHANGED) { - status = AvdStatus.ERROR_DEVICE_CHANGED; - } else if (deviceStatus == DeviceStatus.MISSING) { - status = AvdStatus.ERROR_DEVICE_MISSING; - } else { - status = AvdStatus.OK; - } - - AvdInfo info = new AvdInfo( - name, - iniPath, - avdPath, - targetHash, - target, - abiType, - properties, - status); - - return info; - } - - /** - * Writes a .ini file from a set of properties, using UTF-8 encoding. - * The file should be read back later by {@link #parseIniFile(IAbstractFile, ILogger)}. - * - * @param iniFile The file to generate. - * @param values THe properties to place in the ini file. - * @throws IOException if {@link FileWriter} fails to open, write or close the file. - */ - private static void writeIniFile(File iniFile, Map<String, String> values) - throws IOException { - - Charset charset = Charsets.ISO_8859_1; - OutputStreamWriter writer = new OutputStreamWriter(new FileOutputStream(iniFile), charset); - - // Write down the charset used in case we want to use it later. - writer.write(String.format("%1$s=%2$s\n", AVD_INI_ENCODING, charset.name())); - - for (Entry<String, String> entry : values.entrySet()) { - writer.write(String.format("%1$s=%2$s\n", entry.getKey(), entry.getValue())); - } - writer.close(); - } - - /** - * Parses a property file and returns a map of the content. - * <p/> - * If the file is not present, null is returned with no error messages sent to the log. - * <p/> - * Charset encoding will be either the system's default or the one specified by the - * {@link #AVD_INI_ENCODING} key if present. - * - * @param propFile the property file to parse - * @param log the ILogger object receiving warning/error from the parsing. - * @return the map of (key,value) pairs, or null if the parsing failed. - */ - private static Map<String, String> parseIniFile( - @NonNull IAbstractFile propFile, - @Nullable ILogger log) { - return parseIniFileImpl(propFile, log, null /*charset*/); - } - - /** - * Implementation helper for the {@link #parseIniFile(IAbstractFile, ILogger)} method. - * Don't call this one directly. - * - * @param propFile the property file to parse - * @param log the ILogger object receiving warning/error from the parsing. - * @param charset When a specific charset is specified, this will be used as-is. - * When null, the default charset will first be used and if the key - * {@link #AVD_INI_ENCODING} is found the parsing will restart using that specific - * charset. - * @return the map of (key,value) pairs, or null if the parsing failed. - */ - private static Map<String, String> parseIniFileImpl( - @NonNull IAbstractFile propFile, - @Nullable ILogger log, - @Nullable Charset charset) { - - BufferedReader reader = null; - try { - boolean canChangeCharset = false; - if (charset == null) { - canChangeCharset = false; - charset = Charsets.ISO_8859_1; - } - reader = new BufferedReader(new InputStreamReader(propFile.getContents(), charset)); - - String line = null; - Map<String, String> map = new HashMap<String, String>(); - while ((line = reader.readLine()) != null) { - line = line.trim(); - if (line.length() > 0 && line.charAt(0) != '#') { - - Matcher m = INI_LINE_PATTERN.matcher(line); - if (m.matches()) { - // Note: we do NOT escape values. - String key = m.group(1); - String value = m.group(2); - - // If we find the charset encoding and it's not the same one and - // it's a valid one, re-read the file using that charset. - if (canChangeCharset && - AVD_INI_ENCODING.equals(key) && - !charset.name().equals(value) && - Charset.isSupported(value)) { - charset = Charset.forName(value); - return parseIniFileImpl(propFile, log, charset); - } - - map.put(key, value); - } else { - if (log != null) { - log.warning("Error parsing '%1$s': \"%2$s\" is not a valid syntax", - propFile.getOsLocation(), - line); - } - return null; - } - } - } - - return map; - } catch (FileNotFoundException e) { - // this should not happen since we usually test the file existence before - // calling the method. - // Return null below. - } catch (IOException e) { - if (log != null) { - log.warning("Error parsing '%1$s': %2$s.", - propFile.getOsLocation(), - e.getMessage()); - } - } catch (StreamException e) { - if (log != null) { - log.warning("Error parsing '%1$s': %2$s.", - propFile.getOsLocation(), - e.getMessage()); - } - } finally { - Closeables.closeQuietly(reader); - } - - return null; - } - - /** - * Invokes the tool to create a new SD card image file. - * - * @param toolLocation The path to the mksdcard tool. - * @param size The size of the new SD Card, compatible with {@link #SDCARD_SIZE_PATTERN}. - * @param location The path of the new sdcard image file to generate. - * @param log the log object to receive action logs. Cannot be null. - * @return True if the sdcard could be created. - */ - private boolean createSdCard(String toolLocation, String size, String location, ILogger log) { - try { - String[] command = new String[3]; - command[0] = toolLocation; - command[1] = size; - command[2] = location; - Process process = Runtime.getRuntime().exec(command); - - final ArrayList<String> errorOutput = new ArrayList<String>(); - final ArrayList<String> stdOutput = new ArrayList<String>(); - - int status = GrabProcessOutput.grabProcessOutput( - process, - Wait.WAIT_FOR_READERS, - new IProcessOutput() { - @Override - public void out(@Nullable String line) { - if (line != null) { - stdOutput.add(line); - } - } - - @Override - public void err(@Nullable String line) { - if (line != null) { - errorOutput.add(line); - } - } - }); - - if (status == 0) { - return true; - } else { - for (String error : errorOutput) { - log.error(null, error); - } - } - - } catch (InterruptedException e) { - // pass, print error below - } catch (IOException e) { - // pass, print error below - } - - log.error(null, "Failed to create the SD card."); - return false; - } - - /** - * Removes an {@link AvdInfo} from the internal list. - * - * @param avdInfo The {@link AvdInfo} to remove. - * @return true if this {@link AvdInfo} was present and has been removed. - */ - public boolean removeAvd(AvdInfo avdInfo) { - synchronized (mAllAvdList) { - if (mAllAvdList.remove(avdInfo)) { - mValidAvdList = mBrokenAvdList = null; - return true; - } - } - - return false; - } - - /** - * Updates an AVD with new path to the system image folders. - * @param name the name of the AVD to update. - * @param log the log object to receive action logs. Cannot be null. - * @throws IOException - */ - public void updateAvd(String name, ILogger log) throws IOException { - // find the AVD to update. It should be be in the broken list. - AvdInfo avd = null; - synchronized (mAllAvdList) { - for (AvdInfo info : mAllAvdList) { - if (info.getName().equals(name)) { - avd = info; - break; - } - } - } - - if (avd == null) { - // not in the broken list, just return. - log.error(null, "There is no Android Virtual Device named '%s'.", name); - return; - } - - updateAvd(avd, log); - } - - - /** - * Updates an AVD with new path to the system image folders. - * @param avd the AVD to update. - * @param log the log object to receive action logs. Cannot be null. - * @throws IOException - */ - public void updateAvd(AvdInfo avd, ILogger log) throws IOException { - // get the properties. This is a unmodifiable Map. - Map<String, String> oldProperties = avd.getProperties(); - - // create a new map - Map<String, String> properties = new HashMap<String, String>(); - if (oldProperties != null) { - properties.putAll(oldProperties); - } - - AvdStatus status; - - // create the path to the new system images. - if (setImagePathProperties(avd.getTarget(), avd.getAbiType(), properties, log)) { - if (properties.containsKey(AVD_INI_IMAGES_1)) { - log.info("Updated '%1$s' with value '%2$s'\n", AVD_INI_IMAGES_1, - properties.get(AVD_INI_IMAGES_1)); - } - - if (properties.containsKey(AVD_INI_IMAGES_2)) { - log.info("Updated '%1$s' with value '%2$s'\n", AVD_INI_IMAGES_2, - properties.get(AVD_INI_IMAGES_2)); - } - - status = AvdStatus.OK; - } else { - log.error(null, "Unable to find non empty system images folders for %1$s", - avd.getName()); - //FIXME: display paths to empty image folders? - status = AvdStatus.ERROR_IMAGE_DIR; - } - updateAvd(avd, properties, status, log); - } - - public void updateAvd(AvdInfo avd, - Map<String, String> newProperties, - AvdStatus status, - ILogger log) throws IOException { - // now write the config file - File configIniFile = new File(avd.getDataFolderPath(), CONFIG_INI); - writeIniFile(configIniFile, newProperties); - - // finally create a new AvdInfo for this unbroken avd and add it to the list. - // instead of creating the AvdInfo object directly we reparse it, to detect other possible - // errors - // FIXME: We may want to create this AvdInfo by reparsing the AVD instead. This could detect other errors. - AvdInfo newAvd = new AvdInfo( - avd.getName(), - avd.getIniFile(), - avd.getDataFolderPath(), - avd.getTargetHash(), - avd.getTarget(), - avd.getAbiType(), - newProperties); - - replaceAvd(avd, newAvd); - } - - /** - * Sets the paths to the system images in a properties map. - * - * @param target the target in which to find the system images. - * @param abiType the abi type of the avd to find - * the architecture-dependent system images. - * @param properties the properties in which to set the paths. - * @param log the log object to receive action logs. Cannot be null. - * @return true if success, false if some path are missing. - */ - private boolean setImagePathProperties(IAndroidTarget target, - String abiType, - Map<String, String> properties, - ILogger log) { - properties.remove(AVD_INI_IMAGES_1); - properties.remove(AVD_INI_IMAGES_2); - - try { - String property = AVD_INI_IMAGES_1; - - // First the image folders of the target itself - String imagePath = getImageRelativePath(target, abiType); - if (imagePath != null) { - properties.put(property, imagePath); - property = AVD_INI_IMAGES_2; - } - - // If the target is an add-on we need to add the Platform image as a backup. - IAndroidTarget parent = target.getParent(); - if (parent != null) { - imagePath = getImageRelativePath(parent, abiType); - if (imagePath != null) { - properties.put(property, imagePath); - } - } - - // we need at least one path! - return properties.containsKey(AVD_INI_IMAGES_1); - } catch (InvalidTargetPathException e) { - log.error(e, e.getMessage()); - } - - return false; - } - - /** - * Replaces an old {@link AvdInfo} with a new one in the lists storing them. - * @param oldAvd the {@link AvdInfo} to remove. - * @param newAvd the {@link AvdInfo} to add. - */ - private void replaceAvd(AvdInfo oldAvd, AvdInfo newAvd) { - synchronized (mAllAvdList) { - mAllAvdList.remove(oldAvd); - mAllAvdList.add(newAvd); - mValidAvdList = mBrokenAvdList = null; - } - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/avd/HardwareProperties.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/avd/HardwareProperties.java deleted file mode 100644 index 02241ef..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/avd/HardwareProperties.java +++ /dev/null @@ -1,303 +0,0 @@ -/* - * Copyright (C) 2008 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.avd; - -import com.android.utils.ILogger; - -import java.io.BufferedReader; -import java.io.File; -import java.io.FileInputStream; -import java.io.FileNotFoundException; -import java.io.IOException; -import java.io.InputStreamReader; -import java.util.Map; -import java.util.TreeMap; -import java.util.regex.Matcher; -import java.util.regex.Pattern; - -public class HardwareProperties { - /** AVD/config.ini key for whether hardware buttons are present. */ - public static final String HW_MAINKEYS = "hw.mainKeys"; - - /** AVD/config.ini key indicating whether trackball is present. */ - public static final String HW_TRACKBALL = "hw.trackBall"; - - /** AVD/config.ini key indicating whether qwerty keyboard is present. */ - public static final String HW_KEYBOARD = "hw.keyboard"; - - /** AVD/config.ini key indicating whether dpad is present. */ - public static final String HW_DPAD = "hw.dPad"; - - /** AVD/config.ini key indicating whether gps is present. */ - public static final String HW_GPS = "hw.gps"; - - /** AVD/config.ini key indicating whether the device is running on battery. */ - public static final String HW_BATTERY = "hw.battery"; - - /** AVD/config.ini key indicating whether accelerometer is present. */ - public static final String HW_ACCELEROMETER = "hw.accelerometer"; - - /** AVD/config.ini key indicating whether gyroscope is present. */ - public static final String HW_ORIENTATION_SENSOR = "hw.sensors.orientation"; - - /** AVD/config.ini key indicating whether h/w mic is present. */ - public static final String HW_AUDIO_INPUT = "hw.audioInput"; - - /** AVD/config.ini key indicating whether sdcard is present. */ - public static final String HW_SDCARD = "hw.sdCard"; - - /** AVD/config.ini key for LCD density. */ - public static final String HW_LCD_DENSITY = "hw.lcd.density"; - - /** AVD/config.ini key indicating whether proximity sensor present. */ - public static final String HW_PROXIMITY_SENSOR = "hw.sensors.proximity"; - - - private final static Pattern PATTERN_PROP = Pattern.compile( - "^([a-zA-Z0-9._-]+)\\s*=\\s*(.*)\\s*$"); - - /** Property name in the generated avd config file; String; e.g. "hw.screen" */ - private final static String HW_PROP_NAME = "name"; //$NON-NLS-1$ - /** Property type, one of {@link HardwarePropertyType} */ - private final static String HW_PROP_TYPE = "type"; //$NON-NLS-1$ - /** Default value of the property. String matching the property type. */ - private final static String HW_PROP_DEFAULT = "default"; //$NON-NLS-1$ - /** User-visible name of the property. String. */ - private final static String HW_PROP_ABSTRACT = "abstract"; //$NON-NLS-1$ - /** User-visible description of the property. String. */ - private final static String HW_PROP_DESC = "description"; //$NON-NLS-1$ - /** Comma-separate values for a property of type "enum" */ - private final static String HW_PROP_ENUM = "enum"; //$NON-NLS-1$ - - public final static String BOOLEAN_YES = "yes"; - public final static String BOOLEAN_NO = "no"; - public final static String[] BOOLEAN_VALUES = new String[] { BOOLEAN_YES, BOOLEAN_NO }; - public final static Pattern DISKSIZE_PATTERN = Pattern.compile("\\d+[MK]B"); //$NON-NLS-1$ - - /** Represents the type of a hardware property value. */ - public enum HardwarePropertyType { - INTEGER ("integer", false /*isEnum*/), //$NON-NLS-1$ - BOOLEAN ("boolean", false /*isEnum*/), //$NON-NLS-1$ - DISKSIZE ("diskSize", false /*isEnum*/), //$NON-NLS-1$ - STRING ("string", false /*isEnum*/), //$NON-NLS-1$ - INTEGER_ENUM("integer", true /*isEnum*/), //$NON-NLS-1$ - STRING_ENUM ("string", true /*isEnum*/); //$NON-NLS-1$ - - - private String mName; - private boolean mIsEnum; - - HardwarePropertyType(String name, boolean isEnum) { - mName = name; - mIsEnum = isEnum; - } - - /** Returns the name of the type (e.g. "string", "boolean", etc.) */ - public String getName() { - return mName; - } - - /** Indicates whether this type is an enum (e.g. "enum of strings"). */ - public boolean isEnum() { - return mIsEnum; - } - - /** Returns the internal HardwarePropertyType object matching the given type name. */ - public static HardwarePropertyType getEnum(String name, boolean isEnum) { - for (HardwarePropertyType type : values()) { - if (type.mName.equals(name) && type.mIsEnum == isEnum) { - return type; - } - } - - return null; - } - } - - public static final class HardwareProperty { - private String mName; - private HardwarePropertyType mType; - /** the string representation of the default value. can be null. */ - private String mDefault; - /** the choices for an enum. Null if not an enum. */ - private String[] mEnum; - private String mAbstract; - private String mDescription; - - public HardwareProperty() { - // initialize strings to sane defaults, as not all properties will be set from - // the ini file - mName = ""; - mDefault = ""; - mAbstract = ""; - mDescription = ""; - } - - /** Returns the hardware config name of the property, e.g. "hw.screen" */ - public String getName() { - return mName; - } - - /** Returns the property type, one of {@link HardwarePropertyType} */ - public HardwarePropertyType getType() { - return mType; - } - - /** - * Returns the default value of the property. - * String matching the property type. - * Can be null. - */ - public String getDefault() { - return mDefault; - } - - /** Returns the user-visible name of the property. */ - public String getAbstract() { - return mAbstract; - } - - /** Returns the user-visible description of the property. */ - public String getDescription() { - return mDescription; - } - - /** Returns the possible values for an enum property. Can be null. */ - public String[] getEnum() { - return mEnum; - } - - public boolean isValidForUi() { - // don't display single string type for now. - return mType != HardwarePropertyType.STRING || mType.isEnum(); - } - } - - /** - * Parses the hardware definition file. - * @param file the property file to parse - * @param log the ILogger object receiving warning/error from the parsing. Cannot be null. - * @return the map of (key,value) pairs, or null if the parsing failed. - */ - public static Map<String, HardwareProperty> parseHardwareDefinitions(File file, ILogger log) { - BufferedReader reader = null; - try { - FileInputStream fis = new FileInputStream(file); - reader = new BufferedReader(new InputStreamReader(fis)); - - Map<String, HardwareProperty> map = new TreeMap<String, HardwareProperty>(); - - String line = null; - HardwareProperty prop = null; - while ((line = reader.readLine()) != null) { - if (line.length() > 0 && line.charAt(0) != '#') { - Matcher m = PATTERN_PROP.matcher(line); - if (m.matches()) { - String key = m.group(1); - String value = m.group(2); - - if (HW_PROP_NAME.equals(key)) { - prop = new HardwareProperty(); - prop.mName = value; - map.put(prop.mName, prop); - } - - if (prop == null) { - log.warning("Error parsing '%1$s': missing '%2$s'", - file.getAbsolutePath(), HW_PROP_NAME); - return null; - } - - if (HW_PROP_TYPE.equals(key)) { - // Note: we don't know yet whether this type is an enum. - // This is indicated by the "enum = value" line that is parsed later. - prop.mType = HardwarePropertyType.getEnum(value, false); - assert (prop.mType != null); - } else if (HW_PROP_DEFAULT.equals(key)) { - prop.mDefault = value; - } else if (HW_PROP_ABSTRACT.equals(key)) { - prop.mAbstract = value; - } else if (HW_PROP_DESC.equals(key)) { - prop.mDescription = value; - } else if (HW_PROP_ENUM.equals(key)) { - if (!prop.mType.isEnum()) { - // Change the type to an enum, if valid. - prop.mType = HardwarePropertyType.getEnum(prop.mType.getName(), - true); - assert (prop.mType != null); - } - - // Sanitize input: trim spaces, ignore empty entries. - String[] v = value.split(","); - int n = 0; - for (int i = 0; i < v.length; i++) { - String s = v[i] = v[i].trim(); - if (s.length() > 0) { - n++; - } - } - prop.mEnum = new String[n]; - n = 0; - for (int i = 0; i < v.length; i++) { - String s = v[i]; - if (s.length() > 0) { - prop.mEnum[n++] = s; - } - } - } - } else { - log.warning("Error parsing '%1$s': \"%2$s\" is not a valid syntax", - file.getAbsolutePath(), line); - return null; - } - } - } - - return map; - } catch (FileNotFoundException e) { - // this should not happen since we usually test the file existence before - // calling the method. - // Return null below. - } catch (IOException e) { - log.warning("Error parsing '%1$s': %2$s.", file.getAbsolutePath(), - e.getMessage()); - } finally { - if (reader != null) { - try { - reader.close(); - } catch (IOException e) { - // ignore - } - } - } - - return null; - } - - /** - * Returns the index of <var>value</var> in {@link #BOOLEAN_VALUES}. - */ - public static int getBooleanValueIndex(String value) { - if (BOOLEAN_YES.equals(value)) { - return 0; - } else if (BOOLEAN_NO.equals(value)) { - return 1; - } - - return -1; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/build/BuildConfig.template b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/build/BuildConfig.template deleted file mode 100644 index 0344b55..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/build/BuildConfig.template +++ /dev/null @@ -1,6 +0,0 @@ -/** Automatically generated file. DO NOT MODIFY */ -package #PACKAGE#; - -public final class BuildConfig { - public final static boolean DEBUG = #DEBUG#; -}
\ No newline at end of file diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/build/BuildConfigGenerator.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/build/BuildConfigGenerator.java deleted file mode 100644 index 038975a..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/build/BuildConfigGenerator.java +++ /dev/null @@ -1,152 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.build; - -import java.io.BufferedReader; -import java.io.ByteArrayInputStream; -import java.io.File; -import java.io.FileOutputStream; -import java.io.IOException; -import java.io.InputStream; -import java.io.InputStreamReader; -import java.util.HashMap; -import java.util.Map; -import java.util.Map.Entry; - -/** - * Class able to generate a BuildConfig class in Android project. - * The BuildConfig class contains constants related to the build target. - */ -public class BuildConfigGenerator { - - public final static String BUILD_CONFIG_NAME = "BuildConfig.java"; - - private final static String PH_PACKAGE = "#PACKAGE#"; - private final static String PH_DEBUG = "#DEBUG#"; - - private final String mGenFolder; - private final String mAppPackage; - private final boolean mDebug; - - /** - * Creates a generator - * @param genFolder the gen folder of the project - * @param appPackage the application package - * @param debug whether it's a debug build - */ - public BuildConfigGenerator(String genFolder, String appPackage, boolean debug) { - mGenFolder = genFolder; - mAppPackage = appPackage; - mDebug = debug; - } - - /** - * Returns a File representing where the BuildConfig class will be. - */ - public File getFolderPath() { - File genFolder = new File(mGenFolder); - return new File(genFolder, mAppPackage.replace('.', File.separatorChar)); - } - - public File getBuildConfigFile() { - File folder = getFolderPath(); - return new File(folder, BUILD_CONFIG_NAME); - } - - /** - * Generates the BuildConfig class. - */ - public void generate() throws IOException { - String template = readEmbeddedTextFile("BuildConfig.template"); - - Map<String, String> map = new HashMap<String, String>(); - map.put(PH_PACKAGE, mAppPackage); - map.put(PH_DEBUG, Boolean.toString(mDebug)); - - String content = replaceParameters(template, map); - - File pkgFolder = getFolderPath(); - if (pkgFolder.isDirectory() == false) { - pkgFolder.mkdirs(); - } - - File buildConfigJava = new File(pkgFolder, BUILD_CONFIG_NAME); - writeFile(buildConfigJava, content); - } - - /** - * Reads and returns the content of a text file embedded in the jar file. - * @param filepath the file path to the text file - * @return null if the file could not be read - * @throws IOException - */ - private String readEmbeddedTextFile(String filepath) throws IOException { - InputStream is = BuildConfigGenerator.class.getResourceAsStream(filepath); - if (is != null) { - BufferedReader reader = new BufferedReader(new InputStreamReader(is)); - - String line; - StringBuilder total = new StringBuilder(reader.readLine()); - while ((line = reader.readLine()) != null) { - total.append('\n'); - total.append(line); - } - - return total.toString(); - } - - // this really shouldn't happen unless the sdklib packaging is broken. - throw new IOException("BuildConfig template is missing!"); - } - - private void writeFile(File file, String content) throws IOException { - FileOutputStream fos = null; - try { - fos = new FileOutputStream(file); - InputStream source = new ByteArrayInputStream(content.getBytes("UTF-8")); - - byte[] buffer = new byte[1024]; - int count = 0; - while ((count = source.read(buffer)) != -1) { - fos.write(buffer, 0, count); - } - } finally { - if (fos != null) { - fos.close(); - } - } - } - - /** - * Replaces placeholders found in a string with values. - * - * @param str the string to search for placeholders. - * @param parameters a map of <placeholder, Value> to search for in the string - * @return A new String object with the placeholder replaced by the values. - */ - private String replaceParameters(String str, Map<String, String> parameters) { - - for (Entry<String, String> entry : parameters.entrySet()) { - String value = entry.getValue(); - if (value != null) { - str = str.replaceAll(entry.getKey(), value); - } - } - - return str; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/build/DebugKeyProvider.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/build/DebugKeyProvider.java deleted file mode 100644 index 4f4af36..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/build/DebugKeyProvider.java +++ /dev/null @@ -1,212 +0,0 @@ -/* - * Copyright (C) 2008 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.build; - -import com.android.prefs.AndroidLocation; -import com.android.prefs.AndroidLocation.AndroidLocationException; - -import java.io.FileInputStream; -import java.io.FileNotFoundException; -import java.io.IOException; -import java.security.KeyStore; -import java.security.KeyStoreException; -import java.security.NoSuchAlgorithmException; -import java.security.PrivateKey; -import java.security.UnrecoverableEntryException; -import java.security.UnrecoverableKeyException; -import java.security.cert.Certificate; -import java.security.cert.CertificateException; - -/** - * A provider of a dummy key to sign Android application for debugging purpose. - * <p/>This provider uses a custom keystore to create and store a key with a known password. - */ -public class DebugKeyProvider { - - public interface IKeyGenOutput { - public void out(String message); - public void err(String message); - } - - private static final String PASSWORD_STRING = "android"; - private static final char[] PASSWORD_CHAR = PASSWORD_STRING.toCharArray(); - private static final String DEBUG_ALIAS = "AndroidDebugKey"; - - // Certificate CN value. This is a hard-coded value for the debug key. - // Android Market checks against this value in order to refuse applications signed with - // debug keys. - private static final String CERTIFICATE_DESC = "CN=Android Debug,O=Android,C=US"; - - private KeyStore.PrivateKeyEntry mEntry; - - public static class KeytoolException extends Exception { - /** default serial uid */ - private static final long serialVersionUID = 1L; - private String mJavaHome = null; - private String mCommandLine = null; - - KeytoolException(String message) { - super(message); - } - - KeytoolException(String message, String javaHome, String commandLine) { - super(message); - - mJavaHome = javaHome; - mCommandLine = commandLine; - } - - public String getJavaHome() { - return mJavaHome; - } - - public String getCommandLine() { - return mCommandLine; - } - } - - /** - * Creates a provider using a keystore at the given location. - * <p/>The keystore, and a new random android debug key are created if they do not yet exist. - * <p/>Password for the store/key is <code>android</code>, and the key alias is - * <code>AndroidDebugKey</code>. - * @param osKeyStorePath the OS path to the keystore, or <code>null</code> if the default one - * is to be used. - * @param storeType an optional keystore type, or <code>null</code> if the default is to - * be used. - * @param output an optional {@link IKeyGenOutput} object to get the stdout and stderr - * of the keytool process call. - * @throws KeytoolException If the creation of the debug key failed. - * @throws AndroidLocationException - */ - public DebugKeyProvider(String osKeyStorePath, String storeType, IKeyGenOutput output) - throws KeyStoreException, NoSuchAlgorithmException, CertificateException, - UnrecoverableEntryException, IOException, KeytoolException, AndroidLocationException { - - if (osKeyStorePath == null) { - osKeyStorePath = getDefaultKeyStoreOsPath(); - } - - if (loadKeyEntry(osKeyStorePath, storeType) == false) { - // create the store with the key - createNewStore(osKeyStorePath, storeType, output); - } - } - - /** - * Returns the OS path to the default debug keystore. - * - * @return The OS path to the default debug keystore. - * @throws KeytoolException - * @throws AndroidLocationException - */ - public static String getDefaultKeyStoreOsPath() - throws KeytoolException, AndroidLocationException { - String folder = AndroidLocation.getFolder(); - if (folder == null) { - throw new KeytoolException("Failed to get HOME directory!\n"); - } - String osKeyStorePath = folder + "debug.keystore"; - - return osKeyStorePath; - } - - /** - * Returns the debug {@link PrivateKey} to use to sign applications for debug purpose. - * @return the private key or <code>null</code> if its creation failed. - */ - @SuppressWarnings("unused") // the thrown Exceptions are not actually thrown - public PrivateKey getDebugKey() throws KeyStoreException, NoSuchAlgorithmException, - UnrecoverableKeyException, UnrecoverableEntryException { - if (mEntry != null) { - return mEntry.getPrivateKey(); - } - - return null; - } - - /** - * Returns the debug {@link Certificate} to use to sign applications for debug purpose. - * @return the certificate or <code>null</code> if its creation failed. - */ - @SuppressWarnings("unused") // the thrown Exceptions are not actually thrown - public Certificate getCertificate() throws KeyStoreException, NoSuchAlgorithmException, - UnrecoverableKeyException, UnrecoverableEntryException { - if (mEntry != null) { - return mEntry.getCertificate(); - } - - return null; - } - - /** - * Loads the debug key from the keystore. - * @param osKeyStorePath the OS path to the keystore. - * @param storeType an optional keystore type, or <code>null</code> if the default is to - * be used. - * @return <code>true</code> if success, <code>false</code> if the keystore does not exist. - */ - private boolean loadKeyEntry(String osKeyStorePath, String storeType) throws KeyStoreException, - NoSuchAlgorithmException, CertificateException, IOException, - UnrecoverableEntryException { - FileInputStream fis = null; - try { - KeyStore keyStore = KeyStore.getInstance( - storeType != null ? storeType : KeyStore.getDefaultType()); - fis = new FileInputStream(osKeyStorePath); - keyStore.load(fis, PASSWORD_CHAR); - mEntry = (KeyStore.PrivateKeyEntry)keyStore.getEntry( - DEBUG_ALIAS, new KeyStore.PasswordProtection(PASSWORD_CHAR)); - } catch (FileNotFoundException e) { - return false; - } finally { - if (fis != null) { - try { - fis.close(); - } catch (IOException e) { - // pass - } - } - } - - return true; - } - - /** - * Creates a new store - * @param osKeyStorePath the location of the store - * @param storeType an optional keystore type, or <code>null</code> if the default is to - * be used. - * @param output an optional {@link IKeyGenOutput} object to get the stdout and stderr - * of the keytool process call. - * @throws KeyStoreException - * @throws NoSuchAlgorithmException - * @throws CertificateException - * @throws UnrecoverableEntryException - * @throws IOException - * @throws KeytoolException - */ - private void createNewStore(String osKeyStorePath, String storeType, IKeyGenOutput output) - throws KeyStoreException, NoSuchAlgorithmException, CertificateException, - UnrecoverableEntryException, IOException, KeytoolException { - - if (KeystoreHelper.createNewStore(osKeyStorePath, storeType, PASSWORD_STRING, DEBUG_ALIAS, - PASSWORD_STRING, CERTIFICATE_DESC, 30 /* validity*/, output)) { - loadKeyEntry(osKeyStorePath, storeType); - } - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/build/KeystoreHelper.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/build/KeystoreHelper.java deleted file mode 100644 index ba4ce8c..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/build/KeystoreHelper.java +++ /dev/null @@ -1,170 +0,0 @@ -/* - * Copyright (C) 2008 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.build; - -import com.android.annotations.Nullable; -import com.android.sdklib.internal.build.DebugKeyProvider.IKeyGenOutput; -import com.android.sdklib.internal.build.DebugKeyProvider.KeytoolException; -import com.android.sdklib.util.GrabProcessOutput; -import com.android.sdklib.util.GrabProcessOutput.IProcessOutput; -import com.android.sdklib.util.GrabProcessOutput.Wait; - -import java.io.File; -import java.io.IOException; -import java.security.KeyStoreException; -import java.security.NoSuchAlgorithmException; -import java.security.UnrecoverableEntryException; -import java.security.cert.CertificateException; -import java.util.ArrayList; - -/** - * A Helper to create new keystore/key. - */ -public final class KeystoreHelper { - - /** - * Creates a new store - * @param osKeyStorePath the location of the store - * @param storeType an optional keystore type, or <code>null</code> if the default is to - * be used. - * @param output an optional {@link IKeyGenOutput} object to get the stdout and stderr - * of the keytool process call. - * @throws KeyStoreException - * @throws NoSuchAlgorithmException - * @throws CertificateException - * @throws UnrecoverableEntryException - * @throws IOException - * @throws KeytoolException - */ - public static boolean createNewStore( - String osKeyStorePath, - String storeType, - String storePassword, - String alias, - String keyPassword, - String description, - int validityYears, - final IKeyGenOutput output) - throws KeyStoreException, NoSuchAlgorithmException, CertificateException, - UnrecoverableEntryException, IOException, KeytoolException { - - // get the executable name of keytool depending on the platform. - String os = System.getProperty("os.name"); - - String keytoolCommand; - if (os.startsWith("Windows")) { - keytoolCommand = "keytool.exe"; - } else { - keytoolCommand = "keytool"; - } - - String javaHome = System.getProperty("java.home"); - - if (javaHome != null && javaHome.length() > 0) { - keytoolCommand = javaHome + File.separator + "bin" + File.separator + keytoolCommand; - } - - // create the command line to call key tool to build the key with no user input. - ArrayList<String> commandList = new ArrayList<String>(); - commandList.add(keytoolCommand); - commandList.add("-genkey"); - commandList.add("-alias"); - commandList.add(alias); - commandList.add("-keyalg"); - commandList.add("RSA"); - commandList.add("-dname"); - commandList.add(description); - commandList.add("-validity"); - commandList.add(Integer.toString(validityYears * 365)); - commandList.add("-keypass"); - commandList.add(keyPassword); - commandList.add("-keystore"); - commandList.add(osKeyStorePath); - commandList.add("-storepass"); - commandList.add(storePassword); - if (storeType != null) { - commandList.add("-storetype"); - commandList.add(storeType); - } - - String[] commandArray = commandList.toArray(new String[commandList.size()]); - - // launch the command line process - int result = 0; - try { - Process process = Runtime.getRuntime().exec(commandArray); - result = GrabProcessOutput.grabProcessOutput( - process, - Wait.WAIT_FOR_READERS, - new IProcessOutput() { - @Override - public void out(@Nullable String line) { - if (line != null) { - if (output != null) { - output.out(line); - } else { - System.out.println(line); - } - } - } - - @Override - public void err(@Nullable String line) { - if (line != null) { - if (output != null) { - output.err(line); - } else { - System.err.println(line); - } - } - } - }); - } catch (Exception e) { - // create the command line as one string for debugging purposes - StringBuilder builder = new StringBuilder(); - boolean firstArg = true; - for (String arg : commandArray) { - boolean hasSpace = arg.indexOf(' ') != -1; - - if (firstArg == true) { - firstArg = false; - } else { - builder.append(' '); - } - - if (hasSpace) { - builder.append('"'); - } - - builder.append(arg); - - if (hasSpace) { - builder.append('"'); - } - } - - throw new KeytoolException("Failed to create key: " + e.getMessage(), - javaHome, builder.toString()); - } - - if (result != 0) { - return false; - } - - return true; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/build/SignedJarBuilder.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/build/SignedJarBuilder.java deleted file mode 100644 index 5044b45..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/build/SignedJarBuilder.java +++ /dev/null @@ -1,394 +0,0 @@ -/* - * Copyright (C) 2008 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.build; - -import com.android.sdklib.internal.build.SignedJarBuilder.IZipEntryFilter.ZipAbortException; - -import sun.misc.BASE64Encoder; -import sun.security.pkcs.ContentInfo; -import sun.security.pkcs.PKCS7; -import sun.security.pkcs.SignerInfo; -import sun.security.x509.AlgorithmId; -import sun.security.x509.X500Name; - -import java.io.ByteArrayOutputStream; -import java.io.File; -import java.io.FileInputStream; -import java.io.FilterOutputStream; -import java.io.IOException; -import java.io.InputStream; -import java.io.OutputStream; -import java.io.PrintStream; -import java.security.DigestOutputStream; -import java.security.GeneralSecurityException; -import java.security.MessageDigest; -import java.security.NoSuchAlgorithmException; -import java.security.PrivateKey; -import java.security.Signature; -import java.security.SignatureException; -import java.security.cert.X509Certificate; -import java.util.Map; -import java.util.jar.Attributes; -import java.util.jar.JarEntry; -import java.util.jar.JarFile; -import java.util.jar.JarOutputStream; -import java.util.jar.Manifest; -import java.util.zip.ZipEntry; -import java.util.zip.ZipInputStream; - -/** - * A Jar file builder with signature support. - */ -public class SignedJarBuilder { - private static final String DIGEST_ALGORITHM = "SHA1"; - private static final String DIGEST_ATTR = "SHA1-Digest"; - private static final String DIGEST_MANIFEST_ATTR = "SHA1-Digest-Manifest"; - - /** Write to another stream and also feed it to the Signature object. */ - private static class SignatureOutputStream extends FilterOutputStream { - private Signature mSignature; - private int mCount = 0; - - public SignatureOutputStream(OutputStream out, Signature sig) { - super(out); - mSignature = sig; - } - - @Override - public void write(int b) throws IOException { - try { - mSignature.update((byte) b); - } catch (SignatureException e) { - throw new IOException("SignatureException: " + e); - } - super.write(b); - mCount++; - } - - @Override - public void write(byte[] b, int off, int len) throws IOException { - try { - mSignature.update(b, off, len); - } catch (SignatureException e) { - throw new IOException("SignatureException: " + e); - } - super.write(b, off, len); - mCount += len; - } - - public int size() { - return mCount; - } - } - - private JarOutputStream mOutputJar; - private PrivateKey mKey; - private X509Certificate mCertificate; - private Manifest mManifest; - private BASE64Encoder mBase64Encoder; - private MessageDigest mMessageDigest; - - private byte[] mBuffer = new byte[4096]; - - /** - * Classes which implement this interface provides a method to check whether a file should - * be added to a Jar file. - */ - public interface IZipEntryFilter { - - /** - * An exception thrown during packaging of a zip file into APK file. - * This is typically thrown by implementations of - * {@link IZipEntryFilter#checkEntry(String)}. - */ - public static class ZipAbortException extends Exception { - private static final long serialVersionUID = 1L; - - public ZipAbortException() { - super(); - } - - public ZipAbortException(String format, Object... args) { - super(String.format(format, args)); - } - - public ZipAbortException(Throwable cause, String format, Object... args) { - super(String.format(format, args), cause); - } - - public ZipAbortException(Throwable cause) { - super(cause); - } - } - - - /** - * Checks a file for inclusion in a Jar archive. - * @param archivePath the archive file path of the entry - * @return <code>true</code> if the file should be included. - * @throws ZipAbortException if writing the file should be aborted. - */ - public boolean checkEntry(String archivePath) throws ZipAbortException; - } - - /** - * Creates a {@link SignedJarBuilder} with a given output stream, and signing information. - * <p/>If either <code>key</code> or <code>certificate</code> is <code>null</code> then - * the archive will not be signed. - * @param out the {@link OutputStream} where to write the Jar archive. - * @param key the {@link PrivateKey} used to sign the archive, or <code>null</code>. - * @param certificate the {@link X509Certificate} used to sign the archive, or - * <code>null</code>. - * @throws IOException - * @throws NoSuchAlgorithmException - */ - public SignedJarBuilder(OutputStream out, PrivateKey key, X509Certificate certificate) - throws IOException, NoSuchAlgorithmException { - mOutputJar = new JarOutputStream(out); - mOutputJar.setLevel(9); - mKey = key; - mCertificate = certificate; - - if (mKey != null && mCertificate != null) { - mManifest = new Manifest(); - Attributes main = mManifest.getMainAttributes(); - main.putValue("Manifest-Version", "1.0"); - main.putValue("Created-By", "1.0 (Android)"); - - mBase64Encoder = new BASE64Encoder(); - mMessageDigest = MessageDigest.getInstance(DIGEST_ALGORITHM); - } - } - - /** - * Writes a new {@link File} into the archive. - * @param inputFile the {@link File} to write. - * @param jarPath the filepath inside the archive. - * @throws IOException - */ - public void writeFile(File inputFile, String jarPath) throws IOException { - // Get an input stream on the file. - FileInputStream fis = new FileInputStream(inputFile); - try { - - // create the zip entry - JarEntry entry = new JarEntry(jarPath); - entry.setTime(inputFile.lastModified()); - - writeEntry(fis, entry); - } finally { - // close the file stream used to read the file - fis.close(); - } - } - - /** - * Copies the content of a Jar/Zip archive into the receiver archive. - * <p/>An optional {@link IZipEntryFilter} allows to selectively choose which files - * to copy over. - * @param input the {@link InputStream} for the Jar/Zip to copy. - * @param filter the filter or <code>null</code> - * @throws IOException - * @throws ZipAbortException if the {@link IZipEntryFilter} filter indicated that the write - * must be aborted. - */ - public void writeZip(InputStream input, IZipEntryFilter filter) - throws IOException, ZipAbortException { - ZipInputStream zis = new ZipInputStream(input); - - try { - // loop on the entries of the intermediary package and put them in the final package. - ZipEntry entry; - while ((entry = zis.getNextEntry()) != null) { - String name = entry.getName(); - - // do not take directories or anything inside a potential META-INF folder. - if (entry.isDirectory() || name.startsWith("META-INF/")) { - continue; - } - - // if we have a filter, we check the entry against it - if (filter != null && filter.checkEntry(name) == false) { - continue; - } - - JarEntry newEntry; - - // Preserve the STORED method of the input entry. - if (entry.getMethod() == JarEntry.STORED) { - newEntry = new JarEntry(entry); - } else { - // Create a new entry so that the compressed len is recomputed. - newEntry = new JarEntry(name); - } - - writeEntry(zis, newEntry); - - zis.closeEntry(); - } - } finally { - zis.close(); - } - } - - /** - * Closes the Jar archive by creating the manifest, and signing the archive. - * @throws IOException - * @throws GeneralSecurityException - */ - public void close() throws IOException, GeneralSecurityException { - if (mManifest != null) { - // write the manifest to the jar file - mOutputJar.putNextEntry(new JarEntry(JarFile.MANIFEST_NAME)); - mManifest.write(mOutputJar); - - // CERT.SF - Signature signature = Signature.getInstance("SHA1with" + mKey.getAlgorithm()); - signature.initSign(mKey); - mOutputJar.putNextEntry(new JarEntry("META-INF/CERT.SF")); - SignatureOutputStream out = new SignatureOutputStream(mOutputJar, signature); - writeSignatureFile(out); - - // CERT.* - mOutputJar.putNextEntry(new JarEntry("META-INF/CERT." + mKey.getAlgorithm())); - writeSignatureBlock(signature, mCertificate, mKey); - - // close out at the end because it can also close mOutputJar. - // (there's some timing issue here I think, because it's worked before with out - // being closed after writing CERT.SF). - out.close(); - } - - mOutputJar.close(); - mOutputJar = null; - } - - /** - * Clean up of the builder for interrupted workflow. - * This does nothing if {@link #close()} was called successfully. - */ - public void cleanUp() { - if (mOutputJar != null) { - try { - mOutputJar.close(); - } catch (IOException e) { - // pass - } - } - } - - /** - * Adds an entry to the output jar, and write its content from the {@link InputStream} - * @param input The input stream from where to write the entry content. - * @param entry the entry to write in the jar. - * @throws IOException - */ - private void writeEntry(InputStream input, JarEntry entry) throws IOException { - // add the entry to the jar archive - mOutputJar.putNextEntry(entry); - - // read the content of the entry from the input stream, and write it into the archive. - int count; - while ((count = input.read(mBuffer)) != -1) { - mOutputJar.write(mBuffer, 0, count); - - // update the digest - if (mMessageDigest != null) { - mMessageDigest.update(mBuffer, 0, count); - } - } - - // close the entry for this file - mOutputJar.closeEntry(); - - if (mManifest != null) { - // update the manifest for this entry. - Attributes attr = mManifest.getAttributes(entry.getName()); - if (attr == null) { - attr = new Attributes(); - mManifest.getEntries().put(entry.getName(), attr); - } - attr.putValue(DIGEST_ATTR, mBase64Encoder.encode(mMessageDigest.digest())); - } - } - - /** Writes a .SF file with a digest to the manifest. */ - private void writeSignatureFile(SignatureOutputStream out) - throws IOException, GeneralSecurityException { - Manifest sf = new Manifest(); - Attributes main = sf.getMainAttributes(); - main.putValue("Signature-Version", "1.0"); - main.putValue("Created-By", "1.0 (Android)"); - - BASE64Encoder base64 = new BASE64Encoder(); - MessageDigest md = MessageDigest.getInstance(DIGEST_ALGORITHM); - PrintStream print = new PrintStream( - new DigestOutputStream(new ByteArrayOutputStream(), md), - true, "UTF-8"); - - // Digest of the entire manifest - mManifest.write(print); - print.flush(); - main.putValue(DIGEST_MANIFEST_ATTR, base64.encode(md.digest())); - - Map<String, Attributes> entries = mManifest.getEntries(); - for (Map.Entry<String, Attributes> entry : entries.entrySet()) { - // Digest of the manifest stanza for this entry. - print.print("Name: " + entry.getKey() + "\r\n"); - for (Map.Entry<Object, Object> att : entry.getValue().entrySet()) { - print.print(att.getKey() + ": " + att.getValue() + "\r\n"); - } - print.print("\r\n"); - print.flush(); - - Attributes sfAttr = new Attributes(); - sfAttr.putValue(DIGEST_ATTR, base64.encode(md.digest())); - sf.getEntries().put(entry.getKey(), sfAttr); - } - - sf.write(out); - - // A bug in the java.util.jar implementation of Android platforms - // up to version 1.6 will cause a spurious IOException to be thrown - // if the length of the signature file is a multiple of 1024 bytes. - // As a workaround, add an extra CRLF in this case. - if ((out.size() % 1024) == 0) { - out.write('\r'); - out.write('\n'); - } - } - - /** Write the certificate file with a digital signature. */ - private void writeSignatureBlock(Signature signature, X509Certificate publicKey, - PrivateKey privateKey) - throws IOException, GeneralSecurityException { - SignerInfo signerInfo = new SignerInfo( - new X500Name(publicKey.getIssuerX500Principal().getName()), - publicKey.getSerialNumber(), - AlgorithmId.get(DIGEST_ALGORITHM), - AlgorithmId.get(privateKey.getAlgorithm()), - signature.sign()); - - PKCS7 pkcs7 = new PKCS7( - new AlgorithmId[] { AlgorithmId.get(DIGEST_ALGORITHM) }, - new ContentInfo(ContentInfo.DATA_OID, null), - new X509Certificate[] { publicKey }, - new SignerInfo[] { signerInfo }); - - pkcs7.encodeSignedData(mOutputJar); - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/build/SymbolLoader.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/build/SymbolLoader.java deleted file mode 100644 index 3be729e..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/build/SymbolLoader.java +++ /dev/null @@ -1,94 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.build; - -import com.google.common.base.Charsets; -import com.google.common.collect.HashBasedTable; -import com.google.common.collect.Table; -import com.google.common.io.Files; - -import java.io.File; -import java.io.IOException; -import java.util.List; - -/** - */ -public class SymbolLoader { - - private final File mSymbolFile; - private Table<String, String, SymbolEntry> mSymbols; - - public static class SymbolEntry { - private final String mName; - private final String mType; - private final String mValue; - - public SymbolEntry(String name, String type, String value) { - mName = name; - mType = type; - mValue = value; - } - - public String getValue() { - return mValue; - } - - public String getName() { - return mName; - } - - public String getType() { - return mType; - } - } - - public SymbolLoader(File symbolFile) { - mSymbolFile = symbolFile; - } - - public void load() throws IOException { - List<String> lines = Files.readLines(mSymbolFile, Charsets.UTF_8); - - mSymbols = HashBasedTable.create(); - - String currentLine = ""; - try { - for (String line : lines) { - currentLine = line; - // format is "<type> <class> <name> <value>" - // don't want to split on space as value could contain spaces. - int pos = line.indexOf(' '); - String type = line.substring(0, pos); - int pos2 = line.indexOf(' ', pos + 1); - String className = line.substring(pos + 1, pos2); - int pos3 = line.indexOf(' ', pos2 + 1); - String name = line.substring(pos2 + 1, pos3); - String value = line.substring(pos3 + 1); - - mSymbols.put(className, name, new SymbolEntry(name, type, value)); - } - } catch (Exception e) { - // Catch both ArrayIndexOutOfBoundsException and StringIndexOutOfBoundsException - throw new IOException("File format error reading " + mSymbolFile.getAbsolutePath() - + ": " + currentLine, e); - } - } - - Table<String, String, SymbolEntry> getSymbols() { - return mSymbols; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/build/SymbolWriter.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/build/SymbolWriter.java deleted file mode 100644 index 7411517..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/build/SymbolWriter.java +++ /dev/null @@ -1,105 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.build; - -import com.android.SdkConstants; -import com.android.sdklib.internal.build.SymbolLoader.SymbolEntry; -import com.google.common.base.Charsets; -import com.google.common.base.Splitter; -import com.google.common.collect.Table; -import com.google.common.io.Closeables; -import com.google.common.io.Files; - -import java.io.BufferedWriter; -import java.io.File; -import java.io.IOException; -import java.util.Map; - -/** - */ -public class SymbolWriter { - - private final String mOutFolder; - private final String mPackageName; - private final SymbolLoader mSymbols; - private final SymbolLoader mValues; - - public SymbolWriter(String outFolder, String packageName, SymbolLoader symbols, - SymbolLoader values) { - mOutFolder = outFolder; - mPackageName = packageName; - mSymbols = symbols; - mValues = values; - } - - @SuppressWarnings("resource") // Eclipse does handle Closeables.closeQuietly; see E#381445 - public void write() throws IOException { - Splitter splitter = Splitter.on('.'); - Iterable<String> folders = splitter.split(mPackageName); - File file = new File(mOutFolder); - for (String folder : folders) { - file = new File(file, folder); - } - file.mkdirs(); - file = new File(file, SdkConstants.FN_RESOURCE_CLASS); - - BufferedWriter writer = null; - try { - writer = Files.newWriter(file, Charsets.UTF_8); - - writer.write("/* AUTO-GENERATED FILE. DO NOT MODIFY.\n"); - writer.write(" *\n"); - writer.write(" * This class was automatically generated by the\n"); - writer.write(" * aapt tool from the resource data it found. It\n"); - writer.write(" * should not be modified by hand.\n"); - writer.write(" */\n"); - - writer.write("package "); - writer.write(mPackageName); - writer.write(";\n\npublic final class R {\n"); - - Table<String, String, SymbolEntry> symbols = mSymbols.getSymbols(); - Table<String, String, SymbolEntry> values = mValues.getSymbols(); - - for (String row : symbols.rowKeySet()) { - writer.write("\tpublic static final class "); - writer.write(row); - writer.write(" {\n"); - - for (Map.Entry<String, SymbolEntry> symbol : symbols.row(row).entrySet()) { - // get the matching SymbolEntry from the values Table. - SymbolEntry value = values.get(row, symbol.getKey()); - if (value != null) { - writer.write("\t\tpublic static final "); - writer.write(value.getType()); - writer.write(" "); - writer.write(value.getName()); - writer.write(" = "); - writer.write(value.getValue()); - writer.write(";\n"); - } - } - - writer.write("\t}\n"); - } - - writer.write("}\n"); - } finally { - Closeables.closeQuietly(writer); - } - } -}
\ No newline at end of file diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/project/IPropertySource.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/project/IPropertySource.java deleted file mode 100644 index 92bd6b9..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/project/IPropertySource.java +++ /dev/null @@ -1,26 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.project; - -/** - * A source able to return properties by name. - * - */ -public interface IPropertySource { - String getProperty(String name); - void debugPrint(); -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/project/ProjectCreator.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/project/ProjectCreator.java deleted file mode 100644 index 1fdea64..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/project/ProjectCreator.java +++ /dev/null @@ -1,1322 +0,0 @@ -/* - * Copyright (C) 2007 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.project; - -import com.android.SdkConstants; -import com.android.io.FileWrapper; -import com.android.io.FolderWrapper; -import com.android.sdklib.IAndroidTarget; -import com.android.sdklib.SdkManager; -import com.android.sdklib.internal.project.ProjectProperties.PropertyType; -import com.android.utils.ILogger; -import com.android.xml.AndroidManifest; -import com.android.xml.AndroidXPathFactory; - -import org.w3c.dom.NodeList; -import org.xml.sax.InputSource; - -import java.io.BufferedReader; -import java.io.BufferedWriter; -import java.io.File; -import java.io.FileInputStream; -import java.io.FileNotFoundException; -import java.io.FileOutputStream; -import java.io.FileReader; -import java.io.FileWriter; -import java.io.IOException; -import java.util.HashMap; -import java.util.Map; -import java.util.regex.Matcher; -import java.util.regex.Pattern; - -import javax.xml.xpath.XPath; -import javax.xml.xpath.XPathConstants; -import javax.xml.xpath.XPathExpressionException; -import javax.xml.xpath.XPathFactory; - -/** - * Creates the basic files needed to get an Android project up and running. - */ -public class ProjectCreator { - - /** Version of the build.xml. Stored in version-tag */ - private final static int MIN_BUILD_VERSION_TAG = 1; - - /** Package path substitution string used in template files, i.e. "PACKAGE_PATH" */ - private final static String PH_JAVA_FOLDER = "PACKAGE_PATH"; - /** Package name substitution string used in template files, i.e. "PACKAGE" */ - private final static String PH_PACKAGE = "PACKAGE"; - /** Activity name substitution string used in template files, i.e. "ACTIVITY_NAME". - * @deprecated This is only used for older templates. For new ones see - * {@link #PH_ACTIVITY_ENTRY_NAME}, and {@link #PH_ACTIVITY_CLASS_NAME}. */ - @Deprecated - private final static String PH_ACTIVITY_NAME = "ACTIVITY_NAME"; - /** Activity name substitution string used in manifest templates, i.e. "ACTIVITY_ENTRY_NAME".*/ - private final static String PH_ACTIVITY_ENTRY_NAME = "ACTIVITY_ENTRY_NAME"; - /** Activity name substitution string used in class templates, i.e. "ACTIVITY_CLASS_NAME".*/ - private final static String PH_ACTIVITY_CLASS_NAME = "ACTIVITY_CLASS_NAME"; - /** Activity FQ-name substitution string used in class templates, i.e. "ACTIVITY_FQ_NAME".*/ - private final static String PH_ACTIVITY_FQ_NAME = "ACTIVITY_FQ_NAME"; - /** Original Activity class name substitution string used in class templates, i.e. - * "ACTIVITY_TESTED_CLASS_NAME".*/ - private final static String PH_ACTIVITY_TESTED_CLASS_NAME = "ACTIVITY_TESTED_CLASS_NAME"; - /** Project name substitution string used in template files, i.e. "PROJECT_NAME". */ - public final static String PH_PROJECT_NAME = "PROJECT_NAME"; - /** Application icon substitution string used in the manifest template */ - private final static String PH_ICON = "ICON"; - /** Version tag name substitution string used in template files, i.e. "VERSION_TAG". */ - private final static String PH_VERSION_TAG = "VERSION_TAG"; - - /** The xpath to find a project name in an Ant build file. */ - private static final String XPATH_PROJECT_NAME = "/project/@name"; - - /** Pattern for characters accepted in a project name. Since this will be used as a - * directory name, we're being a bit conservative on purpose: dot and space cannot be used. */ - public static final Pattern RE_PROJECT_NAME = Pattern.compile("[a-zA-Z0-9_]+"); - /** List of valid characters for a project name. Used for display purposes. */ - public final static String CHARS_PROJECT_NAME = "a-z A-Z 0-9 _"; - - /** Pattern for characters accepted in a package name. A package is list of Java identifier - * separated by a dot. We need to have at least one dot (e.g. a two-level package name). - * A Java identifier cannot start by a digit. */ - public static final Pattern RE_PACKAGE_NAME = - Pattern.compile("[a-zA-Z_][a-zA-Z0-9_]*(?:\\.[a-zA-Z_][a-zA-Z0-9_]*)+"); - /** List of valid characters for a project name. Used for display purposes. */ - public final static String CHARS_PACKAGE_NAME = "a-z A-Z 0-9 _"; - - /** Pattern for characters accepted in an activity name, which is a Java identifier. */ - public static final Pattern RE_ACTIVITY_NAME = - Pattern.compile("[a-zA-Z_][a-zA-Z0-9_]*"); - /** List of valid characters for a project name. Used for display purposes. */ - public final static String CHARS_ACTIVITY_NAME = "a-z A-Z 0-9 _"; - - - public enum OutputLevel { - /** Silent mode. Project creation will only display errors. */ - SILENT, - /** Normal mode. Project creation will display what's being done, display - * error but not warnings. */ - NORMAL, - /** Verbose mode. Project creation will display what's being done, errors and warnings. */ - VERBOSE; - } - - /** - * Exception thrown when a project creation fails, typically because a template - * file cannot be written. - */ - private static class ProjectCreateException extends Exception { - /** default UID. This will not be serialized anyway. */ - private static final long serialVersionUID = 1L; - - @SuppressWarnings("unused") - ProjectCreateException(String message) { - super(message); - } - - ProjectCreateException(Throwable t, String format, Object... args) { - super(format != null ? String.format(format, args) : format, t); - } - - ProjectCreateException(String format, Object... args) { - super(String.format(format, args)); - } - } - - /** The {@link OutputLevel} verbosity. */ - private final OutputLevel mLevel; - /** Logger for errors and output. Cannot be null. */ - private final ILogger mLog; - /** The OS path of the SDK folder. */ - private final String mSdkFolder; - /** The {@link SdkManager} instance. */ - private final SdkManager mSdkManager; - - /** - * Helper class to create android projects. - * - * @param sdkManager The {@link SdkManager} instance. - * @param sdkFolder The OS path of the SDK folder. - * @param level The {@link OutputLevel} verbosity. - * @param log Logger for errors and output. Cannot be null. - */ - public ProjectCreator(SdkManager sdkManager, String sdkFolder, OutputLevel level, ILogger log) { - mSdkManager = sdkManager; - mSdkFolder = sdkFolder; - mLevel = level; - mLog = log; - } - - /** - * Creates a new project. - * <p/> - * The caller should have already checked and sanitized the parameters. - * - * @param folderPath the folder of the project to create. - * @param projectName the name of the project. The name must match the - * {@link #RE_PROJECT_NAME} regex. - * @param packageName the package of the project. The name must match the - * {@link #RE_PACKAGE_NAME} regex. - * @param activityEntry the activity of the project as it will appear in the manifest. Can be - * null if no activity should be created. The name must match the - * {@link #RE_ACTIVITY_NAME} regex. - * @param target the project target. - * @param library whether the project is a library. - * @param pathToMainProject if non-null the project will be setup to test a main project - * located at the given path. - */ - public void createProject(String folderPath, String projectName, - String packageName, String activityEntry, IAndroidTarget target, boolean library, - String pathToMainProject) { - - // create project folder if it does not exist - File projectFolder = checkNewProjectLocation(folderPath); - if (projectFolder == null) { - return; - } - - try { - boolean isTestProject = pathToMainProject != null; - - // first create the project properties. - - // location of the SDK goes in localProperty - ProjectPropertiesWorkingCopy localProperties = ProjectProperties.create(folderPath, - PropertyType.LOCAL); - localProperties.setProperty(ProjectProperties.PROPERTY_SDK, mSdkFolder); - localProperties.save(); - - // target goes in project properties - ProjectPropertiesWorkingCopy projectProperties = ProjectProperties.create(folderPath, - PropertyType.PROJECT); - projectProperties.setProperty(ProjectProperties.PROPERTY_TARGET, target.hashString()); - if (library) { - projectProperties.setProperty(ProjectProperties.PROPERTY_LIBRARY, "true"); - } - projectProperties.save(); - - // create a ant.properties file with just the application package - ProjectPropertiesWorkingCopy antProperties = ProjectProperties.create(folderPath, - PropertyType.ANT); - - if (isTestProject) { - antProperties.setProperty(ProjectProperties.PROPERTY_TESTED_PROJECT, - pathToMainProject); - } - - antProperties.save(); - - // create the map for place-holders of values to replace in the templates - final HashMap<String, String> keywords = new HashMap<String, String>(); - - // create the required folders. - // compute src folder path - final String packagePath = - stripString(packageName.replace(".", File.separator), - File.separatorChar); - - // put this path in the place-holder map for project files that needs to list - // files manually. - keywords.put(PH_JAVA_FOLDER, packagePath); - keywords.put(PH_PACKAGE, packageName); - keywords.put(PH_VERSION_TAG, Integer.toString(MIN_BUILD_VERSION_TAG)); - - - // compute some activity related information - String fqActivityName = null, activityPath = null, activityClassName = null; - String originalActivityEntry = activityEntry; - String originalActivityClassName = null; - if (activityEntry != null) { - if (isTestProject) { - // append Test so that it doesn't collide with the main project activity. - activityEntry += "Test"; - - // get the classname from the original activity entry. - int pos = originalActivityEntry.lastIndexOf('.'); - if (pos != -1) { - originalActivityClassName = originalActivityEntry.substring(pos + 1); - } else { - originalActivityClassName = originalActivityEntry; - } - } - - // get the fully qualified name of the activity - fqActivityName = AndroidManifest.combinePackageAndClassName(packageName, - activityEntry); - - // get the activity path (replace the . to /) - activityPath = stripString(fqActivityName.replace(".", File.separator), - File.separatorChar); - - // remove the last segment, so that we only have the path to the activity, but - // not the activity filename itself. - activityPath = activityPath.substring(0, - activityPath.lastIndexOf(File.separatorChar)); - - // finally, get the class name for the activity - activityClassName = fqActivityName.substring(fqActivityName.lastIndexOf('.') + 1); - } - - // at this point we have the following for the activity: - // activityEntry: this is the manifest entry. For instance .MyActivity - // fqActivityName: full-qualified class name: com.foo.MyActivity - // activityClassName: only the classname: MyActivity - // originalActivityClassName: the classname of the activity being tested (if applicable) - - // Add whatever activity info is needed in the place-holder map. - // Older templates only expect ACTIVITY_NAME to be the same (and unmodified for tests). - if (target.getVersion().getApiLevel() < 4) { // legacy - if (originalActivityEntry != null) { - keywords.put(PH_ACTIVITY_NAME, originalActivityEntry); - } - } else { - // newer templates make a difference between the manifest entries, classnames, - // as well as the main and test classes. - if (activityEntry != null) { - keywords.put(PH_ACTIVITY_ENTRY_NAME, activityEntry); - keywords.put(PH_ACTIVITY_CLASS_NAME, activityClassName); - keywords.put(PH_ACTIVITY_FQ_NAME, fqActivityName); - if (originalActivityClassName != null) { - keywords.put(PH_ACTIVITY_TESTED_CLASS_NAME, originalActivityClassName); - } - } - } - - // Take the project name from the command line if there's one - if (projectName != null) { - keywords.put(PH_PROJECT_NAME, projectName); - } else { - if (activityClassName != null) { - // Use the activity class name as project name - keywords.put(PH_PROJECT_NAME, activityClassName); - } else { - // We need a project name. Just pick up the basename of the project - // directory. - projectName = projectFolder.getName(); - keywords.put(PH_PROJECT_NAME, projectName); - } - } - - // create the source folder for the activity - if (activityClassName != null) { - String srcActivityFolderPath = - SdkConstants.FD_SOURCES + File.separator + activityPath; - File sourceFolder = createDirs(projectFolder, srcActivityFolderPath); - - String javaTemplate = isTestProject ? "java_tests_file.template" - : "java_file.template"; - String activityFileName = activityClassName + ".java"; - - installTargetTemplate(javaTemplate, new File(sourceFolder, activityFileName), - keywords, target); - } else { - // we should at least create 'src' - createDirs(projectFolder, SdkConstants.FD_SOURCES); - } - - // create other useful folders - File resourceFolder = createDirs(projectFolder, SdkConstants.FD_RESOURCES); - createDirs(projectFolder, SdkConstants.FD_OUTPUT); - createDirs(projectFolder, SdkConstants.FD_NATIVE_LIBS); - - if (isTestProject == false) { - /* Make res files only for non test projects */ - File valueFolder = createDirs(resourceFolder, SdkConstants.FD_RES_VALUES); - installTargetTemplate("strings.template", new File(valueFolder, "strings.xml"), - keywords, target); - - File layoutFolder = createDirs(resourceFolder, SdkConstants.FD_RES_LAYOUT); - installTargetTemplate("layout.template", new File(layoutFolder, "main.xml"), - keywords, target); - - // create the icons - if (installIcons(resourceFolder, target)) { - keywords.put(PH_ICON, "android:icon=\"@drawable/ic_launcher\""); - } else { - keywords.put(PH_ICON, ""); - } - } - - /* Make AndroidManifest.xml and build.xml files */ - String manifestTemplate = "AndroidManifest.template"; - if (isTestProject) { - manifestTemplate = "AndroidManifest.tests.template"; - } - - installTargetTemplate(manifestTemplate, - new File(projectFolder, SdkConstants.FN_ANDROID_MANIFEST_XML), - keywords, target); - - installTemplate("build.template", - new File(projectFolder, SdkConstants.FN_BUILD_XML), - keywords); - - // install the proguard config file. - installTemplate(SdkConstants.FN_PROJECT_PROGUARD_FILE, - new File(projectFolder, SdkConstants.FN_PROJECT_PROGUARD_FILE), - null /*keywords*/); - } catch (Exception e) { - mLog.error(e, null); - } - } - - private File checkNewProjectLocation(String folderPath) { - File projectFolder = new File(folderPath); - if (!projectFolder.exists()) { - - boolean created = false; - Throwable t = null; - try { - created = projectFolder.mkdirs(); - } catch (Exception e) { - t = e; - } - - if (created) { - println("Created project directory: %1$s", projectFolder); - } else { - mLog.error(t, "Could not create directory: %1$s", projectFolder); - return null; - } - } else { - Exception e = null; - String error = null; - try { - String[] content = projectFolder.list(); - if (content == null) { - error = "Project folder '%1$s' is not a directory."; - } else if (content.length != 0) { - error = "Project folder '%1$s' is not empty. Please consider using '%2$s update' instead."; - } - } catch (Exception e1) { - e = e1; - } - - if (e != null || error != null) { - mLog.error(e, error, projectFolder, SdkConstants.androidCmdName()); - } - } - return projectFolder; - } - - /** - * Updates an existing project. - * <p/> - * Workflow: - * <ul> - * <li> Check AndroidManifest.xml is present (required) - * <li> Check if there's a legacy properties file and convert it - * <li> Check there's a project.properties with a target *or* --target was specified - * <li> Update default.prop if --target was specified - * <li> Refresh/create "sdk" in local.properties - * <li> Build.xml: create if not present or if version-tag is found or not. version-tag:custom - * prevent any overwrite. version-tag:[integer] will override. missing version-tag will query - * the dev. - * </ul> - * - * @param folderPath the folder of the project to update. This folder must exist. - * @param target the project target. Can be null. - * @param projectName The project name from --name. Can be null. - * @param libraryPath the path to a library to add to the references. Can be null. - * @return true if the project was successfully updated. - */ - @SuppressWarnings("deprecation") - public boolean updateProject(String folderPath, IAndroidTarget target, String projectName, - String libraryPath) { - // since this is an update, check the folder does point to a project - FileWrapper androidManifest = checkProjectFolder(folderPath, - SdkConstants.FN_ANDROID_MANIFEST_XML); - if (androidManifest == null) { - return false; - } - - // get the parent folder. - FolderWrapper projectFolder = (FolderWrapper) androidManifest.getParentFolder(); - - boolean hasProguard = false; - - // Check there's a project.properties with a target *or* --target was specified - IAndroidTarget originalTarget = null; - boolean writeProjectProp = false; - ProjectProperties props = ProjectProperties.load(projectFolder, PropertyType.PROJECT); - - if (props == null) { - // no project.properties, try to load default.properties - props = ProjectProperties.load(projectFolder, PropertyType.LEGACY_DEFAULT); - writeProjectProp = true; - } - - if (props != null) { - String targetHash = props.getProperty(ProjectProperties.PROPERTY_TARGET); - originalTarget = mSdkManager.getTargetFromHashString(targetHash); - - // if the project is already setup with proguard, we won't copy the proguard config. - hasProguard = props.getProperty(ProjectProperties.PROPERTY_PROGUARD_CONFIG) != null; - } - - if (originalTarget == null && target == null) { - mLog.error(null, - "The project either has no target set or the target is invalid.\n" + - "Please provide a --target to the '%1$s update' command.", - SdkConstants.androidCmdName()); - return false; - } - - boolean saveProjectProps = false; - - ProjectPropertiesWorkingCopy propsWC = null; - - // Update default.prop if --target was specified - if (target != null || writeProjectProp) { - // we already attempted to load the file earlier, if that failed, create it. - if (props == null) { - propsWC = ProjectProperties.create(projectFolder, PropertyType.PROJECT); - } else { - propsWC = props.makeWorkingCopy(PropertyType.PROJECT); - } - - // set or replace the target - if (target != null) { - propsWC.setProperty(ProjectProperties.PROPERTY_TARGET, target.hashString()); - } - saveProjectProps = true; - } - - if (libraryPath != null) { - // At this point, the default properties already exists, either because they were - // already there or because they were created with a new target - if (propsWC == null) { - assert props != null; - propsWC = props.makeWorkingCopy(); - } - - // check the reference is valid - File libProject = new File(libraryPath); - String resolvedPath; - if (libProject.isAbsolute() == false) { - libProject = new File(projectFolder, libraryPath); - try { - resolvedPath = libProject.getCanonicalPath(); - } catch (IOException e) { - mLog.error(e, "Unable to resolve path to library project: %1$s", libraryPath); - return false; - } - } else { - resolvedPath = libProject.getAbsolutePath(); - } - - println("Resolved location of library project to: %1$s", resolvedPath); - - // check the lib project exists - if (checkProjectFolder(resolvedPath, SdkConstants.FN_ANDROID_MANIFEST_XML) == null) { - mLog.error(null, "No Android Manifest at: %1$s", resolvedPath); - return false; - } - - // look for other references to figure out the index - int index = 1; - while (true) { - String propName = ProjectProperties.PROPERTY_LIB_REF + Integer.toString(index); - assert props != null; - if (props == null) { - // This should not happen yet SDK bug 20535 says it can, not sure how. - break; - } - String ref = props.getProperty(propName); - if (ref == null) { - break; - } else { - index++; - } - } - - String propName = ProjectProperties.PROPERTY_LIB_REF + Integer.toString(index); - propsWC.setProperty(propName, libraryPath); - saveProjectProps = true; - } - - // save the default props if needed. - if (saveProjectProps) { - try { - assert propsWC != null; - propsWC.save(); - if (writeProjectProp) { - println("Updated and renamed %1$s to %2$s", - PropertyType.LEGACY_DEFAULT.getFilename(), - PropertyType.PROJECT.getFilename()); - } else { - println("Updated %1$s", PropertyType.PROJECT.getFilename()); - } - } catch (Exception e) { - mLog.error(e, "Failed to write %1$s file in '%2$s'", - PropertyType.PROJECT.getFilename(), - folderPath); - return false; - } - - if (writeProjectProp) { - // need to delete the default prop file. - ProjectProperties.delete(projectFolder, PropertyType.LEGACY_DEFAULT); - } - } - - // Refresh/create "sdk" in local.properties - // because the file may already exists and contain other values (like apk config), - // we first try to load it. - props = ProjectProperties.load(projectFolder, PropertyType.LOCAL); - if (props == null) { - propsWC = ProjectProperties.create(projectFolder, PropertyType.LOCAL); - } else { - propsWC = props.makeWorkingCopy(); - } - - // set or replace the sdk location. - propsWC.setProperty(ProjectProperties.PROPERTY_SDK, mSdkFolder); - try { - propsWC.save(); - println("Updated %1$s", PropertyType.LOCAL.getFilename()); - } catch (Exception e) { - mLog.error(e, "Failed to write %1$s file in '%2$s'", - PropertyType.LOCAL.getFilename(), - folderPath); - return false; - } - - // legacy: check if build.properties must be renamed to ant.properties. - props = ProjectProperties.load(projectFolder, PropertyType.ANT); - if (props == null) { - props = ProjectProperties.load(projectFolder, PropertyType.LEGACY_BUILD); - if (props != null) { - try { - // get a working copy with the new property type - propsWC = props.makeWorkingCopy(PropertyType.ANT); - propsWC.save(); - - // delete the old file - ProjectProperties.delete(projectFolder, PropertyType.LEGACY_BUILD); - - println("Renamed %1$s to %2$s", - PropertyType.LEGACY_BUILD.getFilename(), - PropertyType.ANT.getFilename()); - } catch (Exception e) { - mLog.error(e, "Failed to write %1$s file in '%2$s'", - PropertyType.ANT.getFilename(), - folderPath); - return false; - } - } - } - - // Build.xml: create if not present or no <androidinit/> in it - File buildXml = new File(projectFolder, SdkConstants.FN_BUILD_XML); - boolean needsBuildXml = projectName != null || !buildXml.exists(); - - // if it seems there's no need for a new build.xml, look for inside the file - // to try to detect old ones that may need updating. - if (!needsBuildXml) { - // we are looking for version-tag: followed by either an integer or "custom". - if (checkFileContainsRegexp(buildXml, "version-tag:\\s*custom") != null) { //$NON-NLS-1$ - println("%1$s: Found version-tag: custom. File will not be updated.", - SdkConstants.FN_BUILD_XML); - } else { - Matcher m = checkFileContainsRegexp(buildXml, "version-tag:\\s*(\\d+)"); //$NON-NLS-1$ - if (m == null) { - println("----------\n" + - "%1$s: Failed to find version-tag string. File must be updated.\n" + - "In order to not erase potential customizations, the file will not be automatically regenerated.\n" + - "If no changes have been made to the file, delete it manually and run the command again.\n" + - "If you have made customizations to the build process, the file must be manually updated.\n" + - "It is recommended to:\n" + - "\t* Copy current file to a safe location.\n" + - "\t* Delete original file.\n" + - "\t* Run command again to generate a new file.\n" + - "\t* Port customizations to the new file, by looking at the new rules file\n" + - "\t located at <SDK>/tools/ant/build.xml\n" + - "\t* Update file to contain\n" + - "\t version-tag: custom\n" + - "\t to prevent file from being rewritten automatically by the SDK tools.\n" + - "----------\n", - SdkConstants.FN_BUILD_XML); - } else { - String versionStr = m.group(1); - if (versionStr != null) { - // can't fail due to regexp above. - int version = Integer.parseInt(versionStr); - if (version < MIN_BUILD_VERSION_TAG) { - println("%1$s: Found version-tag: %2$d. Expected version-tag: %3$d: file must be updated.", - SdkConstants.FN_BUILD_XML, version, MIN_BUILD_VERSION_TAG); - needsBuildXml = true; - } - } - } - } - } - - if (needsBuildXml) { - // create the map for place-holders of values to replace in the templates - final HashMap<String, String> keywords = new HashMap<String, String>(); - - // put the current version-tag value - keywords.put(PH_VERSION_TAG, Integer.toString(MIN_BUILD_VERSION_TAG)); - - // if there was no project name on the command line, figure one out. - if (projectName == null) { - // otherwise, take it from the existing build.xml if it exists already. - if (buildXml.exists()) { - try { - XPathFactory factory = XPathFactory.newInstance(); - XPath xpath = factory.newXPath(); - - projectName = xpath.evaluate(XPATH_PROJECT_NAME, - new InputSource(new FileInputStream(buildXml))); - } catch (XPathExpressionException e) { - // this is ok since we're going to recreate the file. - mLog.error(e, "Unable to find existing project name from %1$s", - SdkConstants.FN_BUILD_XML); - } catch (FileNotFoundException e) { - // can't happen since we check above. - } - } - - // if the project is still null, then we find another way. - if (projectName == null) { - extractPackageFromManifest(androidManifest, keywords); - if (keywords.containsKey(PH_ACTIVITY_ENTRY_NAME)) { - String activity = keywords.get(PH_ACTIVITY_ENTRY_NAME); - // keep only the last segment if applicable - int pos = activity.lastIndexOf('.'); - if (pos != -1) { - activity = activity.substring(pos + 1); - } - - // Use the activity as project name - projectName = activity; - - println("No project name specified, using Activity name '%1$s'.\n" + - "If you wish to change it, edit the first line of %2$s.", - activity, SdkConstants.FN_BUILD_XML); - } else { - // We need a project name. Just pick up the basename of the project - // directory. - File projectCanonicalFolder = projectFolder; - try { - projectCanonicalFolder = projectCanonicalFolder.getCanonicalFile(); - } catch (IOException e) { - // ignore, keep going - } - - // Use the folder name as project name - projectName = projectCanonicalFolder.getName(); - - println("No project name specified, using project folder name '%1$s'.\n" + - "If you wish to change it, edit the first line of %2$s.", - projectName, SdkConstants.FN_BUILD_XML); - } - } - } - - // put the project name in the map for replacement during the template installation. - keywords.put(PH_PROJECT_NAME, projectName); - - if (mLevel == OutputLevel.VERBOSE) { - println("Regenerating %1$s with project name %2$s", - SdkConstants.FN_BUILD_XML, - keywords.get(PH_PROJECT_NAME)); - } - - try { - installTemplate("build.template", buildXml, keywords); - } catch (ProjectCreateException e) { - mLog.error(e, null); - return false; - } - } - - if (hasProguard == false) { - try { - installTemplate(SdkConstants.FN_PROJECT_PROGUARD_FILE, - // Write ProGuard config files with the extension .pro which - // is what is used in the ProGuard documentation and samples - new File(projectFolder, SdkConstants.FN_PROJECT_PROGUARD_FILE), - null /*placeholderMap*/); - } catch (ProjectCreateException e) { - mLog.error(e, null); - return false; - } - } - - return true; - } - - /** - * Updates a test project with a new path to the main (tested) project. - * @param folderPath the path of the test project. - * @param pathToMainProject the path to the main project, relative to the test project. - */ - @SuppressWarnings("deprecation") - public void updateTestProject(final String folderPath, final String pathToMainProject, - final SdkManager sdkManager) { - // since this is an update, check the folder does point to a project - if (checkProjectFolder(folderPath, SdkConstants.FN_ANDROID_MANIFEST_XML) == null) { - return; - } - - // check the path to the main project is valid. - File mainProject = new File(pathToMainProject); - String resolvedPath; - if (mainProject.isAbsolute() == false) { - mainProject = new File(folderPath, pathToMainProject); - try { - resolvedPath = mainProject.getCanonicalPath(); - } catch (IOException e) { - mLog.error(e, "Unable to resolve path to main project: %1$s", pathToMainProject); - return; - } - } else { - resolvedPath = mainProject.getAbsolutePath(); - } - - println("Resolved location of main project to: %1$s", resolvedPath); - - // check the main project exists - if (checkProjectFolder(resolvedPath, SdkConstants.FN_ANDROID_MANIFEST_XML) == null) { - mLog.error(null, "No Android Manifest at: %1$s", resolvedPath); - return; - } - - // now get the target from the main project - ProjectProperties projectProp = ProjectProperties.load(resolvedPath, PropertyType.PROJECT); - if (projectProp == null) { - // legacy support for older file name. - projectProp = ProjectProperties.load(resolvedPath, PropertyType.LEGACY_DEFAULT); - if (projectProp == null) { - mLog.error(null, "No %1$s at: %2$s", PropertyType.PROJECT.getFilename(), - resolvedPath); - return; - } - } - - String targetHash = projectProp.getProperty(ProjectProperties.PROPERTY_TARGET); - if (targetHash == null) { - mLog.error(null, "%1$s in the main project has no target property.", - PropertyType.PROJECT.getFilename()); - return; - } - - IAndroidTarget target = sdkManager.getTargetFromHashString(targetHash); - if (target == null) { - mLog.error(null, "Main project target %1$s is not a valid target.", targetHash); - return; - } - - // update test-project does not support the --name parameter, therefore the project - // name should generally not be passed to updateProject(). - // However if build.xml does not exist then updateProject() will recreate it. In this - // case we will need the project name. - // To do this, we look for the parent project name and add "test" to it. - // If the main project does not have a project name (yet), then the default behavior - // will be used (look for activity and then folder name) - String projectName = null; - XPathFactory factory = XPathFactory.newInstance(); - XPath xpath = factory.newXPath(); - - File testBuildXml = new File(folderPath, SdkConstants.FN_BUILD_XML); - if (testBuildXml.isFile() == false) { - File mainBuildXml = new File(resolvedPath, SdkConstants.FN_BUILD_XML); - if (mainBuildXml.isFile()) { - try { - // get the name of the main project and add Test to it. - String mainProjectName = xpath.evaluate(XPATH_PROJECT_NAME, - new InputSource(new FileInputStream(mainBuildXml))); - projectName = mainProjectName + "Test"; - } catch (XPathExpressionException e) { - // it's ok, updateProject() will figure out a name automatically. - // We do log the error though as the build.xml file may be broken. - mLog.warning("Failed to parse %1$s.\n" + - "File may not be valid. Consider running 'android update project' on the main project.", - mainBuildXml.getPath()); - } catch (FileNotFoundException e) { - // should not happen since we check first. - } - } - } - - // now update the project as if it's a normal project - if (updateProject(folderPath, target, projectName, null /*libraryPath*/) == false) { - // error message has already been displayed. - return; - } - - // add the test project specific properties. - // At this point, we know build.prop has been renamed ant.prop - ProjectProperties antProps = ProjectProperties.load(folderPath, PropertyType.ANT); - ProjectPropertiesWorkingCopy antWorkingCopy; - if (antProps == null) { - antWorkingCopy = ProjectProperties.create(folderPath, PropertyType.ANT); - } else { - antWorkingCopy = antProps.makeWorkingCopy(); - } - - // set or replace the path to the main project - antWorkingCopy.setProperty(ProjectProperties.PROPERTY_TESTED_PROJECT, pathToMainProject); - try { - antWorkingCopy.save(); - println("Updated %1$s", PropertyType.ANT.getFilename()); - } catch (Exception e) { - mLog.error(e, "Failed to write %1$s file in '%2$s'", - PropertyType.ANT.getFilename(), - folderPath); - return; - } - } - - /** - * Checks whether the give <var>folderPath</var> is a valid project folder, and returns - * a {@link FileWrapper} to the required file. - * <p/>This checks that the folder exists and contains an AndroidManifest.xml file in it. - * <p/>Any error are output using {@link #mLog}. - * @param folderPath the folder to check - * @param requiredFilename the file name of the file that's required. - * @return a {@link FileWrapper} to the AndroidManifest.xml file, or null otherwise. - */ - private FileWrapper checkProjectFolder(String folderPath, String requiredFilename) { - // project folder must exist and be a directory, since this is an update - FolderWrapper projectFolder = new FolderWrapper(folderPath); - if (!projectFolder.isDirectory()) { - mLog.error(null, "Project folder '%1$s' is not a valid directory.", - projectFolder); - return null; - } - - // Check AndroidManifest.xml is present - FileWrapper requireFile = new FileWrapper(projectFolder, requiredFilename); - if (!requireFile.isFile()) { - mLog.error(null, - "%1$s is not a valid project (%2$s not found).", - folderPath, requiredFilename); - return null; - } - - return requireFile; - } - - /** - * Looks for a given regex in a file and returns the matcher if any line of the input file - * contains the requested regexp. - * - * @param file the file to search. - * @param regexp the regexp to search for. - * - * @return a Matcher or null if the regexp is not found. - */ - private Matcher checkFileContainsRegexp(File file, String regexp) { - Pattern p = Pattern.compile(regexp); - - BufferedReader in = null; - try { - in = new BufferedReader(new FileReader(file)); - String line; - - while ((line = in.readLine()) != null) { - Matcher m = p.matcher(line); - if (m.find()) { - return m; - } - } - - in.close(); - } catch (Exception e) { - // ignore - } finally { - if (in != null) { - try { - in.close(); - } catch (IOException e) { - // ignore - } - } - } - - return null; - } - - /** - * Extracts a "full" package & activity name from an AndroidManifest.xml. - * <p/> - * The keywords dictionary is always filed the package name under the key {@link #PH_PACKAGE}. - * If an activity name can be found, it is filed under the key {@link #PH_ACTIVITY_ENTRY_NAME}. - * When no activity is found, this key is not created. - * - * @param manifestFile The AndroidManifest.xml file - * @param outKeywords Place where to put the out parameters: package and activity names. - * @return True if the package/activity was parsed and updated in the keyword dictionary. - */ - private boolean extractPackageFromManifest(File manifestFile, - Map<String, String> outKeywords) { - try { - XPath xpath = AndroidXPathFactory.newXPath(); - - InputSource source = new InputSource(new FileReader(manifestFile)); - String packageName = xpath.evaluate("/manifest/@package", source); - - source = new InputSource(new FileReader(manifestFile)); - - // Select the "android:name" attribute of all <activity> nodes but only if they - // contain a sub-node <intent-filter><action> with an "android:name" attribute which - // is 'android.intent.action.MAIN' and an <intent-filter><category> with an - // "android:name" attribute which is 'android.intent.category.LAUNCHER' - String expression = String.format("/manifest/application/activity" + - "[intent-filter/action/@%1$s:name='android.intent.action.MAIN' and " + - "intent-filter/category/@%1$s:name='android.intent.category.LAUNCHER']" + - "/@%1$s:name", AndroidXPathFactory.DEFAULT_NS_PREFIX); - - NodeList activityNames = (NodeList) xpath.evaluate(expression, source, - XPathConstants.NODESET); - - // If we get here, both XPath expressions were valid so we're most likely dealing - // with an actual AndroidManifest.xml file. The nodes may not have the requested - // attributes though, if which case we should warn. - - if (packageName == null || packageName.length() == 0) { - mLog.error(null, - "Missing <manifest package=\"...\"> in '%1$s'", - manifestFile.getName()); - return false; - } - - // Get the first activity that matched earlier. If there is no activity, - // activityName is set to an empty string and the generated "combined" name - // will be in the form "package." (with a dot at the end). - String activityName = ""; - if (activityNames.getLength() > 0) { - activityName = activityNames.item(0).getNodeValue(); - } - - if (mLevel == OutputLevel.VERBOSE && activityNames.getLength() > 1) { - println("WARNING: There is more than one activity defined in '%1$s'.\n" + - "Only the first one will be used. If this is not appropriate, you need\n" + - "to specify one of these values manually instead:", - manifestFile.getName()); - - for (int i = 0; i < activityNames.getLength(); i++) { - String name = activityNames.item(i).getNodeValue(); - name = combinePackageActivityNames(packageName, name); - println("- %1$s", name); - } - } - - if (activityName.length() == 0) { - mLog.warning("Missing <activity %1$s:name=\"...\"> in '%2$s'.\n" + - "No activity will be generated.", - AndroidXPathFactory.DEFAULT_NS_PREFIX, manifestFile.getName()); - } else { - outKeywords.put(PH_ACTIVITY_ENTRY_NAME, activityName); - } - - outKeywords.put(PH_PACKAGE, packageName); - return true; - - } catch (IOException e) { - mLog.error(e, "Failed to read %1$s", manifestFile.getName()); - } catch (XPathExpressionException e) { - Throwable t = e.getCause(); - mLog.error(t == null ? e : t, - "Failed to parse %1$s", - manifestFile.getName()); - } - - return false; - } - - private String combinePackageActivityNames(String packageName, String activityName) { - // Activity Name can have 3 forms: - // - ".Name" means this is a class name in the given package name. - // The full FQCN is thus packageName + ".Name" - // - "Name" is an older variant of the former. Full FQCN is packageName + "." + "Name" - // - "com.blah.Name" is a full FQCN. Ignore packageName and use activityName as-is. - // To be valid, the package name should have at least two components. This is checked - // later during the creation of the build.xml file, so we just need to detect there's - // a dot but not at pos==0. - - int pos = activityName.indexOf('.'); - if (pos == 0) { - return packageName + activityName; - } else if (pos > 0) { - return activityName; - } else { - return packageName + "." + activityName; - } - } - - /** - * Installs a new file that is based on a template file provided by a given target. - * Each match of each key from the place-holder map in the template will be replaced with its - * corresponding value in the created file. - * - * @param templateName the name of to the template file - * @param destFile the path to the destination file, relative to the project - * @param placeholderMap a map of (place-holder, value) to create the file from the template. - * @param target the Target of the project that will be providing the template. - * @throws ProjectCreateException - */ - private void installTargetTemplate(String templateName, File destFile, - Map<String, String> placeholderMap, IAndroidTarget target) - throws ProjectCreateException { - // query the target for its template directory - String templateFolder = target.getPath(IAndroidTarget.TEMPLATES); - final String sourcePath = templateFolder + File.separator + templateName; - - installFullPathTemplate(sourcePath, destFile, placeholderMap); - } - - /** - * Installs a new file that is based on a template file provided by the tools folder. - * Each match of each key from the place-holder map in the template will be replaced with its - * corresponding value in the created file. - * - * @param templateName the name of to the template file - * @param destFile the path to the destination file, relative to the project - * @param placeholderMap a map of (place-holder, value) to create the file from the template. - * @throws ProjectCreateException - */ - public void installTemplate(String templateName, File destFile, - Map<String, String> placeholderMap) - throws ProjectCreateException { - // query the target for its template directory - String templateFolder = mSdkFolder + File.separator + SdkConstants.OS_SDK_TOOLS_LIB_FOLDER; - final String sourcePath = templateFolder + File.separator + templateName; - - installFullPathTemplate(sourcePath, destFile, placeholderMap); - } - - /** - * Installs a new file that is based on a template. - * Each match of each key from the place-holder map in the template will be replaced with its - * corresponding value in the created file. - * - * @param sourcePath the full path to the source template file - * @param destFile the destination file - * @param placeholderMap a map of (place-holder, value) to create the file from the template. - * @throws ProjectCreateException - */ - private void installFullPathTemplate(String sourcePath, File destFile, - Map<String, String> placeholderMap) throws ProjectCreateException { - - boolean existed = destFile.exists(); - - try { - BufferedWriter out = new BufferedWriter(new FileWriter(destFile)); - BufferedReader in = new BufferedReader(new FileReader(sourcePath)); - String line; - - while ((line = in.readLine()) != null) { - if (placeholderMap != null) { - for (Map.Entry<String, String> entry : placeholderMap.entrySet()) { - line = line.replace(entry.getKey(), entry.getValue()); - } - } - - out.write(line); - out.newLine(); - } - - out.close(); - in.close(); - } catch (Exception e) { - throw new ProjectCreateException(e, "Could not access %1$s: %2$s", - destFile, e.getMessage()); - } - - println("%1$s file %2$s", - existed ? "Updated" : "Added", - destFile); - } - - /** - * Installs the project icons. - * @param resourceFolder the resource folder - * @param target the target of the project. - * @return true if any icon was installed. - */ - private boolean installIcons(File resourceFolder, IAndroidTarget target) - throws ProjectCreateException { - // query the target for its template directory - String templateFolder = target.getPath(IAndroidTarget.TEMPLATES); - - boolean installedIcon = false; - - installedIcon |= installIcon(templateFolder, "ic_launcher_xhdpi.png", resourceFolder, - "drawable-xhdpi"); - installedIcon |= installIcon(templateFolder, "ic_launcher_hdpi.png", resourceFolder, - "drawable-hdpi"); - installedIcon |= installIcon(templateFolder, "ic_launcher_mdpi.png", resourceFolder, - "drawable-mdpi"); - installedIcon |= installIcon(templateFolder, "ic_launcher_ldpi.png", resourceFolder, - "drawable-ldpi"); - - return installedIcon; - } - - /** - * Installs an Icon in the project. - * @return true if the icon was installed. - */ - private boolean installIcon(String templateFolder, String iconName, File resourceFolder, - String folderName) throws ProjectCreateException { - File icon = new File(templateFolder, iconName); - if (icon.exists()) { - File drawable = createDirs(resourceFolder, folderName); - installBinaryFile(icon, new File(drawable, "ic_launcher.png")); - return true; - } - - return false; - } - - /** - * Installs a binary file - * @param source the source file to copy - * @param destination the destination file to write - * @throws ProjectCreateException - */ - private void installBinaryFile(File source, File destination) throws ProjectCreateException { - byte[] buffer = new byte[8192]; - - FileInputStream fis = null; - FileOutputStream fos = null; - try { - fis = new FileInputStream(source); - fos = new FileOutputStream(destination); - - int read; - while ((read = fis.read(buffer)) != -1) { - fos.write(buffer, 0, read); - } - - } catch (FileNotFoundException e) { - // shouldn't happen since we check before. - } catch (IOException e) { - throw new ProjectCreateException(e, "Failed to read binary file: %1$s", - source.getAbsolutePath()); - } finally { - if (fis != null) { - try { - fis.close(); - } catch (IOException e) { - // ignore - } - } - if (fos != null) { - try { - fos.close(); - } catch (IOException e) { - // ignore - } - } - } - - } - - /** - * Prints a message unless silence is enabled. - * <p/> - * This is just a convenience wrapper around {@link ILogger#info(String, Object...)} from - * {@link #mLog} after testing if output level is {@link OutputLevel#VERBOSE}. - * - * @param format Format for String.format - * @param args Arguments for String.format - */ - private void println(String format, Object... args) { - if (mLevel != OutputLevel.SILENT) { - if (!format.endsWith("\n")) { - format += "\n"; - } - mLog.info(format, args); - } - } - - /** - * Creates a new folder, along with any parent folders that do not exists. - * - * @param parent the parent folder - * @param name the name of the directory to create. - * @throws ProjectCreateException - */ - private File createDirs(File parent, String name) throws ProjectCreateException { - final File newFolder = new File(parent, name); - boolean existedBefore = true; - - if (!newFolder.exists()) { - if (!newFolder.mkdirs()) { - throw new ProjectCreateException("Could not create directory: %1$s", newFolder); - } - existedBefore = false; - } - - if (newFolder.isDirectory()) { - if (!newFolder.canWrite()) { - throw new ProjectCreateException("Path is not writable: %1$s", newFolder); - } - } else { - throw new ProjectCreateException("Path is not a directory: %1$s", newFolder); - } - - if (!existedBefore) { - try { - println("Created directory %1$s", newFolder.getCanonicalPath()); - } catch (IOException e) { - throw new ProjectCreateException( - "Could not determine canonical path of created directory", e); - } - } - - return newFolder; - } - - /** - * Strips the string of beginning and trailing characters (multiple - * characters will be stripped, example stripString("..test...", '.') - * results in "test"; - * - * @param s the string to strip - * @param strip the character to strip from beginning and end - * @return the stripped string or the empty string if everything is stripped. - */ - private static String stripString(String s, char strip) { - final int sLen = s.length(); - int newStart = 0, newEnd = sLen - 1; - - while (newStart < sLen && s.charAt(newStart) == strip) { - newStart++; - } - while (newEnd >= 0 && s.charAt(newEnd) == strip) { - newEnd--; - } - - /* - * newEnd contains a char we want, and substring takes end as being - * exclusive - */ - newEnd++; - - if (newStart >= sLen || newEnd < 0) { - return ""; - } - - return s.substring(newStart, newEnd); - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/project/ProjectProperties.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/project/ProjectProperties.java deleted file mode 100644 index 48acb56..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/project/ProjectProperties.java +++ /dev/null @@ -1,535 +0,0 @@ -/* - * Copyright (C) 2008 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.project; - -import com.android.SdkConstants; -import com.android.annotations.NonNull; -import com.android.annotations.Nullable; -import com.android.io.FolderWrapper; -import com.android.io.IAbstractFile; -import com.android.io.IAbstractFolder; -import com.android.io.StreamException; -import com.android.utils.ILogger; -import com.google.common.io.Closeables; - -import java.io.BufferedReader; -import java.io.FileNotFoundException; -import java.io.IOException; -import java.io.InputStreamReader; -import java.util.Arrays; -import java.util.Collections; -import java.util.HashMap; -import java.util.HashSet; -import java.util.Map; -import java.util.Map.Entry; -import java.util.Properties; -import java.util.Set; -import java.util.regex.Matcher; -import java.util.regex.Pattern; - -/** - * Class representing project properties for both ADT and Ant-based build. - * <p/>The class is associated to a {@link PropertyType} that indicate which of the project - * property file is represented. - * <p/>To load an existing file, use {@link #load(IAbstractFolder, PropertyType)}. - * <p/>The class is meant to be always in sync (or at least not newer) than the file it represents. - * Once created, it can only be updated through {@link #reload()} - * - * <p/>The make modification or make new file, use a {@link ProjectPropertiesWorkingCopy} instance, - * either through {@link #create(IAbstractFolder, PropertyType)} or through - * {@link #makeWorkingCopy()}. - * - */ -public class ProjectProperties implements IPropertySource { - protected final static Pattern PATTERN_PROP = Pattern.compile( - "^([a-zA-Z0-9._-]+)\\s*=\\s*(.*)\\s*$"); - - /** The property name for the project target */ - public final static String PROPERTY_TARGET = "target"; - /** The property name for the renderscript build target */ - public final static String PROPERTY_RS_TARGET = "renderscript.target"; - - public final static String PROPERTY_LIBRARY = "android.library"; - public final static String PROPERTY_LIB_REF = "android.library.reference."; - private final static String PROPERTY_LIB_REF_REGEX = "android.library.reference.\\d+"; - - public final static String PROPERTY_PROGUARD_CONFIG = "proguard.config"; - public final static String PROPERTY_RULES_PATH = "layoutrules.jars"; - - public final static String PROPERTY_SDK = "sdk.dir"; - // LEGACY - Kept so that we can actually remove it from local.properties. - private final static String PROPERTY_SDK_LEGACY = "sdk-location"; - - public final static String PROPERTY_SPLIT_BY_DENSITY = "split.density"; - public final static String PROPERTY_SPLIT_BY_ABI = "split.abi"; - public final static String PROPERTY_SPLIT_BY_LOCALE = "split.locale"; - - public final static String PROPERTY_TESTED_PROJECT = "tested.project.dir"; - - public final static String PROPERTY_BUILD_SOURCE_DIR = "source.dir"; - public final static String PROPERTY_BUILD_OUT_DIR = "out.dir"; - - public final static String PROPERTY_PACKAGE = "package"; - public final static String PROPERTY_VERSIONCODE = "versionCode"; - public final static String PROPERTY_PROJECTS = "projects"; - public final static String PROPERTY_KEY_STORE = "key.store"; - public final static String PROPERTY_KEY_ALIAS = "key.alias"; - - public static enum PropertyType { - ANT(SdkConstants.FN_ANT_PROPERTIES, BUILD_HEADER, new String[] { - PROPERTY_BUILD_SOURCE_DIR, PROPERTY_BUILD_OUT_DIR - }, null), - PROJECT(SdkConstants.FN_PROJECT_PROPERTIES, DEFAULT_HEADER, new String[] { - PROPERTY_TARGET, PROPERTY_LIBRARY, PROPERTY_LIB_REF_REGEX, - PROPERTY_KEY_STORE, PROPERTY_KEY_ALIAS, PROPERTY_PROGUARD_CONFIG, - PROPERTY_RULES_PATH - }, null), - LOCAL(SdkConstants.FN_LOCAL_PROPERTIES, LOCAL_HEADER, new String[] { - PROPERTY_SDK - }, - new String[] { PROPERTY_SDK_LEGACY }), - @Deprecated - LEGACY_DEFAULT("default.properties", null, null, null), - @Deprecated - LEGACY_BUILD("build.properties", null, null, null); - - - private final String mFilename; - private final String mHeader; - private final Set<String> mKnownProps; - private final Set<String> mRemovedProps; - - /** - * Returns the PropertyTypes ordered the same way Ant order them. - */ - public static PropertyType[] getOrderedTypes() { - return new PropertyType[] { - PropertyType.LOCAL, PropertyType.ANT, PropertyType.PROJECT - }; - } - - PropertyType(String filename, String header, String[] validProps, String[] removedProps) { - mFilename = filename; - mHeader = header; - HashSet<String> s = new HashSet<String>(); - if (validProps != null) { - s.addAll(Arrays.asList(validProps)); - } - mKnownProps = Collections.unmodifiableSet(s); - - s = new HashSet<String>(); - if (removedProps != null) { - s.addAll(Arrays.asList(removedProps)); - } - mRemovedProps = Collections.unmodifiableSet(s); - - } - - public String getFilename() { - return mFilename; - } - - public String getHeader() { - return mHeader; - } - - /** - * Returns whether a given property is known for the property type. - */ - public boolean isKnownProperty(String name) { - for (String propRegex : mKnownProps) { - if (propRegex.equals(name) || Pattern.matches(propRegex, name)) { - return true; - } - } - - return false; - } - - /** - * Returns whether a given property should be removed for the property type. - */ - public boolean isRemovedProperty(String name) { - for (String propRegex : mRemovedProps) { - if (propRegex.equals(name) || Pattern.matches(propRegex, name)) { - return true; - } - } - - return false; - } - } - - private final static String LOCAL_HEADER = -// 1-------10--------20--------30--------40--------50--------60--------70--------80 - "# This file is automatically generated by Android Tools.\n" + - "# Do not modify this file -- YOUR CHANGES WILL BE ERASED!\n" + - "#\n" + - "# This file must *NOT* be checked into Version Control Systems,\n" + - "# as it contains information specific to your local configuration.\n" + - "\n"; - - private final static String DEFAULT_HEADER = -// 1-------10--------20--------30--------40--------50--------60--------70--------80 - "# This file is automatically generated by Android Tools.\n" + - "# Do not modify this file -- YOUR CHANGES WILL BE ERASED!\n" + - "#\n" + - "# This file must be checked in Version Control Systems.\n" + - "#\n" + - "# To customize properties used by the Ant build system edit\n" + - "# \"ant.properties\", and override values to adapt the script to your\n" + - "# project structure.\n" + - "#\n" + - "# To enable ProGuard to shrink and obfuscate your code, uncomment this " - + "(available properties: sdk.dir, user.home):\n" + - // Note: always use / separators in the properties paths. Both Ant and - // our ExportHelper will convert them properly according to the platform. - "#" + PROPERTY_PROGUARD_CONFIG + "=${" + PROPERTY_SDK +"}/" - + SdkConstants.FD_TOOLS + '/' + SdkConstants.FD_PROGUARD + '/' - + SdkConstants.FN_ANDROID_PROGUARD_FILE + ':' - + SdkConstants.FN_PROJECT_PROGUARD_FILE +'\n' + - "\n"; - - private final static String BUILD_HEADER = -// 1-------10--------20--------30--------40--------50--------60--------70--------80 - "# This file is used to override default values used by the Ant build system.\n" + - "#\n" + - "# This file must be checked into Version Control Systems, as it is\n" + - "# integral to the build system of your project.\n" + - "\n" + - "# This file is only used by the Ant script.\n" + - "\n" + - "# You can use this to override default values such as\n" + - "# 'source.dir' for the location of your java source folder and\n" + - "# 'out.dir' for the location of your output folder.\n" + - "\n" + - "# You can also use it define how the release builds are signed by declaring\n" + - "# the following properties:\n" + - "# 'key.store' for the location of your keystore and\n" + - "# 'key.alias' for the name of the key to use.\n" + - "# The password will be asked during the build when you use the 'release' target.\n" + - "\n"; - - protected final IAbstractFolder mProjectFolder; - protected final Map<String, String> mProperties; - protected final PropertyType mType; - - /** - * Loads a project properties file and return a {@link ProjectProperties} object - * containing the properties. - * - * @param projectFolderOsPath the project folder. - * @param type One the possible {@link PropertyType}s. - */ - public static ProjectProperties load(String projectFolderOsPath, PropertyType type) { - IAbstractFolder wrapper = new FolderWrapper(projectFolderOsPath); - return load(wrapper, type); - } - - /** - * Loads a project properties file and return a {@link ProjectProperties} object - * containing the properties. - * - * @param projectFolder the project folder. - * @param type One the possible {@link PropertyType}s. - */ - public static ProjectProperties load(IAbstractFolder projectFolder, PropertyType type) { - if (projectFolder.exists()) { - IAbstractFile propFile = projectFolder.getFile(type.mFilename); - if (propFile.exists()) { - Map<String, String> map = parsePropertyFile(propFile, null /* log */); - if (map != null) { - return new ProjectProperties(projectFolder, map, type); - } - } - } - return null; - } - - /** - * Deletes a project properties file. - * - * @param projectFolder the project folder. - * @param type One the possible {@link PropertyType}s. - * @return true if success. - */ - public static boolean delete(IAbstractFolder projectFolder, PropertyType type) { - if (projectFolder.exists()) { - IAbstractFile propFile = projectFolder.getFile(type.mFilename); - if (propFile.exists()) { - return propFile.delete(); - } - } - - return false; - } - - /** - * Deletes a project properties file. - * - * @param projectFolderOsPath the project folder. - * @param type One the possible {@link PropertyType}s. - * @return true if success. - */ - public static boolean delete(String projectFolderOsPath, PropertyType type) { - IAbstractFolder wrapper = new FolderWrapper(projectFolderOsPath); - return delete(wrapper, type); - } - - - /** - * Creates a new project properties object, with no properties. - * <p/>The file is not created until {@link ProjectPropertiesWorkingCopy#save()} is called. - * @param projectFolderOsPath the project folder. - * @param type the type of property file to create - * - * @see #createEmpty(String, PropertyType) - */ - public static ProjectPropertiesWorkingCopy create(@NonNull String projectFolderOsPath, - @NonNull PropertyType type) { - // create and return a ProjectProperties with an empty map. - IAbstractFolder folder = new FolderWrapper(projectFolderOsPath); - return create(folder, type); - } - - /** - * Creates a new project properties object, with no properties. - * <p/>The file is not created until {@link ProjectPropertiesWorkingCopy#save()} is called. - * @param projectFolder the project folder. - * @param type the type of property file to create - * - * @see #createEmpty(IAbstractFolder, PropertyType) - */ - public static ProjectPropertiesWorkingCopy create(@NonNull IAbstractFolder projectFolder, - @NonNull PropertyType type) { - // create and return a ProjectProperties with an empty map. - return new ProjectPropertiesWorkingCopy(projectFolder, new HashMap<String, String>(), type); - } - - /** - * Creates a new project properties object, with no properties. - * <p/>Nothing can be added to it, unless a {@link ProjectPropertiesWorkingCopy} is created - * first with {@link #makeWorkingCopy()}. - * @param projectFolderOsPath the project folder. - * @param type the type of property file to create - * - * @see #create(String, PropertyType) - */ - public static ProjectProperties createEmpty(@NonNull String projectFolderOsPath, - @NonNull PropertyType type) { - // create and return a ProjectProperties with an empty map. - IAbstractFolder folder = new FolderWrapper(projectFolderOsPath); - return createEmpty(folder, type); - } - - /** - * Creates a new project properties object, with no properties. - * <p/>Nothing can be added to it, unless a {@link ProjectPropertiesWorkingCopy} is created - * first with {@link #makeWorkingCopy()}. - * @param projectFolder the project folder. - * @param type the type of property file to create - * - * @see #create(IAbstractFolder, PropertyType) - */ - public static ProjectProperties createEmpty(@NonNull IAbstractFolder projectFolder, - @NonNull PropertyType type) { - // create and return a ProjectProperties with an empty map. - return new ProjectProperties(projectFolder, new HashMap<String, String>(), type); - } - - /** - * Returns the location of this property file. - */ - public IAbstractFile getFile() { - return mProjectFolder.getFile(mType.mFilename); - } - - /** - * Creates and returns a copy of the current properties as a - * {@link ProjectPropertiesWorkingCopy} that can be modified and saved. - * @return a new instance of {@link ProjectPropertiesWorkingCopy} - */ - public ProjectPropertiesWorkingCopy makeWorkingCopy() { - return makeWorkingCopy(mType); - } - - /** - * Creates and returns a copy of the current properties as a - * {@link ProjectPropertiesWorkingCopy} that can be modified and saved. This also allows - * converting to a new type, by specifying a different {@link PropertyType}. - * - * @param type the {@link PropertyType} of the prop file to save. - * - * @return a new instance of {@link ProjectPropertiesWorkingCopy} - */ - public ProjectPropertiesWorkingCopy makeWorkingCopy(PropertyType type) { - // copy the current properties in a new map - Map<String, String> propList = new HashMap<String, String>(mProperties); - - return new ProjectPropertiesWorkingCopy(mProjectFolder, propList, type); - } - - /** - * Returns the type of the property file. - * - * @see PropertyType - */ - public PropertyType getType() { - return mType; - } - - /** - * Returns the value of a property. - * @param name the name of the property. - * @return the property value or null if the property is not set. - */ - @Override - public synchronized String getProperty(String name) { - return mProperties.get(name); - } - - /** - * Returns a set of the property keys. Unlike {@link Map#keySet()} this is not a view of the - * map keys. Modifying the returned {@link Set} will not impact the underlying {@link Map}. - */ - public synchronized Set<String> keySet() { - return new HashSet<String>(mProperties.keySet()); - } - - /** - * Reloads the properties from the underlying file. - */ - public synchronized void reload() { - if (mProjectFolder.exists()) { - IAbstractFile propFile = mProjectFolder.getFile(mType.mFilename); - if (propFile.exists()) { - Map<String, String> map = parsePropertyFile(propFile, null /* log */); - if (map != null) { - mProperties.clear(); - mProperties.putAll(map); - } - } - } - } - - /** - * Parses a property file (using UTF-8 encoding) and returns a map of the content. - * <p/> - * If the file is not present, null is returned with no error messages sent to the log. - * <p/> - * IMPORTANT: This method is now unfortunately used in multiple places to parse random - * property files. This is NOT a safe practice since there is no corresponding method - * to write property files unless you use {@link ProjectPropertiesWorkingCopy#save()}. - * Code that writes INI or properties without at least using {@link #escape(String)} will - * certainly not load back correct data. <br/> - * Unless there's a strong legacy need to support existing files, new callers should - * probably just use Java's {@link Properties} which has well defined semantics. - * It's also a mistake to write/read property files using this code and expect it to - * work with Java's {@link Properties} or external tools (e.g. ant) since there can be - * differences in escaping and in character encoding. - * - * @param propFile the property file to parse - * @param log the ILogger object receiving warning/error from the parsing. - * @return the map of (key,value) pairs, or null if the parsing failed. - */ - public static Map<String, String> parsePropertyFile( - @NonNull IAbstractFile propFile, - @Nullable ILogger log) { - BufferedReader reader = null; - try { - reader = new BufferedReader(new InputStreamReader(propFile.getContents(), - SdkConstants.INI_CHARSET)); - - String line = null; - Map<String, String> map = new HashMap<String, String>(); - while ((line = reader.readLine()) != null) { - line = line.trim(); - if (line.length() > 0 && line.charAt(0) != '#') { - - Matcher m = PATTERN_PROP.matcher(line); - if (m.matches()) { - map.put(m.group(1), unescape(m.group(2))); - } else { - if (log != null) { - log.warning("Error parsing '%1$s': \"%2$s\" is not a valid syntax", - propFile.getOsLocation(), - line); - } - return null; - } - } - } - - return map; - } catch (FileNotFoundException e) { - // this should not happen since we usually test the file existence before - // calling the method. - // Return null below. - } catch (IOException e) { - if (log != null) { - log.warning("Error parsing '%1$s': %2$s.", - propFile.getOsLocation(), - e.getMessage()); - } - } catch (StreamException e) { - if (log != null) { - log.warning("Error parsing '%1$s': %2$s.", - propFile.getOsLocation(), - e.getMessage()); - } - } finally { - Closeables.closeQuietly(reader); - } - - return null; - } - - /** - * Private constructor. - * <p/> - * Use {@link #load(String, PropertyType)} or {@link #create(String, PropertyType)} - * to instantiate. - */ - protected ProjectProperties( - @NonNull IAbstractFolder projectFolder, - @NonNull Map<String, String> map, - @NonNull PropertyType type) { - mProjectFolder = projectFolder; - mProperties = map; - mType = type; - } - - private static String unescape(String value) { - return value.replaceAll("\\\\\\\\", "\\\\"); - } - - protected static String escape(String value) { - return value.replaceAll("\\\\", "\\\\\\\\"); - } - - @Override - public void debugPrint() { - System.out.println("DEBUG PROJECTPROPERTIES: " + mProjectFolder); - System.out.println("type: " + mType); - for (Entry<String, String> entry : mProperties.entrySet()) { - System.out.println(entry.getKey() + " -> " + entry.getValue()); - } - System.out.println("<<< DEBUG PROJECTPROPERTIES"); - - } - -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/project/ProjectPropertiesWorkingCopy.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/project/ProjectPropertiesWorkingCopy.java deleted file mode 100644 index 0bb9bd6..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/project/ProjectPropertiesWorkingCopy.java +++ /dev/null @@ -1,256 +0,0 @@ -/* - * Copyright (C) 2010 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.project; - -import com.android.SdkConstants; -import com.android.annotations.NonNull; -import com.android.io.IAbstractFile; -import com.android.io.IAbstractFolder; -import com.android.io.StreamException; -import com.google.common.io.Closeables; - -import java.io.BufferedReader; -import java.io.ByteArrayOutputStream; -import java.io.IOException; -import java.io.InputStreamReader; -import java.io.OutputStream; -import java.io.OutputStreamWriter; -import java.util.HashMap; -import java.util.HashSet; -import java.util.Map; -import java.util.Map.Entry; -import java.util.Set; -import java.util.regex.Matcher; - -/** - * A modifyable and saveable copy of a {@link ProjectProperties}. - * <p/>This copy gives access to modification method such as {@link #setProperty(String, String)} - * and {@link #removeProperty(String)}. - * - * To get access to an instance, use {@link ProjectProperties#makeWorkingCopy()} or - * {@link ProjectProperties#create(IAbstractFolder, PropertyType)}. - */ -public class ProjectPropertiesWorkingCopy extends ProjectProperties { - - private final static Map<String, String> COMMENT_MAP = new HashMap<String, String>(); - static { -// 1-------10--------20--------30--------40--------50--------60--------70--------80 - COMMENT_MAP.put(PROPERTY_TARGET, - "# Project target.\n"); - COMMENT_MAP.put(PROPERTY_SPLIT_BY_DENSITY, - "# Indicates whether an apk should be generated for each density.\n"); - COMMENT_MAP.put(PROPERTY_SDK, - "# location of the SDK. This is only used by Ant\n" + - "# For customization when using a Version Control System, please read the\n" + - "# header note.\n"); - COMMENT_MAP.put(PROPERTY_PACKAGE, - "# Package of the application being exported\n"); - COMMENT_MAP.put(PROPERTY_VERSIONCODE, - "# Major version code\n"); - COMMENT_MAP.put(PROPERTY_PROJECTS, - "# List of the Android projects being used for the export.\n" + - "# The list is made of paths that are relative to this project,\n" + - "# using forward-slash (/) as separator, and are separated by colons (:).\n"); - } - - - /** - * Sets a new properties. If a property with the same name already exists, it is replaced. - * @param name the name of the property. - * @param value the value of the property. - */ - public synchronized void setProperty(String name, String value) { - mProperties.put(name, value); - } - - /** - * Removes a property and returns its previous value (or null if the property did not exist). - * @param name the name of the property to remove. - */ - public synchronized String removeProperty(String name) { - return mProperties.remove(name); - } - - /** - * Merges all properties from the given file into the current properties. - * <p/> - * This emulates the Ant behavior: existing properties are <em>not</em> overridden. - * Only new undefined properties become defined. - * <p/> - * Typical usage: - * <ul> - * <li>Create a ProjectProperties with {@code PropertyType#ANT} - * <li>Merge in values using {@code PropertyType#PROJECT} - * <li>The result is that this contains all the properties from default plus those - * overridden by the build.properties file. - * </ul> - * - * @param type One the possible {@link ProjectProperties.PropertyType}s. - * @return this object, for chaining. - */ - public synchronized ProjectPropertiesWorkingCopy merge(PropertyType type) { - if (mProjectFolder.exists() && mType != type) { - IAbstractFile propFile = mProjectFolder.getFile(type.getFilename()); - if (propFile.exists()) { - Map<String, String> map = parsePropertyFile(propFile, null /* log */); - if (map != null) { - for (Entry<String, String> entry : map.entrySet()) { - String key = entry.getKey(); - String value = entry.getValue(); - if (!mProperties.containsKey(key) && value != null) { - mProperties.put(key, value); - } - } - } - } - } - return this; - } - - - /** - * Saves the property file, using UTF-8 encoding. - * @throws IOException - * @throws StreamException - */ - public synchronized void save() throws IOException, StreamException { - IAbstractFile toSave = mProjectFolder.getFile(mType.getFilename()); - - // write the whole file in a byte array before dumping it in the file. This - // This is so that if the file already existing - ByteArrayOutputStream baos = new ByteArrayOutputStream(); - OutputStreamWriter writer = new OutputStreamWriter(baos, SdkConstants.INI_CHARSET); - - if (toSave.exists()) { - BufferedReader reader = new BufferedReader(new InputStreamReader(toSave.getContents(), - SdkConstants.INI_CHARSET)); - - // since we're reading the existing file and replacing values with new ones, or skipping - // removed values, we need to record what properties have been visited, so that - // we can figure later what new properties need to be added at the end of the file. - Set<String> visitedProps = new HashSet<String>(); - - String line = null; - while ((line = reader.readLine()) != null) { - // check if this is a line containing a property. - if (line.length() > 0 && line.charAt(0) != '#') { - - Matcher m = PATTERN_PROP.matcher(line); - if (m.matches()) { - String key = m.group(1); - String value = m.group(2); - - // record the prop - visitedProps.add(key); - - // check if this property must be removed. - if (mType.isRemovedProperty(key)) { - value = null; - } else if (mProperties.containsKey(key)) { // if the property still exists. - // put the new value. - value = mProperties.get(key); - } else { - // property doesn't exist. Check if it's a known property. - // if it's a known one, we'll remove it, otherwise, leave it untouched. - if (mType.isKnownProperty(key)) { - value = null; - } - } - - // if the value is still valid, write it down. - if (value != null) { - writeValue(writer, key, value, false /*addComment*/); - } - } else { - // the line was wrong, let's just ignore it so that it's removed from the - // file. - } - } else { - // non-property line: just write the line in the output as-is. - writer.append(line).append('\n'); - } - } - - // now add the new properties. - for (Entry<String, String> entry : mProperties.entrySet()) { - if (visitedProps.contains(entry.getKey()) == false) { - String value = entry.getValue(); - if (value != null) { - writeValue(writer, entry.getKey(), value, true /*addComment*/); - } - } - } - - Closeables.closeQuietly(reader); - - } else { - // new file, just write it all - - // write the header (can be null, for example for PropertyType.LEGACY_BUILD) - if (mType.getHeader() != null) { - writer.write(mType.getHeader()); - } - - // write the properties. - for (Entry<String, String> entry : mProperties.entrySet()) { - String value = entry.getValue(); - if (value != null) { - writeValue(writer, entry.getKey(), value, true /*addComment*/); - } - } - } - - writer.flush(); - - // now put the content in the file. - OutputStream filestream = toSave.getOutputStream(); - filestream.write(baos.toByteArray()); - filestream.flush(); - filestream.close(); - } - - private void writeValue(OutputStreamWriter writer, String key, String value, - boolean addComment) throws IOException { - if (addComment) { - String comment = COMMENT_MAP.get(key); - if (comment != null) { - writer.write(comment); - } - } - - writer.write(String.format("%s=%s\n", key, escape(value))); - } - - /** - * Private constructor. - * <p/> - * Use {@link #load(String, PropertyType)} or {@link #create(String, PropertyType)} - * to instantiate. - */ - ProjectPropertiesWorkingCopy(IAbstractFolder projectFolder, Map<String, String> map, - PropertyType type) { - super(projectFolder, map, type); - } - - @NonNull - public ProjectProperties makeReadOnlyCopy() { - // copy the current properties in a new map - Map<String, String> propList = new HashMap<String, String>(mProperties); - - return new ProjectProperties(mProjectFolder, propList, mType); - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/AdbWrapper.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/AdbWrapper.java deleted file mode 100755 index 8d4a0c2..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/AdbWrapper.java +++ /dev/null @@ -1,152 +0,0 @@ -/* - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository; - -import com.android.SdkConstants; - -import java.io.File; -import java.io.IOException; - -/** - * A lightweight wrapper to start & stop ADB. - * This is <b>specific</b> to the SDK Manager install process. - */ -public class AdbWrapper { - - /* - * Note: we could bring ddmlib in SdkManager for that purpose, however this allows us to - * specialize the start/stop methods to our needs (e.g. a task monitor, etc.) - */ - - private final String mAdbOsLocation; - private final ITaskMonitor mMonitor; - - /** - * Creates a new lightweight ADB wrapper. - * - * @param osSdkPath The root OS path of the SDK. Cannot be null. - * @param monitor A logger object. Cannot be null. - */ - public AdbWrapper(String osSdkPath, ITaskMonitor monitor) { - mMonitor = monitor; - - if (!osSdkPath.endsWith(File.separator)) { - osSdkPath += File.separator; - } - mAdbOsLocation = osSdkPath + SdkConstants.OS_SDK_PLATFORM_TOOLS_FOLDER - + SdkConstants.FN_ADB; - } - - private void display(String format, Object...args) { - mMonitor.log(format, args); - } - - private void displayError(String format, Object...args) { - mMonitor.logError(format, args); - } - - /** - * Starts the adb host side server. - * @return true if success - */ - public synchronized boolean startAdb() { - if (mAdbOsLocation == null) { - displayError("Error: missing path to ADB."); //$NON-NLS-1$ - return false; - } - - Process proc; - int status = -1; - - try { - ProcessBuilder processBuilder = new ProcessBuilder( - mAdbOsLocation, - "start-server"); //$NON-NLS-1$ - proc = processBuilder.start(); - status = proc.waitFor(); - - // Implementation note: normally on Windows we need to capture stderr/stdout - // to make sure the process isn't blocked if it's output isn't read. However - // in this case this happens to hang when reading stdout with no proper way - // to properly close the streams. On the other hand the output from start - // server is rather short and not very interesting so we just drop it. - - } catch (IOException ioe) { - displayError("Unable to run 'adb': %1$s.", ioe.getMessage()); //$NON-NLS-1$ - // we'll return false; - } catch (InterruptedException ie) { - displayError("Unable to run 'adb': %1$s.", ie.getMessage()); //$NON-NLS-1$ - // we'll return false; - } - - if (status != 0) { - displayError(String.format( - "Starting ADB server failed (code %d).", //$NON-NLS-1$ - status)); - return false; - } - - display("Starting ADB server succeeded."); //$NON-NLS-1$ - - return true; - } - - /** - * Stops the adb host side server. - * @return true if success - */ - public synchronized boolean stopAdb() { - if (mAdbOsLocation == null) { - displayError("Error: missing path to ADB."); //$NON-NLS-1$ - return false; - } - - Process proc; - int status = -1; - - try { - String[] command = new String[2]; - command[0] = mAdbOsLocation; - command[1] = "kill-server"; //$NON-NLS-1$ - proc = Runtime.getRuntime().exec(command); - status = proc.waitFor(); - - // See comment in startAdb about not needing/wanting to capture stderr/stdout. - } - catch (IOException ioe) { - // we'll return false; - } - catch (InterruptedException ie) { - // we'll return false; - } - - // adb kill-server returns: - // 0 if adb was running and was correctly killed. - // 1 if adb wasn't running and thus wasn't killed. - // This error case is not worth reporting. - - if (status != 0 && status != 1) { - displayError(String.format( - "Stopping ADB server failed (code %d).", //$NON-NLS-1$ - status)); - return false; - } - - display("Stopping ADB server succeeded."); //$NON-NLS-1$ - return true; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/AddonsListFetcher.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/AddonsListFetcher.java deleted file mode 100755 index ac7b5d0..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/AddonsListFetcher.java +++ /dev/null @@ -1,609 +0,0 @@ -/* - * Copyright (C) 2010 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository; - -import com.android.annotations.VisibleForTesting; -import com.android.annotations.VisibleForTesting.Visibility; -import com.android.sdklib.io.NonClosingInputStream; -import com.android.sdklib.io.NonClosingInputStream.CloseBehavior; -import com.android.sdklib.repository.SdkAddonsListConstants; -import com.android.sdklib.repository.SdkRepoConstants; - -import org.w3c.dom.Document; -import org.w3c.dom.NamedNodeMap; -import org.w3c.dom.Node; -import org.xml.sax.ErrorHandler; -import org.xml.sax.InputSource; -import org.xml.sax.SAXException; -import org.xml.sax.SAXParseException; - -import java.io.FileNotFoundException; -import java.io.IOException; -import java.io.InputStream; -import java.net.UnknownHostException; -import java.util.ArrayList; -import java.util.regex.Matcher; -import java.util.regex.Pattern; - -import javax.net.ssl.SSLKeyException; -import javax.xml.XMLConstants; -import javax.xml.parsers.DocumentBuilder; -import javax.xml.parsers.DocumentBuilderFactory; -import javax.xml.parsers.ParserConfigurationException; -import javax.xml.transform.stream.StreamSource; -import javax.xml.validation.Schema; -import javax.xml.validation.SchemaFactory; -import javax.xml.validation.Validator; - -/** - * Fetches and loads an sdk-addons-list XML. - * <p/> - * Such an XML contains a simple list of add-ons site that are to be loaded by default by the - * SDK Manager. <br/> - * The XML must conform to the sdk-addons-list-N.xsd. <br/> - * Constants used in the XML are defined in {@link SdkAddonsListConstants}. - */ -public class AddonsListFetcher { - - public enum SiteType { - ADDON_SITE, - SYS_IMG_SITE - } - - /** - * An immutable structure representing an add-on site. - */ - public static class Site { - private final String mUrl; - private final String mUiName; - private final SiteType mType; - - private Site(String url, String uiName, SiteType type) { - mType = type; - mUrl = url.trim(); - mUiName = uiName; - } - - public String getUrl() { - return mUrl; - } - - public String getUiName() { - return mUiName; - } - - public SiteType getType() { - return mType; - } - - /** Returns a debug string representation of this object. Not for user display. */ - @Override - public String toString() { - return String.format("<%1$s URL='%2$s' Name='%3$s'>", //$NON-NLS-1$ - mType, mUrl, mUiName); - } - } - - /** - * Fetches the addons list from the given URL. - * - * @param url The URL of an XML file resource that conforms to the latest sdk-addons-list-N.xsd. - * For the default operation, use {@link SdkAddonsListConstants#URL_ADDON_LIST}. - * Cannot be null. - * @param cache The {@link DownloadCache} instance to use. Cannot be null. - * @param monitor A monitor to report errors. Cannot be null. - * @return An array of {@link Site} on success (possibly empty), or null on error. - */ - public Site[] fetch(String url, DownloadCache cache, ITaskMonitor monitor) { - - url = url == null ? "" : url.trim(); - - monitor.setProgressMax(6); - monitor.setDescription("Fetching %1$s", url); - monitor.incProgress(1); - - Exception[] exception = new Exception[] { null }; - Boolean[] validatorFound = new Boolean[] { Boolean.FALSE }; - String[] validationError = new String[] { null }; - Document validatedDoc = null; - String validatedUri = null; - - String[] defaultNames = new String[SdkAddonsListConstants.NS_LATEST_VERSION]; - for (int version = SdkAddonsListConstants.NS_LATEST_VERSION, i = 0; - version >= 1; - version--, i++) { - defaultNames[i] = SdkAddonsListConstants.getDefaultName(version); - } - - InputStream xml = fetchXmlUrl(url, cache, monitor.createSubMonitor(1), exception); - if (xml != null) { - int version = getXmlSchemaVersion(xml); - if (version == 0) { - closeStream(xml); - xml = null; - } - } - - String baseUrl = url; - if (!baseUrl.endsWith("/")) { //$NON-NLS-1$ - int pos = baseUrl.lastIndexOf('/'); - if (pos > 0) { - baseUrl = baseUrl.substring(0, pos + 1); - } - } - - // If we can't find the latest version, try earlier schema versions. - if (xml == null && defaultNames.length > 0) { - ITaskMonitor subMonitor = monitor.createSubMonitor(1); - subMonitor.setProgressMax(defaultNames.length); - - for (String name : defaultNames) { - String newUrl = baseUrl + name; - if (newUrl.equals(url)) { - continue; - } - xml = fetchXmlUrl(newUrl, cache, subMonitor.createSubMonitor(1), exception); - if (xml != null) { - int version = getXmlSchemaVersion(xml); - if (version == 0) { - closeStream(xml); - xml = null; - } else { - url = newUrl; - subMonitor.incProgress( - subMonitor.getProgressMax() - subMonitor.getProgress()); - break; - } - } - } - } else { - monitor.incProgress(1); - } - - if (xml != null) { - monitor.setDescription("Validate XML"); - - // Explore the XML to find the potential XML schema version - int version = getXmlSchemaVersion(xml); - - if (version >= 1 && version <= SdkAddonsListConstants.NS_LATEST_VERSION) { - // This should be a version we can handle. Try to validate it - // and report any error as invalid XML syntax, - - String uri = validateXml(xml, url, version, validationError, validatorFound); - if (uri != null) { - // Validation was successful - validatedDoc = getDocument(xml, monitor); - validatedUri = uri; - - } - } else if (version > SdkAddonsListConstants.NS_LATEST_VERSION) { - // The schema used is more recent than what is supported by this tool. - // We don't have an upgrade-path support yet, so simply ignore the document. - closeStream(xml); - return null; - } - } - - // If any exception was handled during the URL fetch, display it now. - if (exception[0] != null) { - String reason = null; - if (exception[0] instanceof FileNotFoundException) { - // FNF has no useful getMessage, so we need to special handle it. - reason = "File not found"; - } else if (exception[0] instanceof UnknownHostException && - exception[0].getMessage() != null) { - // This has no useful getMessage yet could really use one - reason = String.format("Unknown Host %1$s", exception[0].getMessage()); - } else if (exception[0] instanceof SSLKeyException) { - // That's a common error and we have a pref for it. - reason = "HTTPS SSL error. You might want to force download through HTTP in the settings."; - } else if (exception[0].getMessage() != null) { - reason = exception[0].getMessage(); - } else { - // We don't know what's wrong. Let's give the exception class at least. - reason = String.format("Unknown (%1$s)", exception[0].getClass().getName()); - } - - monitor.logError("Failed to fetch URL %1$s, reason: %2$s", url, reason); - } - - if (validationError[0] != null) { - monitor.logError("%s", validationError[0]); //$NON-NLS-1$ - } - - // Stop here if we failed to validate the XML. We don't want to load it. - if (validatedDoc == null) { - closeStream(xml); - return null; - } - - monitor.incProgress(1); - - Site[] result = null; - - if (xml != null) { - monitor.setDescription("Parse XML"); - monitor.incProgress(1); - result = parseAddonsList(validatedDoc, validatedUri, baseUrl, monitor); - } - - // done - monitor.incProgress(1); - - closeStream(xml); - return result; - } - - /** - * Fetches the document at the given URL and returns it as a stream. Returns - * null if anything wrong happens. - * - * @param urlString The URL to load, as a string. - * @param monitor {@link ITaskMonitor} related to this URL. - * @param outException If non null, where to store any exception that - * happens during the fetch. - * @see UrlOpener UrlOpener, which handles all URL logic. - */ - private InputStream fetchXmlUrl(String urlString, - DownloadCache cache, - ITaskMonitor monitor, - Exception[] outException) { - try { - InputStream xml = cache.openCachedUrl(urlString, monitor); - if (xml != null) { - xml.mark(500000); - xml = new NonClosingInputStream(xml); - ((NonClosingInputStream) xml).setCloseBehavior(CloseBehavior.RESET); - } - return xml; - } catch (Exception e) { - if (outException != null) { - outException[0] = e; - } - } - - return null; - } - - /** - * Closes the stream, ignore any exception from InputStream.close(). - * If the stream is a NonClosingInputStream, sets it to CloseBehavior.CLOSE first. - */ - private void closeStream(InputStream is) { - if (is != null) { - if (is instanceof NonClosingInputStream) { - ((NonClosingInputStream) is).setCloseBehavior(CloseBehavior.CLOSE); - } - try { - is.close(); - } catch (IOException ignore) {} - } - } - - /** - * Manually parses the root element of the XML to extract the schema version - * at the end of the xmlns:sdk="http://schemas.android.com/sdk/android/addons-list/$N" - * declaration. - * - * @return 1..{@link SdkAddonsListConstants#NS_LATEST_VERSION} for a valid schema version - * or 0 if no schema could be found. - */ - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected int getXmlSchemaVersion(InputStream xml) { - if (xml == null) { - return 0; - } - - // Get an XML document - Document doc = null; - try { - assert xml.markSupported(); - xml.reset(); - - DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance(); - factory.setIgnoringComments(false); - factory.setValidating(false); - - // Parse the old document using a non namespace aware builder - factory.setNamespaceAware(false); - DocumentBuilder builder = factory.newDocumentBuilder(); - - // We don't want the default handler which prints errors to stderr. - builder.setErrorHandler(new ErrorHandler() { - @Override - public void warning(SAXParseException e) throws SAXException { - // pass - } - @Override - public void fatalError(SAXParseException e) throws SAXException { - throw e; - } - @Override - public void error(SAXParseException e) throws SAXException { - throw e; - } - }); - - doc = builder.parse(xml); - - // Prepare a new document using a namespace aware builder - factory.setNamespaceAware(true); - builder = factory.newDocumentBuilder(); - - } catch (Exception e) { - // Failed to reset XML stream - // Failed to get builder factor - // Failed to create XML document builder - // Failed to parse XML document - // Failed to read XML document - //--For debug--System.err.println("getXmlSchemaVersion exception: " + e.toString()); - } - - if (doc == null) { - return 0; - } - - // Check the root element is an XML with at least the following properties: - // <sdk:sdk-addons-list - // xmlns:sdk="http://schemas.android.com/sdk/android/addons-list/$N"> - // - // Note that we don't have namespace support enabled, we just do it manually. - - Pattern nsPattern = Pattern.compile(SdkAddonsListConstants.NS_PATTERN); - - String prefix = null; - for (Node child = doc.getFirstChild(); child != null; child = child.getNextSibling()) { - if (child.getNodeType() == Node.ELEMENT_NODE) { - prefix = null; - String name = child.getNodeName(); - int pos = name.indexOf(':'); - if (pos > 0 && pos < name.length() - 1) { - prefix = name.substring(0, pos); - name = name.substring(pos + 1); - } - if (SdkAddonsListConstants.NODE_SDK_ADDONS_LIST.equals(name)) { - NamedNodeMap attrs = child.getAttributes(); - String xmlns = "xmlns"; //$NON-NLS-1$ - if (prefix != null) { - xmlns += ":" + prefix; //$NON-NLS-1$ - } - Node attr = attrs.getNamedItem(xmlns); - if (attr != null) { - String uri = attr.getNodeValue(); - if (uri != null) { - Matcher m = nsPattern.matcher(uri); - if (m.matches()) { - String version = m.group(1); - try { - return Integer.parseInt(version); - } catch (NumberFormatException e) { - return 0; - } - } - } - } - } - } - } - - return 0; - } - - /** - * Validates this XML against one of the requested SDK Repository schemas. - * If the XML was correctly validated, returns the schema that worked. - * If it doesn't validate, returns null and stores the error in outError[0]. - * If we can't find a validator, returns null and set validatorFound[0] to false. - */ - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected String validateXml(InputStream xml, String url, int version, - String[] outError, Boolean[] validatorFound) { - - if (xml == null) { - return null; - } - - try { - Validator validator = getValidator(version); - - if (validator == null) { - validatorFound[0] = Boolean.FALSE; - outError[0] = String.format( - "XML verification failed for %1$s.\nNo suitable XML Schema Validator could be found in your Java environment. Please consider updating your version of Java.", - url); - return null; - } - - validatorFound[0] = Boolean.TRUE; - - // Reset the stream if it supports that operation. - assert xml.markSupported(); - xml.reset(); - - // Validation throws a bunch of possible Exceptions on failure. - validator.validate(new StreamSource(xml)); - return SdkAddonsListConstants.getSchemaUri(version); - - } catch (SAXParseException e) { - outError[0] = String.format( - "XML verification failed for %1$s.\nLine %2$d:%3$d, Error: %4$s", - url, - e.getLineNumber(), - e.getColumnNumber(), - e.toString()); - - } catch (Exception e) { - outError[0] = String.format( - "XML verification failed for %1$s.\nError: %2$s", - url, - e.toString()); - } - return null; - } - - /** - * Helper method that returns a validator for our XSD, or null if the current Java - * implementation can't process XSD schemas. - * - * @param version The version of the XML Schema. - * See {@link SdkAddonsListConstants#getXsdStream(int)} - */ - private Validator getValidator(int version) throws SAXException { - InputStream xsdStream = SdkAddonsListConstants.getXsdStream(version); - SchemaFactory factory = SchemaFactory.newInstance(XMLConstants.W3C_XML_SCHEMA_NS_URI); - - if (factory == null) { - return null; - } - - // This may throw a SAX Exception if the schema itself is not a valid XSD - Schema schema = factory.newSchema(new StreamSource(xsdStream)); - - Validator validator = schema == null ? null : schema.newValidator(); - - return validator; - } - - /** - * Takes an XML document as a string as parameter and returns a DOM for it. - * - * On error, returns null and prints a (hopefully) useful message on the monitor. - */ - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected Document getDocument(InputStream xml, ITaskMonitor monitor) { - try { - DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance(); - factory.setIgnoringComments(true); - factory.setNamespaceAware(true); - - DocumentBuilder builder = factory.newDocumentBuilder(); - assert xml.markSupported(); - xml.reset(); - Document doc = builder.parse(new InputSource(xml)); - - return doc; - } catch (ParserConfigurationException e) { - monitor.logError("Failed to create XML document builder"); - - } catch (SAXException e) { - monitor.logError("Failed to parse XML document"); - - } catch (IOException e) { - monitor.logError("Failed to read XML document"); - } - - return null; - } - - /** - * Parse all sites defined in the Addaons list XML and returns an array of sites. - * - * @param doc The XML DOM to parse. - * @param nsUri The addons-list schema URI of the document. - * @param baseUrl The base URL of the caller (e.g. where addons-list-N.xml was fetched from.) - * @param monitor A non-null monitor to print to. - */ - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected Site[] parseAddonsList( - Document doc, - String nsUri, - String baseUrl, - ITaskMonitor monitor) { - - String testBaseUrl = System.getenv("SDK_TEST_BASE_URL"); //$NON-NLS-1$ - if (testBaseUrl != null) { - if (testBaseUrl.length() <= 0 || !testBaseUrl.endsWith("/")) { //$NON-NLS-1$ - testBaseUrl = null; - } - } - - Node root = getFirstChild(doc, nsUri, SdkAddonsListConstants.NODE_SDK_ADDONS_LIST); - if (root != null) { - ArrayList<Site> sites = new ArrayList<Site>(); - - for (Node child = root.getFirstChild(); - child != null; - child = child.getNextSibling()) { - if (child.getNodeType() == Node.ELEMENT_NODE && - nsUri.equals(child.getNamespaceURI())) { - - String elementName = child.getLocalName(); - SiteType type = null; - - if (SdkAddonsListConstants.NODE_SYS_IMG_SITE.equals(elementName)) { - type = SiteType.SYS_IMG_SITE; - - } else if (SdkAddonsListConstants.NODE_ADDON_SITE.equals(elementName)) { - type = SiteType.ADDON_SITE; - } - - // Not an addon-site nor a sys-img-site, don't process this. - if (type == null) { - continue; - } - - Node url = getFirstChild(child, nsUri, SdkAddonsListConstants.NODE_URL); - Node name = getFirstChild(child, nsUri, SdkAddonsListConstants.NODE_NAME); - - if (name != null && url != null) { - String strUrl = url.getTextContent().trim(); - String strName = name.getTextContent().trim(); - - if (testBaseUrl != null && - strUrl.startsWith(SdkRepoConstants.URL_GOOGLE_SDK_SITE)) { - strUrl = testBaseUrl + - strUrl.substring(SdkRepoConstants.URL_GOOGLE_SDK_SITE.length()); - } else if (!strUrl.startsWith("http://") && //$NON-NLS-1$ - !strUrl.startsWith("https://")) { //$NON-NLS-1$ - // This looks like a relative URL, add the fetcher's base URL to it. - strUrl = baseUrl + strUrl; - } - - if (strUrl.length() > 0 && strName.length() > 0) { - sites.add(new Site(strUrl, strName, type)); - } - } - } - } - - return sites.toArray(new Site[sites.size()]); - } - - return null; - } - - /** - * Returns the first child element with the given XML local name. - * If xmlLocalName is null, returns the very first child element. - */ - private Node getFirstChild(Node node, String nsUri, String xmlLocalName) { - - for(Node child = node.getFirstChild(); child != null; child = child.getNextSibling()) { - if (child.getNodeType() == Node.ELEMENT_NODE && - nsUri.equals(child.getNamespaceURI())) { - if (xmlLocalName == null || child.getLocalName().equals(xmlLocalName)) { - return child; - } - } - } - - return null; - } - - -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/CanceledByUserException.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/CanceledByUserException.java deleted file mode 100755 index a0a74d8..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/CanceledByUserException.java +++ /dev/null @@ -1,30 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository; - -/** - * Exception thrown by {@link DownloadCache} and {@link UrlOpener} when a user - * cancels an HTTP Basic authentication or NTML authentication dialog. - */ -public class CanceledByUserException extends Exception { - private static final long serialVersionUID = -7669346110926032403L; - - public CanceledByUserException(String message) { - super(message); - } -} - diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/DownloadCache.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/DownloadCache.java deleted file mode 100755 index e02023d..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/DownloadCache.java +++ /dev/null @@ -1,830 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository; - -import com.android.SdkConstants; -import com.android.annotations.NonNull; -import com.android.annotations.Nullable; -import com.android.annotations.VisibleForTesting; -import com.android.annotations.VisibleForTesting.Visibility; -import com.android.prefs.AndroidLocation; -import com.android.prefs.AndroidLocation.AndroidLocationException; -import com.android.utils.Pair; - -import org.apache.http.Header; -import org.apache.http.HttpHeaders; -import org.apache.http.HttpResponse; -import org.apache.http.HttpStatus; -import org.apache.http.message.BasicHeader; - -import java.io.ByteArrayInputStream; -import java.io.File; -import java.io.FileInputStream; -import java.io.FileNotFoundException; -import java.io.FileOutputStream; -import java.io.IOException; -import java.io.InputStream; -import java.io.OutputStream; -import java.util.ArrayList; -import java.util.Arrays; -import java.util.List; -import java.util.Locale; -import java.util.Properties; -import java.util.concurrent.atomic.AtomicInteger; - - -/** - * A simple cache for the XML resources handled by the SDK Manager. - * <p/> - * Callers should use {@link #openDirectUrl} to download "large files" - * that should not be cached (like actual installation packages which are several MBs big) - * and call {@link #openCachedUrl(String, ITaskMonitor)} to download small XML files. - * <p/> - * The cache can work in 3 different strategies (direct is a pass-through, fresh-cache is the - * default and tries to update resources if they are older than 10 minutes by respecting - * either ETag or Last-Modified, and finally server-cache is a strategy to always serve - * cached entries if present.) - */ -public class DownloadCache { - - /* - * HTTP/1.1 references: - * - Possible headers: - * http://www.w3.org/Protocols/rfc2616/rfc2616-sec14.html - * - Rules about conditional requests: - * http://www.w3.org/Protocols/rfc2616/rfc2616-sec13.html#sec13.3.4 - * - Error codes: - * http://www.w3.org/Protocols/rfc2616/rfc2616-sec6.html#sec6.1.1 - */ - - private static final boolean DEBUG = System.getenv("SDKMAN_DEBUG_CACHE") != null; //$NON-NLS-1$ - - /** Key for the Status-Code in the info properties. */ - private static final String KEY_STATUS_CODE = "Status-Code"; //$NON-NLS-1$ - /** Key for the URL in the info properties. */ - private static final String KEY_URL = "URL"; //$NON-NLS-1$ - - /** Prefix of binary files stored in the {@link SdkConstants#FD_CACHE} directory. */ - private final static String BIN_FILE_PREFIX = "sdkbin"; //$NON-NLS-1$ - /** Prefix of meta info files stored in the {@link SdkConstants#FD_CACHE} directory. */ - private final static String INFO_FILE_PREFIX = "sdkinf"; //$NON-NLS-1$ - /* Revision suffixed to the prefix. */ - private final static String REV_FILE_PREFIX = "-1_"; //$NON-NLS-1$ - - /** - * Minimum time before we consider a cached entry is potentially stale. - * Expressed in milliseconds. - * <p/> - * When using the {@link Strategy#FRESH_CACHE}, the cache will not try to refresh - * a cached file if it's has been saved more recently than this time. - * When using the direct mode or the serve mode, the cache either doesn't serve - * cached files or always serves caches files so this expiration delay is not used. - * <p/> - * Default is 10 minutes. - * <p/> - * TODO: change for a dynamic preference later. - */ - private final static long MIN_TIME_EXPIRED_MS = 10*60*1000; - /** - * Maximum time before we consider a cache entry to be stale. - * Expressed in milliseconds. - * <p/> - * When using the {@link Strategy#FRESH_CACHE}, entries that have no ETag - * or Last-Modified will be refreshed if their file timestamp is older than - * this value. - * <p/> - * Default is 4 hours. - * <p/> - * TODO: change for a dynamic preference later. - */ - private final static long MAX_TIME_EXPIRED_MS = 4*60*60*1000; - - /** - * The maximum file size we'll cache for "small" files. - * 640KB is more than enough and is already a stretch since these are read in memory. - * (The actual typical size of the files handled here is in the 4-64KB range.) - */ - private final static int MAX_SMALL_FILE_SIZE = 640 * 1024; - - /** - * HTTP Headers that are saved in an info file. - * For HTTP/1.1 header names, see http://www.w3.org/Protocols/rfc2616/rfc2616-sec14.html - */ - private final static String[] INFO_HTTP_HEADERS = { - HttpHeaders.LAST_MODIFIED, - HttpHeaders.ETAG, - HttpHeaders.CONTENT_LENGTH, - HttpHeaders.DATE - }; - - private final Strategy mStrategy; - private final File mCacheRoot; - - public enum Strategy { - /** - * Exclusively serves data from the cache. If files are available in the - * cache, serve them as is (without trying to refresh them). If files are - * not available, they are <em>not</em> fetched at all. - */ - ONLY_CACHE, - /** - * If the files are available in the cache, serve them as-is, otherwise - * download them and return the cached version. No expiration or refresh - * is attempted if a file is in the cache. - */ - SERVE_CACHE, - /** - * If the files are available in the cache, check if there's an update - * (either using an e-tag check or comparing to the default time expiration). - * If files have expired or are not in the cache then download them and return - * the cached version. - */ - FRESH_CACHE, - /** - * Disables caching. URLs are always downloaded and returned directly. - * Downloaded streams aren't cached locally. - */ - DIRECT - } - - /** Creates a default instance of the URL cache */ - public DownloadCache(Strategy strategy) { - mCacheRoot = initCacheRoot(); - - // If this is defined in the environment, never use the cache. Useful for testing. - if (System.getenv("SDKMAN_DISABLE_CACHE") != null) { //$NON-NLS-1$ - strategy = Strategy.DIRECT; - } - - mStrategy = mCacheRoot == null ? Strategy.DIRECT : strategy; - } - - public Strategy getStrategy() { - return mStrategy; - } - - public File getCacheRoot() { - return mCacheRoot; - } - - /** - * Computes the size of the cached files. - * - * @return The sum of the byte size of the cached files. - */ - public long getCurrentSize() { - long size = 0; - - if (mCacheRoot != null) { - File[] files = mCacheRoot.listFiles(); - if (files != null) { - for (File f : files) { - if (f.isFile()) { - String name = f.getName(); - if (name.startsWith(BIN_FILE_PREFIX) || - name.startsWith(INFO_FILE_PREFIX)) { - size += f.length(); - } - } - } - } - } - - return size; - } - - /** - * Removes all cached files from the cache directory. - */ - public void clearCache() { - if (mCacheRoot != null) { - File[] files = mCacheRoot.listFiles(); - if (files != null) { - for (File f : files) { - if (f.isFile()) { - String name = f.getName(); - if (name.startsWith(BIN_FILE_PREFIX) || - name.startsWith(INFO_FILE_PREFIX)) { - f.delete(); - } - } - } - } - } - } - - /** - * Removes all obsolete cached files from the cache directory - * that do not match the latest revision. - */ - public void clearOldCache() { - String prefix1 = BIN_FILE_PREFIX + REV_FILE_PREFIX; - String prefix2 = INFO_FILE_PREFIX + REV_FILE_PREFIX; - if (mCacheRoot != null) { - File[] files = mCacheRoot.listFiles(); - if (files != null) { - for (File f : files) { - if (f.isFile()) { - String name = f.getName(); - if (name.startsWith(BIN_FILE_PREFIX) || - name.startsWith(INFO_FILE_PREFIX)) { - if (!name.startsWith(prefix1) && !name.startsWith(prefix2)) { - f.delete(); - } - } - } - } - } - } - } - - /** - * Returns the directory to be used as a cache. - * Creates it if necessary. - * Makes it possible to disable or override the cache location in unit tests. - * - * @return An existing directory to use as a cache root dir, - * or null in case of error in which case the cache will be disabled. - */ - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected File initCacheRoot() { - try { - File root = new File(AndroidLocation.getFolder()); - root = new File(root, SdkConstants.FD_CACHE); - if (!root.exists()) { - root.mkdirs(); - } - return root; - } catch (AndroidLocationException e) { - // No root? Disable the cache. - return null; - } - } - - /** - * Does a direct download of the given URL using {@link UrlOpener}. - * This does not check the download cache and does not attempt to cache the file. - * Instead the HttpClient library returns a progressive download stream. - * <p/> - * For details on realm authentication and user/password handling, - * check the underlying {@link UrlOpener#openUrl(String, boolean, ITaskMonitor, Header[])} - * documentation. - * <p/> - * The resulting input stream may not support mark/reset. - * - * @param urlString the URL string to be opened. - * @param headers An optional set of headers to pass when requesting the resource. Can be null. - * @param monitor {@link ITaskMonitor} which is related to this URL - * fetching. - * @return Returns a pair with a {@link InputStream} and an {@link HttpResponse}. - * The pair is never null. - * The input stream can be null in case of error, although in general the - * method will probably throw an exception instead. - * The caller should look at the response code's status and only accept the - * input stream if it's the desired code (e.g. 200 or 206). - * @throws IOException Exception thrown when there are problems retrieving - * the URL or its content. - * @throws CanceledByUserException Exception thrown if the user cancels the - * authentication dialog. - */ - public Pair<InputStream, HttpResponse> openDirectUrl( - @NonNull String urlString, - @Nullable Header[] headers, - @NonNull ITaskMonitor monitor) - throws IOException, CanceledByUserException { - if (DEBUG) { - System.out.println(String.format("%s : Direct download", urlString)); //$NON-NLS-1$ - } - return UrlOpener.openUrl( - urlString, - false /*needsMarkResetSupport*/, - monitor, - headers); - } - - /** - * This is a simplified convenience method that calls - * {@link #openDirectUrl(String, Header[], ITaskMonitor)} - * without passing any specific HTTP headers and returns the resulting input stream - * and the HTTP status code. - * See the original method's description for details on its behavior. - * <p/> - * {@link #openDirectUrl(String, Header[], ITaskMonitor)} can accept customized - * HTTP headers to send with the requests and also returns the full HTTP - * response -- status line with code and protocol and all headers. - * <p/> - * The resulting input stream may not support mark/reset. - * - * @param urlString the URL string to be opened. - * @param monitor {@link ITaskMonitor} which is related to this URL - * fetching. - * @return Returns a pair with a {@link InputStream} and an HTTP status code. - * The pair is never null. - * The input stream can be null in case of error, although in general the - * method will probably throw an exception instead. - * The caller should look at the response code's status and only accept the - * input stream if it's the desired code (e.g. 200 or 206). - * @throws IOException Exception thrown when there are problems retrieving - * the URL or its content. - * @throws CanceledByUserException Exception thrown if the user cancels the - * authentication dialog. - * @see #openDirectUrl(String, Header[], ITaskMonitor) - */ - public Pair<InputStream, Integer> openDirectUrl( - @NonNull String urlString, - @NonNull ITaskMonitor monitor) - throws IOException, CanceledByUserException { - if (DEBUG) { - System.out.println(String.format("%s : Direct download", urlString)); //$NON-NLS-1$ - } - Pair<InputStream, HttpResponse> result = UrlOpener.openUrl( - urlString, - false /*needsMarkResetSupport*/, - monitor, - null /*headers*/); - return Pair.of(result.getFirst(), result.getSecond().getStatusLine().getStatusCode()); - } - - /** - * Downloads a small file, typically XML manifests. - * The current {@link Strategy} governs whether the file is served as-is - * from the cache, potentially updated first or directly downloaded. - * <p/> - * For large downloads (e.g. installable archives) please do not invoke the - * cache and instead use the {@link #openDirectUrl} method. - * <p/> - * For details on realm authentication and user/password handling, - * check the underlying {@link UrlOpener#openUrl(String, boolean, ITaskMonitor, Header[])} - * documentation. - * - * @param urlString the URL string to be opened. - * @param monitor {@link ITaskMonitor} which is related to this URL - * fetching. - * @return Returns an {@link InputStream} holding the URL content. - * Returns null if there's no content (e.g. resource not found.) - * Returns null if the document is not cached and strategy is {@link Strategy#ONLY_CACHE}. - * @throws IOException Exception thrown when there are problems retrieving - * the URL or its content. - * @throws CanceledByUserException Exception thrown if the user cancels the - * authentication dialog. - */ - public InputStream openCachedUrl(String urlString, ITaskMonitor monitor) - throws IOException, CanceledByUserException { - // Don't cache in direct mode. - if (mStrategy == Strategy.DIRECT) { - Pair<InputStream, HttpResponse> result = UrlOpener.openUrl( - urlString, - true /*needsMarkResetSupport*/, - monitor, - null /*headers*/); - return result.getFirst(); - } - - File cached = new File(mCacheRoot, getCacheFilename(urlString)); - File info = new File(mCacheRoot, getInfoFilename(cached.getName())); - - boolean useCached = cached.exists(); - - if (useCached && mStrategy == Strategy.FRESH_CACHE) { - // Check whether the file should be served from the cache or - // refreshed first. - - long cacheModifiedMs = cached.lastModified(); /* last mod time in epoch/millis */ - boolean checkCache = true; - - Properties props = readInfo(info); - if (props == null) { - // No properties, no chocolate for you. - useCached = false; - } else { - long minExpiration = System.currentTimeMillis() - MIN_TIME_EXPIRED_MS; - checkCache = cacheModifiedMs < minExpiration; - - if (!checkCache && DEBUG) { - System.out.println(String.format( - "%s : Too fresh [%,d ms], not checking yet.", //$NON-NLS-1$ - urlString, cacheModifiedMs - minExpiration)); - } - } - - if (useCached && checkCache) { - assert props != null; - - // Right now we only support 200 codes and will requery all 404s. - String code = props.getProperty(KEY_STATUS_CODE, ""); //$NON-NLS-1$ - useCached = Integer.toString(HttpStatus.SC_OK).equals(code); - - if (!useCached && DEBUG) { - System.out.println(String.format( - "%s : cache disabled by code %s", //$NON-NLS-1$ - urlString, code)); - } - - if (useCached) { - // Do we have a valid Content-Length? If so, it should match the file size. - try { - long length = Long.parseLong(props.getProperty(HttpHeaders.CONTENT_LENGTH, - "-1")); //$NON-NLS-1$ - if (length >= 0) { - useCached = length == cached.length(); - - if (!useCached && DEBUG) { - System.out.println(String.format( - "%s : cache disabled by length mismatch %d, expected %d", //$NON-NLS-1$ - urlString, length, cached.length())); - } - } - } catch (NumberFormatException ignore) {} - } - - if (useCached) { - // Do we have an ETag and/or a Last-Modified? - String etag = props.getProperty(HttpHeaders.ETAG); - String lastMod = props.getProperty(HttpHeaders.LAST_MODIFIED); - - if (etag != null || lastMod != null) { - // Details on how to use them is defined at - // http://www.w3.org/Protocols/rfc2616/rfc2616-sec13.html#sec13.3.4 - // Bottom line: - // - if there's an ETag, it should be used first with an - // If-None-Match header. That's a strong comparison for HTTP/1.1 servers. - // - otherwise use a Last-Modified if an If-Modified-Since header exists. - // In this case, we place both and the rules indicates a spec-abiding - // server should strongly match ETag and weakly the Modified-Since. - - // TODO there are some servers out there which report ETag/Last-Mod - // yet don't honor them when presented with a precondition. In this - // case we should identify it in the reply and invalidate ETag support - // for these servers and instead fallback on the pure-timeout case below. - - AtomicInteger statusCode = new AtomicInteger(0); - InputStream is = null; - List<Header> headers = new ArrayList<Header>(2); - - if (etag != null) { - headers.add(new BasicHeader(HttpHeaders.IF_NONE_MATCH, etag)); - } - - if (lastMod != null) { - headers.add(new BasicHeader(HttpHeaders.IF_MODIFIED_SINCE, lastMod)); - } - - if (!headers.isEmpty()) { - is = downloadAndCache(urlString, monitor, cached, info, - headers.toArray(new Header[headers.size()]), - statusCode); - } - - if (is != null && statusCode.get() == HttpStatus.SC_OK) { - // The resource was modified, the server said there was something - // new, which has been cached. We can return that to the caller. - return is; - } - - // If we get here, we should have is == null and code - // could be: - // - 304 for not-modified -- same resource, still available, in - // which case we'll use the cached one. - // - 404 -- resource doesn't exist anymore in which case there's - // no point in retrying. - // - For any other code, just retry a download. - - if (is != null) { - try { - is.close(); - } catch (Exception ignore) {} - is = null; - } - - if (statusCode.get() == HttpStatus.SC_NOT_MODIFIED) { - // Cached file was not modified. - // Change its timestamp for the next MIN_TIME_EXPIRED_MS check. - cached.setLastModified(System.currentTimeMillis()); - - // At this point useCached==true so we'll return - // the cached file below. - } else { - // URL fetch returned something other than 200 or 304. - // For 404, we're done, no need to check the server again. - // For all other codes, we'll retry a download below. - useCached = false; - if (statusCode.get() == HttpStatus.SC_NOT_FOUND) { - return null; - } - } - } else { - // If we don't have an Etag nor Last-Modified, let's use a - // basic file timestamp and compare to a 1 hour threshold. - - long maxExpiration = System.currentTimeMillis() - MAX_TIME_EXPIRED_MS; - useCached = cacheModifiedMs >= maxExpiration; - - if (!useCached && DEBUG) { - System.out.println(String.format( - "[%1$s] cache disabled by timestamp %2$tD %2$tT < %3$tD %3$tT", //$NON-NLS-1$ - urlString, cacheModifiedMs, maxExpiration)); - } - } - } - } - } - - if (useCached) { - // The caller needs an InputStream that supports the reset() operation. - // The default FileInputStream does not, so load the file into a byte - // array and return that. - try { - InputStream is = readCachedFile(cached); - if (is != null) { - if (DEBUG) { - System.out.println(String.format("%s : Use cached file", urlString)); //$NON-NLS-1$ - } - - return is; - } - } catch (IOException ignore) {} - } - - if (!useCached && mStrategy == Strategy.ONLY_CACHE) { - // We don't have a document to serve from the cache. - if (DEBUG) { - System.out.println(String.format("%s : file not in cache", urlString)); //$NON-NLS-1$ - } - return null; - } - - // If we're not using the cache, try to remove the cache and download again. - try { - cached.delete(); - info.delete(); - } catch (SecurityException ignore) {} - - return downloadAndCache(urlString, monitor, cached, info, - null /*headers*/, null /*statusCode*/); - } - - - - // -------------- - - private InputStream readCachedFile(File cached) throws IOException { - InputStream is = null; - - int inc = 65536; - int curr = 0; - long len = cached.length(); - assert len < Integer.MAX_VALUE; - if (len >= MAX_SMALL_FILE_SIZE) { - // This is supposed to cache small files, not 2+ GB files. - return null; - } - byte[] result = new byte[(int) (len > 0 ? len : inc)]; - - try { - is = new FileInputStream(cached); - - int n; - while ((n = is.read(result, curr, result.length - curr)) != -1) { - curr += n; - if (curr == result.length) { - byte[] temp = new byte[curr + inc]; - System.arraycopy(result, 0, temp, 0, curr); - result = temp; - } - } - - return new ByteArrayInputStream(result, 0, curr); - - } finally { - if (is != null) { - try { - is.close(); - } catch (IOException ignore) {} - } - } - } - - /** - * Download, cache and return as an in-memory byte stream. - * The download is only done if the server returns 200/OK. - * On success, store an info file next to the download with - * a few headers. - * <p/> - * This method deletes the cached file and the info file ONLY if it - * attempted a download and it failed to complete. It doesn't erase - * anything if there's no download because the server returned a 404 - * or 304 or similar. - * - * @return An in-memory byte buffer input stream for the downloaded - * and locally cached file, or null if nothing was downloaded - * (including if it was a 304 Not-Modified status code.) - */ - private InputStream downloadAndCache( - String urlString, - ITaskMonitor monitor, - File cached, - File info, - @Nullable Header[] headers, - @Nullable AtomicInteger outStatusCode) - throws FileNotFoundException, IOException, CanceledByUserException { - InputStream is = null; - OutputStream os = null; - - int inc = 65536; - int curr = 0; - byte[] result = new byte[inc]; - - try { - Pair<InputStream, HttpResponse> r = - UrlOpener.openUrl(urlString, true /*needsMarkResetSupport*/, monitor, headers); - - is = r.getFirst(); - HttpResponse response = r.getSecond(); - - if (DEBUG) { - System.out.println(String.format("%s : fetch: %s => %s", //$NON-NLS-1$ - urlString, - headers == null ? "" : Arrays.toString(headers), //$NON-NLS-1$ - response.getStatusLine())); - } - - int code = response.getStatusLine().getStatusCode(); - - if (outStatusCode != null) { - outStatusCode.set(code); - } - - if (code != HttpStatus.SC_OK) { - // Only a 200 response code makes sense here. - // Even the other 20x codes should not apply, e.g. no content or partial - // content are not statuses we want to handle and should never happen. - // (see http://www.w3.org/Protocols/rfc2616/rfc2616-sec6.html#sec6.1.1 for list) - return null; - } - - os = new FileOutputStream(cached); - - int n; - while ((n = is.read(result, curr, result.length - curr)) != -1) { - if (os != null && n > 0) { - os.write(result, curr, n); - } - - curr += n; - - if (os != null && curr > MAX_SMALL_FILE_SIZE) { - // If the file size exceeds our "small file size" threshold, - // stop caching. We don't want to fill the disk. - try { - os.close(); - } catch (IOException ignore) {} - try { - cached.delete(); - info.delete(); - } catch (SecurityException ignore) {} - os = null; - } - if (curr == result.length) { - byte[] temp = new byte[curr + inc]; - System.arraycopy(result, 0, temp, 0, curr); - result = temp; - } - } - - // Close the output stream, signaling it was stored properly. - if (os != null) { - try { - os.close(); - os = null; - - saveInfo(urlString, response, info); - } catch (IOException ignore) {} - } - - return new ByteArrayInputStream(result, 0, curr); - - } finally { - if (is != null) { - try { - is.close(); - } catch (IOException ignore) {} - } - if (os != null) { - try { - os.close(); - } catch (IOException ignore) {} - // If we get here with the output stream not null, it means there - // was an issue and we don't want to keep that file. We'll try to - // delete it. - try { - cached.delete(); - info.delete(); - } catch (SecurityException ignore) {} - } - } - } - - /** - * Saves part of the HTTP Response to the info file. - */ - private void saveInfo(String urlString, HttpResponse response, File info) throws IOException { - Properties props = new Properties(); - - // we don't need the status code & URL right now. - // Save it in case we want to have it later (e.g. to differentiate 200 and 404.) - props.setProperty(KEY_URL, urlString); - props.setProperty(KEY_STATUS_CODE, - Integer.toString(response.getStatusLine().getStatusCode())); - - for (String name : INFO_HTTP_HEADERS) { - Header h = response.getFirstHeader(name); - if (h != null) { - props.setProperty(name, h.getValue()); - } - } - - FileOutputStream os = null; - try { - os = new FileOutputStream(info); - props.store(os, "## Meta data for SDK Manager cache. Do not modify."); //$NON-NLS-1$ - } finally { - if (os != null) { - os.close(); - } - } - } - - /** - * Reads the info properties file. - * @return The properties found or null if there's no file or it can't be read. - */ - private Properties readInfo(File info) { - if (info.exists()) { - Properties props = new Properties(); - - InputStream is = null; - try { - is = new FileInputStream(info); - props.load(is); - return props; - } catch (IOException ignore) { - } finally { - if (is != null) { - try { - is.close(); - } catch (IOException ignore) {} - } - } - } - return null; - } - - /** - * Computes the cache filename for the given URL. - * The filename uses the {@link #BIN_FILE_PREFIX}, the full URL string's hashcode and - * a sanitized portion of the URL filename. The returned filename is never - * more than 64 characters to ensure maximum file system compatibility. - * - * @param urlString The download URL. - * @return A leaf filename for the cached download file. - */ - private String getCacheFilename(String urlString) { - String hash = String.format("%08x", urlString.hashCode()); - - String leaf = urlString.toLowerCase(Locale.US); - if (leaf.length() >= 2) { - int index = urlString.lastIndexOf('/', leaf.length() - 2); - leaf = urlString.substring(index + 1); - } - - leaf = leaf.replaceAll("[^a-z0-9_-]+", "_"); - leaf = leaf.replaceAll("__+", "_"); - - leaf = hash + '-' + leaf; - String prefix = BIN_FILE_PREFIX + REV_FILE_PREFIX; - int n = 64 - prefix.length(); - if (leaf.length() > n) { - leaf = leaf.substring(0, n); - } - - return prefix + leaf; - } - - private String getInfoFilename(String cacheFilename) { - return cacheFilename.replaceFirst(BIN_FILE_PREFIX, INFO_FILE_PREFIX); - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/IDescription.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/IDescription.java deleted file mode 100755 index 7226360..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/IDescription.java +++ /dev/null @@ -1,40 +0,0 @@ -/* - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository; - -/** - * Interface for elements that can provide a description of themselves. - */ -public interface IDescription { - - /** - * Returns a description of the given element. Cannot be null. - * <p/> - * A description is a multi-line of text, typically much more - * elaborate than what {@link Object#toString()} would provide. - */ - public abstract String getShortDescription(); - - /** - * Returns a description of the given element. Cannot be null. - * <p/> - * A description is a multi-line of text, typically much more - * elaborate than what {@link Object#toString()} would provide. - */ - public abstract String getLongDescription(); - -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/ITask.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/ITask.java deleted file mode 100755 index 5e561eb..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/ITask.java +++ /dev/null @@ -1,26 +0,0 @@ -/* - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository; - - -/** - * A task that executes and can update a monitor to display its status. - * The task will generally be run in a separate thread. - */ -public interface ITask { - public abstract void run(ITaskMonitor monitor); -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/ITaskFactory.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/ITaskFactory.java deleted file mode 100755 index 959549b..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/ITaskFactory.java +++ /dev/null @@ -1,59 +0,0 @@ -/* - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository; - - -/** - * A factory that can start and run new {@link ITask}s. - */ -public interface ITaskFactory { - - /** - * Starts a new task with a new {@link ITaskMonitor}. - * <p/> - * The task will execute in a thread and runs it own UI loop. - * This means the task can perform UI operations using - * {@code Display#asyncExec(Runnable)}. - * <p/> - * In either case, the method only returns when the task has finished. - * - * @param title The title of the task, displayed in the monitor if any. - * @param task The task to run. - */ - public abstract void start(String title, ITask task); - - /** - * Starts a new task contributing to an already existing {@link ITaskMonitor}. - * <p/> - * To use this properly, you should use {@link ITaskMonitor#createSubMonitor(int)} - * and give the sub-monitor to the new task with the number of work units you want - * it to fill. The {@link #start} method will make sure to <em>fill</em> the progress - * when the task is completed, in case the actual task did not. - * <p/> - * When a task is started from within a monitor, it reuses the thread - * from the parent. Otherwise it starts a new thread and runs it own - * UI loop. This means the task can perform UI operations using - * {@code Display#asyncExec(Runnable)}. - * <p/> - * In either case, the method only returns when the task has finished. - * - * @param title The title of the task, displayed in the monitor if any. - * @param parentMonitor The parent monitor. Can be null. - * @param task The task to run and have it display on the monitor. - */ - public abstract void start(String title, ITaskMonitor parentMonitor, ITask task); -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/ITaskMonitor.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/ITaskMonitor.java deleted file mode 100755 index 74dd14a..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/ITaskMonitor.java +++ /dev/null @@ -1,147 +0,0 @@ -/* - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository; - -import com.android.utils.ILogger; - - -/** - * A monitor interface for a {@link ITask}. - * <p/> - * Depending on the task factory that created the task, there might not be any UI - * or it might not implement all the methods, in which case calling them would be - * a no-op but is guaranteed not to crash. - * <p/> - * If the task runs in a non-UI worker thread, the task factory implementation - * will take care of the update the UI in the correct thread. The task itself - * must not have to deal with it. - * <p/> - * A monitor typically has 3 levels of text displayed: <br/> - * - A <b>title</b> <em>may</em> be present on a task dialog, typically when a task - * dialog is created. This is not covered by this monitor interface. <br/> - * - A <b>description</b> displays prominent information on what the task - * is currently doing. This is expected to vary over time, typically changing - * with each sub-monitor, and typically only the last description is visible. - * For example an updater would typically have descriptions such as "downloading", - * "installing" and finally "done". This is set using {@link #setDescription}. <br/> - * - A <b>verbose</b> optional log that can provide more information than the summary - * description and is typically displayed in some kind of scrollable multi-line - * text field so that the user can keep track of what happened. 3 levels are - * provided: error, normal and verbose. An UI may hide the log till an error is - * logged and/or might hide the verbose text unless a flag is checked by the user. - * This is set using {@link #log}, {@link #logError} and {@link #logVerbose}. - * <p/> - * A monitor is also an {@link ILogger} implementation. - */ -public interface ITaskMonitor extends ILogger { - - /** - * Sets the description in the current task dialog. - * This method can be invoked from a non-UI thread. - */ - public void setDescription(String format, Object...args); - - /** - * Logs a "normal" information line. - * This method can be invoked from a non-UI thread. - */ - public void log(String format, Object...args); - - /** - * Logs an "error" information line. - * This method can be invoked from a non-UI thread. - */ - public void logError(String format, Object...args); - - /** - * Logs a "verbose" information line, that is extra details which are typically - * not that useful for the end-user and might be hidden until explicitly shown. - * This method can be invoked from a non-UI thread. - */ - public void logVerbose(String format, Object...args); - - /** - * Sets the max value of the progress bar. - * This method can be invoked from a non-UI thread. - * - * This method MUST be invoked once before using {@link #incProgress(int)} or - * {@link #getProgress()} or {@link #createSubMonitor(int)}. Callers are - * discouraged from using more than once -- implementations can either discard - * the next calls or behave incoherently. - */ - public void setProgressMax(int max); - - /** - * Returns the max valie of the progress bar, as last set by {@link #setProgressMax(int)}. - * Returns 0 if the max has never been set yet. - */ - public int getProgressMax(); - - /** - * Increments the current value of the progress bar. - * This method can be invoked from a non-UI thread. - * - * Callers MUST use setProgressMax before using this method. - */ - public void incProgress(int delta); - - /** - * Returns the current value of the progress bar, - * between 0 and up to {@link #setProgressMax(int)} - 1. - * - * Callers MUST use setProgressMax before using this method. - */ - public int getProgress(); - - /** - * Returns true if the user requested to cancel the operation. - * It is up to the task thread to pool this and exit as soon - * as possible. - */ - public boolean isCancelRequested(); - - /** - * Creates a sub-monitor that will use up to tickCount on the progress bar. - * tickCount must be 1 or more. - */ - public ITaskMonitor createSubMonitor(int tickCount); - - /** - * Display a yes/no question dialog box. - * - * Implementations MUST allow this to be called from any thread, e.g. by - * making sure the dialog is opened synchronously in the ui thread. - * - * @param title The title of the dialog box - * @param message The error message - * @return true if YES was clicked. - */ - public boolean displayPrompt(final String title, final String message); - - /** - * Launch an interface which asks for user credentials. Implementations - * MUST allow this to be called from any thread, e.g. by making sure the - * dialog is opened synchronously in the UI thread. - * - * @param title The title of the dialog box. - * @param message The message to be displayed as an instruction. - * @return Returns the user provided credentials. Some fields may be blank if the user - * did not provide any input. - If operation is <b>canceled</b> by user the return value must be <b>null</b>. - */ - public UserCredentials displayLoginCredentialsPrompt(String title, String message); -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/LocalSdkParser.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/LocalSdkParser.java deleted file mode 100755 index 313819b..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/LocalSdkParser.java +++ /dev/null @@ -1,659 +0,0 @@ -/* - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository; - -import com.android.SdkConstants; -import com.android.annotations.NonNull; -import com.android.sdklib.IAndroidTarget; -import com.android.sdklib.ISystemImage; -import com.android.sdklib.ISystemImage.LocationType; -import com.android.sdklib.SdkManager; -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; -import com.android.sdklib.internal.repository.packages.AddonPackage; -import com.android.sdklib.internal.repository.packages.DocPackage; -import com.android.sdklib.internal.repository.packages.ExtraPackage; -import com.android.sdklib.internal.repository.packages.Package; -import com.android.sdklib.internal.repository.packages.PlatformPackage; -import com.android.sdklib.internal.repository.packages.PlatformToolPackage; -import com.android.sdklib.internal.repository.packages.SamplePackage; -import com.android.sdklib.internal.repository.packages.SourcePackage; -import com.android.sdklib.internal.repository.packages.SystemImagePackage; -import com.android.sdklib.internal.repository.packages.ToolPackage; -import com.android.utils.ILogger; -import com.android.utils.Pair; - -import java.io.File; -import java.io.FileInputStream; -import java.io.IOException; -import java.util.ArrayList; -import java.util.Collections; -import java.util.HashSet; -import java.util.Map; -import java.util.Properties; - -/** - * Scans a local SDK to find which packages are currently installed. - */ -public class LocalSdkParser { - - private Package[] mPackages; - - /** Parse all SDK folders. */ - public static final int PARSE_ALL = 0xFFFF; - /** Parse the SDK/tools folder. */ - public static final int PARSE_TOOLS = 0x0001; - /** Parse the SDK/platform-tools folder */ - public static final int PARSE_PLATFORM_TOOLS = 0x0002; - /** Parse the SDK/docs folder. */ - public static final int PARSE_DOCS = 0x0004; - /** - * Equivalent to parsing the SDK/platforms folder but does so - * by using the <em>valid</em> targets loaded by the {@link SdkManager}. - * Parsing the platforms also parses the SDK/system-images folder. - */ - public static final int PARSE_PLATFORMS = 0x0010; - /** - * Equivalent to parsing the SDK/addons folder but does so - * by using the <em>valid</em> targets loaded by the {@link SdkManager}. - */ - public static final int PARSE_ADDONS = 0x0020; - /** Parse the SDK/samples folder. - * Note: this will not detect samples located in the SDK/extras packages. */ - public static final int PARSE_SAMPLES = 0x0100; - /** Parse the SDK/sources folder. */ - public static final int PARSE_SOURCES = 0x0200; - /** Parse the SDK/extras folder. */ - public static final int PARSE_EXTRAS = 0x0400; - - public LocalSdkParser() { - // pass - } - - /** - * Returns the packages found by the last call to {@link #parseSdk}. - * <p/> - * This returns initially returns null. - * Once the parseSdk() method has been called, this returns a possibly empty but non-null array. - */ - public Package[] getPackages() { - return mPackages; - } - - /** - * Clear the internal packages list. After this call, {@link #getPackages()} will return - * null till {@link #parseSdk} is called. - */ - public void clearPackages() { - mPackages = null; - } - - /** - * Scan the give SDK to find all the packages already installed at this location. - * <p/> - * Store the packages internally. You can use {@link #getPackages()} to retrieve them - * at any time later. - * <p/> - * Equivalent to calling {@code parseSdk(..., PARSE_ALL, ...); } - * - * @param osSdkRoot The path to the SDK folder, typically {@code sdkManager.getLocation()}. - * @param sdkManager An existing SDK manager to list current platforms and addons. - * @param monitor A monitor to track progress. Cannot be null. - * @return The packages found. Can be retrieved later using {@link #getPackages()}. - */ - public @NonNull Package[] parseSdk( - @NonNull String osSdkRoot, - @NonNull SdkManager sdkManager, - @NonNull ITaskMonitor monitor) { - return parseSdk(osSdkRoot, sdkManager, PARSE_ALL, monitor); - } - - /** - * Scan the give SDK to find all the packages already installed at this location. - * <p/> - * Store the packages internally. You can use {@link #getPackages()} to retrieve them - * at any time later. - * - * @param osSdkRoot The path to the SDK folder, typically {@code sdkManager.getLocation()}. - * @param sdkManager An existing SDK manager to list current platforms and addons. - * @param parseFilter Either {@link #PARSE_ALL} or an ORed combination of the other - * {@code PARSE_} constants to indicate what should be parsed. - * @param monitor A monitor to track progress. Cannot be null. - * @return The packages found. Can be retrieved later using {@link #getPackages()}. - */ - public @NonNull Package[] parseSdk( - @NonNull String osSdkRoot, - @NonNull SdkManager sdkManager, - int parseFilter, - @NonNull ITaskMonitor monitor) { - ArrayList<Package> packages = new ArrayList<Package>(); - HashSet<File> visited = new HashSet<File>(); - - monitor.setProgressMax(10); - - File dir = null; - Package pkg = null; - - if ((parseFilter & PARSE_DOCS) != 0) { - dir = new File(osSdkRoot, SdkConstants.FD_DOCS); - pkg = scanDoc(dir, monitor); - if (pkg != null) { - packages.add(pkg); - visited.add(dir); - } - } - monitor.incProgress(1); - - if ((parseFilter & PARSE_TOOLS) != 0) { - dir = new File(osSdkRoot, SdkConstants.FD_TOOLS); - pkg = scanTools(dir, monitor); - if (pkg != null) { - packages.add(pkg); - visited.add(dir); - } - } - monitor.incProgress(1); - - if ((parseFilter & PARSE_PLATFORM_TOOLS) != 0) { - dir = new File(osSdkRoot, SdkConstants.FD_PLATFORM_TOOLS); - pkg = scanPlatformTools(dir, monitor); - if (pkg != null) { - packages.add(pkg); - visited.add(dir); - } - } - monitor.incProgress(1); - - // for platforms, add-ons and samples, rely on the SdkManager parser - if ((parseFilter & (PARSE_ADDONS | PARSE_PLATFORMS)) != 0) { - File samplesRoot = new File(osSdkRoot, SdkConstants.FD_SAMPLES); - - for(IAndroidTarget target : sdkManager.getTargets()) { - Properties props = parseProperties(new File(target.getLocation(), - SdkConstants.FN_SOURCE_PROP)); - - try { - pkg = null; - if (target.isPlatform() && (parseFilter & PARSE_PLATFORMS) != 0) { - pkg = PlatformPackage.create(target, props); - - if (samplesRoot.isDirectory()) { - // Get the samples dir for a platform if it is located in the new - // root /samples dir. We purposely ignore "old" samples that are - // located under the platform dir. - File samplesDir = new File(target.getPath(IAndroidTarget.SAMPLES)); - if (samplesDir.exists() && - samplesDir.getParentFile().equals(samplesRoot)) { - Properties samplesProps = parseProperties( - new File(samplesDir, SdkConstants.FN_SOURCE_PROP)); - if (samplesProps != null) { - Package pkg2 = SamplePackage.create(target, samplesProps); - packages.add(pkg2); - } - visited.add(samplesDir); - } - } - } else if ((parseFilter & PARSE_ADDONS) != 0) { - pkg = AddonPackage.create(target, props); - } - - if (pkg != null) { - for (ISystemImage systemImage : target.getSystemImages()) { - if (systemImage.getLocationType() == LocationType.IN_SYSTEM_IMAGE) { - File siDir = systemImage.getLocation(); - if (siDir.isDirectory()) { - Properties siProps = parseProperties( - new File(siDir, SdkConstants.FN_SOURCE_PROP)); - Package pkg2 = new SystemImagePackage( - target.getVersion(), - 0 /*rev*/, // this will use the one from siProps - systemImage.getAbiType(), - siProps, - siDir.getAbsolutePath()); - packages.add(pkg2); - visited.add(siDir); - } - } - } - } - - } catch (Exception e) { - monitor.error(e, null); - } - - if (pkg != null) { - packages.add(pkg); - visited.add(new File(target.getLocation())); - } - } - } - monitor.incProgress(1); - - if ((parseFilter & PARSE_PLATFORMS) != 0) { - scanMissingSystemImages(sdkManager, visited, packages, monitor); - } - monitor.incProgress(1); - if ((parseFilter & PARSE_ADDONS) != 0) { - scanMissingAddons(sdkManager, visited, packages, monitor); - } - monitor.incProgress(1); - if ((parseFilter & PARSE_SAMPLES) != 0) { - scanMissingSamples(sdkManager, visited, packages, monitor); - } - monitor.incProgress(1); - if ((parseFilter & PARSE_EXTRAS) != 0) { - scanExtras(sdkManager, visited, packages, monitor); - } - monitor.incProgress(1); - if ((parseFilter & PARSE_EXTRAS) != 0) { - scanExtrasDirectory(osSdkRoot, visited, packages, monitor); - } - monitor.incProgress(1); - if ((parseFilter & PARSE_SOURCES) != 0) { - scanSources(sdkManager, visited, packages, monitor); - } - monitor.incProgress(1); - - Collections.sort(packages); - - mPackages = packages.toArray(new Package[packages.size()]); - return mPackages; - } - - /** - * Find any directory in the /extras/vendors/path folders for extra packages. - * This isn't a recursive search. - */ - private void scanExtras(SdkManager sdkManager, - HashSet<File> visited, - ArrayList<Package> packages, - ILogger log) { - File root = new File(sdkManager.getLocation(), SdkConstants.FD_EXTRAS); - - if (!root.isDirectory()) { - // This should not happen. It makes listFiles() return null so let's avoid it. - return; - } - - for (File vendor : root.listFiles()) { - if (vendor.isDirectory()) { - scanExtrasDirectory(vendor.getAbsolutePath(), visited, packages, log); - } - } - } - - /** - * Find any other directory in the given "root" directory that hasn't been visited yet - * and assume they contain extra packages. This is <em>not</em> a recursive search. - */ - private void scanExtrasDirectory(String extrasRoot, - HashSet<File> visited, - ArrayList<Package> packages, - ILogger log) { - File root = new File(extrasRoot); - - if (!root.isDirectory()) { - // This should not happen. It makes listFiles() return null so let's avoid it. - return; - } - - for (File dir : root.listFiles()) { - if (dir.isDirectory() && !visited.contains(dir)) { - Properties props = parseProperties(new File(dir, SdkConstants.FN_SOURCE_PROP)); - if (props != null) { - try { - Package pkg = ExtraPackage.create( - null, //source - props, //properties - null, //vendor - dir.getName(), //path - 0, //revision - null, //license - null, //description - null, //descUrl - Os.getCurrentOs(), //archiveOs - Arch.getCurrentArch(), //archiveArch - dir.getPath() //archiveOsPath - ); - - packages.add(pkg); - visited.add(dir); - } catch (Exception e) { - log.error(e, null); - } - } - } - } - } - - /** - * Find any other sub-directories under the /samples root that hasn't been visited yet - * and assume they contain sample packages. This is <em>not</em> a recursive search. - * <p/> - * The use case is to find samples dirs under /samples when their target isn't loaded. - */ - private void scanMissingSamples(SdkManager sdkManager, - HashSet<File> visited, - ArrayList<Package> packages, - ILogger log) { - File root = new File(sdkManager.getLocation()); - root = new File(root, SdkConstants.FD_SAMPLES); - - if (!root.isDirectory()) { - // It makes listFiles() return null so let's avoid it. - return; - } - - for (File dir : root.listFiles()) { - if (dir.isDirectory() && !visited.contains(dir)) { - Properties props = parseProperties(new File(dir, SdkConstants.FN_SOURCE_PROP)); - if (props != null) { - try { - Package pkg = SamplePackage.create(dir.getAbsolutePath(), props); - packages.add(pkg); - visited.add(dir); - } catch (Exception e) { - log.error(e, null); - } - } - } - } - } - - /** - * The sdk manager only lists valid addons. However here we also want to find "broken" - * addons, i.e. addons that failed to load for some reason. - * <p/> - * Find any other sub-directories under the /add-ons root that hasn't been visited yet - * and assume they contain broken addons. - */ - private void scanMissingAddons(SdkManager sdkManager, - HashSet<File> visited, - ArrayList<Package> packages, - ILogger log) { - File addons = new File(new File(sdkManager.getLocation()), SdkConstants.FD_ADDONS); - - File[] files = addons.listFiles(); - if (files == null) { - return; - } - - for (File dir : files) { - if (dir.isDirectory() && !visited.contains(dir)) { - Pair<Map<String, String>, String> infos = - SdkManager.parseAddonProperties(dir, sdkManager.getTargets(), log); - Properties sourceProps = - parseProperties(new File(dir, SdkConstants.FN_SOURCE_PROP)); - - Map<String, String> addonProps = infos.getFirst(); - String error = infos.getSecond(); - try { - Package pkg = AddonPackage.createBroken(dir.getAbsolutePath(), - sourceProps, - addonProps, - error); - packages.add(pkg); - visited.add(dir); - } catch (Exception e) { - log.error(e, null); - } - } - } - } - - /** - * The sdk manager only lists valid system image via its addons or platform targets. - * However here we also want to find "broken" system images, that is system images - * that are located in the sdk/system-images folder but somehow not loaded properly. - */ - private void scanMissingSystemImages(SdkManager sdkManager, - HashSet<File> visited, - ArrayList<Package> packages, - ILogger log) { - File siRoot = new File(sdkManager.getLocation(), SdkConstants.FD_SYSTEM_IMAGES); - - File[] files = siRoot.listFiles(); - if (files == null) { - return; - } - - // The system-images folder contains a list of platform folders. - for (File platformDir : files) { - if (platformDir.isDirectory() && !visited.contains(platformDir)) { - visited.add(platformDir); - - // In the platform directory, we expect a list of abi folders - File[] platformFiles = platformDir.listFiles(); - if (platformFiles != null) { - for (File abiDir : platformFiles) { - if (abiDir.isDirectory() && !visited.contains(abiDir)) { - visited.add(abiDir); - - // Ignore empty directories - File[] abiFiles = abiDir.listFiles(); - if (abiFiles != null && abiFiles.length > 0) { - Properties props = - parseProperties(new File(abiDir, SdkConstants.FN_SOURCE_PROP)); - - try { - Package pkg = SystemImagePackage.createBroken(abiDir, props); - packages.add(pkg); - } catch (Exception e) { - log.error(e, null); - } - } - } - } - } - } - } - } - - /** - * Scan the sources/folders and register valid as well as broken source packages. - */ - private void scanSources(SdkManager sdkManager, - HashSet<File> visited, - ArrayList<Package> packages, - ILogger log) { - File srcRoot = new File(sdkManager.getLocation(), SdkConstants.FD_PKG_SOURCES); - - File[] subDirs = srcRoot.listFiles(); - if (subDirs == null) { - return; - } - - // The sources folder contains a list of platform folders. - for (File platformDir : subDirs) { - if (platformDir.isDirectory() && !visited.contains(platformDir)) { - visited.add(platformDir); - - // Ignore empty directories - File[] srcFiles = platformDir.listFiles(); - if (srcFiles != null && srcFiles.length > 0) { - Properties props = - parseProperties(new File(platformDir, SdkConstants.FN_SOURCE_PROP)); - - try { - Package pkg = SourcePackage.create(platformDir, props); - packages.add(pkg); - } catch (Exception e) { - log.error(e, null); - } - } - } - } - } - - /** - * Try to find a tools package at the given location. - * Returns null if not found. - */ - private Package scanTools(File toolFolder, ILogger log) { - // Can we find some properties? - Properties props = parseProperties(new File(toolFolder, SdkConstants.FN_SOURCE_PROP)); - - // We're not going to check that all tools are present. At the very least - // we should expect to find android and an emulator adapted to the current OS. - boolean hasEmulator = false; - boolean hasAndroid = false; - String android1 = SdkConstants.androidCmdName().replace(".bat", ".exe"); - String android2 = android1.indexOf('.') == -1 ? null : android1.replace(".exe", ".bat"); - File[] files = toolFolder.listFiles(); - if (files != null) { - for (File file : files) { - String name = file.getName(); - if (SdkConstants.FN_EMULATOR.equals(name)) { - hasEmulator = true; - } - if (android1.equals(name) || (android2 != null && android2.equals(name))) { - hasAndroid = true; - } - } - } - - if (!hasAndroid || !hasEmulator) { - return null; - } - - // Create our package. use the properties if we found any. - try { - Package pkg = ToolPackage.create( - null, //source - props, //properties - 0, //revision - null, //license - "Tools", //description - null, //descUrl - Os.getCurrentOs(), //archiveOs - Arch.getCurrentArch(), //archiveArch - toolFolder.getPath() //archiveOsPath - ); - - return pkg; - } catch (Exception e) { - log.error(e, null); - } - return null; - } - - /** - * Try to find a platform-tools package at the given location. - * Returns null if not found. - */ - private Package scanPlatformTools(File platformToolsFolder, ILogger log) { - // Can we find some properties? - Properties props = parseProperties(new File(platformToolsFolder, - SdkConstants.FN_SOURCE_PROP)); - - // We're not going to check that all tools are present. At the very least - // we should expect to find adb, aidl, aapt and dx (adapted to the current OS). - - if (platformToolsFolder.listFiles() == null) { - // ListFiles is null if the directory doesn't even exist. - // Not going to find anything in there... - return null; - } - - // Create our package. use the properties if we found any. - try { - Package pkg = PlatformToolPackage.create( - null, //source - props, //properties - 0, //revision - null, //license - "Platform Tools", //description - null, //descUrl - Os.getCurrentOs(), //archiveOs - Arch.getCurrentArch(), //archiveArch - platformToolsFolder.getPath() //archiveOsPath - ); - - return pkg; - } catch (Exception e) { - log.error(e, null); - } - return null; - } - - /** - * Try to find a docs package at the given location. - * Returns null if not found. - */ - private Package scanDoc(File docFolder, ILogger log) { - // Can we find some properties? - Properties props = parseProperties(new File(docFolder, SdkConstants.FN_SOURCE_PROP)); - - // To start with, a doc folder should have an "index.html" to be acceptable. - // We don't actually check the content of the file. - if (new File(docFolder, "index.html").isFile()) { - try { - Package pkg = DocPackage.create( - null, //source - props, //properties - 0, //apiLevel - null, //codename - 0, //revision - null, //license - null, //description - null, //descUrl - Os.getCurrentOs(), //archiveOs - Arch.getCurrentArch(), //archiveArch - docFolder.getPath() //archiveOsPath - ); - - return pkg; - } catch (Exception e) { - log.error(e, null); - } - } - - return null; - } - - /** - * Parses the given file as properties file if it exists. - * Returns null if the file does not exist, cannot be parsed or has no properties. - */ - private Properties parseProperties(File propsFile) { - FileInputStream fis = null; - try { - if (propsFile.exists()) { - fis = new FileInputStream(propsFile); - - Properties props = new Properties(); - props.load(fis); - - // To be valid, there must be at least one property in it. - if (props.size() > 0) { - return props; - } - } - - } catch (IOException e) { - e.printStackTrace(); - } finally { - if (fis != null) { - try { - fis.close(); - } catch (IOException e) { - } - } - } - return null; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/NullTaskMonitor.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/NullTaskMonitor.java deleted file mode 100755 index f69e37d..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/NullTaskMonitor.java +++ /dev/null @@ -1,134 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository; - -import com.android.annotations.NonNull; -import com.android.utils.ILogger; -import com.android.utils.NullLogger; - - -/** - * A no-op implementation of the {@link ITaskMonitor} interface. - * <p/> - * This can be passed to methods that require a monitor when the caller doesn't - * have any UI to update or means to report tracked progress. - * A custom {@link ILogger} is used. Clients could use {@link NullLogger} if - * they really don't care about the logging either. - */ -public class NullTaskMonitor implements ITaskMonitor { - - private final ILogger mLog; - - /** - * Creates a no-op {@link ITaskMonitor} that defers logging to the specified - * logger. - * <p/> - * This can be passed to methods that require a monitor when the caller doesn't - * have any UI to update or means to report tracked progress. - * - * @param log An {@link ILogger}. Must not be null. Consider using {@link NullLogger}. - */ - public NullTaskMonitor(ILogger log) { - mLog = log; - } - - @Override - public void setDescription(String format, Object...args) { - // pass - } - - @Override - public void log(String format, Object...args) { - mLog.info(format, args); - } - - @Override - public void logError(String format, Object...args) { - mLog.error(null /*throwable*/, format, args); - } - - @Override - public void logVerbose(String format, Object...args) { - mLog.verbose(format, args); - } - - @Override - public void setProgressMax(int max) { - // pass - } - - @Override - public int getProgressMax() { - return 0; - } - - @Override - public void incProgress(int delta) { - // pass - } - - /** Always return 1. */ - @Override - public int getProgress() { - return 1; - } - - /** Always return false. */ - @Override - public boolean isCancelRequested() { - return false; - } - - @Override - public ITaskMonitor createSubMonitor(int tickCount) { - return this; - } - - /** Always return false. */ - @Override - public boolean displayPrompt(final String title, final String message) { - return false; - } - - /** Always return null. */ - @Override - public UserCredentials displayLoginCredentialsPrompt(String title, String message) { - return null; - } - - // --- ILogger --- - - @Override - public void error(Throwable t, String errorFormat, Object... args) { - mLog.error(t, errorFormat, args); - } - - @Override - public void warning(@NonNull String warningFormat, Object... args) { - mLog.warning(warningFormat, args); - } - - @Override - public void info(@NonNull String msgFormat, Object... args) { - mLog.info(msgFormat, args); - } - - @Override - public void verbose(@NonNull String msgFormat, Object... args) { - mLog.verbose(msgFormat, args); - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/SdkStats.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/SdkStats.java deleted file mode 100755 index 0301b5e..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/SdkStats.java +++ /dev/null @@ -1,622 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository; - -import com.android.annotations.VisibleForTesting; -import com.android.annotations.VisibleForTesting.Visibility; -import com.android.sdklib.io.NonClosingInputStream; -import com.android.sdklib.io.NonClosingInputStream.CloseBehavior; -import com.android.sdklib.repository.SdkStatsConstants; -import com.android.sdklib.util.SparseArray; - -import org.w3c.dom.Document; -import org.w3c.dom.NamedNodeMap; -import org.w3c.dom.Node; -import org.xml.sax.ErrorHandler; -import org.xml.sax.InputSource; -import org.xml.sax.SAXException; -import org.xml.sax.SAXParseException; - -import java.io.FileNotFoundException; -import java.io.IOException; -import java.io.InputStream; -import java.net.UnknownHostException; -import java.util.regex.Matcher; -import java.util.regex.Pattern; - -import javax.net.ssl.SSLKeyException; -import javax.xml.XMLConstants; -import javax.xml.parsers.DocumentBuilder; -import javax.xml.parsers.DocumentBuilderFactory; -import javax.xml.parsers.ParserConfigurationException; -import javax.xml.transform.stream.StreamSource; -import javax.xml.validation.Schema; -import javax.xml.validation.SchemaFactory; -import javax.xml.validation.Validator; - - -/** - * Retrieves stats on platforms. - * <p/> - * This returns information stored on the repository in a different XML file - * and isn't directly tied to the existence of the listed platforms. - */ -public class SdkStats { - - public static class PlatformStatBase { - private final int mApiLevel; - private final String mVersionName; - private final String mCodeName; - private final float mShare; - - public PlatformStatBase(int apiLevel, - String versionName, - String codeName, - float share) { - mApiLevel = apiLevel; - mVersionName = versionName; - mCodeName = codeName; - mShare = share; - } - - /** The Android API Level for the platform. An int > 0. */ - public int getApiLevel() { - return mApiLevel; - } - - /** The official codename for this platform, for example "Cupcake". */ - public String getCodeName() { - return mCodeName; - } - - /** The official version name of this platform, for example "Android 1.5". */ - public String getVersionName() { - return mVersionName; - } - - /** An approximate share percentage of this platform and all the - * platforms of lower API level. */ - public float getShare() { - return mShare; - } - - /** Returns a string representation of this object, for debugging purposes. */ - @Override - public String toString() { - return String.format("api=%d, code=%s, vers=%s, share=%.1f%%", //$NON-NLS-1$ - mApiLevel, mCodeName, mVersionName, mShare); - } - } - - public static class PlatformStat extends PlatformStatBase { - private final float mAccumShare; - - public PlatformStat(int apiLevel, - String versionName, - String codeName, - float share, - float accumShare) { - super(apiLevel, versionName, codeName, share); - mAccumShare = accumShare; - } - - public PlatformStat(PlatformStatBase base, float accumShare) { - super(base.getApiLevel(), - base.getVersionName(), - base.getCodeName(), - base.getShare()); - mAccumShare = accumShare; - } - - /** The accumulated approximate share percentage of that platform. */ - public float getAccumShare() { - return mAccumShare; - } - - /** Returns a string representation of this object, for debugging purposes. */ - @Override - public String toString() { - return String.format("<Stat %s, accum=%.1f%%>", super.toString(), mAccumShare); - } - } - - private final SparseArray<PlatformStat> mStats = new SparseArray<SdkStats.PlatformStat>(); - - public SdkStats() { - } - - public SparseArray<PlatformStat> getStats() { - return mStats; - } - - public void load(DownloadCache cache, boolean forceHttp, ITaskMonitor monitor) { - - String url = SdkStatsConstants.URL_STATS; - - if (forceHttp) { - url = url.replaceAll("https://", "http://"); //$NON-NLS-1$ //$NON-NLS-2$ - } - - monitor.setProgressMax(5); - monitor.setDescription("Fetching %1$s", url); - monitor.incProgress(1); - - Exception[] exception = new Exception[] { null }; - Boolean[] validatorFound = new Boolean[] { Boolean.FALSE }; - String[] validationError = new String[] { null }; - Document validatedDoc = null; - String validatedUri = null; - - InputStream xml = fetchXmlUrl(url, cache, monitor.createSubMonitor(1), exception); - - if (xml != null) { - monitor.setDescription("Validate XML"); - - // Explore the XML to find the potential XML schema version - int version = getXmlSchemaVersion(xml); - - if (version >= 1 && version <= SdkStatsConstants.NS_LATEST_VERSION) { - // This should be a version we can handle. Try to validate it - // and report any error as invalid XML syntax, - - String uri = validateXml(xml, url, version, validationError, validatorFound); - if (uri != null) { - // Validation was successful - validatedDoc = getDocument(xml, monitor); - validatedUri = uri; - - } - } else if (version > SdkStatsConstants.NS_LATEST_VERSION) { - // The schema used is more recent than what is supported by this tool. - // We don't have an upgrade-path support yet, so simply ignore the document. - closeStream(xml); - return; - } - } - - // If any exception was handled during the URL fetch, display it now. - if (exception[0] != null) { - String reason = null; - if (exception[0] instanceof FileNotFoundException) { - // FNF has no useful getMessage, so we need to special handle it. - reason = "File not found"; - } else if (exception[0] instanceof UnknownHostException && - exception[0].getMessage() != null) { - // This has no useful getMessage yet could really use one - reason = String.format("Unknown Host %1$s", exception[0].getMessage()); - } else if (exception[0] instanceof SSLKeyException) { - // That's a common error and we have a pref for it. - reason = "HTTPS SSL error. You might want to force download through HTTP in the settings."; - } else if (exception[0].getMessage() != null) { - reason = exception[0].getMessage(); - } else { - // We don't know what's wrong. Let's give the exception class at least. - reason = String.format("Unknown (%1$s)", exception[0].getClass().getName()); - } - - monitor.logError("Failed to fetch URL %1$s, reason: %2$s", url, reason); - } - - if (validationError[0] != null) { - monitor.logError("%s", validationError[0]); //$NON-NLS-1$ - } - - // Stop here if we failed to validate the XML. We don't want to load it. - if (validatedDoc == null) { - closeStream(xml); - return; - } - - monitor.incProgress(1); - - if (xml != null) { - monitor.setDescription("Parse XML"); - monitor.incProgress(1); - parseStatsDocument(validatedDoc, validatedUri, monitor); - } - - // done - monitor.incProgress(1); - closeStream(xml); - } - - /** - * Fetches the document at the given URL and returns it as a stream. Returns - * null if anything wrong happens. - * - * @param urlString The URL to load, as a string. - * @param monitor {@link ITaskMonitor} related to this URL. - * @param outException If non null, where to store any exception that - * happens during the fetch. - * @see UrlOpener UrlOpener, which handles all URL logic. - */ - private InputStream fetchXmlUrl(String urlString, - DownloadCache cache, - ITaskMonitor monitor, - Exception[] outException) { - try { - InputStream xml = cache.openCachedUrl(urlString, monitor); - if (xml != null) { - xml.mark(500000); - xml = new NonClosingInputStream(xml); - ((NonClosingInputStream) xml).setCloseBehavior(CloseBehavior.RESET); - } - return xml; - } catch (Exception e) { - if (outException != null) { - outException[0] = e; - } - } - - return null; - } - - /** - * Closes the stream, ignore any exception from InputStream.close(). - * If the stream is a NonClosingInputStream, sets it to CloseBehavior.CLOSE first. - */ - private void closeStream(InputStream is) { - if (is != null) { - if (is instanceof NonClosingInputStream) { - ((NonClosingInputStream) is).setCloseBehavior(CloseBehavior.CLOSE); - } - try { - is.close(); - } catch (IOException ignore) {} - } - } - - /** - * Manually parses the root element of the XML to extract the schema version - * at the end of the xmlns:sdk="http://schemas.android.com/sdk/android/addons-list/$N" - * declaration. - * - * @return 1..{@link SdkStatsConstants#NS_LATEST_VERSION} for a valid schema version - * or 0 if no schema could be found. - */ - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected int getXmlSchemaVersion(InputStream xml) { - if (xml == null) { - return 0; - } - - // Get an XML document - Document doc = null; - try { - xml.reset(); - - DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance(); - factory.setIgnoringComments(false); - factory.setValidating(false); - - // Parse the old document using a non namespace aware builder - factory.setNamespaceAware(false); - DocumentBuilder builder = factory.newDocumentBuilder(); - - // We don't want the default handler which prints errors to stderr. - builder.setErrorHandler(new ErrorHandler() { - @Override - public void warning(SAXParseException e) throws SAXException { - // pass - } - @Override - public void fatalError(SAXParseException e) throws SAXException { - throw e; - } - @Override - public void error(SAXParseException e) throws SAXException { - throw e; - } - }); - - doc = builder.parse(xml); - - // Prepare a new document using a namespace aware builder - factory.setNamespaceAware(true); - builder = factory.newDocumentBuilder(); - - } catch (Exception e) { - // Failed to reset XML stream - // Failed to get builder factor - // Failed to create XML document builder - // Failed to parse XML document - // Failed to read XML document - } - - if (doc == null) { - return 0; - } - - // Check the root element is an XML with at least the following properties: - // <sdk:sdk-addons-list - // xmlns:sdk="http://schemas.android.com/sdk/android/addons-list/$N"> - // - // Note that we don't have namespace support enabled, we just do it manually. - - Pattern nsPattern = Pattern.compile(SdkStatsConstants.NS_PATTERN); - - String prefix = null; - for (Node child = doc.getFirstChild(); child != null; child = child.getNextSibling()) { - if (child.getNodeType() == Node.ELEMENT_NODE) { - prefix = null; - String name = child.getNodeName(); - int pos = name.indexOf(':'); - if (pos > 0 && pos < name.length() - 1) { - prefix = name.substring(0, pos); - name = name.substring(pos + 1); - } - if (SdkStatsConstants.NODE_SDK_STATS.equals(name)) { - NamedNodeMap attrs = child.getAttributes(); - String xmlns = "xmlns"; //$NON-NLS-1$ - if (prefix != null) { - xmlns += ":" + prefix; //$NON-NLS-1$ - } - Node attr = attrs.getNamedItem(xmlns); - if (attr != null) { - String uri = attr.getNodeValue(); - if (uri != null) { - Matcher m = nsPattern.matcher(uri); - if (m.matches()) { - String version = m.group(1); - try { - return Integer.parseInt(version); - } catch (NumberFormatException e) { - return 0; - } - } - } - } - } - } - } - - return 0; - } - - /** - * Validates this XML against one of the requested SDK Repository schemas. - * If the XML was correctly validated, returns the schema that worked. - * If it doesn't validate, returns null and stores the error in outError[0]. - * If we can't find a validator, returns null and set validatorFound[0] to false. - */ - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected String validateXml(InputStream xml, String url, int version, - String[] outError, Boolean[] validatorFound) { - - if (xml == null) { - return null; - } - - try { - Validator validator = getValidator(version); - - if (validator == null) { - validatorFound[0] = Boolean.FALSE; - outError[0] = String.format( - "XML verification failed for %1$s.\nNo suitable XML Schema Validator could be found in your Java environment. Please consider updating your version of Java.", - url); - return null; - } - - validatorFound[0] = Boolean.TRUE; - - // Reset the stream if it supports that operation. - xml.reset(); - - // Validation throws a bunch of possible Exceptions on failure. - validator.validate(new StreamSource(xml)); - return SdkStatsConstants.getSchemaUri(version); - - } catch (SAXParseException e) { - outError[0] = String.format( - "XML verification failed for %1$s.\nLine %2$d:%3$d, Error: %4$s", - url, - e.getLineNumber(), - e.getColumnNumber(), - e.toString()); - - } catch (Exception e) { - outError[0] = String.format( - "XML verification failed for %1$s.\nError: %2$s", - url, - e.toString()); - } - return null; - } - - /** - * Helper method that returns a validator for our XSD, or null if the current Java - * implementation can't process XSD schemas. - * - * @param version The version of the XML Schema. - * See {@link SdkStatsConstants#getXsdStream(int)} - */ - private Validator getValidator(int version) throws SAXException { - InputStream xsdStream = SdkStatsConstants.getXsdStream(version); - try { - SchemaFactory factory = SchemaFactory.newInstance(XMLConstants.W3C_XML_SCHEMA_NS_URI); - - if (factory == null) { - return null; - } - - // This may throw a SAX Exception if the schema itself is not a valid XSD - Schema schema = factory.newSchema(new StreamSource(xsdStream)); - - Validator validator = schema == null ? null : schema.newValidator(); - - return validator; - } finally { - if (xsdStream != null) { - try { - xsdStream.close(); - } catch (IOException ignore) {} - } - } - } - - /** - * Takes an XML document as a string as parameter and returns a DOM for it. - * - * On error, returns null and prints a (hopefully) useful message on the monitor. - */ - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected Document getDocument(InputStream xml, ITaskMonitor monitor) { - try { - DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance(); - factory.setIgnoringComments(true); - factory.setNamespaceAware(true); - - DocumentBuilder builder = factory.newDocumentBuilder(); - xml.reset(); - Document doc = builder.parse(new InputSource(xml)); - - return doc; - } catch (ParserConfigurationException e) { - monitor.logError("Failed to create XML document builder"); - - } catch (SAXException e) { - monitor.logError("Failed to parse XML document"); - - } catch (IOException e) { - monitor.logError("Failed to read XML document"); - } - - return null; - } - - /** - * Parses all valid platforms found in the XML. - * Changes the stats array returned by {@link #getStats()} - * (also returns the value directly, useful for unti tests.) - */ - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected SparseArray<PlatformStat> parseStatsDocument( - Document doc, - String nsUri, - ITaskMonitor monitor) { - - String baseUrl = System.getenv("SDK_TEST_BASE_URL"); //$NON-NLS-1$ - if (baseUrl != null) { - if (baseUrl.length() <= 0 || !baseUrl.endsWith("/")) { //$NON-NLS-1$ - baseUrl = null; - } - } - - SparseArray<PlatformStatBase> platforms = new SparseArray<SdkStats.PlatformStatBase>(); - int maxApi = 0; - - Node root = getFirstChild(doc, nsUri, SdkStatsConstants.NODE_SDK_STATS); - if (root != null) { - for (Node child = root.getFirstChild(); - child != null; - child = child.getNextSibling()) { - if (child.getNodeType() == Node.ELEMENT_NODE && - nsUri.equals(child.getNamespaceURI()) && - child.getLocalName().equals(SdkStatsConstants.NODE_PLATFORM)) { - - try { - Node node = getFirstChild(child, nsUri, SdkStatsConstants.NODE_API_LEVEL); - int apiLevel = Integer.parseInt(node.getTextContent().trim()); - - if (apiLevel < 1) { - // bad API level, ignore it. - continue; - } - - if (platforms.indexOfKey(apiLevel) >= 0) { - // if we already loaded that API, ignore duplicates - continue; - } - - String codeName = - getFirstChild(child, nsUri, SdkStatsConstants.NODE_CODENAME). - getTextContent().trim(); - String versName = - getFirstChild(child, nsUri, SdkStatsConstants.NODE_VERSION). - getTextContent().trim(); - - if (codeName == null || versName == null || - codeName.length() == 0 || versName.length() == 0) { - // bad names. ignore. - continue; - } - - node = getFirstChild(child, nsUri, SdkStatsConstants.NODE_SHARE); - float percent = Float.parseFloat(node.getTextContent().trim()); - - if (percent < 0 || percent > 100) { - // invalid percentage. ignore. - continue; - } - - PlatformStatBase p = new PlatformStatBase( - apiLevel, versName, codeName, percent); - platforms.put(apiLevel, p); - - maxApi = apiLevel > maxApi ? apiLevel : maxApi; - - } catch (Exception ignore) { - // Error parsing this platform. Ignore it. - continue; - } - } - } - } - - mStats.clear(); - - // Compute cumulative share percents & fill in final map - for (int api = 1; api <= maxApi; api++) { - PlatformStatBase p = platforms.get(api); - if (p == null) { - continue; - } - - float sum = p.getShare(); - for (int j = api + 1; j <= maxApi; j++) { - PlatformStatBase pj = platforms.get(j); - if (pj != null) { - sum += pj.getShare(); - } - } - - mStats.put(api, new PlatformStat(p, sum)); - } - - return mStats; - } - - /** - * Returns the first child element with the given XML local name. - * If xmlLocalName is null, returns the very first child element. - */ - private Node getFirstChild(Node node, String nsUri, String xmlLocalName) { - - for(Node child = node.getFirstChild(); child != null; child = child.getNextSibling()) { - if (child.getNodeType() == Node.ELEMENT_NODE && - nsUri.equals(child.getNamespaceURI())) { - if (xmlLocalName == null || child.getLocalName().equals(xmlLocalName)) { - return child; - } - } - } - - return null; - } - -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/UrlOpener.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/UrlOpener.java deleted file mode 100644 index 52724c7..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/UrlOpener.java +++ /dev/null @@ -1,523 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository; - -import com.android.annotations.NonNull; -import com.android.annotations.Nullable; -import com.android.utils.Pair; - -import org.apache.http.Header; -import org.apache.http.HttpEntity; -import org.apache.http.HttpResponse; -import org.apache.http.HttpStatus; -import org.apache.http.ProtocolVersion; -import org.apache.http.auth.AuthScope; -import org.apache.http.auth.AuthState; -import org.apache.http.auth.Credentials; -import org.apache.http.auth.NTCredentials; -import org.apache.http.auth.params.AuthPNames; -import org.apache.http.client.ClientProtocolException; -import org.apache.http.client.methods.HttpGet; -import org.apache.http.client.params.AuthPolicy; -import org.apache.http.client.protocol.ClientContext; -import org.apache.http.impl.client.DefaultHttpClient; -import org.apache.http.impl.conn.ProxySelectorRoutePlanner; -import org.apache.http.message.BasicHttpResponse; -import org.apache.http.params.BasicHttpParams; -import org.apache.http.params.HttpConnectionParams; -import org.apache.http.params.HttpParams; -import org.apache.http.protocol.BasicHttpContext; -import org.apache.http.protocol.HttpContext; - -import java.io.BufferedInputStream; -import java.io.ByteArrayInputStream; -import java.io.FileNotFoundException; -import java.io.FilterInputStream; -import java.io.IOException; -import java.io.InputStream; -import java.net.HttpURLConnection; -import java.net.Proxy; -import java.net.ProxySelector; -import java.net.URI; -import java.net.URL; -import java.net.URLConnection; -import java.net.UnknownHostException; -import java.util.ArrayList; -import java.util.Arrays; -import java.util.HashMap; -import java.util.List; -import java.util.Map; -import java.util.Map.Entry; -import java.util.Properties; - -/** - * This class holds static methods for downloading URL resources. - * @see #openUrl(String, boolean, ITaskMonitor, Header[]) - * <p/> - * Implementation detail: callers should use {@link DownloadCache} instead of this class. - * {@link DownloadCache#openDirectUrl} is a direct pass-through to {@link UrlOpener} since - * there's no caching. However from an implementation perspective it's still recommended - * to pass down a {@link DownloadCache} instance, which will let us override the implementation - * later on (for testing, for example.) - */ -class UrlOpener { - - private static final boolean DEBUG = - System.getenv("ANDROID_DEBUG_URL_OPENER") != null; //$NON-NLS-1$ - - private static Map<String, UserCredentials> sRealmCache = - new HashMap<String, UserCredentials>(); - - /** Timeout to establish a connection, in milliseconds. */ - private static int sConnectionTimeoutMs; - /** Timeout waiting for data on a socket, in milliseconds. */ - private static int sSocketTimeoutMs; - - static { - if (DEBUG) { - Properties props = System.getProperties(); - for (String key : new String[] { - "http.proxyHost", //$NON-NLS-1$ - "http.proxyPort", //$NON-NLS-1$ - "https.proxyHost", //$NON-NLS-1$ - "https.proxyPort" }) { //$NON-NLS-1$ - String prop = props.getProperty(key); - if (prop != null) { - System.out.printf( - "SdkLib.UrlOpener Java.Prop %s='%s'\n", //$NON-NLS-1$ - key, prop); - } - } - } - - try { - sConnectionTimeoutMs = Integer.parseInt(System.getenv("ANDROID_SDKMAN_CONN_TIMEOUT")); - } catch (Exception ignore) { - sConnectionTimeoutMs = 2 * 60 * 1000; - } - - try { - sSocketTimeoutMs = Integer.parseInt(System.getenv("ANDROID_SDKMAN_READ_TIMEOUT")); - } catch (Exception ignore) { - sSocketTimeoutMs = 1 * 60 * 1000; - } - } - - /** - * This class cannot be instantiated. - * @see #openUrl(String, boolean, ITaskMonitor, Header[]) - */ - private UrlOpener() { - } - - /** - * Opens a URL. It can be a simple URL or one which requires basic - * authentication. - * <p/> - * Tries to access the given URL. If http response is either - * {@code HttpStatus.SC_UNAUTHORIZED} or - * {@code HttpStatus.SC_PROXY_AUTHENTICATION_REQUIRED}, asks for - * login/password and tries to authenticate into proxy server and/or URL. - * <p/> - * This implementation relies on the Apache Http Client due to its - * capabilities of proxy/http authentication. <br/> - * Proxy configuration is determined by {@link ProxySelectorRoutePlanner} using the JVM proxy - * settings by default. - * <p/> - * For more information see: <br/> - * - {@code http://hc.apache.org/httpcomponents-client-ga/} <br/> - * - {@code http://hc.apache.org/httpcomponents-client-ga/httpclient/apidocs/org/apache/http/impl/conn/ProxySelectorRoutePlanner.html} - * <p/> - * There's a very simple realm cache implementation. - * Login/Password for each realm are stored in a static {@link Map}. - * Before asking the user the method verifies if the information is already - * available in the memory cache. - * - * @param url the URL string to be opened. - * @param needsMarkResetSupport Indicates the caller <em>must</em> have an input stream that - * supports the mark/reset operations (as indicated by {@link InputStream#markSupported()}. - * Implementation detail: If the original stream does not, it will be fetched and wrapped - * into a {@link ByteArrayInputStream}. This can only work sanely if the resource is a - * small file that can fit in memory. It also means the caller has no chance of showing - * a meaningful download progress. If unsure, callers should set this to false. - * @param monitor {@link ITaskMonitor} to output status. - * @param headers An optional array of HTTP headers to use in the GET request. - * @return Returns a {@link Pair} with {@code first} holding an {@link InputStream} - * and {@code second} holding an {@link HttpResponse}. - * The returned pair is never null and contains - * at least a code; for http requests that provide them the response - * also contains locale, headers and an status line. - * The input stream can be null, especially in case of error. - * The caller must only accept the stream if the response code is 200 or similar. - * @throws IOException Exception thrown when there are problems retrieving - * the URL or its content. - * @throws CanceledByUserException Exception thrown if the user cancels the - * authentication dialog. - */ - static @NonNull Pair<InputStream, HttpResponse> openUrl( - @NonNull String url, - boolean needsMarkResetSupport, - @NonNull ITaskMonitor monitor, - @Nullable Header[] headers) - throws IOException, CanceledByUserException { - - Exception fallbackOnJavaUrlConnect = null; - Pair<InputStream, HttpResponse> result = null; - - try { - result = openWithHttpClient(url, monitor, headers); - - } catch (UnknownHostException e) { - // Host in unknown. No need to even retry with the Url object, - // if it's broken, it's broken. It's already an IOException but - // it could use a better message. - throw new IOException("Unknown Host " + e.getMessage(), e); - - } catch (ClientProtocolException e) { - // We get this when HttpClient fails to accept the current protocol, - // e.g. when processing file:// URLs. - fallbackOnJavaUrlConnect = e; - - } catch (IOException e) { - throw e; - - } catch (CanceledByUserException e) { - // HTTP Basic Auth or NTLM login was canceled by user. - throw e; - - } catch (Exception e) { - if (DEBUG) { - System.out.printf("[HttpClient Error] %s : %s\n", url, e.toString()); - } - - fallbackOnJavaUrlConnect = e; - } - - if (fallbackOnJavaUrlConnect != null) { - // If the protocol is not supported by HttpClient (e.g. file:///), - // revert to the standard java.net.Url.open. - - try { - result = openWithUrl(url, headers); - } catch (IOException e) { - throw e; - } catch (Exception e) { - if (DEBUG && !fallbackOnJavaUrlConnect.equals(e)) { - System.out.printf("[Url Error] %s : %s\n", url, e.toString()); - } - } - } - - // If the caller requires an InputStream that supports mark/reset, let's - // make sure we have such a stream. - if (result != null && needsMarkResetSupport) { - InputStream is = result.getFirst(); - if (is != null) { - if (!is.markSupported()) { - try { - // Consume the whole input stream and offer a byte array stream instead. - // This can only work sanely if the resource is a small file that can - // fit in memory. It also means the caller has no chance of showing - // a meaningful download progress. - InputStream is2 = toByteArrayInputStream(is); - if (is2 != null) { - result = Pair.of(is2, result.getSecond()); - try { - is.close(); - } catch (Exception ignore) {} - } - } catch (Exception e3) { - // Ignore. If this can't work, caller will fail later. - } - } - } - } - - if (result == null) { - // Make up an error code if we don't have one already. - HttpResponse outResponse = new BasicHttpResponse( - new ProtocolVersion("HTTP", 1, 0), //$NON-NLS-1$ - HttpStatus.SC_METHOD_FAILURE, ""); //$NON-NLS-1$; // 420=Method Failure - result = Pair.of(null, outResponse); - } - - return result; - } - - // ByteArrayInputStream is the duct tape of input streams. - private static InputStream toByteArrayInputStream(InputStream is) throws IOException { - int inc = 4096; - int curr = 0; - byte[] result = new byte[inc]; - - int n; - while ((n = is.read(result, curr, result.length - curr)) != -1) { - curr += n; - if (curr == result.length) { - byte[] temp = new byte[curr + inc]; - System.arraycopy(result, 0, temp, 0, curr); - result = temp; - } - } - - return new ByteArrayInputStream(result, 0, curr); - } - - private static Pair<InputStream, HttpResponse> openWithUrl( - String url, - Header[] inHeaders) throws IOException { - URL u = new URL(url); - - URLConnection c = u.openConnection(); - - c.setConnectTimeout(sConnectionTimeoutMs); - c.setReadTimeout(sSocketTimeoutMs); - - if (inHeaders != null) { - for (Header header : inHeaders) { - c.setRequestProperty(header.getName(), header.getValue()); - } - } - - // Trigger the access to the resource - // (at which point setRequestProperty can't be used anymore.) - int code = 200; - - if (c instanceof HttpURLConnection) { - code = ((HttpURLConnection) c).getResponseCode(); - } - - // Get the input stream. That can fail for a file:// that doesn't exist - // in which case we set the response code to 404. - // Also we need a buffered input stream since the caller need to use is.reset(). - InputStream is = null; - try { - is = new BufferedInputStream(c.getInputStream()); - } catch (Exception ignore) { - if (is == null && code == 200) { - code = 404; - } - } - - HttpResponse outResponse = new BasicHttpResponse( - new ProtocolVersion(u.getProtocol(), 1, 0), // make up the protocol version - code, ""); //$NON-NLS-1$; - - Map<String, List<String>> outHeaderMap = c.getHeaderFields(); - - for (Entry<String, List<String>> entry : outHeaderMap.entrySet()) { - String name = entry.getKey(); - if (name != null) { - List<String> values = entry.getValue(); - if (!values.isEmpty()) { - outResponse.setHeader(name, values.get(0)); - } - } - } - - return Pair.of(is, outResponse); - } - - private static @NonNull Pair<InputStream, HttpResponse> openWithHttpClient( - @NonNull String url, - @NonNull ITaskMonitor monitor, - Header[] inHeaders) - throws IOException, ClientProtocolException, CanceledByUserException { - UserCredentials result = null; - String realm = null; - - HttpParams params = new BasicHttpParams(); - HttpConnectionParams.setConnectionTimeout(params, sConnectionTimeoutMs); - HttpConnectionParams.setSoTimeout(params, sSocketTimeoutMs); - - // use the simple one - final DefaultHttpClient httpClient = new DefaultHttpClient(params); - - - // create local execution context - HttpContext localContext = new BasicHttpContext(); - final HttpGet httpGet = new HttpGet(url); - if (inHeaders != null) { - for (Header header : inHeaders) { - httpGet.addHeader(header); - } - } - - // retrieve local java configured network in case there is the need to - // authenticate a proxy - ProxySelectorRoutePlanner routePlanner = new ProxySelectorRoutePlanner( - httpClient.getConnectionManager().getSchemeRegistry(), - ProxySelector.getDefault()); - httpClient.setRoutePlanner(routePlanner); - - // Set preference order for authentication options. - // In particular, we don't add AuthPolicy.SPNEGO, which is given preference over NTLM in - // servers that support both, as it is more secure. However, we don't seem to handle it - // very well, so we leave it off the list. - // See http://hc.apache.org/httpcomponents-client-ga/tutorial/html/authentication.html for - // more info. - List<String> authpref = new ArrayList<String>(); - authpref.add(AuthPolicy.BASIC); - authpref.add(AuthPolicy.DIGEST); - authpref.add(AuthPolicy.NTLM); - httpClient.getParams().setParameter(AuthPNames.PROXY_AUTH_PREF, authpref); - httpClient.getParams().setParameter(AuthPNames.TARGET_AUTH_PREF, authpref); - - if (DEBUG) { - try { - URI uri = new URI(url); - ProxySelector sel = routePlanner.getProxySelector(); - if (sel != null && uri.getScheme().startsWith("httP")) { //$NON-NLS-1$ - List<Proxy> list = sel.select(uri); - System.out.printf( - "SdkLib.UrlOpener:\n Connect to: %s\n Proxy List: %s\n", //$NON-NLS-1$ - url, - list == null ? "(null)" : Arrays.toString(list.toArray()));//$NON-NLS-1$ - } - } catch (Exception e) { - System.out.printf( - "SdkLib.UrlOpener: Failed to get proxy info for %s: %s\n", //$NON-NLS-1$ - url, e.toString()); - } - } - - boolean trying = true; - // loop while the response is being fetched - while (trying) { - // connect and get status code - HttpResponse response = httpClient.execute(httpGet, localContext); - int statusCode = response.getStatusLine().getStatusCode(); - - if (DEBUG) { - System.out.printf(" Status: %d\n", statusCode); //$NON-NLS-1$ - } - - // check whether any authentication is required - AuthState authenticationState = null; - if (statusCode == HttpStatus.SC_UNAUTHORIZED) { - // Target host authentication required - authenticationState = (AuthState) localContext - .getAttribute(ClientContext.TARGET_AUTH_STATE); - } - if (statusCode == HttpStatus.SC_PROXY_AUTHENTICATION_REQUIRED) { - // Proxy authentication required - authenticationState = (AuthState) localContext - .getAttribute(ClientContext.PROXY_AUTH_STATE); - } - if (statusCode == HttpStatus.SC_OK || statusCode == HttpStatus.SC_NOT_MODIFIED) { - // in case the status is OK and there is a realm and result, - // cache it - if (realm != null && result != null) { - sRealmCache.put(realm, result); - } - } - - // there is the need for authentication - if (authenticationState != null) { - - // get scope and realm - AuthScope authScope = authenticationState.getAuthScope(); - - // If the current realm is different from the last one it means - // a pass was performed successfully to the last URL, therefore - // cache the last realm - if (realm != null && !realm.equals(authScope.getRealm())) { - sRealmCache.put(realm, result); - } - - realm = authScope.getRealm(); - - // in case there is cache for this Realm, use it to authenticate - if (sRealmCache.containsKey(realm)) { - result = sRealmCache.get(realm); - } else { - // since there is no cache, request for login and password - result = monitor.displayLoginCredentialsPrompt("Site Authentication", - "Please login to the following domain: " + realm + - "\n\nServer requiring authentication:\n" + authScope.getHost()); - if (result == null) { - throw new CanceledByUserException("User canceled login dialog."); - } - } - - // retrieve authentication data - String user = result.getUserName(); - String password = result.getPassword(); - String workstation = result.getWorkstation(); - String domain = result.getDomain(); - - // proceed in case there is indeed a user - if (user != null && user.length() > 0) { - Credentials credentials = new NTCredentials(user, password, - workstation, domain); - httpClient.getCredentialsProvider().setCredentials(authScope, credentials); - trying = true; - } else { - trying = false; - } - } else { - trying = false; - } - - HttpEntity entity = response.getEntity(); - - if (entity != null) { - if (trying) { - // in case another pass to the Http Client will be performed, close the entity. - entity.getContent().close(); - } else { - // since no pass to the Http Client is needed, retrieve the - // entity's content. - - // Note: don't use something like a BufferedHttpEntity since it would consume - // all content and store it in memory, resulting in an OutOfMemory exception - // on a large download. - InputStream is = new FilterInputStream(entity.getContent()) { - @Override - public void close() throws IOException { - // Since Http Client is no longer needed, close it. - - // Bug #21167: we need to tell http client to shutdown - // first, otherwise the super.close() would continue - // downloading and not return till complete. - - httpClient.getConnectionManager().shutdown(); - super.close(); - } - }; - - HttpResponse outResponse = new BasicHttpResponse(response.getStatusLine()); - outResponse.setHeaders(response.getAllHeaders()); - outResponse.setLocale(response.getLocale()); - - return Pair.of(is, outResponse); - } - } else if (statusCode == HttpStatus.SC_NOT_MODIFIED) { - // It's ok to not have an entity (e.g. nothing to download) for a 304 - HttpResponse outResponse = new BasicHttpResponse(response.getStatusLine()); - outResponse.setHeaders(response.getAllHeaders()); - outResponse.setLocale(response.getLocale()); - - return Pair.of(null, outResponse); - } - } - - // We get here if we did not succeed. Callers do not expect a null result. - httpClient.getConnectionManager().shutdown(); - throw new FileNotFoundException(url); - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/UserCredentials.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/UserCredentials.java deleted file mode 100644 index 16aed79..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/UserCredentials.java +++ /dev/null @@ -1,47 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository; - -public class UserCredentials { - private final String mUserName; - private final String mPassword; - private final String mWorkstation; - private final String mDomain; - - public UserCredentials(String userName, String password, String workstation, String domain) { - mUserName = userName; - mPassword = password; - mWorkstation = workstation; - mDomain = domain; - } - - public String getUserName() { - return mUserName; - } - - public String getPassword() { - return mPassword; - } - - public String getWorkstation() { - return mWorkstation; - } - - public String getDomain() { - return mDomain; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/archives/Archive.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/archives/Archive.java deleted file mode 100755 index 508911f..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/archives/Archive.java +++ /dev/null @@ -1,504 +0,0 @@ -/* - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.archives; - -import com.android.annotations.VisibleForTesting; -import com.android.annotations.VisibleForTesting.Visibility; -import com.android.sdklib.internal.repository.IDescription; -import com.android.sdklib.internal.repository.packages.Package; -import com.android.sdklib.internal.repository.sources.SdkSource; -import com.android.sdklib.io.FileOp; - -import java.io.File; -import java.security.MessageDigest; -import java.security.NoSuchAlgorithmException; -import java.util.Locale; -import java.util.Properties; - - -/** - * A {@link Archive} is the base class for "something" that can be downloaded from - * the SDK repository. - * <p/> - * A package has some attributes (revision, description) and a list of archives - * which represent the downloadable bits. - * <p/> - * Packages are offered by a {@link SdkSource} (a download site). - * The {@link ArchiveInstaller} takes care of downloading, unpacking and installing an archive. - */ -public class Archive implements IDescription, Comparable<Archive> { - - private static final String PROP_OS = "Archive.Os"; //$NON-NLS-1$ - private static final String PROP_ARCH = "Archive.Arch"; //$NON-NLS-1$ - - /** The checksum type. */ - public enum ChecksumType { - /** A SHA1 checksum, represented as a 40-hex string. */ - SHA1("SHA-1"); //$NON-NLS-1$ - - private final String mAlgorithmName; - - /** - * Constructs a {@link ChecksumType} with the algorigth name - * suitable for {@link MessageDigest#getInstance(String)}. - * <p/> - * These names are officially documented at - * http://java.sun.com/javase/6/docs/technotes/guides/security/StandardNames.html#MessageDigest - */ - private ChecksumType(String algorithmName) { - mAlgorithmName = algorithmName; - } - - /** - * Returns a new {@link MessageDigest} instance for this checksum type. - * @throws NoSuchAlgorithmException if this algorithm is not available. - */ - public MessageDigest getMessageDigest() throws NoSuchAlgorithmException { - return MessageDigest.getInstance(mAlgorithmName); - } - } - - /** The OS that this archive can be downloaded on. */ - public enum Os { - ANY("Any"), - LINUX("Linux"), - MACOSX("MacOS X"), - WINDOWS("Windows"); - - private final String mUiName; - - private Os(String uiName) { - mUiName = uiName; - } - - /** Returns the UI name of the OS. */ - public String getUiName() { - return mUiName; - } - - /** Returns the XML name of the OS. */ - public String getXmlName() { - return toString().toLowerCase(Locale.US); - } - - /** - * Returns the current OS as one of the {@link Os} enum values or null. - */ - public static Os getCurrentOs() { - String os = System.getProperty("os.name"); //$NON-NLS-1$ - if (os.startsWith("Mac")) { //$NON-NLS-1$ - return Os.MACOSX; - - } else if (os.startsWith("Windows")) { //$NON-NLS-1$ - return Os.WINDOWS; - - } else if (os.startsWith("Linux")) { //$NON-NLS-1$ - return Os.LINUX; - } - - return null; - } - - /** Returns true if this OS is compatible with the current one. */ - public boolean isCompatible() { - if (this == ANY) { - return true; - } - - Os os = getCurrentOs(); - return this == os; - } - } - - /** The Architecture that this archive can be downloaded on. */ - public enum Arch { - ANY("Any"), - PPC("PowerPC"), - X86("x86"), - X86_64("x86_64"); - - private final String mUiName; - - private Arch(String uiName) { - mUiName = uiName; - } - - /** Returns the UI name of the architecture. */ - public String getUiName() { - return mUiName; - } - - /** Returns the XML name of the architecture. */ - public String getXmlName() { - return toString().toLowerCase(Locale.US); - } - - /** - * Returns the current architecture as one of the {@link Arch} enum values or null. - */ - public static Arch getCurrentArch() { - // Values listed from http://lopica.sourceforge.net/os.html - String arch = System.getProperty("os.arch"); - - if (arch.equalsIgnoreCase("x86_64") || arch.equalsIgnoreCase("amd64")) { - return Arch.X86_64; - - } else if (arch.equalsIgnoreCase("x86") - || arch.equalsIgnoreCase("i386") - || arch.equalsIgnoreCase("i686")) { - return Arch.X86; - - } else if (arch.equalsIgnoreCase("ppc") || arch.equalsIgnoreCase("PowerPC")) { - return Arch.PPC; - } - - return null; - } - - /** Returns true if this architecture is compatible with the current one. */ - public boolean isCompatible() { - if (this == ANY) { - return true; - } - - Arch arch = getCurrentArch(); - return this == arch; - } - } - - private final Os mOs; - private final Arch mArch; - private final String mUrl; - private final long mSize; - private final String mChecksum; - private final ChecksumType mChecksumType = ChecksumType.SHA1; - private final Package mPackage; - private final String mLocalOsPath; - private final boolean mIsLocal; - - /** - * Creates a new remote archive. - */ - public Archive(Package pkg, Os os, Arch arch, String url, long size, String checksum) { - mPackage = pkg; - mOs = os; - mArch = arch; - mUrl = url == null ? null : url.trim(); - mLocalOsPath = null; - mSize = size; - mChecksum = checksum; - mIsLocal = false; - } - - /** - * Creates a new local archive. - * Uses the properties from props first, if possible. Props can be null. - */ - @VisibleForTesting(visibility=Visibility.PACKAGE) - public Archive(Package pkg, Properties props, Os os, Arch arch, String localOsPath) { - mPackage = pkg; - - mOs = props == null ? os : Os.valueOf( props.getProperty(PROP_OS, os.toString())); - mArch = props == null ? arch : Arch.valueOf(props.getProperty(PROP_ARCH, arch.toString())); - - mUrl = null; - mLocalOsPath = localOsPath; - mSize = 0; - mChecksum = ""; - mIsLocal = localOsPath != null; - } - - /** - * Save the properties of the current archive in the give {@link Properties} object. - * These properties will later be give the constructor that takes a {@link Properties} object. - */ - void saveProperties(Properties props) { - props.setProperty(PROP_OS, mOs.toString()); - props.setProperty(PROP_ARCH, mArch.toString()); - } - - /** - * Returns true if this is a locally installed archive. - * Returns false if this is a remote archive that needs to be downloaded. - */ - public boolean isLocal() { - return mIsLocal; - } - - /** - * Returns the package that created and owns this archive. - * It should generally not be null. - */ - public Package getParentPackage() { - return mPackage; - } - - /** - * Returns the archive size, an int > 0. - * Size will be 0 if this a local installed folder of unknown size. - */ - public long getSize() { - return mSize; - } - - /** - * Returns the SHA1 archive checksum, as a 40-char hex. - * Can be empty but not null for local installed folders. - */ - public String getChecksum() { - return mChecksum; - } - - /** - * Returns the checksum type, always {@link ChecksumType#SHA1} right now. - */ - public ChecksumType getChecksumType() { - return mChecksumType; - } - - /** - * Returns the download archive URL, either absolute or relative to the repository xml. - * Always return null for a local installed folder. - * @see #getLocalOsPath() - */ - public String getUrl() { - return mUrl; - } - - /** - * Returns the local OS folder where a local archive is installed. - * Always return null for remote archives. - * @see #getUrl() - */ - public String getLocalOsPath() { - return mLocalOsPath; - } - - /** - * Returns the archive {@link Os} enum. - * Can be null for a local installed folder on an unknown OS. - */ - public Os getOs() { - return mOs; - } - - /** - * Returns the archive {@link Arch} enum. - * Can be null for a local installed folder on an unknown architecture. - */ - public Arch getArch() { - return mArch; - } - - /** - * Generates a description for this archive of the OS/Arch supported by this archive. - */ - public String getOsDescription() { - String os; - if (mOs == null) { - os = "unknown OS"; - } else if (mOs == Os.ANY) { - os = "any OS"; - } else { - os = mOs.getUiName(); - } - - String arch = ""; //$NON-NLS-1$ - if (mArch != null && mArch != Arch.ANY) { - arch = mArch.getUiName(); - } - - return String.format("%1$s%2$s%3$s", - os, - arch.length() > 0 ? " " : "", //$NON-NLS-2$ - arch); - } - - /** - * Returns the short description of the source, if not null. - * Otherwise returns the default Object toString result. - * <p/> - * This is mostly helpful for debugging. - * For UI display, use the {@link IDescription} interface. - */ - @Override - public String toString() { - String s = getShortDescription(); - if (s != null) { - return s; - } - return super.toString(); - } - - /** - * Generates a short description for this archive. - */ - @Override - public String getShortDescription() { - return String.format("Archive for %1$s", getOsDescription()); - } - - /** - * Generates a longer description for this archive. - */ - @Override - public String getLongDescription() { - return String.format("%1$s\n%2$s\n%3$s", - getShortDescription(), - getSizeDescription(), - getSha1Description()); - } - - public String getSizeDescription() { - long size = getSize(); - String sizeStr; - if (size < 1024) { - sizeStr = String.format("%d Bytes", size); - } else if (size < 1024 * 1024) { - sizeStr = String.format("%d KiB", Math.round(size / 1024.0)); - } else if (size < 1024 * 1024 * 1024) { - sizeStr = String.format("%.1f MiB", - Math.round(10.0 * size / (1024 * 1024.0))/ 10.0); - } else { - sizeStr = String.format("%.1f GiB", - Math.round(10.0 * size / (1024 * 1024 * 1024.0))/ 10.0); - } - - return String.format("Size: %1$s", sizeStr); - } - - public String getSha1Description() { - return String.format("SHA1: %1$s", getChecksum()); - } - - /** - * Returns true if this archive can be installed on the current platform. - */ - public boolean isCompatible() { - return getOs().isCompatible() && getArch().isCompatible(); - } - - /** - * Delete the archive folder if this is a local archive. - */ - public void deleteLocal() { - if (isLocal()) { - new FileOp().deleteFileOrFolder(new File(getLocalOsPath())); - } - } - - /** - * Archives are compared using their {@link Package} ordering. - * - * @see Package#compareTo(Package) - */ - @Override - public int compareTo(Archive rhs) { - if (mPackage != null && rhs != null) { - return mPackage.compareTo(rhs.getParentPackage()); - } - return 0; - } - - /** - * Note: An {@link Archive}'s hash code does NOT depend on the parent {@link Package} hash code. - * <p/> - * {@inheritDoc} - */ - @Override - public int hashCode() { - final int prime = 31; - int result = 1; - result = prime * result + ((mArch == null) ? 0 : mArch.hashCode()); - result = prime * result + ((mChecksum == null) ? 0 : mChecksum.hashCode()); - result = prime * result + ((mChecksumType == null) ? 0 : mChecksumType.hashCode()); - result = prime * result + (mIsLocal ? 1231 : 1237); - result = prime * result + ((mLocalOsPath == null) ? 0 : mLocalOsPath.hashCode()); - result = prime * result + ((mOs == null) ? 0 : mOs.hashCode()); - result = prime * result + (int) (mSize ^ (mSize >>> 32)); - result = prime * result + ((mUrl == null) ? 0 : mUrl.hashCode()); - return result; - } - - /** - * Note: An {@link Archive}'s equality does NOT depend on the parent {@link Package} equality. - * <p/> - * {@inheritDoc} - */ - @Override - public boolean equals(Object obj) { - if (this == obj) { - return true; - } - if (obj == null) { - return false; - } - if (!(obj instanceof Archive)) { - return false; - } - Archive other = (Archive) obj; - if (mArch == null) { - if (other.mArch != null) { - return false; - } - } else if (!mArch.equals(other.mArch)) { - return false; - } - if (mChecksum == null) { - if (other.mChecksum != null) { - return false; - } - } else if (!mChecksum.equals(other.mChecksum)) { - return false; - } - if (mChecksumType == null) { - if (other.mChecksumType != null) { - return false; - } - } else if (!mChecksumType.equals(other.mChecksumType)) { - return false; - } - if (mIsLocal != other.mIsLocal) { - return false; - } - if (mLocalOsPath == null) { - if (other.mLocalOsPath != null) { - return false; - } - } else if (!mLocalOsPath.equals(other.mLocalOsPath)) { - return false; - } - if (mOs == null) { - if (other.mOs != null) { - return false; - } - } else if (!mOs.equals(other.mOs)) { - return false; - } - if (mSize != other.mSize) { - return false; - } - if (mUrl == null) { - if (other.mUrl != null) { - return false; - } - } else if (!mUrl.equals(other.mUrl)) { - return false; - } - return true; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/archives/ArchiveInstaller.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/archives/ArchiveInstaller.java deleted file mode 100755 index 75e8912..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/archives/ArchiveInstaller.java +++ /dev/null @@ -1,1167 +0,0 @@ -/* - * Copyright (C) 2010 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.archives; - -import com.android.SdkConstants; -import com.android.annotations.Nullable; -import com.android.annotations.VisibleForTesting; -import com.android.annotations.VisibleForTesting.Visibility; -import com.android.sdklib.SdkManager; -import com.android.sdklib.internal.repository.CanceledByUserException; -import com.android.sdklib.internal.repository.DownloadCache; -import com.android.sdklib.internal.repository.ITaskMonitor; -import com.android.sdklib.internal.repository.packages.Package; -import com.android.sdklib.internal.repository.sources.SdkSource; -import com.android.sdklib.io.FileOp; -import com.android.sdklib.io.IFileOp; -import com.android.sdklib.repository.RepoConstants; -import com.android.sdklib.util.GrabProcessOutput; -import com.android.sdklib.util.GrabProcessOutput.IProcessOutput; -import com.android.sdklib.util.GrabProcessOutput.Wait; -import com.android.utils.Pair; - -import org.apache.commons.compress.archivers.zip.ZipArchiveEntry; -import org.apache.commons.compress.archivers.zip.ZipFile; -import org.apache.http.Header; -import org.apache.http.HttpHeaders; -import org.apache.http.HttpResponse; -import org.apache.http.HttpStatus; -import org.apache.http.message.BasicHeader; - -import java.io.EOFException; -import java.io.File; -import java.io.FileInputStream; -import java.io.FileNotFoundException; -import java.io.FileOutputStream; -import java.io.IOException; -import java.io.InputStream; -import java.security.MessageDigest; -import java.security.NoSuchAlgorithmException; -import java.util.ArrayList; -import java.util.Arrays; -import java.util.Enumeration; -import java.util.HashSet; -import java.util.List; -import java.util.Properties; -import java.util.Set; -import java.util.TreeSet; -import java.util.regex.Pattern; - -/** - * Performs the work of installing a given {@link Archive}. - */ -public class ArchiveInstaller { - - private static final String PROP_STATUS_CODE = "StatusCode"; //$NON-NLS-1$ - public static final String ENV_VAR_IGNORE_COMPAT = "ANDROID_SDK_IGNORE_COMPAT"; //$NON-NLS-1$ - - public static final int NUM_MONITOR_INC = 100; - - /** The current {@link FileOp} to use. Never null. */ - private final IFileOp mFileOp; - - /** - * Generates an {@link ArchiveInstaller} that relies on the default {@link FileOp}. - */ - public ArchiveInstaller() { - mFileOp = new FileOp(); - } - - /** - * Generates an {@link ArchiveInstaller} that relies on the given {@link FileOp}. - * - * @param fileUtils An alternate version of {@link FileOp} to use for file operations. - */ - protected ArchiveInstaller(IFileOp fileUtils) { - mFileOp = fileUtils; - } - - /** Returns current {@link FileOp} to use. Never null. */ - protected IFileOp getFileOp() { - return mFileOp; - } - - /** - * Install this {@link ArchiveReplacement}s. - * A "replacement" is composed of the actual new archive to install - * (c.f. {@link ArchiveReplacement#getNewArchive()} and an <em>optional</em> - * archive being replaced (c.f. {@link ArchiveReplacement#getReplaced()}. - * In the case of a new install, the later should be null. - * <p/> - * The new archive to install will be skipped if it is incompatible. - * - * @return True if the archive was installed, false otherwise. - */ - public boolean install(ArchiveReplacement archiveInfo, - String osSdkRoot, - boolean forceHttp, - SdkManager sdkManager, - DownloadCache cache, - ITaskMonitor monitor) { - - Archive newArchive = archiveInfo.getNewArchive(); - Package pkg = newArchive.getParentPackage(); - - String name = pkg.getShortDescription(); - - if (newArchive.isLocal()) { - // This should never happen. - monitor.log("Skipping already installed archive: %1$s for %2$s", - name, - newArchive.getOsDescription()); - return false; - } - - // In detail mode, give us a way to force install of incompatible archives. - boolean checkIsCompatible = System.getenv(ENV_VAR_IGNORE_COMPAT) == null; - - if (checkIsCompatible && !newArchive.isCompatible()) { - monitor.log("Skipping incompatible archive: %1$s for %2$s", - name, - newArchive.getOsDescription()); - return false; - } - - Pair<File, File> files = downloadFile(newArchive, osSdkRoot, cache, monitor, forceHttp); - File tmpFile = files == null ? null : files.getFirst(); - File propsFile = files == null ? null : files.getSecond(); - if (tmpFile != null) { - // Unarchive calls the pre/postInstallHook methods. - if (unarchive(archiveInfo, osSdkRoot, tmpFile, sdkManager, monitor)) { - monitor.log("Installed %1$s", name); - // Delete the temp archive if it exists, only on success - mFileOp.deleteFileOrFolder(tmpFile); - mFileOp.deleteFileOrFolder(propsFile); - return true; - } - } - - return false; - } - - /** - * Downloads an archive and returns the temp file with it. - * Caller is responsible with deleting the temp file when done. - */ - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected Pair<File, File> downloadFile(Archive archive, - String osSdkRoot, - DownloadCache cache, - ITaskMonitor monitor, - boolean forceHttp) { - - String pkgName = archive.getParentPackage().getShortDescription(); - monitor.setDescription("Downloading %1$s", pkgName); - monitor.log("Downloading %1$s", pkgName); - - String link = archive.getUrl(); - if (!link.startsWith("http://") //$NON-NLS-1$ - && !link.startsWith("https://") //$NON-NLS-1$ - && !link.startsWith("ftp://")) { //$NON-NLS-1$ - // Make the URL absolute by prepending the source - Package pkg = archive.getParentPackage(); - SdkSource src = pkg.getParentSource(); - if (src == null) { - monitor.logError("Internal error: no source for archive %1$s", pkgName); - return null; - } - - // take the URL to the repository.xml and remove the last component - // to get the base - String repoXml = src.getUrl(); - int pos = repoXml.lastIndexOf('/'); - String base = repoXml.substring(0, pos + 1); - - link = base + link; - } - - if (forceHttp) { - link = link.replaceAll("https://", "http://"); //$NON-NLS-1$ //$NON-NLS-2$ - } - - // Get the basename of the file we're downloading, i.e. the last component - // of the URL - int pos = link.lastIndexOf('/'); - String base = link.substring(pos + 1); - - // Rather than create a real temp file in the system, we simply use our - // temp folder (in the SDK base folder) and use the archive name for the - // download. This allows us to reuse or continue downloads. - - File tmpFolder = getTempFolder(osSdkRoot); - if (!mFileOp.isDirectory(tmpFolder)) { - if (mFileOp.isFile(tmpFolder)) { - mFileOp.deleteFileOrFolder(tmpFolder); - } - if (!mFileOp.mkdirs(tmpFolder)) { - monitor.logError("Failed to create directory %1$s", tmpFolder.getPath()); - return null; - } - } - File tmpFile = new File(tmpFolder, base); - - // property file were we'll keep partial/resume information for reuse. - File propsFile = new File(tmpFolder, base + ".inf"); //$NON-NLS-1$ - - // if the file exists, check its checksum & size. Use it if complete - if (mFileOp.exists(tmpFile)) { - if (mFileOp.length(tmpFile) == archive.getSize()) { - String chksum = ""; //$NON-NLS-1$ - try { - chksum = fileChecksum(archive.getChecksumType().getMessageDigest(), - tmpFile, - monitor); - } catch (NoSuchAlgorithmException e) { - // Ignore. - } - if (chksum.equalsIgnoreCase(archive.getChecksum())) { - // File is good, let's use it. - return Pair.of(tmpFile, propsFile); - } else { - // The file has the right size but the wrong content. - // Just remove it and this will trigger a full download below. - mFileOp.deleteFileOrFolder(tmpFile); - } - } - } - - Header[] resumeHeaders = preparePartialDownload(archive, tmpFile, propsFile); - - if (fetchUrl(archive, resumeHeaders, tmpFile, propsFile, link, pkgName, cache, monitor)) { - // Fetching was successful, let's use this file. - return Pair.of(tmpFile, propsFile); - } - return null; - } - - /** - * Prepares to do a partial/resume download. - * - * @param archive The archive we're trying to download. - * @param tmpFile The destination file to download (e.g. something.zip) - * @param propsFile A properties file generated by the last partial download (e.g. .zip.inf) - * @return Null in case we should perform a full download, or a set of headers - * to resume a partial download. - */ - private Header[] preparePartialDownload(Archive archive, File tmpFile, File propsFile) { - // We need both the destination file and its properties to do a resume. - if (mFileOp.isFile(tmpFile) && mFileOp.isFile(propsFile)) { - // The caller already checked the case were the destination file has the - // right size _and_ checksum, so we know at this point one of them is wrong - // here. - // We can obviously only resume a file if its size is smaller than expected. - if (mFileOp.length(tmpFile) < archive.getSize()) { - Properties props = mFileOp.loadProperties(propsFile); - - List<Header> headers = new ArrayList<Header>(2); - headers.add(new BasicHeader(HttpHeaders.RANGE, - String.format("bytes=%d-", mFileOp.length(tmpFile)))); - - // Don't use the properties if there's not at least a 200 or 206 code from - // the last download. - int status = 0; - try { - status = Integer.parseInt(props.getProperty(PROP_STATUS_CODE)); - } catch (Exception ignore) {} - - if (status == HttpStatus.SC_OK || status == HttpStatus.SC_PARTIAL_CONTENT) { - // Do we have an ETag and/or a Last-Modified? - String etag = props.getProperty(HttpHeaders.ETAG); - String lastMod = props.getProperty(HttpHeaders.LAST_MODIFIED); - - if (etag != null && etag.length() > 0) { - headers.add(new BasicHeader(HttpHeaders.IF_MATCH, etag)); - } else if (lastMod != null && lastMod.length() > 0) { - headers.add(new BasicHeader(HttpHeaders.IF_MATCH, lastMod)); - } - - return headers.toArray(new Header[headers.size()]); - } - } - } - - // Existing file is either of different size or content. - // Remove the existing file and request a full download. - mFileOp.deleteFileOrFolder(tmpFile); - mFileOp.deleteFileOrFolder(propsFile); - - return null; - } - - /** - * Computes the SHA-1 checksum of the content of the given file. - * Returns an empty string on error (rather than null). - */ - private String fileChecksum(MessageDigest digester, File tmpFile, ITaskMonitor monitor) { - InputStream is = null; - try { - is = new FileInputStream(tmpFile); - - byte[] buf = new byte[65536]; - int n; - - while ((n = is.read(buf)) >= 0) { - if (n > 0) { - digester.update(buf, 0, n); - } - } - - return getDigestChecksum(digester); - - } catch (FileNotFoundException e) { - // The FNF message is just the URL. Make it a bit more useful. - monitor.logError("File not found: %1$s", e.getMessage()); - - } catch (Exception e) { - monitor.logError("%1$s", e.getMessage()); //$NON-NLS-1$ - - } finally { - if (is != null) { - try { - is.close(); - } catch (IOException e) { - // pass - } - } - } - - return ""; //$NON-NLS-1$ - } - - /** - * Returns the SHA-1 from a {@link MessageDigest} as an hex string - * that can be compared with {@link Archive#getChecksum()}. - */ - private String getDigestChecksum(MessageDigest digester) { - int n; - // Create an hex string from the digest - byte[] digest = digester.digest(); - n = digest.length; - String hex = "0123456789abcdef"; //$NON-NLS-1$ - char[] hexDigest = new char[n * 2]; - for (int i = 0; i < n; i++) { - int b = digest[i] & 0x0FF; - hexDigest[i*2 + 0] = hex.charAt(b >>> 4); - hexDigest[i*2 + 1] = hex.charAt(b & 0x0f); - } - - return new String(hexDigest); - } - - /** - * Actually performs the download. - * Also computes the SHA1 of the file on the fly. - * <p/> - * Success is defined as downloading as many bytes as was expected and having the same - * SHA1 as expected. Returns true on success or false if any of those checks fail. - * <p/> - * Increments the monitor by {@link #NUM_MONITOR_INC}. - * - * @param archive The archive we're trying to download. - * @param resumeHeaders The headers to use for a partial resume, or null when fetching - * a whole new file. - * @param tmpFile The destination file to download (e.g. something.zip) - * @param propsFile A properties file generated by the last partial download (e.g. .zip.inf) - * @param urlString The URL as a string - * @param pkgName The archive's package name, used for progress output. - * @param cache The {@link DownloadCache} instance to use. - * @param monitor The monitor to output the progress and errors. - * @return True if we fetched the file successfully. - * False if the download failed or was aborted. - */ - private boolean fetchUrl(Archive archive, - Header[] resumeHeaders, - File tmpFile, - File propsFile, - String urlString, - String pkgName, - DownloadCache cache, - ITaskMonitor monitor) { - - FileOutputStream os = null; - InputStream is = null; - int inc_remain = NUM_MONITOR_INC; - try { - Pair<InputStream, HttpResponse> result = - cache.openDirectUrl(urlString, resumeHeaders, monitor); - - is = result.getFirst(); - HttpResponse resp = result.getSecond(); - int status = resp.getStatusLine().getStatusCode(); - if (status == HttpStatus.SC_NOT_FOUND) { - throw new Exception("URL not found."); - } - if (is == null) { - throw new Exception("No content."); - } - - - Properties props = new Properties(); - props.setProperty(PROP_STATUS_CODE, Integer.toString(status)); - if (resp.containsHeader(HttpHeaders.ETAG)) { - props.setProperty(HttpHeaders.ETAG, - resp.getFirstHeader(HttpHeaders.ETAG).getValue()); - } - if (resp.containsHeader(HttpHeaders.LAST_MODIFIED)) { - props.setProperty(HttpHeaders.LAST_MODIFIED, - resp.getFirstHeader(HttpHeaders.LAST_MODIFIED).getValue()); - } - - mFileOp.saveProperties(propsFile, props, "## Android SDK Download."); //$NON-NLS-1$ - - // On success, status can be: - // - 206 (Partial content), if resumeHeaders is not null (we asked for a partial - // download, and we get partial content for that download => we'll need to append - // to the existing file.) - // - 200 (OK) meaning we're getting whole new content from scratch. This can happen - // even if resumeHeaders is not null (typically means the server has a new version - // of the file to serve.) In this case we reset the file and write from scratch. - - boolean append = status == HttpStatus.SC_PARTIAL_CONTENT; - if (status != HttpStatus.SC_OK && !(append && resumeHeaders != null)) { - throw new Exception(String.format("Unexpected HTTP Status %1$d", status)); - } - MessageDigest digester = archive.getChecksumType().getMessageDigest(); - - if (append) { - // Seed the digest with the existing content. - InputStream temp = null; - try { - temp = new FileInputStream(tmpFile); - - byte[] buf = new byte[65536]; - int n; - - while ((n = temp.read(buf)) >= 0) { - if (n > 0) { - digester.update(buf, 0, n); - } - } - } catch (Exception ignore) { - } finally { - if (temp != null) { - try { - temp.close(); - } catch (IOException ignore) {} - } - } - } - - // Open the output stream in append for a resume, or reset for a full download. - os = new FileOutputStream(tmpFile, append); - - byte[] buf = new byte[65536]; - int n; - - long total = 0; - long size = archive.getSize(); - if (append) { - long len = mFileOp.length(tmpFile); - int percent = (int) (len * 100 / size); - size -= len; - monitor.logVerbose( - "Resuming %1$s download at %2$d (%3$d%%)", pkgName, len, percent); - } - long inc = size / NUM_MONITOR_INC; - long next_inc = inc; - - long startMs = System.currentTimeMillis(); - long nextMs = startMs + 2000; // start update after 2 seconds - - while ((n = is.read(buf)) >= 0) { - if (n > 0) { - os.write(buf, 0, n); - digester.update(buf, 0, n); - } - - long timeMs = System.currentTimeMillis(); - - total += n; - if (total >= next_inc) { - monitor.incProgress(1); - inc_remain--; - next_inc += inc; - } - - if (timeMs > nextMs) { - long delta = timeMs - startMs; - if (total > 0 && delta > 0) { - // percent left to download - int percent = (int) (100 * total / size); - // speed in KiB/s - float speed = (float)total / (float)delta * (1000.f / 1024.f); - // time left to download the rest at the current KiB/s rate - int timeLeft = (speed > 1e-3) ? - (int)(((size - total) / 1024.0f) / speed) : - 0; - String timeUnit = "seconds"; - if (timeLeft > 120) { - timeUnit = "minutes"; - timeLeft /= 60; - } - - monitor.setDescription( - "Downloading %1$s (%2$d%%, %3$.0f KiB/s, %4$d %5$s left)", - pkgName, - percent, - speed, - timeLeft, - timeUnit); - } - nextMs = timeMs + 1000; // update every second - } - - if (monitor.isCancelRequested()) { - monitor.log("Download aborted by user at %1$d bytes.", total); - return false; - } - - } - - if (total != size) { - monitor.logError( - "Download finished with wrong size. Expected %1$d bytes, got %2$d bytes.", - size, total); - return false; - } - - // Create an hex string from the digest - String actual = getDigestChecksum(digester); - String expected = archive.getChecksum(); - if (!actual.equalsIgnoreCase(expected)) { - monitor.logError("Download finished with wrong checksum. Expected %1$s, got %2$s.", - expected, actual); - return false; - } - - return true; - - } catch (CanceledByUserException e) { - // HTTP Basic Auth or NTLM login was canceled by user. - // Don't output an error in the log. - - } catch (FileNotFoundException e) { - // The FNF message is just the URL. Make it a bit more useful. - monitor.logError("URL not found: %1$s", e.getMessage()); - - } catch (Exception e) { - monitor.logError("Download interrupted: %1$s", e.getMessage()); //$NON-NLS-1$ - - } finally { - if (os != null) { - try { - os.close(); - } catch (IOException e) { - // pass - } - } - - if (is != null) { - try { - is.close(); - } catch (IOException e) { - // pass - } - } - if (inc_remain > 0) { - monitor.incProgress(inc_remain); - } - } - - return false; - } - - /** - * Install the given archive in the given folder. - */ - private boolean unarchive(ArchiveReplacement archiveInfo, - String osSdkRoot, - File archiveFile, - SdkManager sdkManager, - ITaskMonitor monitor) { - boolean success = false; - Archive newArchive = archiveInfo.getNewArchive(); - Package pkg = newArchive.getParentPackage(); - String pkgName = pkg.getShortDescription(); - monitor.setDescription("Installing %1$s", pkgName); - monitor.log("Installing %1$s", pkgName); - - // Ideally we want to always unzip in a temp folder which name depends on the package - // type (e.g. addon, tools, etc.) and then move the folder to the destination folder. - // If the destination folder exists, it will be renamed and deleted at the very - // end if everything succeeded. This provides a nice atomic swap and should leave the - // original folder untouched in case something wrong (e.g. program crash) in the - // middle of the unzip operation. - // - // However that doesn't work on Windows, we always end up not being able to move the - // new folder. There are actually 2 cases: - // A- A process such as a the explorer is locking the *old* folder or a file inside - // (e.g. adb.exe) - // In this case we really shouldn't be tried to work around it and we need to let - // the user know and let it close apps that access that folder. - // B- A process is locking the *new* folder. Very often this turns to be a file indexer - // or an anti-virus that is busy scanning the new folder that we just unzipped. - // - // So we're going to change the strategy: - // 1- Try to move the old folder to a temp/old folder. This might fail in case of issue A. - // Note: for platform-tools, we can try killing adb first. - // If it still fails, we do nothing and ask the user to terminate apps that can be - // locking that folder. - // 2- Once the old folder is out of the way, we unzip the archive directly into the - // optimal new location. We no longer unzip it in a temp folder and move it since we - // know that's what fails in most of the cases. - // 3- If the unzip fails, remove everything and try to restore the old folder by doing - // a *copy* in place and not a folder move (which will likely fail too). - - String pkgKind = pkg.getClass().getSimpleName(); - - File destFolder = null; - File oldDestFolder = null; - - try { - // -0- Compute destination directory and check install pre-conditions - - destFolder = pkg.getInstallFolder(osSdkRoot, sdkManager); - - if (destFolder == null) { - // this should not seriously happen. - monitor.log("Failed to compute installation directory for %1$s.", pkgName); - return false; - } - - if (!pkg.preInstallHook(newArchive, monitor, osSdkRoot, destFolder)) { - monitor.log("Skipping archive: %1$s", pkgName); - return false; - } - - // -1- move old folder. - - if (mFileOp.exists(destFolder)) { - // Create a new temp/old dir - if (oldDestFolder == null) { - oldDestFolder = getNewTempFolder(osSdkRoot, pkgKind, "old"); //$NON-NLS-1$ - } - if (oldDestFolder == null) { - // this should not seriously happen. - monitor.logError("Failed to find a temp directory in %1$s.", osSdkRoot); - return false; - } - - // Try to move the current dest dir to the temp/old one. Tell the user if it failed. - while(true) { - if (!moveFolder(destFolder, oldDestFolder)) { - monitor.logError("Failed to rename directory %1$s to %2$s.", - destFolder.getPath(), oldDestFolder.getPath()); - - if (SdkConstants.CURRENT_PLATFORM == SdkConstants.PLATFORM_WINDOWS) { - boolean tryAgain = true; - - tryAgain = windowsDestDirLocked(osSdkRoot, destFolder, monitor); - - if (tryAgain) { - // loop, trying to rename the temp dir into the destination - continue; - } else { - return false; - } - } - } - break; - } - } - - assert !mFileOp.exists(destFolder); - - // -2- Unzip new content directly in place. - - if (!mFileOp.mkdirs(destFolder)) { - monitor.logError("Failed to create directory %1$s", destFolder.getPath()); - return false; - } - - if (!unzipFolder(archiveInfo, - archiveFile, - destFolder, - monitor)) { - return false; - } - - if (!generateSourceProperties(newArchive, destFolder)) { - monitor.logError("Failed to generate source.properties in directory %1$s", - destFolder.getPath()); - return false; - } - - // In case of success, if we were replacing an archive - // and the older one had a different path, remove it now. - Archive oldArchive = archiveInfo.getReplaced(); - if (oldArchive != null && oldArchive.isLocal()) { - String oldPath = oldArchive.getLocalOsPath(); - File oldFolder = oldPath == null ? null : new File(oldPath); - if (oldFolder == null && oldArchive.getParentPackage() != null) { - oldFolder = oldArchive.getParentPackage().getInstallFolder( - osSdkRoot, sdkManager); - } - if (oldFolder != null && mFileOp.exists(oldFolder) && - !oldFolder.equals(destFolder)) { - monitor.logVerbose("Removing old archive at %1$s", oldFolder.getAbsolutePath()); - mFileOp.deleteFileOrFolder(oldFolder); - } - } - - success = true; - pkg.postInstallHook(newArchive, monitor, destFolder); - return true; - - } finally { - if (!success) { - // In case of failure, we try to restore the old folder content. - if (oldDestFolder != null) { - restoreFolder(oldDestFolder, destFolder); - } - - // We also call the postInstallHool with a null directory to give a chance - // to the archive to cleanup after preInstallHook. - pkg.postInstallHook(newArchive, monitor, null /*installDir*/); - } - - // Cleanup if the unzip folder is still set. - mFileOp.deleteFileOrFolder(oldDestFolder); - } - } - - private boolean windowsDestDirLocked( - String osSdkRoot, - File destFolder, - final ITaskMonitor monitor) { - String msg = null; - - assert SdkConstants.CURRENT_PLATFORM == SdkConstants.PLATFORM_WINDOWS; - - File findLockExe = FileOp.append( - osSdkRoot, SdkConstants.FD_TOOLS, SdkConstants.FD_LIB, SdkConstants.FN_FIND_LOCK); - - if (mFileOp.exists(findLockExe)) { - try { - final StringBuilder result = new StringBuilder(); - String command[] = new String[] { - findLockExe.getAbsolutePath(), - destFolder.getAbsolutePath() - }; - Process process = Runtime.getRuntime().exec(command); - int retCode = GrabProcessOutput.grabProcessOutput( - process, - Wait.WAIT_FOR_READERS, - new IProcessOutput() { - @Override - public void out(@Nullable String line) { - if (line != null) { - result.append(line).append("\n"); - } - } - - @Override - public void err(@Nullable String line) { - if (line != null) { - monitor.logError("[find_lock] Error: %1$s", line); - } - } - }); - - if (retCode == 0 && result.length() > 0) { - // TODO create a better dialog - - String found = result.toString().trim(); - monitor.logError("[find_lock] Directory locked by %1$s", found); - - TreeSet<String> apps = new TreeSet<String>(Arrays.asList( - found.split(Pattern.quote(";")))); //$NON-NLS-1$ - StringBuilder appStr = new StringBuilder(); - for (String app : apps) { - appStr.append("\n - ").append(app.trim()); //$NON-NLS-1$ - } - - msg = String.format( - "-= Warning ! =-\n" + - "The following processes: %1$s\n" + - "are locking the following directory: \n" + - " %2$s\n" + - "Please close these applications so that the installation can continue.\n" + - "When ready, press YES to try again.", - appStr.toString(), - destFolder.getPath()); - } - - } catch (Exception e) { - monitor.error(e, "[find_lock failed]"); - } - - - } - - if (msg == null) { - // Old way: simply display a generic text and let user figure it out. - msg = String.format( - "-= Warning ! =-\n" + - "A folder failed to be moved. On Windows this " + - "typically means that a program is using that folder (for " + - "example Windows Explorer or your anti-virus software.)\n" + - "Please momentarily deactivate your anti-virus software or " + - "close any running programs that may be accessing the " + - "directory '%1$s'.\n" + - "When ready, press YES to try again.", - destFolder.getPath()); - } - - boolean tryAgain = monitor.displayPrompt("SDK Manager: failed to install", msg); - return tryAgain; - } - - /** - * Tries to rename/move a folder. - * <p/> - * Contract: - * <ul> - * <li> When we start, oldDir must exist and be a directory. newDir must not exist. </li> - * <li> On successful completion, oldDir must not exists. - * newDir must exist and have the same content. </li> - * <li> On failure completion, oldDir must have the same content as before. - * newDir must not exist. </li> - * </ul> - * <p/> - * The simple "rename" operation on a folder can typically fail on Windows for a variety - * of reason, in fact as soon as a single process holds a reference on a directory. The - * most common case are the Explorer, the system's file indexer, Tortoise SVN cache or - * an anti-virus that are busy indexing a new directory having been created. - * - * @param oldDir The old location to move. It must exist and be a directory. - * @param newDir The new location where to move. It must not exist. - * @return True if the move succeeded. On failure, we try hard to not have touched the old - * directory in order not to loose its content. - */ - private boolean moveFolder(File oldDir, File newDir) { - // This is a simple folder rename that works on Linux/Mac all the time. - // - // On Windows this might fail if an indexer is busy looking at a new directory - // (e.g. right after we unzip our archive), so it fails let's be nice and give - // it a bit of time to succeed. - for (int i = 0; i < 5; i++) { - if (mFileOp.renameTo(oldDir, newDir)) { - return true; - } - try { - Thread.sleep(500 /*ms*/); - } catch (InterruptedException e) { - // ignore - } - } - - return false; - } - - /** - * Unzips a zip file into the given destination directory. - * - * The archive file MUST have a unique "root" folder. - * This root folder is skipped when unarchiving. - */ - @SuppressWarnings("unchecked") - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected boolean unzipFolder( - ArchiveReplacement archiveInfo, - File archiveFile, - File unzipDestFolder, - ITaskMonitor monitor) { - - Archive newArchive = archiveInfo.getNewArchive(); - Package pkg = newArchive.getParentPackage(); - String pkgName = pkg.getShortDescription(); - long compressedSize = newArchive.getSize(); - - ZipFile zipFile = null; - try { - zipFile = new ZipFile(archiveFile); - - // To advance the percent and the progress bar, we don't know the number of - // items left to unzip. However we know the size of the archive and the size of - // each uncompressed item. The zip file format overhead is negligible so that's - // a good approximation. - long incStep = compressedSize / NUM_MONITOR_INC; - long incTotal = 0; - long incCurr = 0; - int lastPercent = 0; - - byte[] buf = new byte[65536]; - - Enumeration<ZipArchiveEntry> entries = zipFile.getEntries(); - while (entries.hasMoreElements()) { - ZipArchiveEntry entry = entries.nextElement(); - - String name = entry.getName(); - - // ZipFile entries should have forward slashes, but not all Zip - // implementations can be expected to do that. - name = name.replace('\\', '/'); - - // Zip entries are always packages in a top-level directory - // (e.g. docs/index.html). However we want to use our top-level - // directory so we drop the first segment of the path name. - int pos = name.indexOf('/'); - if (pos < 0 || pos == name.length() - 1) { - continue; - } else { - name = name.substring(pos + 1); - } - - File destFile = new File(unzipDestFolder, name); - - if (name.endsWith("/")) { //$NON-NLS-1$ - // Create directory if it doesn't exist yet. This allows us to create - // empty directories. - if (!mFileOp.isDirectory(destFile) && !mFileOp.mkdirs(destFile)) { - monitor.logError("Failed to create directory %1$s", - destFile.getPath()); - return false; - } - continue; - } else if (name.indexOf('/') != -1) { - // Otherwise it's a file in a sub-directory. - // Make sure the parent directory has been created. - File parentDir = destFile.getParentFile(); - if (!mFileOp.isDirectory(parentDir)) { - if (!mFileOp.mkdirs(parentDir)) { - monitor.logError("Failed to create directory %1$s", - parentDir.getPath()); - return false; - } - } - } - - FileOutputStream fos = null; - long remains = entry.getSize(); - try { - fos = new FileOutputStream(destFile); - - // Java bug 4040920: do not rely on the input stream EOF and don't - // try to read more than the entry's size. - InputStream entryContent = zipFile.getInputStream(entry); - int n; - while (remains > 0 && - (n = entryContent.read( - buf, 0, (int) Math.min(remains, buf.length))) != -1) { - remains -= n; - if (n > 0) { - fos.write(buf, 0, n); - } - } - } catch (EOFException e) { - monitor.logError("Error uncompressing file %s. Size: %d bytes, Unwritten: %d bytes.", - entry.getName(), entry.getSize(), remains); - throw e; - } finally { - if (fos != null) { - fos.close(); - } - } - - pkg.postUnzipFileHook(newArchive, monitor, mFileOp, destFile, entry); - - // Increment progress bar to match. We update only between files. - for(incTotal += entry.getCompressedSize(); incCurr < incTotal; incCurr += incStep) { - monitor.incProgress(1); - } - - int percent = (int) (100 * incTotal / compressedSize); - if (percent != lastPercent) { - monitor.setDescription("Unzipping %1$s (%2$d%%)", pkgName, percent); - lastPercent = percent; - } - - if (monitor.isCancelRequested()) { - return false; - } - } - - return true; - - } catch (IOException e) { - monitor.logError("Unzip failed: %1$s", e.getMessage()); - - } finally { - if (zipFile != null) { - try { - zipFile.close(); - } catch (IOException e) { - // pass - } - } - } - - return false; - } - - /** - * Returns an unused temp folder path in the form of osBasePath/temp/prefix.suffixNNN. - * <p/> - * This does not actually <em>create</em> the folder. It just scan the base path for - * a free folder name to use and returns the file to use to reference it. - * <p/> - * This operation is not atomic so there's no guarantee the folder can't get - * created in between. This is however unlikely and the caller can assume the - * returned folder does not exist yet. - * <p/> - * Returns null if no such folder can be found (e.g. if all candidates exist, - * which is rather unlikely) or if the base temp folder cannot be created. - */ - private File getNewTempFolder(String osBasePath, String prefix, String suffix) { - File baseTempFolder = getTempFolder(osBasePath); - - if (!mFileOp.isDirectory(baseTempFolder)) { - if (mFileOp.isFile(baseTempFolder)) { - mFileOp.deleteFileOrFolder(baseTempFolder); - } - if (!mFileOp.mkdirs(baseTempFolder)) { - return null; - } - } - - for (int i = 1; i < 100; i++) { - File folder = new File(baseTempFolder, - String.format("%1$s.%2$s%3$02d", prefix, suffix, i)); //$NON-NLS-1$ - if (!mFileOp.exists(folder)) { - return folder; - } - } - return null; - } - - /** - * Returns the single fixed "temp" folder used by the SDK Manager. - * This folder is always at osBasePath/temp. - * <p/> - * This does not actually <em>create</em> the folder. - */ - private File getTempFolder(String osBasePath) { - File baseTempFolder = new File(osBasePath, RepoConstants.FD_TEMP); - return baseTempFolder; - } - - /** - * Generates a source.properties in the destination folder that contains all the infos - * relevant to this archive, this package and the source so that we can reload them - * locally later. - */ - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected boolean generateSourceProperties(Archive archive, File unzipDestFolder) { - Properties props = new Properties(); - - archive.saveProperties(props); - - Package pkg = archive.getParentPackage(); - if (pkg != null) { - pkg.saveProperties(props); - } - - return mFileOp.saveProperties( - new File(unzipDestFolder, SdkConstants.FN_SOURCE_PROP), - props, - "## Android Tool: Source of this archive."); //$NON-NLS-1$ - } - - /** - * Recursively restore srcFolder into destFolder by performing a copy of the file - * content rather than rename/moves. - * - * @param srcFolder The source folder to restore. - * @param destFolder The destination folder where to restore. - * @return True if the folder was successfully restored, false if it was not at all or - * only partially restored. - */ - private boolean restoreFolder(File srcFolder, File destFolder) { - boolean result = true; - - // Process sub-folders first - File[] srcFiles = mFileOp.listFiles(srcFolder); - if (srcFiles == null) { - // Source does not exist. That is quite odd. - return false; - } - - if (mFileOp.isFile(destFolder)) { - if (!mFileOp.delete(destFolder)) { - // There's already a file in there where we want a directory and - // we can't delete it. This is rather unexpected. Just give up on - // that folder. - return false; - } - } else if (!mFileOp.isDirectory(destFolder)) { - mFileOp.mkdirs(destFolder); - } - - // Get all the files and dirs of the current destination. - // We are not going to clean up the destination first. - // Instead we'll copy over and just remove any remaining files or directories. - Set<File> destDirs = new HashSet<File>(); - Set<File> destFiles = new HashSet<File>(); - File[] files = mFileOp.listFiles(destFolder); - if (files != null) { - for (File f : files) { - if (mFileOp.isDirectory(f)) { - destDirs.add(f); - } else { - destFiles.add(f); - } - } - } - - // First restore all source directories. - for (File dir : srcFiles) { - if (mFileOp.isDirectory(dir)) { - File d = new File(destFolder, dir.getName()); - destDirs.remove(d); - if (!restoreFolder(dir, d)) { - result = false; - } - } - } - - // Remove any remaining directories not processed above. - for (File dir : destDirs) { - mFileOp.deleteFileOrFolder(dir); - } - - // Copy any source files over to the destination. - for (File file : srcFiles) { - if (mFileOp.isFile(file)) { - File f = new File(destFolder, file.getName()); - destFiles.remove(f); - try { - mFileOp.copyFile(file, f); - } catch (IOException e) { - result = false; - } - } - } - - // Remove any remaining files not processed above. - for (File file : destFiles) { - mFileOp.deleteFileOrFolder(file); - } - - return result; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/archives/ArchiveReplacement.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/archives/ArchiveReplacement.java deleted file mode 100755 index b6570db..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/archives/ArchiveReplacement.java +++ /dev/null @@ -1,112 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.archives; - -import com.android.sdklib.internal.repository.IDescription; -import com.android.sdklib.internal.repository.packages.Package; - - -/** - * Represents an archive that we want to install and the archive that it is - * going to replace, if any. - */ -public class ArchiveReplacement implements IDescription { - - private final Archive mNewArchive; - private final Archive mReplaced; - - /** - * Creates a new replacement where the {@code newArchive} will replace the - * currently installed {@code replaced} archive. - * When {@code newArchive} is not intended to replace anything (e.g. because - * the user is installing a new package not present on her system yet), then - * {@code replace} shall be null. - * - * @param newArchive A "new archive" to be installed. This is always an archive - * that comes from a remote site. This <em>may</em> be null. - * @param replaced An optional local archive that the new one will replace. - * Can be null if this archive does not replace anything. - */ - public ArchiveReplacement(Archive newArchive, Archive replaced) { - mNewArchive = newArchive; - mReplaced = replaced; - } - - /** - * Returns the "new archive" to be installed. - * This <em>may</em> be null for missing archives. - */ - public Archive getNewArchive() { - return mNewArchive; - } - - /** - * Returns an optional local archive that the new one will replace. - * Can be null if this archive does not replace anything. - */ - public Archive getReplaced() { - return mReplaced; - } - - /** - * Returns the long description of the parent package of the new archive, if not null. - * Otherwise returns an empty string. - */ - @Override - public String getLongDescription() { - if (mNewArchive != null) { - Package p = mNewArchive.getParentPackage(); - if (p != null) { - return p.getLongDescription(); - } - } - return ""; - } - - /** - * Returns the short description of the parent package of the new archive, if not null. - * Otherwise returns an empty string. - */ - @Override - public String getShortDescription() { - if (mNewArchive != null) { - Package p = mNewArchive.getParentPackage(); - if (p != null) { - return p.getShortDescription(); - } - } - return ""; - } - - /** - * Returns the short description of the parent package of the new archive, if not null. - * Otherwise returns the default Object toString result. - * <p/> - * This is mostly helpful for debugging. For UI display, use the {@link IDescription} - * interface. - */ - @Override - public String toString() { - if (mNewArchive != null) { - Package p = mNewArchive.getParentPackage(); - if (p != null) { - return p.getShortDescription(); - } - } - return super.toString(); - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/AddonPackage.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/AddonPackage.java deleted file mode 100755 index a388f54..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/AddonPackage.java +++ /dev/null @@ -1,699 +0,0 @@ -/* - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.SdkConstants; -import com.android.annotations.NonNull; -import com.android.annotations.VisibleForTesting; -import com.android.annotations.VisibleForTesting.Visibility; -import com.android.sdklib.AndroidVersion; -import com.android.sdklib.IAndroidTarget; -import com.android.sdklib.IAndroidTarget.IOptionalLibrary; -import com.android.sdklib.SdkManager; -import com.android.sdklib.internal.repository.IDescription; -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; -import com.android.sdklib.internal.repository.sources.SdkSource; -import com.android.sdklib.repository.PkgProps; -import com.android.sdklib.repository.SdkAddonConstants; -import com.android.sdklib.repository.SdkRepoConstants; -import com.android.utils.Pair; - -import org.w3c.dom.Node; - -import java.io.File; -import java.util.ArrayList; -import java.util.Arrays; -import java.util.Locale; -import java.util.Map; -import java.util.Properties; - -/** - * Represents an add-on XML node in an SDK repository. - */ -public class AddonPackage extends MajorRevisionPackage - implements IAndroidVersionProvider, IPlatformDependency, - IExactApiLevelDependency, ILayoutlibVersion { - - private final String mVendorId; - private final String mVendorDisplay; - private final String mNameId; - private final String mDisplayName; - private final AndroidVersion mVersion; - - /** - * The helper handling the layoutlib version. - */ - private final LayoutlibVersionMixin mLayoutlibVersion; - - /** An add-on library. */ - public static class Lib { - private final String mName; - private final String mDescription; - - public Lib(String name, String description) { - mName = name; - mDescription = description; - } - - public String getName() { - return mName; - } - - public String getDescription() { - return mDescription; - } - - @Override - public int hashCode() { - final int prime = 31; - int result = 1; - result = prime * result + ((mDescription == null) ? 0 : mDescription.hashCode()); - result = prime * result + ((mName == null) ? 0 : mName.hashCode()); - return result; - } - - @Override - public boolean equals(Object obj) { - if (this == obj) { - return true; - } - if (obj == null) { - return false; - } - if (!(obj instanceof Lib)) { - return false; - } - Lib other = (Lib) obj; - if (mDescription == null) { - if (other.mDescription != null) { - return false; - } - } else if (!mDescription.equals(other.mDescription)) { - return false; - } - if (mName == null) { - if (other.mName != null) { - return false; - } - } else if (!mName.equals(other.mName)) { - return false; - } - return true; - } - } - - private final Lib[] mLibs; - - /** - * Creates a new add-on package from the attributes and elements of the given XML node. - * This constructor should throw an exception if the package cannot be created. - * - * @param source The {@link SdkSource} where this is loaded from. - * @param packageNode The XML element being parsed. - * @param nsUri The namespace URI of the originating XML document, to be able to deal with - * parameters that vary according to the originating XML schema. - * @param licenses The licenses loaded from the XML originating document. - */ - public AddonPackage( - SdkSource source, - Node packageNode, - String nsUri, - Map<String,String> licenses) { - super(source, packageNode, nsUri, licenses); - - // --- name id/display --- - // addon-4.xsd introduces the name-id, name-display, vendor-id and vendor-display. - // These are not optional but we still need to support a fallback for older addons - // that only provide name and vendor. If the addon provides neither set of fields, - // it will simply not work as expected. - - String nameId = PackageParserUtils.getXmlString(packageNode, - SdkRepoConstants.NODE_NAME_ID); - String nameDisp = PackageParserUtils.getXmlString(packageNode, - SdkRepoConstants.NODE_NAME_DISPLAY); - String name = PackageParserUtils.getXmlString(packageNode, - SdkRepoConstants.NODE_NAME); - - // The old <name> is equivalent to the new <name-display> - if (nameDisp.length() == 0) { - nameDisp = name; - } - - // For a missing id, we simply use a sanitized version of the display name - if (nameId.length() == 0) { - nameId = sanitizeDisplayToNameId(name.length() > 0 ? name : nameDisp); - } - - assert nameId.length() > 0; - assert nameDisp.length() > 0; - - mNameId = nameId.trim(); - mDisplayName = nameDisp.trim(); - - // --- vendor id/display --- - // Same processing for vendor id vs display - - String vendorId = PackageParserUtils.getXmlString(packageNode, - SdkAddonConstants.NODE_VENDOR_ID); - String vendorDisp = PackageParserUtils.getXmlString(packageNode, - SdkAddonConstants.NODE_VENDOR_DISPLAY); - String vendor = PackageParserUtils.getXmlString(packageNode, - SdkAddonConstants.NODE_VENDOR); - - // The old <vendor> is equivalent to the new <vendor-display> - if (vendorDisp.length() == 0) { - vendorDisp = vendor; - } - - // For a missing id, we simply use a sanitized version of the display vendor - if (vendorId.length() == 0) { - boolean hasVendor = vendor.length() > 0; - vendorId = sanitizeDisplayToNameId(hasVendor ? vendor : vendorDisp); - } - - assert vendorId.length() > 0; - assert vendorDisp.length() > 0; - - mVendorId = vendorId.trim(); - mVendorDisplay = vendorDisp.trim(); - - // --- other attributes - - int apiLevel = - PackageParserUtils.getXmlInt(packageNode, SdkAddonConstants.NODE_API_LEVEL, 0); - mVersion = new AndroidVersion(apiLevel, null /*codeName*/); - - mLibs = parseLibs( - PackageParserUtils.findChildElement(packageNode, SdkAddonConstants.NODE_LIBS)); - - mLayoutlibVersion = new LayoutlibVersionMixin(packageNode); - } - - /** - * Creates a new platform package based on an actual {@link IAndroidTarget} (which - * {@link IAndroidTarget#isPlatform()} false) from the {@link SdkManager}. - * This is used to list local SDK folders in which case there is one archive which - * URL is the actual target location. - * <p/> - * By design, this creates a package with one and only one archive. - */ - public static Package create(IAndroidTarget target, Properties props) { - return new AddonPackage(target, props); - } - - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected AddonPackage(IAndroidTarget target, Properties props) { - this(null /*source*/, target, props); - } - - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected AddonPackage(SdkSource source, IAndroidTarget target, Properties props) { - super( source, //source - props, //properties - target.getRevision(), //revision - null, //license - target.getDescription(), //description - null, //descUrl - Os.getCurrentOs(), //archiveOs - Arch.getCurrentArch(), //archiveArch - target.getLocation() //archiveOsPath - ); - - // --- name id/display --- - // addon-4.xsd introduces the name-id, name-display, vendor-id and vendor-display. - // These are not optional but we still need to support a fallback for older addons - // that only provide name and vendor. If the addon provides neither set of fields, - // it will simply not work as expected. - - String nameId = getProperty(props, PkgProps.ADDON_NAME_ID, ""); //$NON-NLS-1$ - String nameDisp = getProperty(props, PkgProps.ADDON_NAME_DISPLAY, ""); //$NON-NLS-1$ - String name = getProperty(props, PkgProps.ADDON_NAME, target.getName()); - - // The old <name> is equivalent to the new <name-display> - if (nameDisp.length() == 0) { - nameDisp = name; - } - - // For a missing id, we simply use a sanitized version of the display name - if (nameId.length() == 0) { - nameId = sanitizeDisplayToNameId(name.length() > 0 ? name : nameDisp); - } - - assert nameId.length() > 0; - assert nameDisp.length() > 0; - - mNameId = nameId.trim(); - mDisplayName = nameDisp.trim(); - - // --- vendor id/display --- - // Same processing for vendor id vs display - - String vendorId = getProperty(props, PkgProps.ADDON_VENDOR_ID, ""); //$NON-NLS-1$ - String vendorDisp = getProperty(props, PkgProps.ADDON_VENDOR_DISPLAY, ""); //$NON-NLS-1$ - String vendor = getProperty(props, PkgProps.ADDON_VENDOR, target.getVendor()); - - // The old <vendor> is equivalent to the new <vendor-display> - if (vendorDisp.length() == 0) { - vendorDisp = vendor; - } - - // For a missing id, we simply use a sanitized version of the display vendor - if (vendorId.length() == 0) { - boolean hasVendor = vendor.length() > 0; - vendorId = sanitizeDisplayToNameId(hasVendor ? vendor : vendorDisp); - } - - assert vendorId.length() > 0; - assert vendorDisp.length() > 0; - - mVendorId = vendorId.trim(); - mVendorDisplay = vendorDisp.trim(); - - // --- other attributes - - mVersion = target.getVersion(); - mLayoutlibVersion = new LayoutlibVersionMixin(props); - - IOptionalLibrary[] optLibs = target.getOptionalLibraries(); - if (optLibs == null || optLibs.length == 0) { - mLibs = new Lib[0]; - } else { - mLibs = new Lib[optLibs.length]; - for (int i = 0; i < optLibs.length; i++) { - mLibs[i] = new Lib(optLibs[i].getName(), optLibs[i].getDescription()); - } - } - } - - /** - * Creates a broken addon which we know failed to load properly. - * - * @param archiveOsPath The absolute OS path of the addon folder. - * @param sourceProps The properties parsed from the addon's source.properties. Can be null. - * @param addonProps The properties parsed from the addon manifest (NOT the source.properties). - * @param error The error indicating why this addon failed to be loaded. - */ - public static Package createBroken( - String archiveOsPath, - Properties sourceProps, - Map<String, String> addonProps, - String error) { - String name = getProperty(sourceProps, - PkgProps.ADDON_NAME_DISPLAY, - getProperty(sourceProps, - PkgProps.ADDON_NAME, - addonProps.get(SdkManager.ADDON_NAME))); - String vendor = getProperty(sourceProps, - PkgProps.ADDON_VENDOR_DISPLAY, - getProperty(sourceProps, - PkgProps.ADDON_VENDOR, - addonProps.get(SdkManager.ADDON_VENDOR))); - String api = addonProps.get(SdkManager.ADDON_API); - String revision = addonProps.get(SdkManager.ADDON_REVISION); - - String shortDesc = String.format("%1$s by %2$s, Android API %3$s, revision %4$s [*]", - name, - vendor, - api, - revision); - - String longDesc = String.format( - "%1$s\n" + - "[*] Addon failed to load: %2$s", - shortDesc, - error); - - int apiLevel = IExactApiLevelDependency.API_LEVEL_INVALID; - - try { - apiLevel = Integer.parseInt(api); - } catch(NumberFormatException e) { - // ignore - } - - return new BrokenPackage(null/*props*/, shortDesc, longDesc, - IMinApiLevelDependency.MIN_API_LEVEL_NOT_SPECIFIED, - apiLevel, - archiveOsPath); - } - - @Override - public int getExactApiLevel() { - return mVersion.getApiLevel(); - } - - /** - * Save the properties of the current packages in the given {@link Properties} object. - * These properties will later be given to a constructor that takes a {@link Properties} object. - */ - @Override - public void saveProperties(Properties props) { - super.saveProperties(props); - - mVersion.saveProperties(props); - mLayoutlibVersion.saveProperties(props); - - props.setProperty(PkgProps.ADDON_NAME_ID, mNameId); - props.setProperty(PkgProps.ADDON_NAME_DISPLAY, mDisplayName); - props.setProperty(PkgProps.ADDON_VENDOR_ID, mVendorId); - props.setProperty(PkgProps.ADDON_VENDOR_DISPLAY, mVendorDisplay); - } - - /** - * Parses a <libs> element. - */ - private Lib[] parseLibs(Node libsNode) { - ArrayList<Lib> libs = new ArrayList<Lib>(); - - if (libsNode != null) { - String nsUri = libsNode.getNamespaceURI(); - for(Node child = libsNode.getFirstChild(); - child != null; - child = child.getNextSibling()) { - - if (child.getNodeType() == Node.ELEMENT_NODE && - nsUri.equals(child.getNamespaceURI()) && - SdkRepoConstants.NODE_LIB.equals(child.getLocalName())) { - libs.add(parseLib(child)); - } - } - } - - return libs.toArray(new Lib[libs.size()]); - } - - /** - * Parses a <lib> element from a <libs> container. - */ - private Lib parseLib(Node libNode) { - return new Lib(PackageParserUtils.getXmlString(libNode, SdkRepoConstants.NODE_NAME), - PackageParserUtils.getXmlString(libNode, SdkRepoConstants.NODE_DESCRIPTION)); - } - - /** Returns the vendor id, a string, for add-on packages. */ - public @NonNull String getVendorId() { - return mVendorId; - } - - /** Returns the vendor, a string for display purposes. */ - public @NonNull String getDisplayVendor() { - return mVendorDisplay; - } - - /** Returns the name id, a string, for add-on packages or for libraries. */ - public @NonNull String getNameId() { - return mNameId; - } - - /** Returns the name, a string for display purposes. */ - public @NonNull String getDisplayName() { - return mDisplayName; - } - - /** - * Returns the version of the platform dependency of this package. - * <p/> - * An add-on has the same {@link AndroidVersion} as the platform it depends on. - */ - @Override @NonNull - public AndroidVersion getAndroidVersion() { - return mVersion; - } - - /** Returns the libs defined in this add-on. Can be an empty array but not null. */ - public @NonNull Lib[] getLibs() { - return mLibs; - } - - /** - * Returns the layoutlib version. - * <p/> - * The first integer is the API of layoublib, which should be > 0. - * It will be equal to {@link ILayoutlibVersion#LAYOUTLIB_API_NOT_SPECIFIED} (0) - * if the layoutlib version isn't specified. - * <p/> - * The second integer is the revision for that given API. It is >= 0 - * and works as a minor revision number, incremented for the same API level. - * - * @since sdk-addon-2.xsd - */ - @Override - public @NonNull Pair<Integer, Integer> getLayoutlibVersion() { - return mLayoutlibVersion.getLayoutlibVersion(); - } - - /** - * Returns a string identifier to install this package from the command line. - * For add-ons, we use "addon-vendor-name-N" where N is the base platform API. - * <p/> - * {@inheritDoc} - */ - @Override - public @NonNull String installId() { - return encodeAddonName(); - } - - /** - * Returns a description of this package that is suitable for a list display. - * <p/> - * {@inheritDoc} - */ - @Override - public String getListDescription() { - return String.format("%1$s%2$s", - getDisplayName(), - isObsolete() ? " (Obsolete)" : ""); - } - - /** - * Returns a short description for an {@link IDescription}. - */ - @Override - public String getShortDescription() { - return String.format("%1$s, Android API %2$s, revision %3$s%4$s", - getDisplayName(), - mVersion.getApiString(), - getRevision().toShortString(), - isObsolete() ? " (Obsolete)" : ""); - } - - /** - * Returns a long description for an {@link IDescription}. - * - * The long description is whatever the XML contains for the <description> field, - * or the short description if the former is empty. - */ - @Override - public String getLongDescription() { - String s = String.format("%1$s, Android API %2$s, revision %3$s%4$s\nBy %5$s", - getDisplayName(), - mVersion.getApiString(), - getRevision().toShortString(), - isObsolete() ? " (Obsolete)" : "", //$NON-NLS-2$ - getDisplayVendor()); - - String d = getDescription(); - if (d != null && d.length() > 0) { - s += '\n' + d; - } - - s += String.format("\nRequires SDK Platform Android API %1$s", - mVersion.getApiString()); - return s; - } - - /** - * Computes a potential installation folder if an archive of this package were - * to be installed right away in the given SDK root. - * <p/> - * An add-on package is typically installed in SDK/add-ons/"addon-name"-"api-level". - * The name needs to be sanitized to be acceptable as a directory name. - * However if we can find a different directory under SDK/add-ons that already - * has this add-ons installed, we'll use that one. - * - * @param osSdkRoot The OS path of the SDK root folder. - * @param sdkManager An existing SDK manager to list current platforms and addons. - * @return A new {@link File} corresponding to the directory to use to install this package. - */ - @Override - public File getInstallFolder(String osSdkRoot, SdkManager sdkManager) { - File addons = new File(osSdkRoot, SdkConstants.FD_ADDONS); - - // First find if this add-on is already installed. If so, reuse the same directory. - for (IAndroidTarget target : sdkManager.getTargets()) { - if (!target.isPlatform() && target.getVersion().equals(mVersion)) { - // Starting with addon-4.xsd, the addon source.properties differentiate - // between ids and display strings. However the addon target which relies - // on the manifest.ini does not so we need to cover both cases. - // TODO fix when we get rid of manifest.ini for addons - if ((target.getName().equals(getNameId()) && - target.getVendor().equals(getVendorId())) || - (target.getName().equals(getDisplayName()) && - target.getVendor().equals(getDisplayVendor()))) { - return new File(target.getLocation()); - } - } - } - - // Compute a folder directory using the addon declared name and vendor strings. - String name = encodeAddonName(); - - for (int i = 0; i < 100; i++) { - String name2 = i == 0 ? name : String.format("%s-%d", name, i); //$NON-NLS-1$ - File folder = new File(addons, name2); - if (!folder.exists()) { - return folder; - } - } - - // We shouldn't really get here. I mean, seriously, we tried hard enough. - return null; - } - - private String encodeAddonName() { - String name = String.format("addon-%s-%s-%s", //$NON-NLS-1$ - getNameId(), getVendorId(), mVersion.getApiString()); - name = name.toLowerCase(Locale.US); - name = name.replaceAll("[^a-z0-9_-]+", "_"); //$NON-NLS-1$ //$NON-NLS-2$ - name = name.replaceAll("_+", "_"); //$NON-NLS-1$ //$NON-NLS-2$ - return name; - } - - /** - * Computes a sanitized name-id based on an addon name-display. - * This is used to provide compatibility with older addons that lacks the new fields. - * - * @param displayName A name-display field or a old-style name field. - * @return A non-null sanitized name-id that fits in the {@code [a-zA-Z0-9_-]+} pattern. - */ - private String sanitizeDisplayToNameId(String displayName) { - String name = displayName.toLowerCase(Locale.US); - name = name.replaceAll("[^a-z0-9_-]+", "_"); //$NON-NLS-1$ //$NON-NLS-2$ - name = name.replaceAll("_+", "_"); //$NON-NLS-1$ //$NON-NLS-2$ - - // Trim leading and trailing underscores - if (name.length() > 1) { - name = name.replaceAll("^_+", ""); //$NON-NLS-1$ //$NON-NLS-2$ - } - if (name.length() > 1) { - name = name.replaceAll("_+$", ""); //$NON-NLS-1$ //$NON-NLS-2$ - } - return name; - } - - @Override - public boolean sameItemAs(Package pkg) { - if (pkg instanceof AddonPackage) { - AddonPackage newPkg = (AddonPackage)pkg; - - // check they are the same add-on. - if (getNameId().equals(newPkg.getNameId()) && - getAndroidVersion().equals(newPkg.getAndroidVersion())) { - // Check the vendor-id field. - if (getVendorId().equals(newPkg.getVendorId())) { - return true; - } - - // When loading addons from the v3 schema that only had a <vendor> - // field, the vendor field has been converted to vendor-display so - // as a transition mechanism we should test this also. - // TODO: in a couple iterations of the SDK Manager, remove this check - // and only compare using the vendor-id field. - return getDisplayVendor().equals(newPkg.getDisplayVendor()); - } - } - - return false; - } - - @Override - public int hashCode() { - final int prime = 31; - int result = super.hashCode(); - result = prime * result + ((mLayoutlibVersion == null) ? 0 : mLayoutlibVersion.hashCode()); - result = prime * result + Arrays.hashCode(mLibs); - result = prime * result + ((mDisplayName == null) ? 0 : mDisplayName.hashCode()); - result = prime * result + ((mVendorDisplay == null) ? 0 : mVendorDisplay.hashCode()); - result = prime * result + ((mVersion == null) ? 0 : mVersion.hashCode()); - return result; - } - - @Override - public boolean equals(Object obj) { - if (this == obj) { - return true; - } - if (!super.equals(obj)) { - return false; - } - if (!(obj instanceof AddonPackage)) { - return false; - } - AddonPackage other = (AddonPackage) obj; - if (mLayoutlibVersion == null) { - if (other.mLayoutlibVersion != null) { - return false; - } - } else if (!mLayoutlibVersion.equals(other.mLayoutlibVersion)) { - return false; - } - if (!Arrays.equals(mLibs, other.mLibs)) { - return false; - } - if (mNameId == null) { - if (other.mNameId != null) { - return false; - } - } else if (!mNameId.equals(other.mNameId)) { - return false; - } - if (mVendorId == null) { - if (other.mVendorId != null) { - return false; - } - } else if (!mVendorId.equals(other.mVendorId)) { - return false; - } - if (mVersion == null) { - if (other.mVersion != null) { - return false; - } - } else if (!mVersion.equals(other.mVersion)) { - return false; - } - return true; - } - - /** - * For addon packages, we want to add vendor|name to the sorting key - * <em>before<em/> the revision number. - * <p/> - * {@inheritDoc} - */ - @Override - protected String comparisonKey() { - String s = super.comparisonKey(); - int pos = s.indexOf("|r:"); //$NON-NLS-1$ - assert pos > 0; - s = s.substring(0, pos) + - "|vid:" + getVendorId() + //$NON-NLS-1$ - "|nid:" + getNameId() + //$NON-NLS-1$ - s.substring(pos); - return s; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/BrokenPackage.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/BrokenPackage.java deleted file mode 100755 index e2c11a0..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/BrokenPackage.java +++ /dev/null @@ -1,201 +0,0 @@ -/* - * Copyright (C) 2010 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.SdkManager; -import com.android.sdklib.internal.repository.IDescription; -import com.android.sdklib.internal.repository.ITaskMonitor; -import com.android.sdklib.internal.repository.archives.Archive; -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; - -import java.io.File; -import java.util.Properties; - -/** - * Represents an SDK repository package that is incomplete. - * It has a distinct icon and a specific error that is supposed to help the user on how to fix it. - */ -public class BrokenPackage extends MajorRevisionPackage - implements IExactApiLevelDependency, IMinApiLevelDependency { - - /** - * The minimal API level required by this package, if > 0, - * or {@link #MIN_API_LEVEL_NOT_SPECIFIED} if there is no such requirement. - */ - private final int mMinApiLevel; - - /** - * The exact API level required by this package, if > 0, - * or {@link #API_LEVEL_INVALID} if there is no such requirement. - */ - private final int mExactApiLevel; - - private final String mShortDescription; - private final String mLongDescription; - - /** - * Creates a new "broken" package that represents a package that we failed to load, - * for whatever error indicated in {@code longDescription}. - * There is also an <em>optional</em> API level dependency that can be specified. - * <p/> - * By design, this creates a package with one and only one archive. - */ - BrokenPackage(Properties props, - String shortDescription, - String longDescription, - int minApiLevel, - int exactApiLevel, - String archiveOsPath) { - super( null, //source - props, //properties - 0, //revision will be taken from props - null, //license - longDescription, //description - null, //descUrl - Os.ANY, //archiveOs - Arch.ANY, //archiveArch - archiveOsPath //archiveOsPath - ); - mShortDescription = shortDescription; - mLongDescription = longDescription; - mMinApiLevel = minApiLevel; - mExactApiLevel = exactApiLevel; - } - - /** - * Save the properties of the current packages in the given {@link Properties} object. - * These properties will later be given to a constructor that takes a {@link Properties} object. - * <p/> - * Base implementation override: We don't actually save properties for a broken package. - */ - @Override - public void saveProperties(Properties props) { - // Nop. We don't actually save properties for a broken package. - } - - /** - * Returns the minimal API level required by this package, if > 0, - * or {@link #MIN_API_LEVEL_NOT_SPECIFIED} if there is no such requirement. - */ - @Override - public int getMinApiLevel() { - return mMinApiLevel; - } - - /** - * Returns the exact API level required by this package, if > 0, - * or {@link #API_LEVEL_INVALID} if the value was missing. - */ - @Override - public int getExactApiLevel() { - return mExactApiLevel; - } - - /** - * Returns a string identifier to install this package from the command line. - * For broken packages, we return an empty string. These are not installable. - * <p/> - * {@inheritDoc} - */ - @Override - public String installId() { - return ""; //$NON-NLS-1$ - } - - /** - * Returns a description of this package that is suitable for a list display. - * <p/> - * {@inheritDoc} - */ - @Override - public String getListDescription() { - return mShortDescription; - } - - /** - * Returns a short description for an {@link IDescription}. - */ - @Override - public String getShortDescription() { - return mShortDescription; - } - - /** - * Returns a long description for an {@link IDescription}. - * - * The long description uses what was given to the constructor. - * If it's missing, it will use whatever the XML contains for the <description> field, - * or the short description if the former is empty. - */ - @Override - public String getLongDescription() { - - String s = mLongDescription; - if (s != null && s.length() != 0) { - return s; - } - - s = getDescription(); - if (s != null && s.length() != 0) { - return s; - } - return getShortDescription(); - } - - /** - * We should not be attempting to install a broken package. - * - * {@inheritDoc} - */ - @Override - public File getInstallFolder(String osSdkRoot, SdkManager sdkManager) { - // We should not be attempting to install a broken package. - return null; - } - - @Override - public boolean sameItemAs(Package pkg) { - if (pkg instanceof BrokenPackage) { - return mShortDescription.equals(((BrokenPackage) pkg).mShortDescription) && - getDescription().equals(pkg.getDescription()) && - getMinApiLevel() == ((BrokenPackage) pkg).getMinApiLevel(); - } - - return false; - } - - @Override - public boolean preInstallHook(Archive archive, - ITaskMonitor monitor, - String osSdkRoot, - File installFolder) { - // Nothing specific to do. - return super.preInstallHook(archive, monitor, osSdkRoot, installFolder); - } - - /** - * Computes a hash of the installed content (in case of successful install.) - * - * {@inheritDoc} - */ - @Override - public void postInstallHook(Archive archive, ITaskMonitor monitor, File installFolder) { - // Nothing specific to do. - super.postInstallHook(archive, monitor, installFolder); - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/DocPackage.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/DocPackage.java deleted file mode 100755 index 927d361..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/DocPackage.java +++ /dev/null @@ -1,307 +0,0 @@ -/* - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.SdkConstants; -import com.android.annotations.NonNull; -import com.android.sdklib.AndroidVersion; -import com.android.sdklib.SdkManager; -import com.android.sdklib.internal.repository.IDescription; -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; -import com.android.sdklib.internal.repository.sources.SdkSource; -import com.android.sdklib.repository.SdkRepoConstants; - -import org.w3c.dom.Node; - -import java.io.File; -import java.util.Map; -import java.util.Properties; - -/** - * Represents a doc XML node in an SDK repository. - * <p/> - * Note that a doc package has a version and thus implements {@link IAndroidVersionProvider}. - * However there is no mandatory dependency that limits installation so this does not - * implement {@link IPlatformDependency}. - */ -public class DocPackage extends MajorRevisionPackage implements IAndroidVersionProvider { - - private final AndroidVersion mVersion; - - /** - * Creates a new doc package from the attributes and elements of the given XML node. - * This constructor should throw an exception if the package cannot be created. - * - * @param source The {@link SdkSource} where this is loaded from. - * @param packageNode The XML element being parsed. - * @param nsUri The namespace URI of the originating XML document, to be able to deal with - * parameters that vary according to the originating XML schema. - * @param licenses The licenses loaded from the XML originating document. - */ - public DocPackage(SdkSource source, - Node packageNode, - String nsUri, - Map<String,String> licenses) { - super(source, packageNode, nsUri, licenses); - - int apiLevel = - PackageParserUtils.getXmlInt (packageNode, SdkRepoConstants.NODE_API_LEVEL, 0); - String codeName = - PackageParserUtils.getXmlString(packageNode, SdkRepoConstants.NODE_CODENAME); - if (codeName.length() == 0) { - codeName = null; - } - mVersion = new AndroidVersion(apiLevel, codeName); - } - - /** - * Manually create a new package with one archive and the given attributes. - * This is used to create packages from local directories in which case there must be - * one archive which URL is the actual target location. - * <p/> - * By design, this creates a package with one and only one archive. - */ - public static Package create(SdkSource source, - Properties props, - int apiLevel, - String codename, - int revision, - String license, - String description, - String descUrl, - Os archiveOs, - Arch archiveArch, - String archiveOsPath) { - return new DocPackage(source, props, apiLevel, codename, revision, license, description, - descUrl, archiveOs, archiveArch, archiveOsPath); - } - - private DocPackage(SdkSource source, - Properties props, - int apiLevel, - String codename, - int revision, - String license, - String description, - String descUrl, - Os archiveOs, - Arch archiveArch, - String archiveOsPath) { - super(source, - props, - revision, - license, - description, - descUrl, - archiveOs, - archiveArch, - archiveOsPath); - mVersion = new AndroidVersion(props, apiLevel, codename); - } - - /** - * Save the properties of the current packages in the given {@link Properties} object. - * These properties will later be give the constructor that takes a {@link Properties} object. - */ - @Override - public void saveProperties(Properties props) { - super.saveProperties(props); - - mVersion.saveProperties(props); - } - - /** - * Returns the version, for platform, add-on and doc packages. - * Can be 0 if this is a local package of unknown api-level. - */ - @Override @NonNull - public AndroidVersion getAndroidVersion() { - return mVersion; - } - - /** - * Returns a string identifier to install this package from the command line. - * For docs, we use "doc-N" where N is the API or the preview codename. - * <p/> - * {@inheritDoc} - */ - @Override - public String installId() { - return "doc-" + mVersion.getApiString(); //$NON-NLS-1$ - } - - /** - * Returns a description of this package that is suitable for a list display. - * <p/> - * {@inheritDoc} - */ - @Override - public String getListDescription() { - if (mVersion.isPreview()) { - return String.format("Documentation for Android '%1$s' Preview SDK%2$s", - mVersion.getCodename(), - isObsolete() ? " (Obsolete)" : ""); - } else { - return String.format("Documentation for Android SDK%2$s", - mVersion.getApiLevel(), - isObsolete() ? " (Obsolete)" : ""); - } - } - - /** - * Returns a short description for an {@link IDescription}. - */ - @Override - public String getShortDescription() { - if (mVersion.isPreview()) { - return String.format("Documentation for Android '%1$s' Preview SDK, revision %2$s%3$s", - mVersion.getCodename(), - getRevision().toShortString(), - isObsolete() ? " (Obsolete)" : ""); - } else { - return String.format("Documentation for Android SDK, API %1$d, revision %2$s%3$s", - mVersion.getApiLevel(), - getRevision().toShortString(), - isObsolete() ? " (Obsolete)" : ""); - } - } - - /** - * Returns a long description for an {@link IDescription}. - * - * The long description is whatever the XML contains for the <description> field, - * or the short description if the former is empty. - */ - @Override - public String getLongDescription() { - String s = getDescription(); - if (s == null || s.length() == 0) { - s = getShortDescription(); - } - - if (s.indexOf("revision") == -1) { - s += String.format("\nRevision %1$s%2$s", - getRevision().toShortString(), - isObsolete() ? " (Obsolete)" : ""); - } - - return s; - } - - /** - * Computes a potential installation folder if an archive of this package were - * to be installed right away in the given SDK root. - * <p/> - * A "doc" package should always be located in SDK/docs. - * - * @param osSdkRoot The OS path of the SDK root folder. - * @param sdkManager An existing SDK manager to list current platforms and addons. - * @return A new {@link File} corresponding to the directory to use to install this package. - */ - @Override - public File getInstallFolder(String osSdkRoot, SdkManager sdkManager) { - return new File(osSdkRoot, SdkConstants.FD_DOCS); - } - - /** - * Consider doc packages to be the same if they cover the same API level, - * regardless of their revision number. - */ - @Override - public boolean sameItemAs(Package pkg) { - if (pkg instanceof DocPackage) { - AndroidVersion rev2 = ((DocPackage) pkg).getAndroidVersion(); - return this.getAndroidVersion().equals(rev2); - } - - return false; - } - - /** - * {@inheritDoc} - * <hr> - * Doc packages are a bit different since there can only be one doc installed at - * the same time. - * <p/> - * We now consider that docs for different APIs are NOT updates, e.g. doc for API N+1 - * is no longer considered an update for doc API N. - * However docs that have the same API version (API level + codename) are considered - * updates if they have a higher revision number (so 15 rev 2 is an update for 15 rev 1, - * but is not an update for 14 rev 1.) - */ - @Override - public UpdateInfo canBeUpdatedBy(Package replacementPackage) { - // check they are the same kind of object - if (!(replacementPackage instanceof DocPackage)) { - return UpdateInfo.INCOMPATIBLE; - } - - DocPackage replacementDoc = (DocPackage)replacementPackage; - - AndroidVersion replacementVersion = replacementDoc.getAndroidVersion(); - - // Check if they're the same exact (api and codename) - if (replacementVersion.equals(mVersion)) { - // exact same version, so check the revision level - if (replacementPackage.getRevision().compareTo(this.getRevision()) > 0) { - return UpdateInfo.UPDATE; - } - } else { - // not the same version? we check if they have the same api level and the new one - // is a preview, in which case it's also an update (since preview have the api level - // of the _previous_ version.) - if (replacementVersion.getApiLevel() == mVersion.getApiLevel() && - replacementVersion.isPreview()) { - return UpdateInfo.UPDATE; - } - } - - // not an upgrade but not incompatible either. - return UpdateInfo.NOT_UPDATE; - } - - @Override - public int hashCode() { - final int prime = 31; - int result = super.hashCode(); - result = prime * result + ((mVersion == null) ? 0 : mVersion.hashCode()); - return result; - } - - @Override - public boolean equals(Object obj) { - if (this == obj) { - return true; - } - if (!super.equals(obj)) { - return false; - } - if (!(obj instanceof DocPackage)) { - return false; - } - DocPackage other = (DocPackage) obj; - if (mVersion == null) { - if (other.mVersion != null) { - return false; - } - } else if (!mVersion.equals(other.mVersion)) { - return false; - } - return true; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/ExtraPackage.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/ExtraPackage.java deleted file mode 100755 index 78a2450..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/ExtraPackage.java +++ /dev/null @@ -1,751 +0,0 @@ -/* - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.SdkConstants; -import com.android.annotations.Nullable; -import com.android.annotations.VisibleForTesting; -import com.android.annotations.VisibleForTesting.Visibility; -import com.android.sdklib.SdkManager; -import com.android.sdklib.internal.repository.IDescription; -import com.android.sdklib.internal.repository.LocalSdkParser; -import com.android.sdklib.internal.repository.NullTaskMonitor; -import com.android.sdklib.internal.repository.archives.Archive; -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; -import com.android.sdklib.internal.repository.sources.SdkSource; -import com.android.sdklib.repository.PkgProps; -import com.android.sdklib.repository.RepoConstants; -import com.android.utils.NullLogger; - -import org.w3c.dom.Node; - -import java.io.File; -import java.util.ArrayList; -import java.util.Arrays; -import java.util.Map; -import java.util.Properties; -import java.util.regex.Pattern; - -/** - * Represents a extra XML node in an SDK repository. - */ -public class ExtraPackage extends MinToolsPackage - implements IMinApiLevelDependency { - - /** - * The extra display name. Used in the UI to represent the package. It can be anything. - */ - private final String mDisplayName; - - /** - * The vendor id name. It is a simple alphanumeric string [a-zA-Z0-9_-]. - */ - private final String mVendorId; - - /** - * The vendor display name. Used in the UI to represent the vendor. It can be anything. - */ - private final String mVendorDisplay; - - /** - * The sub-folder name. It must be a non-empty single-segment path. - */ - private final String mPath; - - /** - * The optional old_paths, if any. If present, this is a list of old "path" values that - * we'd like to migrate to the current "path" name for this extra. - */ - private final String mOldPaths; - - /** - * The minimal API level required by this extra package, if > 0, - * or {@link #MIN_API_LEVEL_NOT_SPECIFIED} if there is no such requirement. - */ - private final int mMinApiLevel; - - /** - * The project-files listed by this extra package. - * The array can be empty but not null. - */ - private final String[] mProjectFiles; - - /** - * Creates a new tool package from the attributes and elements of the given XML node. - * This constructor should throw an exception if the package cannot be created. - * - * @param source The {@link SdkSource} where this is loaded from. - * @param packageNode The XML element being parsed. - * @param nsUri The namespace URI of the originating XML document, to be able to deal with - * parameters that vary according to the originating XML schema. - * @param licenses The licenses loaded from the XML originating document. - */ - public ExtraPackage( - SdkSource source, - Node packageNode, - String nsUri, - Map<String,String> licenses) { - super(source, packageNode, nsUri, licenses); - - mPath = PackageParserUtils.getXmlString(packageNode, RepoConstants.NODE_PATH); - - // Read name-display, vendor-display and vendor-id, introduced in addon-4.xsd. - // These are not optional, they are mandatory in addon-4 but we still treat them - // as optional so that we can fallback on using <vendor> which was the only one - // defined in addon-3.xsd. - String name = - PackageParserUtils.getXmlString(packageNode, RepoConstants.NODE_NAME_DISPLAY); - String vname = - PackageParserUtils.getXmlString(packageNode, RepoConstants.NODE_VENDOR_DISPLAY); - String vid = - PackageParserUtils.getXmlString(packageNode, RepoConstants.NODE_VENDOR_ID); - - if (vid.length() == 0) { - // If vid is missing, use the old <vendor> attribute. - // Note that in a valid XML, vendor-id cannot be an empty string. - // The only reason vid can be empty is when <vendor-id> is missing, which - // happens in an addon-3 schema, in which case the old <vendor> needs to be used. - String vendor = PackageParserUtils.getXmlString(packageNode, RepoConstants.NODE_VENDOR); - vid = sanitizeLegacyVendor(vendor); - if (vname.length() == 0) { - vname = vendor; - } - } - if (vname.length() == 0) { - // The vendor-display name can be empty, in which case we use the vendor-id. - vname = vid; - } - mVendorDisplay = vname.trim(); - mVendorId = vid.trim(); - - if (name.length() == 0) { - // If name is missing, use the <path> attribute as done in an addon-3 schema. - name = getPrettyName(); - } - mDisplayName = name.trim(); - - mMinApiLevel = PackageParserUtils.getXmlInt( - packageNode, RepoConstants.NODE_MIN_API_LEVEL, MIN_API_LEVEL_NOT_SPECIFIED); - - mProjectFiles = parseProjectFiles( - PackageParserUtils.findChildElement(packageNode, RepoConstants.NODE_PROJECT_FILES)); - - mOldPaths = PackageParserUtils.getXmlString(packageNode, RepoConstants.NODE_OLD_PATHS); - } - - private String[] parseProjectFiles(Node projectFilesNode) { - ArrayList<String> paths = new ArrayList<String>(); - - if (projectFilesNode != null) { - String nsUri = projectFilesNode.getNamespaceURI(); - for(Node child = projectFilesNode.getFirstChild(); - child != null; - child = child.getNextSibling()) { - - if (child.getNodeType() == Node.ELEMENT_NODE && - nsUri.equals(child.getNamespaceURI()) && - RepoConstants.NODE_PATH.equals(child.getLocalName())) { - String path = child.getTextContent(); - if (path != null) { - path = path.trim(); - if (path.length() > 0) { - paths.add(path); - } - } - } - } - } - - return paths.toArray(new String[paths.size()]); - } - - /** - * Manually create a new package with one archive and the given attributes or properties. - * This is used to create packages from local directories in which case there must be - * one archive which URL is the actual target location. - * <p/> - * By design, this creates a package with one and only one archive. - */ - public static Package create(SdkSource source, - Properties props, - String vendor, - String path, - int revision, - String license, - String description, - String descUrl, - Os archiveOs, - Arch archiveArch, - String archiveOsPath) { - ExtraPackage ep = new ExtraPackage(source, props, vendor, path, revision, license, - description, descUrl, archiveOs, archiveArch, archiveOsPath); - return ep; - } - - /** - * Constructor used to create a mock {@link ExtraPackage}. - * Most of the attributes here are optional. - * When not defined, they will be extracted from the {@code props} properties. - */ - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected ExtraPackage(SdkSource source, - Properties props, - String vendorId, - String path, - int revision, - String license, - String description, - String descUrl, - Os archiveOs, - Arch archiveArch, - String archiveOsPath) { - super(source, - props, - revision, - license, - description, - descUrl, - archiveOs, - archiveArch, - archiveOsPath); - - // The path argument comes before whatever could be in the properties - mPath = path != null ? path : getProperty(props, PkgProps.EXTRA_PATH, path); - - String name = getProperty(props, PkgProps.EXTRA_NAME_DISPLAY, ""); //$NON-NLS-1$ - String vname = getProperty(props, PkgProps.EXTRA_VENDOR_DISPLAY, ""); //$NON-NLS-1$ - String vid = vendorId != null ? vendorId : - getProperty(props, PkgProps.EXTRA_VENDOR_ID, ""); //$NON-NLS-1$ - - if (vid.length() == 0) { - // If vid is missing, use the old <vendor> attribute. - // <vendor> did not exist prior to schema repo-v3 and tools r8. - String vendor = getProperty(props, PkgProps.EXTRA_VENDOR, ""); //$NON-NLS-1$ - vid = sanitizeLegacyVendor(vendor); - if (vname.length() == 0) { - vname = vendor; - } - } - if (vname.length() == 0) { - // The vendor-display name can be empty, in which case we use the vendor-id. - vname = vid; - } - mVendorDisplay = vname.trim(); - mVendorId = vid.trim(); - - if (name.length() == 0) { - // If name is missing, use the <path> attribute as done in an addon-3 schema. - name = getPrettyName(); - } - mDisplayName = name.trim(); - - mOldPaths = getProperty(props, PkgProps.EXTRA_OLD_PATHS, null); - - mMinApiLevel = getPropertyInt(props, PkgProps.EXTRA_MIN_API_LEVEL, - MIN_API_LEVEL_NOT_SPECIFIED); - - String projectFiles = getProperty(props, PkgProps.EXTRA_PROJECT_FILES, null); - ArrayList<String> filePaths = new ArrayList<String>(); - if (projectFiles != null && projectFiles.length() > 0) { - for (String filePath : projectFiles.split(Pattern.quote(File.pathSeparator))) { - filePath = filePath.trim(); - if (filePath.length() > 0) { - filePaths.add(filePath); - } - } - } - mProjectFiles = filePaths.toArray(new String[filePaths.size()]); - } - - /** - * Save the properties of the current packages in the given {@link Properties} object. - * These properties will later be give the constructor that takes a {@link Properties} object. - */ - @Override - public void saveProperties(Properties props) { - super.saveProperties(props); - - props.setProperty(PkgProps.EXTRA_PATH, mPath); - props.setProperty(PkgProps.EXTRA_NAME_DISPLAY, mDisplayName); - props.setProperty(PkgProps.EXTRA_VENDOR_DISPLAY, mVendorDisplay); - props.setProperty(PkgProps.EXTRA_VENDOR_ID, mVendorId); - - if (getMinApiLevel() != MIN_API_LEVEL_NOT_SPECIFIED) { - props.setProperty(PkgProps.EXTRA_MIN_API_LEVEL, Integer.toString(getMinApiLevel())); - } - - if (mProjectFiles.length > 0) { - StringBuilder sb = new StringBuilder(); - for (int i = 0; i < mProjectFiles.length; i++) { - if (i > 0) { - sb.append(File.pathSeparatorChar); - } - sb.append(mProjectFiles[i]); - } - props.setProperty(PkgProps.EXTRA_PROJECT_FILES, sb.toString()); - } - - if (mOldPaths != null && mOldPaths.length() > 0) { - props.setProperty(PkgProps.EXTRA_OLD_PATHS, mOldPaths); - } - } - - /** - * Returns the minimal API level required by this extra package, if > 0, - * or {@link #MIN_API_LEVEL_NOT_SPECIFIED} if there is no such requirement. - */ - @Override - public int getMinApiLevel() { - return mMinApiLevel; - } - - /** - * The project-files listed by this extra package. - * The array can be empty but not null. - * <p/> - * IMPORTANT: directory separators are NOT translated and may not match - * the {@link File#separatorChar} of the current platform. It's up to the - * user to adequately interpret the paths. - * Similarly, no guarantee is made on the validity of the paths. - * Users are expected to apply all usual sanity checks such as removing - * "./" and "../" and making sure these paths don't reference files outside - * of the installed archive. - * - * @since sdk-repository-4.xsd or sdk-addon-2.xsd - */ - public String[] getProjectFiles() { - return mProjectFiles; - } - - /** - * Returns the old_paths, a list of obsolete path names for the extra package. - * <p/> - * These can be used by the installer to migrate an extra package using one of the - * old paths into the new path. - * <p/> - * These can also be used to recognize "old" renamed packages as the same as - * the current one. - * - * @return A list of old paths. Can be empty but not null. - */ - public String[] getOldPaths() { - if (mOldPaths == null || mOldPaths.length() == 0) { - return new String[0]; - } - return mOldPaths.split(";"); //$NON-NLS-1$ - } - - /** - * Returns the sanitized path folder name. It is a single-segment path. - * <p/> - * The package is installed in SDK/extras/vendor_name/path_name. - */ - public String getPath() { - // The XSD specifies the XML vendor and path should only contain [a-zA-Z0-9]+ - // and cannot be empty. Let's be defensive and enforce that anyway since things - // like "____" are still valid values that we don't want to allow. - - // Sanitize the path - String path = mPath.replaceAll("[^a-zA-Z0-9-]+", "_"); //$NON-NLS-1$ - if (path.length() == 0 || path.equals("_")) { //$NON-NLS-1$ - int h = path.hashCode(); - path = String.format("extra%08x", h); //$NON-NLS-1$ - } - - return path; - } - - /** - * Returns the vendor id. - */ - public String getVendorId() { - return mVendorId; - } - - public String getVendorDisplay() { - return mVendorDisplay; - } - - public String getDisplayName() { - return mDisplayName; - } - - /** Transforms the legacy vendor name into a usable vendor id. */ - private String sanitizeLegacyVendor(String vendorDisplay) { - // The XSD specifies the XML vendor and path should only contain [a-zA-Z0-9]+ - // and cannot be empty. Let's be defensive and enforce that anyway since things - // like "____" are still valid values that we don't want to allow. - - if (vendorDisplay != null && vendorDisplay.length() > 0) { - String vendor = vendorDisplay.trim(); - // Sanitize the vendor - vendor = vendor.replaceAll("[^a-zA-Z0-9-]+", "_"); //$NON-NLS-1$ - if (vendor.equals("_")) { //$NON-NLS-1$ - int h = vendor.hashCode(); - vendor = String.format("vendor%08x", h); //$NON-NLS-1$ - } - - return vendor; - } - - return ""; //$NON-NLS-1$ - - } - - /** - * Used to produce a suitable name-display based on the current {@link #mPath} - * and {@link #mVendorDisplay} in addon-3 schemas. - */ - private String getPrettyName() { - String name = mPath; - - // In the past, we used to save the extras in a folder vendor-path, - // and that "vendor" would end up in the path when we reload the extra from - // disk. Detect this and compensate. - if (mVendorDisplay != null && mVendorDisplay.length() > 0) { - if (name.startsWith(mVendorDisplay + "-")) { //$NON-NLS-1$ - name = name.substring(mVendorDisplay.length() + 1); - } - } - - // Uniformize all spaces in the name - if (name != null) { - name = name.replaceAll("[ _\t\f-]+", " ").trim(); //$NON-NLS-1$ //$NON-NLS-2$ - } - if (name == null || name.length() == 0) { - name = "Unknown Extra"; - } - - if (mVendorDisplay != null && mVendorDisplay.length() > 0) { - name = mVendorDisplay + " " + name; //$NON-NLS-1$ - name = name.replaceAll("[ _\t\f-]+", " ").trim(); //$NON-NLS-1$ //$NON-NLS-2$ - } - - // Look at all lower case characters in range [1..n-1] and replace them by an upper - // case if they are preceded by a space. Also upper cases the first character of the - // string. - boolean changed = false; - char[] chars = name.toCharArray(); - for (int n = chars.length - 1, i = 0; i < n; i++) { - if (Character.isLowerCase(chars[i]) && (i == 0 || chars[i - 1] == ' ')) { - chars[i] = Character.toUpperCase(chars[i]); - changed = true; - } - } - if (changed) { - name = new String(chars); - } - - // Special case: reformat a few typical acronyms. - name = name.replaceAll(" Usb ", " USB "); //$NON-NLS-1$ - name = name.replaceAll(" Api ", " API "); //$NON-NLS-1$ - - return name; - } - - /** - * Returns a string identifier to install this package from the command line. - * For extras, we use "extra-vendor-path". - * <p/> - * {@inheritDoc} - */ - @Override - public String installId() { - return String.format("extra-%1$s-%2$s", //$NON-NLS-1$ - getVendorId(), - getPath()); - } - - /** - * Returns a description of this package that is suitable for a list display. - * <p/> - * {@inheritDoc} - */ - @Override - public String getListDescription() { - String s = String.format("%1$s%2$s", - getDisplayName(), - isObsolete() ? " (Obsolete)" : ""); //$NON-NLS-2$ - - return s; - } - - /** - * Returns a short description for an {@link IDescription}. - */ - @Override - public String getShortDescription() { - String s = String.format("%1$s, revision %2$s%3$s", - getDisplayName(), - getRevision().toShortString(), - isObsolete() ? " (Obsolete)" : ""); //$NON-NLS-2$ - - return s; - } - - /** - * Returns a long description for an {@link IDescription}. - * - * The long description is whatever the XML contains for the <description> field, - * or the short description if the former is empty. - */ - @Override - public String getLongDescription() { - String s = String.format("%1$s, revision %2$s%3$s\nBy %4$s", - getDisplayName(), - getRevision().toShortString(), - isObsolete() ? " (Obsolete)" : "", //$NON-NLS-2$ - getVendorDisplay()); - - String d = getDescription(); - if (d != null && d.length() > 0) { - s += '\n' + d; - } - - if (!getMinToolsRevision().equals(MIN_TOOLS_REV_NOT_SPECIFIED)) { - s += String.format("\nRequires tools revision %1$s", - getMinToolsRevision().toShortString()); - } - - if (getMinApiLevel() != MIN_API_LEVEL_NOT_SPECIFIED) { - s += String.format("\nRequires SDK Platform Android API %1$s", getMinApiLevel()); - } - - File localPath = getLocalArchivePath(); - if (localPath != null) { - // For a local archive, also put the install path in the long description. - // This should help users locate the extra on their drive. - s += String.format("\nLocation: %1$s", localPath.getAbsolutePath()); - } else { - // For a non-installed archive, indicate where it would be installed. - s += String.format("\nInstall path: %1$s", - getInstallSubFolder(null/*sdk root*/).getPath()); - } - - return s; - } - - /** - * Computes a potential installation folder if an archive of this package were - * to be installed right away in the given SDK root. - * <p/> - * A "tool" package should always be located in SDK/tools. - * - * @param osSdkRoot The OS path of the SDK root folder. Must NOT be null. - * @param sdkManager An existing SDK manager to list current platforms and addons. - * Not used in this implementation. - * @return A new {@link File} corresponding to the directory to use to install this package. - */ - @Override - public File getInstallFolder(String osSdkRoot, SdkManager sdkManager) { - - // First find if this extra is already installed. If so, reuse the same directory. - LocalSdkParser localParser = new LocalSdkParser(); - Package[] pkgs = localParser.parseSdk( - osSdkRoot, - sdkManager, - LocalSdkParser.PARSE_EXTRAS, - new NullTaskMonitor(NullLogger.getLogger())); - - for (Package pkg : pkgs) { - if (sameItemAs(pkg) && pkg instanceof ExtraPackage) { - File localPath = ((ExtraPackage) pkg).getLocalArchivePath(); - if (localPath != null) { - return localPath; - } - } - } - - return getInstallSubFolder(osSdkRoot); - } - - /** - * Computes the "sub-folder" install path, relative to the given SDK root. - * For an extra package, this is generally ".../extra/vendor-id/path". - * - * @param osSdkRoot The OS path of the SDK root folder if known. - * This CAN be null, in which case the path will start at /extra. - * @return Either /extra/vendor/path or sdk-root/extra/vendor-id/path. - */ - private File getInstallSubFolder(@Nullable String osSdkRoot) { - // The /extras dir at the root of the SDK - File path = new File(osSdkRoot, SdkConstants.FD_EXTRAS); - - String vendor = getVendorId(); - if (vendor != null && vendor.length() > 0) { - path = new File(path, vendor); - } - - String name = getPath(); - if (name != null && name.length() > 0) { - path = new File(path, name); - } - - return path; - } - - @Override - public boolean sameItemAs(Package pkg) { - // Extra packages are similar if they have the same path and vendor - if (pkg instanceof ExtraPackage) { - ExtraPackage ep = (ExtraPackage) pkg; - - String[] epOldPaths = ep.getOldPaths(); - int lenEpOldPaths = epOldPaths.length; - for (int indexEp = -1; indexEp < lenEpOldPaths; indexEp++) { - if (sameVendorAndPath( - mVendorId, mPath, - ep.mVendorId, indexEp < 0 ? ep.mPath : epOldPaths[indexEp])) { - return true; - } - } - - String[] thisOldPaths = getOldPaths(); - int lenThisOldPaths = thisOldPaths.length; - for (int indexThis = -1; indexThis < lenThisOldPaths; indexThis++) { - if (sameVendorAndPath( - mVendorId, indexThis < 0 ? mPath : thisOldPaths[indexThis], - ep.mVendorId, ep.mPath)) { - return true; - } - } - } - - return false; - } - - private static boolean sameVendorAndPath( - String thisVendor, String thisPath, - String otherVendor, String otherPath) { - // To be backward compatible, we need to support the old vendor-path form - // in either the current or the remote package. - // - // The vendor test below needs to account for an old installed package - // (e.g. with an install path of vendor-name) that has then been updated - // in-place and thus when reloaded contains the vendor name in both the - // path and the vendor attributes. - if (otherPath != null && thisPath != null && thisVendor != null) { - if (otherPath.equals(thisVendor + '-' + thisPath) && - (otherVendor == null || - otherVendor.length() == 0 || - otherVendor.equals(thisVendor))) { - return true; - } - } - if (thisPath != null && otherPath != null && otherVendor != null) { - if (thisPath.equals(otherVendor + '-' + otherPath) && - (thisVendor == null || - thisVendor.length() == 0 || - thisVendor.equals(otherVendor))) { - return true; - } - } - - - if (thisPath != null && thisPath.equals(otherPath)) { - if ((thisVendor == null && otherVendor == null) || - (thisVendor != null && thisVendor.equals(otherVendor))) { - return true; - } - } - - return false; - } - - /** - * For extra packages, we want to add vendor|path to the sorting key - * <em>before<em/> the revision number. - * <p/> - * {@inheritDoc} - */ - @Override - protected String comparisonKey() { - String s = super.comparisonKey(); - int pos = s.indexOf("|r:"); //$NON-NLS-1$ - assert pos > 0; - s = s.substring(0, pos) + - "|ve:" + getVendorId() + //$NON-NLS-1$ - "|pa:" + getPath() + //$NON-NLS-1$ - s.substring(pos); - return s; - } - - // --- - - /** - * If this package is installed, returns the install path of the archive if valid. - * Returns null if not installed or if the path does not exist. - */ - private File getLocalArchivePath() { - Archive[] archives = getArchives(); - if (archives.length == 1 && archives[0].isLocal()) { - File path = new File(archives[0].getLocalOsPath()); - if (path.isDirectory()) { - return path; - } - } - - return null; - } - - @Override - public int hashCode() { - final int prime = 31; - int result = super.hashCode(); - result = prime * result + mMinApiLevel; - result = prime * result + ((mPath == null) ? 0 : mPath.hashCode()); - result = prime * result + Arrays.hashCode(mProjectFiles); - result = prime * result + ((mVendorDisplay == null) ? 0 : mVendorDisplay.hashCode()); - return result; - } - - @Override - public boolean equals(Object obj) { - if (this == obj) { - return true; - } - if (!super.equals(obj)) { - return false; - } - if (!(obj instanceof ExtraPackage)) { - return false; - } - ExtraPackage other = (ExtraPackage) obj; - if (mMinApiLevel != other.mMinApiLevel) { - return false; - } - if (mPath == null) { - if (other.mPath != null) { - return false; - } - } else if (!mPath.equals(other.mPath)) { - return false; - } - if (!Arrays.equals(mProjectFiles, other.mProjectFiles)) { - return false; - } - if (mVendorDisplay == null) { - if (other.mVendorDisplay != null) { - return false; - } - } else if (!mVendorDisplay.equals(other.mVendorDisplay)) { - return false; - } - return true; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/FullRevision.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/FullRevision.java deleted file mode 100755 index 715028e..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/FullRevision.java +++ /dev/null @@ -1,268 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.annotations.NonNull; - -import java.util.regex.Matcher; -import java.util.regex.Pattern; - - -/** - * Package multi-part revision number composed of a tuple - * (major.minor.micro) and an optional preview revision - * (the lack of a preview number indicates it's not a preview - * but a final package.) - * - * @see MajorRevision - */ -public class FullRevision implements Comparable<FullRevision> { - - public static final int MISSING_MAJOR_REV = 0; - public static final int IMPLICIT_MINOR_REV = 0; - public static final int IMPLICIT_MICRO_REV = 0; - public static final int NOT_A_PREVIEW = 0; - - private final static Pattern FULL_REVISION_PATTERN = - // 1=major 2=minor 3=micro 4=preview - Pattern.compile("\\s*([0-9]+)(?:\\.([0-9]+)(?:\\.([0-9]+))?)?\\s*(?:rc([0-9]+))?\\s*"); - - private final int mMajor; - private final int mMinor; - private final int mMicro; - private final int mPreview; - - public FullRevision(int major) { - this(major, 0, 0); - } - - public FullRevision(int major, int minor, int micro) { - this(major, minor, micro, NOT_A_PREVIEW); - } - - public FullRevision(int major, int minor, int micro, int preview) { - mMajor = major; - mMinor = minor; - mMicro = micro; - mPreview = preview; - } - - public int getMajor() { - return mMajor; - } - - public int getMinor() { - return mMinor; - } - - public int getMicro() { - return mMicro; - } - - public boolean isPreview() { - return mPreview > NOT_A_PREVIEW; - } - - public int getPreview() { - return mPreview; - } - - /** - * Parses a string of format "major.minor.micro rcPreview" and returns - * a new {@link FullRevision} for it. All the fields except major are - * optional. - * <p/> - * The parsing is equivalent to the pseudo-BNF/regexp: - * <pre> - * Major/Minor/Micro/Preview := [0-9]+ - * Revision := Major ('.' Minor ('.' Micro)? )? \s* ('rc'Preview)? - * </pre> - * - * @param revision A non-null revision to parse. - * @return A new non-null {@link FullRevision}. - * @throws NumberFormatException if the parsing failed. - */ - public static @NonNull FullRevision parseRevision(@NonNull String revision) - throws NumberFormatException { - - if (revision == null) { - throw new NumberFormatException("revision is <null>"); //$NON-NLS-1$ - } - - Throwable cause = null; - try { - Matcher m = FULL_REVISION_PATTERN.matcher(revision); - if (m != null && m.matches()) { - int major = Integer.parseInt(m.group(1)); - String s = m.group(2); - int minor = s == null ? IMPLICIT_MINOR_REV : Integer.parseInt(s); - s = m.group(3); - int micro = s == null ? IMPLICIT_MICRO_REV : Integer.parseInt(s); - s = m.group(4); - int preview = s == null ? NOT_A_PREVIEW : Integer.parseInt(s); - - return new FullRevision(major, minor, micro, preview); - } - } catch (Throwable t) { - cause = t; - } - - NumberFormatException n = new NumberFormatException( - "Invalid full revision: " + revision); //$NON-NLS-1$ - n.initCause(cause); - throw n; - } - - /** - * Returns the version in a fixed format major.minor.micro - * with an optional "rc preview#". For example it would - * return "18.0.0", "18.1.0" or "18.1.2 rc5". - */ - @Override - public String toString() { - StringBuilder sb = new StringBuilder(); - sb.append(mMajor) - .append('.').append(mMinor) - .append('.').append(mMicro); - - if (mPreview != NOT_A_PREVIEW) { - sb.append(" rc").append(mPreview); - } - - return sb.toString(); - } - - /** - * Returns the version in a dynamic format "major.minor.micro rc#". - * This is similar to {@link #toString()} except it omits minor, micro - * or preview versions when they are zero. - * For example it would return "18 rc1" instead of "18.0.0 rc1", - * or "18.1 rc2" instead of "18.1.0 rc2". - */ - public String toShortString() { - StringBuilder sb = new StringBuilder(); - sb.append(mMajor); - if (mMinor > 0 || mMicro > 0) { - sb.append('.').append(mMinor); - } - if (mMicro > 0) { - sb.append('.').append(mMicro); - } - if (mPreview != NOT_A_PREVIEW) { - sb.append(" rc").append(mPreview); - } - - return sb.toString(); - } - - /** - * Returns the version number as an integer array, in the form - * [major, minor, micro] or [major, minor, micro, preview]. - * - * This is useful to initialize an instance of - * {@code org.apache.tools.ant.util.DeweyDecimal} using a - * {@link FullRevision}. - * - * @param includePreview If true the output will contain 4 fields - * to include the preview number (even if 0.) If false the output - * will contain only 3 fields (major, minor and micro.) - * @return A new int array, never null, with either 3 or 4 fields. - */ - public int[] toIntArray(boolean includePreview) { - int size = includePreview ? 4 : 3; - int[] result = new int[size]; - result[0] = mMajor; - result[1] = mMinor; - result[2] = mMicro; - if (result.length > 3) { - result[3] = mPreview; - } - return result; - } - - @Override - public int hashCode() { - final int prime = 31; - int result = 1; - result = prime * result + mMajor; - result = prime * result + mMinor; - result = prime * result + mMicro; - result = prime * result + mPreview; - return result; - } - - @Override - public boolean equals(Object rhs) { - if (this == rhs) { - return true; - } - if (rhs == null) { - return false; - } - if (!(rhs instanceof FullRevision)) { - return false; - } - FullRevision other = (FullRevision) rhs; - if (mMajor != other.mMajor) { - return false; - } - if (mMinor != other.mMinor) { - return false; - } - if (mMicro != other.mMicro) { - return false; - } - if (mPreview != other.mPreview) { - return false; - } - return true; - } - - /** - * Trivial comparison of a version, e.g 17.1.2 < 18.0.0. - * - * Note that preview/release candidate are released before their final version, - * so "18.0.0 rc1" comes below "18.0.0". The best way to think of it as if the - * lack of preview number was "+inf": - * "18.1.2 rc5" => "18.1.2.5" so its less than "18.1.2.+INF" but more than "18.1.1.0" - * and more than "18.1.2.4" - */ - @Override - public int compareTo(FullRevision rhs) { - int delta = mMajor - rhs.mMajor; - if (delta != 0) { - return delta; - } - - delta = mMinor - rhs.mMinor; - if (delta != 0) { - return delta; - } - - delta = mMicro - rhs.mMicro; - if (delta != 0) { - return delta; - } - - int p1 = mPreview == NOT_A_PREVIEW ? Integer.MAX_VALUE : mPreview; - int p2 = rhs.mPreview == NOT_A_PREVIEW ? Integer.MAX_VALUE : rhs.mPreview; - delta = p1 - p2; - return delta; - } - - -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/FullRevisionPackage.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/FullRevisionPackage.java deleted file mode 100755 index 88827f5..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/FullRevisionPackage.java +++ /dev/null @@ -1,170 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; -import com.android.sdklib.internal.repository.sources.SdkSource; -import com.android.sdklib.repository.PkgProps; -import com.android.sdklib.repository.SdkRepoConstants; - -import org.w3c.dom.Node; - -import java.util.Map; -import java.util.Properties; - -/** - * Represents a package in an SDK repository that has a {@link FullRevision}, - * which is a multi-part revision number (major.minor.micro) and an optional preview revision. - */ -public abstract class FullRevisionPackage extends Package - implements IFullRevisionProvider { - - private final FullRevision mPreviewVersion; - - /** - * Creates a new package from the attributes and elements of the given XML node. - * This constructor should throw an exception if the package cannot be created. - * - * @param source The {@link SdkSource} where this is loaded from. - * @param packageNode The XML element being parsed. - * @param nsUri The namespace URI of the originating XML document, to be able to deal with - * parameters that vary according to the originating XML schema. - * @param licenses The licenses loaded from the XML originating document. - */ - FullRevisionPackage(SdkSource source, - Node packageNode, - String nsUri, - Map<String,String> licenses) { - super(source, packageNode, nsUri, licenses); - - mPreviewVersion = PackageParserUtils.parseFullRevisionElement( - PackageParserUtils.findChildElement(packageNode, SdkRepoConstants.NODE_REVISION)); - } - - /** - * Manually create a new package with one archive and the given attributes. - * This is used to create packages from local directories in which case there must be - * one archive which URL is the actual target location. - * <p/> - * Properties from props are used first when possible, e.g. if props is non null. - * <p/> - * By design, this creates a package with one and only one archive. - */ - public FullRevisionPackage( - SdkSource source, - Properties props, - int revision, - String license, - String description, - String descUrl, - Os archiveOs, - Arch archiveArch, - String archiveOsPath) { - super(source, props, revision, license, description, descUrl, - archiveOs, archiveArch, archiveOsPath); - - String revStr = getProperty(props, PkgProps.PKG_REVISION, null); - - FullRevision rev = null; - if (revStr != null) { - try { - rev = FullRevision.parseRevision(revStr); - } catch (NumberFormatException ignore) {} - } - if (rev == null) { - rev = new FullRevision(revision); - } - - mPreviewVersion = rev; - } - - @Override - public FullRevision getRevision() { - return mPreviewVersion; - } - - @Override - public void saveProperties(Properties props) { - super.saveProperties(props); - props.setProperty(PkgProps.PKG_REVISION, mPreviewVersion.toShortString()); - } - - @Override - public int hashCode() { - final int prime = 31; - int result = super.hashCode(); - result = prime * result + ((mPreviewVersion == null) ? 0 : mPreviewVersion.hashCode()); - return result; - } - - @Override - public boolean equals(Object obj) { - if (this == obj) { - return true; - } - if (!super.equals(obj)) { - return false; - } - if (!(obj instanceof FullRevisionPackage)) { - return false; - } - FullRevisionPackage other = (FullRevisionPackage) obj; - if (mPreviewVersion == null) { - if (other.mPreviewVersion != null) { - return false; - } - } else if (!mPreviewVersion.equals(other.mPreviewVersion)) { - return false; - } - return true; - } - - /** - * Computes whether the given package is a suitable update for the current package. - * <p/> - * A specific case here is that a release package can update a preview, whereas - * a preview can only update another preview. - * <p/> - * {@inheritDoc} - */ - @Override - public UpdateInfo canBeUpdatedBy(Package replacementPackage) { - if (replacementPackage == null) { - return UpdateInfo.INCOMPATIBLE; - } - - // check they are the same item, ignoring the preview bit. - if (!sameItemAs(replacementPackage, true /*ignorePreviews*/)) { - return UpdateInfo.INCOMPATIBLE; - } - - // a preview cannot update a non-preview - if (!getRevision().isPreview() && replacementPackage.getRevision().isPreview()) { - return UpdateInfo.INCOMPATIBLE; - } - - // check revision number - if (replacementPackage.getRevision().compareTo(this.getRevision()) > 0) { - return UpdateInfo.UPDATE; - } - - // not an upgrade but not incompatible either. - return UpdateInfo.NOT_UPDATE; - } - -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/IAndroidVersionProvider.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/IAndroidVersionProvider.java deleted file mode 100755 index 14d6214..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/IAndroidVersionProvider.java +++ /dev/null @@ -1,37 +0,0 @@ -/* - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.annotations.NonNull; -import com.android.sdklib.AndroidVersion; - -/** - * Interface for packages that provide an {@link AndroidVersion}. - * <p/> - * Note that {@link IPlatformDependency} is a similar interface, but with a different semantic. - * The {@link IPlatformDependency} denotes that a given package can only be installed if the - * requested platform is present, whereas this interface denotes that the given package simply - * has a version, which is not necessarily a dependency. - */ -public interface IAndroidVersionProvider { - - /** - * Returns the android version, for platform, add-on and doc packages. - * Can be 0 if this is a local package of unknown api-level. - */ - public abstract @NonNull AndroidVersion getAndroidVersion(); -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/IExactApiLevelDependency.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/IExactApiLevelDependency.java deleted file mode 100755 index eaeccdb..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/IExactApiLevelDependency.java +++ /dev/null @@ -1,49 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.repository.RepoConstants; - -/** - * Interface used to decorate a {@link Package} that has a dependency - * on a specific API level, e.g. which XML has a {@code <api-level>} element. - * <p/> - * For example an add-on package requires a platform with an exact API level to be installed - * at the same time. - * This is not the same as {@link IMinApiLevelDependency} which requests that a platform with at - * least the requested API level be present or installed at the same time. - * <p/> - * Such package requires the {@code <api-level>} element. It is not an optional - * property, however it can be invalid. - */ -public interface IExactApiLevelDependency { - - /** - * The value of {@link #getExactApiLevel()} when the {@link RepoConstants#NODE_API_LEVEL} - * was not specified in the XML source. - */ - public static final int API_LEVEL_INVALID = 0; - - /** - * Returns the exact API level required by this package, if > 0, - * or {@link #API_LEVEL_INVALID} if the value was missing. - * <p/> - * This attribute is mandatory and should not be normally missing. - * It can only happen when dealing with an invalid repository XML. - */ - public abstract int getExactApiLevel(); -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/IFullRevisionProvider.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/IFullRevisionProvider.java deleted file mode 100755 index e4ec292..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/IFullRevisionProvider.java +++ /dev/null @@ -1,43 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - - - -/** - * Interface for packages that provide a {@link FullRevision}, - * which is a multi-part revision number (major.minor.micro) and an optional preview revision. - * <p/> - * This interface is a tag. It indicates that {@link Package#getRevision()} returns a - * {@link FullRevision} instead of a limited {@link MajorRevision}. <br/> - * The preview version number is available via {@link Package#getRevision()}. - */ -public interface IFullRevisionProvider { - - /** - * Returns whether the give package represents the same item as the current package. - * <p/> - * Two packages are considered the same if they represent the same thing, except for the - * revision number. - * @param pkg the package to compare - * @param ignorePreviews true if 2 packages should be considered the same even if one - * is a preview and the other one is not. - * @return true if the item are the same. - */ - public abstract boolean sameItemAs(Package pkg, boolean ignorePreviews); - -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/ILayoutlibVersion.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/ILayoutlibVersion.java deleted file mode 100755 index 39c1dc2..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/ILayoutlibVersion.java +++ /dev/null @@ -1,42 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.utils.Pair; - -/** - * Interface used to decorate a {@link Package} that provides a version for layout lib. - */ -public interface ILayoutlibVersion { - - public static final int LAYOUTLIB_API_NOT_SPECIFIED = 0; - public static final int LAYOUTLIB_REV_NOT_SPECIFIED = 0; - - /** - * Returns the layoutlib version. Mandatory starting with repository XSD rev 4. - * <p/> - * The first integer is the API of layoublib, which should be > 0. - * It will be equal to {@link #LAYOUTLIB_API_NOT_SPECIFIED} (0) if the layoutlib - * version isn't specified. - * <p/> - * The second integer is the revision for that given API. It is >= 0 - * and works as a minor revision number, incremented for the same API level. - * - * @since sdk-repository-4.xsd - */ - public Pair<Integer, Integer> getLayoutlibVersion(); -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/IMinApiLevelDependency.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/IMinApiLevelDependency.java deleted file mode 100755 index 8baafe9..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/IMinApiLevelDependency.java +++ /dev/null @@ -1,41 +0,0 @@ -/* - * Copyright (C) 2010 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.repository.SdkRepoConstants; - -/** - * Interface used to decorate a {@link Package} that has a dependency - * on a minimal API level, e.g. which XML has a <code><min-api-level></code> element. - * <p/> - * A package that has this dependency can only be installed if a platform with at least the - * requested API level is present or installed at the same time. - */ -public interface IMinApiLevelDependency { - - /** - * The value of {@link #getMinApiLevel()} when the {@link SdkRepoConstants#NODE_MIN_API_LEVEL} - * was not specified in the XML source. - */ - public static final int MIN_API_LEVEL_NOT_SPECIFIED = 0; - - /** - * Returns the minimal API level required by this package, if > 0, - * or {@link #MIN_API_LEVEL_NOT_SPECIFIED} if there is no such requirement. - */ - public abstract int getMinApiLevel(); -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/IMinPlatformToolsDependency.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/IMinPlatformToolsDependency.java deleted file mode 100755 index d17b800..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/IMinPlatformToolsDependency.java +++ /dev/null @@ -1,49 +0,0 @@ -/* - * Copyright (C) 2010 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.repository.SdkRepoConstants; - -/** - * Interface used to decorate a {@link Package} that has a dependency - * on a minimal platform-tools revision, e.g. which XML has a - * <code><min-platform-tools-rev></code> element. - * <p/> - * A package that has this dependency can only be installed if the requested platform-tools - * revision is present or installed at the same time. - */ -public interface IMinPlatformToolsDependency { - - /** - * The value of {@link #getMinPlatformToolsRevision()} when the - * {@link SdkRepoConstants#NODE_MIN_PLATFORM_TOOLS_REV} was not specified in the XML source. - * Since this is a required attribute in the XML schema, it can only happen when dealing - * with an invalid repository XML. - */ - public static final FullRevision MIN_PLATFORM_TOOLS_REV_INVALID = - new FullRevision(FullRevision.MISSING_MAJOR_REV); - - /** - * The minimal revision of the tools package required by this package if > 0, - * or {@link #MIN_PLATFORM_TOOLS_REV_INVALID} if the value was missing. - * <p/> - * This attribute is mandatory and should not be normally missing. - * It can only happen when dealing with an invalid repository XML. - */ - public abstract FullRevision getMinPlatformToolsRevision(); - -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/IMinToolsDependency.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/IMinToolsDependency.java deleted file mode 100755 index 064f1d3..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/IMinToolsDependency.java +++ /dev/null @@ -1,42 +0,0 @@ -/* - * Copyright (C) 2010 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.repository.SdkRepoConstants; - -/** - * Interface used to decorate a {@link Package} that has a dependency - * on a minimal tools revision, e.g. which XML has a <code><min-tools-rev></code> element. - * <p/> - * A package that has this dependency can only be installed if the requested tools revision - * is present or installed at the same time. - */ -public interface IMinToolsDependency { - - /** - * The value of {@link #getMinToolsRevision()} when the - * {@link SdkRepoConstants#NODE_MIN_TOOLS_REV} was not specified in the XML source. - */ - public static final FullRevision MIN_TOOLS_REV_NOT_SPECIFIED = - new FullRevision(FullRevision.MISSING_MAJOR_REV); - - /** - * The minimal revision of the tools package required by this extra package if > 0, - * or {@link #MIN_TOOLS_REV_NOT_SPECIFIED} if there is no such requirement. - */ - public abstract FullRevision getMinToolsRevision(); -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/IPlatformDependency.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/IPlatformDependency.java deleted file mode 100755 index 9665528..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/IPlatformDependency.java +++ /dev/null @@ -1,37 +0,0 @@ -/* - * Copyright (C) 2010 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.AndroidVersion; - -/** - * Interface used to decorate a {@link Package} that has a dependency - * on a specific platform (API level and/or code name). - * <p/> - * A package that has this dependency can only be installed if a platform with at least the - * requested API level is present or installed at the same time. - * <p/> - * Note that although this interface looks like {@link IAndroidVersionProvider}, it does - * not convey the same semantic since {@link IAndroidVersionProvider} does <em>not</em> - * imply any dependency being a limiting factor as far as installation is concerned. - */ -public interface IPlatformDependency { - - /** Returns the version of the platform dependency of this package. */ - AndroidVersion getAndroidVersion(); - -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/LayoutlibVersionMixin.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/LayoutlibVersionMixin.java deleted file mode 100755 index ab9a31e..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/LayoutlibVersionMixin.java +++ /dev/null @@ -1,131 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.repository.PkgProps; -import com.android.sdklib.repository.RepoConstants; -import com.android.utils.Pair; - -import org.w3c.dom.Node; - -import java.util.Properties; - -/** - * Helper class to handle the layoutlib version provided by a package. - */ -public class LayoutlibVersionMixin implements ILayoutlibVersion { - - /** - * The layoutlib version. - * The first integer is the API of layoublib, which should be > 0. - * It will be equal to {@link #LAYOUTLIB_API_NOT_SPECIFIED} (0) if the layoutlib - * version isn't specified. - * The second integer is the revision for that given API. It is >= 0 - * and works as a minor revision number, incremented for the same API level. - */ - private final Pair<Integer, Integer> mLayoutlibVersion; - - /** - * Parses an XML node to process the {@code <layoutlib>} element. - * - * The layoutlib element is new in the XSD rev 4, so we need to cope with it missing - * in earlier XMLs. - */ - public LayoutlibVersionMixin(Node pkgNode) { - - int api = LAYOUTLIB_API_NOT_SPECIFIED; - int rev = LAYOUTLIB_REV_NOT_SPECIFIED; - - Node layoutlibNode = - PackageParserUtils.findChildElement(pkgNode, RepoConstants.NODE_LAYOUT_LIB); - - if (layoutlibNode != null) { - api = PackageParserUtils.getXmlInt(layoutlibNode, RepoConstants.NODE_API, 0); - rev = PackageParserUtils.getXmlInt(layoutlibNode, RepoConstants.NODE_REVISION, 0); - } - - mLayoutlibVersion = Pair.of(api, rev); - } - - /** - * Parses the layoutlib version optionally available in the given {@link Properties}. - */ - public LayoutlibVersionMixin(Properties props) { - int layoutlibApi = Package.getPropertyInt(props, PkgProps.LAYOUTLIB_API, - LAYOUTLIB_API_NOT_SPECIFIED); - int layoutlibRev = Package.getPropertyInt(props, PkgProps.LAYOUTLIB_REV, - LAYOUTLIB_REV_NOT_SPECIFIED); - mLayoutlibVersion = Pair.of(layoutlibApi, layoutlibRev); - } - - /** - * Stores the layoutlib version in the given {@link Properties}. - */ - void saveProperties(Properties props) { - if (mLayoutlibVersion.getFirst().intValue() != LAYOUTLIB_API_NOT_SPECIFIED) { - props.setProperty(PkgProps.LAYOUTLIB_API, mLayoutlibVersion.getFirst().toString()); - props.setProperty(PkgProps.LAYOUTLIB_REV, mLayoutlibVersion.getSecond().toString()); - } - } - - /** - * Returns the layoutlib version. - * <p/> - * The first integer is the API of layoublib, which should be > 0. - * It will be equal to {@link #LAYOUTLIB_API_NOT_SPECIFIED} (0) if the layoutlib - * version isn't specified. - * <p/> - * The second integer is the revision for that given API. It is >= 0 - * and works as a minor revision number, incremented for the same API level. - * - * @since sdk-repository-4.xsd and sdk-addon-2.xsd - */ - @Override - public Pair<Integer, Integer> getLayoutlibVersion() { - return mLayoutlibVersion; - } - - @Override - public int hashCode() { - final int prime = 31; - int result = 1; - result = prime * result + ((mLayoutlibVersion == null) ? 0 : mLayoutlibVersion.hashCode()); - return result; - } - - @Override - public boolean equals(Object obj) { - if (this == obj) { - return true; - } - if (obj == null) { - return false; - } - if (!(obj instanceof LayoutlibVersionMixin)) { - return false; - } - LayoutlibVersionMixin other = (LayoutlibVersionMixin) obj; - if (mLayoutlibVersion == null) { - if (other.mLayoutlibVersion != null) { - return false; - } - } else if (!mLayoutlibVersion.equals(other.mLayoutlibVersion)) { - return false; - } - return true; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/MajorRevision.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/MajorRevision.java deleted file mode 100755 index ad33ed4..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/MajorRevision.java +++ /dev/null @@ -1,56 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.annotations.NonNull; - - -/** - * Package revision number composed of a <em>single</em> major revision. - * <p/> - * Contrary to a {@link FullRevision}, a {@link MajorRevision} does not - * provide minor, micro and preview revision numbers -- these are all - * set to zero. - */ -public class MajorRevision extends FullRevision { - - public MajorRevision(int major) { - super(major, 0, 0); - } - - @Override - public String toString() { - return super.toShortString(); - } - - /** - * Parses a single-integer string and returns a new {@link MajorRevision} for it. - * - * @param revision A non-null revision to parse. - * @return A new non-null {@link MajorRevision}. - * @throws NumberFormatException if the parsing failed. - */ - public static @NonNull MajorRevision parseRevision(@NonNull String revision) - throws NumberFormatException { - - if (revision == null) { - throw new NumberFormatException("revision is <null>"); //$NON-NLS-1$ - } - - return new MajorRevision(Integer.parseInt(revision.trim())); - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/MajorRevisionPackage.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/MajorRevisionPackage.java deleted file mode 100755 index 4591297..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/MajorRevisionPackage.java +++ /dev/null @@ -1,132 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; -import com.android.sdklib.internal.repository.sources.SdkSource; -import com.android.sdklib.repository.PkgProps; -import com.android.sdklib.repository.SdkRepoConstants; - -import org.w3c.dom.Node; - -import java.util.Map; -import java.util.Properties; - -/** - * Represents a package in an SDK repository that has a {@link MajorRevision}, - * which is a single major revision number (not minor, micro or previews). - */ -public abstract class MajorRevisionPackage extends Package { - - private final MajorRevision mRevision; - - /** - * Creates a new package from the attributes and elements of the given XML node. - * This constructor should throw an exception if the package cannot be created. - * - * @param source The {@link SdkSource} where this is loaded from. - * @param packageNode The XML element being parsed. - * @param nsUri The namespace URI of the originating XML document, to be able to deal with - * parameters that vary according to the originating XML schema. - * @param licenses The licenses loaded from the XML originating document. - */ - MajorRevisionPackage(SdkSource source, - Node packageNode, - String nsUri, - Map<String,String> licenses) { - super(source, packageNode, nsUri, licenses); - - mRevision = new MajorRevision( - PackageParserUtils.getXmlInt(packageNode, SdkRepoConstants.NODE_REVISION, 0)); - } - - /** - * Manually create a new package with one archive and the given attributes. - * This is used to create packages from local directories in which case there must be - * one archive which URL is the actual target location. - * <p/> - * Properties from props are used first when possible, e.g. if props is non null. - * <p/> - * By design, this creates a package with one and only one archive. - */ - public MajorRevisionPackage( - SdkSource source, - Properties props, - int revision, - String license, - String description, - String descUrl, - Os archiveOs, - Arch archiveArch, - String archiveOsPath) { - super(source, props, revision, license, description, descUrl, - archiveOs, archiveArch, archiveOsPath); - - String revStr = getProperty(props, PkgProps.PKG_REVISION, null); - - MajorRevision rev = null; - if (revStr != null) { - try { - rev = MajorRevision.parseRevision(revStr); - } catch (NumberFormatException ignore) {} - } - if (rev == null) { - rev = new MajorRevision(revision); - } - - mRevision = rev; - } - - /** - * Returns the revision, an int > 0, for all packages (platform, add-on, tool, doc). - * Can be 0 if this is a local package of unknown revision. - */ - @Override - public FullRevision getRevision() { - return mRevision; - } - - - @Override - public void saveProperties(Properties props) { - super.saveProperties(props); - props.setProperty(PkgProps.PKG_REVISION, mRevision.toString()); - } - - @Override - public UpdateInfo canBeUpdatedBy(Package replacementPackage) { - if (replacementPackage == null) { - return UpdateInfo.INCOMPATIBLE; - } - - // check they are the same item. - if (!sameItemAs(replacementPackage)) { - return UpdateInfo.INCOMPATIBLE; - } - - // check revision number - if (replacementPackage.getRevision().compareTo(this.getRevision()) > 0) { - return UpdateInfo.UPDATE; - } - - // not an upgrade but not incompatible either. - return UpdateInfo.NOT_UPDATE; - } - - -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/MinToolsPackage.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/MinToolsPackage.java deleted file mode 100755 index a608a3c..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/MinToolsPackage.java +++ /dev/null @@ -1,139 +0,0 @@ -/* - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; -import com.android.sdklib.internal.repository.sources.SdkSource; -import com.android.sdklib.repository.PkgProps; -import com.android.sdklib.repository.SdkRepoConstants; - -import org.w3c.dom.Node; - -import java.util.Map; -import java.util.Properties; - -/** - * Represents an XML node in an SDK repository that has a min-tools-rev requirement. - */ -public abstract class MinToolsPackage extends MajorRevisionPackage implements IMinToolsDependency { - - /** - * The minimal revision of the tools package required by this extra package, if > 0, - * or {@link #MIN_TOOLS_REV_NOT_SPECIFIED} if there is no such requirement. - */ - private final FullRevision mMinToolsRevision; - - /** - * Creates a new package from the attributes and elements of the given XML node. - * This constructor should throw an exception if the package cannot be created. - * - * @param source The {@link SdkSource} where this is loaded from. - * @param packageNode The XML element being parsed. - * @param nsUri The namespace URI of the originating XML document, to be able to deal with - * parameters that vary according to the originating XML schema. - * @param licenses The licenses loaded from the XML originating document. - */ - MinToolsPackage(SdkSource source, Node packageNode, String nsUri, Map<String,String> licenses) { - super(source, packageNode, nsUri, licenses); - - mMinToolsRevision = PackageParserUtils.parseFullRevisionElement( - PackageParserUtils.findChildElement(packageNode, SdkRepoConstants.NODE_MIN_TOOLS_REV)); - } - - /** - * Manually create a new package with one archive and the given attributes. - * This is used to create packages from local directories in which case there must be - * one archive which URL is the actual target location. - * <p/> - * Properties from props are used first when possible, e.g. if props is non null. - * <p/> - * By design, this creates a package with one and only one archive. - */ - public MinToolsPackage( - SdkSource source, - Properties props, - int revision, - String license, - String description, - String descUrl, - Os archiveOs, - Arch archiveArch, - String archiveOsPath) { - super(source, props, revision, license, description, descUrl, - archiveOs, archiveArch, archiveOsPath); - - String revStr = getProperty(props, PkgProps.MIN_TOOLS_REV, null); - - FullRevision rev = MIN_TOOLS_REV_NOT_SPECIFIED; - if (revStr != null) { - try { - rev = FullRevision.parseRevision(revStr); - } catch (NumberFormatException ignore) {} - } - - mMinToolsRevision = rev; - } - - /** - * The minimal revision of the tools package required by this extra package, if > 0, - * or {@link #MIN_TOOLS_REV_NOT_SPECIFIED} if there is no such requirement. - */ - @Override - public FullRevision getMinToolsRevision() { - return mMinToolsRevision; - } - - @Override - public void saveProperties(Properties props) { - super.saveProperties(props); - - if (!getMinToolsRevision().equals(MIN_TOOLS_REV_NOT_SPECIFIED)) { - props.setProperty(PkgProps.MIN_TOOLS_REV, getMinToolsRevision().toShortString()); - } - } - - @Override - public int hashCode() { - final int prime = 31; - int result = super.hashCode(); - result = prime * result + ((mMinToolsRevision == null) ? 0 : mMinToolsRevision.hashCode()); - return result; - } - - @Override - public boolean equals(Object obj) { - if (this == obj) { - return true; - } - if (!super.equals(obj)) { - return false; - } - if (!(obj instanceof MinToolsPackage)) { - return false; - } - MinToolsPackage other = (MinToolsPackage) obj; - if (mMinToolsRevision == null) { - if (other.mMinToolsRevision != null) { - return false; - } - } else if (!mMinToolsRevision.equals(other.mMinToolsRevision)) { - return false; - } - return true; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/Package.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/Package.java deleted file mode 100755 index feab109..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/Package.java +++ /dev/null @@ -1,823 +0,0 @@ -/* - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.SdkConstants; -import com.android.annotations.NonNull; -import com.android.annotations.Nullable; -import com.android.annotations.VisibleForTesting; -import com.android.annotations.VisibleForTesting.Visibility; -import com.android.sdklib.AndroidVersion; -import com.android.sdklib.SdkManager; -import com.android.sdklib.internal.repository.IDescription; -import com.android.sdklib.internal.repository.ITaskMonitor; -import com.android.sdklib.internal.repository.archives.Archive; -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; -import com.android.sdklib.internal.repository.sources.SdkAddonSource; -import com.android.sdklib.internal.repository.sources.SdkRepoSource; -import com.android.sdklib.internal.repository.sources.SdkSource; -import com.android.sdklib.io.IFileOp; -import com.android.sdklib.repository.PkgProps; -import com.android.sdklib.repository.SdkAddonConstants; -import com.android.sdklib.repository.SdkRepoConstants; - -import org.apache.commons.compress.archivers.zip.ZipArchiveEntry; -import org.w3c.dom.Node; - -import java.io.File; -import java.io.IOException; -import java.util.ArrayList; -import java.util.Arrays; -import java.util.Map; -import java.util.Properties; - -/** - * A {@link Package} is the base class for "something" that can be downloaded from - * the SDK repository. - * <p/> - * A package has some attributes (revision, description) and a list of archives - * which represent the downloadable bits. - * <p/> - * Packages are contained by a {@link SdkSource} (a download site). - * <p/> - * Derived classes must implement the {@link IDescription} methods. - */ -public abstract class Package implements IDescription, Comparable<Package> { - - private final String mObsolete; - private final String mLicense; - private final String mDescription; - private final String mDescUrl; - private final String mReleaseNote; - private final String mReleaseUrl; - private final Archive[] mArchives; - private final SdkSource mSource; - - - // figure if we'll need to set the unix permissions - private static final boolean sUsingUnixPerm = - SdkConstants.CURRENT_PLATFORM == SdkConstants.PLATFORM_DARWIN || - SdkConstants.CURRENT_PLATFORM == SdkConstants.PLATFORM_LINUX; - - - /** - * Enum for the result of {@link Package#canBeUpdatedBy(Package)}. This used so that we can - * differentiate between a package that is totally incompatible, and one that is the same item - * but just not an update. - * @see #canBeUpdatedBy(Package) - */ - public static enum UpdateInfo { - /** Means that the 2 packages are not the same thing */ - INCOMPATIBLE, - /** Means that the 2 packages are the same thing but one does not upgrade the other. - * </p> - * TODO: this name is confusing. We need to dig deeper. */ - NOT_UPDATE, - /** Means that the 2 packages are the same thing, and one is the upgrade of the other */ - UPDATE; - } - - /** - * Creates a new package from the attributes and elements of the given XML node. - * This constructor should throw an exception if the package cannot be created. - * - * @param source The {@link SdkSource} where this is loaded from. - * @param packageNode The XML element being parsed. - * @param nsUri The namespace URI of the originating XML document, to be able to deal with - * parameters that vary according to the originating XML schema. - * @param licenses The licenses loaded from the XML originating document. - */ - Package(SdkSource source, Node packageNode, String nsUri, Map<String,String> licenses) { - mSource = source; - mDescription = - PackageParserUtils.getXmlString(packageNode, SdkRepoConstants.NODE_DESCRIPTION); - mDescUrl = - PackageParserUtils.getXmlString(packageNode, SdkRepoConstants.NODE_DESC_URL); - mReleaseNote = - PackageParserUtils.getXmlString(packageNode, SdkRepoConstants.NODE_RELEASE_NOTE); - mReleaseUrl = - PackageParserUtils.getXmlString(packageNode, SdkRepoConstants.NODE_RELEASE_URL); - mObsolete = - PackageParserUtils.getOptionalXmlString(packageNode, SdkRepoConstants.NODE_OBSOLETE); - - mLicense = parseLicense(packageNode, licenses); - mArchives = parseArchives( - PackageParserUtils.findChildElement(packageNode, SdkRepoConstants.NODE_ARCHIVES)); - } - - /** - * Manually create a new package with one archive and the given attributes. - * This is used to create packages from local directories in which case there must be - * one archive which URL is the actual target location. - * <p/> - * Properties from props are used first when possible, e.g. if props is non null. - * <p/> - * By design, this creates a package with one and only one archive. - */ - public Package( - SdkSource source, - Properties props, - int revision, - String license, - String description, - String descUrl, - Os archiveOs, - Arch archiveArch, - String archiveOsPath) { - - if (description == null) { - description = ""; - } - if (descUrl == null) { - descUrl = ""; - } - - mLicense = getProperty(props, PkgProps.PKG_LICENSE, license); - mDescription = getProperty(props, PkgProps.PKG_DESC, description); - mDescUrl = getProperty(props, PkgProps.PKG_DESC_URL, descUrl); - mReleaseNote = getProperty(props, PkgProps.PKG_RELEASE_NOTE, ""); //$NON-NLS-1$ - mReleaseUrl = getProperty(props, PkgProps.PKG_RELEASE_URL, ""); //$NON-NLS-1$ - mObsolete = getProperty(props, PkgProps.PKG_OBSOLETE, null); - - // If source is null and we can find a source URL in the properties, generate - // a dummy source just to store the URL. This allows us to easily remember where - // a package comes from. - String srcUrl = getProperty(props, PkgProps.PKG_SOURCE_URL, null); - if (props != null && source == null && srcUrl != null) { - // Both Addon and Extra packages can come from an addon source. - // For Extras, we can tell by looking at the source URL. - if (this instanceof AddonPackage || - ((this instanceof ExtraPackage) && - srcUrl.endsWith(SdkAddonConstants.URL_DEFAULT_FILENAME))) { - source = new SdkAddonSource(srcUrl, null /*uiName*/); - } else { - source = new SdkRepoSource(srcUrl, null /*uiName*/); - } - } - mSource = source; - - assert archiveOsPath != null; - mArchives = initializeArchives(props, archiveOs, archiveArch, archiveOsPath); - } - - /** - * Called by the constructor to get the initial {@link #mArchives} array. - * <p/> - * This is invoked by the local-package constructor and allows mock testing - * classes to override the archives created. - * This is an <em>implementation</em> details and clients must <em>not</em> - * rely on this. - * - * @return Always return a non-null array. The array may be empty. - */ - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected Archive[] initializeArchives( - Properties props, - Os archiveOs, - Arch archiveArch, - String archiveOsPath) { - return new Archive[] { - new Archive(this, - props, - archiveOs, - archiveArch, - archiveOsPath) }; - } - - /** - * Utility method that returns a property from a {@link Properties} object. - * Returns the default value if props is null or if the property is not defined. - * - * @param props The {@link Properties} to search into. - * If null, the default value is returned. - * @param propKey The name of the property. Must not be null. - * @param defaultValue The default value to return if {@code props} is null or if the - * key is not found. Can be null. - * @return The string value of the given key in the properties, or null if the key - * isn't found or if {@code props} is null. - */ - @Nullable - static String getProperty( - @Nullable Properties props, - @NonNull String propKey, - @Nullable String defaultValue) { - if (props == null) { - return defaultValue; - } - return props.getProperty(propKey, defaultValue); - } - - /** - * Utility method that returns an integer property from a {@link Properties} object. - * Returns the default value if props is null or if the property is not defined or - * cannot be parsed to an integer. - * - * @param props The {@link Properties} to search into. - * If null, the default value is returned. - * @param propKey The name of the property. Must not be null. - * @param defaultValue The default value to return if {@code props} is null or if the - * key is not found. Can be null. - * @return The integer value of the given key in the properties, or the {@code defaultValue}. - */ - static int getPropertyInt( - @Nullable Properties props, - @NonNull String propKey, - int defaultValue) { - String s = props != null ? props.getProperty(propKey, null) : null; - if (s != null) { - try { - return Integer.parseInt(s); - } catch (Exception ignore) {} - } - return defaultValue; - } - - /** - * Save the properties of the current packages in the given {@link Properties} object. - * These properties will later be give the constructor that takes a {@link Properties} object. - */ - public void saveProperties(Properties props) { - if (mLicense != null && mLicense.length() > 0) { - props.setProperty(PkgProps.PKG_LICENSE, mLicense); - } - if (mDescription != null && mDescription.length() > 0) { - props.setProperty(PkgProps.PKG_DESC, mDescription); - } - if (mDescUrl != null && mDescUrl.length() > 0) { - props.setProperty(PkgProps.PKG_DESC_URL, mDescUrl); - } - - if (mReleaseNote != null && mReleaseNote.length() > 0) { - props.setProperty(PkgProps.PKG_RELEASE_NOTE, mReleaseNote); - } - if (mReleaseUrl != null && mReleaseUrl.length() > 0) { - props.setProperty(PkgProps.PKG_RELEASE_URL, mReleaseUrl); - } - if (mObsolete != null) { - props.setProperty(PkgProps.PKG_OBSOLETE, mObsolete); - } - if (mSource != null) { - props.setProperty(PkgProps.PKG_SOURCE_URL, mSource.getUrl()); - } - } - - /** - * Parses the uses-licence node of this package, if any, and returns the license - * definition if there's one. Returns null if there's no uses-license element or no - * license of this name defined. - */ - private String parseLicense(Node packageNode, Map<String, String> licenses) { - Node usesLicense = - PackageParserUtils.findChildElement(packageNode, SdkRepoConstants.NODE_USES_LICENSE); - if (usesLicense != null) { - Node ref = usesLicense.getAttributes().getNamedItem(SdkRepoConstants.ATTR_REF); - if (ref != null) { - String licenseRef = ref.getNodeValue(); - return licenses.get(licenseRef); - } - } - return null; - } - - /** - * Parses an XML node to process the <archives> element. - * Always return a non-null array. The array may be empty. - */ - private Archive[] parseArchives(Node archivesNode) { - ArrayList<Archive> archives = new ArrayList<Archive>(); - - if (archivesNode != null) { - String nsUri = archivesNode.getNamespaceURI(); - for(Node child = archivesNode.getFirstChild(); - child != null; - child = child.getNextSibling()) { - - if (child.getNodeType() == Node.ELEMENT_NODE && - nsUri.equals(child.getNamespaceURI()) && - SdkRepoConstants.NODE_ARCHIVE.equals(child.getLocalName())) { - archives.add(parseArchive(child)); - } - } - } - - return archives.toArray(new Archive[archives.size()]); - } - - /** - * Parses one <archive> element from an <archives> container. - */ - private Archive parseArchive(Node archiveNode) { - Archive a = new Archive( - this, - (Os) PackageParserUtils.getEnumAttribute( - archiveNode, SdkRepoConstants.ATTR_OS, Os.values(), null), - (Arch) PackageParserUtils.getEnumAttribute( - archiveNode, SdkRepoConstants.ATTR_ARCH, Arch.values(), Arch.ANY), - PackageParserUtils.getXmlString(archiveNode, SdkRepoConstants.NODE_URL), - PackageParserUtils.getXmlLong (archiveNode, SdkRepoConstants.NODE_SIZE, 0), - PackageParserUtils.getXmlString(archiveNode, SdkRepoConstants.NODE_CHECKSUM) - ); - - return a; - } - - /** - * Returns the source that created (and owns) this package. Can be null. - */ - public SdkSource getParentSource() { - return mSource; - } - - /** - * Returns true if the package is deemed obsolete, that is it contains an - * actual <code><obsolete></code> element. - */ - public boolean isObsolete() { - return mObsolete != null; - } - - /** - * Returns the revision, an int > 0, for all packages (platform, add-on, tool, doc). - * Can be 0 if this is a local package of unknown revision. - */ - public abstract FullRevision getRevision(); - - /** - * Returns the optional description for all packages (platform, add-on, tool, doc) or - * for a lib. It is null if the element has not been specified in the repository XML. - */ - public String getLicense() { - return mLicense; - } - - /** - * Returns the optional description for all packages (platform, add-on, tool, doc) or - * for a lib. Can be empty but not null. - */ - public String getDescription() { - return mDescription; - } - - /** - * Returns the optional description URL for all packages (platform, add-on, tool, doc). - * Can be empty but not null. - */ - public String getDescUrl() { - return mDescUrl; - } - - /** - * Returns the optional release note for all packages (platform, add-on, tool, doc) or - * for a lib. Can be empty but not null. - */ - public String getReleaseNote() { - return mReleaseNote; - } - - /** - * Returns the optional release note URL for all packages (platform, add-on, tool, doc). - * Can be empty but not null. - */ - public String getReleaseNoteUrl() { - return mReleaseUrl; - } - - /** - * Returns the archives defined in this package. - * Can be an empty array but not null. - */ - public Archive[] getArchives() { - return mArchives; - } - - /** - * Returns true if this package contains the exact given archive. - * Important: This compares object references, not object equality. - */ - public boolean hasArchive(Archive archive) { - for (Archive a : mArchives) { - if (a == archive) { - return true; - } - } - return false; - } - - /** - * Returns whether the {@link Package} has at least one {@link Archive} compatible with - * the host platform. - */ - public boolean hasCompatibleArchive() { - for (Archive archive : mArchives) { - if (archive.isCompatible()) { - return true; - } - } - - return false; - } - - /** - * Returns a short, reasonably unique string identifier that can be used - * to identify this package when installing from the command-line interface. - * {@code 'android list sdk'} will show these IDs and then in turn they can - * be provided to {@code 'android update sdk --no-ui --filter'} to select - * some specific packages. - * <p/> - * The identifiers must have the following properties: <br/> - * - They must contain only simple alphanumeric characters. <br/> - * - Commas, whitespace and any special character that could be obviously problematic - * to a shell interface should be avoided (so dash/underscore are OK, but things - * like colon, pipe or dollar should be avoided.) <br/> - * - The name must be consistent across calls and reasonably unique for the package - * type. Collisions can occur but should be rare. <br/> - * - Different package types should have a clearly different name pattern. <br/> - * - The revision number should not be included, as this would prevent updates - * from being automated (which is the whole point.) <br/> - * - It must remain reasonably human readable. <br/> - * - If no such id can exist (for example for a local package that cannot be installed) - * then an empty string should be returned. Don't return null. - * <p/> - * Important: This is <em>not</em> a strong unique identifier for the package. - * If you need a strong unique identifier, you should use {@link #comparisonKey()} - * and the {@link Comparable} interface. - */ - public abstract String installId(); - - /** - * Returns the short description of the source, if not null. - * Otherwise returns the default Object toString result. - * <p/> - * This is mostly helpful for debugging. - * For UI display, use the {@link IDescription} interface. - */ - @Override - public String toString() { - String s = getShortDescription(); - if (s != null) { - return s; - } - return super.toString(); - } - - /** - * Returns a description of this package that is suitable for a list display. - * Should not be empty. Must never be null. - * <p/> - * Note that this is the "base" name for the package - * with no specific revision nor API mentionned. - * In contrast, {@link #getShortDescription()} should be used if you want more details - * such as the package revision number or the API, if applicable. - */ - public abstract String getListDescription(); - - /** - * Returns a short description for an {@link IDescription}. - * Can be empty but not null. - */ - @Override - public abstract String getShortDescription(); - - /** - * Returns a long description for an {@link IDescription}. - * Can be empty but not null. - */ - @Override - public String getLongDescription() { - StringBuilder sb = new StringBuilder(); - - String s = getDescription(); - if (s != null) { - sb.append(s); - } - if (sb.length() > 0) { - sb.append("\n"); - } - - sb.append(String.format("Revision %1$s%2$s", - getRevision().toShortString(), - isObsolete() ? " (Obsolete)" : "")); - - s = getDescUrl(); - if (s != null && s.length() > 0) { - sb.append(String.format("\n\nMore information at %1$s", s)); - } - - s = getReleaseNote(); - if (s != null && s.length() > 0) { - sb.append("\n\nRelease note:\n").append(s); - } - - s = getReleaseNoteUrl(); - if (s != null && s.length() > 0) { - sb.append("\nRelease note URL: ").append(s); - } - - return sb.toString(); - } - - /** - * A package is local (that is 'installed locally') if it contains a single - * archive that is local. If not local, it's a remote package, only available - * on a remote source for download and installation. - */ - public boolean isLocal() { - return mArchives.length == 1 && mArchives[0].isLocal(); - } - - /** - * Computes a potential installation folder if an archive of this package were - * to be installed right away in the given SDK root. - * <p/> - * Some types of packages install in a fix location, for example docs and tools. - * In this case the returned folder may already exist with a different archive installed - * at the desired location. <br/> - * For other packages types, such as add-on or platform, the folder name is only partially - * relevant to determine the content and thus a real check will be done to provide an - * existing or new folder depending on the current content of the SDK. - * <p/> - * Note that the installer *will* create all directories returned here just before - * installation so this method must not attempt to create them. - * - * @param osSdkRoot The OS path of the SDK root folder. - * @param sdkManager An existing SDK manager to list current platforms and addons. - * @return A new {@link File} corresponding to the directory to use to install this package. - */ - public abstract File getInstallFolder(String osSdkRoot, SdkManager sdkManager); - - /** - * Hook called right before an archive is installed. The archive has already - * been downloaded successfully and will be installed in the directory specified by - * <var>installFolder</var> when this call returns. - * <p/> - * The hook lets the package decide if installation of this specific archive should - * be continue. The installer will still install the remaining packages if possible. - * <p/> - * The base implementation always return true. - * <p/> - * Note that the installer *will* create all directories specified by - * {@link #getInstallFolder} just before installation, so they must not be - * created here. This is also called before the previous install dir is removed - * so the previous content is still there during upgrade. - * - * @param archive The archive that will be installed - * @param monitor The {@link ITaskMonitor} to display errors. - * @param osSdkRoot The OS path of the SDK root folder. - * @param installFolder The folder where the archive will be installed. Note that this - * is <em>not</em> the folder where the archive was temporary - * unzipped. The installFolder, if it exists, contains the old - * archive that will soon be replaced by the new one. - * @return True if installing this archive shall continue, false if it should be skipped. - */ - public boolean preInstallHook(Archive archive, ITaskMonitor monitor, - String osSdkRoot, File installFolder) { - // Nothing to do in base class. - return true; - } - - /** - * Hook called right after a file has been unzipped (during an install). - * <p/> - * The base class implementation makes sure to properly adjust set executable - * permission on Linux and MacOS system if the zip entry was marked as +x. - * - * @param archive The archive that is being installed. - * @param monitor The {@link ITaskMonitor} to display errors. - * @param fileOp The {@link IFileOp} used by the archive installer. - * @param unzippedFile The file that has just been unzipped in the install temp directory. - * @param zipEntry The {@link ZipArchiveEntry} that has just been unzipped. - */ - public void postUnzipFileHook( - Archive archive, - ITaskMonitor monitor, - IFileOp fileOp, - File unzippedFile, - ZipArchiveEntry zipEntry) { - - // if needed set the permissions. - if (sUsingUnixPerm && fileOp.isFile(unzippedFile)) { - // get the mode and test if it contains the executable bit - int mode = zipEntry.getUnixMode(); - if ((mode & 0111) != 0) { - try { - fileOp.setExecutablePermission(unzippedFile); - } catch (IOException ignore) {} - } - } - - } - - /** - * Hook called right after an archive has been installed. - * - * @param archive The archive that has been installed. - * @param monitor The {@link ITaskMonitor} to display errors. - * @param installFolder The folder where the archive was successfully installed. - * Null if the installation failed, in case the archive needs to - * do some cleanup after <code>preInstallHook</code>. - */ - public void postInstallHook(Archive archive, ITaskMonitor monitor, File installFolder) { - // Nothing to do in base class. - } - - /** - * Returns whether the give package represents the same item as the current package. - * <p/> - * Two packages are considered the same if they represent the same thing, except for the - * revision number. - * @param pkg the package to compare. - * @return true if the item as equivalent. - */ - public abstract boolean sameItemAs(Package pkg); - - /** - * Computes whether the given package is a suitable update for the current package. - * <p/> - * An update is just that: a new package that supersedes the current one. If the new - * package does not represent the same item or if it has the same or lower revision as the - * current one, it's not an update. - * - * @param replacementPackage The potential replacement package. - * @return One of the {@link UpdateInfo} values. - * - * @see #sameItemAs(Package) - */ - public abstract UpdateInfo canBeUpdatedBy(Package replacementPackage); - - /** - * Returns an ordering <b>suitable for display</b> like this: <br/> - * - Tools <br/> - * - Platform-Tools <br/> - * - Docs. <br/> - * - Platform n preview <br/> - * - Platform n <br/> - * - Platform n-1 <br/> - * - Samples packages <br/> - * - Add-on based on n preview <br/> - * - Add-on based on n <br/> - * - Add-on based on n-1 <br/> - * - Extra packages <br/> - * <p/> - * Important: this must NOT be used to compare if two packages are the same thing. - * This is achieved by {@link #sameItemAs(Package)} or {@link #canBeUpdatedBy(Package)}. - * <p/> - * The order done here is suitable for display, and this may not be the appropriate - * order when comparing whether packages are equal or of greater revision -- if you need - * to compare revisions, then use {@link #getRevision()}{@code .compareTo(rev)} directly. - * <p/> - * This {@link #compareTo(Package)} method is purely an implementation detail to - * perform the right ordering of the packages in the list of available or installed packages. - * <p/> - * <em>Important</em>: Derived classes should consider overriding {@link #comparisonKey()} - * instead of this method. - */ - @Override - public int compareTo(Package other) { - String s1 = this.comparisonKey(); - String s2 = other.comparisonKey(); - - int r = s1.compareTo(s2); - return r; - } - - /** - * Computes a comparison key for each package used by {@link #compareTo(Package)}. - * The key is a string. - * The base package class return a string that encodes the package type, - * the revision number and the platform version, if applicable, in the form: - * <pre> - * t:N|v:NNNN.P|r:NNNN| - * </pre> - * All fields must start by a "letter colon" prefix and end with a vertical pipe (|, ASCII 124). - * <p/> - * The string format <em>may</em> change between releases and clients should not - * store them outside of the session or expect them to be consistent between - * different releases. They are purely an internal implementation details of the - * {@link #compareTo(Package)} method. - * <p/> - * Derived classes should get the string from the super class and then append - * or <em>insert</em> their own |-separated content. - * For example an extra vendor name & path can be inserted before the revision - * number, since it has more sorting weight. - */ - protected String comparisonKey() { - - StringBuilder sb = new StringBuilder(); - - sb.append("t:"); //$NON-NLS-1$ - if (this instanceof ToolPackage) { - sb.append(0); - } else if (this instanceof PlatformToolPackage) { - sb.append(1); - } else if (this instanceof DocPackage) { - sb.append(2); - } else if (this instanceof PlatformPackage) { - sb.append(3); - } else if (this instanceof SamplePackage) { - sb.append(4); - } else if (this instanceof SystemImagePackage) { - sb.append(5); - } else if (this instanceof AddonPackage) { - sb.append(6); - } else { - // extras and everything else - sb.append(9); - } - - - // We insert the package version here because it is more important - // than the revision number. - // In the list display, we want package version to be sorted - // top-down, so we'll use 10k-api as the sorting key. The day we - // reach 10k APIs, we'll need to revisit this. - sb.append("|v:"); //$NON-NLS-1$ - if (this instanceof IAndroidVersionProvider) { - AndroidVersion v = ((IAndroidVersionProvider) this).getAndroidVersion(); - - sb.append(String.format("%1$04d.%2$d", //$NON-NLS-1$ - 10000 - v.getApiLevel(), - v.isPreview() ? 1 : 0 - )); - } - - // Append revision number - sb.append("|r:"); //$NON-NLS-1$ - FullRevision rev = getRevision(); - sb.append(rev.getMajor()).append('.') - .append(rev.getMinor()).append('.') - .append(rev.getMicro()).append('.'); - // Hack: When comparing packages for installation purposes, we want to treat - // "final releases" packages as more important than rc/preview packages. - // However like for the API level above, when sorting for list display purposes - // we want the final release package listed before its rc/preview packages. - if (rev.isPreview()) { - sb.append(rev.getPreview()); - } else { - sb.append('0'); // 0=Final (!preview), to make "18.0" < "18.1" (18 Final < 18 RC1) - } - - sb.append('|'); - return sb.toString(); - } - - @Override - public int hashCode() { - final int prime = 31; - int result = 1; - result = prime * result + Arrays.hashCode(mArchives); - result = prime * result + ((mObsolete == null) ? 0 : mObsolete.hashCode()); - result = prime * result + getRevision().hashCode(); - result = prime * result + ((mSource == null) ? 0 : mSource.hashCode()); - return result; - } - - @Override - public boolean equals(Object obj) { - if (this == obj) { - return true; - } - if (obj == null) { - return false; - } - if (!(obj instanceof Package)) { - return false; - } - Package other = (Package) obj; - if (!Arrays.equals(mArchives, other.mArchives)) { - return false; - } - if (mObsolete == null) { - if (other.mObsolete != null) { - return false; - } - } else if (!mObsolete.equals(other.mObsolete)) { - return false; - } - if (!getRevision().equals(other.getRevision())) { - return false; - } - if (mSource == null) { - if (other.mSource != null) { - return false; - } - } else if (!mSource.equals(other.mSource)) { - return false; - } - return true; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/PackageParserUtils.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/PackageParserUtils.java deleted file mode 100755 index a6986e1..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/PackageParserUtils.java +++ /dev/null @@ -1,180 +0,0 @@ -/* - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.repository.SdkRepoConstants; - -import org.w3c.dom.Node; - -/** - * Misc utilities to help extracting elements and attributes out of an XML document. - */ -public class PackageParserUtils { - - /** - * Parses a full revision element such as <revision> or <min-tools-rev>. - * This supports both the single-integer format as well as the full revision - * format with major/minor/micro/preview sub-elements. - * - * @param revisionNode The node to parse. - * @return A new {@link FullRevision}. If parsing failed, major is set to - * {@link FullRevision#MISSING_MAJOR_REV}. - */ - public static FullRevision parseFullRevisionElement(Node revisionNode) { - // This needs to support two modes: - // - For repository XSD >= 7, <revision> contains sub-elements such as <major> or <minor>. - // - Otherwise for repository XSD < 7, <revision> contains an integer. - // The <major> element is mandatory, so it's easy to distinguish between both cases. - int major = FullRevision.MISSING_MAJOR_REV, - minor = FullRevision.IMPLICIT_MINOR_REV, - micro = FullRevision.IMPLICIT_MICRO_REV, - preview = FullRevision.NOT_A_PREVIEW; - - if (revisionNode != null) { - if (PackageParserUtils.findChildElement(revisionNode, - SdkRepoConstants.NODE_MAJOR_REV) != null) { - // <revision> has a <major> sub-element, so it's a repository XSD >= 7. - major = PackageParserUtils.getXmlInt(revisionNode, - SdkRepoConstants.NODE_MAJOR_REV, FullRevision.MISSING_MAJOR_REV); - minor = PackageParserUtils.getXmlInt(revisionNode, - SdkRepoConstants.NODE_MINOR_REV, FullRevision.IMPLICIT_MINOR_REV); - micro = PackageParserUtils.getXmlInt(revisionNode, - SdkRepoConstants.NODE_MICRO_REV, FullRevision.IMPLICIT_MICRO_REV); - preview = PackageParserUtils.getXmlInt(revisionNode, - SdkRepoConstants.NODE_PREVIEW, FullRevision.NOT_A_PREVIEW); - } else { - try { - String majorStr = revisionNode.getTextContent().trim(); - major = Integer.parseInt(majorStr); - } catch (Exception e) { - } - } - } - - return new FullRevision(major, minor, micro, preview); - } - - /** - * Returns the first child element with the given XML local name. - * If xmlLocalName is null, returns the very first child element. - */ - public static Node findChildElement(Node node, String xmlLocalName) { - if (node != null) { - String nsUri = node.getNamespaceURI(); - for(Node child = node.getFirstChild(); child != null; child = child.getNextSibling()) { - if (child.getNodeType() == Node.ELEMENT_NODE && - nsUri.equals(child.getNamespaceURI())) { - if (xmlLocalName == null || xmlLocalName.equals(child.getLocalName())) { - return child; - } - } - } - } - return null; - } - - /** - * Retrieves the value of that XML element as a string. - * Returns an empty string whether the element is missing or empty, - * so you can't tell the difference. - * <p/> - * Note: use {@link #getOptionalXmlString(Node, String)} if you need to know when the - * element is missing versus empty. - * - * @param node The XML <em>parent</em> node to parse. - * @param xmlLocalName The XML local name to find in the parent node. - * @return The text content of the element. Returns an empty string whether the element - * is missing or empty, so you can't tell the difference. - */ - public static String getXmlString(Node node, String xmlLocalName) { - Node child = findChildElement(node, xmlLocalName); - - return child == null ? "" : child.getTextContent(); //$NON-NLS-1$ - } - - /** - * Retrieves the value of that XML element as a string. - * Returns null when the element is missing, so you can tell between a missing element - * and an empty one. - * <p/> - * Note: use {@link #getXmlString(Node, String)} if you don't need to know when the - * element is missing versus empty. - * - * @param node The XML <em>parent</em> node to parse. - * @param xmlLocalName The XML local name to find in the parent node. - * @return The text content of the element. Returns null when the element is missing. - * Returns an empty string whether the element is present but empty. - */ - public static String getOptionalXmlString(Node node, String xmlLocalName) { - Node child = findChildElement(node, xmlLocalName); - - return child == null ? null : child.getTextContent(); //$NON-NLS-1$ - } - - /** - * Retrieves the value of that XML element as an integer. - * Returns the default value when the element is missing or is not an integer. - */ - public static int getXmlInt(Node node, String xmlLocalName, int defaultValue) { - String s = getXmlString(node, xmlLocalName); - try { - return Integer.parseInt(s); - } catch (NumberFormatException e) { - return defaultValue; - } - } - - /** - * Retrieves the value of that XML element as a long. - * Returns the default value when the element is missing or is not an integer. - */ - public static long getXmlLong(Node node, String xmlLocalName, long defaultValue) { - String s = getXmlString(node, xmlLocalName); - try { - return Long.parseLong(s); - } catch (NumberFormatException e) { - return defaultValue; - } - } - - /** - * Retrieve an attribute which value must match one of the given enums using a - * case-insensitive name match. - * - * Returns defaultValue if the attribute does not exist or its value does not match - * the given enum values. - */ - public static Object getEnumAttribute( - Node archiveNode, - String attrName, - Object[] values, - Object defaultValue) { - - Node attr = archiveNode.getAttributes().getNamedItem(attrName); - if (attr != null) { - String found = attr.getNodeValue(); - for (Object value : values) { - if (value.toString().equalsIgnoreCase(found)) { - return value; - } - } - } - - return defaultValue; - } - -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/PlatformPackage.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/PlatformPackage.java deleted file mode 100755 index 71d91ef..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/PlatformPackage.java +++ /dev/null @@ -1,353 +0,0 @@ -/* - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.SdkConstants; -import com.android.annotations.NonNull; -import com.android.annotations.VisibleForTesting; -import com.android.annotations.VisibleForTesting.Visibility; -import com.android.sdklib.AndroidVersion; -import com.android.sdklib.IAndroidTarget; -import com.android.sdklib.SdkManager; -import com.android.sdklib.internal.repository.IDescription; -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; -import com.android.sdklib.internal.repository.sources.SdkSource; -import com.android.sdklib.repository.PkgProps; -import com.android.sdklib.repository.SdkRepoConstants; -import com.android.utils.Pair; - -import org.w3c.dom.Node; - -import java.io.File; -import java.util.Map; -import java.util.Properties; - -/** - * Represents a platform XML node in an SDK repository. - */ -public class PlatformPackage extends MinToolsPackage - implements IAndroidVersionProvider, ILayoutlibVersion { - - /** The package version, for platform, add-on and doc packages. */ - private final AndroidVersion mVersion; - - /** The version, a string, for platform packages. */ - private final String mVersionName; - - /** The ABI of the system-image included in this platform. Can be null but not empty. */ - private final String mIncludedAbi; - - /** The helper handling the layoutlib version. */ - private final LayoutlibVersionMixin mLayoutlibVersion; - - /** - * Creates a new platform package from the attributes and elements of the given XML node. - * This constructor should throw an exception if the package cannot be created. - * - * @param source The {@link SdkSource} where this is loaded from. - * @param packageNode The XML element being parsed. - * @param nsUri The namespace URI of the originating XML document, to be able to deal with - * parameters that vary according to the originating XML schema. - * @param licenses The licenses loaded from the XML originating document. - */ - public PlatformPackage( - SdkSource source, - Node packageNode, - String nsUri, - Map<String,String> licenses) { - super(source, packageNode, nsUri, licenses); - - mVersionName = - PackageParserUtils.getXmlString(packageNode, SdkRepoConstants.NODE_VERSION); - - int apiLevel = - PackageParserUtils.getXmlInt (packageNode, SdkRepoConstants.NODE_API_LEVEL, 0); - String codeName = - PackageParserUtils.getXmlString(packageNode, SdkRepoConstants.NODE_CODENAME); - if (codeName.length() == 0) { - codeName = null; - } - mVersion = new AndroidVersion(apiLevel, codeName); - - mIncludedAbi = PackageParserUtils.getOptionalXmlString(packageNode, - SdkRepoConstants.NODE_ABI_INCLUDED); - - mLayoutlibVersion = new LayoutlibVersionMixin(packageNode); - } - - /** - * Creates a new platform package based on an actual {@link IAndroidTarget} (which - * must have {@link IAndroidTarget#isPlatform()} true) from the {@link SdkManager}. - * This is used to list local SDK folders in which case there is one archive which - * URL is the actual target location. - * <p/> - * By design, this creates a package with one and only one archive. - */ - public static Package create(IAndroidTarget target, Properties props) { - return new PlatformPackage(target, props); - } - - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected PlatformPackage(IAndroidTarget target, Properties props) { - this(null /*source*/, target, props); - } - - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected PlatformPackage(SdkSource source, IAndroidTarget target, Properties props) { - super( source, //source - props, //properties - target.getRevision(), //revision - null, //license - target.getDescription(), //description - null, //descUrl - Os.getCurrentOs(), //archiveOs - Arch.getCurrentArch(), //archiveArch - target.getLocation() //archiveOsPath - ); - - mVersion = target.getVersion(); - mVersionName = target.getVersionName(); - mLayoutlibVersion = new LayoutlibVersionMixin(props); - mIncludedAbi = props == null ? null : props.getProperty(PkgProps.PLATFORM_INCLUDED_ABI); - } - - /** - * Save the properties of the current packages in the given {@link Properties} object. - * These properties will later be given to a constructor that takes a {@link Properties} object. - */ - @Override - public void saveProperties(Properties props) { - super.saveProperties(props); - - mVersion.saveProperties(props); - mLayoutlibVersion.saveProperties(props); - - if (mVersionName != null) { - props.setProperty(PkgProps.PLATFORM_VERSION, mVersionName); - } - - if (mIncludedAbi != null) { - props.setProperty(PkgProps.PLATFORM_INCLUDED_ABI, mIncludedAbi); - } - - } - - /** Returns the version, a string, for platform packages. */ - public String getVersionName() { - return mVersionName; - } - - /** Returns the package version, for platform, add-on and doc packages. */ - @Override @NonNull - public AndroidVersion getAndroidVersion() { - return mVersion; - } - - /** - * Returns the ABI of the system-image included in this platform. - * - * @return Null if the platform does not include any system-image. - * Otherwise should be a valid non-empty ABI string (e.g. "x86" or "armeabi-v7a"). - */ - public String getIncludedAbi() { - return mIncludedAbi; - } - - /** - * Returns the layoutlib version. Mandatory starting with repository XSD rev 4. - * <p/> - * The first integer is the API of layoublib, which should be > 0. - * It will be equal to {@link ILayoutlibVersion#LAYOUTLIB_API_NOT_SPECIFIED} (0) - * if the layoutlib version isn't specified. - * <p/> - * The second integer is the revision for that given API. It is >= 0 - * and works as a minor revision number, incremented for the same API level. - * - * @since sdk-repository-4.xsd - */ - @Override - public Pair<Integer, Integer> getLayoutlibVersion() { - return mLayoutlibVersion.getLayoutlibVersion(); - } - - /** - * Returns a string identifier to install this package from the command line. - * For platforms, we use "android-N" where N is the API or the preview codename. - * <p/> - * {@inheritDoc} - */ - @Override - public String installId() { - return "android-" + mVersion.getApiString(); //$NON-NLS-1$ - } - - /** - * Returns a description of this package that is suitable for a list display. - * <p/> - * {@inheritDoc} - */ - @Override - public String getListDescription() { - String s; - - if (mVersion.isPreview()) { - s = String.format("SDK Platform Android %1$s Preview%2$s", - getVersionName(), - isObsolete() ? " (Obsolete)" : ""); //$NON-NLS-2$ - } else { - s = String.format("SDK Platform Android %1$s%2$s", - getVersionName(), - isObsolete() ? " (Obsolete)" : ""); //$NON-NLS-2$ - } - - return s; - } - - /** - * Returns a short description for an {@link IDescription}. - */ - @Override - public String getShortDescription() { - String s; - - if (mVersion.isPreview()) { - s = String.format("SDK Platform Android %1$s Preview, revision %2$s%3$s", - getVersionName(), - getRevision().toShortString(), - isObsolete() ? " (Obsolete)" : ""); //$NON-NLS-2$ - } else { - s = String.format("SDK Platform Android %1$s, API %2$d, revision %3$s%4$s", - getVersionName(), - mVersion.getApiLevel(), - getRevision().toShortString(), - isObsolete() ? " (Obsolete)" : ""); //$NON-NLS-2$ - } - - return s; - } - - /** - * Returns a long description for an {@link IDescription}. - * - * The long description is whatever the XML contains for the <description> field, - * or the short description if the former is empty. - */ - @Override - public String getLongDescription() { - String s = getDescription(); - if (s == null || s.length() == 0) { - s = getShortDescription(); - } - - if (s.indexOf("revision") == -1) { - s += String.format("\nRevision %1$s%2$s", - getRevision().toShortString(), - isObsolete() ? " (Obsolete)" : ""); - } - - return s; - } - - /** - * Computes a potential installation folder if an archive of this package were - * to be installed right away in the given SDK root. - * <p/> - * A platform package is typically installed in SDK/platforms/android-"version". - * However if we can find a different directory under SDK/platform that already - * has this platform version installed, we'll use that one. - * - * @param osSdkRoot The OS path of the SDK root folder. - * @param sdkManager An existing SDK manager to list current platforms and addons. - * @return A new {@link File} corresponding to the directory to use to install this package. - */ - @Override - public File getInstallFolder(String osSdkRoot, SdkManager sdkManager) { - - // First find if this platform is already installed. If so, reuse the same directory. - for (IAndroidTarget target : sdkManager.getTargets()) { - if (target.isPlatform() && target.getVersion().equals(mVersion)) { - return new File(target.getLocation()); - } - } - - File platforms = new File(osSdkRoot, SdkConstants.FD_PLATFORMS); - File folder = new File(platforms, - String.format("android-%s", getAndroidVersion().getApiString())); //$NON-NLS-1$ - - return folder; - } - - @Override - public boolean sameItemAs(Package pkg) { - if (pkg instanceof PlatformPackage) { - PlatformPackage newPkg = (PlatformPackage)pkg; - - // check they are the same version. - return newPkg.getAndroidVersion().equals(this.getAndroidVersion()); - } - - return false; - } - - @Override - public int hashCode() { - final int prime = 31; - int result = super.hashCode(); - result = prime * result + - ((mLayoutlibVersion == null) ? 0 : mLayoutlibVersion.hashCode()); - result = prime * result + ((mVersion == null) ? 0 : mVersion.hashCode()); - result = prime * result + ((mVersionName == null) ? 0 : mVersionName.hashCode()); - return result; - } - - @Override - public boolean equals(Object obj) { - if (this == obj) { - return true; - } - if (!super.equals(obj)) { - return false; - } - if (!(obj instanceof PlatformPackage)) { - return false; - } - PlatformPackage other = (PlatformPackage) obj; - if (mLayoutlibVersion == null) { - if (other.mLayoutlibVersion != null) { - return false; - } - } else if (!mLayoutlibVersion.equals(other.mLayoutlibVersion)) { - return false; - } - if (mVersion == null) { - if (other.mVersion != null) { - return false; - } - } else if (!mVersion.equals(other.mVersion)) { - return false; - } - if (mVersionName == null) { - if (other.mVersionName != null) { - return false; - } - } else if (!mVersionName.equals(other.mVersionName)) { - return false; - } - return true; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/PlatformToolPackage.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/PlatformToolPackage.java deleted file mode 100755 index c46e940..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/PlatformToolPackage.java +++ /dev/null @@ -1,270 +0,0 @@ -/* - * Copyright (C) 2010 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.SdkConstants; -import com.android.annotations.VisibleForTesting; -import com.android.annotations.VisibleForTesting.Visibility; -import com.android.sdklib.SdkManager; -import com.android.sdklib.internal.repository.AdbWrapper; -import com.android.sdklib.internal.repository.IDescription; -import com.android.sdklib.internal.repository.ITaskMonitor; -import com.android.sdklib.internal.repository.archives.Archive; -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; -import com.android.sdklib.internal.repository.sources.SdkSource; - -import org.w3c.dom.Node; - -import java.io.File; -import java.util.HashSet; -import java.util.Map; -import java.util.Properties; -import java.util.Set; - -/** - * Represents a platform-tool XML node in an SDK repository. - */ -public class PlatformToolPackage extends FullRevisionPackage { - - /** The value returned by {@link PlatformToolPackage#installId()}. */ - public static final String INSTALL_ID = "platform-tools"; //$NON-NLS-1$ - /** The value returned by {@link PlatformToolPackage#installId()}. */ - public static final String INSTALL_ID_PREVIEW = "platform-tools-preview"; //$NON-NLS-1$ - - /** - * Creates a new platform-tool package from the attributes and elements of the given XML node. - * This constructor should throw an exception if the package cannot be created. - * - * @param source The {@link SdkSource} where this is loaded from. - * @param packageNode The XML element being parsed. - * @param nsUri The namespace URI of the originating XML document, to be able to deal with - * parameters that vary according to the originating XML schema. - * @param licenses The licenses loaded from the XML originating document. - */ - public PlatformToolPackage(SdkSource source, Node packageNode, - String nsUri, Map<String,String> licenses) { - super(source, packageNode, nsUri, licenses); - } - - /** - * Manually create a new package with one archive and the given attributes or properties. - * This is used to create packages from local directories in which case there must be - * one archive which URL is the actual target location. - * <p/> - * By design, this creates a package with one and only one archive. - */ - public static Package create( - SdkSource source, - Properties props, - int revision, - String license, - String description, - String descUrl, - Os archiveOs, - Arch archiveArch, - String archiveOsPath) { - - PlatformToolPackage ptp = new PlatformToolPackage(source, props, revision, license, - description, descUrl, archiveOs, archiveArch, archiveOsPath); - - File platformToolsFolder = new File(archiveOsPath); - String error = null; - if (!platformToolsFolder.isDirectory()) { - error = "platform-tools folder is missing"; - } else { - File[] files = platformToolsFolder.listFiles(); - if (files == null || files.length == 0) { - error = "platform-tools folder is empty"; - } else { - Set<String> names = new HashSet<String>(); - for (File file : files) { - names.add(file.getName()); - } - for (String name : new String[] { SdkConstants.FN_ADB, - SdkConstants.FN_AAPT, - SdkConstants.FN_AIDL, - SdkConstants.FN_DX } ) { - if (!names.contains(name)) { - if (error == null) { - error = "platform-tools folder is missing "; - } else { - error += ", "; - } - error += name; - } - } - } - } - - if (error != null) { - String shortDesc = ptp.getShortDescription() + " [*]"; //$NON-NLS-1$ - - String longDesc = String.format( - "Broken Platform-Tools Package: %1$s\n" + - "[*] Package cannot be used due to error: %2$s", - description, - error); - - BrokenPackage ba = new BrokenPackage(props, shortDesc, longDesc, - IMinApiLevelDependency.MIN_API_LEVEL_NOT_SPECIFIED, - IExactApiLevelDependency.API_LEVEL_INVALID, - archiveOsPath); - return ba; - } - - - return ptp; - } - - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected PlatformToolPackage( - SdkSource source, - Properties props, - int revision, - String license, - String description, - String descUrl, - Os archiveOs, - Arch archiveArch, - String archiveOsPath) { - super(source, - props, - revision, - license, - description, - descUrl, - archiveOs, - archiveArch, - archiveOsPath); - } - - /** - * Returns a string identifier to install this package from the command line. - * For platform-tools, we use "platform-tools" or "platform-tools-preview" since - * this package type is unique. - * <p/> - * {@inheritDoc} - */ - @Override - public String installId() { - if (getRevision().isPreview()) { - return INSTALL_ID_PREVIEW; - } else { - return INSTALL_ID; - } - } - - /** - * Returns a description of this package that is suitable for a list display. - * <p/> - * {@inheritDoc} - */ - @Override - public String getListDescription() { - return String.format("Android SDK Platform-tools%1$s", - isObsolete() ? " (Obsolete)" : ""); - } - - /** - * Returns a short description for an {@link IDescription}. - */ - @Override - public String getShortDescription() { - return String.format("Android SDK Platform-tools, revision %1$s%2$s", - getRevision().toShortString(), - isObsolete() ? " (Obsolete)" : ""); - } - - /** Returns a long description for an {@link IDescription}. */ - @Override - public String getLongDescription() { - String s = getDescription(); - if (s == null || s.length() == 0) { - s = getShortDescription(); - } - - if (s.indexOf("revision") == -1) { - s += String.format("\nRevision %1$s%2$s", - getRevision().toShortString(), - isObsolete() ? " (Obsolete)" : ""); - } - - return s; - } - - /** - * Computes a potential installation folder if an archive of this package were - * to be installed right away in the given SDK root. - * <p/> - * A "tool" package should always be located in SDK/tools. - * - * @param osSdkRoot The OS path of the SDK root folder. - * @param sdkManager An existing SDK manager to list current platforms and addons. - * @return A new {@link File} corresponding to the directory to use to install this package. - */ - @Override - public File getInstallFolder(String osSdkRoot, SdkManager sdkManager) { - return new File(osSdkRoot, SdkConstants.FD_PLATFORM_TOOLS); - } - - /** - * Check whether 2 platform-tool packages are the same <em>and</em> have the - * same preview bit. - */ - @Override - public boolean sameItemAs(Package pkg) { - return sameItemAs(pkg, false /*ignorePreviews*/); - } - - @Override - public boolean sameItemAs(Package pkg, boolean ignorePreviews) { - // only one platform-tool package so any platform-tool package is the same item. - if (pkg instanceof PlatformToolPackage) { - if (ignorePreviews) { - return true; - } else { - // however previews can only match previews by default, unless we ignore that check. - return ((PlatformToolPackage) pkg).getRevision().isPreview() == - getRevision().isPreview(); - } - } - return false; - } - - /** - * Hook called right before an archive is installed. - * This is used here to stop ADB before trying to replace the platform-tool package. - * - * @param archive The archive that will be installed - * @param monitor The {@link ITaskMonitor} to display errors. - * @param osSdkRoot The OS path of the SDK root folder. - * @param installFolder The folder where the archive will be installed. Note that this - * is <em>not</em> the folder where the archive was temporary - * unzipped. The installFolder, if it exists, contains the old - * archive that will soon be replaced by the new one. - * @return True if installing this archive shall continue, false if it should be skipped. - */ - @Override - public boolean preInstallHook(Archive archive, ITaskMonitor monitor, - String osSdkRoot, File installFolder) { - AdbWrapper aw = new AdbWrapper(osSdkRoot, monitor); - aw.stopAdb(); - return super.preInstallHook(archive, monitor, osSdkRoot, installFolder); - } - -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/SamplePackage.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/SamplePackage.java deleted file mode 100755 index 06eabb9..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/SamplePackage.java +++ /dev/null @@ -1,536 +0,0 @@ -/* - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.SdkConstants; -import com.android.annotations.NonNull; -import com.android.sdklib.AndroidVersion; -import com.android.sdklib.AndroidVersion.AndroidVersionException; -import com.android.sdklib.IAndroidTarget; -import com.android.sdklib.SdkManager; -import com.android.sdklib.internal.repository.IDescription; -import com.android.sdklib.internal.repository.ITaskMonitor; -import com.android.sdklib.internal.repository.archives.Archive; -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; -import com.android.sdklib.internal.repository.sources.SdkSource; -import com.android.sdklib.io.IFileOp; -import com.android.sdklib.repository.PkgProps; -import com.android.sdklib.repository.SdkRepoConstants; - -import org.apache.commons.compress.archivers.zip.ZipArchiveEntry; -import org.w3c.dom.Node; - -import java.io.File; -import java.io.FileInputStream; -import java.io.FileOutputStream; -import java.io.IOException; -import java.io.UnsupportedEncodingException; -import java.security.MessageDigest; -import java.security.NoSuchAlgorithmException; -import java.util.Map; -import java.util.Properties; - -/** - * Represents a sample XML node in an SDK repository. - */ -public class SamplePackage extends MinToolsPackage - implements IAndroidVersionProvider, IMinApiLevelDependency { - - /** The matching platform version. */ - private final AndroidVersion mVersion; - - /** - * The minimal API level required by this extra package, if > 0, - * or {@link #MIN_API_LEVEL_NOT_SPECIFIED} if there is no such requirement. - */ - private final int mMinApiLevel; - - /** - * Creates a new sample package from the attributes and elements of the given XML node. - * This constructor should throw an exception if the package cannot be created. - * - * @param source The {@link SdkSource} where this is loaded from. - * @param packageNode The XML element being parsed. - * @param nsUri The namespace URI of the originating XML document, to be able to deal with - * parameters that vary according to the originating XML schema. - * @param licenses The licenses loaded from the XML originating document. - */ - public SamplePackage(SdkSource source, - Node packageNode, - String nsUri, - Map<String,String> licenses) { - super(source, packageNode, nsUri, licenses); - - int apiLevel = - PackageParserUtils.getXmlInt (packageNode, SdkRepoConstants.NODE_API_LEVEL, 0); - String codeName = - PackageParserUtils.getXmlString(packageNode, SdkRepoConstants.NODE_CODENAME); - if (codeName.length() == 0) { - codeName = null; - } - mVersion = new AndroidVersion(apiLevel, codeName); - - mMinApiLevel = PackageParserUtils.getXmlInt(packageNode, - SdkRepoConstants.NODE_MIN_API_LEVEL, - MIN_API_LEVEL_NOT_SPECIFIED); - } - - /** - * Creates a new sample package based on an actual {@link IAndroidTarget} (which - * must have {@link IAndroidTarget#isPlatform()} true) from the {@link SdkManager}. - * <p/> - * The target <em>must</em> have an existing sample directory that uses the /samples - * root form rather than the old form where the samples dir was located under the - * platform dir. - * <p/> - * This is used to list local SDK folders in which case there is one archive which - * URL is the actual samples path location. - * <p/> - * By design, this creates a package with one and only one archive. - */ - public static Package create(IAndroidTarget target, Properties props) { - return new SamplePackage(target, props); - } - - private SamplePackage(IAndroidTarget target, Properties props) { - super( null, //source - props, //properties - 0, //revision will be taken from props - null, //license - null, //description - null, //descUrl - Os.ANY, //archiveOs - Arch.ANY, //archiveArch - target.getPath(IAndroidTarget.SAMPLES) //archiveOsPath - ); - - mVersion = target.getVersion(); - - mMinApiLevel = getPropertyInt(props, PkgProps.SAMPLE_MIN_API_LEVEL, - MIN_API_LEVEL_NOT_SPECIFIED); - } - - /** - * Creates a new sample package from an actual directory path and previously - * saved properties. - * <p/> - * This is used to list local SDK folders in which case there is one archive which - * URL is the actual samples path location. - * <p/> - * By design, this creates a package with one and only one archive. - * - * @throws AndroidVersionException if the {@link AndroidVersion} can't be restored - * from properties. - */ - public static Package create(String archiveOsPath, Properties props) - throws AndroidVersionException { - return new SamplePackage(archiveOsPath, props); - } - - private SamplePackage(String archiveOsPath, Properties props) throws AndroidVersionException { - super(null, //source - props, //properties - 0, //revision will be taken from props - null, //license - null, //description - null, //descUrl - Os.ANY, //archiveOs - Arch.ANY, //archiveArch - archiveOsPath //archiveOsPath - ); - - mVersion = new AndroidVersion(props); - - mMinApiLevel = getPropertyInt(props, PkgProps.SAMPLE_MIN_API_LEVEL, - MIN_API_LEVEL_NOT_SPECIFIED); - } - - /** - * Save the properties of the current packages in the given {@link Properties} object. - * These properties will later be given to a constructor that takes a {@link Properties} object. - */ - @Override - public void saveProperties(Properties props) { - super.saveProperties(props); - - mVersion.saveProperties(props); - - if (getMinApiLevel() != MIN_API_LEVEL_NOT_SPECIFIED) { - props.setProperty(PkgProps.SAMPLE_MIN_API_LEVEL, Integer.toString(getMinApiLevel())); - } - } - - /** - * Returns the minimal API level required by this extra package, if > 0, - * or {@link #MIN_API_LEVEL_NOT_SPECIFIED} if there is no such requirement. - */ - @Override - public int getMinApiLevel() { - return mMinApiLevel; - } - - /** Returns the matching platform version. */ - @Override @NonNull - public AndroidVersion getAndroidVersion() { - return mVersion; - } - - /** - * Returns a string identifier to install this package from the command line. - * For samples, we use "sample-N" where N is the API or the preview codename. - * <p/> - * {@inheritDoc} - */ - @Override - public String installId() { - return "sample-" + mVersion.getApiString(); //$NON-NLS-1$ - } - - /** - * Returns a description of this package that is suitable for a list display. - * <p/> - * {@inheritDoc} - */ - @Override - public String getListDescription() { - String s = String.format("Samples for SDK API %1$s%2$s%3$s", - mVersion.getApiString(), - mVersion.isPreview() ? " Preview" : "", - isObsolete() ? " (Obsolete)" : ""); - return s; - } - - /** - * Returns a short description for an {@link IDescription}. - */ - @Override - public String getShortDescription() { - String s = String.format("Samples for SDK API %1$s%2$s, revision %3$s%4$s", - mVersion.getApiString(), - mVersion.isPreview() ? " Preview" : "", - getRevision().toShortString(), - isObsolete() ? " (Obsolete)" : ""); - return s; - } - - /** - * Returns a long description for an {@link IDescription}. - * - * The long description is whatever the XML contains for the <description> field, - * or the short description if the former is empty. - */ - @Override - public String getLongDescription() { - String s = getDescription(); - if (s == null || s.length() == 0) { - s = getShortDescription(); - } - - if (s.indexOf("revision") == -1) { - s += String.format("\nRevision %1$s%2$s", - getRevision().toShortString(), - isObsolete() ? " (Obsolete)" : ""); - } - - return s; - } - - /** - * Computes a potential installation folder if an archive of this package were - * to be installed right away in the given SDK root. - * <p/> - * A sample package is typically installed in SDK/samples/android-"version". - * However if we can find a different directory that already has this sample - * version installed, we'll use that one. - * - * @param osSdkRoot The OS path of the SDK root folder. - * @param sdkManager An existing SDK manager to list current platforms and addons. - * @return A new {@link File} corresponding to the directory to use to install this package. - */ - @Override - public File getInstallFolder(String osSdkRoot, SdkManager sdkManager) { - - // The /samples dir at the root of the SDK - File samplesRoot = new File(osSdkRoot, SdkConstants.FD_SAMPLES); - - // First find if this sample is already installed. If so, reuse the same directory. - for (IAndroidTarget target : sdkManager.getTargets()) { - if (target.isPlatform() && - target.getVersion().equals(mVersion)) { - String p = target.getPath(IAndroidTarget.SAMPLES); - File f = new File(p); - if (f.isDirectory()) { - // We *only* use this directory if it's using the "new" location - // under SDK/samples. We explicitly do not reuse the "old" location - // under SDK/platform/android-N/samples. - if (f.getParentFile().equals(samplesRoot)) { - return f; - } - } - } - } - - // Otherwise, get a suitable default - File folder = new File(samplesRoot, - String.format("android-%s", getAndroidVersion().getApiString())); //$NON-NLS-1$ - - for (int n = 1; folder.exists(); n++) { - // Keep trying till we find an unused directory. - folder = new File(samplesRoot, - String.format("android-%s_%d", getAndroidVersion().getApiString(), n)); //$NON-NLS-1$ - } - - return folder; - } - - @Override - public boolean sameItemAs(Package pkg) { - if (pkg instanceof SamplePackage) { - SamplePackage newPkg = (SamplePackage)pkg; - - // check they are the same version. - return newPkg.getAndroidVersion().equals(this.getAndroidVersion()); - } - - return false; - } - - /** - * Makes sure the base /samples folder exists before installing. - * - * {@inheritDoc} - */ - @Override - public boolean preInstallHook(Archive archive, - ITaskMonitor monitor, - String osSdkRoot, - File installFolder) { - - if (installFolder != null && installFolder.isDirectory()) { - // Get the hash computed during the last installation - String storedHash = readContentHash(installFolder); - if (storedHash != null && storedHash.length() > 0) { - - // Get the hash of the folder now - String currentHash = computeContentHash(installFolder); - - if (!storedHash.equals(currentHash)) { - // The hashes differ. The content was modified. - // Ask the user if we should still wipe the old samples. - - String pkgName = archive.getParentPackage().getShortDescription(); - - String msg = String.format( - "-= Warning ! =-\n" + - "You are about to replace the content of the folder:\n " + - " %1$s\n" + - "by the new package:\n" + - " %2$s.\n" + - "\n" + - "However it seems that the content of the existing samples " + - "has been modified since it was last installed. Are you sure " + - "you want to DELETE the existing samples? This cannot be undone.\n" + - "Please select YES to delete the existing sample and replace them " + - "by the new ones.\n" + - "Please select NO to skip this package. You can always install it later.", - installFolder.getAbsolutePath(), - pkgName); - - // Returns true if we can wipe & replace. - return monitor.displayPrompt("SDK Manager: overwrite samples?", msg); - } - } - } - - // The default is to allow installation - return super.preInstallHook(archive, monitor, osSdkRoot, installFolder); - } - - /** - * Computes a hash of the installed content (in case of successful install.) - * - * {@inheritDoc} - */ - @Override - public void postInstallHook(Archive archive, ITaskMonitor monitor, File installFolder) { - super.postInstallHook(archive, monitor, installFolder); - - if (installFolder != null) { - String h = computeContentHash(installFolder); - saveContentHash(installFolder, h); - } - } - - /** - * Set all the files from a sample package as read-only so that - * users don't end up modifying sources by mistake in Eclipse - * (samples are copied if using the NPW > Create from sample.) - */ - @Override - public void postUnzipFileHook( - Archive archive, - ITaskMonitor monitor, - IFileOp fileOp, - File unzippedFile, - ZipArchiveEntry zipEntry) { - super.postUnzipFileHook(archive, monitor, fileOp, unzippedFile, zipEntry); - - if (fileOp.isFile(unzippedFile) && - !SdkConstants.FN_SOURCE_PROP.equals(unzippedFile.getName())) { - fileOp.setReadOnly(unzippedFile); - } - } - - /** - * Reads the hash from the properties file, if it exists. - * Returns null if something goes wrong, e.g. there's no property file or - * it doesn't contain our hash. Returns an empty string if the hash wasn't - * correctly computed last time by {@link #saveContentHash(File, String)}. - */ - private String readContentHash(File folder) { - Properties props = new Properties(); - - FileInputStream fis = null; - try { - File f = new File(folder, SdkConstants.FN_CONTENT_HASH_PROP); - if (f.isFile()) { - fis = new FileInputStream(f); - props.load(fis); - return props.getProperty("content-hash", null); //$NON-NLS-1$ - } - } catch (Exception e) { - // ignore - } finally { - if (fis != null) { - try { - fis.close(); - } catch (IOException e) { - } - } - } - - return null; - } - - /** - * Saves the hash using a properties file - */ - private void saveContentHash(File folder, String hash) { - Properties props = new Properties(); - - props.setProperty("content-hash", hash == null ? "" : hash); //$NON-NLS-1$ //$NON-NLS-2$ - - FileOutputStream fos = null; - try { - File f = new File(folder, SdkConstants.FN_CONTENT_HASH_PROP); - fos = new FileOutputStream(f); - props.store( fos, "## Android - hash of this archive."); //$NON-NLS-1$ - } catch (IOException e) { - e.printStackTrace(); - } finally { - if (fos != null) { - try { - fos.close(); - } catch (IOException e) { - } - } - } - } - - /** - * Computes a hash of the files names and sizes installed in the folder - * using the SHA-1 digest. - * Returns null if the digest algorithm is not available. - */ - private String computeContentHash(File installFolder) { - MessageDigest md = null; - try { - // SHA-1 is a standard algorithm. - // http://java.sun.com/j2se/1.4.2/docs/guide/security/CryptoSpec.html#AppB - md = MessageDigest.getInstance("SHA-1"); //$NON-NLS-1$ - } catch (NoSuchAlgorithmException e) { - // We're unlikely to get there unless this JVM is not spec conforming - // in which case there won't be any hash available. - } - - if (md != null) { - hashDirectoryContent(installFolder, md); - return getDigestHexString(md); - } - - return null; - } - - /** - * Computes a hash of the *content* of this directory. The hash only uses - * the files names and the file sizes. - */ - private void hashDirectoryContent(File folder, MessageDigest md) { - if (folder == null || md == null || !folder.isDirectory()) { - return; - } - - for (File f : folder.listFiles()) { - if (f.isDirectory()) { - hashDirectoryContent(f, md); - - } else { - String name = f.getName(); - - // Skip the file we use to store the content hash - if (name == null || SdkConstants.FN_CONTENT_HASH_PROP.equals(name)) { - continue; - } - - try { - md.update(name.getBytes("UTF-8")); //$NON-NLS-1$ - } catch (UnsupportedEncodingException e) { - // There is no valid reason for UTF-8 to be unsupported. Ignore. - } - try { - long len = f.length(); - md.update((byte) (len & 0x0FF)); - md.update((byte) ((len >> 8) & 0x0FF)); - md.update((byte) ((len >> 16) & 0x0FF)); - md.update((byte) ((len >> 24) & 0x0FF)); - - } catch (SecurityException e) { - // Might happen if file is not readable. Ignore. - } - } - } - } - - /** - * Returns a digest as an hex string. - */ - private String getDigestHexString(MessageDigest digester) { - // Create an hex string from the digest - byte[] digest = digester.digest(); - int n = digest.length; - String hex = "0123456789abcdef"; //$NON-NLS-1$ - char[] hexDigest = new char[n * 2]; - for (int i = 0; i < n; i++) { - int b = digest[i] & 0x0FF; - hexDigest[i*2 + 0] = hex.charAt(b >>> 4); - hexDigest[i*2 + 1] = hex.charAt(b & 0x0f); - } - - return new String(hexDigest); - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/SourcePackage.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/SourcePackage.java deleted file mode 100755 index fb38f40..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/SourcePackage.java +++ /dev/null @@ -1,340 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.SdkConstants; -import com.android.annotations.NonNull; -import com.android.annotations.VisibleForTesting; -import com.android.annotations.VisibleForTesting.Visibility; -import com.android.sdklib.AndroidVersion; -import com.android.sdklib.AndroidVersion.AndroidVersionException; -import com.android.sdklib.SdkManager; -import com.android.sdklib.internal.repository.IDescription; -import com.android.sdklib.internal.repository.ITaskMonitor; -import com.android.sdklib.internal.repository.archives.Archive; -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; -import com.android.sdklib.internal.repository.sources.SdkSource; -import com.android.sdklib.io.IFileOp; -import com.android.sdklib.repository.SdkRepoConstants; - -import org.apache.commons.compress.archivers.zip.ZipArchiveEntry; -import org.w3c.dom.Node; - -import java.io.File; -import java.util.Map; -import java.util.Properties; - -/** - * Represents a source XML node in an SDK repository. - * <p/> - * Note that a source package has a version and thus implements {@link IAndroidVersionProvider}. - * However there is no mandatory dependency that limits installation so this does not - * implement {@link IPlatformDependency}. - */ -public class SourcePackage extends MajorRevisionPackage implements IAndroidVersionProvider { - - /** The package version, for platform, add-on and doc packages. */ - private final AndroidVersion mVersion; - - /** - * Creates a new source package from the attributes and elements of the given XML node. - * This constructor should throw an exception if the package cannot be created. - * - * @param source The {@link SdkSource} where this is loaded from. - * @param packageNode The XML element being parsed. - * @param nsUri The namespace URI of the originating XML document, to be able to deal with - * parameters that vary according to the originating XML schema. - * @param licenses The licenses loaded from the XML originating document. - */ - public SourcePackage(SdkSource source, - Node packageNode, - String nsUri, - Map<String,String> licenses) { - super(source, packageNode, nsUri, licenses); - - int apiLevel = - PackageParserUtils.getXmlInt(packageNode, SdkRepoConstants.NODE_API_LEVEL, 0); - String codeName = - PackageParserUtils.getXmlString(packageNode, SdkRepoConstants.NODE_CODENAME); - if (codeName.length() == 0) { - codeName = null; - } - mVersion = new AndroidVersion(apiLevel, codeName); - } - - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected SourcePackage( - AndroidVersion platformVersion, - int revision, - Properties props, - String localOsPath) { - this(null /*source*/, platformVersion, revision, props, localOsPath); - } - - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected SourcePackage( - SdkSource source, - AndroidVersion platformVersion, - int revision, - Properties props, - String localOsPath) { - super( source, //source - props, //properties - revision, //revision - null, //license - null, //description - null, //descUrl - Os.getCurrentOs(), //archiveOs - Arch.getCurrentArch(), //archiveArch - localOsPath //archiveOsPath - ); - mVersion = platformVersion; - } - - /** - * Creates either a valid {@link SourcePackage} or a {@link BrokenPackage}. - * <p/> - * If the source directory contains valid properties, this creates a new {@link SourcePackage} - * with the android version listed in the properties. - * Otherwise returns a new {@link BrokenPackage} with some explanation on what failed. - * - * @param srcDir The SDK/sources/android-N folder - * @param props The properties located in {@code srcDir} or null if not found. - * @return A new {@link SourcePackage} or a new {@link BrokenPackage}. - */ - public static Package create(File srcDir, Properties props) { - AndroidVersion version = null; - String error = null; - - // Try to load the android version from the sources.props. - // If we don't find them, it would explain why this package is broken. - if (props == null) { - error = String.format("Missing file %1$s", SdkConstants.FN_SOURCE_PROP); - } else { - try { - version = new AndroidVersion(props); - // The constructor will extract the revision from the properties - // and it will not consider a missing revision as being fatal. - return new SourcePackage(version, 0 /*revision*/, props, srcDir.getAbsolutePath()); - } catch (AndroidVersionException e) { - error = String.format("Invalid file %1$s: %2$s", - SdkConstants.FN_SOURCE_PROP, - e.getMessage()); - } - } - - if (version == null) { - try { - // Try to parse the first number out of the platform folder name. - // This is just a wild guess in case we can create a broken package using that info. - String platform = srcDir.getParentFile().getName(); - platform = platform.replaceAll("[^0-9]+", " ").trim(); //$NON-NLS-1$ //$NON-NLS-2$ - int pos = platform.indexOf(' '); - if (pos >= 0) { - platform = platform.substring(0, pos); - } - int apiLevel = Integer.parseInt(platform); - version = new AndroidVersion(apiLevel, null /*codename*/); - } catch (Exception ignore) { - } - } - - StringBuilder sb = new StringBuilder("Broken Source Package"); - if (version != null) { - sb.append(String.format(", API %1$s", version.getApiString())); - } - - String shortDesc = sb.toString(); - - if (error != null) { - sb.append('\n').append(error); - } - - String longDesc = sb.toString(); - - return new BrokenPackage(props, shortDesc, longDesc, - IMinApiLevelDependency.MIN_API_LEVEL_NOT_SPECIFIED, - version==null ? IExactApiLevelDependency.API_LEVEL_INVALID : version.getApiLevel(), - srcDir.getAbsolutePath()); - } - - /** - * Save the properties of the current packages in the given {@link Properties} object. - * These properties will later be given to a constructor that takes a {@link Properties} object. - */ - @Override - public void saveProperties(Properties props) { - super.saveProperties(props); - mVersion.saveProperties(props); - } - - /** - * Returns the android version of this package. - */ - @Override @NonNull - public AndroidVersion getAndroidVersion() { - return mVersion; - } - - /** - * Returns a string identifier to install this package from the command line. - * For sources, we use "source-N" where N is the API or the preview codename. - * <p/> - * {@inheritDoc} - */ - @Override - public String installId() { - return "source-" + mVersion.getApiString(); //$NON-NLS-1$ - } - - /** - * Returns a description of this package that is suitable for a list display. - * <p/> - * {@inheritDoc} - */ - @Override - public String getListDescription() { - if (mVersion.isPreview()) { - return String.format("Sources for Android '%1$s' Preview SDK%2$s", - mVersion.getCodename(), - isObsolete() ? " (Obsolete)" : ""); - } else { - return String.format("Sources for Android SDK%2$s", - mVersion.getApiLevel(), - isObsolete() ? " (Obsolete)" : ""); - } - } - - /** - * Returns a short description for an {@link IDescription}. - */ - @Override - public String getShortDescription() { - if (mVersion.isPreview()) { - return String.format("Sources for Android '%1$s' Preview SDK, revision %2$s%3$s", - mVersion.getCodename(), - getRevision().toShortString(), - isObsolete() ? " (Obsolete)" : ""); - } else { - return String.format("Sources for Android SDK, API %1$d, revision %2$s%3$s", - mVersion.getApiLevel(), - getRevision().toShortString(), - isObsolete() ? " (Obsolete)" : ""); - } - } - - /** - * Returns a long description for an {@link IDescription}. - * - * The long description is whatever the XML contains for the {@code description} field, - * or the short description if the former is empty. - */ - @Override - public String getLongDescription() { - String s = getDescription(); - if (s == null || s.length() == 0) { - s = getShortDescription(); - } - - if (s.indexOf("revision") == -1) { - s += String.format("\nRevision %1$s%2$s", - getRevision().toShortString(), - isObsolete() ? " (Obsolete)" : ""); - } - - return s; - } - - /** - * Computes a potential installation folder if an archive of this package were - * to be installed right away in the given SDK root. - * <p/> - * A sources package is typically installed in SDK/sources/platform. - * - * @param osSdkRoot The OS path of the SDK root folder. - * @param sdkManager An existing SDK manager to list current platforms and addons. - * @return A new {@link File} corresponding to the directory to use to install this package. - */ - @Override - public File getInstallFolder(String osSdkRoot, SdkManager sdkManager) { - File folder = new File(osSdkRoot, SdkConstants.FD_PKG_SOURCES); - folder = new File(folder, "android-" + mVersion.getApiString()); //$NON-NLS-1$ - return folder; - } - - /** - * Set all the files from a source package as read-only - * so that users don't end up modifying sources by mistake in Eclipse. - */ - @Override - public void postUnzipFileHook( - Archive archive, - ITaskMonitor monitor, - IFileOp fileOp, - File unzippedFile, - ZipArchiveEntry zipEntry) { - super.postUnzipFileHook(archive, monitor, fileOp, unzippedFile, zipEntry); - - if (fileOp.isFile(unzippedFile) && - !SdkConstants.FN_SOURCE_PROP.equals(unzippedFile.getName())) { - fileOp.setReadOnly(unzippedFile); - } - } - - @Override - public boolean sameItemAs(Package pkg) { - if (pkg instanceof SourcePackage) { - SourcePackage newPkg = (SourcePackage)pkg; - - // check they are the same version. - return getAndroidVersion().equals(newPkg.getAndroidVersion()); - } - - return false; - } - - @Override - public int hashCode() { - final int prime = 31; - int result = super.hashCode(); - result = prime * result + ((mVersion == null) ? 0 : mVersion.hashCode()); - return result; - } - - @Override - public boolean equals(Object obj) { - if (this == obj) { - return true; - } - if (!super.equals(obj)) { - return false; - } - if (!(obj instanceof SourcePackage)) { - return false; - } - SourcePackage other = (SourcePackage) obj; - if (mVersion == null) { - if (other.mVersion != null) { - return false; - } - } else if (!mVersion.equals(other.mVersion)) { - return false; - } - return true; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/SystemImagePackage.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/SystemImagePackage.java deleted file mode 100755 index 69335a5..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/SystemImagePackage.java +++ /dev/null @@ -1,379 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.SdkConstants; -import com.android.annotations.NonNull; -import com.android.annotations.VisibleForTesting; -import com.android.annotations.VisibleForTesting.Visibility; -import com.android.sdklib.AndroidVersion; -import com.android.sdklib.AndroidVersion.AndroidVersionException; -import com.android.sdklib.SdkManager; -import com.android.sdklib.SystemImage; -import com.android.sdklib.internal.repository.IDescription; -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; -import com.android.sdklib.internal.repository.sources.SdkSource; -import com.android.sdklib.repository.PkgProps; -import com.android.sdklib.repository.SdkRepoConstants; - -import org.w3c.dom.Node; - -import java.io.File; -import java.util.Locale; -import java.util.Map; -import java.util.Properties; - -/** - * Represents a system-image XML node in an SDK repository. - */ -public class SystemImagePackage extends MajorRevisionPackage - implements IAndroidVersionProvider, IPlatformDependency { - - /** The package version, for platform, add-on and doc packages. */ - private final AndroidVersion mVersion; - - /** The ABI of the system-image. Must not be null nor empty. */ - private final String mAbi; - - /** - * Creates a new system-image package from the attributes and elements of the given XML node. - * This constructor should throw an exception if the package cannot be created. - * - * @param source The {@link SdkSource} where this is loaded from. - * @param packageNode The XML element being parsed. - * @param nsUri The namespace URI of the originating XML document, to be able to deal with - * parameters that vary according to the originating XML schema. - * @param licenses The licenses loaded from the XML originating document. - */ - public SystemImagePackage(SdkSource source, - Node packageNode, - String nsUri, - Map<String,String> licenses) { - super(source, packageNode, nsUri, licenses); - - int apiLevel = - PackageParserUtils.getXmlInt(packageNode, SdkRepoConstants.NODE_API_LEVEL, 0); - String codeName = - PackageParserUtils.getXmlString(packageNode, SdkRepoConstants.NODE_CODENAME); - if (codeName.length() == 0) { - codeName = null; - } - mVersion = new AndroidVersion(apiLevel, codeName); - - mAbi = PackageParserUtils.getXmlString(packageNode, SdkRepoConstants.NODE_ABI); - } - - @VisibleForTesting(visibility=Visibility.PRIVATE) - public SystemImagePackage( - AndroidVersion platformVersion, - int revision, - String abi, - Properties props, - String localOsPath) { - this(null /*source*/, platformVersion, revision, abi, props, localOsPath); - } - - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected SystemImagePackage( - SdkSource source, - AndroidVersion platformVersion, - int revision, - String abi, - Properties props, - String localOsPath) { - super( source, //source - props, //properties - revision, //revision - null, //license - null, //description - null, //descUrl - Os.getCurrentOs(), //archiveOs - Arch.getCurrentArch(), //archiveArch - localOsPath //archiveOsPath - ); - mVersion = platformVersion; - if (abi == null && props != null) { - abi = props.getProperty(PkgProps.SYS_IMG_ABI); - } - assert abi != null : "To use this SystemImagePackage constructor you must pass an ABI as a parameter or as a PROP_ABI property"; - mAbi = abi; - } - - /** - * Creates a {@link BrokenPackage} representing a system image that failed to load - * with the regular {@link SdkManager} workflow. - * - * @param abiDir The SDK/system-images/android-N/abi folder - * @param props The properties located in {@code abiDir} or null if not found. - * @return A new {@link BrokenPackage} that represents this installed package. - */ - public static Package createBroken(File abiDir, Properties props) { - AndroidVersion version = null; - String abiType = abiDir.getName(); - String error = null; - - // Try to load the android version & ABI from the sources.props. - // If we don't find them, it would explain why this package is broken. - if (props == null) { - error = String.format("Missing file %1$s", SdkConstants.FN_SOURCE_PROP); - } else { - try { - version = new AndroidVersion(props); - - String abi = props.getProperty(PkgProps.SYS_IMG_ABI); - if (abi != null) { - abiType = abi; - } else { - error = String.format("Invalid file %1$s: Missing property %2$s", - SdkConstants.FN_SOURCE_PROP, - PkgProps.SYS_IMG_ABI); - } - } catch (AndroidVersionException e) { - error = String.format("Invalid file %1$s: %2$s", - SdkConstants.FN_SOURCE_PROP, - e.getMessage()); - } - } - - if (version == null) { - try { - // Try to parse the first number out of the platform folder name. - String platform = abiDir.getParentFile().getName(); - platform = platform.replaceAll("[^0-9]+", " ").trim(); //$NON-NLS-1$ //$NON-NLS-2$ - int pos = platform.indexOf(' '); - if (pos >= 0) { - platform = platform.substring(0, pos); - } - int apiLevel = Integer.parseInt(platform); - version = new AndroidVersion(apiLevel, null /*codename*/); - } catch (Exception ignore) { - } - } - - StringBuilder sb = new StringBuilder( - String.format("Broken %1$s System Image", getAbiDisplayNameInternal(abiType))); - if (version != null) { - sb.append(String.format(", API %1$s", version.getApiString())); - } - - String shortDesc = sb.toString(); - - if (error != null) { - sb.append('\n').append(error); - } - - String longDesc = sb.toString(); - - return new BrokenPackage(props, shortDesc, longDesc, - IMinApiLevelDependency.MIN_API_LEVEL_NOT_SPECIFIED, - version==null ? IExactApiLevelDependency.API_LEVEL_INVALID : version.getApiLevel(), - abiDir.getAbsolutePath()); - } - - /** - * Save the properties of the current packages in the given {@link Properties} object. - * These properties will later be given to a constructor that takes a {@link Properties} object. - */ - @Override - public void saveProperties(Properties props) { - super.saveProperties(props); - - mVersion.saveProperties(props); - props.setProperty(PkgProps.SYS_IMG_ABI, mAbi); - } - - /** Returns the ABI of the system-image. Cannot be null nor empty. */ - public String getAbi() { - return mAbi; - } - - /** Returns a display-friendly name for the ABI of the system-image. */ - public String getAbiDisplayName() { - return getAbiDisplayNameInternal(mAbi); - } - - private static String getAbiDisplayNameInternal(String abi) { - return abi.replace("armeabi", "ARM EABI") //$NON-NLS-1$ //$NON-NLS-2$ - .replace("x86", "Intel x86 Atom") //$NON-NLS-1$ //$NON-NLS-2$ - .replace("mips", "MIPS") //$NON-NLS-1$ //$NON-NLS-2$ - .replace("-", " "); //$NON-NLS-1$ //$NON-NLS-2$ - } - - /** - * Returns the version of the platform dependency of this package. - * <p/> - * A system-image has the same {@link AndroidVersion} as the platform it depends on. - */ - @Override @NonNull - public AndroidVersion getAndroidVersion() { - return mVersion; - } - - /** - * Returns a string identifier to install this package from the command line. - * For system images, we use "sysimg-N" where N is the API or the preview codename. - * <p/> - * {@inheritDoc} - */ - @Override - public String installId() { - return "sysimg-" + mVersion.getApiString(); //$NON-NLS-1$ - } - - /** - * Returns a description of this package that is suitable for a list display. - * <p/> - * {@inheritDoc} - */ - @Override - public String getListDescription() { - return String.format("%1$s System Image%2$s", - getAbiDisplayName(), - isObsolete() ? " (Obsolete)" : ""); - } - - /** - * Returns a short description for an {@link IDescription}. - */ - @Override - public String getShortDescription() { - return String.format("%1$s System Image, Android API %2$s, revision %3$s%4$s", - getAbiDisplayName(), - mVersion.getApiString(), - getRevision().toShortString(), - isObsolete() ? " (Obsolete)" : ""); - } - - /** - * Returns a long description for an {@link IDescription}. - * - * The long description is whatever the XML contains for the {@code description} field, - * or the short description if the former is empty. - */ - @Override - public String getLongDescription() { - String s = getDescription(); - if (s == null || s.length() == 0) { - s = getShortDescription(); - } - - if (s.indexOf("revision") == -1) { - s += String.format("\nRevision %1$s%2$s", - getRevision().toShortString(), - isObsolete() ? " (Obsolete)" : ""); - } - - s += String.format("\nRequires SDK Platform Android API %1$s", - mVersion.getApiString()); - return s; - } - - /** - * Computes a potential installation folder if an archive of this package were - * to be installed right away in the given SDK root. - * <p/> - * A system-image package is typically installed in SDK/systems/platform/abi. - * The name needs to be sanitized to be acceptable as a directory name. - * - * @param osSdkRoot The OS path of the SDK root folder. - * @param sdkManager An existing SDK manager to list current platforms and addons. - * @return A new {@link File} corresponding to the directory to use to install this package. - */ - @Override - public File getInstallFolder(String osSdkRoot, SdkManager sdkManager) { - File folder = new File(osSdkRoot, SdkConstants.FD_SYSTEM_IMAGES); - folder = new File(folder, SystemImage.ANDROID_PREFIX + mVersion.getApiString()); - - // Computes a folder directory using the sanitized abi string. - String abi = mAbi; - abi = abi.toLowerCase(Locale.US); - abi = abi.replaceAll("[^a-z0-9_-]+", "_"); //$NON-NLS-1$ //$NON-NLS-2$ - abi = abi.replaceAll("_+", "_"); //$NON-NLS-1$ //$NON-NLS-2$ - - folder = new File(folder, abi); - return folder; - } - - @Override - public boolean sameItemAs(Package pkg) { - if (pkg instanceof SystemImagePackage) { - SystemImagePackage newPkg = (SystemImagePackage)pkg; - - // check they are the same abi and version. - return getAbi().equals(newPkg.getAbi()) && - getAndroidVersion().equals(newPkg.getAndroidVersion()); - } - - return false; - } - - @Override - public int hashCode() { - final int prime = 31; - int result = super.hashCode(); - result = prime * result + ((mAbi == null) ? 0 : mAbi.hashCode()); - result = prime * result + ((mVersion == null) ? 0 : mVersion.hashCode()); - return result; - } - - @Override - public boolean equals(Object obj) { - if (this == obj) { - return true; - } - if (!super.equals(obj)) { - return false; - } - if (!(obj instanceof SystemImagePackage)) { - return false; - } - SystemImagePackage other = (SystemImagePackage) obj; - if (mAbi == null) { - if (other.mAbi != null) { - return false; - } - } else if (!mAbi.equals(other.mAbi)) { - return false; - } - if (mVersion == null) { - if (other.mVersion != null) { - return false; - } - } else if (!mVersion.equals(other.mVersion)) { - return false; - } - return true; - } - - /** - * For sys img packages, we want to add abi to the sorting key - * <em>before<em/> the revision number. - * <p/> - * {@inheritDoc} - */ - @Override - protected String comparisonKey() { - String s = super.comparisonKey(); - int pos = s.indexOf("|r:"); //$NON-NLS-1$ - assert pos > 0; - s = s.substring(0, pos) + - "|abi:" + getAbiDisplayName() + //$NON-NLS-1$ - s.substring(pos); - return s; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/ToolPackage.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/ToolPackage.java deleted file mode 100755 index 8084c6b..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/packages/ToolPackage.java +++ /dev/null @@ -1,373 +0,0 @@ -/* - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.SdkConstants; -import com.android.annotations.Nullable; -import com.android.annotations.VisibleForTesting; -import com.android.annotations.VisibleForTesting.Visibility; -import com.android.sdklib.SdkManager; -import com.android.sdklib.internal.repository.IDescription; -import com.android.sdklib.internal.repository.ITaskMonitor; -import com.android.sdklib.internal.repository.archives.Archive; -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; -import com.android.sdklib.internal.repository.sources.SdkSource; -import com.android.sdklib.repository.PkgProps; -import com.android.sdklib.repository.SdkRepoConstants; -import com.android.sdklib.util.GrabProcessOutput; -import com.android.sdklib.util.GrabProcessOutput.IProcessOutput; -import com.android.sdklib.util.GrabProcessOutput.Wait; - -import org.w3c.dom.Node; - -import java.io.File; -import java.util.Map; -import java.util.Properties; -import java.util.regex.Matcher; -import java.util.regex.Pattern; - -/** - * Represents a tool XML node in an SDK repository. - */ -public class ToolPackage extends FullRevisionPackage implements IMinPlatformToolsDependency { - - /** The value returned by {@link ToolPackage#installId()}. */ - public static final String INSTALL_ID = "tools"; //$NON-NLS-1$ - /** The value returned by {@link ToolPackage#installId()}. */ - private static final String INSTALL_ID_PREVIEW = "tools-preview"; //$NON-NLS-1$ - - /** - * The minimal revision of the platform-tools package required by this package - * or {@link #MIN_PLATFORM_TOOLS_REV_INVALID} if the value was missing. - */ - private final FullRevision mMinPlatformToolsRevision; - - /** - * Creates a new tool package from the attributes and elements of the given XML node. - * This constructor should throw an exception if the package cannot be created. - * - * @param source The {@link SdkSource} where this is loaded from. - * @param packageNode The XML element being parsed. - * @param nsUri The namespace URI of the originating XML document, to be able to deal with - * parameters that vary according to the originating XML schema. - * @param licenses The licenses loaded from the XML originating document. - */ - public ToolPackage(SdkSource source, - Node packageNode, - String nsUri, - Map<String,String> licenses) { - super(source, packageNode, nsUri, licenses); - - mMinPlatformToolsRevision = PackageParserUtils.parseFullRevisionElement( - PackageParserUtils.findChildElement(packageNode, - SdkRepoConstants.NODE_MIN_PLATFORM_TOOLS_REV)); - - if (mMinPlatformToolsRevision.equals(MIN_PLATFORM_TOOLS_REV_INVALID)) { - // This revision number is mandatory starting with sdk-repository-3.xsd - // and did not exist before. Complain if the URI has level >= 3. - - boolean needRevision = false; - - Pattern nsPattern = Pattern.compile(SdkRepoConstants.NS_PATTERN); - Matcher m = nsPattern.matcher(nsUri); - if (m.matches()) { - String version = m.group(1); - try { - needRevision = Integer.parseInt(version) >= 3; - } catch (NumberFormatException e) { - // ignore. needRevision defaults to false - } - } - - if (needRevision) { - throw new IllegalArgumentException( - String.format("Missing %1$s element in %2$s package", - SdkRepoConstants.NODE_MIN_PLATFORM_TOOLS_REV, - SdkRepoConstants.NODE_PLATFORM_TOOL)); - } - } - } - - /** - * Manually create a new package with one archive and the given attributes or properties. - * This is used to create packages from local directories in which case there must be - * one archive which URL is the actual target location. - * <p/> - * By design, this creates a package with one and only one archive. - */ - public static Package create( - SdkSource source, - Properties props, - int revision, - String license, - String description, - String descUrl, - Os archiveOs, - Arch archiveArch, - String archiveOsPath) { - return new ToolPackage(source, props, revision, license, description, - descUrl, archiveOs, archiveArch, archiveOsPath); - } - - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected ToolPackage( - SdkSource source, - Properties props, - int revision, - String license, - String description, - String descUrl, - Os archiveOs, - Arch archiveArch, - String archiveOsPath) { - super(source, - props, - revision, - license, - description, - descUrl, - archiveOs, - archiveArch, - archiveOsPath); - - String revStr = getProperty(props, PkgProps.MIN_PLATFORM_TOOLS_REV, null); - - FullRevision rev = MIN_PLATFORM_TOOLS_REV_INVALID; - if (revStr != null) { - try { - rev = FullRevision.parseRevision(revStr); - } catch (NumberFormatException ignore) {} - } - - mMinPlatformToolsRevision = rev; - } - - /** - * The minimal revision of the tools package required by this package if > 0, - * or {@link #MIN_PLATFORM_TOOLS_REV_INVALID} if the value was missing. - * <p/> - * This attribute is mandatory and should not be normally missing. - */ - @Override - public FullRevision getMinPlatformToolsRevision() { - return mMinPlatformToolsRevision; - } - - /** - * Returns a string identifier to install this package from the command line. - * For tools, we use "tools" or "tools-preview" since this package is unique. - * <p/> - * {@inheritDoc} - */ - @Override - public String installId() { - if (getRevision().isPreview()) { - return INSTALL_ID_PREVIEW; - } else { - return INSTALL_ID; - } - } - - /** - * Returns a description of this package that is suitable for a list display. - * <p/> - * {@inheritDoc} - */ - @Override - public String getListDescription() { - return String.format("Android SDK Tools%1$s", - isObsolete() ? " (Obsolete)" : ""); - } - - /** - * Returns a short description for an {@link IDescription}. - */ - @Override - public String getShortDescription() { - return String.format("Android SDK Tools, revision %1$s%2$s", - getRevision().toShortString(), - isObsolete() ? " (Obsolete)" : ""); - } - - /** Returns a long description for an {@link IDescription}. */ - @Override - public String getLongDescription() { - String s = getDescription(); - if (s == null || s.length() == 0) { - s = getShortDescription(); - } - - if (s.indexOf("revision") == -1) { - s += String.format("\nRevision %1$s%2$s", - getRevision().toShortString(), - isObsolete() ? " (Obsolete)" : ""); - } - - return s; - } - - /** - * Computes a potential installation folder if an archive of this package were - * to be installed right away in the given SDK root. - * <p/> - * A "tool" package should always be located in SDK/tools. - * - * @param osSdkRoot The OS path of the SDK root folder. - * @param sdkManager An existing SDK manager to list current platforms and addons. - * @return A new {@link File} corresponding to the directory to use to install this package. - */ - @Override - public File getInstallFolder(String osSdkRoot, SdkManager sdkManager) { - return new File(osSdkRoot, SdkConstants.FD_TOOLS); - } - - /** - * Check whether 2 tool packages are the same <em>and</em> have the - * same preview bit. - */ - @Override - public boolean sameItemAs(Package pkg) { - // Only one tool package so any tool package is the same item - return sameItemAs(pkg, false /*ignorePreviews*/); - } - - @Override - public boolean sameItemAs(Package pkg, boolean ignorePreviews) { - // only one tool package so any tool package is the same item. - if (pkg instanceof ToolPackage) { - if (ignorePreviews) { - return true; - } else { - // however previews can only match previews by default, unless we ignore that check. - return ((ToolPackage) pkg).getRevision().isPreview() == - getRevision().isPreview(); - } - } - return false; - } - - @Override - public void saveProperties(Properties props) { - super.saveProperties(props); - - if (!getMinPlatformToolsRevision().equals(MIN_PLATFORM_TOOLS_REV_INVALID)) { - props.setProperty(PkgProps.MIN_PLATFORM_TOOLS_REV, - getMinPlatformToolsRevision().toShortString()); - } - } - - /** - * The tool package executes tools/lib/post_tools_install[.bat|.sh] - * {@inheritDoc} - */ - @Override - public void postInstallHook(Archive archive, final ITaskMonitor monitor, File installFolder) { - super.postInstallHook(archive, monitor, installFolder); - - if (installFolder == null) { - return; - } - - File libDir = new File(installFolder, SdkConstants.FD_LIB); - if (!libDir.isDirectory()) { - return; - } - - String scriptName = "post_tools_install"; //$NON-NLS-1$ - String shell = ""; //$NON-NLS-1$ - if (SdkConstants.currentPlatform() == SdkConstants.PLATFORM_WINDOWS) { - shell = "cmd.exe /c "; //$NON-NLS-1$ - scriptName += ".bat"; //$NON-NLS-1$ - } else { - scriptName += ".sh"; //$NON-NLS-1$ - } - - File scriptFile = new File(libDir, scriptName); - if (!scriptFile.isFile()) { - return; - } - - int status = -1; - - try { - Process proc = Runtime.getRuntime().exec( - shell + scriptName, // command - null, // environment - libDir); // working dir - - final String tag = scriptName; - status = GrabProcessOutput.grabProcessOutput( - proc, - Wait.WAIT_FOR_PROCESS, - new IProcessOutput() { - @Override - public void out(@Nullable String line) { - if (line != null) { - monitor.log("[%1$s] %2$s", tag, line); - } - } - - @Override - public void err(@Nullable String line) { - if (line != null) { - monitor.logError("[%1$s] Error: %2$s", tag, line); - } - } - }); - - } catch (Exception e) { - monitor.logError("Exception: %s", e.toString()); - } - - if (status != 0) { - monitor.logError("Failed to execute %s", scriptName); - return; - } - } - - @Override - public int hashCode() { - final int prime = 31; - int result = super.hashCode(); - result = prime * result - + ((mMinPlatformToolsRevision == null) ? 0 : mMinPlatformToolsRevision.hashCode()); - return result; - } - - @Override - public boolean equals(Object obj) { - if (this == obj) { - return true; - } - if (!super.equals(obj)) { - return false; - } - if (!(obj instanceof ToolPackage)) { - return false; - } - ToolPackage other = (ToolPackage) obj; - if (mMinPlatformToolsRevision == null) { - if (other.mMinPlatformToolsRevision != null) { - return false; - } - } else if (!mMinPlatformToolsRevision.equals(other.mMinPlatformToolsRevision)) { - return false; - } - return true; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/sources/SdkAddonSource.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/sources/SdkAddonSource.java deleted file mode 100755 index 98bfc5a..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/sources/SdkAddonSource.java +++ /dev/null @@ -1,109 +0,0 @@ -/* - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.sources; - -import com.android.annotations.Nullable; -import com.android.sdklib.internal.repository.packages.Package; -import com.android.sdklib.repository.SdkAddonConstants; - -import org.w3c.dom.Document; - -import java.io.InputStream; - - -/** - * An sdk-addon source, i.e. a download site for addons and extra packages. - * A repository describes one or more {@link Package}s available for download. - */ -public class SdkAddonSource extends SdkSource { - - /** - * Constructs a new source for the given repository URL. - * @param url The source URL. Cannot be null. If the URL ends with a /, the default - * addon.xml filename will be appended automatically. - * @param uiName The UI-visible name of the source. Can be null. - */ - public SdkAddonSource(String url, String uiName) { - super(url, uiName); - } - - /** - * Returns true if this is an addon source. - * We only load addons and extras from these sources. - */ - @Override - public boolean isAddonSource() { - return true; - } - - /** - * Returns true if this is a system-image source. - * We only load system-images from these sources. - */ - @Override - public boolean isSysImgSource() { - return false; - } - - - @Override - protected String[] getDefaultXmlFileUrls() { - return new String[] { SdkAddonConstants.URL_DEFAULT_FILENAME }; - } - - @Override - protected int getNsLatestVersion() { - return SdkAddonConstants.NS_LATEST_VERSION; - } - - @Override - protected String getNsUri() { - return SdkAddonConstants.NS_URI; - } - - @Override - protected String getNsPattern() { - return SdkAddonConstants.NS_PATTERN; - } - - @Override - protected String getSchemaUri(int version) { - return SdkAddonConstants.getSchemaUri(version); - } - - @Override - protected String getRootElementName() { - return SdkAddonConstants.NODE_SDK_ADDON; - } - - @Override - protected InputStream getXsdStream(int version) { - return SdkAddonConstants.getXsdStream(version); - } - - /** - * This kind of schema does not support forward-evolution of the <tool> element. - * - * @param xml The input XML stream. Can be null. - * @return Always null. - * @null This implementation always return null. - */ - @Override - protected Document findAlternateToolsXml(@Nullable InputStream xml) { - return null; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/sources/SdkRepoSource.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/sources/SdkRepoSource.java deleted file mode 100755 index 09913ed..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/sources/SdkRepoSource.java +++ /dev/null @@ -1,524 +0,0 @@ -/* - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.sources; - -import com.android.annotations.Nullable; -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; -import com.android.sdklib.internal.repository.packages.Package; -import com.android.sdklib.internal.repository.packages.PackageParserUtils; -import com.android.sdklib.repository.RepoConstants; -import com.android.sdklib.repository.SdkRepoConstants; - -import org.w3c.dom.Attr; -import org.w3c.dom.Document; -import org.w3c.dom.Element; -import org.w3c.dom.NamedNodeMap; -import org.w3c.dom.Node; -import org.w3c.dom.Text; -import org.xml.sax.ErrorHandler; - -import java.io.IOException; -import java.io.InputStream; -import java.util.regex.Pattern; - -import javax.xml.parsers.DocumentBuilder; -import javax.xml.parsers.DocumentBuilderFactory; - - -/** - * An sdk-repository source, i.e. a download site. - * A repository describes one or more {@link Package}s available for download. - */ -public class SdkRepoSource extends SdkSource { - - /** - * Constructs a new source for the given repository URL. - * @param url The source URL. Cannot be null. If the URL ends with a /, the default - * repository.xml filename will be appended automatically. - * @param uiName The UI-visible name of the source. Can be null. - */ - public SdkRepoSource(String url, String uiName) { - super(url, uiName); - } - - /** - * Returns true if this is an addon source. - * We only load addons and extras from these sources. - */ - @Override - public boolean isAddonSource() { - return false; - } - - /** - * Returns true if this is a system-image source. - * We only load system-images from these sources. - */ - @Override - public boolean isSysImgSource() { - return false; - } - - private static String[] sDefaults = null; // lazily allocated in getDefaultXmlFileUrls - - @Override - protected String[] getDefaultXmlFileUrls() { - if (sDefaults == null) { - sDefaults = new String[SdkRepoConstants.NS_LATEST_VERSION - - SdkRepoConstants.NS_SERVER_MIN_VERSION - + 2]; - int k = 0; - for (int i = SdkRepoConstants.NS_LATEST_VERSION; - i >= SdkRepoConstants.NS_SERVER_MIN_VERSION; - i--) { - sDefaults[k++] = String.format(SdkRepoConstants.URL_FILENAME_PATTERN, i); - } - sDefaults[k++] = SdkRepoConstants.URL_DEFAULT_FILENAME; - assert k == sDefaults.length; - } - - return sDefaults; - } - - @Override - protected int getNsLatestVersion() { - return SdkRepoConstants.NS_LATEST_VERSION; - } - - @Override - protected String getNsUri() { - return SdkRepoConstants.NS_URI; - } - - @Override - protected String getNsPattern() { - return SdkRepoConstants.NS_PATTERN; - } - - @Override - protected String getSchemaUri(int version) { - return SdkRepoConstants.getSchemaUri(version); - } - - @Override - protected String getRootElementName() { - return SdkRepoConstants.NODE_SDK_REPOSITORY; - } - - @Override - protected InputStream getXsdStream(int version) { - return SdkRepoConstants.getXsdStream(version); - } - - /** - * The purpose of this method is to support forward evolution of our schema. - * <p/> - * At this point, we know that xml does not point to any schema that this version of - * the tool knows how to process, so it's not one of the possible 1..N versions of our - * XSD schema. - * <p/> - * We thus try to interpret the byte stream as a possible XML stream. It may not be - * one at all in the first place. If it looks anything line an XML schema, we try to - * find its <tool> and the <platform-tools> elements. If we find any, - * we recreate a suitable document that conforms to what we expect from our XSD schema - * with only those elements. - * <p/> - * To be valid, the <tool> and the <platform-tools> elements must have at - * least one <archive> compatible with this platform. - * <p/> - * Starting the sdk-repository schema v3, <tools> has a <min-platform-tools-rev> - * node, so technically the corresponding XML schema will be usable only if there's a - * <platform-tools> with the request revision number. We don't enforce that here, as - * this is done at install time. - * <p/> - * If we don't find anything suitable, we drop the whole thing. - * - * @param xml The input XML stream. Can be null. - * @return Either a new XML document conforming to our schema with at least one <tool> - * and <platform-tools> element or null. - * @throws IOException if InputStream.reset() fails - * @null Can return null on failure. - */ - @Override - protected Document findAlternateToolsXml(@Nullable InputStream xml) throws IOException { - return findAlternateToolsXml(xml, null /*errorHandler*/); - } - - /** - * An alternate version of {@link #findAlternateToolsXml(InputStream)} that allows - * the caller to specify the XML error handler. The default from the underlying Java - * XML Xerces parser will dump to stdout/stderr, which is not convenient during unit tests. - * - * @param xml The input XML stream. Can be null. - * @param errorHandler An optional XML error handler. If null, the default will be used. - * @return Either a new XML document conforming to our schema with at least one <tool> - * and <platform-tools> element or null. - * @throws IOException if InputStream.reset() fails - * @null Can return null on failure. - * @see #findAlternateToolsXml(InputStream) findAlternateToolsXml() provides more details. - */ - protected Document findAlternateToolsXml( - @Nullable InputStream xml, - @Nullable ErrorHandler errorHandler) - throws IOException { - if (xml == null) { - return null; - } - - // Reset the stream if it supports that operation. - assert xml.markSupported(); - xml.reset(); - - // Get an XML document - - Document oldDoc = null; - Document newDoc = null; - try { - DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance(); - factory.setIgnoringComments(false); - factory.setValidating(false); - - // Parse the old document using a non namespace aware builder - factory.setNamespaceAware(false); - DocumentBuilder builder = factory.newDocumentBuilder(); - - if (errorHandler != null) { - builder.setErrorHandler(errorHandler); - } - - oldDoc = builder.parse(xml); - - // Prepare a new document using a namespace aware builder - factory.setNamespaceAware(true); - builder = factory.newDocumentBuilder(); - newDoc = builder.newDocument(); - - } catch (Exception e) { - // Failed to get builder factor - // Failed to create XML document builder - // Failed to parse XML document - // Failed to read XML document - } - - if (oldDoc == null || newDoc == null) { - return null; - } - - - // Check the root element is an XML with at least the following properties: - // <sdk:sdk-repository - // xmlns:sdk="http://schemas.android.com/sdk/android/repository/$N"> - // - // Note that we don't have namespace support enabled, we just do it manually. - - Pattern nsPattern = Pattern.compile(getNsPattern()); - - Node oldRoot = null; - String prefix = null; - for (Node child = oldDoc.getFirstChild(); child != null; child = child.getNextSibling()) { - if (child.getNodeType() == Node.ELEMENT_NODE) { - prefix = null; - String name = child.getNodeName(); - int pos = name.indexOf(':'); - if (pos > 0 && pos < name.length() - 1) { - prefix = name.substring(0, pos); - name = name.substring(pos + 1); - } - if (SdkRepoConstants.NODE_SDK_REPOSITORY.equals(name)) { - NamedNodeMap attrs = child.getAttributes(); - String xmlns = "xmlns"; //$NON-NLS-1$ - if (prefix != null) { - xmlns += ":" + prefix; //$NON-NLS-1$ - } - Node attr = attrs.getNamedItem(xmlns); - if (attr != null) { - String uri = attr.getNodeValue(); - if (uri != null && nsPattern.matcher(uri).matches()) { - oldRoot = child; - break; - } - } - } - } - } - - // we must have found the root node, and it must have an XML namespace prefix. - if (oldRoot == null || prefix == null || prefix.length() == 0) { - return null; - } - - final String ns = getNsUri(); - Element newRoot = newDoc.createElementNS(ns, getRootElementName()); - newRoot.setPrefix(prefix); - newDoc.appendChild(newRoot); - int numTool = 0; - - // Find any inner <tool> or <platform-tool> nodes and extract their required parameters - - String[] elementNames = { - SdkRepoConstants.NODE_TOOL, - SdkRepoConstants.NODE_PLATFORM_TOOL, - SdkRepoConstants.NODE_LICENSE - }; - - Element element = null; - while ((element = findChild(oldRoot, element, prefix, elementNames)) != null) { - boolean isElementValid = false; - - String name = element.getLocalName(); - if (name == null) { - name = element.getNodeName(); - - int pos = name.indexOf(':'); - if (pos > 0 && pos < name.length() - 1) { - name = name.substring(pos + 1); - } - } - - // To be valid, the tool or platform-tool element must have: - // - a <revision> element with a number - // - a <min-platform-tools-rev> element with a number for a <tool> element - // - an <archives> element with one or more <archive> elements inside - // - one of the <archive> elements must have an "os" and "arch" attributes - // compatible with the current platform. Only keep the first such element found. - // - the <archive> element must contain a <size>, a <checksum> and a <url>. - // - none of the above for a license element - - if (SdkRepoConstants.NODE_LICENSE.equals(name)) { - isElementValid = true; - - } else { - try { - Node revision = findChild(element, null, prefix, RepoConstants.NODE_REVISION); - Node archives = findChild(element, null, prefix, RepoConstants.NODE_ARCHIVES); - - if (revision == null || archives == null) { - continue; - } - - // check revision contains a number - try { - String content = revision.getTextContent(); - content = content.trim(); - int rev = Integer.parseInt(content); - if (rev < 1) { - continue; - } - } catch (NumberFormatException ignore) { - continue; - } - - if (SdkRepoConstants.NODE_TOOL.equals(name)) { - Node minPTRev = findChild(element, null, prefix, - RepoConstants.NODE_MIN_PLATFORM_TOOLS_REV); - - if (minPTRev == null) { - continue; - } - - // check min-platform-tools-rev contains a number - try { - String content = minPTRev.getTextContent(); - content = content.trim(); - int rev = Integer.parseInt(content); - if (rev < 1) { - continue; - } - } catch (NumberFormatException ignore) { - continue; - } - } - - Node archive = null; - while ((archive = findChild(archives, - archive, - prefix, - RepoConstants.NODE_ARCHIVE)) != null) { - try { - Os os = (Os) PackageParserUtils.getEnumAttribute(archive, - RepoConstants.ATTR_OS, - Os.values(), - null /*default*/); - Arch arch = (Arch) PackageParserUtils.getEnumAttribute(archive, - RepoConstants.ATTR_ARCH, - Arch.values(), - Arch.ANY); - if (os == null || !os.isCompatible() || - arch == null || !arch.isCompatible()) { - continue; - } - - Node node = findChild(archive, null, prefix, RepoConstants.NODE_URL); - String url = node == null ? null : node.getTextContent().trim(); - if (url == null || url.length() == 0) { - continue; - } - - node = findChild(archive, null, prefix, RepoConstants.NODE_SIZE); - long size = 0; - try { - size = Long.parseLong(node.getTextContent()); - } catch (Exception e) { - // pass - } - if (size < 1) { - continue; - } - - node = findChild(archive, null, prefix, RepoConstants.NODE_CHECKSUM); - // double check that the checksum element contains a type=sha1 attribute - if (node == null) { - continue; - } - NamedNodeMap attrs = node.getAttributes(); - Node typeNode = attrs.getNamedItem(RepoConstants.ATTR_TYPE); - if (typeNode == null || - !RepoConstants.ATTR_TYPE.equals(typeNode.getNodeName()) || - !RepoConstants.SHA1_TYPE.equals(typeNode.getNodeValue())) { - continue; - } - String sha1 = node == null ? null : node.getTextContent().trim(); - if (sha1 == null || - sha1.length() != RepoConstants.SHA1_CHECKSUM_LEN) { - continue; - } - - isElementValid = true; - - } catch (Exception ignore1) { - // pass - } - } // while <archive> - } catch (Exception ignore2) { - // For debugging it is useful to re-throw the exception. - // For end-users, not so much. It would be nice to make it - // happen automatically during unit tests. - if (System.getenv("TESTING") != null) { - throw new RuntimeException(ignore2); - } - } - } - - if (isElementValid) { - duplicateNode(newRoot, element, SdkRepoConstants.NS_URI, prefix); - numTool++; - } - } // while <tool> - - return numTool > 0 ? newDoc : null; - } - - /** - * Helper method used by {@link #findAlternateToolsXml(InputStream)} to find a given - * element child in a root XML node. - */ - private Element findChild(Node rootNode, Node after, String prefix, String[] nodeNames) { - for (int i = 0; i < nodeNames.length; i++) { - if (nodeNames[i].indexOf(':') < 0) { - nodeNames[i] = prefix + ":" + nodeNames[i]; - } - } - Node child = after == null ? rootNode.getFirstChild() : after.getNextSibling(); - for(; child != null; child = child.getNextSibling()) { - if (child.getNodeType() != Node.ELEMENT_NODE) { - continue; - } - for (String nodeName : nodeNames) { - if (nodeName.equals(child.getNodeName())) { - return (Element) child; - } - } - } - return null; - } - - /** - * Helper method used by {@link #findAlternateToolsXml(InputStream)} to find a given - * element child in a root XML node. - */ - private Node findChild(Node rootNode, Node after, String prefix, String nodeName) { - return findChild(rootNode, after, prefix, new String[] { nodeName }); - } - - /** - * Helper method used by {@link #findAlternateToolsXml(InputStream)} to duplicate a node - * and attach it to the given root in the new document. - */ - private Element duplicateNode(Element newRootNode, Element oldNode, - String namespaceUri, String prefix) { - // The implementation here is more or less equivalent to - // - // newRoot.appendChild(newDoc.importNode(oldNode, deep=true)) - // - // except we can't just use importNode() since we need to deal with the fact - // that the old document is not namespace-aware yet the new one is. - - Document newDoc = newRootNode.getOwnerDocument(); - Element newNode = null; - - String nodeName = oldNode.getNodeName(); - int pos = nodeName.indexOf(':'); - if (pos > 0 && pos < nodeName.length() - 1) { - nodeName = nodeName.substring(pos + 1); - newNode = newDoc.createElementNS(namespaceUri, nodeName); - newNode.setPrefix(prefix); - } else { - newNode = newDoc.createElement(nodeName); - } - - newRootNode.appendChild(newNode); - - // Merge in all the attributes - NamedNodeMap attrs = oldNode.getAttributes(); - for (int i = 0; i < attrs.getLength(); i++) { - Attr attr = (Attr) attrs.item(i); - Attr newAttr = null; - - String attrName = attr.getNodeName(); - pos = attrName.indexOf(':'); - if (pos > 0 && pos < attrName.length() - 1) { - attrName = attrName.substring(pos + 1); - newAttr = newDoc.createAttributeNS(namespaceUri, attrName); - newAttr.setPrefix(prefix); - } else { - newAttr = newDoc.createAttribute(attrName); - } - - newAttr.setNodeValue(attr.getNodeValue()); - - if (pos > 0) { - newNode.getAttributes().setNamedItemNS(newAttr); - } else { - newNode.getAttributes().setNamedItem(newAttr); - } - } - - // Merge all child elements and texts - for (Node child = oldNode.getFirstChild(); child != null; child = child.getNextSibling()) { - if (child.getNodeType() == Node.ELEMENT_NODE) { - duplicateNode(newNode, (Element) child, namespaceUri, prefix); - - } else if (child.getNodeType() == Node.TEXT_NODE) { - Text newText = newDoc.createTextNode(child.getNodeValue()); - newNode.appendChild(newText); - } - } - - return newNode; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/sources/SdkSource.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/sources/SdkSource.java deleted file mode 100755 index 2558e71..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/sources/SdkSource.java +++ /dev/null @@ -1,991 +0,0 @@ -/* - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.sources; - -import com.android.annotations.Nullable; -import com.android.annotations.VisibleForTesting; -import com.android.annotations.VisibleForTesting.Visibility; -import com.android.sdklib.internal.repository.CanceledByUserException; -import com.android.sdklib.internal.repository.DownloadCache; -import com.android.sdklib.internal.repository.IDescription; -import com.android.sdklib.internal.repository.ITaskMonitor; -import com.android.sdklib.internal.repository.packages.AddonPackage; -import com.android.sdklib.internal.repository.packages.DocPackage; -import com.android.sdklib.internal.repository.packages.ExtraPackage; -import com.android.sdklib.internal.repository.packages.Package; -import com.android.sdklib.internal.repository.packages.PlatformPackage; -import com.android.sdklib.internal.repository.packages.PlatformToolPackage; -import com.android.sdklib.internal.repository.packages.SamplePackage; -import com.android.sdklib.internal.repository.packages.SourcePackage; -import com.android.sdklib.internal.repository.packages.SystemImagePackage; -import com.android.sdklib.internal.repository.packages.ToolPackage; -import com.android.sdklib.io.NonClosingInputStream; -import com.android.sdklib.io.NonClosingInputStream.CloseBehavior; -import com.android.sdklib.repository.RepoConstants; -import com.android.sdklib.repository.SdkAddonConstants; -import com.android.sdklib.repository.SdkRepoConstants; - -import org.w3c.dom.Document; -import org.w3c.dom.NamedNodeMap; -import org.w3c.dom.Node; -import org.xml.sax.ErrorHandler; -import org.xml.sax.InputSource; -import org.xml.sax.SAXException; -import org.xml.sax.SAXParseException; - -import java.io.FileNotFoundException; -import java.io.IOException; -import java.io.InputStream; -import java.net.MalformedURLException; -import java.net.URL; -import java.util.ArrayList; -import java.util.Arrays; -import java.util.HashMap; -import java.util.regex.Matcher; -import java.util.regex.Pattern; - -import javax.net.ssl.SSLKeyException; -import javax.xml.XMLConstants; -import javax.xml.parsers.DocumentBuilder; -import javax.xml.parsers.DocumentBuilderFactory; -import javax.xml.parsers.ParserConfigurationException; -import javax.xml.transform.stream.StreamSource; -import javax.xml.validation.Schema; -import javax.xml.validation.SchemaFactory; -import javax.xml.validation.Validator; - -/** - * An sdk-addon or sdk-repository source, i.e. a download site. - * It may be a full repository or an add-on only repository. - * A repository describes one or {@link Package}s available for download. - */ -public abstract class SdkSource implements IDescription, Comparable<SdkSource> { - - private String mUrl; - - private Package[] mPackages; - private String mDescription; - private String mFetchError; - private final String mUiName; - - private static final SdkSourceProperties sSourcesProps = new SdkSourceProperties(); - - /** - * Constructs a new source for the given repository URL. - * @param url The source URL. Cannot be null. If the URL ends with a /, the default - * repository.xml filename will be appended automatically. - * @param uiName The UI-visible name of the source. Can be null. - */ - public SdkSource(String url, String uiName) { - - // URLs should not be null and should not have whitespace. - if (url == null) { - url = ""; - } - url = url.trim(); - - // if the URL ends with a /, it must be "directory" resource, - // in which case we automatically add the default file that will - // looked for. This way it will be obvious to the user which - // resource we are actually trying to fetch. - if (url.endsWith("/")) { //$NON-NLS-1$ - String[] names = getDefaultXmlFileUrls(); - if (names.length > 0) { - url += names[0]; - } - } - - if (uiName == null) { - uiName = sSourcesProps.getProperty(SdkSourceProperties.KEY_NAME, url, null); - } else { - sSourcesProps.setProperty(SdkSourceProperties.KEY_NAME, url, uiName); - } - - mUrl = url; - mUiName = uiName; - setDefaultDescription(); - } - - /** - * Returns true if this is an addon source. - * We only load addons and extras from these sources. - */ - public abstract boolean isAddonSource(); - - /** - * Returns true if this is a system-image source. - * We only load system-images from these sources. - */ - public abstract boolean isSysImgSource(); - - - /** - * Returns the basename of the default URLs to try to download the - * XML manifest. - * E.g. this is typically SdkRepoConstants.URL_DEFAULT_XML_FILE - * or SdkAddonConstants.URL_DEFAULT_XML_FILE - */ - protected abstract String[] getDefaultXmlFileUrls(); - - /** Returns SdkRepoConstants.NS_LATEST_VERSION or SdkAddonConstants.NS_LATEST_VERSION. */ - protected abstract int getNsLatestVersion(); - - /** Returns SdkRepoConstants.NS_URI or SdkAddonConstants.NS_URI. */ - protected abstract String getNsUri(); - - /** Returns SdkRepoConstants.NS_PATTERN or SdkAddonConstants.NS_PATTERN. */ - protected abstract String getNsPattern(); - - /** Returns SdkRepoConstants.getSchemaUri() or SdkAddonConstants.getSchemaUri(). */ - protected abstract String getSchemaUri(int version); - - /* Returns SdkRepoConstants.NODE_SDK_REPOSITORY or SdkAddonConstants.NODE_SDK_ADDON. */ - protected abstract String getRootElementName(); - - /** Returns SdkRepoConstants.getXsdStream() or SdkAddonConstants.getXsdStream(). */ - protected abstract InputStream getXsdStream(int version); - - /** - * In case we fail to load an XML, examine the XML to see if it matches a <b>future</b> - * schema that as at least a <code>tools</code> node that we could load to update the - * SDK Manager. - * - * @param xml The input XML stream. Can be null. - * @return Null on failure, otherwise returns an XML DOM with just the tools we - * need to update this SDK Manager. - * @null Can return null on failure. - */ - protected abstract Document findAlternateToolsXml(@Nullable InputStream xml) - throws IOException; - - /** - * Two repo source are equal if they have the same URL. - */ - @Override - public boolean equals(Object obj) { - if (obj instanceof SdkSource) { - SdkSource rs = (SdkSource) obj; - return rs.getUrl().equals(this.getUrl()); - } - return false; - } - - @Override - public int hashCode() { - return mUrl.hashCode(); - } - - /** - * Implementation of the {@link Comparable} interface. - * Simply compares the URL using the string's default ordering. - */ - @Override - public int compareTo(SdkSource rhs) { - return this.getUrl().compareTo(rhs.getUrl()); - } - - /** - * Returns the UI-visible name of the source. Can be null. - */ - public String getUiName() { - return mUiName; - } - - /** Returns the URL of the XML file for this source. */ - public String getUrl() { - return mUrl; - } - - /** - * Returns the list of known packages found by the last call to load(). - * This is null when the source hasn't been loaded yet -- caller should - * then call {@link #load} to load the packages. - */ - public Package[] getPackages() { - return mPackages; - } - - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected void setPackages(Package[] packages) { - mPackages = packages; - - if (mPackages != null) { - // Order the packages. - Arrays.sort(mPackages, null); - } - } - - /** - * Clear the internal packages list. After this call, {@link #getPackages()} will return - * null till load() is called. - */ - public void clearPackages() { - setPackages(null); - } - - /** - * Indicates if the source is enabled. - * <p/> - * A 3rd-party add-on source can be disabled by the user to prevent from loading it. - * - * @return True if the source is enabled (default is true). - */ - public boolean isEnabled() { - // A URL is enabled if it's not in the disabled list. - return sSourcesProps.getProperty(SdkSourceProperties.KEY_DISABLED, mUrl, null) == null; - } - - /** - * Changes whether the source is marked as enabled. - * <p/> - * When <em>changing</em> the enable state, the current package list is purged - * and the next {@code load} will either return an empty list (if disabled) or - * the actual package list (if enabled.) - * - * @param enabled True for the source to be enabled (can be loaded), false otherwise. - */ - public void setEnabled(boolean enabled) { - if (enabled != isEnabled()) { - // First we clear the current package list, which will force the - // next load() to actually set the package list as desired. - clearPackages(); - - sSourcesProps.setProperty(SdkSourceProperties.KEY_DISABLED, mUrl, - enabled ? null /*remove*/ : "disabled"); //$NON-NLS-1$ - } - } - - /** - * Returns the short description of the source, if not null. - * Otherwise returns the default Object toString result. - * <p/> - * This is mostly helpful for debugging. - * For UI display, use the {@link IDescription} interface. - */ - @Override - public String toString() { - String s = getShortDescription(); - if (s != null) { - return s; - } - return super.toString(); - } - - @Override - public String getShortDescription() { - - if (mUiName != null && mUiName.length() > 0) { - - String host = "malformed URL"; - - try { - URL u = new URL(mUrl); - host = u.getHost(); - } catch (MalformedURLException e) { - } - - return String.format("%1$s (%2$s)", mUiName, host); - - } - return mUrl; - } - - @Override - public String getLongDescription() { - // Note: in a normal workflow, mDescription is filled by setDefaultDescription(). - // However for packages made by unit tests or such, this can be null. - return mDescription == null ? "" : mDescription; //$NON-NLS-1$ - } - - /** - * Returns the last fetch error description. - * If there was no error, returns null. - */ - public String getFetchError() { - return mFetchError; - } - - /** - * Tries to fetch the repository index for the given URL and updates the package list. - * When a source is disabled, this create an empty non-null package list. - * <p/> - * Callers can get the package list using {@link #getPackages()} after this. It will be - * null in case of error, in which case {@link #getFetchError()} can be used to an - * error message. - */ - public void load(DownloadCache cache, ITaskMonitor monitor, boolean forceHttp) { - - setDefaultDescription(); - monitor.setProgressMax(7); - - if (!isEnabled()) { - setPackages(new Package[0]); - mDescription += "\nSource is disabled."; - monitor.incProgress(7); - return; - } - - String url = mUrl; - if (forceHttp) { - url = url.replaceAll("https://", "http://"); //$NON-NLS-1$ //$NON-NLS-2$ - } - - monitor.setDescription("Fetching URL: %1$s", url); - monitor.incProgress(1); - - mFetchError = null; - Boolean[] validatorFound = new Boolean[] { Boolean.FALSE }; - String[] validationError = new String[] { null }; - Exception[] exception = new Exception[] { null }; - Document validatedDoc = null; - boolean usingAlternateXml = false; - boolean usingAlternateUrl = false; - String validatedUri = null; - - String[] defaultNames = getDefaultXmlFileUrls(); - String firstDefaultName = defaultNames.length > 0 ? defaultNames[0] : ""; - - InputStream xml = fetchXmlUrl(url, cache, monitor.createSubMonitor(1), exception); - if (xml != null) { - int version = getXmlSchemaVersion(xml); - if (version == 0) { - closeStream(xml); - xml = null; - } - } - - // FIXME: this is a quick fix to support an alternate upgrade path. - // The whole logic below needs to be updated. - if (xml == null && defaultNames.length > 0) { - ITaskMonitor subMonitor = monitor.createSubMonitor(1); - subMonitor.setProgressMax(defaultNames.length); - - String baseUrl = url; - if (!baseUrl.endsWith("/")) { - int pos = baseUrl.lastIndexOf('/'); - if (pos > 0) { - baseUrl = baseUrl.substring(0, pos + 1); - } - } - - for (String name : defaultNames) { - String newUrl = baseUrl + name; - if (newUrl.equals(url)) { - continue; - } - xml = fetchXmlUrl(newUrl, cache, subMonitor.createSubMonitor(1), exception); - if (xml != null) { - int version = getXmlSchemaVersion(xml); - if (version == 0) { - closeStream(xml); - xml = null; - } else { - url = newUrl; - subMonitor.incProgress( - subMonitor.getProgressMax() - subMonitor.getProgress()); - break; - } - } - } - } else { - monitor.incProgress(1); - } - - // If the original URL can't be fetched - // and the URL doesn't explicitly end with our filename - // and it wasn't an HTTP authentication operation canceled by the user - // then make another tentative after changing the URL. - if (xml == null - && !url.endsWith(firstDefaultName) - && !(exception[0] instanceof CanceledByUserException)) { - if (!url.endsWith("/")) { //$NON-NLS-1$ - url += "/"; //$NON-NLS-1$ - } - url += firstDefaultName; - - xml = fetchXmlUrl(url, cache, monitor.createSubMonitor(1), exception); - usingAlternateUrl = true; - } else { - monitor.incProgress(1); - } - - // FIXME this needs to revisited. - if (xml != null) { - monitor.setDescription("Validate XML: %1$s", url); - - ITaskMonitor subMonitor = monitor.createSubMonitor(2); - subMonitor.setProgressMax(2); - for (int tryOtherUrl = 0; tryOtherUrl < 2; tryOtherUrl++) { - // Explore the XML to find the potential XML schema version - int version = getXmlSchemaVersion(xml); - - if (version >= 1 && version <= getNsLatestVersion()) { - // This should be a version we can handle. Try to validate it - // and report any error as invalid XML syntax, - - String uri = validateXml(xml, url, version, validationError, validatorFound); - if (uri != null) { - // Validation was successful - validatedDoc = getDocument(xml, monitor); - validatedUri = uri; - - if (usingAlternateUrl && validatedDoc != null) { - // If the second tentative succeeded, indicate it in the console - // with the URL that worked. - monitor.log("Repository found at %1$s", url); - - // Keep the modified URL - mUrl = url; - } - } else if (validatorFound[0].equals(Boolean.FALSE)) { - // Validation failed because this JVM lacks a proper XML Validator - mFetchError = validationError[0]; - } else { - // We got a validator but validation failed. We know there's - // what looks like a suitable root element with a suitable XMLNS - // so it must be a genuine error of an XML not conforming to the schema. - } - } else if (version > getNsLatestVersion()) { - // The schema used is more recent than what is supported by this tool. - // Tell the user to upgrade, pointing him to the right version of the tool - // package. - - try { - validatedDoc = findAlternateToolsXml(xml); - } catch (IOException e) { - // Failed, will be handled below. - } - if (validatedDoc != null) { - validationError[0] = null; // remove error from XML validation - validatedUri = getNsUri(); - usingAlternateXml = true; - } - - } else if (version < 1 && tryOtherUrl == 0 && !usingAlternateUrl) { - // This is obviously not one of our documents. - mFetchError = String.format( - "Failed to validate the XML for the repository at URL '%1$s'", - url); - - // If we haven't already tried the alternate URL, let's do it now. - // We don't capture any fetch exception that happen during the second - // fetch in order to avoid hidding any previous fetch errors. - if (!url.endsWith(firstDefaultName)) { - if (!url.endsWith("/")) { //$NON-NLS-1$ - url += "/"; //$NON-NLS-1$ - } - url += firstDefaultName; - - closeStream(xml); - xml = fetchXmlUrl(url, cache, subMonitor.createSubMonitor(1), - null /* outException */); - subMonitor.incProgress(1); - // Loop to try the alternative document - if (xml != null) { - usingAlternateUrl = true; - continue; - } - } - } else if (version < 1 && usingAlternateUrl && mFetchError == null) { - // The alternate URL is obviously not a valid XML either. - // We only report the error if we failed to produce one earlier. - mFetchError = String.format( - "Failed to validate the XML for the repository at URL '%1$s'", - url); - } - - // If we get here either we succeeded or we ran out of alternatives. - break; - } - } - - // If any exception was handled during the URL fetch, display it now. - if (exception[0] != null) { - mFetchError = "Failed to fetch URL"; - - String reason = null; - if (exception[0] instanceof FileNotFoundException) { - // FNF has no useful getMessage, so we need to special handle it. - reason = "File not found"; - mFetchError += ": " + reason; - } else if (exception[0] instanceof SSLKeyException) { - // That's a common error and we have a pref for it. - reason = "HTTPS SSL error. You might want to force download through HTTP in the settings."; - mFetchError += ": HTTPS SSL error"; - } else if (exception[0].getMessage() != null) { - reason = - exception[0].getClass().getSimpleName().replace("Exception", "") //$NON-NLS-1$ //$NON-NLS-2$ - + ' ' - + exception[0].getMessage(); - } else { - reason = exception[0].toString(); - } - - monitor.logError("Failed to fetch URL %1$s, reason: %2$s", url, reason); - } - - if (validationError[0] != null) { - monitor.logError("%s", validationError[0]); //$NON-NLS-1$ - } - - // Stop here if we failed to validate the XML. We don't want to load it. - if (validatedDoc == null) { - return; - } - - if (usingAlternateXml) { - // We found something using the "alternate" XML schema (that is the one made up - // to support schema upgrades). That means the user can only install the tools - // and needs to upgrade them before it download more stuff. - - // Is the manager running from inside ADT? - // We check that com.android.ide.eclipse.adt.AdtPlugin exists using reflection. - - boolean isADT = false; - try { - Class<?> adt = Class.forName("com.android.ide.eclipse.adt.AdtPlugin"); //$NON-NLS-1$ - isADT = (adt != null); - } catch (ClassNotFoundException e) { - // pass - } - - String info; - if (isADT) { - info = "This repository requires a more recent version of ADT. Please update the Eclipse Android plugin."; - mDescription = "This repository requires a more recent version of ADT, the Eclipse Android plugin.\nYou must update it before you can see other new packages."; - - } else { - info = "This repository requires a more recent version of the Tools. Please update."; - mDescription = "This repository requires a more recent version of the Tools.\nYou must update it before you can see other new packages."; - } - - mFetchError = mFetchError == null ? info : mFetchError + ". " + info; - } - - monitor.incProgress(1); - - if (xml != null) { - monitor.setDescription("Parse XML: %1$s", url); - monitor.incProgress(1); - parsePackages(validatedDoc, validatedUri, monitor); - if (mPackages == null || mPackages.length == 0) { - mDescription += "\nNo packages found."; - } else if (mPackages.length == 1) { - mDescription += "\nOne package found."; - } else { - mDescription += String.format("\n%1$d packages found.", mPackages.length); - } - } - - // done - monitor.incProgress(1); - closeStream(xml); - } - - private void setDefaultDescription() { - if (isAddonSource()) { - String desc = ""; - - if (mUiName != null) { - desc += "Add-on Provider: " + mUiName; - desc += "\n"; - } - desc += "Add-on URL: " + mUrl; - - mDescription = desc; - } else { - mDescription = String.format("SDK Source: %1$s", mUrl); - } - } - - /** - * Fetches the document at the given URL and returns it as a string. Returns - * null if anything wrong happens and write errors to the monitor. - * - * @param urlString The URL to load, as a string. - * @param monitor {@link ITaskMonitor} related to this URL. - * @param outException If non null, where to store any exception that - * happens during the fetch. - */ - private InputStream fetchXmlUrl(String urlString, - DownloadCache cache, - ITaskMonitor monitor, - Exception[] outException) { - try { - InputStream xml = cache.openCachedUrl(urlString, monitor); - if (xml != null) { - xml.mark(500000); - xml = new NonClosingInputStream(xml); - ((NonClosingInputStream) xml).setCloseBehavior(CloseBehavior.RESET); - } - return xml; - } catch (Exception e) { - if (outException != null) { - outException[0] = e; - } - } - - return null; - } - - /** - * Closes the stream, ignore any exception from InputStream.close(). - * If the stream is a NonClosingInputStream, sets it to CloseBehavior.CLOSE first. - */ - private void closeStream(InputStream is) { - if (is != null) { - if (is instanceof NonClosingInputStream) { - ((NonClosingInputStream) is).setCloseBehavior(CloseBehavior.CLOSE); - } - try { - is.close(); - } catch (IOException ignore) {} - } - } - - /** - * Validates this XML against one of the requested SDK Repository schemas. - * If the XML was correctly validated, returns the schema that worked. - * If it doesn't validate, returns null and stores the error in outError[0]. - * If we can't find a validator, returns null and set validatorFound[0] to false. - */ - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected String validateXml(InputStream xml, String url, int version, - String[] outError, Boolean[] validatorFound) { - - if (xml == null) { - return null; - } - - try { - Validator validator = getValidator(version); - - if (validator == null) { - validatorFound[0] = Boolean.FALSE; - outError[0] = String.format( - "XML verification failed for %1$s.\nNo suitable XML Schema Validator could be found in your Java environment. Please consider updating your version of Java.", - url); - return null; - } - - validatorFound[0] = Boolean.TRUE; - - // Reset the stream if it supports that operation. - assert xml.markSupported(); - xml.reset(); - - // Validation throws a bunch of possible Exceptions on failure. - validator.validate(new StreamSource(xml)); - return getSchemaUri(version); - - } catch (SAXParseException e) { - outError[0] = String.format( - "XML verification failed for %1$s.\nLine %2$d:%3$d, Error: %4$s", - url, - e.getLineNumber(), - e.getColumnNumber(), - e.toString()); - - } catch (Exception e) { - outError[0] = String.format( - "XML verification failed for %1$s.\nError: %2$s", - url, - e.toString()); - } - return null; - } - - /** - * Manually parses the root element of the XML to extract the schema version - * at the end of the xmlns:sdk="http://schemas.android.com/sdk/android/repository/$N" - * declaration. - * - * @return 1..{@link SdkRepoConstants#NS_LATEST_VERSION} for a valid schema version - * or 0 if no schema could be found. - */ - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected int getXmlSchemaVersion(InputStream xml) { - if (xml == null) { - return 0; - } - - // Get an XML document - Document doc = null; - try { - assert xml.markSupported(); - xml.reset(); - - DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance(); - factory.setIgnoringComments(false); - factory.setValidating(false); - - // Parse the old document using a non namespace aware builder - factory.setNamespaceAware(false); - DocumentBuilder builder = factory.newDocumentBuilder(); - - // We don't want the default handler which prints errors to stderr. - builder.setErrorHandler(new ErrorHandler() { - @Override - public void warning(SAXParseException e) throws SAXException { - // pass - } - @Override - public void fatalError(SAXParseException e) throws SAXException { - throw e; - } - @Override - public void error(SAXParseException e) throws SAXException { - throw e; - } - }); - - doc = builder.parse(xml); - - // Prepare a new document using a namespace aware builder - factory.setNamespaceAware(true); - builder = factory.newDocumentBuilder(); - - } catch (Exception e) { - // Failed to reset XML stream - // Failed to get builder factor - // Failed to create XML document builder - // Failed to parse XML document - // Failed to read XML document - } - - if (doc == null) { - return 0; - } - - // Check the root element is an XML with at least the following properties: - // <sdk:sdk-repository - // xmlns:sdk="http://schemas.android.com/sdk/android/repository/$N"> - // - // Note that we don't have namespace support enabled, we just do it manually. - - Pattern nsPattern = Pattern.compile(getNsPattern()); - - String prefix = null; - for (Node child = doc.getFirstChild(); child != null; child = child.getNextSibling()) { - if (child.getNodeType() == Node.ELEMENT_NODE) { - prefix = null; - String name = child.getNodeName(); - int pos = name.indexOf(':'); - if (pos > 0 && pos < name.length() - 1) { - prefix = name.substring(0, pos); - name = name.substring(pos + 1); - } - if (getRootElementName().equals(name)) { - NamedNodeMap attrs = child.getAttributes(); - String xmlns = "xmlns"; //$NON-NLS-1$ - if (prefix != null) { - xmlns += ":" + prefix; //$NON-NLS-1$ - } - Node attr = attrs.getNamedItem(xmlns); - if (attr != null) { - String uri = attr.getNodeValue(); - if (uri != null) { - Matcher m = nsPattern.matcher(uri); - if (m.matches()) { - String version = m.group(1); - try { - return Integer.parseInt(version); - } catch (NumberFormatException e) { - return 0; - } - } - } - } - } - } - } - - return 0; - } - - /** - * Helper method that returns a validator for our XSD, or null if the current Java - * implementation can't process XSD schemas. - * - * @param version The version of the XML Schema. - * See {@link SdkRepoConstants#getXsdStream(int)} - */ - private Validator getValidator(int version) throws SAXException { - InputStream xsdStream = getXsdStream(version); - SchemaFactory factory = SchemaFactory.newInstance(XMLConstants.W3C_XML_SCHEMA_NS_URI); - - if (factory == null) { - return null; - } - - // This may throw a SAX Exception if the schema itself is not a valid XSD - Schema schema = factory.newSchema(new StreamSource(xsdStream)); - - Validator validator = schema == null ? null : schema.newValidator(); - - // We don't want the default handler, which by default dumps errors to stderr. - validator.setErrorHandler(new ErrorHandler() { - @Override - public void warning(SAXParseException e) throws SAXException { - // pass - } - @Override - public void fatalError(SAXParseException e) throws SAXException { - throw e; - } - @Override - public void error(SAXParseException e) throws SAXException { - throw e; - } - }); - - return validator; - } - - /** - * Parse all packages defined in the SDK Repository XML and creates - * a new mPackages array with them. - */ - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected boolean parsePackages(Document doc, String nsUri, ITaskMonitor monitor) { - - Node root = getFirstChild(doc, nsUri, getRootElementName()); - if (root != null) { - - ArrayList<Package> packages = new ArrayList<Package>(); - - // Parse license definitions - HashMap<String, String> licenses = new HashMap<String, String>(); - for (Node child = root.getFirstChild(); - child != null; - child = child.getNextSibling()) { - if (child.getNodeType() == Node.ELEMENT_NODE && - nsUri.equals(child.getNamespaceURI()) && - child.getLocalName().equals(RepoConstants.NODE_LICENSE)) { - Node id = child.getAttributes().getNamedItem(RepoConstants.ATTR_ID); - if (id != null) { - licenses.put(id.getNodeValue(), child.getTextContent()); - } - } - } - - // Parse packages - for (Node child = root.getFirstChild(); - child != null; - child = child.getNextSibling()) { - if (child.getNodeType() == Node.ELEMENT_NODE && - nsUri.equals(child.getNamespaceURI())) { - String name = child.getLocalName(); - Package p = null; - - try { - // We can load addon and extra packages from all sources, either - // internal or user sources. - if (SdkAddonConstants.NODE_ADD_ON.equals(name)) { - p = new AddonPackage(this, child, nsUri, licenses); - - } else if (SdkAddonConstants.NODE_EXTRA.equals(name)) { - p = new ExtraPackage(this, child, nsUri, licenses); - - } else if (!isAddonSource()) { - // We only load platform, doc and tool packages from internal - // sources, never from user sources. - if (SdkRepoConstants.NODE_PLATFORM.equals(name)) { - p = new PlatformPackage(this, child, nsUri, licenses); - } else if (SdkRepoConstants.NODE_DOC.equals(name)) { - p = new DocPackage(this, child, nsUri, licenses); - } else if (SdkRepoConstants.NODE_TOOL.equals(name)) { - p = new ToolPackage(this, child, nsUri, licenses); - } else if (SdkRepoConstants.NODE_PLATFORM_TOOL.equals(name)) { - p = new PlatformToolPackage(this, child, nsUri, licenses); - } else if (SdkRepoConstants.NODE_SAMPLE.equals(name)) { - p = new SamplePackage(this, child, nsUri, licenses); - } else if (SdkRepoConstants.NODE_SYSTEM_IMAGE.equals(name)) { - p = new SystemImagePackage(this, child, nsUri, licenses); - } else if (SdkRepoConstants.NODE_SOURCE.equals(name)) { - p = new SourcePackage(this, child, nsUri, licenses); - } - } - - if (p != null) { - packages.add(p); - monitor.logVerbose("Found %1$s", p.getShortDescription()); - } - } catch (Exception e) { - // Ignore invalid packages - monitor.logError("Ignoring invalid %1$s element: %2$s", name, e.toString()); - } - } - } - - setPackages(packages.toArray(new Package[packages.size()])); - - return true; - } - - return false; - } - - /** - * Returns the first child element with the given XML local name. - * If xmlLocalName is null, returns the very first child element. - */ - private Node getFirstChild(Node node, String nsUri, String xmlLocalName) { - - for(Node child = node.getFirstChild(); child != null; child = child.getNextSibling()) { - if (child.getNodeType() == Node.ELEMENT_NODE && - nsUri.equals(child.getNamespaceURI())) { - if (xmlLocalName == null || child.getLocalName().equals(xmlLocalName)) { - return child; - } - } - } - - return null; - } - - /** - * Takes an XML document as a string as parameter and returns a DOM for it. - * - * On error, returns null and prints a (hopefully) useful message on the monitor. - */ - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected Document getDocument(InputStream xml, ITaskMonitor monitor) { - try { - DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance(); - factory.setIgnoringComments(true); - factory.setNamespaceAware(true); - - DocumentBuilder builder = factory.newDocumentBuilder(); - assert xml.markSupported(); - xml.reset(); - Document doc = builder.parse(new InputSource(xml)); - - return doc; - } catch (ParserConfigurationException e) { - monitor.logError("Failed to create XML document builder"); - - } catch (SAXException e) { - monitor.logError("Failed to parse XML document"); - - } catch (IOException e) { - monitor.logError("Failed to read XML document"); - } - - return null; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/sources/SdkSourceCategory.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/sources/SdkSourceCategory.java deleted file mode 100755 index 5272cd5..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/sources/SdkSourceCategory.java +++ /dev/null @@ -1,89 +0,0 @@ -/* - * Copyright (C) 2010 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.sources; - -import com.android.sdklib.internal.repository.IDescription; - - -/** - * The category of a given {@link SdkSource} (which represents a download site). - */ -public enum SdkSourceCategory implements IDescription { - - /** - * The default canonical and official Android repository. - */ - ANDROID_REPO("Android Repository", true), - - /** - * Repositories contributed by the SDK_UPDATER_URLS env var, - * only used for local debugging. - */ - GETENV_REPOS("Custom Repositories", false), - - /** - * All third-party add-ons fetched from the Android repository. - */ - ADDONS_3RD_PARTY("Third party Add-ons", true), - - /** - * All add-ons contributed locally by the user via the "Add Add-on Site" button. - */ - USER_ADDONS("User Add-ons", false), - - /** - * Add-ons contributed by the SDK_UPDATER_USER_URLS env var, - * only used for local debugging. - */ - GETENV_ADDONS("Custom Add-ons", false); - - - private final String mUiName; - private final boolean mAlwaysDisplay; - - private SdkSourceCategory(String uiName, boolean alwaysDisplay) { - mUiName = uiName; - mAlwaysDisplay = alwaysDisplay; - } - - /** - * Returns the UI-visible name of the cateogry. Displayed in the available package tree. - * Cannot be null nor empty. - */ - public String getUiName() { - return mUiName; - } - - /** - * True if this category must always be displayed by the available package tree, even - * if empty. - * When false, the category must not be displayed when empty. - */ - public boolean getAlwaysDisplay() { - return mAlwaysDisplay; - } - - @Override - public String getLongDescription() { - return getUiName(); - } - - @Override - public String getShortDescription() { - return getUiName(); - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/sources/SdkSourceProperties.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/sources/SdkSourceProperties.java deleted file mode 100755 index cdd428f..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/sources/SdkSourceProperties.java +++ /dev/null @@ -1,249 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.sources; - -import com.android.annotations.NonNull; -import com.android.annotations.Nullable; -import com.android.annotations.VisibleForTesting; -import com.android.annotations.VisibleForTesting.Visibility; -import com.android.prefs.AndroidLocation; -import com.android.prefs.AndroidLocation.AndroidLocationException; - -import java.io.File; -import java.io.FileInputStream; -import java.io.FileOutputStream; -import java.io.IOException; -import java.util.Collections; -import java.util.Comparator; -import java.util.List; -import java.util.Properties; - -/** - * Properties for individual sources which are persisted by a local settings file. - * <p/> - * All instances of {@link SdkSourceProperties} share the same singleton storage. - * The persisted setting file is loaded as necessary, however callers must persist - * it at some point by calling {@link #save()}. - */ -public class SdkSourceProperties { - - /** - * An internal file version number, in case we want to change the format later. - */ - private static final String KEY_VERSION = "@version@"; //$NON-NLS-1$ - /** - * The last known UI name of the source. - */ - public static final String KEY_NAME = "@name@"; //$NON-NLS-1$ - /** - * A non-null string if the source is disabled. Null if the source is enabled. - */ - public static final String KEY_DISABLED = "@disabled@"; //$NON-NLS-1$ - - private static final Properties sSourcesProperties = new Properties(); - private static final String SRC_FILENAME = "sites-settings.cfg"; //$NON-NLS-1$ - - private static boolean sModified = false; - - public SdkSourceProperties() { - } - - public void save() { - synchronized (sSourcesProperties) { - if (sModified && !sSourcesProperties.isEmpty()) { - saveLocked(); - sModified = false; - } - } - } - - /** - * Retrieves a property for the given source URL and the given key type. - * <p/> - * Implementation detail: this loads the persistent settings file as needed. - * - * @param key The kind of property to retrieve for that source URL. - * @param sourceUrl The source URL. - * @param defaultValue The default value to return, if the property isn't found. Can be null. - * @return The non-null string property for the key/sourceUrl or the default value. - */ - @Nullable - public String getProperty(@NonNull String key, - @NonNull String sourceUrl, - @Nullable String defaultValue) { - String value = defaultValue; - - synchronized (sSourcesProperties) { - if (sSourcesProperties.isEmpty()) { - loadLocked(); - } - - value = sSourcesProperties.getProperty(key + sourceUrl, defaultValue); - } - - return value; - } - - /** - * Sets or remove a property for the given source URL and the given key type. - * <p/> - * Implementation detail: this does <em>not</em> save the persistent settings file. - * Somehow the caller will need to call the {@link #save()} method later. - * - * @param key The kind of property to retrieve for that source URL. - * @param sourceUrl The source URL. - * @param value The new value to set (if non null) or null to remove an existing property. - */ - public void setProperty(String key, String sourceUrl, String value) { - synchronized (sSourcesProperties) { - if (sSourcesProperties.isEmpty()) { - loadLocked(); - } - - key += sourceUrl; - - String old = sSourcesProperties.getProperty(key); - if (value == null) { - if (old != null) { - sSourcesProperties.remove(key); - sModified = true; - } - } else if (old == null || !old.equals(value)) { - sSourcesProperties.setProperty(key, value); - sModified = true; - } - } - } - - /** - * Returns an internal string representation of the underlying Properties map, - * sorted by ascending keys. Useful for debugging and testing purposes only. - */ - @Override - public String toString() { - StringBuilder sb = new StringBuilder("<SdkSourceProperties"); //$NON-NLS-1$ - synchronized (sSourcesProperties) { - List<Object> keys = Collections.list(sSourcesProperties.keys()); - Collections.sort(keys, new Comparator<Object>() { - @Override - public int compare(Object o1, Object o2) { - return o1.toString().compareTo(o2.toString()); - }}); - - for (Object key : keys) { - sb.append('\n').append(key) - .append(" = ").append(sSourcesProperties.get(key)); //$NON-NLS-1$ - } - } - sb.append('>'); - return sb.toString(); - } - - /** Load state from persistent file. Expects sSourcesProperties to be synchronized. */ - private void loadLocked() { - // Load state from persistent file - if (loadProperties()) { - // If it lacks our magic version key, don't use it - if (sSourcesProperties.getProperty(KEY_VERSION) == null) { - sSourcesProperties.clear(); - } - - sModified = false; - } - - if (sSourcesProperties.isEmpty()) { - // Nothing was loaded. Initialize the storage with a version - // identified. This isn't currently checked back, but we might - // want it later if we decide to change the way this works. - // The version key is choosen on purpose to not match any valid URL. - sSourcesProperties.setProperty(KEY_VERSION, "1"); //$NON-NLS-1$ //$NON-NLS-2$ - } - } - - /** - * Load properties from default file. Extracted so that it can be mocked in tests. - * - * @return True if actually loaded the file. False if there was an IO error or no - * file and nothing was loaded. - */ - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected boolean loadProperties() { - try { - String folder = AndroidLocation.getFolder(); - File f = new File(folder, SRC_FILENAME); - if (f.exists()) { - FileInputStream fis = null; - try { - fis = new FileInputStream(f); - sSourcesProperties.load(fis); - } catch (IOException ignore) { - // nop - } finally { - if (fis != null) { - try { - fis.close(); - } catch (IOException ignore) {} - } - } - - return true; - } - } catch (AndroidLocationException ignore) { - // nop - } - return false; - } - - /** - * Save file to disk. Expects sSourcesProperties to be synchronized. - * Made accessible for testing purposes. - * For public usage, please use {@link #save()} instead. - */ - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected void saveLocked() { - // Persist it to the file - FileOutputStream fos = null; - try { - String folder = AndroidLocation.getFolder(); - File f = new File(folder, SRC_FILENAME); - - fos = new FileOutputStream(f); - - sSourcesProperties.store(fos,"## Sites Settings for Android SDK Manager");//$NON-NLS-1$ - - } catch (AndroidLocationException ignore) { - // nop - } catch (IOException ignore) { - // nop - } finally { - if (fos != null) { - try { - fos.close(); - } catch (IOException ignore) {} - } - } - } - - /** Empty current property list. Made accessible for testing purposes. */ - @VisibleForTesting(visibility=Visibility.PRIVATE) - protected void clear() { - synchronized (sSourcesProperties) { - sSourcesProperties.clear(); - sModified = false; - } - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/sources/SdkSources.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/sources/SdkSources.java deleted file mode 100755 index c89df5e..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/sources/SdkSources.java +++ /dev/null @@ -1,429 +0,0 @@ -/* - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.sources; - -import com.android.prefs.AndroidLocation; -import com.android.prefs.AndroidLocation.AndroidLocationException; -import com.android.sdklib.repository.SdkSysImgConstants; -import com.android.utils.ILogger; - -import java.io.File; -import java.io.FileInputStream; -import java.io.FileOutputStream; -import java.io.IOException; -import java.util.ArrayList; -import java.util.EnumMap; -import java.util.Iterator; -import java.util.Properties; -import java.util.Map.Entry; - -/** - * A list of sdk-repository and sdk-addon sources, sorted by {@link SdkSourceCategory}. - */ -public class SdkSources { - - private static final String KEY_COUNT = "count"; - - private static final String KEY_SRC = "src"; - - private static final String SRC_FILENAME = "repositories.cfg"; //$NON-NLS-1$ - - private final EnumMap<SdkSourceCategory, ArrayList<SdkSource>> mSources = - new EnumMap<SdkSourceCategory, ArrayList<SdkSource>>(SdkSourceCategory.class); - - private ArrayList<Runnable> mChangeListeners; // lazily initialized - - - public SdkSources() { - } - - /** - * Adds a new source to the Sources list. - * <p/> - * Implementation detail: {@link SdkSources} doesn't invoke {@link #notifyChangeListeners()} - * directly. Callers who use {@code add()} are responsible for notifying the listeners once - * they are done modifying the sources list. The intent is to notify the listeners only once - * at the end, not for every single addition. - */ - public void add(SdkSourceCategory category, SdkSource source) { - synchronized (mSources) { - ArrayList<SdkSource> list = mSources.get(category); - if (list == null) { - list = new ArrayList<SdkSource>(); - mSources.put(category, list); - } - - list.add(source); - } - } - - /** - * Removes a source from the Sources list. - * <p/> - * Callers who remove entries are responsible for notifying the listeners using - * {@link #notifyChangeListeners()} once they are done modifying the sources list. - */ - public void remove(SdkSource source) { - synchronized (mSources) { - Iterator<Entry<SdkSourceCategory, ArrayList<SdkSource>>> it = - mSources.entrySet().iterator(); - while (it.hasNext()) { - Entry<SdkSourceCategory, ArrayList<SdkSource>> entry = it.next(); - ArrayList<SdkSource> list = entry.getValue(); - - if (list.remove(source)) { - if (list.isEmpty()) { - // remove the entry since the source list became empty - it.remove(); - } - } - } - } - } - - /** - * Removes all the sources in the given category. - * <p/> - * Callers who remove entries are responsible for notifying the listeners using - * {@link #notifyChangeListeners()} once they are done modifying the sources list. - */ - public void removeAll(SdkSourceCategory category) { - synchronized (mSources) { - mSources.remove(category); - } - } - - /** - * Returns a set of all categories that must be displayed. This includes all - * categories that are to be always displayed as well as all categories which - * have at least one source. - * Might return a empty array, but never returns null. - */ - public SdkSourceCategory[] getCategories() { - ArrayList<SdkSourceCategory> cats = new ArrayList<SdkSourceCategory>(); - - for (SdkSourceCategory cat : SdkSourceCategory.values()) { - if (cat.getAlwaysDisplay()) { - cats.add(cat); - } else { - synchronized (mSources) { - ArrayList<SdkSource> list = mSources.get(cat); - if (list != null && !list.isEmpty()) { - cats.add(cat); - } - } - } - } - - return cats.toArray(new SdkSourceCategory[cats.size()]); - } - - /** - * Returns a new array of sources attached to the given category. - * Might return an empty array, but never returns null. - */ - public SdkSource[] getSources(SdkSourceCategory category) { - synchronized (mSources) { - ArrayList<SdkSource> list = mSources.get(category); - if (list == null) { - return new SdkSource[0]; - } else { - return list.toArray(new SdkSource[list.size()]); - } - } - } - - /** - * Returns an array of the sources across all categories. This is never null. - */ - public SdkSource[] getAllSources() { - synchronized (mSources) { - int n = 0; - - for (ArrayList<SdkSource> list : mSources.values()) { - n += list.size(); - } - - SdkSource[] sources = new SdkSource[n]; - - int i = 0; - for (ArrayList<SdkSource> list : mSources.values()) { - for (SdkSource source : list) { - sources[i++] = source; - } - } - - return sources; - } - } - - /** - * Each source keeps a local cache of whatever it loaded recently. - * This calls {@link SdkSource#clearPackages()} on all the available sources, - * and the next call to {@link SdkSource#getPackages()} will actually reload - * the remote package list. - */ - public void clearAllPackages() { - synchronized (mSources) { - for (ArrayList<SdkSource> list : mSources.values()) { - for (SdkSource source : list) { - source.clearPackages(); - } - } - } - } - - /** - * Returns the category of a given source, or null if the source is unknown. - * <p/> - * Note that this method uses object identity to find a given source, and does - * not identify sources by their URL like {@link #hasSourceUrl(SdkSource)} does. - * <p/> - * The search is O(N), which should be acceptable on the expectedly small source list. - */ - public SdkSourceCategory getCategory(SdkSource source) { - if (source != null) { - synchronized (mSources) { - for (Entry<SdkSourceCategory, ArrayList<SdkSource>> entry : mSources.entrySet()) { - if (entry.getValue().contains(source)) { - return entry.getKey(); - } - } - } - } - return null; - } - - /** - * Returns true if there's already a similar source in the sources list - * under any category. - * <p/> - * Important: The match is NOT done on object identity. - * Instead, this searches for a <em>similar</em> source, based on - * {@link SdkSource#equals(Object)} which compares the source URLs. - * <p/> - * The search is O(N), which should be acceptable on the expectedly small source list. - */ - public boolean hasSourceUrl(SdkSource source) { - synchronized (mSources) { - for (ArrayList<SdkSource> list : mSources.values()) { - for (SdkSource s : list) { - if (s.equals(source)) { - return true; - } - } - } - return false; - } - } - - /** - * Returns true if there's already a similar source in the sources list - * under the specified category. - * <p/> - * Important: The match is NOT done on object identity. - * Instead, this searches for a <em>similar</em> source, based on - * {@link SdkSource#equals(Object)} which compares the source URLs. - * <p/> - * The search is O(N), which should be acceptable on the expectedly small source list. - */ - public boolean hasSourceUrl(SdkSourceCategory category, SdkSource source) { - synchronized (mSources) { - ArrayList<SdkSource> list = mSources.get(category); - if (list != null) { - for (SdkSource s : list) { - if (s.equals(source)) { - return true; - } - } - } - return false; - } - } - - /** - * Loads all user sources. This <em>replaces</em> all existing user sources - * by the ones from the property file. - * <p/> - * This calls {@link #notifyChangeListeners()} at the end of the operation. - */ - public void loadUserAddons(ILogger log) { - // Implementation detail: synchronize on the sources list to make sure that - // a- the source list doesn't change while we load/save it, and most important - // b- to make sure it's not being saved while loaded or the reverse. - // In most cases we do these operation from the UI thread so it's not really - // that necessary. This is more a protection in case of someone calls this - // from a worker thread by mistake. - synchronized (mSources) { - // Remove all existing user sources - removeAll(SdkSourceCategory.USER_ADDONS); - - // Load new user sources from property file - FileInputStream fis = null; - try { - String folder = AndroidLocation.getFolder(); - File f = new File(folder, SRC_FILENAME); - if (f.exists()) { - fis = new FileInputStream(f); - - Properties props = new Properties(); - props.load(fis); - - int count = Integer.parseInt(props.getProperty(KEY_COUNT, "0")); - - for (int i = 0; i < count; i++) { - String url = props.getProperty(String.format("%s%02d", KEY_SRC, i)); //$NON-NLS-1$ - if (url != null) { - // FIXME: this code originally only dealt with add-on XML sources. - // Now we'd like it to deal with system-image sources too, but we - // don't know which kind of object it is (at least not without - // trying to fetch it.) As a temporary workaround, just take a - // guess based on the leaf URI name. However ideally what we can - // simply do is add a checkbox "is system-image XML" in the user - // dialog and pass this info down here. Another alternative is to - // make a "dynamic" source object that tries to guess its type once - // the URI has been fetched. - SdkSource s; - if (url.endsWith(SdkSysImgConstants.URL_DEFAULT_FILENAME)) { - s = new SdkSysImgSource(url, null/*uiName*/); - } else { - s = new SdkAddonSource(url, null/*uiName*/); - } - if (!hasSourceUrl(s)) { - add(SdkSourceCategory.USER_ADDONS, s); - } - } - } - } - - } catch (NumberFormatException e) { - log.error(e, null); - - } catch (AndroidLocationException e) { - log.error(e, null); - - } catch (IOException e) { - log.error(e, null); - - } finally { - if (fis != null) { - try { - fis.close(); - } catch (IOException e) { - } - } - } - } - notifyChangeListeners(); - } - - /** - * Saves all the user sources. - * @param log Logger. Cannot be null. - */ - public void saveUserAddons(ILogger log) { - // See the implementation detail note in loadUserAddons() about the synchronization. - synchronized (mSources) { - FileOutputStream fos = null; - try { - String folder = AndroidLocation.getFolder(); - File f = new File(folder, SRC_FILENAME); - - fos = new FileOutputStream(f); - - Properties props = new Properties(); - - int count = 0; - for (SdkSource s : getSources(SdkSourceCategory.USER_ADDONS)) { - props.setProperty(String.format("%s%02d", KEY_SRC, count), //$NON-NLS-1$ - s.getUrl()); - count++; - } - props.setProperty(KEY_COUNT, Integer.toString(count)); - - props.store( fos, "## User Sources for Android SDK Manager"); //$NON-NLS-1$ - - } catch (AndroidLocationException e) { - log.error(e, null); - - } catch (IOException e) { - log.error(e, null); - - } finally { - if (fos != null) { - try { - fos.close(); - } catch (IOException e) { - } - } - } - } - } - - /** - * Adds a listener that will be notified when the sources list has changed. - * - * @param changeListener A non-null listener to add. Ignored if already present. - * @see SdkSources#notifyChangeListeners() - */ - public void addChangeListener(Runnable changeListener) { - assert changeListener != null; - if (mChangeListeners == null) { - mChangeListeners = new ArrayList<Runnable>(); - } - synchronized (mChangeListeners) { - if (changeListener != null && !mChangeListeners.contains(changeListener)) { - mChangeListeners.add(changeListener); - } - } - } - - /** - * Removes a listener from the list of listeners to notify when the sources change. - * - * @param changeListener A listener to remove. Ignored if not previously added. - */ - public void removeChangeListener(Runnable changeListener) { - if (mChangeListeners != null && changeListener != null) { - synchronized (mChangeListeners) { - mChangeListeners.remove(changeListener); - } - } - } - - /** - * Invoke all the registered change listeners, if any. - * <p/> - * This <em>may</em> be called from a worker thread, in which case the runnable - * should take care of only updating UI from a main thread. - */ - public void notifyChangeListeners() { - if (mChangeListeners == null) { - return; - } - synchronized (mChangeListeners) { - for (Runnable runnable : mChangeListeners) { - try { - runnable.run(); - } catch (Throwable ignore) { - assert ignore == null : - "A SdkSource.ChangeListener failed with an exception: " + ignore.toString(); - } - } - } - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/sources/SdkSysImgSource.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/sources/SdkSysImgSource.java deleted file mode 100755 index 7909bff..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/internal/repository/sources/SdkSysImgSource.java +++ /dev/null @@ -1,109 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.sources; - -import com.android.annotations.Nullable; -import com.android.sdklib.internal.repository.packages.Package; -import com.android.sdklib.repository.SdkSysImgConstants; - -import org.w3c.dom.Document; - -import java.io.InputStream; - - -/** - * An sdk-sys-img source, i.e. a download site for system-image packages. - * A repository describes one or more {@link Package}s available for download. - */ -public class SdkSysImgSource extends SdkSource { - - /** - * Constructs a new source for the given repository URL. - * @param url The source URL. Cannot be null. If the URL ends with a /, the default - * sys-img.xml filename will be appended automatically. - * @param uiName The UI-visible name of the source. Can be null. - */ - public SdkSysImgSource(String url, String uiName) { - super(url, uiName); - } - - /** - * Returns true if this is an addon source. - * We only load addons and extras from these sources. - */ - @Override - public boolean isAddonSource() { - return false; - } - - /** - * Returns true if this is a system-image source. - * We only load system-images from these sources. - */ - @Override - public boolean isSysImgSource() { - return true; - } - - - @Override - protected String[] getDefaultXmlFileUrls() { - return new String[] { SdkSysImgConstants.URL_DEFAULT_FILENAME }; - } - - @Override - protected int getNsLatestVersion() { - return SdkSysImgConstants.NS_LATEST_VERSION; - } - - @Override - protected String getNsUri() { - return SdkSysImgConstants.NS_URI; - } - - @Override - protected String getNsPattern() { - return SdkSysImgConstants.NS_PATTERN; - } - - @Override - protected String getSchemaUri(int version) { - return SdkSysImgConstants.getSchemaUri(version); - } - - @Override - protected String getRootElementName() { - return SdkSysImgConstants.NODE_SDK_SYS_IMG; - } - - @Override - protected InputStream getXsdStream(int version) { - return SdkSysImgConstants.getXsdStream(version); - } - - /** - * This kind of schema does not support forward-evolution of the <tool> element. - * - * @param xml The input XML stream. Can be null. - * @return Always null. - * @null This implementation always return null. - */ - @Override - protected Document findAlternateToolsXml(@Nullable InputStream xml) { - return null; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/io/FileOp.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/io/FileOp.java deleted file mode 100755 index f9793cc..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/io/FileOp.java +++ /dev/null @@ -1,382 +0,0 @@ -/* - * Copyright (C) 2010 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.io; - -import com.android.SdkConstants; -import com.android.annotations.NonNull; -import com.google.common.io.Closeables; - -import java.io.File; -import java.io.FileInputStream; -import java.io.FileNotFoundException; -import java.io.FileOutputStream; -import java.io.IOException; -import java.io.OutputStream; -import java.lang.reflect.InvocationTargetException; -import java.lang.reflect.Method; -import java.util.Arrays; -import java.util.Properties; - - -/** - * Wraps some common {@link File} operations on files and folders. - * <p/> - * This makes it possible to override/mock/stub some file operations in unit tests. - */ -public class FileOp implements IFileOp { - - /** - * Reflection method for File.setExecutable(boolean, boolean). Only present in Java 6. - */ - private static Method sFileSetExecutable = null; - - /** - * Parameters to call File.setExecutable through reflection. - */ - private final static Object[] sFileSetExecutableParams = new Object[] { - Boolean.TRUE, Boolean.FALSE }; - - // static initialization of sFileSetExecutable. - static { - try { - sFileSetExecutable = File.class.getMethod("setExecutable", //$NON-NLS-1$ - boolean.class, boolean.class); - - } catch (SecurityException e) { - // do nothing we'll use chdmod instead - } catch (NoSuchMethodException e) { - // do nothing we'll use chdmod instead - } - } - - /** - * Appends the given {@code segments} to the {@code base} file. - * - * @param base A base file, non-null. - * @param segments Individual folder or filename segments to append to the base file. - * @return A new file representing the concatenation of the base path with all the segments. - */ - public static File append(File base, String...segments) { - for (String segment : segments) { - base = new File(base, segment); - } - return base; - } - - /** - * Appends the given {@code segments} to the {@code base} file. - * - * @param base A base file path, non-empty and non-null. - * @param segments Individual folder or filename segments to append to the base path. - * @return A new file representing the concatenation of the base path with all the segments. - */ - public static File append(String base, String...segments) { - return append(new File(base), segments); - } - - /** - * Helper to delete a file or a directory. - * For a directory, recursively deletes all of its content. - * Files that cannot be deleted right away are marked for deletion on exit. - * It's ok for the file or folder to not exist at all. - * The argument can be null. - */ - @Override - public void deleteFileOrFolder(File fileOrFolder) { - if (fileOrFolder != null) { - if (isDirectory(fileOrFolder)) { - // Must delete content recursively first - File[] files = fileOrFolder.listFiles(); - if (files != null) { - for (File item : files) { - deleteFileOrFolder(item); - } - } - } - - // Don't try to delete it if it doesn't exist. - if (!exists(fileOrFolder)) { - return; - } - - if (SdkConstants.CURRENT_PLATFORM == SdkConstants.PLATFORM_WINDOWS) { - // Trying to delete a resource on windows might fail if there's a file - // indexer locking the resource. Generally retrying will be enough to - // make it work. - // - // Try for half a second before giving up. - - for (int i = 0; i < 5; i++) { - if (fileOrFolder.delete()) { - return; - } - - try { - Thread.sleep(100 /*ms*/); - } catch (InterruptedException e) { - // Ignore. - } - } - - fileOrFolder.deleteOnExit(); - - } else { - // On Linux or Mac, just straight deleting it should just work. - - if (!fileOrFolder.delete()) { - fileOrFolder.deleteOnExit(); - } - } - } - } - - /** - * Sets the executable Unix permission (+x) on a file or folder. - * <p/> - * This attempts to use File#setExecutable through reflection if - * it's available. - * If this is not available, this invokes a chmod exec instead, - * so there is no guarantee of it being fast. - * <p/> - * Caller must make sure to not invoke this under Windows. - * - * @param file The file to set permissions on. - * @throws IOException If an I/O error occurs - */ - @Override - public void setExecutablePermission(File file) throws IOException { - - if (sFileSetExecutable != null) { - try { - sFileSetExecutable.invoke(file, sFileSetExecutableParams); - return; - } catch (IllegalArgumentException e) { - // we'll run chmod below - } catch (IllegalAccessException e) { - // we'll run chmod below - } catch (InvocationTargetException e) { - // we'll run chmod below - } - } - - Runtime.getRuntime().exec(new String[] { - "chmod", "+x", file.getAbsolutePath() //$NON-NLS-1$ //$NON-NLS-2$ - }); - } - - /** - * {@inheritDoc} - */ - @Override - public void setReadOnly(File file) { - file.setReadOnly(); - } - - /** - * Copies a binary file. - * - * @param source the source file to copy. - * @param dest the destination file to write. - * @throws FileNotFoundException if the source file doesn't exist. - * @throws IOException if there's a problem reading or writing the file. - */ - @Override - public void copyFile(File source, File dest) throws IOException { - byte[] buffer = new byte[8192]; - - FileInputStream fis = null; - FileOutputStream fos = null; - try { - fis = new FileInputStream(source); - fos = new FileOutputStream(dest); - - int read; - while ((read = fis.read(buffer)) != -1) { - fos.write(buffer, 0, read); - } - - } finally { - if (fis != null) { - try { - fis.close(); - } catch (IOException e) { - // Ignore. - } - } - if (fos != null) { - try { - fos.close(); - } catch (IOException e) { - // Ignore. - } - } - } - } - - /** - * Checks whether 2 binary files are the same. - * - * @param source the source file to copy - * @param destination the destination file to write - * @throws FileNotFoundException if the source files don't exist. - * @throws IOException if there's a problem reading the files. - */ - @Override - public boolean isSameFile(File source, File destination) throws IOException { - - if (source.length() != destination.length()) { - return false; - } - - FileInputStream fis1 = null; - FileInputStream fis2 = null; - - try { - fis1 = new FileInputStream(source); - fis2 = new FileInputStream(destination); - - byte[] buffer1 = new byte[8192]; - byte[] buffer2 = new byte[8192]; - - int read1; - while ((read1 = fis1.read(buffer1)) != -1) { - int read2 = 0; - while (read2 < read1) { - int n = fis2.read(buffer2, read2, read1 - read2); - if (n == -1) { - break; - } - } - - if (read2 != read1) { - return false; - } - - if (!Arrays.equals(buffer1, buffer2)) { - return false; - } - } - } finally { - if (fis2 != null) { - try { - fis2.close(); - } catch (IOException e) { - // ignore - } - } - if (fis1 != null) { - try { - fis1.close(); - } catch (IOException e) { - // ignore - } - } - } - - return true; - } - - /** Invokes {@link File#isFile()} on the given {@code file}. */ - @Override - public boolean isFile(File file) { - return file.isFile(); - } - - /** Invokes {@link File#isDirectory()} on the given {@code file}. */ - @Override - public boolean isDirectory(File file) { - return file.isDirectory(); - } - - /** Invokes {@link File#exists()} on the given {@code file}. */ - @Override - public boolean exists(File file) { - return file.exists(); - } - - /** Invokes {@link File#length()} on the given {@code file}. */ - @Override - public long length(File file) { - return file.length(); - } - - /** - * Invokes {@link File#delete()} on the given {@code file}. - * Note: for a recursive folder version, consider {@link #deleteFileOrFolder(File)}. - */ - @Override - public boolean delete(File file) { - return file.delete(); - } - - /** Invokes {@link File#mkdirs()} on the given {@code file}. */ - @Override - public boolean mkdirs(File file) { - return file.mkdirs(); - } - - /** Invokes {@link File#listFiles()} on the given {@code file}. */ - @Override - public File[] listFiles(File file) { - return file.listFiles(); - } - - /** Invokes {@link File#renameTo(File)} on the given files. */ - @Override - public boolean renameTo(File oldFile, File newFile) { - return oldFile.renameTo(newFile); - } - - /** Creates a new {@link FileOutputStream} for the given {@code file}. */ - @Override - public OutputStream newFileOutputStream(File file) throws FileNotFoundException { - return new FileOutputStream(file); - } - - @SuppressWarnings("resource") // Eclipse doesn't understand Closeables.closeQuietly - @Override - public @NonNull Properties loadProperties(@NonNull File file) { - Properties props = new Properties(); - FileInputStream fis = null; - try { - fis = new FileInputStream(file); - props.load(fis); - } catch (IOException ignore) { - } finally { - Closeables.closeQuietly(fis); - } - return props; - } - - @SuppressWarnings("resource") // Eclipse doesn't understand Closeables.closeQuietly - @Override - public boolean saveProperties(@NonNull File file, @NonNull Properties props, - @NonNull String comments) { - OutputStream fos = null; - try { - fos = newFileOutputStream(file); - - props.store(fos, comments); - return true; - } catch (IOException ignore) { - } finally { - Closeables.closeQuietly(fos); - } - - return false; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/io/IFileOp.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/io/IFileOp.java deleted file mode 100755 index 5b131d5..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/io/IFileOp.java +++ /dev/null @@ -1,139 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.io; - -import com.android.annotations.NonNull; - -import java.io.File; -import java.io.FileNotFoundException; -import java.io.FileOutputStream; -import java.io.IOException; -import java.io.OutputStream; -import java.util.Properties; - - -/** - * Wraps some common {@link File} operations on files and folders. - * <p/> - * This makes it possible to override/mock/stub some file operations in unit tests. - */ -public interface IFileOp { - - /** - * Helper to delete a file or a directory. - * For a directory, recursively deletes all of its content. - * Files that cannot be deleted right away are marked for deletion on exit. - * It's ok for the file or folder to not exist at all. - * The argument can be null. - */ - public abstract void deleteFileOrFolder(File fileOrFolder); - - /** - * Sets the executable Unix permission (+x) on a file or folder. - * <p/> - * This attempts to use File#setExecutable through reflection if - * it's available. - * If this is not available, this invokes a chmod exec instead, - * so there is no guarantee of it being fast. - * <p/> - * Caller must make sure to not invoke this under Windows. - * - * @param file The file to set permissions on. - * @throws IOException If an I/O error occurs - */ - public abstract void setExecutablePermission(File file) throws IOException; - - /** - * Sets the file or directory as read-only. - * - * @param file The file or directory to set permissions on. - */ - public abstract void setReadOnly(File file); - - /** - * Copies a binary file. - * - * @param source the source file to copy. - * @param dest the destination file to write. - * @throws FileNotFoundException if the source file doesn't exist. - * @throws IOException if there's a problem reading or writing the file. - */ - public abstract void copyFile(File source, File dest) throws IOException; - - /** - * Checks whether 2 binary files are the same. - * - * @param source the source file to copy - * @param destination the destination file to write - * @throws FileNotFoundException if the source files don't exist. - * @throws IOException if there's a problem reading the files. - */ - public abstract boolean isSameFile(File source, File destination) - throws IOException; - - /** Invokes {@link File#exists()} on the given {@code file}. */ - public abstract boolean exists(File file); - - /** Invokes {@link File#isFile()} on the given {@code file}. */ - public abstract boolean isFile(File file); - - /** Invokes {@link File#isDirectory()} on the given {@code file}. */ - public abstract boolean isDirectory(File file); - - /** Invokes {@link File#length()} on the given {@code file}. */ - public abstract long length(File file); - - /** - * Invokes {@link File#delete()} on the given {@code file}. - * Note: for a recursive folder version, consider {@link #deleteFileOrFolder(File)}. - */ - public abstract boolean delete(File file); - - /** Invokes {@link File#mkdirs()} on the given {@code file}. */ - public abstract boolean mkdirs(File file); - - /** Invokes {@link File#listFiles()} on the given {@code file}. */ - public abstract File[] listFiles(File file); - - /** Invokes {@link File#renameTo(File)} on the given files. */ - public abstract boolean renameTo(File oldDir, File newDir); - - /** Creates a new {@link FileOutputStream} for the given {@code file}. */ - public abstract OutputStream newFileOutputStream(File file) throws FileNotFoundException; - - /** - * Load {@link Properties} from a file. Returns an empty property set on error. - * - * @param file A non-null file to load from. File may not exist. - * @return A new {@link Properties} with the properties loaded from the file, - * or an empty property set in case of error. - */ - public @NonNull Properties loadProperties(@NonNull File file); - - /** - * Saves (write, store) the given {@link Properties} into the given {@link File}. - * - * @param file A non-null file to write to. - * @param props The properties to write. - * @param comments A non-null description of the properly list, written in the file. - * @return True if the properties could be saved, false otherwise. - */ - public boolean saveProperties( - @NonNull File file, - @NonNull Properties props, - @NonNull String comments); -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/io/NonClosingInputStream.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/io/NonClosingInputStream.java deleted file mode 100755 index 470b706..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/io/NonClosingInputStream.java +++ /dev/null @@ -1,104 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.io; - -import com.android.annotations.NonNull; - -import java.io.FilterInputStream; -import java.io.IOException; -import java.io.InputStream; - - -/** - * Wraps an {@link InputStream} to change its closing behavior: - * this makes it possible to ignore close operations or have them perform a - * {@link InputStream#reset()} instead (if supported by the underlying stream) - * or plain ignored. - */ -public class NonClosingInputStream extends FilterInputStream { - - private final InputStream mInputStream; - private CloseBehavior mCloseBehavior = CloseBehavior.CLOSE; - - public enum CloseBehavior { - /** - * The behavior of {@link NonClosingInputStream#close()} is to close the - * underlying input stream. This is the default. - */ - CLOSE, - /** - * The behavior of {@link NonClosingInputStream#close()} is to ignore the - * close request and do nothing. - */ - IGNORE, - /** - * The behavior of {@link NonClosingInputStream#close()} is to call - * {@link InputStream#reset()} on the underlying stream. This will - * only succeed if the underlying stream supports it, e.g. it must - * have {@link InputStream#markSupported()} return true <em>and</em> - * the caller should have called {@link InputStream#mark(int)} at some - * point before. - */ - RESET - } - - /** - * Wraps an existing stream into this filtering stream. - * @param in A non-null input stream. - */ - public NonClosingInputStream(@NonNull InputStream in) { - super(in); - mInputStream = in; - } - - /** - * Returns the current {@link CloseBehavior}. - * @return the current {@link CloseBehavior}. Never null. - */ - public @NonNull CloseBehavior getCloseBehavior() { - return mCloseBehavior; - } - - /** - * Changes the current {@link CloseBehavior}. - * - * @param closeBehavior A new non-null {@link CloseBehavior}. - * @return Self for chaining. - */ - public NonClosingInputStream setCloseBehavior(@NonNull CloseBehavior closeBehavior) { - mCloseBehavior = closeBehavior; - return this; - } - - /** - * Performs the requested {@code close()} operation, depending on the current - * {@link CloseBehavior}. - */ - @Override - public void close() throws IOException { - switch (mCloseBehavior) { - case IGNORE: - break; - case RESET: - mInputStream.reset(); - break; - case CLOSE: - mInputStream.close(); - break; - } - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/PkgProps.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/PkgProps.java deleted file mode 100755 index 68d7119..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/PkgProps.java +++ /dev/null @@ -1,99 +0,0 @@ -/* - * Copyright (C) 2011 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.sdklib.repository; - - - -/** - * Public constants used by the repository when saving {@code source.properties} - * files in local packages. - * <p/> - * These constants are public and part of the SDK Manager public API. - * Once published we can't change them arbitrarily since various parts - * of our build process depend on them. - */ -public class PkgProps { - - // Base Package - public static final String PKG_REVISION = "Pkg.Revision"; //$NON-NLS-1$ - public static final String PKG_LICENSE = "Pkg.License"; //$NON-NLS-1$ - public static final String PKG_DESC = "Pkg.Desc"; //$NON-NLS-1$ - public static final String PKG_DESC_URL = "Pkg.DescUrl"; //$NON-NLS-1$ - public static final String PKG_RELEASE_NOTE = "Pkg.RelNote"; //$NON-NLS-1$ - public static final String PKG_RELEASE_URL = "Pkg.RelNoteUrl"; //$NON-NLS-1$ - public static final String PKG_SOURCE_URL = "Pkg.SourceUrl"; //$NON-NLS-1$ - public static final String PKG_OBSOLETE = "Pkg.Obsolete"; //$NON-NLS-1$ - - // AndroidVersion - - public static final String VERSION_API_LEVEL = "AndroidVersion.ApiLevel";//$NON-NLS-1$ - /** Code name of the platform if the platform is not final */ - public static final String VERSION_CODENAME = "AndroidVersion.CodeName";//$NON-NLS-1$ - - - // AddonPackage - - public static final String ADDON_NAME = "Addon.Name"; //$NON-NLS-1$ - public static final String ADDON_NAME_ID = "Addon.NameId"; //$NON-NLS-1$ - public static final String ADDON_NAME_DISPLAY = "Addon.NameDisplay"; //$NON-NLS-1$ - - public static final String ADDON_VENDOR = "Addon.Vendor"; //$NON-NLS-1$ - public static final String ADDON_VENDOR_ID = "Addon.VendorId"; //$NON-NLS-1$ - public static final String ADDON_VENDOR_DISPLAY = "Addon.VendorDisplay"; //$NON-NLS-1$ - - // DocPackage - - // ExtraPackage - - public static final String EXTRA_PATH = "Extra.Path"; //$NON-NLS-1$ - public static final String EXTRA_OLD_PATHS = "Extra.OldPaths"; //$NON-NLS-1$ - public static final String EXTRA_MIN_API_LEVEL = "Extra.MinApiLevel"; //$NON-NLS-1$ - public static final String EXTRA_PROJECT_FILES = "Extra.ProjectFiles"; //$NON-NLS-1$ - public static final String EXTRA_VENDOR = "Extra.Vendor"; //$NON-NLS-1$ - public static final String EXTRA_VENDOR_ID = "Extra.VendorId"; //$NON-NLS-1$ - public static final String EXTRA_VENDOR_DISPLAY = "Extra.VendorDisplay"; //$NON-NLS-1$ - public static final String EXTRA_NAME_DISPLAY = "Extra.NameDisplay"; //$NON-NLS-1$ - - // ILayoutlibVersion - - public static final String LAYOUTLIB_API = "Layoutlib.Api"; //$NON-NLS-1$ - public static final String LAYOUTLIB_REV = "Layoutlib.Revision"; //$NON-NLS-1$ - - // MinToolsPackage - - public static final String MIN_TOOLS_REV = "Platform.MinToolsRev"; //$NON-NLS-1$ - - // PlatformPackage - - public static final String PLATFORM_VERSION = "Platform.Version"; //$NON-NLS-1$ - /** Code name of the platform. This has no bearing on the package being a preview or not. */ - public static final String PLATFORM_CODENAME = "Platform.CodeName"; //$NON-NLS-1$ - public static final String PLATFORM_INCLUDED_ABI = "Platform.Included.Abi"; //$NON-NLS-1$ - - // ToolPackage - - public static final String MIN_PLATFORM_TOOLS_REV = "Platform.MinPlatformToolsRev";//$NON-NLS-1$ - - - // SamplePackage - - public static final String SAMPLE_MIN_API_LEVEL = "Sample.MinApiLevel"; //$NON-NLS-1$ - - // SystemImagePackage - - public static final String SYS_IMG_ABI = "SystemImage.Abi"; //$NON-NLS-1$ -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/README.txt b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/README.txt deleted file mode 100755 index e6e0f63..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/README.txt +++ /dev/null @@ -1,25 +0,0 @@ -This directory contains the XML Schemas (XSD) used by the Android SDK Repository. - -The repository exports all the packages that compose the SDK as well as -various manifest that define what is available in the repository. -The XML schemas available here allows clients to validate the manifests. - -TODO: -- overview of schemas -- principles of design -- principles of evolution vs revision numbers -- naming convention -- using by "make sdk_repo" - - -Naming Convention ------------------ - -Repository schemas are named sdk-type-N.xsd where -- type is either addon, addons-list or repository. -- N is the schema revision number, starting at 1 and increment with each revision. - -Schemas can also be named -sdk-type-N.xsd. -The dash prefix means this schema is a *future* schema that is not yet -used in production. This allows the repository to test future schemas -before they are deployed. diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/RepoConstants.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/RepoConstants.java deleted file mode 100755 index 3fdfc91..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/RepoConstants.java +++ /dev/null @@ -1,176 +0,0 @@ -/* - * Copyright (C) 2010 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.sdklib.repository; - -import java.io.InputStream; - - - -/** - * Public constants common to the sdk-repository and sdk-addon XML Schemas. - */ -public class RepoConstants { - - /** The license definition. */ - public static final String NODE_LICENSE = "license"; //$NON-NLS-1$ - /** The optional uses-license for all packages or for a lib. */ - public static final String NODE_USES_LICENSE = "uses-license"; //$NON-NLS-1$ - /** The revision, an int > 0, for all packages. */ - public static final String NODE_REVISION = "revision"; //$NON-NLS-1$ - /** The optional description for all packages or for a lib. */ - public static final String NODE_DESCRIPTION = "description"; //$NON-NLS-1$ - /** The optional description URL for all packages. */ - public static final String NODE_DESC_URL = "desc-url"; //$NON-NLS-1$ - /** The optional release note for all packages. */ - public static final String NODE_RELEASE_NOTE = "release-note"; //$NON-NLS-1$ - /** The optional release note URL for all packages. */ - public static final String NODE_RELEASE_URL = "release-url"; //$NON-NLS-1$ - /** The optional obsolete qualifier for all packages. */ - public static final String NODE_OBSOLETE = "obsolete"; //$NON-NLS-1$ - /** The optional project-files provided by extra packages. */ - public static final String NODE_PROJECT_FILES = "project-files"; //$NON-NLS-1$ - - /** A system-image package. */ - public static final String NODE_SYSTEM_IMAGE = "system-image"; //$NON-NLS-1$ - - /* An included-ABI element for a system-image package. */ - public static final String NODE_ABI_INCLUDED = "included-abi"; //$NON-NLS-1$ - /* An ABI element for a system-image package. */ - public static final String NODE_ABI = "abi"; //$NON-NLS-1$ - - /** The optional minimal tools revision required by platform & extra packages. */ - public static final String NODE_MIN_TOOLS_REV = "min-tools-rev"; //$NON-NLS-1$ - /** The optional minimal platform-tools revision required by tool packages. */ - public static final String NODE_MIN_PLATFORM_TOOLS_REV = "min-platform-tools-rev"; //$NON-NLS-1$ - /** The optional minimal API level required by extra packages. */ - public static final String NODE_MIN_API_LEVEL = "min-api-level"; //$NON-NLS-1$ - - /** The version, a string, for platform packages. */ - public static final String NODE_VERSION = "version"; //$NON-NLS-1$ - /** The api-level, an int > 0, for platform, add-on and doc packages. */ - public static final String NODE_API_LEVEL = "api-level"; //$NON-NLS-1$ - /** The codename, a string, for platform packages. */ - public static final String NODE_CODENAME = "codename"; //$NON-NLS-1$ - /** The *old* vendor, a string, for add-on and extra packages. - * Replaced by {@link #NODE_VENDOR_DISPLAY} and {@link #NODE_VENDOR_ID} in addon-v4.xsd. */ - public static final String NODE_VENDOR = "vendor"; //$NON-NLS-1$ - /** The vendor display string, for add-on and extra packages. */ - public static final String NODE_VENDOR_DISPLAY = "vendor-display"; //$NON-NLS-1$ - /** The unique vendor id string, for add-on and extra packages. */ - public static final String NODE_VENDOR_ID = "vendor-id"; //$NON-NLS-1$ - /** The name, a string, for add-on packages or for libraries. - * Replaced by {@link #NODE_NAME_DISPLAY} and {@link #NODE_NAME_ID} in addon-v4.xsd. */ - public static final String NODE_NAME = "name"; //$NON-NLS-1$ - /** The name display string, for add-on packages or for libraries. */ - public static final String NODE_NAME_DISPLAY = "name-display"; //$NON-NLS-1$ - /** The unique name id string, for add-on packages or for libraries. */ - public static final String NODE_NAME_ID = "name-id"; //$NON-NLS-1$ - - - /** A layoutlib package. */ - public static final String NODE_LAYOUT_LIB = "layoutlib"; //$NON-NLS-1$ - /** The API integer for a layoutlib element. */ - public static final String NODE_API = "api"; //$NON-NLS-1$ - - /** The libs container, optional for an add-on. */ - public static final String NODE_LIBS = "libs"; //$NON-NLS-1$ - /** A lib element in a libs container. */ - public static final String NODE_LIB = "lib"; //$NON-NLS-1$ - - /** The path segment, a string, for extra packages. */ - public static final String NODE_PATH = "path"; //$NON-NLS-1$ - - /** The old_path segments, a string, for extra packages. */ - public static final String NODE_OLD_PATHS = "old-paths"; //$NON-NLS-1$ - - /** The archives container, for all packages. */ - public static final String NODE_ARCHIVES = "archives"; //$NON-NLS-1$ - /** An archive element, for the archives container. */ - public static final String NODE_ARCHIVE = "archive"; //$NON-NLS-1$ - - /** An archive size, an int > 0. */ - public static final String NODE_SIZE = "size"; //$NON-NLS-1$ - /** A sha1 archive checksum, as a 40-char hex. */ - public static final String NODE_CHECKSUM = "checksum"; //$NON-NLS-1$ - /** A download archive URL, either absolute or relative to the repository xml. */ - public static final String NODE_URL = "url"; //$NON-NLS-1$ - - /** An archive checksum type, mandatory. */ - public static final String ATTR_TYPE = "type"; //$NON-NLS-1$ - /** An archive OS attribute, mandatory. */ - public static final String ATTR_OS = "os"; //$NON-NLS-1$ - /** An optional archive Architecture attribute. */ - public static final String ATTR_ARCH = "arch"; //$NON-NLS-1$ - - /** A license definition ID. */ - public static final String ATTR_ID = "id"; //$NON-NLS-1$ - /** A license reference. */ - public static final String ATTR_REF = "ref"; //$NON-NLS-1$ - - /** Type of a sha1 checksum. */ - public static final String SHA1_TYPE = "sha1"; //$NON-NLS-1$ - - /** Length of a string representing a SHA1 checksum; always 40 characters long. */ - public static final int SHA1_CHECKSUM_LEN = 40; - - /** - * Temporary folder used to hold downloads and extract archives during installation. - * This folder will be located in the SDK. - */ - public static final String FD_TEMP = "temp"; //$NON-NLS-1$ - - /** - * Returns a stream to the requested XML Schema. - * This is an internal helper. Users of the library should call - * {@link SdkRepoConstants#getXsdStream(String, int)} or - * {@link SdkAddonConstants#getXsdStream(String, int)}. - * - * @param rootElement The root of the filename of the XML schema. - * This is by convention the same as the root element declared by the schema. - * @param version The XML schema revision number, an integer >= 1. - * @return An {@link InputStream} object for the local XSD file or - * null if there is no schema for the requested version. - * @see SdkRepoConstants#getXsdStream(int) - * @see SdkAddonConstants#getXsdStream(int) - */ - protected static InputStream getXsdStream(String rootElement, int version) { - String filename = String.format("%1$s-%2$d.xsd", rootElement, version); //$NON-NLS-1$ - - InputStream stream = null; - try { - stream = RepoConstants.class.getResourceAsStream(filename); - } catch (Exception e) { - // Some implementations seem to return null on failure, - // others throw an exception. We want to return null. - } - if (stream == null) { - // Try the alternate schemas that are not published yet. - // This allows us to internally test with new schemas before the - // public repository uses it. - filename = String.format("-%1$s-%2$d.xsd", rootElement, version); //$NON-NLS-1$ - try { - stream = RepoConstants.class.getResourceAsStream(filename); - } catch (Exception e) { - // Some implementations seem to return null on failure, - // others throw an exception. We want to return null. - } - } - - return stream; - } - -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/SdkAddonConstants.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/SdkAddonConstants.java deleted file mode 100755 index 4af2276..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/SdkAddonConstants.java +++ /dev/null @@ -1,90 +0,0 @@ -/* - * Copyright (C) 2010 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.sdklib.repository; - - -import com.android.sdklib.internal.repository.sources.SdkSource; - -import java.io.InputStream; - -/** - * Public constants for the sdk-addon XML Schema. - */ -public class SdkAddonConstants extends RepoConstants { - - /** - * The default name looked for by {@link SdkSource} when trying to load an - * sdk-addon XML if the URL doesn't match an existing resource. - */ - public static final String URL_DEFAULT_FILENAME = "addon.xml"; //$NON-NLS-1$ - - /** The base of our sdk-addon XML namespace. */ - private static final String NS_BASE = - "http://schemas.android.com/sdk/android/addon/"; //$NON-NLS-1$ - - /** - * The pattern of our sdk-addon XML namespace. - * Matcher's group(1) is the schema version (integer). - */ - public static final String NS_PATTERN = NS_BASE + "([1-9][0-9]*)"; //$NON-NLS-1$ - - /** - * The latest version of the sdk-addon XML Schema. - * Valid version numbers are between 1 and this number, included. - */ - public static final int NS_LATEST_VERSION = 5; - - /** The XML namespace of the latest sdk-addon XML. */ - public static final String NS_URI = getSchemaUri(NS_LATEST_VERSION); - - /** The root sdk-addon element */ - public static final String NODE_SDK_ADDON = "sdk-addon"; //$NON-NLS-1$ - - /** An add-on package. */ - public static final String NODE_ADD_ON = "add-on"; //$NON-NLS-1$ - - /** An extra package. */ - public static final String NODE_EXTRA = "extra"; //$NON-NLS-1$ - - /** - * List of possible nodes in a repository XML. Used to populate options automatically - * in the no-GUI mode. - */ - public static final String[] NODES = { - NODE_ADD_ON, - NODE_EXTRA - }; - - /** - * Returns a stream to the requested {@code sdk-addon} XML Schema. - * - * @param version Between 1 and {@link #NS_LATEST_VERSION}, included. - * @return An {@link InputStream} object for the local XSD file or - * null if there is no schema for the requested version. - */ - public static InputStream getXsdStream(int version) { - return getXsdStream(NODE_SDK_ADDON, version); - } - - /** - * Returns the URI of the sdk-addon schema for the given version number. - * @param version Between 1 and {@link #NS_LATEST_VERSION} included. - */ - public static String getSchemaUri(int version) { - return String.format(NS_BASE + "%d", version); //$NON-NLS-1$ - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/SdkAddonsListConstants.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/SdkAddonsListConstants.java deleted file mode 100755 index 4f6b897..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/SdkAddonsListConstants.java +++ /dev/null @@ -1,108 +0,0 @@ -/* - * Copyright (C) 2010 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.sdklib.repository; - - -import java.io.InputStream; - -/** - * Public constants for the sdk-addons-list XML Schema. - */ -public class SdkAddonsListConstants { - - /** The base of our sdk-addons-list XML namespace. */ - private static final String NS_BASE = - "http://schemas.android.com/sdk/android/addons-list/"; //$NON-NLS-1$ - - /** - * The pattern of our sdk-addons-list XML namespace. - * Matcher's group(1) is the schema version (integer). - */ - public static final String NS_PATTERN = NS_BASE + "([1-9][0-9]*)"; //$NON-NLS-1$ - - /** The latest version of the sdk-addons-list XML Schema. - * Valid version numbers are between 1 and this number, included. */ - public static final int NS_LATEST_VERSION = 2; - - /** The XML namespace of the latest sdk-addons-list XML. */ - public static final String NS_URI = getSchemaUri(NS_LATEST_VERSION); - - - /** The canonical URL filename for addons-list XML files. */ - public static final String URL_DEFAULT_FILENAME = getDefaultName(NS_LATEST_VERSION); - - /** The URL where to find the official addons list fle. */ - public static final String URL_ADDON_LIST = - SdkRepoConstants.URL_GOOGLE_SDK_SITE + URL_DEFAULT_FILENAME; - - - - /** The root sdk-addons-list element */ - public static final String NODE_SDK_ADDONS_LIST = "sdk-addons-list"; //$NON-NLS-1$ - - /** An add-on site. */ - public static final String NODE_ADDON_SITE = "addon-site"; //$NON-NLS-1$ - - /** A system image site. */ - public static final String NODE_SYS_IMG_SITE = "sys-img-site"; //$NON-NLS-1$ - - /** The UI-visible name of the add-on site. */ - public static final String NODE_NAME = "name"; //$NON-NLS-1$ - - /** - * The URL of the site. - * <p/> - * This can be either the exact URL of the an XML resource conforming - * to the latest sdk-addon-N.xsd schema, or it can be the URL of a - * 'directory', in which case the manager will look for a resource - * named 'addon.xml' at this location. - * <p/> - * Examples: - * <pre> - * http://www.example.com/android/my_addons.xml - * or - * http://www.example.com/android/ - * </pre> - * In the second example, the manager will actually look for - * http://www.example.com/android/addon.xml - */ - public static final String NODE_URL = "url"; //$NON-NLS-1$ - - /** - * Returns a stream to the requested sdk-addon XML Schema. - * - * @param version Between 1 and {@link #NS_LATEST_VERSION}, included. - * @return An {@link InputStream} object for the local XSD file or - * null if there is no schema for the requested version. - */ - public static InputStream getXsdStream(int version) { - String filename = String.format("sdk-addons-list-%d.xsd", version); //$NON-NLS-1$ - return SdkAddonsListConstants.class.getResourceAsStream(filename); - } - - /** - * Returns the URI of the sdk-addon schema for the given version number. - * @param version Between 1 and {@link #NS_LATEST_VERSION} included. - */ - public static String getSchemaUri(int version) { - return String.format(NS_BASE + "%d", version); //$NON-NLS-1$ - } - - public static String getDefaultName(int version) { - return String.format("addons_list-%1$d.xml", version); //$NON-NLS-1$ - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/SdkRepoConstants.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/SdkRepoConstants.java deleted file mode 100755 index 48c9b25..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/SdkRepoConstants.java +++ /dev/null @@ -1,146 +0,0 @@ -/* - * Copyright (C) 2009 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.sdklib.repository; - - -import com.android.sdklib.internal.repository.sources.SdkSource; - -import java.io.InputStream; - -/** - * Public constants for the sdk-repository XML Schema. - */ -public class SdkRepoConstants extends RepoConstants { - - /** - * The latest version of the sdk-repository XML Schema. - * Valid version numbers are between 1 and this number, included. - */ - public static final int NS_LATEST_VERSION = 7; - - /** - * The min version of the sdk-repository XML Schema we'll try to load. - * When looking for a repository-N.xml on the server, we'll check from - * {@link #NS_LATEST_VERSION} down to this revision. - * We only introduced the "repository-N.xml" pattern start with revision - * 5, so we know that <em>our</em> server will never contain a repository - * XML with a schema version lower than this one. - */ - public static final int NS_SERVER_MIN_VERSION = 5; - - /** - * The URL of the official Google sdk-repository site. - * The URL ends with a /, allowing easy concatenation. - * */ - public static final String URL_GOOGLE_SDK_SITE = - "https://dl-ssl.google.com/android/repository/"; //$NON-NLS-1$ - - /** - * The default name looked for by {@link SdkSource} when trying to load an - * sdk-repository XML if the URL doesn't match an existing resource. - */ - public static final String URL_DEFAULT_FILENAME = "repository.xml"; //$NON-NLS-1$ - - /** - * The pattern name looked by {@link SdkSource} when trying to load - * an sdk-repository XML that is specific to a given XSD revision. - * <p/> - * This must be used with {@link String#format(String, Object...)} with - * one integer parameter between 1 and {@link #NS_LATEST_VERSION}. - */ - public static final String URL_FILENAME_PATTERN = "repository-%1$d.xml"; //$NON-NLS-1$ - - /** The base of our sdk-repository XML namespace. */ - private static final String NS_BASE = - "http://schemas.android.com/sdk/android/repository/"; //$NON-NLS-1$ - - /** - * The pattern of our sdk-repository XML namespace. - * Matcher's group(1) is the schema version (integer). - */ - public static final String NS_PATTERN = NS_BASE + "([1-9][0-9]*)"; //$NON-NLS-1$ - - /** The XML namespace of the latest sdk-repository XML. */ - public static final String NS_URI = getSchemaUri(NS_LATEST_VERSION); - - /** The root sdk-repository element */ - public static final String NODE_SDK_REPOSITORY = "sdk-repository"; //$NON-NLS-1$ - - /* The major revision for tool and platform-tool package - * (the full revision number is revision.minor.micro + preview#.) - * Mandatory int > 0. 0 when missing, which should not happen in - * a valid document. */ - public static final String NODE_MAJOR_REV = "major"; //$NON-NLS-1$ - /* The minor revision for tool and platform-tool package - * (the full revision number is revision.minor.micro + preview#.) - * Optional int >= 0. Implied to be 0 when missing. */ - public static final String NODE_MINOR_REV = "minor"; //$NON-NLS-1$ - /* The micro revision for tool and platform-tool package - * (the full revision number is revision.minor.micro + preview#.) - * Optional int >= 0. Implied to be 0 when missing. */ - public static final String NODE_MICRO_REV = "micro"; //$NON-NLS-1$ - /* The preview revision for tool and platform-tool package. - * Int > 0, only present for "preview / release candidate" packages. */ - public static final String NODE_PREVIEW = "preview"; //$NON-NLS-1$ - - /** A platform package. */ - public static final String NODE_PLATFORM = "platform"; //$NON-NLS-1$ - /** A tool package. */ - public static final String NODE_TOOL = "tool"; //$NON-NLS-1$ - /** A platform-tool package. */ - public static final String NODE_PLATFORM_TOOL = "platform-tool"; //$NON-NLS-1$ - /** A doc package. */ - public static final String NODE_DOC = "doc"; //$NON-NLS-1$ - /** A sample package. */ - public static final String NODE_SAMPLE = "sample"; //$NON-NLS-1$ - /** A source package. */ - public static final String NODE_SOURCE = "source"; //$NON-NLS-1$ - - - /** - * List of possible nodes in a repository XML. Used to populate options automatically - * in the no-GUI mode. - */ - public static final String[] NODES = { - NODE_PLATFORM, - NODE_SYSTEM_IMAGE, - NODE_TOOL, - NODE_PLATFORM_TOOL, - NODE_DOC, - NODE_SAMPLE, - NODE_SOURCE, - }; - - /** - * Returns a stream to the requested {@code sdk-repository} XML Schema. - * - * @param version Between 1 and {@link #NS_LATEST_VERSION}, included. - * @return An {@link InputStream} object for the local XSD file or - * null if there is no schema for the requested version. - */ - public static InputStream getXsdStream(int version) { - return getXsdStream(NODE_SDK_REPOSITORY, version); - } - - /** - * Returns the URI of the SDK Repository schema for the given version number. - * @param version Between 1 and {@link #NS_LATEST_VERSION} included. - */ - public static String getSchemaUri(int version) { - return String.format(NS_BASE + "%d", version); //$NON-NLS-1$ - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/SdkStatsConstants.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/SdkStatsConstants.java deleted file mode 100755 index 22f8aa2..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/SdkStatsConstants.java +++ /dev/null @@ -1,91 +0,0 @@ -/* - * Copyright (C) 2012 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.sdklib.repository; - - -import java.io.InputStream; - -/** - * Public constants for the sdk-stats XML Schema. - */ -public class SdkStatsConstants { - - /** The canonical URL filename for addons-list XML files. */ - public static final String URL_DEFAULT_FILENAME = "stats-1.xml"; //$NON-NLS-1$ - - /** The URL where to find the official addons list fle. */ - public static final String URL_STATS = - SdkRepoConstants.URL_GOOGLE_SDK_SITE + URL_DEFAULT_FILENAME; - - /** The base of our sdk-addons-list XML namespace. */ - private static final String NS_BASE = - "http://schemas.android.com/sdk/android/stats/"; //$NON-NLS-1$ - - /** - * The pattern of our sdk-stats XML namespace. - * Matcher's group(1) is the schema version (integer). - */ - public static final String NS_PATTERN = NS_BASE + "([1-9][0-9]*)"; //$NON-NLS-1$ - - /** The latest version of the sdk-stats XML Schema. - * Valid version numbers are between 1 and this number, included. */ - public static final int NS_LATEST_VERSION = 1; - - /** The XML namespace of the latest sdk-stats XML. */ - public static final String NS_URI = getSchemaUri(NS_LATEST_VERSION); - - /** The root sdk-stats element */ - public static final String NODE_SDK_STATS = "sdk-stats"; //$NON-NLS-1$ - - /** A platform stat. */ - public static final String NODE_PLATFORM = "platform"; //$NON-NLS-1$ - - /** The Android API Level for the platform. An int > 0. */ - public static final String NODE_API_LEVEL = "api-level"; //$NON-NLS-1$ - - /** The official codename for this platform, for example "Cupcake". */ - public static final String NODE_CODENAME = "codename"; //$NON-NLS-1$ - - /** The official version name of this platform, for example "Android 1.5". */ - public static final String NODE_VERSION = "version"; //$NON-NLS-1$ - - /** - * The <em>approximate</em> share percentage of that platform. - * See the caveat in sdk-stats-1.xsd about value freshness and accuracy. - */ - public static final String NODE_SHARE = "share"; //$NON-NLS-1$ - - /** - * Returns a stream to the requested sdk-stats XML Schema. - * - * @param version Between 1 and {@link #NS_LATEST_VERSION}, included. - * @return An {@link InputStream} object for the local XSD file or - * null if there is no schema for the requested version. - */ - public static InputStream getXsdStream(int version) { - String filename = String.format("sdk-stats-%d.xsd", version); //$NON-NLS-1$ - return SdkStatsConstants.class.getResourceAsStream(filename); - } - - /** - * Returns the URI of the sdk-stats schema for the given version number. - * @param version Between 1 and {@link #NS_LATEST_VERSION} included. - */ - public static String getSchemaUri(int version) { - return String.format(NS_BASE + "%d", version); //$NON-NLS-1$ - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/SdkSysImgConstants.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/SdkSysImgConstants.java deleted file mode 100755 index ba3017f..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/SdkSysImgConstants.java +++ /dev/null @@ -1,83 +0,0 @@ -/* - * Copyright (C) 2012 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.sdklib.repository; - - -import com.android.sdklib.internal.repository.sources.SdkSource; - -import java.io.InputStream; - -/** - * Public constants for the sdk-sys-img XML Schema. - */ -public class SdkSysImgConstants extends RepoConstants { - - /** - * The default name looked for by {@link SdkSource} when trying to load an - * sdk-sys-img XML if the URL doesn't match an existing resource. - */ - public static final String URL_DEFAULT_FILENAME = "sys-img.xml"; //$NON-NLS-1$ - - /** The base of our sdk-sys-img XML namespace. */ - private static final String NS_BASE = - "http://schemas.android.com/sdk/android/sys-img/"; //$NON-NLS-1$ - - /** - * The pattern of our sdk-sys-img XML namespace. - * Matcher's group(1) is the schema version (integer). - */ - public static final String NS_PATTERN = NS_BASE + "([1-9][0-9]*)"; //$NON-NLS-1$ - - /** - * The latest version of the sdk-sys-img XML Schema. - * Valid version numbers are between 1 and this number, included. - */ - public static final int NS_LATEST_VERSION = 1; - - /** The XML namespace of the latest sdk-sys-img XML. */ - public static final String NS_URI = getSchemaUri(NS_LATEST_VERSION); - - /** The root sdk-sys-img element */ - public static final String NODE_SDK_SYS_IMG = "sdk-sys-img"; //$NON-NLS-1$ - - /** - * List of possible nodes in a repository XML. Used to populate options automatically - * in the no-GUI mode. - */ - public static final String[] NODES = { - NODE_SYSTEM_IMAGE, - }; - - /** - * Returns a stream to the requested {@code sdk-sys-img} XML Schema. - * - * @param version Between 1 and {@link #NS_LATEST_VERSION}, included. - * @return An {@link InputStream} object for the local XSD file or - * null if there is no schema for the requested version. - */ - public static InputStream getXsdStream(int version) { - return getXsdStream(NODE_SDK_SYS_IMG, version); - } - - /** - * Returns the URI of the sdk-sys-img schema for the given version number. - * @param version Between 1 and {@link #NS_LATEST_VERSION} included. - */ - public static String getSchemaUri(int version) { - return String.format(NS_BASE + "%d", version); //$NON-NLS-1$ - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-addon-1.xsd b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-addon-1.xsd deleted file mode 100755 index 1d53313..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-addon-1.xsd +++ /dev/null @@ -1,295 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- - * Copyright (C) 2010 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<xsd:schema - targetNamespace="http://schemas.android.com/sdk/android/addon/1" - xmlns:xsd="http://www.w3.org/2001/XMLSchema" - xmlns:sdk="http://schemas.android.com/sdk/android/addon/1" - elementFormDefault="qualified" - attributeFormDefault="unqualified" - version="1"> - - <!-- The repository contains a collection of downloadable items known as - "packages". Each package has a type and various attributes and contains - a list of file "archives" that can be downloaded for specific OSes. - - An Android Addon repository is a web site that contains an "addon.xml" - file that conforms to this XML Schema. - - History: - - v1 is used by the SDK Updater in Tools r8. It is split out of the - main SDK Repository XML Schema and can only contain <addon> and - <extra> packages. - --> - - <xsd:element name="sdk-addon" type="sdk:repositoryType" /> - - <xsd:complexType name="repositoryType"> - <xsd:annotation> - <xsd:documentation> - The repository contains a collection of downloadable packages. - </xsd:documentation> - </xsd:annotation> - <xsd:choice minOccurs="0" maxOccurs="unbounded"> - <xsd:element name="add-on" type="sdk:addonType" /> - <xsd:element name="extra" type="sdk:extraType" /> - <xsd:element name="license" type="sdk:licenseType" /> - </xsd:choice> - </xsd:complexType> - - <!-- The definition of an SDK Add-on package. --> - - <xsd:complexType name="addonType"> - <xsd:annotation> - <xsd:documentation>An SDK add-on package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The name of the add-on. --> - <xsd:element name="name" type="xsd:normalizedString" /> - <!-- The vendor of the add-on. --> - <xsd:element name="vendor" type="xsd:normalizedString" /> - <!-- The Android API Level for the add-on. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- Note: Add-ons do not support 'codename' (a.k.a. API previews). --> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - - <!-- An add-on can declare 0 or more libraries. --> - - <xsd:element name="libs"> - <xsd:complexType> - <xsd:sequence minOccurs="0" maxOccurs="unbounded"> - <xsd:element name="lib"> - <xsd:complexType> - <xsd:all> - <!-- The name of the library. --> - <xsd:element name="name" type="xsd:normalizedString" /> - <!-- The optional description of this add-on library. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - </xsd:element> - </xsd:sequence> - </xsd:complexType> - </xsd:element> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK extra package. This kind of package is for - "free" content. Such packages are installed in SDK/vendor/path. - --> - - <xsd:complexType name="extraType" > - <xsd:annotation> - <xsd:documentation> - An SDK extra package. This kind of package is for "free" content. - Such packages are installed in SDK/vendor/path. - </xsd:documentation> - </xsd:annotation> - <xsd:all> - - <!-- The install path top folder name. It must not be empty. - The segments "add-ons", "docs", "platforms", "platform-tools", "temp" - and "tools" are reserved and cannot be used. - --> - <xsd:element name="vendor" type="sdk:segmentType" /> - - <!-- The install path sub-folder name. It must not be empty. --> - <xsd:element name="path" type="sdk:segmentType" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - <!-- The minimal revision of tools required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-tools-rev" type="xsd:positiveInteger" minOccurs="0" /> - <!-- The minimal API level required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-api-level" type="xsd:positiveInteger" minOccurs="0" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of a path segment used by the extra element. --> - - <xsd:simpleType name="segmentType"> - <xsd:annotation> - <xsd:documentation> - One path segment for the install path of an extra element. - It must be a single-segment path. It must not be empty. - </xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:token"> - <xsd:pattern value="[a-zA-Z0-9_]+"/> - </xsd:restriction> - </xsd:simpleType> - - - <!-- The definition of a license to be referenced by the uses-license element. --> - - <xsd:complexType name="licenseType"> - <xsd:annotation> - <xsd:documentation> - A license definition. Such a license must be used later as a reference - using a uses-license element in one of the package elements. - </xsd:documentation> - </xsd:annotation> - <xsd:simpleContent> - <xsd:extension base="xsd:string"> - <xsd:attribute name="id" type="xsd:ID" /> - <xsd:attribute name="type" type="xsd:token" fixed="text" /> - </xsd:extension> - </xsd:simpleContent> - </xsd:complexType> - - - <!-- Type describing the license used by a package. - The license MUST be defined using a license node and referenced - using the ref attribute of the license element inside a package. - --> - - <xsd:complexType name="usesLicenseType"> - <xsd:annotation> - <xsd:documentation> - Describes the license used by a package. The license MUST be defined - using a license node and referenced using the ref attribute of the - license element inside a package. - </xsd:documentation> - </xsd:annotation> - <xsd:attribute name="ref" type="xsd:IDREF" /> - </xsd:complexType> - - - <!-- A collection of files that can be downloaded for a given architecture. - The <archives> node is mandatory in the repository elements and the - collection must have at least one <archive> declared. - Each archive is a zip file that will be unzipped in a location that depends - on its package type. - --> - - <xsd:complexType name="archivesType"> - <xsd:annotation> - <xsd:documentation> - A collection of files that can be downloaded for a given architecture. - The <archives> node is mandatory in the repository packages and the - collection must have at least one <archive> declared. - Each archive is a zip file that will be unzipped in a location that depends - on its package type. - </xsd:documentation> - </xsd:annotation> - <xsd:sequence minOccurs="1" maxOccurs="unbounded"> - <!-- One archive file --> - <xsd:element name="archive"> - <xsd:complexType> - <!-- Properties of the archive file --> - <xsd:all> - <!-- The size in bytes of the archive to download. --> - <xsd:element name="size" type="xsd:positiveInteger" /> - <!-- The checksum of the archive file. --> - <xsd:element name="checksum" type="sdk:checksumType" /> - <!-- The URL is an absolute URL if it starts with http://, https:// - or ftp://. Otherwise it is relative to the parent directory that - contains this repository.xml --> - <xsd:element name="url" type="xsd:token" /> - </xsd:all> - - <!-- Attributes that identify the OS and architecture --> - <xsd:attribute name="os" use="required"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="any" /> - <xsd:enumeration value="linux" /> - <xsd:enumeration value="macosx" /> - <xsd:enumeration value="windows" /> - </xsd:restriction> - </xsd:simpleType> - </xsd:attribute> - <xsd:attribute name="arch" use="optional"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="any" /> - <xsd:enumeration value="ppc" /> - <xsd:enumeration value="x86" /> - <xsd:enumeration value="x86_64" /> - </xsd:restriction> - </xsd:simpleType> - </xsd:attribute> - </xsd:complexType> - </xsd:element> - </xsd:sequence> - </xsd:complexType> - - - <!-- The definition of a file checksum --> - - <xsd:simpleType name="sha1Number"> - <xsd:annotation> - <xsd:documentation>A SHA1 checksum.</xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:string"> - <xsd:pattern value="([0-9a-fA-F]){40}"/> - </xsd:restriction> - </xsd:simpleType> - - <xsd:complexType name="checksumType"> - <xsd:annotation> - <xsd:documentation>A file checksum, currently only SHA1.</xsd:documentation> - </xsd:annotation> - <xsd:simpleContent> - <xsd:extension base="sdk:sha1Number"> - <xsd:attribute name="type" type="xsd:token" fixed="sha1" /> - </xsd:extension> - </xsd:simpleContent> - </xsd:complexType> - -</xsd:schema> diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-addon-2.xsd b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-addon-2.xsd deleted file mode 100755 index 27fae8b..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-addon-2.xsd +++ /dev/null @@ -1,361 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<xsd:schema - targetNamespace="http://schemas.android.com/sdk/android/addon/2" - xmlns:xsd="http://www.w3.org/2001/XMLSchema" - xmlns:sdk="http://schemas.android.com/sdk/android/addon/2" - elementFormDefault="qualified" - attributeFormDefault="unqualified" - version="1"> - - <!-- The repository contains a collection of downloadable items known as - "packages". Each package has a type and various attributes and contains - a list of file "archives" that can be downloaded for specific OSes. - - An Android Addon repository is a web site that contains an "addon.xml" - file that conforms to this XML Schema. - - History: - - v1 is used by the SDK Updater in Tools r8. It is split out of the - main SDK Repository XML Schema and can only contain <addon> and - <extra> packages. - - - v2 is used by the SDK Updater in Tools r12. - - <extra> element now has a <project-files> element that contains 1 or - or more <path>, each indicating the relative path of a file that this package - can contribute to installed projects. - - <addon> element now has an optional <layoutlib> that indicates the API - and revision of the layout library for this particular add-on, if any. - --> - - <xsd:element name="sdk-addon" type="sdk:repositoryType" /> - - <xsd:complexType name="repositoryType"> - <xsd:annotation> - <xsd:documentation> - The repository contains a collection of downloadable packages. - </xsd:documentation> - </xsd:annotation> - <xsd:choice minOccurs="0" maxOccurs="unbounded"> - <xsd:element name="add-on" type="sdk:addonType" /> - <xsd:element name="extra" type="sdk:extraType" /> - <xsd:element name="license" type="sdk:licenseType" /> - </xsd:choice> - </xsd:complexType> - - <!-- The definition of an SDK Add-on package. --> - - <xsd:complexType name="addonType"> - <xsd:annotation> - <xsd:documentation>An SDK add-on package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The name of the add-on. --> - <xsd:element name="name" type="xsd:normalizedString" /> - <!-- The vendor of the add-on. --> - <xsd:element name="vendor" type="xsd:normalizedString" /> - <!-- The Android API Level for the add-on. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- Note: Add-ons do not support 'codenames' (a.k.a. API previews). --> - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - - <!-- An add-on can declare 0 or more libraries. - This element is mandatory but it can be empty. - --> - - <xsd:element name="libs"> - <xsd:complexType> - <xsd:sequence minOccurs="0" maxOccurs="unbounded"> - <xsd:element name="lib"> - <xsd:complexType> - <xsd:all> - <!-- The name of the library. --> - <xsd:element name="name" type="xsd:normalizedString" /> - <!-- The optional description of this add-on library. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - </xsd:element> - </xsd:sequence> - </xsd:complexType> - </xsd:element> - - <!-- optional elements --> - - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - - <!-- Optional information on the layoutlib packaged in this platform. --> - <xsd:element name="layoutlib" type="sdk:layoutlibType" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of a layout library used by an addon. --> - - <xsd:complexType name="layoutlibType" > - <xsd:annotation> - <xsd:documentation> - Version information for a layoutlib included in an addon. - .</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The layoutlib API level, an int > 0, - incremented with each new incompatible lib. --> - <xsd:element name="api" type="xsd:positiveInteger" /> - <!-- The incremental minor revision for that API, e.g. in case of bug fixes. - Optional. An int >= 0, assumed to be 0 if the element is missing. --> - <xsd:element name="revision" type="xsd:nonNegativeInteger" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK extra package. This kind of package is for - "free" content. Such packages are installed in SDK/vendor/path. - - Important implementation detail: this element is duplicated in the - sdk-repository-N.xsd schema and must be kept in sync there. This is - simpler than trying to use some kind of of include or to request - that clients use a third XML schema for common parts. - --> - - <xsd:complexType name="extraType" > - <xsd:annotation> - <xsd:documentation> - An SDK extra package. This kind of package is for "free" content. - Such packages are installed in SDK/vendor/path. - </xsd:documentation> - </xsd:annotation> - <xsd:all> - - <!-- The install path top folder name. It must not be empty. - The segments "add-ons", "docs", "platforms", "platform-tools", "temp" - and "tools" are reserved and cannot be used. - --> - <xsd:element name="vendor" type="sdk:segmentType" /> - - <!-- The install path sub-folder name. It must not be empty. --> - <xsd:element name="path" type="sdk:segmentType" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - <!-- optional elements --> - - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- The minimal revision of tools required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-tools-rev" type="xsd:positiveInteger" minOccurs="0" /> - <!-- The minimal API level required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-api-level" type="xsd:positiveInteger" minOccurs="0" /> - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - - <!-- A list of project files contributed by this package. Optional. --> - <xsd:element name="project-files" type="sdk:projectFilesType" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of a path segment used by the extra element. --> - - <xsd:simpleType name="segmentType"> - <xsd:annotation> - <xsd:documentation> - One path segment for the install path of an extra element. - It must be a single-segment path. It must not be empty. - </xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:token"> - <xsd:pattern value="[a-zA-Z0-9_]+"/> - </xsd:restriction> - </xsd:simpleType> - - - <!-- The definition of a license to be referenced by the uses-license element. --> - - <xsd:complexType name="licenseType"> - <xsd:annotation> - <xsd:documentation> - A license definition. Such a license must be used later as a reference - using a uses-license element in one of the package elements. - </xsd:documentation> - </xsd:annotation> - <xsd:simpleContent> - <xsd:extension base="xsd:string"> - <xsd:attribute name="id" type="xsd:ID" /> - <xsd:attribute name="type" type="xsd:token" fixed="text" /> - </xsd:extension> - </xsd:simpleContent> - </xsd:complexType> - - - <!-- Type describing the license used by a package. - The license MUST be defined using a license node and referenced - using the ref attribute of the license element inside a package. - --> - - <xsd:complexType name="usesLicenseType"> - <xsd:annotation> - <xsd:documentation> - Describes the license used by a package. The license MUST be defined - using a license node and referenced using the ref attribute of the - license element inside a package. - </xsd:documentation> - </xsd:annotation> - <xsd:attribute name="ref" type="xsd:IDREF" /> - </xsd:complexType> - - - <!-- A collection of files that can be downloaded for a given architecture. - The <archives> node is mandatory in the repository elements and the - collection must have at least one <archive> declared. - Each archive is a zip file that will be unzipped in a location that depends - on its package type. - --> - - <xsd:complexType name="archivesType"> - <xsd:annotation> - <xsd:documentation> - A collection of files that can be downloaded for a given architecture. - The <archives> node is mandatory in the repository packages and the - collection must have at least one <archive> declared. - Each archive is a zip file that will be unzipped in a location that depends - on its package type. - </xsd:documentation> - </xsd:annotation> - <xsd:sequence minOccurs="1" maxOccurs="unbounded"> - <!-- One archive file --> - <xsd:element name="archive"> - <xsd:complexType> - <!-- Properties of the archive file --> - <xsd:all> - <!-- The size in bytes of the archive to download. --> - <xsd:element name="size" type="xsd:positiveInteger" /> - <!-- The checksum of the archive file. --> - <xsd:element name="checksum" type="sdk:checksumType" /> - <!-- The URL is an absolute URL if it starts with http://, https:// - or ftp://. Otherwise it is relative to the parent directory that - contains this repository.xml --> - <xsd:element name="url" type="xsd:token" /> - </xsd:all> - - <!-- Attributes that identify the OS and architecture --> - <xsd:attribute name="os" use="required"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="any" /> - <xsd:enumeration value="linux" /> - <xsd:enumeration value="macosx" /> - <xsd:enumeration value="windows" /> - </xsd:restriction> - </xsd:simpleType> - </xsd:attribute> - <xsd:attribute name="arch" use="optional"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="any" /> - <xsd:enumeration value="ppc" /> - <xsd:enumeration value="x86" /> - <xsd:enumeration value="x86_64" /> - </xsd:restriction> - </xsd:simpleType> - </xsd:attribute> - </xsd:complexType> - </xsd:element> - </xsd:sequence> - </xsd:complexType> - - - <!-- A collection of file paths available in an <extra> package - that can be installed in an Android project. - If present, the <project-files> collection must contain at least one path. - Each path is relative to the root directory of the package. - --> - - <xsd:complexType name="projectFilesType"> - <xsd:annotation> - <xsd:documentation> - A collection of file paths available in an <extra> package - that can be installed in an Android project. - If present, the <project-files> collection must contain at least one path. - Each path is relative to the root directory of the package. - </xsd:documentation> - </xsd:annotation> - <xsd:sequence minOccurs="1" maxOccurs="unbounded"> - <!-- One JAR Path, relative to the root folder of the package. --> - <xsd:element name="path" type="xsd:string" /> - </xsd:sequence> - </xsd:complexType> - - - <!-- The definition of a file checksum --> - - <xsd:simpleType name="sha1Number"> - <xsd:annotation> - <xsd:documentation>A SHA1 checksum.</xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:string"> - <xsd:pattern value="([0-9a-fA-F]){40}"/> - </xsd:restriction> - </xsd:simpleType> - - <xsd:complexType name="checksumType"> - <xsd:annotation> - <xsd:documentation>A file checksum, currently only SHA1.</xsd:documentation> - </xsd:annotation> - <xsd:simpleContent> - <xsd:extension base="sdk:sha1Number"> - <xsd:attribute name="type" type="xsd:token" fixed="sha1" /> - </xsd:extension> - </xsd:simpleContent> - </xsd:complexType> - -</xsd:schema> diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-addon-3.xsd b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-addon-3.xsd deleted file mode 100755 index ccd00c2..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-addon-3.xsd +++ /dev/null @@ -1,381 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<xsd:schema - targetNamespace="http://schemas.android.com/sdk/android/addon/3" - xmlns:xsd="http://www.w3.org/2001/XMLSchema" - xmlns:sdk="http://schemas.android.com/sdk/android/addon/3" - elementFormDefault="qualified" - attributeFormDefault="unqualified" - version="1"> - - <!-- The repository contains a collection of downloadable items known as - "packages". Each package has a type and various attributes and contains - a list of file "archives" that can be downloaded for specific OSes. - - An Android Addon repository is a web site that contains an "addon.xml" - file that conforms to this XML Schema. - - History: - - v1 is used by the SDK Updater in Tools r8. It is split out of the - main SDK Repository XML Schema and can only contain <addon> and - <extra> packages. - - - v2 is used by the SDK Updater in Tools r12. - - <extra> element now has a <project-files> element that contains 1 or - or more <path>, each indicating the relative path of a file that this package - can contribute to installed projects. - - <addon> element now has an optional <layoutlib> that indicates the API - and revision of the layout library for this particular add-on, if any. - - - v3 is used by the SDK Updater in Tools R14: - - <extra> now has an <old-paths> element, a ;-separated list of old paths that - should be detected and migrated to the new <path> for that package. - --> - - <xsd:element name="sdk-addon" type="sdk:repositoryType" /> - - <xsd:complexType name="repositoryType"> - <xsd:annotation> - <xsd:documentation> - The repository contains a collection of downloadable packages. - </xsd:documentation> - </xsd:annotation> - <xsd:choice minOccurs="0" maxOccurs="unbounded"> - <xsd:element name="add-on" type="sdk:addonType" /> - <xsd:element name="extra" type="sdk:extraType" /> - <xsd:element name="license" type="sdk:licenseType" /> - </xsd:choice> - </xsd:complexType> - - <!-- The definition of an SDK Add-on package. --> - - <xsd:complexType name="addonType"> - <xsd:annotation> - <xsd:documentation>An SDK add-on package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The name of the add-on. --> - <xsd:element name="name" type="xsd:normalizedString" /> - <!-- The vendor of the add-on. --> - <xsd:element name="vendor" type="xsd:normalizedString" /> - <!-- The Android API Level for the add-on. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- Note: Add-ons do not support 'codenames' (a.k.a. API previews). --> - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - - <!-- An add-on can declare 0 or more libraries. - This element is mandatory but it can be empty. - --> - - <xsd:element name="libs"> - <xsd:complexType> - <xsd:sequence minOccurs="0" maxOccurs="unbounded"> - <xsd:element name="lib"> - <xsd:complexType> - <xsd:all> - <!-- The name of the library. --> - <xsd:element name="name" type="xsd:normalizedString" /> - <!-- The optional description of this add-on library. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - </xsd:element> - </xsd:sequence> - </xsd:complexType> - </xsd:element> - - <!-- optional elements --> - - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - - <!-- Optional information on the layoutlib packaged in this platform. --> - <xsd:element name="layoutlib" type="sdk:layoutlibType" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of a layout library used by an addon. --> - - <xsd:complexType name="layoutlibType" > - <xsd:annotation> - <xsd:documentation> - Version information for a layoutlib included in an addon. - .</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The layoutlib API level, an int > 0, - incremented with each new incompatible lib. --> - <xsd:element name="api" type="xsd:positiveInteger" /> - <!-- The incremental minor revision for that API, e.g. in case of bug fixes. - Optional. An int >= 0, assumed to be 0 if the element is missing. --> - <xsd:element name="revision" type="xsd:nonNegativeInteger" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK extra package. This kind of package is for - "free" content. Such packages are installed in SDK/vendor/path. - - Important implementation detail: this element is duplicated in the - sdk-repository-N.xsd schema and must be kept in sync there. This is - simpler than trying to use some kind of of include or to request - that clients use a third XML schema for common parts. - --> - - <xsd:complexType name="extraType" > - <xsd:annotation> - <xsd:documentation> - An SDK extra package. This kind of package is for "free" content. - Such packages are installed in SDK/vendor/path. - </xsd:documentation> - </xsd:annotation> - <xsd:all> - - <!-- The install path top folder name. It must not be empty. - The segments "add-ons", "docs", "platforms", "platform-tools", "temp" - and "tools" are reserved and cannot be used. - --> - <xsd:element name="vendor" type="sdk:segmentType" /> - - <!-- The install path sub-folder name. It must not be empty. --> - <xsd:element name="path" type="sdk:segmentType" /> - - <!-- A semi-colon separated list of "obsolete" path names which are equivalent - to the current 'path' name. When a package is seen using an old-paths' name, - the package manager will try to upgrade it to the new path. --> - <xsd:element name="old-paths" type="sdk:segmentListType" minOccurs="0" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - <!-- optional elements --> - - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- The minimal revision of tools required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-tools-rev" type="xsd:positiveInteger" minOccurs="0" /> - <!-- The minimal API level required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-api-level" type="xsd:positiveInteger" minOccurs="0" /> - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - - <!-- A list of project files contributed by this package. Optional. --> - <xsd:element name="project-files" type="sdk:projectFilesType" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of a path segment used by the extra element. --> - - <xsd:simpleType name="segmentType"> - <xsd:annotation> - <xsd:documentation> - One path segment for the install path of an extra element. - It must be a single-segment path. It must not be empty. - </xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:token"> - <xsd:pattern value="[a-zA-Z0-9_]+"/> - </xsd:restriction> - </xsd:simpleType> - - <xsd:simpleType name="segmentListType"> - <xsd:annotation> - <xsd:documentation> - A semi-colon separated list of a segmentTypes. - </xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:token"> - <xsd:pattern value="[a-zA-Z0-9_;]+"/> - </xsd:restriction> - </xsd:simpleType> - - - <!-- The definition of a license to be referenced by the uses-license element. --> - - <xsd:complexType name="licenseType"> - <xsd:annotation> - <xsd:documentation> - A license definition. Such a license must be used later as a reference - using a uses-license element in one of the package elements. - </xsd:documentation> - </xsd:annotation> - <xsd:simpleContent> - <xsd:extension base="xsd:string"> - <xsd:attribute name="id" type="xsd:ID" /> - <xsd:attribute name="type" type="xsd:token" fixed="text" /> - </xsd:extension> - </xsd:simpleContent> - </xsd:complexType> - - - <!-- Type describing the license used by a package. - The license MUST be defined using a license node and referenced - using the ref attribute of the license element inside a package. - --> - - <xsd:complexType name="usesLicenseType"> - <xsd:annotation> - <xsd:documentation> - Describes the license used by a package. The license MUST be defined - using a license node and referenced using the ref attribute of the - license element inside a package. - </xsd:documentation> - </xsd:annotation> - <xsd:attribute name="ref" type="xsd:IDREF" /> - </xsd:complexType> - - - <!-- A collection of files that can be downloaded for a given architecture. - The <archives> node is mandatory in the repository elements and the - collection must have at least one <archive> declared. - Each archive is a zip file that will be unzipped in a location that depends - on its package type. - --> - - <xsd:complexType name="archivesType"> - <xsd:annotation> - <xsd:documentation> - A collection of files that can be downloaded for a given architecture. - The <archives> node is mandatory in the repository packages and the - collection must have at least one <archive> declared. - Each archive is a zip file that will be unzipped in a location that depends - on its package type. - </xsd:documentation> - </xsd:annotation> - <xsd:sequence minOccurs="1" maxOccurs="unbounded"> - <!-- One archive file --> - <xsd:element name="archive"> - <xsd:complexType> - <!-- Properties of the archive file --> - <xsd:all> - <!-- The size in bytes of the archive to download. --> - <xsd:element name="size" type="xsd:positiveInteger" /> - <!-- The checksum of the archive file. --> - <xsd:element name="checksum" type="sdk:checksumType" /> - <!-- The URL is an absolute URL if it starts with http://, https:// - or ftp://. Otherwise it is relative to the parent directory that - contains this repository.xml --> - <xsd:element name="url" type="xsd:token" /> - </xsd:all> - - <!-- Attributes that identify the OS and architecture --> - <xsd:attribute name="os" use="required"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="any" /> - <xsd:enumeration value="linux" /> - <xsd:enumeration value="macosx" /> - <xsd:enumeration value="windows" /> - </xsd:restriction> - </xsd:simpleType> - </xsd:attribute> - <xsd:attribute name="arch" use="optional"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="any" /> - <xsd:enumeration value="ppc" /> - <xsd:enumeration value="x86" /> - <xsd:enumeration value="x86_64" /> - </xsd:restriction> - </xsd:simpleType> - </xsd:attribute> - </xsd:complexType> - </xsd:element> - </xsd:sequence> - </xsd:complexType> - - - <!-- A collection of file paths available in an <extra> package - that can be installed in an Android project. - If present, the <project-files> collection must contain at least one path. - Each path is relative to the root directory of the package. - --> - - <xsd:complexType name="projectFilesType"> - <xsd:annotation> - <xsd:documentation> - A collection of file paths available in an <extra> package - that can be installed in an Android project. - If present, the <project-files> collection must contain at least one path. - Each path is relative to the root directory of the package. - </xsd:documentation> - </xsd:annotation> - <xsd:sequence minOccurs="1" maxOccurs="unbounded"> - <!-- One JAR Path, relative to the root folder of the package. --> - <xsd:element name="path" type="xsd:string" /> - </xsd:sequence> - </xsd:complexType> - - - <!-- The definition of a file checksum --> - - <xsd:simpleType name="sha1Number"> - <xsd:annotation> - <xsd:documentation>A SHA1 checksum.</xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:string"> - <xsd:pattern value="([0-9a-fA-F]){40}"/> - </xsd:restriction> - </xsd:simpleType> - - <xsd:complexType name="checksumType"> - <xsd:annotation> - <xsd:documentation>A file checksum, currently only SHA1.</xsd:documentation> - </xsd:annotation> - <xsd:simpleContent> - <xsd:extension base="sdk:sha1Number"> - <xsd:attribute name="type" type="xsd:token" fixed="sha1" /> - </xsd:extension> - </xsd:simpleContent> - </xsd:complexType> - -</xsd:schema> diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-addon-4.xsd b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-addon-4.xsd deleted file mode 100755 index c31efbf..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-addon-4.xsd +++ /dev/null @@ -1,417 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<xsd:schema - targetNamespace="http://schemas.android.com/sdk/android/addon/4" - xmlns:xsd="http://www.w3.org/2001/XMLSchema" - xmlns:sdk="http://schemas.android.com/sdk/android/addon/4" - elementFormDefault="qualified" - attributeFormDefault="unqualified" - version="1"> - - <!-- The repository contains a collection of downloadable items known as - "packages". Each package has a type and various attributes and contains - a list of file "archives" that can be downloaded for specific OSes. - - An Android Addon repository is a web site that contains an "addon.xml" - file that conforms to this XML Schema. - - History: - - v1 is used by the SDK Updater in Tools r8. It is split out of the - main SDK Repository XML Schema and can only contain <addon> and - <extra> packages. - - - v2 is used by the SDK Updater in Tools r12. - - <extra> element now has a <project-files> element that contains 1 or - or more <path>, each indicating the relative path of a file that this package - can contribute to installed projects. - - <addon> element now has an optional <layoutlib> that indicates the API - and revision of the layout library for this particular add-on, if any. - - - v3 is used by the SDK Manager in Tools r14: - - <extra> now has an <old-paths> element, a ;-separated list of old paths that - should be detected and migrated to the new <path> for that package. - - - v4 is used by the SDK Manager in Tools r18: - - <extra> and <addon> are not in the Repository XSD v6 anymore. - - <extra> get a new field <name-display>, which is used by the SDK Manager to - customize the name of the extra in the list display. The single <vendor> - field becomes <vendor-id> and <vendor-display>, the id being used internally - and the display in the UI. - - <addon> does the same, where <name> is replaced by <name-id> and <name-display> - and <vendor> is replaced by <vendor-id> and <vendor-display>. - --> - - <xsd:element name="sdk-addon" type="sdk:repositoryType" /> - - <xsd:complexType name="repositoryType"> - <xsd:annotation> - <xsd:documentation> - The repository contains a collection of downloadable packages. - </xsd:documentation> - </xsd:annotation> - <xsd:choice minOccurs="0" maxOccurs="unbounded"> - <xsd:element name="add-on" type="sdk:addonType" /> - <xsd:element name="extra" type="sdk:extraType" /> - <xsd:element name="license" type="sdk:licenseType" /> - </xsd:choice> - </xsd:complexType> - - <!-- The definition of an SDK Add-on package. --> - - <xsd:complexType name="addonType"> - <xsd:annotation> - <xsd:documentation>An SDK add-on package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The internal name id of the add-on. Must be unique per vendor. --> - <xsd:element name="name-id" type="sdk:idType" /> - <!-- The displayed name of the add-on. --> - <xsd:element name="name-display" type="xsd:normalizedString" /> - - <!-- The internal vendor id of the add-on. Must be unique amongst vendors. --> - <xsd:element name="vendor-id" type="sdk:idType" /> - <!-- The displayed vendor name of the add-on. --> - <xsd:element name="vendor-display" type="xsd:normalizedString" /> - - <!-- The Android API Level for the add-on. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- Note: Add-ons do not support 'codenames' (a.k.a. API previews). --> - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - - <!-- An add-on can declare 0 or more libraries. - This element is mandatory but it can be empty. - --> - - <xsd:element name="libs"> - <xsd:complexType> - <xsd:sequence minOccurs="0" maxOccurs="unbounded"> - <xsd:element name="lib"> - <xsd:complexType> - <xsd:all> - <!-- The name of the library. --> - <xsd:element name="name" type="xsd:normalizedString" /> - <!-- The optional description of this add-on library. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - </xsd:element> - </xsd:sequence> - </xsd:complexType> - </xsd:element> - - <!-- optional elements --> - - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - - <!-- An optional element indicating the package is a beta/preview. - When present, it indicates the release-candidate number. - When the element is absent, it indicates this is a released package. - DEPRECATED. TODO remove in sdk-addon-5. --> - <xsd:element name="beta-rc" type="xsd:positiveInteger" minOccurs="0" /> - - <!-- Optional information on the layoutlib packaged in this platform. --> - <xsd:element name="layoutlib" type="sdk:layoutlibType" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <xsd:simpleType name="idType"> - <xsd:annotation> - <xsd:documentation> - An ID string for an addon/extra name-id or vendor-id - can only be simple alphanumeric string. - </xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:token"> - <xsd:pattern value="[a-zA-Z0-9_-]+"/> - </xsd:restriction> - </xsd:simpleType> - - - <!-- The definition of a layout library used by an addon. --> - - <xsd:complexType name="layoutlibType" > - <xsd:annotation> - <xsd:documentation> - Version information for a layoutlib included in an addon. - .</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The layoutlib API level, an int > 0, - incremented with each new incompatible lib. --> - <xsd:element name="api" type="xsd:positiveInteger" /> - <!-- The incremental minor revision for that API, e.g. in case of bug fixes. - Optional. An int >= 0, assumed to be 0 if the element is missing. --> - <xsd:element name="revision" type="xsd:nonNegativeInteger" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK extra package. This kind of package is for - "free" content. Such packages are installed in SDK/extras/vendor/path. - --> - - <xsd:complexType name="extraType" > - <xsd:annotation> - <xsd:documentation> - An SDK extra package. This kind of package is for "free" content. - Such packages are installed in SDK/vendor/path. - </xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The displayed name of the extra. --> - <xsd:element name="name-display" type="xsd:normalizedString" /> - - <!-- The internal vendor id of the extra. Must be unique amongst vendors. --> - <xsd:element name="vendor-id" type="sdk:idType" /> - <!-- The displayed vendor name of the extra. --> - <xsd:element name="vendor-display" type="xsd:normalizedString" /> - - <!-- The install path sub-folder name. It must not be empty. --> - <xsd:element name="path" type="sdk:segmentType" /> - - <!-- A semi-colon separated list of "obsolete" path names which are equivalent - to the current 'path' name. When a package is seen using an old-paths' name, - the package manager will try to upgrade it to the new path. --> - <xsd:element name="old-paths" type="sdk:segmentListType" minOccurs="0" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - <!-- optional elements --> - - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- The minimal revision of tools required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-tools-rev" type="xsd:positiveInteger" minOccurs="0" /> - <!-- The minimal API level required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-api-level" type="xsd:positiveInteger" minOccurs="0" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - - <!-- An optional element indicating the package is a beta/preview. - When present, it indicates the release-candidate number. - When the element is absent, it indicates this is a released package. --> - <xsd:element name="beta-rc" type="xsd:positiveInteger" minOccurs="0" /> - - <!-- A list of project files contributed by this package. Optional. --> - <xsd:element name="project-files" type="sdk:projectFilesType" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of a path segment used by the extra element. --> - - <xsd:simpleType name="segmentType"> - <xsd:annotation> - <xsd:documentation> - One path segment for the install path of an extra element. - It must be a single-segment path. It must not be empty. - </xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:token"> - <xsd:pattern value="[a-zA-Z0-9_]+"/> - </xsd:restriction> - </xsd:simpleType> - - <xsd:simpleType name="segmentListType"> - <xsd:annotation> - <xsd:documentation> - A semi-colon separated list of a segmentTypes. - </xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:token"> - <xsd:pattern value="[a-zA-Z0-9_;]+"/> - </xsd:restriction> - </xsd:simpleType> - - - <!-- The definition of a license to be referenced by the uses-license element. --> - - <xsd:complexType name="licenseType"> - <xsd:annotation> - <xsd:documentation> - A license definition. Such a license must be used later as a reference - using a uses-license element in one of the package elements. - </xsd:documentation> - </xsd:annotation> - <xsd:simpleContent> - <xsd:extension base="xsd:string"> - <xsd:attribute name="id" type="xsd:ID" /> - <xsd:attribute name="type" type="xsd:token" fixed="text" /> - </xsd:extension> - </xsd:simpleContent> - </xsd:complexType> - - - <!-- Type describing the license used by a package. - The license MUST be defined using a license node and referenced - using the ref attribute of the license element inside a package. - --> - - <xsd:complexType name="usesLicenseType"> - <xsd:annotation> - <xsd:documentation> - Describes the license used by a package. The license MUST be defined - using a license node and referenced using the ref attribute of the - license element inside a package. - </xsd:documentation> - </xsd:annotation> - <xsd:attribute name="ref" type="xsd:IDREF" /> - </xsd:complexType> - - - <!-- A collection of files that can be downloaded for a given architecture. - The <archives> node is mandatory in the repository elements and the - collection must have at least one <archive> declared. - Each archive is a zip file that will be unzipped in a location that depends - on its package type. - --> - - <xsd:complexType name="archivesType"> - <xsd:annotation> - <xsd:documentation> - A collection of files that can be downloaded for a given architecture. - The <archives> node is mandatory in the repository packages and the - collection must have at least one <archive> declared. - Each archive is a zip file that will be unzipped in a location that depends - on its package type. - </xsd:documentation> - </xsd:annotation> - <xsd:sequence minOccurs="1" maxOccurs="unbounded"> - <!-- One archive file --> - <xsd:element name="archive"> - <xsd:complexType> - <!-- Properties of the archive file --> - <xsd:all> - <!-- The size in bytes of the archive to download. --> - <xsd:element name="size" type="xsd:positiveInteger" /> - <!-- The checksum of the archive file. --> - <xsd:element name="checksum" type="sdk:checksumType" /> - <!-- The URL is an absolute URL if it starts with http://, https:// - or ftp://. Otherwise it is relative to the parent directory that - contains this repository.xml --> - <xsd:element name="url" type="xsd:token" /> - </xsd:all> - - <!-- Attributes that identify the OS and architecture --> - <xsd:attribute name="os" use="required"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="any" /> - <xsd:enumeration value="linux" /> - <xsd:enumeration value="macosx" /> - <xsd:enumeration value="windows" /> - </xsd:restriction> - </xsd:simpleType> - </xsd:attribute> - <xsd:attribute name="arch" use="optional"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="any" /> - <xsd:enumeration value="ppc" /> - <xsd:enumeration value="x86" /> - <xsd:enumeration value="x86_64" /> - </xsd:restriction> - </xsd:simpleType> - </xsd:attribute> - </xsd:complexType> - </xsd:element> - </xsd:sequence> - </xsd:complexType> - - - <!-- A collection of file paths available in an <extra> package - that can be installed in an Android project. - If present, the <project-files> collection must contain at least one path. - Each path is relative to the root directory of the package. - --> - - <xsd:complexType name="projectFilesType"> - <xsd:annotation> - <xsd:documentation> - A collection of file paths available in an <extra> package - that can be installed in an Android project. - If present, the <project-files> collection must contain at least one path. - Each path is relative to the root directory of the package. - </xsd:documentation> - </xsd:annotation> - <xsd:sequence minOccurs="1" maxOccurs="unbounded"> - <!-- One JAR Path, relative to the root folder of the package. --> - <xsd:element name="path" type="xsd:string" /> - </xsd:sequence> - </xsd:complexType> - - - <!-- The definition of a file checksum --> - - <xsd:simpleType name="sha1Number"> - <xsd:annotation> - <xsd:documentation>A SHA1 checksum.</xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:string"> - <xsd:pattern value="([0-9a-fA-F]){40}"/> - </xsd:restriction> - </xsd:simpleType> - - <xsd:complexType name="checksumType"> - <xsd:annotation> - <xsd:documentation>A file checksum, currently only SHA1.</xsd:documentation> - </xsd:annotation> - <xsd:simpleContent> - <xsd:extension base="sdk:sha1Number"> - <xsd:attribute name="type" type="xsd:token" fixed="sha1" /> - </xsd:extension> - </xsd:simpleContent> - </xsd:complexType> - -</xsd:schema> diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-addon-5.xsd b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-addon-5.xsd deleted file mode 100755 index 546b00d..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-addon-5.xsd +++ /dev/null @@ -1,442 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<xsd:schema - targetNamespace="http://schemas.android.com/sdk/android/addon/5" - xmlns:xsd="http://www.w3.org/2001/XMLSchema" - xmlns:sdk="http://schemas.android.com/sdk/android/addon/5" - elementFormDefault="qualified" - attributeFormDefault="unqualified" - version="1"> - - <!-- The repository contains a collection of downloadable items known as - "packages". Each package has a type and various attributes and contains - a list of file "archives" that can be downloaded for specific OSes. - - An Android Addon repository is a web site that contains an "addon.xml" - file that conforms to this XML Schema. - - History: - - v1 is used by the SDK Updater in Tools r8. It is split out of the - main SDK Repository XML Schema and can only contain <addon> and - <extra> packages. - - - v2 is used by the SDK Updater in Tools r12. - - <extra> element now has a <project-files> element that contains 1 or - or more <path>, each indicating the relative path of a file that this package - can contribute to installed projects. - - <addon> element now has an optional <layoutlib> that indicates the API - and revision of the layout library for this particular add-on, if any. - - - v3 is used by the SDK Manager in Tools r14: - - <extra> now has an <old-paths> element, a ;-separated list of old paths that - should be detected and migrated to the new <path> for that package. - - - v4 is used by the SDK Manager in Tools r18: - - <extra> and <addon> are not in the Repository XSD v6 anymore. - - <extra> get a new field <name-display>, which is used by the SDK Manager to - customize the name of the extra in the list display. The single <vendor> - field becomes <vendor-id> and <vendor-display>, the id being used internally - and the display in the UI. - - <addon> does the same, where <name> is replaced by <name-id> and <name-display> - and <vendor> is replaced by <vendor-id> and <vendor-display>. - - - v5 is used by the SDK Manager in Tools r20: - - The <beta-rc> element is no longer supported. It was never implemented anyway. - - For <tool> and <platform-tool> packages, the <revision> element becomes a - a "full revision" element with <major>, <minor>, <micro> and <preview> sub-elements. - - <min-tools-rev> for <extra> becomes a full revision element. - --> - - <xsd:element name="sdk-addon" type="sdk:repositoryType" /> - - <xsd:complexType name="repositoryType"> - <xsd:annotation> - <xsd:documentation> - The repository contains a collection of downloadable packages. - </xsd:documentation> - </xsd:annotation> - <xsd:choice minOccurs="0" maxOccurs="unbounded"> - <xsd:element name="add-on" type="sdk:addonType" /> - <xsd:element name="extra" type="sdk:extraType" /> - <xsd:element name="license" type="sdk:licenseType" /> - </xsd:choice> - </xsd:complexType> - - - <!-- The definition of an SDK Add-on package. --> - - <xsd:complexType name="addonType"> - <xsd:annotation> - <xsd:documentation>An SDK add-on package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The internal name id of the add-on. Must be unique per vendor. --> - <xsd:element name="name-id" type="sdk:idType" /> - <!-- The displayed name of the add-on. --> - <xsd:element name="name-display" type="xsd:normalizedString" /> - - <!-- The internal vendor id of the add-on. Must be unique amongst vendors. --> - <xsd:element name="vendor-id" type="sdk:idType" /> - <!-- The displayed vendor name of the add-on. --> - <xsd:element name="vendor-display" type="xsd:normalizedString" /> - - <!-- The Android API Level for the add-on. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- Note: Add-ons do not support 'codenames' (a.k.a. API previews). --> - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - - <!-- An add-on can declare 0 or more libraries. - This element is mandatory but it can be empty. - --> - - <xsd:element name="libs"> - <xsd:complexType> - <xsd:sequence minOccurs="0" maxOccurs="unbounded"> - <xsd:element name="lib"> - <xsd:complexType> - <xsd:all> - <!-- The name of the library. --> - <xsd:element name="name" type="xsd:normalizedString" /> - <!-- The optional description of this add-on library. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - </xsd:element> - </xsd:sequence> - </xsd:complexType> - </xsd:element> - - <!-- optional elements --> - - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - - <!-- Optional information on the layoutlib packaged in this platform. --> - <xsd:element name="layoutlib" type="sdk:layoutlibType" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <xsd:simpleType name="idType"> - <xsd:annotation> - <xsd:documentation> - An ID string for an addon/extra name-id or vendor-id - can only be simple alphanumeric string. - </xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:token"> - <xsd:pattern value="[a-zA-Z0-9_-]+"/> - </xsd:restriction> - </xsd:simpleType> - - - <!-- The definition of a layout library used by an addon. --> - - <xsd:complexType name="layoutlibType" > - <xsd:annotation> - <xsd:documentation> - Version information for a layoutlib included in an addon. - .</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The layoutlib API level, an int > 0, - incremented with each new incompatible lib. --> - <xsd:element name="api" type="xsd:positiveInteger" /> - <!-- The incremental minor revision for that API, e.g. in case of bug fixes. - Optional. An int >= 0, assumed to be 0 if the element is missing. --> - <xsd:element name="revision" type="xsd:nonNegativeInteger" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK extra package. This kind of package is for - "free" content. Such packages are installed in SDK/extras/vendor/path. - --> - - <xsd:complexType name="extraType" > - <xsd:annotation> - <xsd:documentation> - An SDK extra package. This kind of package is for "free" content. - Such packages are installed in SDK/vendor/path. - </xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The displayed name of the extra. --> - <xsd:element name="name-display" type="xsd:normalizedString" /> - - <!-- The internal vendor id of the extra. Must be unique amongst vendors. --> - <xsd:element name="vendor-id" type="sdk:idType" /> - <!-- The displayed vendor name of the extra. --> - <xsd:element name="vendor-display" type="xsd:normalizedString" /> - - <!-- The install path sub-folder name. It must not be empty. --> - <xsd:element name="path" type="sdk:segmentType" /> - - <!-- A semi-colon separated list of "obsolete" path names which are equivalent - to the current 'path' name. When a package is seen using an old-paths' name, - the package manager will try to upgrade it to the new path. --> - <xsd:element name="old-paths" type="sdk:segmentListType" minOccurs="0" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - <!-- optional elements --> - - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- The minimal revision of tools required by this package. - Optional. If present, must be a revision element. --> - <xsd:element name="min-tools-rev" type="sdk:revisionType" minOccurs="0" /> - <!-- The minimal API level required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-api-level" type="xsd:positiveInteger" minOccurs="0" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - - <!-- A list of project files contributed by this package. Optional. --> - <xsd:element name="project-files" type="sdk:projectFilesType" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- A full revision, with a major.minor.micro and an optional preview number. - The major number is mandatory, the other elements are optional. - --> - - <xsd:complexType name="revisionType"> - <xsd:annotation> - <xsd:documentation> - A full revision, with a major.minor.micro and an - optional preview number. The major number is mandatory. - </xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The major revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="major" type="xsd:positiveInteger" /> - <!-- The minor revision, an int >= 0, incremented each time a new - minor package is generated. Assumed to be 0 if missing. --> - <xsd:element name="minor" type="xsd:nonNegativeInteger" minOccurs="0" /> - <!-- The micro revision, an int >= 0, incremented each time a new - buf fix is generated. Assumed to be 0 if missing. --> - <xsd:element name="micro" type="xsd:nonNegativeInteger" minOccurs="0" /> - <!-- The preview/release candidate revision, an int > 0, - incremented each time a new preview is generated. - Not present for final releases. --> - <xsd:element name="preview" type="xsd:positiveInteger" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of a path segment used by the extra element. --> - - <xsd:simpleType name="segmentType"> - <xsd:annotation> - <xsd:documentation> - One path segment for the install path of an extra element. - It must be a single-segment path. It must not be empty. - </xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:token"> - <xsd:pattern value="[a-zA-Z0-9_]+"/> - </xsd:restriction> - </xsd:simpleType> - - <xsd:simpleType name="segmentListType"> - <xsd:annotation> - <xsd:documentation> - A semi-colon separated list of a segmentTypes. - </xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:token"> - <xsd:pattern value="[a-zA-Z0-9_;]+"/> - </xsd:restriction> - </xsd:simpleType> - - - <!-- The definition of a license to be referenced by the uses-license element. --> - - <xsd:complexType name="licenseType"> - <xsd:annotation> - <xsd:documentation> - A license definition. Such a license must be used later as a reference - using a uses-license element in one of the package elements. - </xsd:documentation> - </xsd:annotation> - <xsd:simpleContent> - <xsd:extension base="xsd:string"> - <xsd:attribute name="id" type="xsd:ID" /> - <xsd:attribute name="type" type="xsd:token" fixed="text" /> - </xsd:extension> - </xsd:simpleContent> - </xsd:complexType> - - - <!-- Type describing the license used by a package. - The license MUST be defined using a license node and referenced - using the ref attribute of the license element inside a package. - --> - - <xsd:complexType name="usesLicenseType"> - <xsd:annotation> - <xsd:documentation> - Describes the license used by a package. The license MUST be defined - using a license node and referenced using the ref attribute of the - license element inside a package. - </xsd:documentation> - </xsd:annotation> - <xsd:attribute name="ref" type="xsd:IDREF" /> - </xsd:complexType> - - - <!-- A collection of files that can be downloaded for a given architecture. - The <archives> node is mandatory in the repository elements and the - collection must have at least one <archive> declared. - Each archive is a zip file that will be unzipped in a location that depends - on its package type. - --> - - <xsd:complexType name="archivesType"> - <xsd:annotation> - <xsd:documentation> - A collection of files that can be downloaded for a given architecture. - The <archives> node is mandatory in the repository packages and the - collection must have at least one <archive> declared. - Each archive is a zip file that will be unzipped in a location that depends - on its package type. - </xsd:documentation> - </xsd:annotation> - <xsd:sequence minOccurs="1" maxOccurs="unbounded"> - <!-- One archive file --> - <xsd:element name="archive"> - <xsd:complexType> - <!-- Properties of the archive file --> - <xsd:all> - <!-- The size in bytes of the archive to download. --> - <xsd:element name="size" type="xsd:positiveInteger" /> - <!-- The checksum of the archive file. --> - <xsd:element name="checksum" type="sdk:checksumType" /> - <!-- The URL is an absolute URL if it starts with http://, https:// - or ftp://. Otherwise it is relative to the parent directory that - contains this repository.xml --> - <xsd:element name="url" type="xsd:token" /> - </xsd:all> - - <!-- Attributes that identify the OS and architecture --> - <xsd:attribute name="os" use="required"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="any" /> - <xsd:enumeration value="linux" /> - <xsd:enumeration value="macosx" /> - <xsd:enumeration value="windows" /> - </xsd:restriction> - </xsd:simpleType> - </xsd:attribute> - <xsd:attribute name="arch" use="optional"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="any" /> - <xsd:enumeration value="ppc" /> - <xsd:enumeration value="x86" /> - <xsd:enumeration value="x86_64" /> - </xsd:restriction> - </xsd:simpleType> - </xsd:attribute> - </xsd:complexType> - </xsd:element> - </xsd:sequence> - </xsd:complexType> - - - <!-- A collection of file paths available in an <extra> package - that can be installed in an Android project. - If present, the <project-files> collection must contain at least one path. - Each path is relative to the root directory of the package. - --> - - <xsd:complexType name="projectFilesType"> - <xsd:annotation> - <xsd:documentation> - A collection of file paths available in an <extra> package - that can be installed in an Android project. - If present, the <project-files> collection must contain at least one path. - Each path is relative to the root directory of the package. - </xsd:documentation> - </xsd:annotation> - <xsd:sequence minOccurs="1" maxOccurs="unbounded"> - <!-- One JAR Path, relative to the root folder of the package. --> - <xsd:element name="path" type="xsd:string" /> - </xsd:sequence> - </xsd:complexType> - - - <!-- The definition of a file checksum --> - - <xsd:simpleType name="sha1Number"> - <xsd:annotation> - <xsd:documentation>A SHA1 checksum.</xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:string"> - <xsd:pattern value="([0-9a-fA-F]){40}"/> - </xsd:restriction> - </xsd:simpleType> - - <xsd:complexType name="checksumType"> - <xsd:annotation> - <xsd:documentation>A file checksum, currently only SHA1.</xsd:documentation> - </xsd:annotation> - <xsd:simpleContent> - <xsd:extension base="sdk:sha1Number"> - <xsd:attribute name="type" type="xsd:token" fixed="sha1" /> - </xsd:extension> - </xsd:simpleContent> - </xsd:complexType> - -</xsd:schema> diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-addons-list-1.xsd b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-addons-list-1.xsd deleted file mode 100755 index 176fb60..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-addons-list-1.xsd +++ /dev/null @@ -1,71 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- - * Copyright (C) 2010 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<xsd:schema - targetNamespace="http://schemas.android.com/sdk/android/addons-list/1" - xmlns:xsd="http://www.w3.org/2001/XMLSchema" - xmlns:sa1="http://schemas.android.com/sdk/android/addons-list/1" - elementFormDefault="qualified" - attributeFormDefault="unqualified" - version="1"> - - <!-- - A simple list of add-ons sites that is loaded by default by the SDK Manager. - --> - - <xsd:element name="sdk-addons-list" type="sa1:addonsListType" /> - - <xsd:complexType name="addonsListType"> - <xsd:annotation> - <xsd:documentation> - A simple list of add-ons site. - </xsd:documentation> - </xsd:annotation> - <xsd:choice minOccurs="0" maxOccurs="unbounded"> - <xsd:element name="addon-site" type="sa1:addonSiteType" /> - </xsd:choice> - </xsd:complexType> - - <!-- The definition of an Add-on Site. --> - - <xsd:complexType name="addonSiteType"> - <xsd:annotation> - <xsd:documentation>An SDK add-on site.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The URL of the site. - - This can be either the exact URL of the an XML resource conforming - to the latest sdk-addon-N.xsd schema, or it can be the URL of a - 'directory', in which case the manager will look for a resource - named 'addon.xml' at this location. - - Examples: - http://www.example.com/android/my_addons.xml - or - http://www.example.com/android/ - - In the second example, the manager will actually look for: - http://www.example.com/android/addon.xml - --> - <xsd:element name="url" type="xsd:token" /> - - <!-- The UI-visible name of the add-on. --> - <xsd:element name="name" type="xsd:normalizedString" /> - </xsd:all> - </xsd:complexType> - -</xsd:schema> diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-addons-list-2.xsd b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-addons-list-2.xsd deleted file mode 100755 index dde7214..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-addons-list-2.xsd +++ /dev/null @@ -1,106 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<xsd:schema - targetNamespace="http://schemas.android.com/sdk/android/addons-list/2" - xmlns:xsd="http://www.w3.org/2001/XMLSchema" - xmlns:sa1="http://schemas.android.com/sdk/android/addons-list/2" - elementFormDefault="qualified" - attributeFormDefault="unqualified" - version="1"> - - <!-- - A simple list of add-ons sites that is loaded by default by the SDK Manager. - - - v1: Defines <addon-site> - - v2: Adds support for <sys-img-site> - --> - - <xsd:element name="sdk-addons-list" type="sa1:addonsListType" /> - - <xsd:complexType name="addonsListType"> - <xsd:annotation> - <xsd:documentation> - A simple list of add-ons site. - </xsd:documentation> - </xsd:annotation> - <xsd:choice minOccurs="0" maxOccurs="unbounded"> - <xsd:element name="addon-site" type="sa1:addonSiteType" /> - <xsd:element name="sys-img-site" type="sa1:sysImgSiteType" /> - </xsd:choice> - </xsd:complexType> - - <!-- The definition of an Add-on Site. --> - - <xsd:complexType name="addonSiteType"> - <xsd:annotation> - <xsd:documentation>An SDK add-on site.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The URL of the site. - - This can be either the exact URL of the an XML resource conforming - to the latest sdk-addon-N.xsd schema, or it can be the URL of a - 'directory', in which case the manager will look for a resource - named 'addon.xml' at this location. - - Examples: - http://www.example.com/android/my_addons.xml - or - http://www.example.com/android/ - - In the second example, the manager will actually look for: - http://www.example.com/android/addon.xml - --> - <xsd:element name="url" type="xsd:token" /> - - <!-- The UI-visible name of the add-on site. --> - <xsd:element name="name" type="xsd:normalizedString" /> - - </xsd:all> - </xsd:complexType> - - <!-- The definition of an Sys-Img Site. --> - - <xsd:complexType name="sysImgSiteType"> - <xsd:annotation> - <xsd:documentation>An SDK sys-img site.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The URL of the site. - - This can be either the exact URL of the an XML resource conforming - to the latest sdk-sys-img-N.xsd schema, or it can be the URL of a - 'directory', in which case the manager will look for a resource - named 'sysimg.xml' at this location. - - Examples: - http://www.example.com/android/my_sys_img.xml - or - http://www.example.com/android/ - - In the second example, the manager will actually look for: - http://www.example.com/android/sysimg.xml - --> - <xsd:element name="url" type="xsd:token" /> - - <!-- The UI-visible name of the sys-img site. --> - <xsd:element name="name" type="xsd:normalizedString" /> - - </xsd:all> - </xsd:complexType> - -</xsd:schema> diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-repository-1.xsd b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-repository-1.xsd deleted file mode 100755 index 38ec309..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-repository-1.xsd +++ /dev/null @@ -1,381 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<xsd:schema - targetNamespace="http://schemas.android.com/sdk/android/repository/1" - xmlns:xsd="http://www.w3.org/2001/XMLSchema" - xmlns:sdk="http://schemas.android.com/sdk/android/repository/1" - elementFormDefault="qualified" - attributeFormDefault="unqualified" - version="1"> - - <!-- The repository contains a collection of downloadable items known as - "packages". Each package has a type and various attributes and contains - a list of file "archives" that can be downloaded for specific OSes. - - An Android SDK repository is a web site that contains a "repository.xml" - file that conforms to this XML Schema. - - History: - - v1 is used by the SDK Updater in Tools r3 and Tools r4. - --> - - <xsd:element name="sdk-repository"> - <xsd:annotation> - <xsd:documentation> - The repository contains collections of downloadable packages. - </xsd:documentation> - </xsd:annotation> - - <xsd:complexType> - <xsd:choice minOccurs="0" maxOccurs="unbounded"> - - <!-- The definition of an SDK platform package. --> - - <xsd:element name="platform"> - <xsd:annotation> - <xsd:documentation>An SDK platform package.</xsd:documentation> - </xsd:annotation> - <xsd:complexType> - <xsd:all> - <!-- The Android platform version. It is string such as "1.0". --> - <xsd:element name="version" type="xsd:normalizedString" /> - <!-- The Android API Level for the platform. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- The optional codename for this platform, if it's a preview. --> - <xsd:element name="codename" type="xsd:string" minOccurs="0" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:licenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - <!-- The minimal revision of tools required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-tools-rev" type="xsd:positiveInteger" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - </xsd:element> - - - <!-- The definition of an SDK Add-on package. --> - - <xsd:element name="add-on"> - <xsd:annotation> - <xsd:documentation>An SDK add-on package.</xsd:documentation> - </xsd:annotation> - <xsd:complexType> - <xsd:all> - <!-- The name of the add-on. --> - <xsd:element name="name" type="xsd:normalizedString" /> - <!-- The vendor of the add-on. --> - <xsd:element name="vendor" type="xsd:normalizedString" /> - <!-- The Android API Level for the add-on. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- Note: Add-ons do not support 'codename' (a.k.a. API previews). --> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:licenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - <!-- An add-on can declare 0 or more libraries. --> - - <xsd:element name="libs"> - <xsd:complexType> - <xsd:sequence minOccurs="0" maxOccurs="unbounded"> - <xsd:element name="lib"> - <xsd:complexType> - <xsd:all> - <!-- The name of the library. --> - <xsd:element name="name" type="xsd:normalizedString" /> - <!-- The optional description of this add-on library. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - </xsd:element> - </xsd:sequence> - </xsd:complexType> - </xsd:element> - </xsd:all> - </xsd:complexType> - </xsd:element> - - - <!-- The definition of an SDK tool package. --> - - <xsd:element name="tool"> - <xsd:annotation> - <xsd:documentation>An SDK tool package.</xsd:documentation> - </xsd:annotation> - <xsd:complexType> - <xsd:all> - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:licenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - </xsd:all> - </xsd:complexType> - </xsd:element> - - - <!-- The definition of an SDK doc package. --> - - <xsd:element name="doc"> - <xsd:annotation> - <xsd:documentation>An SDK doc package.</xsd:documentation> - </xsd:annotation> - <xsd:complexType> - <xsd:all> - <!-- The Android API Level for the documentation. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- The optional codename for this doc, if it's a preview. --> - <xsd:element name="codename" type="xsd:string" minOccurs="0" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:licenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - </xsd:all> - </xsd:complexType> - </xsd:element> - - - <!-- The definition of an SDK extra package. This kind of package is for - "free" content and specifies in which fixed root directory it must be - installed. - --> - - <xsd:element name="extra"> - <xsd:annotation> - <xsd:documentation> - An SDK extra package. This kind of package is for "free" - content and specifies in which fixed root directory it must be - installed. - The paths "add-ons", "platforms", "tools" and "docs" are - reserved and cannot be used. - </xsd:documentation> - </xsd:annotation> - <xsd:complexType> - <xsd:all> - <!-- The install folder name. It must be a single-segment path. - The paths "add-ons", "platforms", "tools" and "docs" are - reserved and cannot be used. - --> - <xsd:element name="path"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:pattern value="[^/\\]+"/> - </xsd:restriction> - </xsd:simpleType> - </xsd:element> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:licenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - <!-- The minimal revision of tools required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-tools-rev" type="xsd:positiveInteger" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - </xsd:element> - - - - <!-- The definition of a license to be referenced by the uses-license element. --> - - <xsd:element name="license"> - <xsd:annotation> - <xsd:documentation> - A license definition. Such a license must be used later as a reference - using a uses-license element in one of the package elements. - </xsd:documentation> - </xsd:annotation> - <xsd:complexType> - <xsd:simpleContent> - <xsd:extension base="xsd:string"> - <xsd:attribute name="id" type="xsd:ID" /> - <xsd:attribute name="type" type="xsd:token" fixed="text" /> - </xsd:extension> - </xsd:simpleContent> - </xsd:complexType> - </xsd:element> - </xsd:choice> - </xsd:complexType> - </xsd:element> - - - <!-- Type describing the license used by a package. - The license MUST be defined using a license node and referenced - using the ref attribute of the license element inside a package. - --> - - <xsd:complexType name="licenseType"> - <xsd:annotation> - <xsd:documentation> - Describes the license used by a package. The license MUST be defined - using a license node and referenced using the ref attribute of the - license element inside a package. - </xsd:documentation> - </xsd:annotation> - <xsd:attribute name="ref" type="xsd:IDREF" /> - </xsd:complexType> - - - <!-- A collection of files that can be downloaded for a given architecture. - The <archives> node is mandatory in the repository elements and the - collection must have at least one <archive> declared. - Each archive is a zip file that will be unzipped in a location that depends - on its package type. - --> - - <xsd:complexType name="archivesType"> - <xsd:annotation> - <xsd:documentation> - A collection of files that can be downloaded for a given architecture. - The <archives> node is mandatory in the repository packages and the - collection must have at least one <archive> declared. - Each archive is a zip file that will be unzipped in a location that depends - on its package type. - </xsd:documentation> - </xsd:annotation> - <xsd:sequence minOccurs="1" maxOccurs="unbounded"> - <!-- One archive file --> - <xsd:element name="archive"> - <xsd:complexType> - <!-- Properties of the archive file --> - <xsd:all> - <!-- The size in bytes of the archive to download. --> - <xsd:element name="size" type="xsd:positiveInteger" /> - <!-- The checksum of the archive file. --> - <xsd:element name="checksum" type="sdk:checksumType" /> - <!-- The URL is an absolute URL if it starts with http://, https:// - or ftp://. Otherwise it is relative to the parent directory that - contains this repository.xml --> - <xsd:element name="url" type="xsd:token" /> - </xsd:all> - - <!-- Attributes that identify the OS and architecture --> - <xsd:attribute name="os" use="required"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="any" /> - <xsd:enumeration value="linux" /> - <xsd:enumeration value="macosx" /> - <xsd:enumeration value="windows" /> - </xsd:restriction> - </xsd:simpleType> - </xsd:attribute> - <xsd:attribute name="arch" use="optional"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="any" /> - <xsd:enumeration value="ppc" /> - <xsd:enumeration value="x86" /> - <xsd:enumeration value="x86_64" /> - </xsd:restriction> - </xsd:simpleType> - </xsd:attribute> - </xsd:complexType> - </xsd:element> - </xsd:sequence> - </xsd:complexType> - - - <!-- The definition of a file checksum --> - - <xsd:simpleType name="sha1Number"> - <xsd:annotation> - <xsd:documentation>A SHA1 checksum.</xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:string"> - <xsd:pattern value="([0-9a-fA-F]){40}"/> - </xsd:restriction> - </xsd:simpleType> - - <xsd:complexType name="checksumType"> - <xsd:annotation> - <xsd:documentation>A file checksum, currently only SHA1.</xsd:documentation> - </xsd:annotation> - <xsd:simpleContent> - <xsd:extension base="sdk:sha1Number"> - <xsd:attribute name="type" type="xsd:token" fixed="sha1" /> - </xsd:extension> - </xsd:simpleContent> - </xsd:complexType> - - -</xsd:schema> diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-repository-2.xsd b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-repository-2.xsd deleted file mode 100755 index ecadc3f..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-repository-2.xsd +++ /dev/null @@ -1,438 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<xsd:schema - targetNamespace="http://schemas.android.com/sdk/android/repository/2" - xmlns:xsd="http://www.w3.org/2001/XMLSchema" - xmlns:sr2="http://schemas.android.com/sdk/android/repository/2" - elementFormDefault="qualified" - attributeFormDefault="unqualified" - version="1"> - - <!-- The repository contains a collection of downloadable items known as - "packages". Each package has a type and various attributes and contains - a list of file "archives" that can be downloaded for specific OSes. - - An Android SDK repository is a web site that contains a "repository.xml" - file that conforms to this XML Schema. - - History: - - v1 is used by the SDK Updater in Tools r3 and r4. - - v2 is used by the SDK Updater in Tools r5: - - new <sample> repository type. - - new <obsolete> in all repository types. - --> - - <xsd:element name="sdk-repository" type="sr2:repositoryType" /> - - <xsd:complexType name="repositoryType"> - <xsd:annotation> - <xsd:documentation> - The repository contains a collection of downloadable packages. - </xsd:documentation> - </xsd:annotation> - <xsd:choice minOccurs="0" maxOccurs="unbounded"> - <xsd:element name="platform" type="sr2:platformType" /> - <xsd:element name="add-on" type="sr2:addonType" /> - <xsd:element name="tool" type="sr2:toolType" /> - <xsd:element name="doc" type="sr2:docType" /> - <xsd:element name="sample" type="sr2:sampleType" /> - <xsd:element name="extra" type="sr2:extraType" /> - <xsd:element name="license" type="sr2:licenseType" /> - </xsd:choice> - </xsd:complexType> - - <!-- The definition of an SDK platform package. --> - - <xsd:complexType name="platformType"> - <xsd:annotation> - <xsd:documentation>An SDK platform package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The Android platform version. It is string such as "1.0". --> - <xsd:element name="version" type="xsd:normalizedString" /> - <!-- The Android API Level for the platform. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- The optional codename for this platform, if it's a preview. --> - <xsd:element name="codename" type="xsd:string" minOccurs="0" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sr2:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sr2:archivesType" /> - <!-- The minimal revision of tools required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-tools-rev" type="xsd:positiveInteger" minOccurs="0" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK Add-on package. --> - - <xsd:complexType name="addonType"> - <xsd:annotation> - <xsd:documentation>An SDK add-on package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The name of the add-on. --> - <xsd:element name="name" type="xsd:normalizedString" /> - <!-- The vendor of the add-on. --> - <xsd:element name="vendor" type="xsd:normalizedString" /> - <!-- The Android API Level for the add-on. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- Note: Add-ons do not support 'codename' (a.k.a. API previews). --> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sr2:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sr2:archivesType" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - - <!-- An add-on can declare 0 or more libraries. --> - - <xsd:element name="libs"> - <xsd:complexType> - <xsd:sequence minOccurs="0" maxOccurs="unbounded"> - <xsd:element name="lib"> - <xsd:complexType> - <xsd:all> - <!-- The name of the library. --> - <xsd:element name="name" type="xsd:normalizedString" /> - <!-- The optional description of this add-on library. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - </xsd:element> - </xsd:sequence> - </xsd:complexType> - </xsd:element> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK tool package. --> - - <xsd:complexType name="toolType" > - <xsd:annotation> - <xsd:documentation>An SDK tool package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sr2:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sr2:archivesType" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK doc package. --> - - <xsd:complexType name="docType" > - <xsd:annotation> - <xsd:documentation>An SDK doc package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The Android API Level for the documentation. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- The optional codename for this doc, if it's a preview. --> - <xsd:element name="codename" type="xsd:string" minOccurs="0" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sr2:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sr2:archivesType" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK sample package. --> - - <xsd:complexType name="sampleType" > - <xsd:annotation> - <xsd:documentation>An SDK sample package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The Android API Level for the documentation. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- The optional codename for this doc, if it's a preview. --> - <xsd:element name="codename" type="xsd:string" minOccurs="0" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sr2:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sr2:archivesType" /> - <!-- The minimal revision of tools required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-tools-rev" type="xsd:positiveInteger" minOccurs="0" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK extra package. This kind of package is for - "free" content and specifies in which fixed root directory it must be - installed. - --> - - <xsd:complexType name="extraType" > - <xsd:annotation> - <xsd:documentation> - An SDK extra package. This kind of package is for "free" - content and specifies in which fixed root directory it must be - installed. - The paths "add-ons", "platforms", "tools" and "docs" are - reserved and cannot be used. - </xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The install folder name. It must be a single-segment path. - The paths "add-ons", "platforms", "tools" and "docs" are - reserved and cannot be used. - --> - <xsd:element name="path"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:pattern value="[^/\\]+"/> - </xsd:restriction> - </xsd:simpleType> - </xsd:element> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sr2:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sr2:archivesType" /> - <!-- The minimal revision of tools required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-tools-rev" type="xsd:positiveInteger" minOccurs="0" /> - <!-- The minimal API level required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-api-level" type="xsd:positiveInteger" minOccurs="0" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of a license to be referenced by the uses-license element. --> - - <xsd:complexType name="licenseType"> - <xsd:annotation> - <xsd:documentation> - A license definition. Such a license must be used later as a reference - using a uses-license element in one of the package elements. - </xsd:documentation> - </xsd:annotation> - <xsd:simpleContent> - <xsd:extension base="xsd:string"> - <xsd:attribute name="id" type="xsd:ID" /> - <xsd:attribute name="type" type="xsd:token" fixed="text" /> - </xsd:extension> - </xsd:simpleContent> - </xsd:complexType> - - - <!-- Type describing the license used by a package. - The license MUST be defined using a license node and referenced - using the ref attribute of the license element inside a package. - --> - - <xsd:complexType name="usesLicenseType"> - <xsd:annotation> - <xsd:documentation> - Describes the license used by a package. The license MUST be defined - using a license node and referenced using the ref attribute of the - license element inside a package. - </xsd:documentation> - </xsd:annotation> - <xsd:attribute name="ref" type="xsd:IDREF" /> - </xsd:complexType> - - - <!-- A collection of files that can be downloaded for a given architecture. - The <archives> node is mandatory in the repository elements and the - collection must have at least one <archive> declared. - Each archive is a zip file that will be unzipped in a location that depends - on its package type. - --> - - <xsd:complexType name="archivesType"> - <xsd:annotation> - <xsd:documentation> - A collection of files that can be downloaded for a given architecture. - The <archives> node is mandatory in the repository packages and the - collection must have at least one <archive> declared. - Each archive is a zip file that will be unzipped in a location that depends - on its package type. - </xsd:documentation> - </xsd:annotation> - <xsd:sequence minOccurs="1" maxOccurs="unbounded"> - <!-- One archive file --> - <xsd:element name="archive"> - <xsd:complexType> - <!-- Properties of the archive file --> - <xsd:all> - <!-- The size in bytes of the archive to download. --> - <xsd:element name="size" type="xsd:positiveInteger" /> - <!-- The checksum of the archive file. --> - <xsd:element name="checksum" type="sr2:checksumType" /> - <!-- The URL is an absolute URL if it starts with http://, https:// - or ftp://. Otherwise it is relative to the parent directory that - contains this repository.xml --> - <xsd:element name="url" type="xsd:token" /> - </xsd:all> - - <!-- Attributes that identify the OS and architecture --> - <xsd:attribute name="os" use="required"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="any" /> - <xsd:enumeration value="linux" /> - <xsd:enumeration value="macosx" /> - <xsd:enumeration value="windows" /> - </xsd:restriction> - </xsd:simpleType> - </xsd:attribute> - <xsd:attribute name="arch" use="optional"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="any" /> - <xsd:enumeration value="ppc" /> - <xsd:enumeration value="x86" /> - <xsd:enumeration value="x86_64" /> - </xsd:restriction> - </xsd:simpleType> - </xsd:attribute> - </xsd:complexType> - </xsd:element> - </xsd:sequence> - </xsd:complexType> - - - <!-- The definition of a file checksum --> - - <xsd:simpleType name="sha1Number"> - <xsd:annotation> - <xsd:documentation>A SHA1 checksum.</xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:string"> - <xsd:pattern value="([0-9a-fA-F]){40}"/> - </xsd:restriction> - </xsd:simpleType> - - <xsd:complexType name="checksumType"> - <xsd:annotation> - <xsd:documentation>A file checksum, currently only SHA1.</xsd:documentation> - </xsd:annotation> - <xsd:simpleContent> - <xsd:extension base="sr2:sha1Number"> - <xsd:attribute name="type" type="xsd:token" fixed="sha1" /> - </xsd:extension> - </xsd:simpleContent> - </xsd:complexType> - -</xsd:schema> diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-repository-3.xsd b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-repository-3.xsd deleted file mode 100755 index 75d8541..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-repository-3.xsd +++ /dev/null @@ -1,436 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- - * Copyright (C) 2010 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<xsd:schema - targetNamespace="http://schemas.android.com/sdk/android/repository/3" - xmlns:xsd="http://www.w3.org/2001/XMLSchema" - xmlns:sdk="http://schemas.android.com/sdk/android/repository/3" - elementFormDefault="qualified" - attributeFormDefault="unqualified" - version="1"> - - <!-- The repository contains a collection of downloadable items known as - "packages". Each package has a type and various attributes and contains - a list of file "archives" that can be downloaded for specific OSes. - - An Android SDK repository is a web site that contains a "repository.xml" - file that conforms to this XML Schema. - - History: - - v1 is used by the SDK Updater in Tools r3 and r4. - - - v2 is used by the SDK Updater in Tools r5: - - It introduces a new <sample> repository type. Previously samples - were included in the <platform> packages. Instead this package is used - and and the samples are installed in $SDK/samples. - - All repository types have a new <obsolete> node. It works as a marker - to indicate the package is obsolete and should not be selected by default. - The UI also hides these out by default. - - - v3 is used by the SDK Updater in Tools r8: - - It introduces a new <platform-tool> repository type. Previously platform-specific - tools were included in the <platform> packages. Instead this package is used - and platform-specific tools are installed in $SDK/platform-tools - - There's a new element <min-platform-tools-rev> in <tool>. The tool package now - requires that at least some minimal version of <platform-tool> be installed. - - It removes the <addon> repository type, which is now in its own XML Schema. - --> - - <xsd:element name="sdk-repository" type="sdk:repositoryType" /> - - <xsd:complexType name="repositoryType"> - <xsd:annotation> - <xsd:documentation> - The repository contains a collection of downloadable packages. - </xsd:documentation> - </xsd:annotation> - <xsd:choice minOccurs="0" maxOccurs="unbounded"> - <xsd:element name="platform" type="sdk:platformType" /> - <xsd:element name="tool" type="sdk:toolType" /> - <xsd:element name="platform-tool" type="sdk:platformToolType" /> - <xsd:element name="doc" type="sdk:docType" /> - <xsd:element name="sample" type="sdk:sampleType" /> - <xsd:element name="extra" type="sdk:extraType" /> - <xsd:element name="license" type="sdk:licenseType" /> - </xsd:choice> - </xsd:complexType> - - <!-- The definition of an SDK platform package. --> - - <xsd:complexType name="platformType"> - <xsd:annotation> - <xsd:documentation>An SDK platform package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The Android platform version. It is string such as "1.0". --> - <xsd:element name="version" type="xsd:normalizedString" /> - <!-- The Android API Level for the platform. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- The optional codename for this platform, if it's a preview. --> - <xsd:element name="codename" type="xsd:string" minOccurs="0" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - <!-- The minimal revision of tools required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-tools-rev" type="xsd:positiveInteger" minOccurs="0" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK tool package. --> - - <xsd:complexType name="toolType" > - <xsd:annotation> - <xsd:documentation>An SDK tool package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - - <!-- The minimal revision of platform-tools required by this package. - Mandatory. Must be an int > 0. --> - <xsd:element name="min-platform-tools-rev" type="xsd:positiveInteger" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK platform-tool package. --> - - <xsd:complexType name="platformToolType" > - <xsd:annotation> - <xsd:documentation>An SDK platform-tool package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK doc package. --> - - <xsd:complexType name="docType" > - <xsd:annotation> - <xsd:documentation>An SDK doc package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The Android API Level for the documentation. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- The optional codename for this doc, if it's a preview. --> - <xsd:element name="codename" type="xsd:string" minOccurs="0" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK sample package. --> - - <xsd:complexType name="sampleType" > - <xsd:annotation> - <xsd:documentation>An SDK sample package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The Android API Level for the documentation. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- The optional codename for this doc, if it's a preview. --> - <xsd:element name="codename" type="xsd:string" minOccurs="0" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - <!-- The minimal revision of tools required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-tools-rev" type="xsd:positiveInteger" minOccurs="0" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK extra package. This kind of package is for - "free" content. Such packages are installed in SDK/vendor/path. - --> - - <xsd:complexType name="extraType" > - <xsd:annotation> - <xsd:documentation> - An SDK extra package. This kind of package is for "free" content. - Such packages are installed in SDK/vendor/path. - </xsd:documentation> - </xsd:annotation> - <xsd:all> - - <!-- The install path top folder name. - The segments "add-ons", "docs", "platforms", "platform-tools", "temp" - and "tools" are reserved and cannot be used. - --> - <xsd:element name="vendor" type="sdk:segmentType" /> - - <!-- The install path sub-folder name. --> - <xsd:element name="path" type="sdk:segmentType" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - <!-- The minimal revision of tools required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-tools-rev" type="xsd:positiveInteger" minOccurs="0" /> - <!-- The minimal API level required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-api-level" type="xsd:positiveInteger" minOccurs="0" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of a path segment used by the extra element. --> - - <xsd:simpleType name="segmentType"> - <xsd:annotation> - <xsd:documentation> - One path segment for the install path of an extra element. - It must be a single-segment path. - </xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:token"> - <xsd:pattern value="[a-zA-Z0-9_]+"/> - </xsd:restriction> - </xsd:simpleType> - - - <!-- The definition of a license to be referenced by the uses-license element. --> - - <xsd:complexType name="licenseType"> - <xsd:annotation> - <xsd:documentation> - A license definition. Such a license must be used later as a reference - using a uses-license element in one of the package elements. - </xsd:documentation> - </xsd:annotation> - <xsd:simpleContent> - <xsd:extension base="xsd:string"> - <xsd:attribute name="id" type="xsd:ID" /> - <xsd:attribute name="type" type="xsd:token" fixed="text" /> - </xsd:extension> - </xsd:simpleContent> - </xsd:complexType> - - - <!-- Type describing the license used by a package. - The license MUST be defined using a license node and referenced - using the ref attribute of the license element inside a package. - --> - - <xsd:complexType name="usesLicenseType"> - <xsd:annotation> - <xsd:documentation> - Describes the license used by a package. The license MUST be defined - using a license node and referenced using the ref attribute of the - license element inside a package. - </xsd:documentation> - </xsd:annotation> - <xsd:attribute name="ref" type="xsd:IDREF" /> - </xsd:complexType> - - - <!-- A collection of files that can be downloaded for a given architecture. - The <archives> node is mandatory in the repository elements and the - collection must have at least one <archive> declared. - Each archive is a zip file that will be unzipped in a location that depends - on its package type. - --> - - <xsd:complexType name="archivesType"> - <xsd:annotation> - <xsd:documentation> - A collection of files that can be downloaded for a given architecture. - The <archives> node is mandatory in the repository packages and the - collection must have at least one <archive> declared. - Each archive is a zip file that will be unzipped in a location that depends - on its package type. - </xsd:documentation> - </xsd:annotation> - <xsd:sequence minOccurs="1" maxOccurs="unbounded"> - <!-- One archive file --> - <xsd:element name="archive"> - <xsd:complexType> - <!-- Properties of the archive file --> - <xsd:all> - <!-- The size in bytes of the archive to download. --> - <xsd:element name="size" type="xsd:positiveInteger" /> - <!-- The checksum of the archive file. --> - <xsd:element name="checksum" type="sdk:checksumType" /> - <!-- The URL is an absolute URL if it starts with http://, https:// - or ftp://. Otherwise it is relative to the parent directory that - contains this repository.xml --> - <xsd:element name="url" type="xsd:token" /> - </xsd:all> - - <!-- Attributes that identify the OS and architecture --> - <xsd:attribute name="os" use="required"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="any" /> - <xsd:enumeration value="linux" /> - <xsd:enumeration value="macosx" /> - <xsd:enumeration value="windows" /> - </xsd:restriction> - </xsd:simpleType> - </xsd:attribute> - <xsd:attribute name="arch" use="optional"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="any" /> - <xsd:enumeration value="ppc" /> - <xsd:enumeration value="x86" /> - <xsd:enumeration value="x86_64" /> - </xsd:restriction> - </xsd:simpleType> - </xsd:attribute> - </xsd:complexType> - </xsd:element> - </xsd:sequence> - </xsd:complexType> - - - <!-- The definition of a file checksum --> - - <xsd:simpleType name="sha1Number"> - <xsd:annotation> - <xsd:documentation>A SHA1 checksum.</xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:string"> - <xsd:pattern value="([0-9a-fA-F]){40}"/> - </xsd:restriction> - </xsd:simpleType> - - <xsd:complexType name="checksumType"> - <xsd:annotation> - <xsd:documentation>A file checksum, currently only SHA1.</xsd:documentation> - </xsd:annotation> - <xsd:simpleContent> - <xsd:extension base="sdk:sha1Number"> - <xsd:attribute name="type" type="xsd:token" fixed="sha1" /> - </xsd:extension> - </xsd:simpleContent> - </xsd:complexType> - -</xsd:schema> diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-repository-4.xsd b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-repository-4.xsd deleted file mode 100755 index 9b14772..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-repository-4.xsd +++ /dev/null @@ -1,500 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<xsd:schema - targetNamespace="http://schemas.android.com/sdk/android/repository/4" - xmlns:xsd="http://www.w3.org/2001/XMLSchema" - xmlns:sdk="http://schemas.android.com/sdk/android/repository/4" - elementFormDefault="qualified" - attributeFormDefault="unqualified" - version="1"> - - <!-- The repository contains a collection of downloadable items known as - "packages". Each package has a type and various attributes and contains - a list of file "archives" that can be downloaded for specific OSes. - - An Android SDK repository is a web site that contains a "repository.xml" - file that conforms to this XML Schema. - - History: - - v1 is used by the SDK Updater in Tools r3 and r4. - - - v2 is used by the SDK Updater in Tools r5: - - It introduces a new <sample> repository type. Previously samples - were included in the <platform> packages. Instead this package is used - and and the samples are installed in $SDK/samples. - - All repository types have a new <obsolete> node. It works as a marker - to indicate the package is obsolete and should not be selected by default. - The UI also hides these out by default. - - - v3 is used by the SDK Updater in Tools r8: - - It introduces a new <platform-tool> repository type. Previously platform-specific - tools were included in the <platform> packages. Instead this package is used - and platform-specific tools are installed in $SDK/platform-tools - - There's a new element <min-platform-tools-rev> in <tool>. The tool package now - requires that at least some minimal version of <platform-tool> be installed. - - It removes the <addon> repository type, which is now in its own XML Schema. - - - v4 is used by the SDK Updater in Tools r12: - - <extra> element now has a <project-files> element that contains 1 or - or more <path>, each indicating the relative path of a file that this package - can contribute to installed projects. - - <platform> element now has a mandatory <layoutlib> that indicates the API - and revision of that layout library for this particular platform. - --> - - <xsd:element name="sdk-repository" type="sdk:repositoryType" /> - - <xsd:complexType name="repositoryType"> - <xsd:annotation> - <xsd:documentation> - The repository contains a collection of downloadable packages. - </xsd:documentation> - </xsd:annotation> - <xsd:choice minOccurs="0" maxOccurs="unbounded"> - <xsd:element name="platform" type="sdk:platformType" /> - <xsd:element name="tool" type="sdk:toolType" /> - <xsd:element name="platform-tool" type="sdk:platformToolType" /> - <xsd:element name="doc" type="sdk:docType" /> - <xsd:element name="sample" type="sdk:sampleType" /> - <xsd:element name="extra" type="sdk:extraType" /> - <xsd:element name="license" type="sdk:licenseType" /> - </xsd:choice> - </xsd:complexType> - - <!-- The definition of an SDK platform package. --> - - <xsd:complexType name="platformType"> - <xsd:annotation> - <xsd:documentation>An SDK platform package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The Android platform version. It is string such as "1.0". --> - <xsd:element name="version" type="xsd:normalizedString" /> - <!-- The Android API Level for the platform. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- The optional codename for this platform, if it's a preview. --> - <xsd:element name="codename" type="xsd:string" minOccurs="0" /> - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - - <!-- Information on the layoutlib packaged in this platform. --> - <xsd:element name="layoutlib" type="sdk:layoutlibType" /> - - <!-- optional elements --> - - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - <!-- The minimal revision of tools required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-tools-rev" type="xsd:positiveInteger" minOccurs="0" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of a layout library used by a platform. --> - - <xsd:complexType name="layoutlibType" > - <xsd:annotation> - <xsd:documentation> - Version information for a layoutlib included in a platform. - </xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The layoutlib API level, an int > 0, - incremented with each new incompatible lib. --> - <xsd:element name="api" type="xsd:positiveInteger" /> - <!-- The incremental minor revision for that API, e.g. in case of bug fixes. - Optional. An int >= 0, assumed to be 0 if the element is missing. --> - <xsd:element name="revision" type="xsd:nonNegativeInteger" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK tool package. --> - - <xsd:complexType name="toolType" > - <xsd:annotation> - <xsd:documentation>An SDK tool package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - - <!-- The minimal revision of platform-tools required by this package. - Mandatory. Must be an int > 0. --> - <xsd:element name="min-platform-tools-rev" type="xsd:positiveInteger" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK platform-tool package. --> - - <xsd:complexType name="platformToolType" > - <xsd:annotation> - <xsd:documentation>An SDK platform-tool package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK doc package. --> - - <xsd:complexType name="docType" > - <xsd:annotation> - <xsd:documentation>An SDK doc package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The Android API Level for the documentation. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- The optional codename for this doc, if it's a preview. --> - <xsd:element name="codename" type="xsd:string" minOccurs="0" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK sample package. --> - - <xsd:complexType name="sampleType" > - <xsd:annotation> - <xsd:documentation>An SDK sample package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The Android API Level for the documentation. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- The optional codename for this doc, if it's a preview. --> - <xsd:element name="codename" type="xsd:string" minOccurs="0" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - <!-- The minimal revision of tools required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-tools-rev" type="xsd:positiveInteger" minOccurs="0" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK extra package. This kind of package is for - "free" content. Such packages are installed in SDK/vendor/path. - - Important implementation detail: this element is duplicated in the - sdk-addon-N.xsd schema and must be kept in sync there. This is - simpler than trying to use some kind of of include or to request - that clients use a third XML schema for common parts. - --> - - <xsd:complexType name="extraType" > - <xsd:annotation> - <xsd:documentation> - An SDK extra package. This kind of package is for "free" content. - Such packages are installed in SDK/vendor/path. - </xsd:documentation> - </xsd:annotation> - <xsd:all> - - <!-- The install path top folder name. - The segments "add-ons", "docs", "platforms", "platform-tools", "temp" - and "tools" are reserved and cannot be used. - --> - <xsd:element name="vendor" type="sdk:segmentType" /> - - <!-- The install path sub-folder name. --> - <xsd:element name="path" type="sdk:segmentType" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - <!-- optional elements --> - - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- The minimal revision of tools required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-tools-rev" type="xsd:positiveInteger" minOccurs="0" /> - <!-- The minimal API level required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-api-level" type="xsd:positiveInteger" minOccurs="0" /> - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - - <!-- A list of project files contributed by this package. Optional. --> - <xsd:element name="project-files" type="sdk:projectFilesType" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of a path segment used by the extra element. --> - - <xsd:simpleType name="segmentType"> - <xsd:annotation> - <xsd:documentation> - One path segment for the install path of an extra element. - It must be a single-segment path. - </xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:token"> - <xsd:pattern value="[a-zA-Z0-9_]+"/> - </xsd:restriction> - </xsd:simpleType> - - - <!-- The definition of a license to be referenced by the uses-license element. --> - - <xsd:complexType name="licenseType"> - <xsd:annotation> - <xsd:documentation> - A license definition. Such a license must be used later as a reference - using a uses-license element in one of the package elements. - </xsd:documentation> - </xsd:annotation> - <xsd:simpleContent> - <xsd:extension base="xsd:string"> - <xsd:attribute name="id" type="xsd:ID" /> - <xsd:attribute name="type" type="xsd:token" fixed="text" /> - </xsd:extension> - </xsd:simpleContent> - </xsd:complexType> - - - <!-- Type describing the license used by a package. - The license MUST be defined using a license node and referenced - using the ref attribute of the license element inside a package. - --> - - <xsd:complexType name="usesLicenseType"> - <xsd:annotation> - <xsd:documentation> - Describes the license used by a package. The license MUST be defined - using a license node and referenced using the ref attribute of the - license element inside a package. - </xsd:documentation> - </xsd:annotation> - <xsd:attribute name="ref" type="xsd:IDREF" /> - </xsd:complexType> - - - <!-- A collection of files that can be downloaded for a given architecture. - The <archives> node is mandatory in the repository elements and the - collection must have at least one <archive> declared. - Each archive is a zip file that will be unzipped in a location that depends - on its package type. - --> - - <xsd:complexType name="archivesType"> - <xsd:annotation> - <xsd:documentation> - A collection of files that can be downloaded for a given architecture. - The <archives> node is mandatory in the repository packages and the - collection must have at least one <archive> declared. - Each archive is a zip file that will be unzipped in a location that depends - on its package type. - </xsd:documentation> - </xsd:annotation> - <xsd:sequence minOccurs="1" maxOccurs="unbounded"> - <!-- One archive file --> - <xsd:element name="archive"> - <xsd:complexType> - <!-- Properties of the archive file --> - <xsd:all> - <!-- The size in bytes of the archive to download. --> - <xsd:element name="size" type="xsd:positiveInteger" /> - <!-- The checksum of the archive file. --> - <xsd:element name="checksum" type="sdk:checksumType" /> - <!-- The URL is an absolute URL if it starts with http://, https:// - or ftp://. Otherwise it is relative to the parent directory that - contains this repository.xml --> - <xsd:element name="url" type="xsd:token" /> - </xsd:all> - - <!-- Attributes that identify the OS and architecture --> - <xsd:attribute name="os" use="required"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="any" /> - <xsd:enumeration value="linux" /> - <xsd:enumeration value="macosx" /> - <xsd:enumeration value="windows" /> - </xsd:restriction> - </xsd:simpleType> - </xsd:attribute> - <xsd:attribute name="arch" use="optional"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="any" /> - <xsd:enumeration value="ppc" /> - <xsd:enumeration value="x86" /> - <xsd:enumeration value="x86_64" /> - </xsd:restriction> - </xsd:simpleType> - </xsd:attribute> - </xsd:complexType> - </xsd:element> - </xsd:sequence> - </xsd:complexType> - - - <!-- A collection of file paths available in an <extra> package - that can be installed in an Android project. - If present, the <project-files> collection must contain at least one path. - Each path is relative to the root directory of the package. - --> - - <xsd:complexType name="projectFilesType"> - <xsd:annotation> - <xsd:documentation> - A collection of file paths available in an <extra> package - that can be installed in an Android project. - If present, the <project-files> collection must contain at least one path. - Each path is relative to the root directory of the package. - </xsd:documentation> - </xsd:annotation> - <xsd:sequence minOccurs="1" maxOccurs="unbounded"> - <!-- One JAR Path, relative to the root folder of the package. --> - <xsd:element name="path" type="xsd:string" /> - </xsd:sequence> - </xsd:complexType> - - - <!-- The definition of a file checksum --> - - <xsd:simpleType name="sha1Number"> - <xsd:annotation> - <xsd:documentation>A SHA1 checksum.</xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:string"> - <xsd:pattern value="([0-9a-fA-F]){40}"/> - </xsd:restriction> - </xsd:simpleType> - - <xsd:complexType name="checksumType"> - <xsd:annotation> - <xsd:documentation>A file checksum, currently only SHA1.</xsd:documentation> - </xsd:annotation> - <xsd:simpleContent> - <xsd:extension base="sdk:sha1Number"> - <xsd:attribute name="type" type="xsd:token" fixed="sha1" /> - </xsd:extension> - </xsd:simpleContent> - </xsd:complexType> - -</xsd:schema> diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-repository-5.xsd b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-repository-5.xsd deleted file mode 100755 index ae8275f..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-repository-5.xsd +++ /dev/null @@ -1,624 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<xsd:schema - targetNamespace="http://schemas.android.com/sdk/android/repository/5" - xmlns:xsd="http://www.w3.org/2001/XMLSchema" - xmlns:sdk="http://schemas.android.com/sdk/android/repository/5" - elementFormDefault="qualified" - attributeFormDefault="unqualified" - version="1"> - - <!-- The repository contains a collection of downloadable items known as - "packages". Each package has a type and various attributes and contains - a list of file "archives" that can be downloaded for specific OSes. - - An Android SDK repository is a web site that contains a "repository.xml" - file that conforms to this XML Schema. - - History: - - v1 is used by the SDK Updater in Tools r3 and r4. - - - v2 is used by the SDK Updater in Tools r5: - - It introduces a new <sample> repository type. Previously samples - were included in the <platform> packages. Instead this package is used - and and the samples are installed in $SDK/samples. - - All repository types have a new <obsolete> node. It works as a marker - to indicate the package is obsolete and should not be selected by default. - The UI also hides these out by default. - - - v3 is used by the SDK Updater in Tools r8: - - It introduces a new <platform-tool> repository type. Previously platform-specific - tools were included in the <platform> packages. Instead this package is used - and platform-specific tools are installed in $SDK/platform-tools - - There's a new element <min-platform-tools-rev> in <tool>. The tool package now - requires that at least some minimal version of <platform-tool> be installed. - - It removes the <addon> repository type, which is now in its own XML Schema. - - - v4 is used by the SDK Updater in Tools r12: - - <extra> element now has a <project-files> element that contains 1 or - or more <path>, each indicating the relative path of a file that this package - can contribute to installed projects. - - <platform> element now has a mandatory <layoutlib> that indicates the API - and revision of that layout library for this particular platform. - - - v5 is used by the SDK Updater in Tools R14: - - <extra> now has an <old-paths> element, a ;-separated list of old paths that - should be detected and migrated to the new <path> for that package. - - <platform> has a new optional <abi-included> that describes the ABI of the - system image included in the platform, if any. - - New <system-image> package type, to store system images outside of <platform>s. - - New <source> package type. - --> - - <xsd:element name="sdk-repository" type="sdk:repositoryType" /> - - <xsd:complexType name="repositoryType"> - <xsd:annotation> - <xsd:documentation> - The repository contains a collection of downloadable packages. - </xsd:documentation> - </xsd:annotation> - <xsd:choice minOccurs="0" maxOccurs="unbounded"> - <xsd:element name="platform" type="sdk:platformType" /> - <xsd:element name="system-image" type="sdk:systemImageType" /> - <xsd:element name="source" type="sdk:sourceType" /> - <xsd:element name="tool" type="sdk:toolType" /> - <xsd:element name="platform-tool" type="sdk:platformToolType" /> - <xsd:element name="doc" type="sdk:docType" /> - <xsd:element name="sample" type="sdk:sampleType" /> - <xsd:element name="extra" type="sdk:extraType" /> - <xsd:element name="license" type="sdk:licenseType" /> - </xsd:choice> - </xsd:complexType> - - <!-- The definition of an SDK platform package. --> - - <xsd:complexType name="platformType"> - <xsd:annotation> - <xsd:documentation>An SDK platform package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The Android platform version. It is string such as "1.0". --> - <xsd:element name="version" type="xsd:normalizedString" /> - <!-- The Android API Level for the platform. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- The optional codename for this platform, if it's a preview. --> - <xsd:element name="codename" type="xsd:string" minOccurs="0" /> - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - - <!-- Information on the layoutlib packaged in this platform. --> - <xsd:element name="layoutlib" type="sdk:layoutlibType" /> - - <!-- optional elements --> - - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - <!-- The minimal revision of tools required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-tools-rev" type="xsd:positiveInteger" minOccurs="0" /> - - <!-- The ABI of the system image *included* in this platform, if any. - When the field is present, it means the platform already embeds one - system image. A platform can also have any number of external - <system-image> associated with it. --> - <xsd:element name="included-abi" type="sdk:abiType" minOccurs="0" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of a layout library used by a platform. --> - - <xsd:complexType name="layoutlibType" > - <xsd:annotation> - <xsd:documentation> - Version information for a layoutlib included in a platform. - </xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The layoutlib API level, an int > 0, - incremented with each new incompatible lib. --> - <xsd:element name="api" type="xsd:positiveInteger" /> - <!-- The incremental minor revision for that API, e.g. in case of bug fixes. - Optional. An int >= 0, assumed to be 0 if the element is missing. --> - <xsd:element name="revision" type="xsd:nonNegativeInteger" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of a system image used by a platform. --> - - <xsd:complexType name="systemImageType" > - <xsd:annotation> - <xsd:documentation> - System Image for a platform. - </xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- api-level + codename identifies the platform to which this system image belongs. --> - - <!-- The Android API Level for the platform. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- The optional codename for this platform, if it's a preview. --> - <xsd:element name="codename" type="xsd:string" minOccurs="0" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - - <!-- The ABI of the system emulated by this image. --> - <xsd:element name="abi" type="sdk:abiType" /> - - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - </xsd:all> - </xsd:complexType> - - <!-- The definition of the ABI supported by a platform's system image. --> - - <xsd:simpleType name="abiType"> - <xsd:annotation> - <xsd:documentation>The ABI of a platform's system image.</xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="armeabi" /> - <xsd:enumeration value="armeabi-v7a" /> - <xsd:enumeration value="x86" /> - </xsd:restriction> - </xsd:simpleType> - - - <!-- The definition of a source package. --> - - <xsd:complexType name="sourceType" > - <xsd:annotation> - <xsd:documentation> - Sources for a platform. - </xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- api-level + codename identifies the platform to which this source belongs. --> - - <!-- The Android API Level for the platform. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- The optional codename for this platform, if it's a preview. --> - <xsd:element name="codename" type="xsd:string" minOccurs="0" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK tool package. --> - - <xsd:complexType name="toolType" > - <xsd:annotation> - <xsd:documentation>An SDK tool package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - - <!-- The minimal revision of platform-tools required by this package. - Mandatory. Must be an int > 0. --> - <xsd:element name="min-platform-tools-rev" type="xsd:positiveInteger" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK platform-tool package. --> - - <xsd:complexType name="platformToolType" > - <xsd:annotation> - <xsd:documentation>An SDK platform-tool package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK doc package. --> - - <xsd:complexType name="docType" > - <xsd:annotation> - <xsd:documentation>An SDK doc package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The Android API Level for the documentation. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- The optional codename for this doc, if it's a preview. --> - <xsd:element name="codename" type="xsd:string" minOccurs="0" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK sample package. --> - - <xsd:complexType name="sampleType" > - <xsd:annotation> - <xsd:documentation>An SDK sample package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The Android API Level for the documentation. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- The optional codename for this doc, if it's a preview. --> - <xsd:element name="codename" type="xsd:string" minOccurs="0" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - <!-- The minimal revision of tools required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-tools-rev" type="xsd:positiveInteger" minOccurs="0" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK extra package. This kind of package is for - "free" content. Such packages are installed in SDK/vendor/path. - - Important implementation detail: this element is duplicated in the - sdk-addon-N.xsd schema and must be kept in sync there. This is - simpler than trying to use some kind of of include or to request - that clients use a third XML schema for common parts. - --> - - <xsd:complexType name="extraType" > - <xsd:annotation> - <xsd:documentation> - An SDK extra package. This kind of package is for "free" content. - Such packages are installed in SDK/vendor/path. - </xsd:documentation> - </xsd:annotation> - <xsd:all> - - <!-- The install path top folder name. - The segments "add-ons", "docs", "platforms", "platform-tools", "temp" - and "tools" are reserved and cannot be used. - --> - <xsd:element name="vendor" type="sdk:segmentType" /> - - <!-- The install path sub-folder name. --> - <xsd:element name="path" type="sdk:segmentType" /> - - <!-- A semi-colon separated list of "obsolete" path names which are equivalent - to the current 'path' name. When a package is seen using an old-paths' name, - the package manager will try to upgrade it to the new path. --> - <xsd:element name="old-paths" type="sdk:segmentListType" minOccurs="0" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - <!-- optional elements --> - - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- The minimal revision of tools required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-tools-rev" type="xsd:positiveInteger" minOccurs="0" /> - <!-- The minimal API level required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-api-level" type="xsd:positiveInteger" minOccurs="0" /> - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - - <!-- A list of project files contributed by this package. Optional. --> - <xsd:element name="project-files" type="sdk:projectFilesType" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of a path segment used by the extra element. --> - - <xsd:simpleType name="segmentType"> - <xsd:annotation> - <xsd:documentation> - One path segment for the install path of an extra element. - It must be a single-segment path. - </xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:token"> - <xsd:pattern value="[a-zA-Z0-9_]+"/> - </xsd:restriction> - </xsd:simpleType> - - <xsd:simpleType name="segmentListType"> - <xsd:annotation> - <xsd:documentation> - A semi-colon separated list of a segmentTypes. - </xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:token"> - <xsd:pattern value="[a-zA-Z0-9_;]+"/> - </xsd:restriction> - </xsd:simpleType> - - - <!-- The definition of a license to be referenced by the uses-license element. --> - - <xsd:complexType name="licenseType"> - <xsd:annotation> - <xsd:documentation> - A license definition. Such a license must be used later as a reference - using a uses-license element in one of the package elements. - </xsd:documentation> - </xsd:annotation> - <xsd:simpleContent> - <xsd:extension base="xsd:string"> - <xsd:attribute name="id" type="xsd:ID" /> - <xsd:attribute name="type" type="xsd:token" fixed="text" /> - </xsd:extension> - </xsd:simpleContent> - </xsd:complexType> - - - <!-- Type describing the license used by a package. - The license MUST be defined using a license node and referenced - using the ref attribute of the license element inside a package. - --> - - <xsd:complexType name="usesLicenseType"> - <xsd:annotation> - <xsd:documentation> - Describes the license used by a package. The license MUST be defined - using a license node and referenced using the ref attribute of the - license element inside a package. - </xsd:documentation> - </xsd:annotation> - <xsd:attribute name="ref" type="xsd:IDREF" /> - </xsd:complexType> - - - <!-- A collection of files that can be downloaded for a given architecture. - The <archives> node is mandatory in the repository elements and the - collection must have at least one <archive> declared. - Each archive is a zip file that will be unzipped in a location that depends - on its package type. - --> - - <xsd:complexType name="archivesType"> - <xsd:annotation> - <xsd:documentation> - A collection of files that can be downloaded for a given architecture. - The <archives> node is mandatory in the repository packages and the - collection must have at least one <archive> declared. - Each archive is a zip file that will be unzipped in a location that depends - on its package type. - </xsd:documentation> - </xsd:annotation> - <xsd:sequence minOccurs="1" maxOccurs="unbounded"> - <!-- One archive file --> - <xsd:element name="archive"> - <xsd:complexType> - <!-- Properties of the archive file --> - <xsd:all> - <!-- The size in bytes of the archive to download. --> - <xsd:element name="size" type="xsd:positiveInteger" /> - <!-- The checksum of the archive file. --> - <xsd:element name="checksum" type="sdk:checksumType" /> - <!-- The URL is an absolute URL if it starts with http://, https:// - or ftp://. Otherwise it is relative to the parent directory that - contains this repository.xml --> - <xsd:element name="url" type="xsd:token" /> - </xsd:all> - - <!-- Attributes that identify the OS and architecture --> - <xsd:attribute name="os" use="required"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="any" /> - <xsd:enumeration value="linux" /> - <xsd:enumeration value="macosx" /> - <xsd:enumeration value="windows" /> - </xsd:restriction> - </xsd:simpleType> - </xsd:attribute> - <xsd:attribute name="arch" use="optional"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="any" /> - <xsd:enumeration value="ppc" /> - <xsd:enumeration value="x86" /> - <xsd:enumeration value="x86_64" /> - </xsd:restriction> - </xsd:simpleType> - </xsd:attribute> - </xsd:complexType> - </xsd:element> - </xsd:sequence> - </xsd:complexType> - - - <!-- A collection of file paths available in an <extra> package - that can be installed in an Android project. - If present, the <project-files> collection must contain at least one path. - Each path is relative to the root directory of the package. - --> - - <xsd:complexType name="projectFilesType"> - <xsd:annotation> - <xsd:documentation> - A collection of file paths available in an <extra> package - that can be installed in an Android project. - If present, the <project-files> collection must contain at least one path. - Each path is relative to the root directory of the package. - </xsd:documentation> - </xsd:annotation> - <xsd:sequence minOccurs="1" maxOccurs="unbounded"> - <!-- One JAR Path, relative to the root folder of the package. --> - <xsd:element name="path" type="xsd:string" /> - </xsd:sequence> - </xsd:complexType> - - - <!-- The definition of a file checksum --> - - <xsd:simpleType name="sha1Number"> - <xsd:annotation> - <xsd:documentation>A SHA1 checksum.</xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:string"> - <xsd:pattern value="([0-9a-fA-F]){40}"/> - </xsd:restriction> - </xsd:simpleType> - - <xsd:complexType name="checksumType"> - <xsd:annotation> - <xsd:documentation>A file checksum, currently only SHA1.</xsd:documentation> - </xsd:annotation> - <xsd:simpleContent> - <xsd:extension base="sdk:sha1Number"> - <xsd:attribute name="type" type="xsd:token" fixed="sha1" /> - </xsd:extension> - </xsd:simpleContent> - </xsd:complexType> - -</xsd:schema> diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-repository-6.xsd b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-repository-6.xsd deleted file mode 100755 index bccce69..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-repository-6.xsd +++ /dev/null @@ -1,608 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<xsd:schema - targetNamespace="http://schemas.android.com/sdk/android/repository/6" - xmlns:xsd="http://www.w3.org/2001/XMLSchema" - xmlns:sdk="http://schemas.android.com/sdk/android/repository/6" - elementFormDefault="qualified" - attributeFormDefault="unqualified" - version="1"> - - <!-- The repository contains a collection of downloadable items known as - "packages". Each package has a type and various attributes and contains - a list of file "archives" that can be downloaded for specific OSes. - - An Android SDK repository is a web site that contains a "repository.xml" - file that conforms to this XML Schema. - - History: - - v1 is used by the SDK Updater in Tools r3 and r4. - - - v2 is used by the SDK Updater in Tools r5: - - It introduces a new <sample> repository type. Previously samples - were included in the <platform> packages. Instead this package is used - and and the samples are installed in $SDK/samples. - - All repository types have a new <obsolete> node. It works as a marker - to indicate the package is obsolete and should not be selected by default. - The UI also hides these out by default. - - - v3 is used by the SDK Updater in Tools r8: - - It introduces a new <platform-tool> repository type. Previously platform-specific - tools were included in the <platform> packages. Instead this package is used - and platform-specific tools are installed in $SDK/platform-tools - - There's a new element <min-platform-tools-rev> in <tool>. The tool package now - requires that at least some minimal version of <platform-tool> be installed. - - It removes the <addon> repository type, which is now in its own XML Schema. - - - v4 is used by the SDK Updater in Tools r12: - - <extra> element now has a <project-files> element that contains 1 or - or more <path>, each indicating the relative path of a file that this package - can contribute to installed projects. - - <platform> element now has a mandatory <layoutlib> that indicates the API - and revision of that layout library for this particular platform. - - - v5 is used by the SDK Manager in Tools r14: - - <extra> now has an <old-paths> element, a ;-separated list of old paths that - should be detected and migrated to the new <path> for that package. - - <platform> has a new optional <abi-included> that describes the ABI of the - system image included in the platform, if any. - - New <system-image> package type, to store system images outside of <platform>s. - - New <source> package type. - - - v6 is used by the SDK Manager in Tools r18: - - <extra> packages are removed. They are served only by the addon XML. - - <platform>, <system-image>, <source>, <tool>, <platform-tool>, <doc> - and <sample> get a new optional field <beta-rc> which can be used to indicate - the package is a Beta Release Candidate and not a final release. - --> - - <xsd:element name="sdk-repository" type="sdk:repositoryType" /> - - <xsd:complexType name="repositoryType"> - <xsd:annotation> - <xsd:documentation> - The repository contains a collection of downloadable packages. - </xsd:documentation> - </xsd:annotation> - <xsd:choice minOccurs="0" maxOccurs="unbounded"> - <xsd:element name="platform" type="sdk:platformType" /> - <xsd:element name="system-image" type="sdk:systemImageType" /> - <xsd:element name="source" type="sdk:sourceType" /> - <xsd:element name="tool" type="sdk:toolType" /> - <xsd:element name="platform-tool" type="sdk:platformToolType" /> - <xsd:element name="doc" type="sdk:docType" /> - <xsd:element name="sample" type="sdk:sampleType" /> - <xsd:element name="license" type="sdk:licenseType" /> - </xsd:choice> - </xsd:complexType> - - <!-- The definition of an SDK platform package. --> - - <xsd:complexType name="platformType"> - <xsd:annotation> - <xsd:documentation>An SDK platform package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The Android platform version. It is string such as "1.0". --> - <xsd:element name="version" type="xsd:normalizedString" /> - <!-- The Android API Level for the platform. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- The optional codename for this platform, if it's a preview. --> - <xsd:element name="codename" type="xsd:string" minOccurs="0" /> - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - - <!-- Information on the layoutlib packaged in this platform. --> - <xsd:element name="layoutlib" type="sdk:layoutlibType" /> - - <!-- optional elements --> - - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - <!-- The minimal revision of tools required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-tools-rev" type="xsd:positiveInteger" minOccurs="0" /> - - <!-- The ABI of the system image *included* in this platform, if any. - When the field is present, it means the platform already embeds one - system image. A platform can also have any number of external - <system-image> associated with it. --> - <xsd:element name="included-abi" type="sdk:abiType" minOccurs="0" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - - <!-- An optional element indicating the package is a beta/preview. - When present, it indicates the release-candidate number. - When the element is absent, it indicates this is a released package. --> - <xsd:element name="beta-rc" type="xsd:positiveInteger" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of a layout library used by a platform. --> - - <xsd:complexType name="layoutlibType" > - <xsd:annotation> - <xsd:documentation> - Version information for a layoutlib included in a platform. - </xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The layoutlib API level, an int > 0, - incremented with each new incompatible lib. --> - <xsd:element name="api" type="xsd:positiveInteger" /> - <!-- The incremental minor revision for that API, e.g. in case of bug fixes. - Optional. An int >= 0, assumed to be 0 if the element is missing. --> - <xsd:element name="revision" type="xsd:nonNegativeInteger" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of a system image used by a platform. --> - - <xsd:complexType name="systemImageType" > - <xsd:annotation> - <xsd:documentation> - System Image for a platform. - </xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- api-level + codename identifies the platform to which this system image belongs. --> - - <!-- The Android API Level for the platform. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- The optional codename for this platform, if it's a preview. --> - <xsd:element name="codename" type="xsd:string" minOccurs="0" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - - <!-- The ABI of the system emulated by this image. --> - <xsd:element name="abi" type="sdk:abiType" /> - - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - - <!-- An optional element indicating the package is a beta/preview. - When present, it indicates the release-candidate number. - When the element is absent, it indicates this is a released package. --> - <xsd:element name="beta-rc" type="xsd:positiveInteger" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - <!-- The definition of the ABI supported by a platform's system image. --> - - <xsd:simpleType name="abiType"> - <xsd:annotation> - <xsd:documentation>The ABI of a platform's system image.</xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="armeabi" /> - <xsd:enumeration value="armeabi-v7a" /> - <xsd:enumeration value="x86" /> - <xsd:enumeration value="mips" /> - </xsd:restriction> - </xsd:simpleType> - - - <!-- The definition of a source package. --> - - <xsd:complexType name="sourceType" > - <xsd:annotation> - <xsd:documentation> - Sources for a platform. - </xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- api-level + codename identifies the platform to which this source belongs. --> - - <!-- The Android API Level for the platform. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- The optional codename for this platform, if it's a preview. --> - <xsd:element name="codename" type="xsd:string" minOccurs="0" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - - <!-- An optional element indicating the package is a beta/preview. - When present, it indicates the release-candidate number. - When the element is absent, it indicates this is a released package. --> - <xsd:element name="beta-rc" type="xsd:positiveInteger" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK tool package. --> - - <xsd:complexType name="toolType" > - <xsd:annotation> - <xsd:documentation>An SDK tool package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - <!-- The minimal revision of platform-tools required by this package. - Mandatory. Must be an int > 0. --> - <xsd:element name="min-platform-tools-rev" type="xsd:positiveInteger" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - - <!-- An optional element indicating the package is a beta/preview. - When present, it indicates the release-candidate number. - When the element is absent, it indicates this is a released package. --> - <xsd:element name="beta-rc" type="xsd:positiveInteger" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK platform-tool package. --> - - <xsd:complexType name="platformToolType" > - <xsd:annotation> - <xsd:documentation>An SDK platform-tool package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - - <!-- An optional element indicating the package is a beta/preview. - When present, it indicates the release-candidate number. - When the element is absent, it indicates this is a released package. --> - <xsd:element name="beta-rc" type="xsd:positiveInteger" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK doc package. --> - - <xsd:complexType name="docType" > - <xsd:annotation> - <xsd:documentation>An SDK doc package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The Android API Level for the documentation. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- The optional codename for this doc, if it's a preview. --> - <xsd:element name="codename" type="xsd:string" minOccurs="0" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - - <!-- An optional element indicating the package is a beta/preview. - When present, it indicates the release-candidate number. - When the element is absent, it indicates this is a released package. --> - <xsd:element name="beta-rc" type="xsd:positiveInteger" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK sample package. --> - - <xsd:complexType name="sampleType" > - <xsd:annotation> - <xsd:documentation>An SDK sample package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The Android API Level for the documentation. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- The optional codename for this doc, if it's a preview. --> - <xsd:element name="codename" type="xsd:string" minOccurs="0" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - <!-- The minimal revision of tools required by this package. - Optional. If present, must be an int > 0. --> - <xsd:element name="min-tools-rev" type="xsd:positiveInteger" minOccurs="0" /> - - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - - <!-- An optional element indicating the package is a beta/preview. - When present, it indicates the release-candidate number. - When the element is absent, it indicates this is a released package. --> - <xsd:element name="beta-rc" type="xsd:positiveInteger" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of a path segment used by the extra element. --> - - <xsd:simpleType name="segmentType"> - <xsd:annotation> - <xsd:documentation> - One path segment for the install path of an extra element. - It must be a single-segment path. - </xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:token"> - <xsd:pattern value="[a-zA-Z0-9_]+"/> - </xsd:restriction> - </xsd:simpleType> - - <xsd:simpleType name="segmentListType"> - <xsd:annotation> - <xsd:documentation> - A semi-colon separated list of a segmentTypes. - </xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:token"> - <xsd:pattern value="[a-zA-Z0-9_;]+"/> - </xsd:restriction> - </xsd:simpleType> - - - <!-- The definition of a license to be referenced by the uses-license element. --> - - <xsd:complexType name="licenseType"> - <xsd:annotation> - <xsd:documentation> - A license definition. Such a license must be used later as a reference - using a uses-license element in one of the package elements. - </xsd:documentation> - </xsd:annotation> - <xsd:simpleContent> - <xsd:extension base="xsd:string"> - <xsd:attribute name="id" type="xsd:ID" /> - <xsd:attribute name="type" type="xsd:token" fixed="text" /> - </xsd:extension> - </xsd:simpleContent> - </xsd:complexType> - - - <!-- Type describing the license used by a package. - The license MUST be defined using a license node and referenced - using the ref attribute of the license element inside a package. - --> - - <xsd:complexType name="usesLicenseType"> - <xsd:annotation> - <xsd:documentation> - Describes the license used by a package. The license MUST be defined - using a license node and referenced using the ref attribute of the - license element inside a package. - </xsd:documentation> - </xsd:annotation> - <xsd:attribute name="ref" type="xsd:IDREF" /> - </xsd:complexType> - - - <!-- A collection of files that can be downloaded for a given architecture. - The <archives> node is mandatory in the repository elements and the - collection must have at least one <archive> declared. - Each archive is a zip file that will be unzipped in a location that depends - on its package type. - --> - - <xsd:complexType name="archivesType"> - <xsd:annotation> - <xsd:documentation> - A collection of files that can be downloaded for a given architecture. - The <archives> node is mandatory in the repository packages and the - collection must have at least one <archive> declared. - Each archive is a zip file that will be unzipped in a location that depends - on its package type. - </xsd:documentation> - </xsd:annotation> - <xsd:sequence minOccurs="1" maxOccurs="unbounded"> - <!-- One archive file --> - <xsd:element name="archive"> - <xsd:complexType> - <!-- Properties of the archive file --> - <xsd:all> - <!-- The size in bytes of the archive to download. --> - <xsd:element name="size" type="xsd:positiveInteger" /> - <!-- The checksum of the archive file. --> - <xsd:element name="checksum" type="sdk:checksumType" /> - <!-- The URL is an absolute URL if it starts with http://, https:// - or ftp://. Otherwise it is relative to the parent directory that - contains this repository.xml --> - <xsd:element name="url" type="xsd:token" /> - </xsd:all> - - <!-- Attributes that identify the OS and architecture --> - <xsd:attribute name="os" use="required"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="any" /> - <xsd:enumeration value="linux" /> - <xsd:enumeration value="macosx" /> - <xsd:enumeration value="windows" /> - </xsd:restriction> - </xsd:simpleType> - </xsd:attribute> - <xsd:attribute name="arch" use="optional"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="any" /> - <xsd:enumeration value="ppc" /> - <xsd:enumeration value="x86" /> - <xsd:enumeration value="x86_64" /> - </xsd:restriction> - </xsd:simpleType> - </xsd:attribute> - </xsd:complexType> - </xsd:element> - </xsd:sequence> - </xsd:complexType> - - - <!-- A collection of file paths available in an <extra> package - that can be installed in an Android project. - If present, the <project-files> collection must contain at least one path. - Each path is relative to the root directory of the package. - --> - - <xsd:complexType name="projectFilesType"> - <xsd:annotation> - <xsd:documentation> - A collection of file paths available in an <extra> package - that can be installed in an Android project. - If present, the <project-files> collection must contain at least one path. - Each path is relative to the root directory of the package. - </xsd:documentation> - </xsd:annotation> - <xsd:sequence minOccurs="1" maxOccurs="unbounded"> - <!-- One JAR Path, relative to the root folder of the package. --> - <xsd:element name="path" type="xsd:string" /> - </xsd:sequence> - </xsd:complexType> - - - <!-- The definition of a file checksum --> - - <xsd:simpleType name="sha1Number"> - <xsd:annotation> - <xsd:documentation>A SHA1 checksum.</xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:string"> - <xsd:pattern value="([0-9a-fA-F]){40}"/> - </xsd:restriction> - </xsd:simpleType> - - <xsd:complexType name="checksumType"> - <xsd:annotation> - <xsd:documentation>A file checksum, currently only SHA1.</xsd:documentation> - </xsd:annotation> - <xsd:simpleContent> - <xsd:extension base="sdk:sha1Number"> - <xsd:attribute name="type" type="xsd:token" fixed="sha1" /> - </xsd:extension> - </xsd:simpleContent> - </xsd:complexType> - -</xsd:schema> diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-repository-7.xsd b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-repository-7.xsd deleted file mode 100755 index ea18070..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-repository-7.xsd +++ /dev/null @@ -1,612 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<xsd:schema - targetNamespace="http://schemas.android.com/sdk/android/repository/7" - xmlns:xsd="http://www.w3.org/2001/XMLSchema" - xmlns:sdk="http://schemas.android.com/sdk/android/repository/7" - elementFormDefault="qualified" - attributeFormDefault="unqualified" - version="1"> - - <!-- The repository contains a collection of downloadable items known as - "packages". Each package has a type and various attributes and contains - a list of file "archives" that can be downloaded for specific OSes. - - An Android SDK repository is a web site that contains a "repository.xml" - file that conforms to this XML Schema. - - History: - - v1 is used by the SDK Updater in Tools r3 and r4. - - - v2 is used by the SDK Updater in Tools r5: - - It introduces a new <sample> repository type. Previously samples - were included in the <platform> packages. Instead this package is used - and and the samples are installed in $SDK/samples. - - All repository types have a new <obsolete> node. It works as a marker - to indicate the package is obsolete and should not be selected by default. - The UI also hides these out by default. - - - v3 is used by the SDK Updater in Tools r8: - - It introduces a new <platform-tool> repository type. Previously platform-specific - tools were included in the <platform> packages. Instead this package is used - and platform-specific tools are installed in $SDK/platform-tools - - There's a new element <min-platform-tools-rev> in <tool>. The tool package now - requires that at least some minimal version of <platform-tool> be installed. - - It removes the <addon> repository type, which is now in its own XML Schema. - - - v4 is used by the SDK Updater in Tools r12: - - <extra> element now has a <project-files> element that contains 1 or - or more <path>, each indicating the relative path of a file that this package - can contribute to installed projects. - - <platform> element now has a mandatory <layoutlib> that indicates the API - and revision of that layout library for this particular platform. - - - v5 is used by the SDK Manager in Tools r14: - - <extra> now has an <old-paths> element, a ;-separated list of old paths that - should be detected and migrated to the new <path> for that package. - - <platform> has a new optional <abi-included> that describes the ABI of the - system image included in the platform, if any. - - New <system-image> package type, to store system images outside of <platform>s. - - New <source> package type. - - - v6 is used by the SDK Manager in Tools r18: - - <extra> packages are removed. They are served only by the addon XML. - - <platform>, <system-image>, <source>, <tool>, <platform-tool>, <doc> - and <sample> get a new optional field <beta-rc> which can be used to indicate - the package is a Beta Release Candidate and not a final release. - - - v7 is used by the SDK Manager in Tools r20: - - For <tool> and <platform-tool> packages, the <revision> element becomes a - a "full revision" element with <major>, <minor>, <micro> and <preview> sub-elements. - - The <beta-rc> element is no longer supported, it is replaced by - <revision> -> <preview> and is only for <tool> and <platform-tool> packages. - - <min-tools-rev> and <min-platform-tools-rev> also become a full revision element. - --> - - <xsd:element name="sdk-repository" type="sdk:repositoryType" /> - - <xsd:complexType name="repositoryType"> - <xsd:annotation> - <xsd:documentation> - The repository contains a collection of downloadable packages. - </xsd:documentation> - </xsd:annotation> - <xsd:choice minOccurs="0" maxOccurs="unbounded"> - <xsd:element name="platform" type="sdk:platformType" /> - <xsd:element name="system-image" type="sdk:systemImageType" /> - <xsd:element name="source" type="sdk:sourceType" /> - <xsd:element name="tool" type="sdk:toolType" /> - <xsd:element name="platform-tool" type="sdk:platformToolType" /> - <xsd:element name="doc" type="sdk:docType" /> - <xsd:element name="sample" type="sdk:sampleType" /> - <xsd:element name="license" type="sdk:licenseType" /> - </xsd:choice> - </xsd:complexType> - - <!-- The definition of an SDK platform package. --> - - <xsd:complexType name="platformType"> - <xsd:annotation> - <xsd:documentation>An SDK platform package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The Android platform version. It is string such as "1.0". --> - <xsd:element name="version" type="xsd:normalizedString" /> - <!-- The Android API Level for the platform. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- The optional codename for this platform, if it's a preview. --> - <xsd:element name="codename" type="xsd:string" minOccurs="0" /> - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - - <!-- Information on the layoutlib packaged in this platform. --> - <xsd:element name="layoutlib" type="sdk:layoutlibType" /> - - <!-- optional elements --> - - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - <!-- The minimal revision of tools required by this package. - Optional. If present, must be a revision element. --> - <xsd:element name="min-tools-rev" type="sdk:revisionType" minOccurs="0" /> - - <!-- The ABI of the system image *included* in this platform, if any. - When the field is present, it means the platform already embeds one - system image. A platform can also have any number of external - <system-image> associated with it. --> - <xsd:element name="included-abi" type="sdk:abiType" minOccurs="0" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of a layout library used by a platform. --> - - <xsd:complexType name="layoutlibType" > - <xsd:annotation> - <xsd:documentation> - Version information for a layoutlib included in a platform. - </xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The layoutlib API level, an int > 0, - incremented with each new incompatible lib. --> - <xsd:element name="api" type="xsd:positiveInteger" /> - <!-- The incremental minor revision for that API, e.g. in case of bug fixes. - Optional. An int >= 0, assumed to be 0 if the element is missing. --> - <xsd:element name="revision" type="xsd:nonNegativeInteger" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of a system image used by a platform. --> - - <xsd:complexType name="systemImageType" > - <xsd:annotation> - <xsd:documentation> - System Image for a platform. - </xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- api-level + codename identifies the platform to which this system image belongs. --> - - <!-- The Android API Level for the platform. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- The optional codename for this platform, if it's a preview. --> - <xsd:element name="codename" type="xsd:string" minOccurs="0" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - - <!-- The ABI of the system emulated by this image. --> - <xsd:element name="abi" type="sdk:abiType" /> - - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of the ABI supported by a platform's system image. --> - - <xsd:simpleType name="abiType"> - <xsd:annotation> - <xsd:documentation>The ABI of a platform's system image.</xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="armeabi" /> - <xsd:enumeration value="armeabi-v7a" /> - <xsd:enumeration value="x86" /> - <xsd:enumeration value="mips" /> - </xsd:restriction> - </xsd:simpleType> - - - <!-- The definition of a source package. --> - - <xsd:complexType name="sourceType" > - <xsd:annotation> - <xsd:documentation> - Sources for a platform. - </xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- api-level + codename identifies the platform to which this source belongs. --> - - <!-- The Android API Level for the platform. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- The optional codename for this platform, if it's a preview. --> - <xsd:element name="codename" type="xsd:string" minOccurs="0" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK tool package. --> - - <xsd:complexType name="toolType" > - <xsd:annotation> - <xsd:documentation>An SDK tool package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The full revision (major.minor.micro.preview), incremented each - time a new package is generated. --> - <xsd:element name="revision" type="sdk:revisionType" /> - - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - <!-- The minimal revision of platform-tools required by this package. - Mandatory. Must be a revision element. --> - <xsd:element name="min-platform-tools-rev" type="sdk:revisionType" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK platform-tool package. --> - - <xsd:complexType name="platformToolType" > - <xsd:annotation> - <xsd:documentation>An SDK platform-tool package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The full revision (major.minor.micro.preview), incremented each - time a new package is generated. --> - <xsd:element name="revision" type="sdk:revisionType" /> - - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK doc package. --> - - <xsd:complexType name="docType" > - <xsd:annotation> - <xsd:documentation>An SDK doc package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The Android API Level for the documentation. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- The optional codename for this doc, if it's a preview. --> - <xsd:element name="codename" type="xsd:string" minOccurs="0" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of an SDK sample package. --> - - <xsd:complexType name="sampleType" > - <xsd:annotation> - <xsd:documentation>An SDK sample package.</xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The Android API Level for the documentation. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- The optional codename for this doc, if it's a preview. --> - <xsd:element name="codename" type="xsd:string" minOccurs="0" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - <!-- The minimal revision of tools required by this package. - Optional. If present, must be a revision element. --> - <xsd:element name="min-tools-rev" type="sdk:revisionType" minOccurs="0" /> - - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of a path segment used by the extra element. --> - - <xsd:simpleType name="segmentType"> - <xsd:annotation> - <xsd:documentation> - One path segment for the install path of an extra element. - It must be a single-segment path. - </xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:token"> - <xsd:pattern value="[a-zA-Z0-9_]+"/> - </xsd:restriction> - </xsd:simpleType> - - <xsd:simpleType name="segmentListType"> - <xsd:annotation> - <xsd:documentation> - A semi-colon separated list of a segmentTypes. - </xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:token"> - <xsd:pattern value="[a-zA-Z0-9_;]+"/> - </xsd:restriction> - </xsd:simpleType> - - - <!-- The definition of a license to be referenced by the uses-license element. --> - - <xsd:complexType name="licenseType"> - <xsd:annotation> - <xsd:documentation> - A license definition. Such a license must be used later as a reference - using a uses-license element in one of the package elements. - </xsd:documentation> - </xsd:annotation> - <xsd:simpleContent> - <xsd:extension base="xsd:string"> - <xsd:attribute name="id" type="xsd:ID" /> - <xsd:attribute name="type" type="xsd:token" fixed="text" /> - </xsd:extension> - </xsd:simpleContent> - </xsd:complexType> - - - <!-- Type describing the license used by a package. - The license MUST be defined using a license node and referenced - using the ref attribute of the license element inside a package. - --> - - <xsd:complexType name="usesLicenseType"> - <xsd:annotation> - <xsd:documentation> - Describes the license used by a package. The license MUST be defined - using a license node and referenced using the ref attribute of the - license element inside a package. - </xsd:documentation> - </xsd:annotation> - <xsd:attribute name="ref" type="xsd:IDREF" /> - </xsd:complexType> - - - <!-- A collection of files that can be downloaded for a given architecture. - The <archives> node is mandatory in the repository elements and the - collection must have at least one <archive> declared. - Each archive is a zip file that will be unzipped in a location that depends - on its package type. - --> - - <xsd:complexType name="archivesType"> - <xsd:annotation> - <xsd:documentation> - A collection of files that can be downloaded for a given architecture. - The <archives> node is mandatory in the repository packages and the - collection must have at least one <archive> declared. - Each archive is a zip file that will be unzipped in a location that depends - on its package type. - </xsd:documentation> - </xsd:annotation> - <xsd:sequence minOccurs="1" maxOccurs="unbounded"> - <!-- One archive file --> - <xsd:element name="archive"> - <xsd:complexType> - <!-- Properties of the archive file --> - <xsd:all> - <!-- The size in bytes of the archive to download. --> - <xsd:element name="size" type="xsd:positiveInteger" /> - <!-- The checksum of the archive file. --> - <xsd:element name="checksum" type="sdk:checksumType" /> - <!-- The URL is an absolute URL if it starts with http://, https:// - or ftp://. Otherwise it is relative to the parent directory that - contains this repository.xml --> - <xsd:element name="url" type="xsd:token" /> - </xsd:all> - - <!-- Attributes that identify the OS and architecture --> - <xsd:attribute name="os" use="required"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="any" /> - <xsd:enumeration value="linux" /> - <xsd:enumeration value="macosx" /> - <xsd:enumeration value="windows" /> - </xsd:restriction> - </xsd:simpleType> - </xsd:attribute> - <xsd:attribute name="arch" use="optional"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="any" /> - <xsd:enumeration value="ppc" /> - <xsd:enumeration value="x86" /> - <xsd:enumeration value="x86_64" /> - </xsd:restriction> - </xsd:simpleType> - </xsd:attribute> - </xsd:complexType> - </xsd:element> - </xsd:sequence> - </xsd:complexType> - - - <!-- A full revision, with a major.minor.micro and an optional preview number. - The major number is mandatory, the other elements are optional. - --> - - <xsd:complexType name="revisionType"> - <xsd:annotation> - <xsd:documentation> - A full revision, with a major.minor.micro and an - optional preview number. The major number is mandatory. - </xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The major revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="major" type="xsd:positiveInteger" /> - <!-- The minor revision, an int >= 0, incremented each time a new - minor package is generated. Assumed to be 0 if missing. --> - <xsd:element name="minor" type="xsd:nonNegativeInteger" minOccurs="0" /> - <!-- The micro revision, an int >= 0, incremented each time a new - buf fix is generated. Assumed to be 0 if missing. --> - <xsd:element name="micro" type="xsd:nonNegativeInteger" minOccurs="0" /> - <!-- The preview/release candidate revision, an int > 0, - incremented each time a new preview is generated. - Not present for final releases. --> - <xsd:element name="preview" type="xsd:positiveInteger" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- A collection of file paths available in an <extra> package - that can be installed in an Android project. - If present, the <project-files> collection must contain at least one path. - Each path is relative to the root directory of the package. - --> - - <xsd:complexType name="projectFilesType"> - <xsd:annotation> - <xsd:documentation> - A collection of file paths available in an <extra> package - that can be installed in an Android project. - If present, the <project-files> collection must contain at least one path. - Each path is relative to the root directory of the package. - </xsd:documentation> - </xsd:annotation> - <xsd:sequence minOccurs="1" maxOccurs="unbounded"> - <!-- One JAR Path, relative to the root folder of the package. --> - <xsd:element name="path" type="xsd:string" /> - </xsd:sequence> - </xsd:complexType> - - - <!-- The definition of a file checksum --> - - <xsd:simpleType name="sha1Number"> - <xsd:annotation> - <xsd:documentation>A SHA1 checksum.</xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:string"> - <xsd:pattern value="([0-9a-fA-F]){40}"/> - </xsd:restriction> - </xsd:simpleType> - - <xsd:complexType name="checksumType"> - <xsd:annotation> - <xsd:documentation>A file checksum, currently only SHA1.</xsd:documentation> - </xsd:annotation> - <xsd:simpleContent> - <xsd:extension base="sdk:sha1Number"> - <xsd:attribute name="type" type="xsd:token" fixed="sha1" /> - </xsd:extension> - </xsd:simpleContent> - </xsd:complexType> - -</xsd:schema> diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-stats-1.xsd b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-stats-1.xsd deleted file mode 100755 index 2944b12..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-stats-1.xsd +++ /dev/null @@ -1,96 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<xsd:schema - targetNamespace="http://schemas.android.com/sdk/android/stats/1" - xmlns:xsd="http://www.w3.org/2001/XMLSchema" - xmlns:ast="http://schemas.android.com/sdk/android/stats/1" - elementFormDefault="qualified" - attributeFormDefault="unqualified" - version="1"> - - <!-- - A simple list of platforms provided by the SDK Manager and some - statistics on them, namely the market share percentage for that - platform. - This can be used by the SDK Manager or the ADT New Project Wizard - to give users an idea of the relative install base of platforms. - - Scope, Caveat & Limitation: - The "share percentage" corresponds to the Platform Versions table - from the SDK Dashboard as seen at - http://developer.android.com/resources/dashboard/platform-versions.html - However the data is not automatically generated and there is NO - freshness implied. The values may or may not be up-to-date and it is - most likely they will only get refreshed when there's a significant - change that affects the usage of the SDK tools. - - => The data is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES - OR CONDITIONS OF ANY KIND, either express or implied. - --> - - <xsd:element name="sdk-stats" type="ast:platformsListType" /> - - <xsd:complexType name="platformsListType"> - <xsd:annotation> - <xsd:documentation> - A simple list of platform stats. - </xsd:documentation> - </xsd:annotation> - <xsd:choice minOccurs="0" maxOccurs="unbounded"> - <xsd:element name="platform" type="ast:platformType" /> - </xsd:choice> - </xsd:complexType> - - - <!-- The definition of stats for a platform. --> - - <xsd:complexType name="platformType"> - <xsd:annotation> - <xsd:documentation>Stats information for a given Android platform. - The api-level acts as a key, and it is epxected there should only - be one platform listed with the same API-level. - </xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- The Android API Level for the platform. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - - <!-- The official codename for this platform, for example "Cupcake". --> - <xsd:element name="codename" type="xsd:normalizedString" /> - - <!-- The official version name of this platform, for example "Android 1.5". --> - <xsd:element name="version" type="xsd:normalizedString" /> - - <!-- An approximate share percentage of this platform. --> - <xsd:element name="share" type="ast:percent" /> - </xsd:all> - </xsd:complexType> - - - <!-- A decimal percentage, between 0.0 and 100.0% --> - - <xsd:simpleType name="percent" id="percent"> - <xsd:annotation> - <xsd:documentation>A decimal percentage, between 0.0 and 100.0%.</xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:decimal"> - <xsd:minInclusive value="0"/> - <xsd:maxInclusive value="100"/> - </xsd:restriction> - </xsd:simpleType> - -</xsd:schema> diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-sys-img-1.xsd b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-sys-img-1.xsd deleted file mode 100755 index a19aa49..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/repository/sdk-sys-img-1.xsd +++ /dev/null @@ -1,229 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<xsd:schema - targetNamespace="http://schemas.android.com/sdk/android/sys-img/1" - xmlns:xsd="http://www.w3.org/2001/XMLSchema" - xmlns:sdk="http://schemas.android.com/sdk/android/sys-img/1" - elementFormDefault="qualified" - attributeFormDefault="unqualified" - version="1"> - - <!-- The repository contains a collection of downloadable items known as - "packages". Each package has a type and various attributes and contains - a list of file "archives" that can be downloaded for specific OSes. - - An Android Addon repository is a web site that contains an "addon.xml" - file that conforms to this XML Schema. - - History: - - v1 is used by the SDK Updater in Tools r20. It is split out of the - main SDK Repository XML Schema and can only contain <system-image> packages. - --> - - <xsd:element name="sdk-sys-img" type="sdk:repositoryType" /> - - <xsd:complexType name="repositoryType"> - <xsd:annotation> - <xsd:documentation> - The repository contains a collection of downloadable system images. - </xsd:documentation> - </xsd:annotation> - <xsd:choice minOccurs="0" maxOccurs="unbounded"> - <xsd:element name="system-image" type="sdk:systemImageType" /> - <xsd:element name="license" type="sdk:licenseType" /> - </xsd:choice> - </xsd:complexType> - - - <!-- The definition of a system image used by a platform. --> - - <xsd:complexType name="systemImageType" > - <xsd:annotation> - <xsd:documentation> - System Image for a platform. - </xsd:documentation> - </xsd:annotation> - <xsd:all> - <!-- api-level+codename identifies the platform to which this system image belongs. --> - - <!-- The Android API Level for the platform. An int > 0. --> - <xsd:element name="api-level" type="xsd:positiveInteger" /> - <!-- The optional codename for this platform, if it's a preview. --> - <xsd:element name="codename" type="xsd:string" minOccurs="0" /> - - <!-- The revision, an int > 0, incremented each time a new - package is generated. --> - <xsd:element name="revision" type="xsd:positiveInteger" /> - - <!-- The ABI of the system emulated by this image. --> - <xsd:element name="abi" type="sdk:abiType" /> - - <!-- The optional license of this package. If present, users will have - to agree to it before downloading. --> - <xsd:element name="uses-license" type="sdk:usesLicenseType" minOccurs="0" /> - <!-- The optional description of this package. --> - <xsd:element name="description" type="xsd:string" minOccurs="0" /> - <!-- The optional description URL of this package --> - <xsd:element name="desc-url" type="xsd:token" minOccurs="0" /> - <!-- The optional release note for this package. --> - <xsd:element name="release-note" type="xsd:string" minOccurs="0" /> - <!-- The optional release note URL of this package --> - <xsd:element name="release-url" type="xsd:token" minOccurs="0" /> - - <!-- A list of file archives for this package. --> - <xsd:element name="archives" type="sdk:archivesType" /> - - <!-- An optional element indicating the package is obsolete. - The string content is however currently not defined and ignored. --> - <xsd:element name="obsolete" type="xsd:string" minOccurs="0" /> - </xsd:all> - </xsd:complexType> - - - <!-- The definition of the ABI supported by a platform's system image. --> - - <xsd:simpleType name="abiType"> - <xsd:annotation> - <xsd:documentation>The ABI of a platform's system image.</xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="armeabi" /> - <xsd:enumeration value="armeabi-v7a" /> - <xsd:enumeration value="x86" /> - <xsd:enumeration value="mips" /> - </xsd:restriction> - </xsd:simpleType> - - - <!-- The definition of a license to be referenced by the uses-license element. --> - - <xsd:complexType name="licenseType"> - <xsd:annotation> - <xsd:documentation> - A license definition. Such a license must be used later as a reference - using a uses-license element in one of the package elements. - </xsd:documentation> - </xsd:annotation> - <xsd:simpleContent> - <xsd:extension base="xsd:string"> - <xsd:attribute name="id" type="xsd:ID" /> - <xsd:attribute name="type" type="xsd:token" fixed="text" /> - </xsd:extension> - </xsd:simpleContent> - </xsd:complexType> - - - <!-- Type describing the license used by a package. - The license MUST be defined using a license node and referenced - using the ref attribute of the license element inside a package. - --> - - <xsd:complexType name="usesLicenseType"> - <xsd:annotation> - <xsd:documentation> - Describes the license used by a package. The license MUST be defined - using a license node and referenced using the ref attribute of the - license element inside a package. - </xsd:documentation> - </xsd:annotation> - <xsd:attribute name="ref" type="xsd:IDREF" /> - </xsd:complexType> - - - <!-- A collection of files that can be downloaded for a given architecture. - The <archives> node is mandatory in the repository elements and the - collection must have at least one <archive> declared. - Each archive is a zip file that will be unzipped in a location that depends - on its package type. - --> - - <xsd:complexType name="archivesType"> - <xsd:annotation> - <xsd:documentation> - A collection of files that can be downloaded for a given architecture. - The <archives> node is mandatory in the repository packages and the - collection must have at least one <archive> declared. - Each archive is a zip file that will be unzipped in a location that depends - on its package type. - </xsd:documentation> - </xsd:annotation> - <xsd:sequence minOccurs="1" maxOccurs="unbounded"> - <!-- One archive file --> - <xsd:element name="archive"> - <xsd:complexType> - <!-- Properties of the archive file --> - <xsd:all> - <!-- The size in bytes of the archive to download. --> - <xsd:element name="size" type="xsd:positiveInteger" /> - <!-- The checksum of the archive file. --> - <xsd:element name="checksum" type="sdk:checksumType" /> - <!-- The URL is an absolute URL if it starts with http://, https:// - or ftp://. Otherwise it is relative to the parent directory that - contains this repository.xml --> - <xsd:element name="url" type="xsd:token" /> - </xsd:all> - - <!-- Attributes that identify the OS and architecture --> - <xsd:attribute name="os" use="required"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="any" /> - <xsd:enumeration value="linux" /> - <xsd:enumeration value="macosx" /> - <xsd:enumeration value="windows" /> - </xsd:restriction> - </xsd:simpleType> - </xsd:attribute> - <xsd:attribute name="arch" use="optional"> - <xsd:simpleType> - <xsd:restriction base="xsd:token"> - <xsd:enumeration value="any" /> - <xsd:enumeration value="ppc" /> - <xsd:enumeration value="x86" /> - <xsd:enumeration value="x86_64" /> - </xsd:restriction> - </xsd:simpleType> - </xsd:attribute> - </xsd:complexType> - </xsd:element> - </xsd:sequence> - </xsd:complexType> - - - <!-- The definition of a file checksum --> - - <xsd:simpleType name="sha1Number"> - <xsd:annotation> - <xsd:documentation>A SHA1 checksum.</xsd:documentation> - </xsd:annotation> - <xsd:restriction base="xsd:string"> - <xsd:pattern value="([0-9a-fA-F]){40}"/> - </xsd:restriction> - </xsd:simpleType> - - <xsd:complexType name="checksumType"> - <xsd:annotation> - <xsd:documentation>A file checksum, currently only SHA1.</xsd:documentation> - </xsd:annotation> - <xsd:simpleContent> - <xsd:extension base="sdk:sha1Number"> - <xsd:attribute name="type" type="xsd:token" fixed="sha1" /> - </xsd:extension> - </xsd:simpleContent> - </xsd:complexType> - -</xsd:schema> diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/util/ArrayUtils.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/util/ArrayUtils.java deleted file mode 100644 index 20f9c01..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/util/ArrayUtils.java +++ /dev/null @@ -1,136 +0,0 @@ -/* - * Copyright (C) 2006 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.util; - -import java.lang.reflect.Array; - -// XXX these should be changed to reflect the actual memory allocator we use. -// it looks like right now objects want to be powers of 2 minus 8 -// and the array size eats another 4 bytes - -/** - * ArrayUtils contains some methods that you can call to find out - * the most efficient increments by which to grow arrays. - */ -/* package */ class ArrayUtils -{ - private static Object[] EMPTY = new Object[0]; - private static final int CACHE_SIZE = 73; - private static Object[] sCache = new Object[CACHE_SIZE]; - - private ArrayUtils() { /* cannot be instantiated */ } - - public static int idealByteArraySize(int need) { - for (int i = 4; i < 32; i++) - if (need <= (1 << i) - 12) - return (1 << i) - 12; - - return need; - } - - public static int idealBooleanArraySize(int need) { - return idealByteArraySize(need); - } - - public static int idealShortArraySize(int need) { - return idealByteArraySize(need * 2) / 2; - } - - public static int idealCharArraySize(int need) { - return idealByteArraySize(need * 2) / 2; - } - - public static int idealIntArraySize(int need) { - return idealByteArraySize(need * 4) / 4; - } - - public static int idealFloatArraySize(int need) { - return idealByteArraySize(need * 4) / 4; - } - - public static int idealObjectArraySize(int need) { - return idealByteArraySize(need * 4) / 4; - } - - public static int idealLongArraySize(int need) { - return idealByteArraySize(need * 8) / 8; - } - - /** - * Checks if the beginnings of two byte arrays are equal. - * - * @param array1 the first byte array - * @param array2 the second byte array - * @param length the number of bytes to check - * @return true if they're equal, false otherwise - */ - public static boolean equals(byte[] array1, byte[] array2, int length) { - if (array1 == array2) { - return true; - } - if (array1 == null || array2 == null || array1.length < length || array2.length < length) { - return false; - } - for (int i = 0; i < length; i++) { - if (array1[i] != array2[i]) { - return false; - } - } - return true; - } - - /** - * Returns an empty array of the specified type. The intent is that - * it will return the same empty array every time to avoid reallocation, - * although this is not guaranteed. - */ - @SuppressWarnings("unchecked") - public static <T> T[] emptyArray(Class<T> kind) { - if (kind == Object.class) { - return (T[]) EMPTY; - } - - int bucket = ((System.identityHashCode(kind) / 8) & 0x7FFFFFFF) % CACHE_SIZE; - Object cache = sCache[bucket]; - - if (cache == null || cache.getClass().getComponentType() != kind) { - cache = Array.newInstance(kind, 0); - sCache[bucket] = cache; - - // Log.e("cache", "new empty " + kind.getName() + " at " + bucket); - } - - return (T[]) cache; - } - - /** - * Checks that value is present as at least one of the elements of the array. - * @param array the array to check in - * @param value the value to check for - * @return true if the value is present in the array - */ - public static <T> boolean contains(T[] array, T value) { - for (T element : array) { - if (element == null) { - if (value == null) return true; - } else { - if (value != null && element.equals(value)) return true; - } - } - return false; - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/util/CommandLineParser.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/util/CommandLineParser.java deleted file mode 100644 index 3a86ea7..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/util/CommandLineParser.java +++ /dev/null @@ -1,968 +0,0 @@ -/* - * Copyright (C) 2008 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.util; - -import com.android.annotations.NonNull; -import com.android.annotations.Nullable; -import com.android.utils.ILogger; - -import java.util.ArrayList; -import java.util.HashMap; -import java.util.List; -import java.util.Map.Entry; - -/** - * Parses the command-line and stores flags needed or requested. - * <p/> - * This is a base class. To be useful you want to: - * <ul> - * <li>override it. - * <li>pass an action array to the constructor. - * <li>define flags for your actions. - * </ul> - * <p/> - * To use, call {@link #parseArgs(String[])} and then - * call {@link #getValue(String, String, String)}. - */ -public class CommandLineParser { - - /* - * Steps needed to add a new action: - * - Each action is defined as a "verb object" followed by parameters. - * - Either reuse a VERB_ constant or define a new one. - * - Either reuse an OBJECT_ constant or define a new one. - * - Add a new entry to mAction with a one-line help summary. - * - In the constructor, add a define() call for each parameter (either mandatory - * or optional) for the given action. - */ - - /** Internal verb name for internally hidden flags. */ - public final static String GLOBAL_FLAG_VERB = "@@internal@@"; //$NON-NLS-1$ - - /** String to use when the verb doesn't need any object. */ - public final static String NO_VERB_OBJECT = ""; //$NON-NLS-1$ - - /** The global help flag. */ - public static final String KEY_HELP = "help"; - /** The global verbose flag. */ - public static final String KEY_VERBOSE = "verbose"; - /** The global silent flag. */ - public static final String KEY_SILENT = "silent"; - - /** Verb requested by the user. Null if none specified, which will be an error. */ - private String mVerbRequested; - /** Direct object requested by the user. Can be null. */ - private String mDirectObjectRequested; - - /** - * Action definitions. - * <p/> - * This list serves two purposes: first it is used to know which verb/object - * actions are acceptable on the command-line; second it provides a summary - * for each action that is printed in the help. - * <p/> - * Each entry is a string array with: - * <ul> - * <li> the verb. - * <li> a direct object (use {@link #NO_VERB_OBJECT} if there's no object). - * <li> a description. - * <li> an alternate form for the object (e.g. plural). - * </ul> - */ - private final String[][] mActions; - - private static final int ACTION_VERB_INDEX = 0; - private static final int ACTION_OBJECT_INDEX = 1; - private static final int ACTION_DESC_INDEX = 2; - private static final int ACTION_ALT_OBJECT_INDEX = 3; - - /** - * The map of all defined arguments. - * <p/> - * The key is a string "verb/directObject/longName". - */ - private final HashMap<String, Arg> mArguments = new HashMap<String, Arg>(); - /** Logger */ - private final ILogger mLog; - - /** - * Constructs a new command-line processor. - * - * @param logger An SDK logger object. Must not be null. - * @param actions The list of actions recognized on the command-line. - * See the javadoc of {@link #mActions} for more details. - * - * @see #mActions - */ - public CommandLineParser(ILogger logger, String[][] actions) { - mLog = logger; - mActions = actions; - - /* - * usage should fit in 80 columns, including the space to print the options: - * " -v --verbose 7890123456789012345678901234567890123456789012345678901234567890" - */ - - define(Mode.BOOLEAN, false, GLOBAL_FLAG_VERB, NO_VERB_OBJECT, "v", KEY_VERBOSE, - "Verbose mode, shows errors, warnings and all messages.", - false); - define(Mode.BOOLEAN, false, GLOBAL_FLAG_VERB, NO_VERB_OBJECT, "s", KEY_SILENT, - "Silent mode, shows errors only.", - false); - define(Mode.BOOLEAN, false, GLOBAL_FLAG_VERB, NO_VERB_OBJECT, "h", KEY_HELP, - "Help on a specific command.", - false); - } - - /** - * Indicates if this command-line can work when no verb is specified. - * The default is false, which generates an error when no verb/object is specified. - * Derived implementations can set this to true if they can deal with a lack - * of verb/action. - */ - public boolean acceptLackOfVerb() { - return false; - } - - - //------------------ - // Helpers to get flags values - - /** Helper that returns true if --verbose was requested. */ - public boolean isVerbose() { - return ((Boolean) getValue(GLOBAL_FLAG_VERB, NO_VERB_OBJECT, KEY_VERBOSE)).booleanValue(); - } - - /** Helper that returns true if --silent was requested. */ - public boolean isSilent() { - return ((Boolean) getValue(GLOBAL_FLAG_VERB, NO_VERB_OBJECT, KEY_SILENT)).booleanValue(); - } - - /** Helper that returns true if --help was requested. */ - public boolean isHelpRequested() { - return ((Boolean) getValue(GLOBAL_FLAG_VERB, NO_VERB_OBJECT, KEY_HELP)).booleanValue(); - } - - /** Returns the verb name from the command-line. Can be null. */ - public String getVerb() { - return mVerbRequested; - } - - /** Returns the direct object name from the command-line. Can be null. */ - public String getDirectObject() { - return mDirectObjectRequested; - } - - //------------------ - - /** - * Raw access to parsed parameter values. - * <p/> - * The default is to scan all parameters. Parameters that have been explicitly set on the - * command line are returned first. Otherwise one with a non-null value is returned. - * <p/> - * Both a verb and a direct object filter can be specified. When they are non-null they limit - * the scope of the search. - * <p/> - * If nothing has been found, return the last default value seen matching the filter. - * - * @param verb The verb name, including {@link #GLOBAL_FLAG_VERB}. If null, all possible - * verbs that match the direct object condition will be examined and the first - * value set will be used. - * @param directObject The direct object name, including {@link #NO_VERB_OBJECT}. If null, - * all possible direct objects that match the verb condition will be examined and - * the first value set will be used. - * @param longFlagName The long flag name for the given action. Mandatory. Cannot be null. - * @return The current value object stored in the parameter, which depends on the argument mode. - */ - public Object getValue(String verb, String directObject, String longFlagName) { - - if (verb != null && directObject != null) { - String key = verb + '/' + directObject + '/' + longFlagName; - Arg arg = mArguments.get(key); - return arg.getCurrentValue(); - } - - Object lastDefault = null; - for (Arg arg : mArguments.values()) { - if (arg.getLongArg().equals(longFlagName)) { - if (verb == null || arg.getVerb().equals(verb)) { - if (directObject == null || arg.getDirectObject().equals(directObject)) { - if (arg.isInCommandLine()) { - return arg.getCurrentValue(); - } - if (arg.getCurrentValue() != null) { - lastDefault = arg.getCurrentValue(); - } - } - } - } - } - - return lastDefault; - } - - /** - * Internal setter for raw parameter value. - * @param verb The verb name, including {@link #GLOBAL_FLAG_VERB}. - * @param directObject The direct object name, including {@link #NO_VERB_OBJECT}. - * @param longFlagName The long flag name for the given action. - * @param value The new current value object stored in the parameter, which depends on the - * argument mode. - */ - protected void setValue(String verb, String directObject, String longFlagName, Object value) { - String key = verb + '/' + directObject + '/' + longFlagName; - Arg arg = mArguments.get(key); - arg.setCurrentValue(value); - } - - /** - * Parses the command-line arguments. - * <p/> - * This method will exit and not return if a parsing error arise. - * - * @param args The arguments typically received by a main method. - */ - public void parseArgs(String[] args) { - String errorMsg = null; - String verb = null; - String directObject = null; - - try { - int n = args.length; - for (int i = 0; i < n; i++) { - Arg arg = null; - String a = args[i]; - if (a.startsWith("--")) { //$NON-NLS-1$ - arg = findLongArg(verb, directObject, a.substring(2)); - } else if (a.startsWith("-")) { //$NON-NLS-1$ - arg = findShortArg(verb, directObject, a.substring(1)); - } - - // No matching argument name found - if (arg == null) { - // Does it looks like a dashed parameter? - if (a.startsWith("-")) { //$NON-NLS-1$ - if (verb == null || directObject == null) { - // It looks like a dashed parameter and we don't have a a verb/object - // set yet, the parameter was just given too early. - - errorMsg = String.format( - "Flag '%1$s' is not a valid global flag. Did you mean to specify it after the verb/object name?", - a); - return; - } else { - // It looks like a dashed parameter but it is unknown by this - // verb-object combination - - errorMsg = String.format( - "Flag '%1$s' is not valid for '%2$s %3$s'.", - a, verb, directObject); - return; - } - } - - if (verb == null) { - // Fill verb first. Find it. - for (String[] actionDesc : mActions) { - if (actionDesc[ACTION_VERB_INDEX].equals(a)) { - verb = a; - break; - } - } - - // Error if it was not a valid verb - if (verb == null) { - errorMsg = String.format( - "Expected verb after global parameters but found '%1$s' instead.", - a); - return; - } - - } else if (directObject == null) { - // Then fill the direct object. Find it. - for (String[] actionDesc : mActions) { - if (actionDesc[ACTION_VERB_INDEX].equals(verb)) { - if (actionDesc[ACTION_OBJECT_INDEX].equals(a)) { - directObject = a; - break; - } else if (actionDesc.length > ACTION_ALT_OBJECT_INDEX && - actionDesc[ACTION_ALT_OBJECT_INDEX].equals(a)) { - // if the alternate form exist and is used, we internally - // only memorize the default direct object form. - directObject = actionDesc[ACTION_OBJECT_INDEX]; - break; - } - } - } - - // Error if it was not a valid object for that verb - if (directObject == null) { - errorMsg = String.format( - "Expected verb after global parameters but found '%1$s' instead.", - a); - return; - - } - } else { - // The argument is not a dashed parameter and we already - // have a verb/object. Must be some extra unknown argument. - errorMsg = String.format( - "Argument '%1$s' is not recognized.", - a); - } - } else if (arg != null) { - // This argument was present on the command line - arg.setInCommandLine(true); - - // Process keyword - Object error = null; - if (arg.getMode().needsExtra()) { - if (i+1 >= n) { - errorMsg = String.format("Missing argument for flag %1$s.", a); - return; - } - - while (i+1 < n) { - String b = args[i+1]; - - if (arg.getMode() != Mode.STRING_ARRAY) { - // We never accept something that looks like a valid argument - // unless we see -- first - Arg dummyArg = null; - if (b.startsWith("--")) { //$NON-NLS-1$ - dummyArg = findLongArg(verb, directObject, b.substring(2)); - } else if (b.startsWith("-")) { //$NON-NLS-1$ - dummyArg = findShortArg(verb, directObject, b.substring(1)); - } - if (dummyArg != null) { - errorMsg = String.format( - "Oops, it looks like you didn't provide an argument for '%1$s'.\n'%2$s' was found instead.", - a, b); - return; - } - } - - error = arg.getMode().process(arg, b); - if (error == Accept.CONTINUE) { - i++; - } else if (error == Accept.ACCEPT_AND_STOP) { - i++; - break; - } else if (error == Accept.REJECT_AND_STOP) { - break; - } else if (error instanceof String) { - // We stop because of an error - break; - } - } - } else { - error = arg.getMode().process(arg, null); - - if (isHelpRequested()) { - // The --help flag was requested. We'll continue the usual processing - // so that we can find the optional verb/object words. Those will be - // used to print specific help. - // Setting a non-null error message triggers printing the help, however - // there is no specific error to print. - errorMsg = ""; //$NON-NLS-1$ - } - } - - if (error instanceof String) { - errorMsg = String.format("Invalid usage for flag %1$s: %2$s.", a, error); - return; - } - } - } - - if (errorMsg == null) { - if (verb == null && !acceptLackOfVerb()) { - errorMsg = "Missing verb name."; - } else if (verb != null) { - if (directObject == null) { - // Make sure this verb has an optional direct object - for (String[] actionDesc : mActions) { - if (actionDesc[ACTION_VERB_INDEX].equals(verb) && - actionDesc[ACTION_OBJECT_INDEX].equals(NO_VERB_OBJECT)) { - directObject = NO_VERB_OBJECT; - break; - } - } - - if (directObject == null) { - errorMsg = String.format("Missing object name for verb '%1$s'.", verb); - return; - } - } - - // Validate that all mandatory arguments are non-null for this action - String missing = null; - boolean plural = false; - for (Entry<String, Arg> entry : mArguments.entrySet()) { - Arg arg = entry.getValue(); - if (arg.getVerb().equals(verb) && - arg.getDirectObject().equals(directObject)) { - if (arg.isMandatory() && arg.getCurrentValue() == null) { - if (missing == null) { - missing = "--" + arg.getLongArg(); //$NON-NLS-1$ - } else { - missing += ", --" + arg.getLongArg(); //$NON-NLS-1$ - plural = true; - } - } - } - } - - if (missing != null) { - errorMsg = String.format( - "The %1$s %2$s must be defined for action '%3$s %4$s'", - plural ? "parameters" : "parameter", - missing, - verb, - directObject); - } - - mVerbRequested = verb; - mDirectObjectRequested = directObject; - } - } - } finally { - if (errorMsg != null) { - printHelpAndExitForAction(verb, directObject, errorMsg); - } - } - } - - /** - * Finds an {@link Arg} given an action name and a long flag name. - * @return The {@link Arg} found or null. - */ - protected Arg findLongArg(String verb, String directObject, String longName) { - if (verb == null) { - verb = GLOBAL_FLAG_VERB; - } - if (directObject == null) { - directObject = NO_VERB_OBJECT; - } - String key = verb + '/' + directObject + '/' + longName; //$NON-NLS-1$ - return mArguments.get(key); - } - - /** - * Finds an {@link Arg} given an action name and a short flag name. - * @return The {@link Arg} found or null. - */ - protected Arg findShortArg(String verb, String directObject, String shortName) { - if (verb == null) { - verb = GLOBAL_FLAG_VERB; - } - if (directObject == null) { - directObject = NO_VERB_OBJECT; - } - - for (Entry<String, Arg> entry : mArguments.entrySet()) { - Arg arg = entry.getValue(); - if (arg.getVerb().equals(verb) && arg.getDirectObject().equals(directObject)) { - if (shortName.equals(arg.getShortArg())) { - return arg; - } - } - } - - return null; - } - - /** - * Prints the help/usage and exits. - * - * @param errorFormat Optional error message to print prior to usage using String.format - * @param args Arguments for String.format - */ - public void printHelpAndExit(String errorFormat, Object... args) { - printHelpAndExitForAction(null /*verb*/, null /*directObject*/, errorFormat, args); - } - - /** - * Prints the help/usage and exits. - * - * @param verb If null, displays help for all verbs. If not null, display help only - * for that specific verb. In all cases also displays general usage and action list. - * @param directObject If null, displays help for all verb objects. - * If not null, displays help only for that specific action - * In all cases also display general usage and action list. - * @param errorFormat Optional error message to print prior to usage using String.format - * @param args Arguments for String.format - */ - public void printHelpAndExitForAction(String verb, String directObject, - String errorFormat, Object... args) { - if (errorFormat != null && errorFormat.length() > 0) { - stderr(errorFormat, args); - } - - /* - * usage should fit in 80 columns - * 12345678901234567890123456789012345678901234567890123456789012345678901234567890 - */ - stdout("\n" + - "Usage:\n" + - " android [global options] %s [action options]\n" + - "\n" + - "Global options:", - verb == null ? "action" : - verb + (directObject == null ? "" : " " + directObject)); //$NON-NLS-1$ - listOptions(GLOBAL_FLAG_VERB, NO_VERB_OBJECT); - - if (verb == null || directObject == null) { - stdout("\nValid actions are composed of a verb and an optional direct object:"); - for (String[] action : mActions) { - if (verb == null || verb.equals(action[ACTION_VERB_INDEX])) { - stdout("- %1$6s %2$-13s: %3$s", - action[ACTION_VERB_INDEX], - action[ACTION_OBJECT_INDEX], - action[ACTION_DESC_INDEX]); - } - } - } - - // Only print details if a verb/object is requested - if (verb != null) { - for (String[] action : mActions) { - if (verb == null || verb.equals(action[ACTION_VERB_INDEX])) { - if (directObject == null || directObject.equals(action[ACTION_OBJECT_INDEX])) { - stdout("\nAction \"%1$s %2$s\":", - action[ACTION_VERB_INDEX], - action[ACTION_OBJECT_INDEX]); - stdout(" %1$s", action[ACTION_DESC_INDEX]); - stdout("Options:"); - listOptions(action[ACTION_VERB_INDEX], action[ACTION_OBJECT_INDEX]); - } - } - } - } - - exit(); - } - - /** - * Internal helper to print all the option flags for a given action name. - */ - protected void listOptions(String verb, String directObject) { - int numOptions = 0; - int longArgLen = 8; - - for (Entry<String, Arg> entry : mArguments.entrySet()) { - Arg arg = entry.getValue(); - if (arg.getVerb().equals(verb) && arg.getDirectObject().equals(directObject)) { - int n = arg.getLongArg().length(); - if (n > longArgLen) { - longArgLen = n; - } - } - } - - for (Entry<String, Arg> entry : mArguments.entrySet()) { - Arg arg = entry.getValue(); - if (arg.getVerb().equals(verb) && arg.getDirectObject().equals(directObject)) { - - String value = ""; //$NON-NLS-1$ - String required = ""; //$NON-NLS-1$ - if (arg.isMandatory()) { - required = " [required]"; - - } else { - if (arg.getDefaultValue() instanceof String[]) { - for (String v : (String[]) arg.getDefaultValue()) { - if (value.length() > 0) { - value += ", "; - } - value += v; - } - } else if (arg.getDefaultValue() != null) { - Object v = arg.getDefaultValue(); - if (arg.getMode() != Mode.BOOLEAN || v.equals(Boolean.TRUE)) { - value = v.toString(); - } - } - if (value.length() > 0) { - value = " [Default: " + value + "]"; - } - } - - // Java doesn't support * for printf variable width, so we'll insert the long arg - // width "manually" in the printf format string. - String longArgWidth = Integer.toString(longArgLen + 2); - - // Print a line in the form " -1_letter_arg --long_arg description" - // where either the 1-letter arg or the long arg are optional. - String output = String.format( - " %1$-2s %2$-" + longArgWidth + "s: %3$s%4$s%5$s", //$NON-NLS-1$ //$NON-NLS-2$ - arg.getShortArg().length() > 0 ? - "-" + arg.getShortArg() : //$NON-NLS-1$ - "", //$NON-NLS-1$ - arg.getLongArg().length() > 0 ? - "--" + arg.getLongArg() : //$NON-NLS-1$ - "", //$NON-NLS-1$ - arg.getDescription(), - value, - required); - stdout(output); - numOptions++; - } - } - - if (numOptions == 0) { - stdout(" No options"); - } - } - - //---- - - private static enum Accept { - CONTINUE, - ACCEPT_AND_STOP, - REJECT_AND_STOP, - } - - /** - * The mode of an argument specifies the type of variable it represents, - * whether an extra parameter is required after the flag and how to parse it. - */ - public static enum Mode { - /** Argument value is a Boolean. Default value is a Boolean. */ - BOOLEAN { - @Override - public boolean needsExtra() { - return false; - } - @Override - public Object process(Arg arg, String extra) { - // Toggle the current value - arg.setCurrentValue(! ((Boolean) arg.getCurrentValue()).booleanValue()); - return Accept.ACCEPT_AND_STOP; - } - }, - - /** Argument value is an Integer. Default value is an Integer. */ - INTEGER { - @Override - public boolean needsExtra() { - return true; - } - @Override - public Object process(Arg arg, String extra) { - try { - arg.setCurrentValue(Integer.parseInt(extra)); - return null; - } catch (NumberFormatException e) { - return String.format("Failed to parse '%1$s' as an integer: %2$s", extra, - e.getMessage()); - } - } - }, - - /** Argument value is a String. Default value is a String[]. */ - ENUM { - @Override - public boolean needsExtra() { - return true; - } - @Override - public Object process(Arg arg, String extra) { - StringBuilder desc = new StringBuilder(); - String[] values = (String[]) arg.getDefaultValue(); - for (String value : values) { - if (value.equals(extra)) { - arg.setCurrentValue(extra); - return Accept.ACCEPT_AND_STOP; - } - - if (desc.length() != 0) { - desc.append(", "); - } - desc.append(value); - } - - return String.format("'%1$s' is not one of %2$s", extra, desc.toString()); - } - }, - - /** Argument value is a String. Default value is a null. */ - STRING { - @Override - public boolean needsExtra() { - return true; - } - @Override - public Object process(Arg arg, String extra) { - arg.setCurrentValue(extra); - return Accept.ACCEPT_AND_STOP; - } - }, - - /** Argument value is a {@link List}<String>. Default value is an empty list. */ - STRING_ARRAY { - @Override - public boolean needsExtra() { - return true; - } - @Override - public Object process(Arg arg, String extra) { - // For simplification, a string array doesn't accept something that - // starts with a dash unless a pure -- was seen before. - if (extra != null) { - Object v = arg.getCurrentValue(); - if (v == null) { - ArrayList<String> a = new ArrayList<String>(); - arg.setCurrentValue(a); - v = a; - } - if (v instanceof List<?>) { - @SuppressWarnings("unchecked") List<String> a = (List<String>) v; - - if (extra.equals("--") || - !extra.startsWith("-") || - (extra.startsWith("-") && a.contains("--"))) { - a.add(extra); - return Accept.CONTINUE; - } else if (a.isEmpty()) { - return "No values provided"; - } - } - } - return Accept.REJECT_AND_STOP; - } - }; - - /** - * Returns true if this mode requires an extra parameter. - */ - public abstract boolean needsExtra(); - - /** - * Processes the flag for this argument. - * - * @param arg The argument being processed. - * @param extra The extra parameter. Null if {@link #needsExtra()} returned false. - * @return {@link Accept#CONTINUE} if this argument can use multiple values and - * wishes to receive more. - * Or {@link Accept#ACCEPT_AND_STOP} if this was the last value accepted by the argument. - * Or {@link Accept#REJECT_AND_STOP} if this was value was reject and the argument - * stops accepting new values with no error. - * Or a string in case of error. - * Never returns null. - */ - public abstract Object process(Arg arg, String extra); - } - - /** - * An argument accepted by the command-line, also called "a flag". - * Arguments must have a short version (one letter), a long version name and a description. - * They can have a default value, or it can be null. - * Depending on the {@link Mode}, the default value can be a Boolean, an Integer, a String - * or a String array (in which case the first item is the current by default.) - */ - static class Arg { - /** Verb for that argument. Never null. */ - private final String mVerb; - /** Direct Object for that argument. Never null, but can be empty string. */ - private final String mDirectObject; - /** The 1-letter short name of the argument, e.g. -v. */ - private final String mShortName; - /** The long name of the argument, e.g. --verbose. */ - private final String mLongName; - /** A description. Never null. */ - private final String mDescription; - /** A default value. Can be null. */ - private final Object mDefaultValue; - /** The argument mode (type + process method). Never null. */ - private final Mode mMode; - /** True if this argument is mandatory for this verb/directobject. */ - private final boolean mMandatory; - /** Current value. Initially set to the default value. */ - private Object mCurrentValue; - /** True if the argument has been used on the command line. */ - private boolean mInCommandLine; - - /** - * Creates a new argument flag description. - * - * @param mode The {@link Mode} for the argument. - * @param mandatory True if this argument is mandatory for this action. - * @param verb The verb name. Never null. Can be {@link CommandLineParser#GLOBAL_FLAG_VERB}. - * @param directObject The action name. Can be {@link CommandLineParser#NO_VERB_OBJECT}. - * @param shortName The one-letter short argument name. Can be empty but not null. - * @param longName The long argument name. Can be empty but not null. - * @param description The description. Cannot be null. - * @param defaultValue The default value (or values), which depends on the selected - * {@link Mode}. Can be null. - */ - public Arg(Mode mode, - boolean mandatory, - @NonNull String verb, - @NonNull String directObject, - @NonNull String shortName, - @NonNull String longName, - @NonNull String description, - @Nullable Object defaultValue) { - mMode = mode; - mMandatory = mandatory; - mVerb = verb; - mDirectObject = directObject; - mShortName = shortName; - mLongName = longName; - mDescription = description; - mDefaultValue = defaultValue; - mInCommandLine = false; - if (defaultValue instanceof String[]) { - mCurrentValue = ((String[])defaultValue)[0]; - } else { - mCurrentValue = mDefaultValue; - } - } - - /** Return true if this argument is mandatory for this verb/directobject. */ - public boolean isMandatory() { - return mMandatory; - } - - /** Returns the 1-letter short name of the argument, e.g. -v. */ - public String getShortArg() { - return mShortName; - } - - /** Returns the long name of the argument, e.g. --verbose. */ - public String getLongArg() { - return mLongName; - } - - /** Returns the description. Never null. */ - public String getDescription() { - return mDescription; - } - - /** Returns the verb for that argument. Never null. */ - public String getVerb() { - return mVerb; - } - - /** Returns the direct Object for that argument. Never null, but can be empty string. */ - public String getDirectObject() { - return mDirectObject; - } - - /** Returns the default value. Can be null. */ - public Object getDefaultValue() { - return mDefaultValue; - } - - /** Returns the current value. Initially set to the default value. Can be null. */ - public Object getCurrentValue() { - return mCurrentValue; - } - - /** Sets the current value. Can be null. */ - public void setCurrentValue(Object currentValue) { - mCurrentValue = currentValue; - } - - /** Returns the argument mode (type + process method). Never null. */ - public Mode getMode() { - return mMode; - } - - /** Returns true if the argument has been used on the command line. */ - public boolean isInCommandLine() { - return mInCommandLine; - } - - /** Sets if the argument has been used on the command line. */ - public void setInCommandLine(boolean inCommandLine) { - mInCommandLine = inCommandLine; - } - } - - /** - * Internal helper to define a new argument for a give action. - * - * @param mode The {@link Mode} for the argument. - * @param mandatory The argument is required (never if {@link Mode#BOOLEAN}) - * @param verb The verb name. Never null. Can be {@link CommandLineParser#GLOBAL_FLAG_VERB}. - * @param directObject The action name. Can be {@link CommandLineParser#NO_VERB_OBJECT}. - * @param shortName The one-letter short argument name. Can be empty but not null. - * @param longName The long argument name. Can be empty but not null. - * @param description The description. Cannot be null. - * @param defaultValue The default value (or values), which depends on the selected - * {@link Mode}. - */ - protected void define(Mode mode, - boolean mandatory, - @NonNull String verb, - @NonNull String directObject, - @NonNull String shortName, - @NonNull String longName, - @NonNull String description, - @Nullable Object defaultValue) { - assert verb != null; - assert(!(mandatory && mode == Mode.BOOLEAN)); // a boolean mode cannot be mandatory - - // We should always have at least a short or long name, ideally both but never none. - assert shortName != null; - assert longName != null; - assert shortName.length() > 0 || longName.length() > 0; - - if (directObject == null) { - directObject = NO_VERB_OBJECT; - } - - String key = verb + '/' + directObject + '/' + longName; - mArguments.put(key, new Arg(mode, mandatory, - verb, directObject, shortName, longName, description, defaultValue)); - } - - /** - * Exits in case of error. - * This is protected so that it can be overridden in unit tests. - */ - protected void exit() { - System.exit(1); - } - - /** - * Prints a line to stdout. - * This is protected so that it can be overridden in unit tests. - * - * @param format The string to be formatted. Cannot be null. - * @param args Format arguments. - */ - protected void stdout(String format, Object...args) { - String output = String.format(format, args); - output = LineUtil.reflowLine(output); - mLog.info("%s\n", output); //$NON-NLS-1$ - } - - /** - * Prints a line to stderr. - * This is protected so that it can be overridden in unit tests. - * - * @param format The string to be formatted. Cannot be null. - * @param args Format arguments. - */ - protected void stderr(String format, Object...args) { - mLog.error(null, format, args); - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/util/FormatUtils.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/util/FormatUtils.java deleted file mode 100755 index fc9258c..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/util/FormatUtils.java +++ /dev/null @@ -1,52 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.util; - -import com.android.annotations.NonNull; - -/** - * Helper methods to do some format conversions. - */ -public abstract class FormatUtils { - - /** - * Converts a byte size to a human readable string, - * for example "3 MiB", "1020 Bytes" or "1.2 GiB". - * - * @param size The byte size to convert. - * @return A new non-null string, with the size expressed in either Bytes - * or KiB or MiB or GiB. - */ - public static @NonNull String byteSizeToString(long size) { - String sizeStr; - - if (size < 1024) { - sizeStr = String.format("%d Bytes", size); - } else if (size < 1024 * 1024) { - sizeStr = String.format("%d KiB", Math.round(size / 1024.0)); - } else if (size < 1024 * 1024 * 1024) { - sizeStr = String.format("%.1f MiB", - Math.round(10.0 * size / (1024 * 1024.0))/ 10.0); - } else { - sizeStr = String.format("%.1f GiB", - Math.round(10.0 * size / (1024 * 1024 * 1024.0))/ 10.0); - } - - return sizeStr; - } - -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/util/GrabProcessOutput.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/util/GrabProcessOutput.java deleted file mode 100755 index 2935493..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/util/GrabProcessOutput.java +++ /dev/null @@ -1,157 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.util; - -import com.android.annotations.NonNull; -import com.android.annotations.Nullable; - -import java.io.BufferedReader; -import java.io.IOException; -import java.io.InputStreamReader; - -public class GrabProcessOutput { - - public enum Wait { - /** - * Doesn't wait for the exec to complete. - * This still monitors the output but does not wait for the process to finish. - * In this mode the process return code is unknown and always 0. - */ - ASYNC, - /** - * This waits for the process to finish. - * In this mode, {@link GrabProcessOutput#grabProcessOutput} returns the - * error code from the process. - * In some rare cases and depending on the OS, the process might not have - * finished dumping data into stdout/stderr. - * <p/> - * Use this when you don't particularly care for the output but instead - * care for the return code of the executed process. - */ - WAIT_FOR_PROCESS, - /** - * This waits for the process to finish <em>and</em> for the stdout/stderr - * threads to complete. - * In this mode, {@link GrabProcessOutput#grabProcessOutput} returns the - * error code from the process. - * <p/> - * Use this one when capturing all the output from the process is important. - */ - WAIT_FOR_READERS, - } - - public interface IProcessOutput { - /** - * Processes an stdout message line. - * @param line The stdout message line. Null when the reader reached the end of stdout. - */ - public void out(@Nullable String line); - /** - * Processes an stderr message line. - * @param line The stderr message line. Null when the reader reached the end of stderr. - */ - public void err(@Nullable String line); - } - - /** - * Get the stderr/stdout outputs of a process and return when the process is done. - * Both <b>must</b> be read or the process will block on windows. - * - * @param process The process to get the ouput from. - * @param output Optional object to capture stdout/stderr. - * Note that on Windows capturing the output is not optional. If output is null - * the stdout/stderr will be captured and discarded. - * @param waitMode Whether to wait for the process and/or the readers to finish. - * @return the process return code. - * @throws InterruptedException if {@link Process#waitFor()} was interrupted. - */ - public static int grabProcessOutput( - @NonNull final Process process, - Wait waitMode, - @Nullable final IProcessOutput output) throws InterruptedException { - // read the lines as they come. if null is returned, it's - // because the process finished - Thread threadErr = new Thread("stderr") { - @Override - public void run() { - // create a buffer to read the stderr output - InputStreamReader is = new InputStreamReader(process.getErrorStream()); - BufferedReader errReader = new BufferedReader(is); - - try { - while (true) { - String line = errReader.readLine(); - if (output != null) { - output.err(line); - } - if (line == null) { - break; - } - } - } catch (IOException e) { - // do nothing. - } - } - }; - - Thread threadOut = new Thread("stdout") { - @Override - public void run() { - InputStreamReader is = new InputStreamReader(process.getInputStream()); - BufferedReader outReader = new BufferedReader(is); - - try { - while (true) { - String line = outReader.readLine(); - if (output != null) { - output.out(line); - } - if (line == null) { - break; - } - } - } catch (IOException e) { - // do nothing. - } - } - }; - - threadErr.start(); - threadOut.start(); - - if (waitMode == Wait.ASYNC) { - return 0; - } - - // it looks like on windows process#waitFor() can return - // before the thread have filled the arrays, so we wait for both threads and the - // process itself. - if (waitMode == Wait.WAIT_FOR_READERS) { - try { - threadErr.join(); - } catch (InterruptedException e) { - } - try { - threadOut.join(); - } catch (InterruptedException e) { - } - } - - // get the return code from the process - return process.waitFor(); - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/util/LineUtil.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/util/LineUtil.java deleted file mode 100755 index c42bd0d..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/util/LineUtil.java +++ /dev/null @@ -1,118 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.util; - - -public abstract class LineUtil { - - /** - * Reformats a line so that it fits in 78 characters max. - * <p/> - * When wrapping the second line and following, prefix the string with a number of - * spaces. This will use the first colon (:) to determine the prefix size - * or use 4 as a minimum if there are no colons in the string. - * - * @param line The line to reflow. Must be non-null. - * @return A new line to print as-is, that contains \n as needed. - */ - public static String reflowLine(String line) { - final int maxLen = 78; - - // Most of time the line will fit in the given length and this will be a no-op - int n = line.length(); - int cr = line.indexOf('\n'); - if (n <= maxLen && (cr == -1 || cr == n - 1)) { - return line; - } - - int prefixSize = line.indexOf(':') + 1; - // If there' some spacing after the colon, use the same when wrapping - if (prefixSize > 0 && prefixSize < maxLen) { - while(prefixSize < n && line.charAt(prefixSize) == ' ') { - prefixSize++; - } - } else { - prefixSize = 4; - } - String prefix = String.format( - "%-" + Integer.toString(prefixSize) + "s", //$NON-NLS-1$ //$NON-NLS-2$ - " "); //$NON-NLS-1$ - - StringBuilder output = new StringBuilder(n + prefixSize); - - while (n > 0) { - cr = line.indexOf('\n'); - if (n <= maxLen && (cr == -1 || cr == n - 1)) { - output.append(line); - break; - } - - // Line is longer than the max length, find the first character before and after - // the whitespace where we want to break the line. - int posNext = maxLen; - if (cr != -1 && cr != n - 1 && cr <= posNext) { - posNext = cr + 1; - while (posNext < n && line.charAt(posNext) == '\n') { - posNext++; - } - } - while (posNext < n && line.charAt(posNext) == ' ') { - posNext++; - } - while (posNext > 0) { - char c = line.charAt(posNext - 1); - if (c != ' ' && c != '\n') { - posNext--; - } else { - break; - } - } - - if (posNext == 0 || (posNext >= n && maxLen < n)) { - // We found no whitespace separator. This should generally not occur. - posNext = maxLen; - } - int posPrev = posNext; - while (posPrev > 0) { - char c = line.charAt(posPrev - 1); - if (c == ' ' || c == '\n') { - posPrev--; - } else { - break; - } - } - - output.append(line.substring(0, posPrev)).append('\n'); - line = prefix + line.substring(posNext); - n = line.length(); - } - - return output.toString(); - } - - /** - * Formats the string using {@link String#format(String, Object...)} - * and then returns the result of {@link #reflowLine(String)}. - * - * @param format The string format. - * @param params The parameters for the string format. - * @return The result of {@link #reflowLine(String)} on the formatted string. - */ - public static String reformatLine(String format, Object...params) { - return reflowLine(String.format(format, params)); - } -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/util/SparseArray.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/util/SparseArray.java deleted file mode 100644 index f0693fe..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/util/SparseArray.java +++ /dev/null @@ -1,401 +0,0 @@ -/* - * Copyright (C) 2006 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.util; - - -/** - * SparseArrays map integers to Objects. Unlike a normal array of Objects, - * there can be gaps in the indices. It is intended to be more efficient - * than using a HashMap to map Integers to Objects. - */ -public class SparseArray<E> { - private static final Object DELETED = new Object(); - private boolean mGarbage = false; - - /** - * Creates a new SparseArray containing no mappings. - */ - public SparseArray() { - this(10); - } - - /** - * Creates a new SparseArray containing no mappings that will not - * require any additional memory allocation to store the specified - * number of mappings. - */ - public SparseArray(int initialCapacity) { - initialCapacity = ArrayUtils.idealIntArraySize(initialCapacity); - - mKeys = new int[initialCapacity]; - mValues = new Object[initialCapacity]; - mSize = 0; - } - - /** - * Gets the Object mapped from the specified key, or <code>null</code> - * if no such mapping has been made. - */ - public E get(int key) { - return get(key, null); - } - - /** - * Gets the Object mapped from the specified key, or the specified Object - * if no such mapping has been made. - */ - @SuppressWarnings("unchecked") - public E get(int key, E valueIfKeyNotFound) { - int i = binarySearch(mKeys, 0, mSize, key); - - if (i < 0 || mValues[i] == DELETED) { - return valueIfKeyNotFound; - } else { - return (E) mValues[i]; - } - } - - /** - * Removes the mapping from the specified key, if there was any. - */ - public void delete(int key) { - int i = binarySearch(mKeys, 0, mSize, key); - - if (i >= 0) { - if (mValues[i] != DELETED) { - mValues[i] = DELETED; - mGarbage = true; - } - } - } - - /** - * Alias for {@link #delete(int)}. - */ - public void remove(int key) { - delete(key); - } - - private void gc() { - // Log.e("SparseArray", "gc start with " + mSize); - - int n = mSize; - int o = 0; - int[] keys = mKeys; - Object[] values = mValues; - - for (int i = 0; i < n; i++) { - Object val = values[i]; - - if (val != DELETED) { - if (i != o) { - keys[o] = keys[i]; - values[o] = val; - } - - o++; - } - } - - mGarbage = false; - mSize = o; - - // Log.e("SparseArray", "gc end with " + mSize); - } - - /** - * Adds a mapping from the specified key to the specified value, - * replacing the previous mapping from the specified key if there - * was one. - */ - public void put(int key, E value) { - int i = binarySearch(mKeys, 0, mSize, key); - - if (i >= 0) { - mValues[i] = value; - } else { - i = ~i; - - if (i < mSize && mValues[i] == DELETED) { - mKeys[i] = key; - mValues[i] = value; - return; - } - - if (mGarbage && mSize >= mKeys.length) { - gc(); - - // Search again because indices may have changed. - i = ~binarySearch(mKeys, 0, mSize, key); - } - - if (mSize >= mKeys.length) { - int n = ArrayUtils.idealIntArraySize(mSize + 1); - - int[] nkeys = new int[n]; - Object[] nvalues = new Object[n]; - - // Log.e("SparseArray", "grow " + mKeys.length + " to " + n); - System.arraycopy(mKeys, 0, nkeys, 0, mKeys.length); - System.arraycopy(mValues, 0, nvalues, 0, mValues.length); - - mKeys = nkeys; - mValues = nvalues; - } - - if (mSize - i != 0) { - // Log.e("SparseArray", "move " + (mSize - i)); - System.arraycopy(mKeys, i, mKeys, i + 1, mSize - i); - System.arraycopy(mValues, i, mValues, i + 1, mSize - i); - } - - mKeys[i] = key; - mValues[i] = value; - mSize++; - } - } - - /** - * Returns the number of key-value mappings that this SparseArray - * currently stores. - */ - public int size() { - if (mGarbage) { - gc(); - } - - return mSize; - } - - /** - * Given an index in the range <code>0...size()-1</code>, returns - * the key from the <code>index</code>th key-value mapping that this - * SparseArray stores. - */ - public int keyAt(int index) { - if (mGarbage) { - gc(); - } - - return mKeys[index]; - } - - /** - * Given an index in the range <code>0...size()-1</code>, returns - * the value from the <code>index</code>th key-value mapping that this - * SparseArray stores. - */ - @SuppressWarnings("unchecked") - public E valueAt(int index) { - if (mGarbage) { - gc(); - } - - return (E) mValues[index]; - } - - /** - * Given an index in the range <code>0...size()-1</code>, sets a new - * value for the <code>index</code>th key-value mapping that this - * SparseArray stores. - */ - public void setValueAt(int index, E value) { - if (mGarbage) { - gc(); - } - - mValues[index] = value; - } - - /** - * Returns the index for which {@link #keyAt} would return the - * specified key, or a negative number if the specified - * key is not mapped. - */ - public int indexOfKey(int key) { - if (mGarbage) { - gc(); - } - - return binarySearch(mKeys, 0, mSize, key); - } - - /** - * Returns an index for which {@link #valueAt} would return the - * specified key, or a negative number if no keys map to the - * specified value. - * Beware that this is a linear search, unlike lookups by key, - * and that multiple keys can map to the same value and this will - * find only one of them. - */ - public int indexOfValue(E value) { - if (mGarbage) { - gc(); - } - - for (int i = 0; i < mSize; i++) - if (mValues[i] == value) - return i; - - return -1; - } - - /** - * Removes all key-value mappings from this SparseArray. - */ - public void clear() { - int n = mSize; - Object[] values = mValues; - - for (int i = 0; i < n; i++) { - values[i] = null; - } - - mSize = 0; - mGarbage = false; - } - - /** - * Puts a key/value pair into the array, optimizing for the case where - * the key is greater than all existing keys in the array. - */ - public void append(int key, E value) { - if (mSize != 0 && key <= mKeys[mSize - 1]) { - put(key, value); - return; - } - - if (mGarbage && mSize >= mKeys.length) { - gc(); - } - - int pos = mSize; - if (pos >= mKeys.length) { - int n = ArrayUtils.idealIntArraySize(pos + 1); - - int[] nkeys = new int[n]; - Object[] nvalues = new Object[n]; - - // Log.e("SparseArray", "grow " + mKeys.length + " to " + n); - System.arraycopy(mKeys, 0, nkeys, 0, mKeys.length); - System.arraycopy(mValues, 0, nvalues, 0, mValues.length); - - mKeys = nkeys; - mValues = nvalues; - } - - mKeys[pos] = key; - mValues[pos] = value; - mSize = pos + 1; - } - - public SparseArray<E> getUnmodifiable() { - final SparseArray<E> mStorage = this; - return new SparseArray<E>() { - - @Override - public E get(int key) { - return mStorage.get(key); - } - - @Override - public E get(int key, E valueIfKeyNotFound) { - return mStorage.get(key, valueIfKeyNotFound); - } - - @Override - public void delete(int key) { - throw new UnsupportedOperationException(); - } - - @Override - public void remove(int key) { - throw new UnsupportedOperationException(); - } - - @Override - public void put(int key, E value) { - throw new UnsupportedOperationException(); - } - - @Override - public int size() { - return mStorage.size(); - } - - @Override - public int keyAt(int index) { - return mStorage.keyAt(index); - } - - @Override - public E valueAt(int index) { - return mStorage.valueAt(index); - } - - @Override - public void setValueAt(int index, E value) { - throw new UnsupportedOperationException(); - } - - @Override - public int indexOfKey(int key) { - return mStorage.indexOfKey(key); - } - - @Override - public int indexOfValue(E value) { - return mStorage.indexOfValue(value); - } - - @Override - public void clear() { - throw new UnsupportedOperationException(); - } - - @Override - public void append(int key, E value) { - throw new UnsupportedOperationException(); - } - - }; - } - - private static int binarySearch(int[] a, int start, int len, int key) { - int high = start + len, low = start - 1, guess; - - while (high - low > 1) { - guess = (high + low) / 2; - - if (a[guess] < key) - low = guess; - else - high = guess; - } - - if (high == start + len) - return ~(start + len); - else if (a[high] == key) - return high; - else - return ~high; - } - - private int[] mKeys; - private Object[] mValues; - private int mSize; -} diff --git a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/util/SparseIntArray.java b/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/util/SparseIntArray.java deleted file mode 100644 index 9573566..0000000 --- a/sdkmanager/libs/sdklib/src/main/java/com/android/sdklib/util/SparseIntArray.java +++ /dev/null @@ -1,238 +0,0 @@ -/* - * Copyright (C) 2006 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.util; - - -/** - * SparseIntArrays map integers to integers. Unlike a normal array of integers, - * there can be gaps in the indices. It is intended to be more efficient - * than using a HashMap to map Integers to Integers. - */ -public class SparseIntArray { - /** - * Creates a new SparseIntArray containing no mappings. - */ - public SparseIntArray() { - this(10); - } - - /** - * Creates a new SparseIntArray containing no mappings that will not - * require any additional memory allocation to store the specified - * number of mappings. - */ - public SparseIntArray(int initialCapacity) { - initialCapacity = ArrayUtils.idealIntArraySize(initialCapacity); - - mKeys = new int[initialCapacity]; - mValues = new int[initialCapacity]; - mSize = 0; - } - - /** - * Gets the int mapped from the specified key, or <code>0</code> - * if no such mapping has been made. - */ - public int get(int key) { - return get(key, 0); - } - - /** - * Gets the int mapped from the specified key, or the specified value - * if no such mapping has been made. - */ - public int get(int key, int valueIfKeyNotFound) { - int i = binarySearch(mKeys, 0, mSize, key); - - if (i < 0) { - return valueIfKeyNotFound; - } else { - return mValues[i]; - } - } - - /** - * Removes the mapping from the specified key, if there was any. - */ - public void delete(int key) { - int i = binarySearch(mKeys, 0, mSize, key); - - if (i >= 0) { - removeAt(i); - } - } - - /** - * Removes the mapping at the given index. - */ - public void removeAt(int index) { - System.arraycopy(mKeys, index + 1, mKeys, index, mSize - (index + 1)); - System.arraycopy(mValues, index + 1, mValues, index, mSize - (index + 1)); - mSize--; - } - - /** - * Adds a mapping from the specified key to the specified value, - * replacing the previous mapping from the specified key if there - * was one. - */ - public void put(int key, int value) { - int i = binarySearch(mKeys, 0, mSize, key); - - if (i >= 0) { - mValues[i] = value; - } else { - i = ~i; - - if (mSize >= mKeys.length) { - int n = ArrayUtils.idealIntArraySize(mSize + 1); - - int[] nkeys = new int[n]; - int[] nvalues = new int[n]; - - // Log.e("SparseIntArray", "grow " + mKeys.length + " to " + n); - System.arraycopy(mKeys, 0, nkeys, 0, mKeys.length); - System.arraycopy(mValues, 0, nvalues, 0, mValues.length); - - mKeys = nkeys; - mValues = nvalues; - } - - if (mSize - i != 0) { - // Log.e("SparseIntArray", "move " + (mSize - i)); - System.arraycopy(mKeys, i, mKeys, i + 1, mSize - i); - System.arraycopy(mValues, i, mValues, i + 1, mSize - i); - } - - mKeys[i] = key; - mValues[i] = value; - mSize++; - } - } - - /** - * Returns the number of key-value mappings that this SparseIntArray - * currently stores. - */ - public int size() { - return mSize; - } - - /** - * Given an index in the range <code>0...size()-1</code>, returns - * the key from the <code>index</code>th key-value mapping that this - * SparseIntArray stores. - */ - public int keyAt(int index) { - return mKeys[index]; - } - - /** - * Given an index in the range <code>0...size()-1</code>, returns - * the value from the <code>index</code>th key-value mapping that this - * SparseIntArray stores. - */ - public int valueAt(int index) { - return mValues[index]; - } - - /** - * Returns the index for which {@link #keyAt} would return the - * specified key, or a negative number if the specified - * key is not mapped. - */ - public int indexOfKey(int key) { - return binarySearch(mKeys, 0, mSize, key); - } - - /** - * Returns an index for which {@link #valueAt} would return the - * specified key, or a negative number if no keys map to the - * specified value. - * Beware that this is a linear search, unlike lookups by key, - * and that multiple keys can map to the same value and this will - * find only one of them. - */ - public int indexOfValue(int value) { - for (int i = 0; i < mSize; i++) - if (mValues[i] == value) - return i; - - return -1; - } - - /** - * Removes all key-value mappings from this SparseIntArray. - */ - public void clear() { - mSize = 0; - } - - /** - * Puts a key/value pair into the array, optimizing for the case where - * the key is greater than all existing keys in the array. - */ - public void append(int key, int value) { - if (mSize != 0 && key <= mKeys[mSize - 1]) { - put(key, value); - return; - } - - int pos = mSize; - if (pos >= mKeys.length) { - int n = ArrayUtils.idealIntArraySize(pos + 1); - - int[] nkeys = new int[n]; - int[] nvalues = new int[n]; - - // Log.e("SparseIntArray", "grow " + mKeys.length + " to " + n); - System.arraycopy(mKeys, 0, nkeys, 0, mKeys.length); - System.arraycopy(mValues, 0, nvalues, 0, mValues.length); - - mKeys = nkeys; - mValues = nvalues; - } - - mKeys[pos] = key; - mValues[pos] = value; - mSize = pos + 1; - } - - private static int binarySearch(int[] a, int start, int len, int key) { - int high = start + len, low = start - 1, guess; - - while (high - low > 1) { - guess = (high + low) / 2; - - if (a[guess] < key) - low = guess; - else - high = guess; - } - - if (high == start + len) - return ~(start + len); - else if (a[high] == key) - return high; - else - return ~high; - } - - private int[] mKeys; - private int[] mValues; - private int mSize; -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/AndroidVersionTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/AndroidVersionTest.java deleted file mode 100755 index 5270bd1..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/AndroidVersionTest.java +++ /dev/null @@ -1,71 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib; - -import junit.framework.TestCase; - -/** - * Unit tests for {@link AndroidVersion}. - */ -public class AndroidVersionTest extends TestCase { - - public final void testAndroidVersion() { - AndroidVersion v = new AndroidVersion(1, " CODENAME "); - assertEquals(1, v.getApiLevel()); - assertEquals("CODENAME", v.getApiString()); - assertTrue(v.isPreview()); - assertEquals("CODENAME", v.getCodename()); - assertEquals("CODENAME".hashCode(), v.hashCode()); - assertEquals("API 1, CODENAME preview", v.toString()); - - v = new AndroidVersion(15, "REL"); - assertEquals(15, v.getApiLevel()); - assertEquals("15", v.getApiString()); - assertFalse(v.isPreview()); - assertNull(v.getCodename()); - assertTrue(v.equals(15)); - assertEquals(15, v.hashCode()); - assertEquals("API 15", v.toString()); - - v = new AndroidVersion(15, null); - assertEquals(15, v.getApiLevel()); - assertEquals("15", v.getApiString()); - assertFalse(v.isPreview()); - assertNull(v.getCodename()); - assertTrue(v.equals(15)); - assertEquals(15, v.hashCode()); - assertEquals("API 15", v.toString()); - - // An empty codename is like a null codename - v = new AndroidVersion(15, " "); - assertFalse(v.isPreview()); - assertNull(v.getCodename()); - assertEquals("15", v.getApiString()); - - v = new AndroidVersion(15, ""); - assertFalse(v.isPreview()); - assertNull(v.getCodename()); - assertEquals("15", v.getApiString()); - - assertTrue(v.isGreaterOrEqualThan(0)); - assertTrue(v.isGreaterOrEqualThan(14)); - assertTrue(v.isGreaterOrEqualThan(15)); - assertFalse(v.isGreaterOrEqualThan(16)); - assertFalse(v.isGreaterOrEqualThan(Integer.MAX_VALUE)); - } - -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/LayoutlibVersionTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/LayoutlibVersionTest.java deleted file mode 100755 index 0c197aa..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/LayoutlibVersionTest.java +++ /dev/null @@ -1,51 +0,0 @@ -/* - * Copyright (C) 2011 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.sdklib; - -import com.android.sdklib.SdkManager.LayoutlibVersion; - -import junit.framework.TestCase; - -/** - * Unit test for {@link LayoutlibVersion}. - */ -public class LayoutlibVersionTest extends TestCase { - - public void testLayoutlibVersion_create() { - LayoutlibVersion lv = new LayoutlibVersion(1, 2); - assertEquals(1, lv.getApi()); - assertEquals(2, lv.getRevision()); - } - - public void testLayoutlibVersion_compare() { - assertTrue(new LayoutlibVersion(1, 1).compareTo(new LayoutlibVersion(1, 1)) == 0); - assertTrue(new LayoutlibVersion(1, 2).compareTo(new LayoutlibVersion(1, 1)) > 0); - assertTrue(new LayoutlibVersion(1, 1).compareTo(new LayoutlibVersion(1, 2)) < 0); - assertTrue(new LayoutlibVersion(2, 2).compareTo(new LayoutlibVersion(1, 3)) > 0); - - // the lack of an API (== 0) naturally sorts as the lowest value possible. - assertTrue(new LayoutlibVersion(0, 1).compareTo(new LayoutlibVersion(0, 2)) < 0); - assertTrue(new LayoutlibVersion(0, 1).compareTo(new LayoutlibVersion(1, 2)) < 0); - assertTrue(new LayoutlibVersion(0, 3).compareTo(new LayoutlibVersion(1, 2)) < 0); - assertTrue(new LayoutlibVersion(1, 2).compareTo(new LayoutlibVersion(0, 3)) > 0); - - // if we lack the revision number, we don't use it in comparison - assertTrue(new LayoutlibVersion(2, 0).compareTo(new LayoutlibVersion(2, 2)) == 0); - assertTrue(new LayoutlibVersion(2, 2).compareTo(new LayoutlibVersion(2, 0)) == 0); - } - -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/SdkManagerTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/SdkManagerTest.java deleted file mode 100755 index 487a96a..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/SdkManagerTest.java +++ /dev/null @@ -1,152 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib; - - -import com.android.SdkConstants; -import com.android.sdklib.ISystemImage.LocationType; -import com.android.sdklib.SdkManager.LayoutlibVersion; - -import java.util.Arrays; -import java.util.regex.Pattern; - -public class SdkManagerTest extends SdkManagerTestCase { - - @SuppressWarnings("deprecation") - public void testSdkManager_LayoutlibVersion() { - SdkManager sdkman = getSdkManager(); - IAndroidTarget t = sdkman.getTargets()[0]; - - assertTrue(t instanceof PlatformTarget); - - LayoutlibVersion lv = ((PlatformTarget) t).getLayoutlibVersion(); - assertNotNull(lv); - assertEquals(5, lv.getApi()); - assertEquals(2, lv.getRevision()); - - assertSame(lv, sdkman.getMaxLayoutlibVersion()); - } - - public void testSdkManager_SystemImage() throws Exception { - SdkManager sdkman = getSdkManager(); - assertEquals("[PlatformTarget API 0 rev 1]", Arrays.toString(sdkman.getTargets())); - IAndroidTarget t = sdkman.getTargets()[0]; - - // By default SdkManagerTestCase creates an SDK with one platform containing - // a legacy armeabi system image. - assertEquals( - "[SystemImage ABI=armeabi, location in platform legacy='$SDK/platforms/v0_0/images']", - cleanPath(sdkman, Arrays.toString(t.getSystemImages()))); - - // Now add a few "platform subfolders" system images and reload the SDK. - // This disables the "legacy" mode, which means that although the armeabi - // target from above is present, it is no longer visible. - - makeSystemImageFolder(new SystemImage( - sdkman, t, LocationType.IN_PLATFORM_SUBFOLDER, SdkConstants.ABI_ARMEABI_V7A)); - makeSystemImageFolder(new SystemImage( - sdkman, t, LocationType.IN_PLATFORM_SUBFOLDER, SdkConstants.ABI_INTEL_ATOM)); - - sdkman.reloadSdk(getLog()); - assertEquals("[PlatformTarget API 0 rev 1]", Arrays.toString(sdkman.getTargets())); - t = sdkman.getTargets()[0]; - - assertEquals( - "[SystemImage ABI=armeabi-v7a, location in platform subfolder='$SDK/platforms/v0_0/images/armeabi-v7a', " + - "SystemImage ABI=x86, location in platform subfolder='$SDK/platforms/v0_0/images/x86']", - cleanPath(sdkman, Arrays.toString(t.getSystemImages()))); - - // Now add arm + arm v7a images using the new SDK/system-images. - // The x86 one from the platform subfolder is still visible. - // The armeabi one from the legacy folder is overridden by the new one. - // The armeabi-v7a one from the platform subfolder is overridden by the new one. - - makeSystemImageFolder(new SystemImage( - sdkman, t, LocationType.IN_SYSTEM_IMAGE, SdkConstants.ABI_ARMEABI)); - makeSystemImageFolder(new SystemImage( - sdkman, t, LocationType.IN_SYSTEM_IMAGE, SdkConstants.ABI_ARMEABI_V7A)); - - sdkman.reloadSdk(getLog()); - assertEquals("[PlatformTarget API 0 rev 1]", Arrays.toString(sdkman.getTargets())); - t = sdkman.getTargets()[0]; - - assertEquals( - "[SystemImage ABI=armeabi, location in system image='$SDK/system-images/android-0/armeabi', " + - "SystemImage ABI=armeabi-v7a, location in system image='$SDK/system-images/android-0/armeabi-v7a', " + - "SystemImage ABI=x86, location in platform subfolder='$SDK/platforms/v0_0/images/x86']", - cleanPath(sdkman, Arrays.toString(t.getSystemImages()))); - } - - public void testSdkManager_SystemImage_LegacyOverride() throws Exception { - SdkManager sdkman = getSdkManager(); - assertEquals("[PlatformTarget API 0 rev 1]", Arrays.toString(sdkman.getTargets())); - IAndroidTarget t = sdkman.getTargets()[0]; - - // By default SdkManagerTestCase creates an SDK with one platform containing - // a legacy armeabi system image. - assertEquals( - "[SystemImage ABI=armeabi, location in platform legacy='$SDK/platforms/v0_0/images']", - cleanPath(sdkman, Arrays.toString(t.getSystemImages()))); - - // Now add a different ABI system image in the new system-images folder. - // This does not hide the legacy one as long as the ABI type is different - // (to contrast: having at least one sub-folder in the platform's legacy images folder - // will hide the legacy system image. Whereas this does not happen with the new type.) - - makeSystemImageFolder(new SystemImage( - sdkman, t, LocationType.IN_SYSTEM_IMAGE, SdkConstants.ABI_INTEL_ATOM)); - - sdkman.reloadSdk(getLog()); - assertEquals("[PlatformTarget API 0 rev 1]", Arrays.toString(sdkman.getTargets())); - t = sdkman.getTargets()[0]; - - assertEquals( - "[SystemImage ABI=armeabi, location in platform legacy='$SDK/platforms/v0_0/images', " + - "SystemImage ABI=x86, location in system image='$SDK/system-images/android-0/x86']", - cleanPath(sdkman, Arrays.toString(t.getSystemImages()))); - - // Now if we have one new system-image using the same ABI type, it will override the - // legacy one. This gives us a good path for updates. - - makeSystemImageFolder(new SystemImage( - sdkman, t, LocationType.IN_SYSTEM_IMAGE, SdkConstants.ABI_ARMEABI)); - - - sdkman.reloadSdk(getLog()); - assertEquals("[PlatformTarget API 0 rev 1]", Arrays.toString(sdkman.getTargets())); - t = sdkman.getTargets()[0]; - - assertEquals( - "[SystemImage ABI=armeabi, location in system image='$SDK/system-images/android-0/armeabi', " + - "SystemImage ABI=x86, location in system image='$SDK/system-images/android-0/x86']", - cleanPath(sdkman, Arrays.toString(t.getSystemImages()))); - } - - /** - * Sanitizes the paths used when testing results. - * <p/> - * The system image text representation contains the absolute path to the SDK. - * However the SDK path is actually a randomized location. - * We clean it by replacing it by the constant '$SDK'. - * Also all the Windows path separators are converted to unix-like / separators. - */ - private String cleanPath(SdkManager sdkman, String string) { - return string - .replaceAll(Pattern.quote(sdkman.getLocation()), "\\$SDK") //$NON-NLS-1$ - .replace('\\', '/'); - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/SdkManagerTestCase.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/SdkManagerTestCase.java deleted file mode 100755 index 86a555a..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/SdkManagerTestCase.java +++ /dev/null @@ -1,264 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib; - - -import com.android.SdkConstants; -import com.android.prefs.AndroidLocation; -import com.android.prefs.AndroidLocation.AndroidLocationException; -import com.android.sdklib.internal.avd.AvdManager; -import com.android.sdklib.io.FileOp; -import com.android.sdklib.mock.MockLog; -import com.android.sdklib.repository.PkgProps; -import com.android.utils.ILogger; - -import java.io.File; -import java.io.FileWriter; -import java.io.IOException; - -import junit.framework.TestCase; - -/** - * Test case that allocates a temporary SDK, a temporary AVD base folder - * with an SdkManager and an AvdManager that points to them. - */ -public class SdkManagerTestCase extends TestCase { - - private File mFakeSdk; - private MockLog mLog; - private SdkManager mSdkManager; - private TmpAvdManager mAvdManager; - - /** Returns the {@link MockLog} for this test case. */ - public MockLog getLog() { - return mLog; - } - - /** Returns the {@link SdkManager} for this test case. */ - public SdkManager getSdkManager() { - return mSdkManager; - } - - /** Returns the {@link AvdManager} for this test case. */ - public TmpAvdManager getAvdManager() { - return mAvdManager; - } - - /** - * Sets up a {@link MockLog}, a fake SDK in a temporary directory - * and an AVD Manager pointing to an initially-empty AVD directory. - */ - @Override - public void setUp() throws Exception { - mLog = new MockLog(); - mFakeSdk = makeFakeSdk(); - mSdkManager = SdkManager.createManager(mFakeSdk.getAbsolutePath(), mLog); - assertNotNull("SdkManager location was invalid", mSdkManager); - - mAvdManager = new TmpAvdManager(mSdkManager, mLog); - } - - /** - * Removes the temporary SDK and AVD directories. - */ - @Override - public void tearDown() throws Exception { - deleteDir(mFakeSdk); - } - - /** - * A empty test method to placate the JUnit test runner, which doesn't - * like TestCase classes with no test methods. - */ - public void testPlaceholder() { - } - - /** - * An {@link AvdManager} that uses a temporary directory - * located <em>inside</em> the SDK directory for testing. - * The AVD list should be initially empty. - */ - protected static class TmpAvdManager extends AvdManager { - - /* - * Implementation detail: - * - When the super.AvdManager constructor is invoked, it will invoke - * the buildAvdFilesList() to fill the initial AVD list, which will in - * turn call getBaseAvdFolder(). - * - That's why mTmpAvdRoot is initialized in getAvdRoot() rather than - * in the constructor, since we can't initialize fields before the super() - * call. - */ - - /** - * AVD Root, initialized "lazily" when the AVD root is first requested. - */ - private File mTmpAvdRoot; - - public TmpAvdManager(SdkManager sdkManager, ILogger log) throws AndroidLocationException { - super(sdkManager, log); - } - - @Override - public String getBaseAvdFolder() throws AndroidLocationException { - if (mTmpAvdRoot == null) { - mTmpAvdRoot = new File(getSdkManager().getLocation(), "tmp_avds"); - mTmpAvdRoot.mkdirs(); - } - return mTmpAvdRoot.getAbsolutePath(); - } - } - - /** - * Build enough of a skeleton SDK to make the tests pass. - * <p/> - * Ideally this wouldn't touch the file system but the current - * structure of the SdkManager and AvdManager makes this difficult. - * - * @return Path to the temporary SDK root - * @throws IOException - */ - private File makeFakeSdk() throws IOException { - // First we create a temp file to "reserve" the temp directory name we want to use. - File sdkDir = File.createTempFile( - this.getClass().getSimpleName() + '_' + this.getName(), null); - // Then erase the file and make the directory - sdkDir.delete(); - sdkDir.mkdirs(); - - AndroidLocation.resetFolder(); - File addonsDir = new File(sdkDir, SdkConstants.FD_ADDONS); - addonsDir.mkdir(); - - File toolsDir = new File(sdkDir, SdkConstants.OS_SDK_TOOLS_FOLDER); - toolsDir.mkdir(); - new File(toolsDir, SdkConstants.androidCmdName()).createNewFile(); - new File(toolsDir, SdkConstants.FN_EMULATOR).createNewFile(); - - // TODO makePlatformTools with at least a source props - - File toolsLibEmuDir = new File(sdkDir, SdkConstants.OS_SDK_TOOLS_LIB_FOLDER + "emulator"); - toolsLibEmuDir.mkdirs(); - new File(toolsLibEmuDir, "snapshots.img").createNewFile(); - File platformsDir = new File(sdkDir, SdkConstants.FD_PLATFORMS); - - // Creating a fake target here on down - File targetDir = makeFakeTargetInternal(platformsDir); - - File imagesDir = new File(targetDir, "images"); - makeFakeSysImgInternal(imagesDir, SdkConstants.ABI_ARMEABI); - - makeFakeSkinInternal(targetDir); - makeFakeSourceInternal(sdkDir); - return sdkDir; - } - - /** - * Creates the system image folder and places a fake userdata.img in it. - * - * @param systemImage A system image with a valid location. - * @throws IOException if the file fails to be created. - */ - protected void makeSystemImageFolder(ISystemImage systemImage) throws IOException { - File imagesDir = systemImage.getLocation(); - imagesDir.mkdirs(); - - makeFakeSysImgInternal(imagesDir, systemImage.getAbiType()); - } - - //---- - - /** Utility used by {@link #makeFakeSdk()} to create a fake target with API 0, rev 0. */ - private File makeFakeTargetInternal(File platformsDir) throws IOException { - File targetDir = new File(platformsDir, "v0_0"); - targetDir.mkdirs(); - new File(targetDir, SdkConstants.FN_FRAMEWORK_LIBRARY).createNewFile(); - new File(targetDir, SdkConstants.FN_FRAMEWORK_AIDL).createNewFile(); - - File sourceProp = new File(targetDir, SdkConstants.FN_SOURCE_PROP); - sourceProp.createNewFile(); - FileWriter out = new FileWriter(sourceProp); - out.write(PkgProps.LAYOUTLIB_API + "=5\n"); - out.write(PkgProps.LAYOUTLIB_REV + "=2\n"); - out.close(); - - File buildProp = new File(targetDir, SdkConstants.FN_BUILD_PROP); - out = new FileWriter(buildProp); - out.write(SdkManager.PROP_VERSION_RELEASE + "=0.0\n"); - out.write(SdkManager.PROP_VERSION_SDK + "=0\n"); - out.write(SdkManager.PROP_VERSION_CODENAME + "=REL\n"); - out.close(); - return targetDir; - } - - /** Utility to create a fake sys image in the given folder. */ - private void makeFakeSysImgInternal(File imagesDir, String abiType) throws IOException { - imagesDir.mkdirs(); - new File(imagesDir, "userdata.img").createNewFile(); - - File sourceProp = new File(imagesDir, SdkConstants.FN_SOURCE_PROP); - sourceProp.createNewFile(); - FileWriter out = new FileWriter(sourceProp); - out.write(PkgProps.VERSION_API_LEVEL + "=0\n"); - out.write(PkgProps.SYS_IMG_ABI + "=" + abiType + "\n"); - out.close(); - } - - /** Utility to make a fake skin for the given target */ - private void makeFakeSkinInternal(File targetDir) { - FileOp.append(targetDir, "skins", "HVGA").mkdirs(); - } - - /** Utility to create a fake source with a few files in the given sdk folder. */ - private void makeFakeSourceInternal(File sdkDir) throws IOException { - File sourcesDir = FileOp.append(sdkDir, SdkConstants.FD_PKG_SOURCES, "android-0"); - sourcesDir.mkdirs(); - - File sourceProp = new File(sourcesDir, SdkConstants.FN_SOURCE_PROP); - sourceProp.createNewFile(); - FileWriter out = new FileWriter(sourceProp); - out.write(PkgProps.VERSION_API_LEVEL + "=0\n"); - out.close(); - - File dir1 = FileOp.append(sourcesDir, "src", "com", "android"); - dir1.mkdirs(); - FileOp.append(dir1, "File1.java").createNewFile(); - FileOp.append(dir1, "File2.java").createNewFile(); - - FileOp.append(sourcesDir, "res", "values").mkdirs(); - FileOp.append(sourcesDir, "res", "values", "styles.xml").createNewFile(); - } - - /** - * Recursive delete directory. Mostly for fake SDKs. - * - * @param root directory to delete - */ - private void deleteDir(File root) { - if (root.exists()) { - for (File file : root.listFiles()) { - if (file.isDirectory()) { - deleteDir(file); - } else { - file.delete(); - } - } - root.delete(); - } - } - -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/devices/DeviceParserTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/devices/DeviceParserTest.java deleted file mode 100644 index f24fbda..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/devices/DeviceParserTest.java +++ /dev/null @@ -1,183 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.devices; - -import java.io.InputStream; -import java.util.HashMap; -import java.util.List; -import java.util.Map; -import java.util.Set; - -import junit.framework.TestCase; - -import org.xml.sax.SAXParseException; - -import com.android.dvlib.DeviceSchemaTest; -import com.android.resources.Density; -import com.android.resources.Keyboard; -import com.android.resources.KeyboardState; -import com.android.resources.Navigation; -import com.android.resources.NavigationState; -import com.android.resources.ScreenOrientation; -import com.android.resources.ScreenRatio; -import com.android.resources.ScreenSize; -import com.android.resources.TouchScreen; -import com.android.sdklib.devices.Storage.Unit; - -public class DeviceParserTest extends TestCase { - - public void testValidDevices() throws Exception { - InputStream devicesFile = DeviceSchemaTest.class.getResourceAsStream("devices_minimal.xml"); - List<Device> devices = DeviceParser.parse(devicesFile); - assertEquals("Parsing devices_minimal.xml produces the wrong number of devices", 1, - devices.size()); - - Device device = devices.get(0); - assertEquals("Galaxy Nexus", device.getName()); - assertEquals("Samsung", device.getManufacturer()); - - // Test Meta information - Meta meta = device.getMeta(); - assertFalse(meta.hasIconSixtyFour()); - assertFalse(meta.hasIconSixteen()); - assertFalse(meta.hasFrame()); - - // Test Hardware information - Hardware hw = device.getDefaultHardware(); - Screen screen = hw.getScreen(); - assertEquals(screen.getSize(), ScreenSize.NORMAL); - assertEquals(4.65, screen.getDiagonalLength()); - assertEquals(Density.XHIGH, screen.getPixelDensity()); - assertEquals(ScreenRatio.LONG, screen.getRatio()); - assertEquals(720, screen.getXDimension()); - assertEquals(1280, screen.getYDimension()); - assertEquals(316.0, screen.getXdpi()); - assertEquals(316.0, screen.getYdpi()); - assertEquals(Multitouch.JAZZ_HANDS, screen.getMultitouch()); - assertEquals(TouchScreen.FINGER, screen.getMechanism()); - assertEquals(ScreenType.CAPACITIVE, screen.getScreenType()); - Set<Network> networks = hw.getNetworking(); - assertTrue(networks.contains(Network.BLUETOOTH)); - assertTrue(networks.contains(Network.WIFI)); - assertTrue(networks.contains(Network.NFC)); - Set<Sensor> sensors = hw.getSensors(); - assertTrue(sensors.contains(Sensor.ACCELEROMETER)); - assertTrue(sensors.contains(Sensor.BAROMETER)); - assertTrue(sensors.contains(Sensor.GYROSCOPE)); - assertTrue(sensors.contains(Sensor.COMPASS)); - assertTrue(sensors.contains(Sensor.GPS)); - assertTrue(sensors.contains(Sensor.PROXIMITY_SENSOR)); - assertTrue(hw.hasMic()); - assertEquals(2, hw.getCameras().size()); - Camera c = hw.getCamera(CameraLocation.FRONT); - assertTrue(c != null); - assertEquals(c.getLocation(), CameraLocation.FRONT); - assertFalse(c.hasFlash()); - assertTrue(c.hasAutofocus()); - c = hw.getCamera(CameraLocation.BACK); - assertTrue(c != null); - assertEquals(c.getLocation(), CameraLocation.BACK); - assertTrue(c.hasFlash()); - assertTrue(c.hasAutofocus()); - assertEquals(Keyboard.NOKEY, hw.getKeyboard()); - assertEquals(Navigation.NONAV, hw.getNav()); - assertEquals(new Storage(1, Unit.GiB), hw.getRam()); - assertEquals(ButtonType.SOFT, hw.getButtonType()); - List<Storage> storage = hw.getInternalStorage(); - assertEquals(1, storage.size()); - assertEquals(new Storage(16, Unit.GiB), storage.get(0)); - storage = hw.getRemovableStorage(); - assertEquals(0, storage.size()); - assertEquals("OMAP 4460", hw.getCpu()); - assertEquals("PowerVR SGX540", hw.getGpu()); - Set<Abi> abis = hw.getSupportedAbis(); - assertEquals(2, abis.size()); - assertTrue(abis.contains(Abi.ARMEABI)); - assertTrue(abis.contains(Abi.ARMEABI_V7A)); - assertEquals(0, hw.getSupportedUiModes().size()); - assertEquals(PowerType.BATTERY, hw.getChargeType()); - - // Test Software - assertEquals(1, device.getAllSoftware().size()); - Software sw = device.getSoftware(15); - assertEquals(15, sw.getMaxSdkLevel()); - assertEquals(15, sw.getMinSdkLevel()); - assertTrue(sw.hasLiveWallpaperSupport()); - assertEquals(12, sw.getBluetoothProfiles().size()); - assertTrue(sw.getBluetoothProfiles().contains(BluetoothProfile.A2DP)); - assertEquals("2.0", sw.getGlVersion()); - assertEquals(29, sw.getGlExtensions().size()); - assertTrue(sw.getGlExtensions().contains("GL_OES_depth24")); - - // Test States - assertEquals(2, device.getAllStates().size()); - State s = device.getDefaultState(); - assertEquals("Portrait", s.getName()); - assertTrue(s.isDefaultState()); - assertEquals("The phone in portrait view", s.getDescription()); - assertEquals(ScreenOrientation.PORTRAIT, s.getOrientation()); - assertEquals(KeyboardState.SOFT, s.getKeyState()); - assertEquals(NavigationState.HIDDEN, s.getNavState()); - s = device.getState("Landscape"); - assertEquals("Landscape", s.getName()); - assertFalse(s.isDefaultState()); - assertEquals(ScreenOrientation.LANDSCAPE, s.getOrientation()); - } - - public void testApiRange() throws Exception { - Map<String, String> replacements = new HashMap<String, String>(); - replacements.put("api-level", "1-"); - InputStream stream = DeviceSchemaTest.getReplacedStream(replacements); - List<Device> devices = DeviceParser.parse(stream); - assertEquals(1, devices.size()); - Device device = devices.get(0); - assertTrue(device.getSoftware(1) != null); - assertTrue(device.getSoftware(2) != null); - assertTrue(device.getSoftware(0) == null); - replacements.put("api-level", "-2"); - stream = DeviceSchemaTest.getReplacedStream(replacements); - device = DeviceParser.parse(stream).get(0); - assertTrue(device.getSoftware(2) != null); - assertTrue(device.getSoftware(3) == null); - replacements.put("api-level", "1-2"); - stream = DeviceSchemaTest.getReplacedStream(replacements); - device = DeviceParser.parse(stream).get(0); - assertTrue(device.getSoftware(0) == null); - assertTrue(device.getSoftware(1) != null); - assertTrue(device.getSoftware(2) != null); - assertTrue(device.getSoftware(3) == null); - replacements.put("api-level", "-"); - stream = DeviceSchemaTest.getReplacedStream(replacements); - device = DeviceParser.parse(stream).get(0); - assertTrue(device.getSoftware(0) != null); - assertTrue(device.getSoftware(15) != null); - } - - public void testBadNetworking() throws Exception { - Map<String, String> replacements = new HashMap<String, String>(); - replacements.put("networking", "NFD"); - InputStream stream = DeviceSchemaTest.getReplacedStream(replacements); - try { - List<Device> devices = DeviceParser.parse(stream); - assertEquals(1, devices.size()); - assertEquals(0, devices.get(0).getDefaultHardware().getNetworking().size()); - fail(); - } catch (SAXParseException e) { - assertTrue(e.getMessage().startsWith("cvc-enumeration-valid: Value 'NFD'")); - } - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/devices/DeviceWriterTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/devices/DeviceWriterTest.java deleted file mode 100644 index e8053be..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/devices/DeviceWriterTest.java +++ /dev/null @@ -1,148 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.devices; - -import com.android.dvlib.DeviceSchemaTest; - -import junit.framework.TestCase; - -import java.io.ByteArrayInputStream; -import java.io.ByteArrayOutputStream; -import java.io.InputStream; -import java.util.HashMap; -import java.util.List; -import java.util.Locale; -import java.util.Map; - -@SuppressWarnings("javadoc") -public class DeviceWriterTest extends TestCase { - - public void testWriteIsValid() throws Exception { - InputStream devicesFile = - DeviceSchemaTest.class.getResourceAsStream("devices.xml"); - List<Device> devices = DeviceParser.parse(devicesFile); - assertEquals("Parsed devices contained an un expected number of devices", - 2, devices.size()); - ByteArrayOutputStream baos = new ByteArrayOutputStream(); - DeviceWriter.writeToXml(baos, devices); - List<Device> writtenDevices = DeviceParser.parse( - new ByteArrayInputStream(baos.toString().getBytes())); - assertEquals("Writing and reparsing returns a different number of devices", - devices.size(), writtenDevices.size()); - for (int i = 0; i < devices.size(); i++){ - assertEquals(devices.get(i), writtenDevices.get(i)); - } - } - - public void testLocale() throws Exception { - Locale prevLocale = Locale.getDefault(); - try { - Locale.setDefault(Locale.FRANCE); - InputStream devicesFile = - DeviceSchemaTest.class.getResourceAsStream("devices.xml"); - List<Device> devices = DeviceParser.parse(devicesFile); - assertEquals("Parsed devices contained an un expected number of devices", - 2, devices.size()); - ByteArrayOutputStream baos = new ByteArrayOutputStream(); - DeviceWriter.writeToXml(baos, devices); - String xml = baos.toString(); - assertTrue(xml.contains(".00")); - assertFalse(xml.contains(",00")); - } finally { - Locale.setDefault(prevLocale); - } - } - - public void testApiLowerBound() throws Exception { - Map<String, String> replacements = new HashMap<String, String>(); - replacements.put("api-level", "1-"); - InputStream stream = DeviceSchemaTest.getReplacedStream(replacements); - List<Device> devices = DeviceParser.parse(stream); - ByteArrayOutputStream baos = new ByteArrayOutputStream(); - DeviceWriter.writeToXml(baos, devices); - List<Device> writtenDevices = DeviceParser.parse( - new ByteArrayInputStream(baos.toString().getBytes())); - assertEquals("Writing and reparsing returns a different number of devices", - devices.size(), writtenDevices.size()); - for (int i = 0; i < devices.size(); i++){ - assertEquals(devices.get(i), writtenDevices.get(i)); - } - } - - public void testApiUpperBound() throws Exception { - Map<String, String> replacements = new HashMap<String, String>(); - replacements.put("api-level", "-10"); - InputStream stream = DeviceSchemaTest.getReplacedStream(replacements); - List<Device> devices = DeviceParser.parse(stream); - ByteArrayOutputStream baos = new ByteArrayOutputStream(); - DeviceWriter.writeToXml(baos, devices); - List<Device> writtenDevices = DeviceParser.parse( - new ByteArrayInputStream(baos.toString().getBytes())); - assertEquals("Writing and reparsing returns a different number of devices", - devices.size(), writtenDevices.size()); - for (int i = 0; i < devices.size(); i++){ - assertEquals(devices.get(i), writtenDevices.get(i)); - } - } - - public void testApiNeitherBound() throws Exception { - Map<String, String> replacements = new HashMap<String, String>(); - replacements.put("api-level", "-"); - InputStream stream = DeviceSchemaTest.getReplacedStream(replacements); - List<Device> devices = DeviceParser.parse(stream); - ByteArrayOutputStream baos = new ByteArrayOutputStream(); - DeviceWriter.writeToXml(baos, devices); - List<Device> writtenDevices = DeviceParser.parse( - new ByteArrayInputStream(baos.toString().getBytes())); - assertEquals("Writing and reparsing returns a different number of devices", - devices.size(), writtenDevices.size()); - for (int i = 0; i < devices.size(); i++){ - assertEquals(devices.get(i), writtenDevices.get(i)); - } - } - - public void testApiBothBound() throws Exception { - Map<String, String> replacements = new HashMap<String, String>(); - replacements.put("api-level", "9-10"); - InputStream stream = DeviceSchemaTest.getReplacedStream(replacements); - List<Device> devices = DeviceParser.parse(stream); - ByteArrayOutputStream baos = new ByteArrayOutputStream(); - DeviceWriter.writeToXml(baos, devices); - List<Device> writtenDevices = DeviceParser.parse( - new ByteArrayInputStream(baos.toString().getBytes())); - assertEquals("Writing and reparsing returns a different number of devices", - devices.size(), writtenDevices.size()); - for (int i = 0; i < devices.size(); i++){ - assertEquals(devices.get(i), writtenDevices.get(i)); - } - } - public void testApiSingle() throws Exception { - Map<String, String> replacements = new HashMap<String, String>(); - replacements.put("api-level", "10"); - InputStream stream = DeviceSchemaTest.getReplacedStream(replacements); - List<Device> devices = DeviceParser.parse(stream); - ByteArrayOutputStream baos = new ByteArrayOutputStream(); - DeviceWriter.writeToXml(baos, devices); - List<Device> writtenDevices = DeviceParser.parse( - new ByteArrayInputStream(baos.toString().getBytes())); - assertEquals("Writing and reparsing returns a different number of devices", - devices.size(), writtenDevices.size()); - for (int i = 0; i < devices.size(); i++){ - assertEquals(devices.get(i), writtenDevices.get(i)); - } - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/build/DebugKeyProviderTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/build/DebugKeyProviderTest.java deleted file mode 100755 index ead66ee..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/build/DebugKeyProviderTest.java +++ /dev/null @@ -1,126 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.build; - -import com.android.sdklib.internal.build.DebugKeyProvider.IKeyGenOutput; - -import java.io.File; -import java.security.PrivateKey; -import java.security.cert.X509Certificate; -import java.util.Calendar; - -import junit.framework.TestCase; - -public class DebugKeyProviderTest extends TestCase { - - private File mTmpFile; - - @Override - protected void setUp() throws Exception { - super.setUp(); - - // We want to allocate a new tmp file but not have it actually exist - mTmpFile = File.createTempFile(this.getClass().getSimpleName(), ".keystore"); - assertTrue(mTmpFile.delete()); - } - - @Override - protected void tearDown() throws Exception { - super.tearDown(); - if (mTmpFile != null) { - if (!mTmpFile.delete()) { - mTmpFile.deleteOnExit(); - } - mTmpFile = null; - } - } - - public void testCreateAndCheckKey() throws Exception { - String osPath = mTmpFile.getAbsolutePath(); - - KeygenOutput keygenOutput = new KeygenOutput(); - - // "now" is just slightly before the key was created - long now = System.currentTimeMillis(); - - DebugKeyProvider provider; - try { - provider = new DebugKeyProvider(osPath, null /*storeType*/, keygenOutput); - } catch (Throwable t) { - // In case we get any kind of exception, rewrap it to make sure we output - // the path used. - String msg = String.format("%1$s in %2$s\n%3$s", - t.getClass().getSimpleName(), osPath, t.toString()); - throw new Exception(msg, t); - } - assertNotNull(provider); - - assertEquals("", keygenOutput.getOut()); - assertEquals("", keygenOutput.getErr()); - - PrivateKey key = provider.getDebugKey(); - assertNotNull(key); - - X509Certificate certificate = (X509Certificate) provider.getCertificate(); - assertNotNull(certificate); - - // The "not-after" (a.k.a. expiration) date should be after "now" - Calendar c = Calendar.getInstance(); - c.setTimeInMillis(now); - assertTrue(certificate.getNotAfter().compareTo(c.getTime()) > 0); - - // It should be valid after 1 year from now (adjust by a second since the 'now' time - // doesn't exactly match the creation time... 1 second should be enough.) - c.add(Calendar.DAY_OF_YEAR, 365); - c.add(Calendar.SECOND, -1); - assertTrue("1 year expiration failed", - certificate.getNotAfter().compareTo(c.getTime()) > 0); - - // and 30 years from now - c.add(Calendar.DAY_OF_YEAR, 29 * 365); - assertTrue("30 year expiration failed", - certificate.getNotAfter().compareTo(c.getTime()) > 0); - - // however expiration date should be passed in 30 years + 1 hour - c.add(Calendar.HOUR, 1); - assertFalse("30 year and 1 hour expiration failed", - certificate.getNotAfter().compareTo(c.getTime()) > 0); - } - - private static class KeygenOutput implements IKeyGenOutput { - private String mOut = ""; //$NON-NLS-1$ - private String mErr = ""; //$NON-NLS-1$ - - @Override - public void out(String message) { - mOut += message + "\n"; //$NON-NLS-1$ - } - - @Override - public void err(String message) { - mErr += message + "\n"; //$NON-NLS-1$ - } - - public String getOut() { - return mOut; - } - - public String getErr() { - return mErr; - } - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/build/SymbolLoaderTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/build/SymbolLoaderTest.java deleted file mode 100644 index a972dfa..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/build/SymbolLoaderTest.java +++ /dev/null @@ -1,59 +0,0 @@ -/* - * Copyright (C) 2012 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.sdklib.internal.build; - -import com.android.sdklib.internal.build.SymbolLoader.SymbolEntry; -import com.google.common.base.Charsets; -import com.google.common.collect.Table; -import com.google.common.io.Files; - -import java.io.File; - -import junit.framework.TestCase; - -@SuppressWarnings("javadoc") -public class SymbolLoaderTest extends TestCase { - public void test() throws Exception { - String r = "" + - "int xml authenticator 0x7f040000\n"; - File file = File.createTempFile(getClass().getSimpleName(), "txt"); - file.deleteOnExit(); - Files.write(r, file, Charsets.UTF_8); - SymbolLoader loader = new SymbolLoader(file); - loader.load(); - Table<String, String, SymbolEntry> symbols = loader.getSymbols(); - assertNotNull(symbols); - assertEquals(1, symbols.size()); - assertNotNull(symbols.get("xml", "authenticator")); - assertEquals("0x7f040000", symbols.get("xml", "authenticator").getValue()); - } - - public void testStyleables() throws Exception { - String r = "" + - "int[] styleable LimitedSizeLinearLayout { 0x7f010000, 0x7f010001 }\n" + - "int styleable LimitedSizeLinearLayout_max_height 1\n" + - "int styleable LimitedSizeLinearLayout_max_width 0\n" + - "int xml authenticator 0x7f040000\n"; - File file = File.createTempFile(getClass().getSimpleName(), "txt"); - file.deleteOnExit(); - Files.write(r, file, Charsets.UTF_8); - SymbolLoader loader = new SymbolLoader(file); - loader.load(); - Table<String, String, SymbolEntry> symbols = loader.getSymbols(); - assertNotNull(symbols); - assertEquals(4, symbols.size()); - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/build/SymbolWriterTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/build/SymbolWriterTest.java deleted file mode 100644 index 9edfb66..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/build/SymbolWriterTest.java +++ /dev/null @@ -1,185 +0,0 @@ -/* - * Copyright (C) 2012 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.sdklib.internal.build; - -import com.android.sdklib.internal.build.SymbolLoader.SymbolEntry; -import com.google.common.base.Charsets; -import com.google.common.collect.Table; -import com.google.common.io.Files; - -import java.io.File; - -import junit.framework.TestCase; - -@SuppressWarnings("javadoc") -public class SymbolWriterTest extends TestCase { - private void check(String packageName, String rText, String rJava) throws Exception { - // Load symbols - File file = File.createTempFile(getClass().getSimpleName(), "txt"); - file.deleteOnExit(); - Files.write(rText, file, Charsets.UTF_8); - SymbolLoader loader = new SymbolLoader(file); - loader.load(); - Table<String, String, SymbolEntry> symbols = loader.getSymbols(); - assertNotNull(symbols); - - // Write symbols - File outFolder = Files.createTempDir(); - outFolder.mkdirs(); - - SymbolWriter writer = new SymbolWriter(outFolder.getPath(), packageName, loader, loader); - writer.write(); - - String contents = Files.toString(new File(outFolder, - packageName.replace('.', File.separatorChar) + File.separator + "R.java"), - Charsets.UTF_8); - - // Ensure we wrote what was expected - assertEquals(rJava, contents.replaceAll("\t", " ")); - } - - public void test1() throws Exception { - check( - // Package - "test.pkg", - - // R.txt - "int xml authenticator 0x7f040000\n", - - // R.java - "/* AUTO-GENERATED FILE. DO NOT MODIFY.\n" + - " *\n" + - " * This class was automatically generated by the\n" + - " * aapt tool from the resource data it found. It\n" + - " * should not be modified by hand.\n" + - " */\n" + - "package test.pkg;\n" + - "\n" + - "public final class R {\n" + - " public static final class xml {\n" + - " public static final int authenticator = 0x7f040000;\n" + - " }\n" + - "}\n" - ); - } - - public void test2() throws Exception { - check( - // Package - "test.pkg", - - // R.txt - "int drawable foobar 0x7f020000\n" + - "int drawable ic_launcher 0x7f020001\n" + - "int string app_name 0x7f030000\n" + - "int string lib1 0x7f030001\n" + - "int style AppBaseTheme 0x7f040000\n" + - "int style AppTheme 0x7f040001\n", - - // R.java - "/* AUTO-GENERATED FILE. DO NOT MODIFY.\n" + - " *\n" + - " * This class was automatically generated by the\n" + - " * aapt tool from the resource data it found. It\n" + - " * should not be modified by hand.\n" + - " */\n" + - "package test.pkg;\n" + - "\n" + - "public final class R {\n" + - " public static final class style {\n" + - " public static final int AppBaseTheme = 0x7f040000;\n" + - " public static final int AppTheme = 0x7f040001;\n" + - " }\n" + - " public static final class string {\n" + - " public static final int app_name = 0x7f030000;\n" + - " public static final int lib1 = 0x7f030001;\n" + - " }\n" + - " public static final class drawable {\n" + - " public static final int ic_launcher = 0x7f020001;\n" + - " public static final int foobar = 0x7f020000;\n" + - " }\n" + - "}\n" - ); - } - - public void testStyleables1() throws Exception { - check( - // Package - "test.pkg", - - // R.txt - "int[] styleable TiledView { 0x7f010000, 0x7f010001, 0x7f010002, 0x7f010003, 0x7f010004 }\n" + - "int styleable TiledView_tileName 2\n" + - "int styleable TiledView_tilingEnum 4\n" + - "int styleable TiledView_tilingMode 3\n" + - "int styleable TiledView_tilingProperty 0\n" + - "int styleable TiledView_tilingResource 1\n", - - // R.java - "/* AUTO-GENERATED FILE. DO NOT MODIFY.\n" + - " *\n" + - " * This class was automatically generated by the\n" + - " * aapt tool from the resource data it found. It\n" + - " * should not be modified by hand.\n" + - " */\n" + - "package test.pkg;\n" + - "\n" + - "public final class R {\n" + - " public static final class styleable {\n" + - " public static final int TiledView_tilingProperty = 0;\n" + - " public static final int TiledView_tilingMode = 3;\n" + - " public static final int TiledView_tilingResource = 1;\n" + - " public static final int TiledView_tileName = 2;\n" + - " public static final int TiledView_tilingEnum = 4;\n" + - " public static final int[] TiledView = { 0x7f010000, 0x7f010001, 0x7f010002, 0x7f010003, 0x7f010004 };\n" + - " }\n" + - "}\n" - ); - } - - public void testStyleables2() throws Exception { - check( - // Package - "test.pkg", - - // R.txt - "int[] styleable LimitedSizeLinearLayout { 0x7f010000, 0x7f010001 }\n" + - "int styleable LimitedSizeLinearLayout_max_height 1\n" + - "int styleable LimitedSizeLinearLayout_max_width 0\n" + - "int xml authenticator 0x7f040000\n", - - // R.java - "/* AUTO-GENERATED FILE. DO NOT MODIFY.\n" + - " *\n" + - " * This class was automatically generated by the\n" + - " * aapt tool from the resource data it found. It\n" + - " * should not be modified by hand.\n" + - " */\n" + - "package test.pkg;\n" + - "\n" + - "public final class R {\n" + - " public static final class styleable {\n" + - " public static final int LimitedSizeLinearLayout_max_height = 1;\n" + - " public static final int LimitedSizeLinearLayout_max_width = 0;\n" + - " public static final int[] LimitedSizeLinearLayout = { 0x7f010000, 0x7f010001 };\n" + - " }\n" + - " public static final class xml {\n" + - " public static final int authenticator = 0x7f040000;\n" + - " }\n" + - "}\n" - ); - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/AddonsListFetcherTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/AddonsListFetcherTest.java deleted file mode 100755 index f62533d..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/AddonsListFetcherTest.java +++ /dev/null @@ -1,216 +0,0 @@ -/* - * Copyright (C) 2009 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.sdklib.internal.repository; - -import com.android.sdklib.internal.repository.AddonsListFetcher.Site; -import com.android.sdklib.repository.SdkAddonsListConstants; - -import org.w3c.dom.Document; - -import java.io.ByteArrayInputStream; -import java.io.FileInputStream; -import java.io.IOException; -import java.io.InputStream; -import java.util.Arrays; - -import junit.framework.TestCase; - -/** - * Tests for {@link AddonsListFetcher} - */ -public class AddonsListFetcherTest extends TestCase { - - /** - * An internal helper class to give us visibility to the protected members we want - * to test. - */ - private static class MockAddonsListFetcher extends AddonsListFetcher { - - public Site[] _parseAddonsList(Document doc, - String nsUri, - String baseUrl, - ITaskMonitor monitor) { - return super.parseAddonsList(doc, nsUri, baseUrl, monitor); - } - - public int _getXmlSchemaVersion(InputStream xml) { - return super.getXmlSchemaVersion(xml); - } - - public String _validateXml(InputStream xml, - String url, - int version, - String[] outError, - Boolean[] validatorFound) { - return super.validateXml(xml, url, version, outError, validatorFound); - } - - public Document _getDocument(InputStream xml, ITaskMonitor monitor) { - return super.getDocument(xml, monitor); - } - - } - - private MockAddonsListFetcher mFetcher; - - @Override - protected void setUp() throws Exception { - super.setUp(); - - mFetcher = new MockAddonsListFetcher(); - } - - @Override - protected void tearDown() throws Exception { - super.tearDown(); - - mFetcher = null; - } - - /** - * Validate we can load a valid addon schema version 1 - */ - public void testLoadSample_1() throws Exception { - InputStream xmlStream = - getTestResource("/com/android/sdklib/testdata/addons_list_sample_1.xml"); - - // guess the version from the XML document - int version = mFetcher._getXmlSchemaVersion(xmlStream); - assertEquals(1, version); - - Boolean[] validatorFound = new Boolean[] { Boolean.FALSE }; - String[] validationError = new String[] { null }; - String url = "not-a-valid-url://addons_list.xml"; - - String uri = mFetcher._validateXml( - xmlStream, url, version, validationError, validatorFound); - assertEquals(Boolean.TRUE, validatorFound[0]); - assertEquals(null, validationError[0]); - assertEquals(SdkAddonsListConstants.getSchemaUri(1), uri); - - // Validation was successful, load the document - MockMonitor monitor = new MockMonitor(); - Document doc = mFetcher._getDocument(xmlStream, monitor); - assertNotNull(doc); - - // Get the sites - Site[] result = mFetcher._parseAddonsList(doc, uri, "http://base/url/", monitor); - - assertEquals("", monitor.getCapturedDescriptions()); - assertEquals("", monitor.getCapturedLog()); - assertEquals("", monitor.getCapturedErrorLog()); - assertEquals("", monitor.getCapturedVerboseLog()); - - // check the sites we found... - // The XML file is UTF-8 so we support character sets (but the Java source file is - // not, so we use the \\u notation to create the Unicode String) - assertEquals( - "[<ADDON_SITE URL='http://www.example.com/my_addons.xml' Name='My Example Add-ons.'>, " + - "<ADDON_SITE URL='http://www.example.co.jp/addons.xml' Name='\u3042\u308A\u304C\u3068\u3046\u3054\u3056\u3044\u307E\u3059\u3002'>, " + - "<ADDON_SITE URL='http://www.example.com/' Name='Example of directory URL.'>, " + - "<ADDON_SITE URL='http://base/url/relative_url.xml' Name='Relative URL.'>]", - Arrays.toString(result)); - assertEquals(4, result.length); - } - - /** - * Validate we can load a valid addon schema version 2 - */ - public void testLoadSample_2() throws Exception { - InputStream xmlStream = - getTestResource("/com/android/sdklib/testdata/addons_list_sample_2.xml"); - - // guess the version from the XML document - int version = mFetcher._getXmlSchemaVersion(xmlStream); - assertEquals(2, version); - - Boolean[] validatorFound = new Boolean[] { Boolean.FALSE }; - String[] validationError = new String[] { null }; - String url = "not-a-valid-url://addons_list.xml"; - - String uri = mFetcher._validateXml( - xmlStream, url, version, validationError, validatorFound); - assertEquals(Boolean.TRUE, validatorFound[0]); - assertEquals(null, validationError[0]); - assertEquals(SdkAddonsListConstants.getSchemaUri(2), uri); - - // Validation was successful, load the document - MockMonitor monitor = new MockMonitor(); - Document doc = mFetcher._getDocument(xmlStream, monitor); - assertNotNull(doc); - - // Get the sites - Site[] result = mFetcher._parseAddonsList(doc, uri, "http://base/url/", monitor); - - assertEquals("", monitor.getCapturedDescriptions()); - assertEquals("", monitor.getCapturedLog()); - assertEquals("", monitor.getCapturedErrorLog()); - assertEquals("", monitor.getCapturedVerboseLog()); - - // check the sites we found... - // The XML file is UTF-8 so we support character sets (but the Java source file is - // not, so we use the \\u notation to create the Unicode String) - assertEquals( - "[<ADDON_SITE URL='http://www.example.com/my_addons.xml' Name='My Example Add-ons.'>, " + - "<ADDON_SITE URL='http://www.example.co.jp/addons.xml' Name='\u3042\u308A\u304C\u3068\u3046\u3054\u3056\u3044\u307E\u3059\u3002'>, " + - "<ADDON_SITE URL='http://www.example.com/' Name='Example of directory URL.'>, " + - "<SYS_IMG_SITE URL='http://www.example.com/' Name='Example of sys-img URL using the default xml filename.'>, " + - "<SYS_IMG_SITE URL='http://www.example.com/specific_file.xml' Name='Example of sys-img URL using a specific xml filename.'>, " + - "<ADDON_SITE URL='http://base/url/relative/url.xml' Name='Relative URL.'>]", - Arrays.toString(result)); - assertEquals(6, result.length); - } - - // IMPORTANT: Each time you add a test here for a new version, you should - // also add a test in ValidateAddonsListXmlTest. - - /** - * Returns an SdkLib file resource as a {@link ByteArrayInputStream}, - * which has the advantage that we can use {@link InputStream#reset()} on it - * at any time to read it multiple times. - * <p/> - * The default for getResourceAsStream() is to return a {@link FileInputStream} that - * does not support reset(), yet we need it in the tested code. - * - * @throws IOException if some I/O read fails - */ - private ByteArrayInputStream getTestResource(String filename) throws IOException { - InputStream xmlStream = this.getClass().getResourceAsStream(filename); - - try { - byte[] data = new byte[8192]; - int offset = 0; - int n; - - while ((n = xmlStream.read(data, offset, data.length - offset)) != -1) { - offset += n; - - if (offset == data.length) { - byte[] newData = new byte[offset + 8192]; - System.arraycopy(data, 0, newData, 0, offset); - data = newData; - } - } - - return new ByteArrayInputStream(data, 0, offset); - } finally { - if (xmlStream != null) { - xmlStream.close(); - } - } - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/LocalSdkParserTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/LocalSdkParserTest.java deleted file mode 100755 index 4989ec3..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/LocalSdkParserTest.java +++ /dev/null @@ -1,159 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository; - -import com.android.SdkConstants; -import com.android.sdklib.IAndroidTarget; -import com.android.sdklib.ISystemImage.LocationType; -import com.android.sdklib.SdkManager; -import com.android.sdklib.SdkManagerTestCase; -import com.android.sdklib.SystemImage; - -import java.util.Arrays; - -public class LocalSdkParserTest extends SdkManagerTestCase { - - public void testLocalSdkParser_SystemImages() throws Exception { - SdkManager sdkman = getSdkManager(); - LocalSdkParser parser = new LocalSdkParser(); - MockMonitor monitor = new MockMonitor(); - - // By default SdkManagerTestCase creates an SDK with one platform containing - // a legacy armeabi system image (this is not a separate system image package) - - assertEquals( - "[Android SDK Tools, revision 0, " + - "SDK Platform Android 0.0, API 0, revision 1, " + - "Sources for Android SDK, API 0, revision 0]", - Arrays.toString(parser.parseSdk(sdkman.getLocation(), sdkman, monitor))); - - assertEquals( - "[SDK Platform Android 0.0, API 0, revision 1, " + - "Sources for Android SDK, API 0, revision 0]", - Arrays.toString(parser.parseSdk(sdkman.getLocation(), - sdkman, - LocalSdkParser.PARSE_PLATFORMS | LocalSdkParser.PARSE_SOURCES, - monitor))); - - assertEquals( - "[SDK Platform Android 0.0, API 0, revision 1]", - Arrays.toString(parser.parseSdk(sdkman.getLocation(), - sdkman, - LocalSdkParser.PARSE_PLATFORMS, - monitor))); - - assertEquals( - "[Sources for Android SDK, API 0, revision 0]", - Arrays.toString(parser.parseSdk(sdkman.getLocation(), - sdkman, - LocalSdkParser.PARSE_SOURCES, - monitor))); - - assertEquals( - "[Android SDK Tools, revision 0]", - Arrays.toString(parser.parseSdk(sdkman.getLocation(), - sdkman, - LocalSdkParser.PARSE_TOOLS, - monitor))); - - // Now add a few "platform subfolders" system images and reload the SDK. - // This disables the "legacy" mode but it still doesn't create any system image package - - IAndroidTarget t = sdkman.getTargets()[0]; - makeSystemImageFolder(new SystemImage( - sdkman, t, LocationType.IN_PLATFORM_SUBFOLDER, SdkConstants.ABI_ARMEABI_V7A)); - makeSystemImageFolder(new SystemImage( - sdkman, t, LocationType.IN_PLATFORM_SUBFOLDER, SdkConstants.ABI_INTEL_ATOM)); - - sdkman.reloadSdk(getLog()); - t = sdkman.getTargets()[0]; - - assertEquals( - "[Android SDK Tools, revision 0, " + - "SDK Platform Android 0.0, API 0, revision 1, " + - "Sources for Android SDK, API 0, revision 0]", - Arrays.toString(parser.parseSdk(sdkman.getLocation(), sdkman, monitor))); - - // Now add arm + arm v7a images using the new SDK/system-images. - // The local parser will find the 2 system image packages which are associated - // with the PlatformTarger in the SdkManager. - - makeSystemImageFolder(new SystemImage( - sdkman, t, LocationType.IN_SYSTEM_IMAGE, SdkConstants.ABI_ARMEABI)); - makeSystemImageFolder(new SystemImage( - sdkman, t, LocationType.IN_SYSTEM_IMAGE, SdkConstants.ABI_ARMEABI_V7A)); - - sdkman.reloadSdk(getLog()); - - assertEquals( - "[Android SDK Tools, revision 0, " + - "SDK Platform Android 0.0, API 0, revision 1, " + - "ARM EABI v7a System Image, Android API 0, revision 0, " + - "ARM EABI System Image, Android API 0, revision 0, " + - "Sources for Android SDK, API 0, revision 0]", - Arrays.toString(parser.parseSdk(sdkman.getLocation(), sdkman, monitor))); - - // Now add an x86 image using the new SDK/system-images. - // Now this time we do NOT reload the SdkManager instance. Instead the parser - // will find an unused system image and load it as a "broken package". - - makeSystemImageFolder(new SystemImage( - sdkman, t, LocationType.IN_SYSTEM_IMAGE, SdkConstants.ABI_INTEL_ATOM)); - - assertEquals( - "[Android SDK Tools, revision 0, " + - "SDK Platform Android 0.0, API 0, revision 1, " + - "ARM EABI v7a System Image, Android API 0, revision 0, " + - "ARM EABI System Image, Android API 0, revision 0, " + - "Sources for Android SDK, API 0, revision 0, " + - "Broken Intel x86 Atom System Image, API 0]", - Arrays.toString(parser.parseSdk(sdkman.getLocation(), sdkman, monitor))); - - assertEquals( - "[Android SDK Tools, revision 0, " + - "SDK Platform Android 0.0, API 0, revision 1, " + - "ARM EABI v7a System Image, Android API 0, revision 0, " + - "ARM EABI System Image, Android API 0, revision 0, " + - "Sources for Android SDK, API 0, revision 0, " + - "Broken Intel x86 Atom System Image, API 0]", - Arrays.toString(parser.parseSdk(sdkman.getLocation(), - sdkman, - LocalSdkParser.PARSE_ALL, - monitor))); - - assertEquals( - "[SDK Platform Android 0.0, API 0, revision 1, " + - "ARM EABI v7a System Image, Android API 0, revision 0, " + - "ARM EABI System Image, Android API 0, revision 0, " + - "Sources for Android SDK, API 0, revision 0, " + - "Broken Intel x86 Atom System Image, API 0]", - Arrays.toString(parser.parseSdk(sdkman.getLocation(), - sdkman, - LocalSdkParser.PARSE_PLATFORMS | // platform also loads system-images - LocalSdkParser.PARSE_SOURCES, - monitor))); - - assertEquals( - "[Sources for Android SDK, API 0, revision 0]", - Arrays.toString(parser.parseSdk(sdkman.getLocation(), - sdkman, - LocalSdkParser.PARSE_SOURCES, - monitor))); - } - -} - diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/MockEmptySdkManager.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/MockEmptySdkManager.java deleted file mode 100755 index be1fb29..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/MockEmptySdkManager.java +++ /dev/null @@ -1,30 +0,0 @@ -/* - * Copyright (C) 2011 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.sdklib.internal.repository; - -import com.android.sdklib.IAndroidTarget; -import com.android.sdklib.SdkManager; - -/** - * An invalid SDK Manager, just good enough to avoid passing a null reference. - */ -public class MockEmptySdkManager extends SdkManager { - public MockEmptySdkManager(String osSdkPath) { - super(osSdkPath); - setTargets(new IAndroidTarget[0]); - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/MockMonitor.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/MockMonitor.java deleted file mode 100755 index 72e7d93..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/MockMonitor.java +++ /dev/null @@ -1,122 +0,0 @@ -/* - * Copyright (C) 2009 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.sdklib.internal.repository; - -import com.android.annotations.NonNull; - -/** - * Mock implementation of {@link ITaskMonitor} that simply captures - * the output in local strings. Does not provide any UI and has no - * support for creating sub-monitors. - */ -public class MockMonitor implements ITaskMonitor { - - String mCapturedLog = ""; //$NON-NLS-1$ - String mCapturedErrorLog = ""; //$NON-NLS-1$ - String mCapturedVerboseLog = ""; //$NON-NLS-1$ - String mCapturedDescriptions = ""; //$NON-NLS-1$ - - public String getCapturedLog() { - return mCapturedLog; - } - - public String getCapturedErrorLog() { - return mCapturedErrorLog; - } - - public String getCapturedVerboseLog() { - return mCapturedVerboseLog; - } - - public String getCapturedDescriptions() { - return mCapturedDescriptions; - } - - @Override - public void log(String format, Object... args) { - mCapturedLog += String.format(format, args) + "\n"; //$NON-NLS-1$ - } - - @Override - public void logError(String format, Object... args) { - mCapturedErrorLog += String.format(format, args) + "\n"; //$NON-NLS-1$ - } - - @Override - public void logVerbose(String format, Object... args) { - mCapturedVerboseLog += String.format(format, args) + "\n"; //$NON-NLS-1$ - } - - @Override - public void setProgressMax(int max) { - } - - @Override - public int getProgressMax() { - return 0; - } - - @Override - public void setDescription(String format, Object... args) { - mCapturedDescriptions += String.format(format, args) + "\n"; //$NON-NLS-1$ - } - - @Override - public boolean isCancelRequested() { - return false; - } - - @Override - public void incProgress(int delta) { - } - - @Override - public int getProgress() { - return 0; - } - - @Override - public boolean displayPrompt(String title, String message) { - return false; - } - - @Override - public ITaskMonitor createSubMonitor(int tickCount) { - return null; - } - - @Override - public void error(Throwable t, String errorFormat, Object... args) { - } - - @Override - public void info(@NonNull String msgFormat, Object... args) { - } - - @Override - public void verbose(@NonNull String msgFormat, Object... args) { - } - - @Override - public void warning(@NonNull String warningFormat, Object... args) { - } - - @Override - public UserCredentials displayLoginCredentialsPrompt(String title, String message) { - return null; - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/MockPlatformTarget.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/MockPlatformTarget.java deleted file mode 100755 index 1d9bb7b..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/MockPlatformTarget.java +++ /dev/null @@ -1,202 +0,0 @@ -/* - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository; - -import com.android.SdkConstants; -import com.android.sdklib.AndroidVersion; -import com.android.sdklib.IAndroidTarget; -import com.android.sdklib.ISystemImage; -import com.android.sdklib.ISystemImage.LocationType; -import com.android.sdklib.SystemImage; -import com.android.sdklib.io.FileOp; - -import java.util.Map; - -/** - * A mock PlatformTarget. - * This reimplements the minimum needed from the interface for our limited testing needs. - */ -public class MockPlatformTarget implements IAndroidTarget { - - private final int mApiLevel; - private final int mRevision; - private ISystemImage[] mSystemImages; - - public MockPlatformTarget(int apiLevel, int revision) { - mApiLevel = apiLevel; - mRevision = revision; - } - - @Override - public String getClasspathName() { - return getName(); - } - - @Override - public String getShortClasspathName() { - return getName(); - } - - @Override - public String getDefaultSkin() { - return null; - } - - @Override - public String getDescription() { - return getName(); - } - - @Override - public String getFullName() { - return getName(); - } - - @Override - public ISystemImage[] getSystemImages() { - if (mSystemImages == null) { - SystemImage si = new SystemImage( - FileOp.append(getLocation(), SdkConstants.OS_IMAGES_FOLDER), - LocationType.IN_PLATFORM_LEGACY, - SdkConstants.ABI_ARMEABI); - mSystemImages = new SystemImage[] { si }; - } - return mSystemImages; - } - - @Override - public ISystemImage getSystemImage(String abiType) { - if (SdkConstants.ABI_ARMEABI.equals(abiType)) { - return getSystemImages()[0]; - } - return null; - } - - @Override - public String getLocation() { - return "/sdk/platforms/android-" + getVersion().getApiString(); - } - - @Override - public IOptionalLibrary[] getOptionalLibraries() { - return null; - } - - @Override - public IAndroidTarget getParent() { - return null; - } - - @Override - public String getPath(int pathId) { - throw new UnsupportedOperationException("Implement this as needed for tests"); - } - - @Override - public String[] getPlatformLibraries() { - return null; - } - - @Override - public String getProperty(String name) { - return null; - } - - @Override - public Integer getProperty(String name, Integer defaultValue) { - return defaultValue; - } - - @Override - public Boolean getProperty(String name, Boolean defaultValue) { - return defaultValue; - } - - @Override - public Map<String, String> getProperties() { - return null; - } - - @Override - public int getRevision() { - return mRevision; - } - - @Override - public String[] getSkins() { - return null; - } - - @Override - public int getUsbVendorId() { - return 0; - } - - /** - * Returns a vendor that depends on the parent *platform* API. - * This works well in Unit Tests where we'll typically have different - * platforms as unique identifiers. - */ - @Override - public String getVendor() { - return "vendor " + Integer.toString(mApiLevel); - } - - /** - * Create a synthetic name using the target API level. - */ - @Override - public String getName() { - return "platform r" + Integer.toString(mApiLevel); - } - - @Override - public AndroidVersion getVersion() { - return new AndroidVersion(mApiLevel, null /*codename*/); - } - - @Override - public String getVersionName() { - return String.format("android-%1$d", mApiLevel); - } - - @Override - public String hashString() { - return getVersionName(); - } - - /** Returns true for a platform. */ - @Override - public boolean isPlatform() { - return true; - } - - @Override - public boolean canRunOn(IAndroidTarget target) { - throw new UnsupportedOperationException("Implement this as needed for tests"); - } - - @Override - public int compareTo(IAndroidTarget o) { - throw new UnsupportedOperationException("Implement this as needed for tests"); - } - - @Override - public boolean hasRenderingLibrary() { - return false; - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/SdkStatsTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/SdkStatsTest.java deleted file mode 100755 index baff6f9..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/SdkStatsTest.java +++ /dev/null @@ -1,172 +0,0 @@ -/* - * Copyright (C) 2012 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.sdklib.internal.repository; - -import com.android.sdklib.internal.repository.SdkStats.PlatformStat; -import com.android.sdklib.repository.SdkStatsConstants; -import com.android.sdklib.util.SparseArray; - -import org.w3c.dom.Document; - -import java.io.ByteArrayInputStream; -import java.io.FileInputStream; -import java.io.IOException; -import java.io.InputStream; -import java.util.Arrays; - -import junit.framework.TestCase; - -/** - * Tests for {@link SdkStats} - */ -public class SdkStatsTest extends TestCase { - - /** - * An internal helper class to give us visibility to the protected members we want - * to test. - */ - private static class MockSdkStats extends SdkStats { - - public SparseArray<PlatformStat> _parseStatsDocument(Document doc, - String nsUri, - ITaskMonitor monitor) { - return super.parseStatsDocument(doc, nsUri, monitor); - } - - public int _getXmlSchemaVersion(InputStream xml) { - return super.getXmlSchemaVersion(xml); - } - - public String _validateXml(InputStream xml, String url, int version, - String[] outError, Boolean[] validatorFound) { - return super.validateXml(xml, url, version, outError, validatorFound); - } - - public Document _getDocument(InputStream xml, ITaskMonitor monitor) { - return super.getDocument(xml, monitor); - } - - } - - private MockSdkStats mStats; - - @Override - protected void setUp() throws Exception { - super.setUp(); - - mStats = new MockSdkStats(); - } - - @Override - protected void tearDown() throws Exception { - super.tearDown(); - - mStats = null; - } - - /** - * Validate we can still load a valid addon schema version 1 - */ - public void testLoadSample_1() throws Exception { - InputStream xmlStream = - getTestResource("/com/android/sdklib/testdata/stats_sample_1.xml"); - - // guess the version from the XML document - int version = mStats._getXmlSchemaVersion(xmlStream); - assertEquals(1, version); - - Boolean[] validatorFound = new Boolean[] { Boolean.FALSE }; - String[] validationError = new String[] { null }; - String url = "not-a-valid-url://stats.xml"; - - String uri = mStats._validateXml( - xmlStream, url, version, validationError, validatorFound); - assertEquals(Boolean.TRUE, validatorFound[0]); - assertEquals(null, validationError[0]); - assertEquals(SdkStatsConstants.getSchemaUri(1), uri); - - // Validation was successful, load the document - MockMonitor monitor = new MockMonitor(); - Document doc = mStats._getDocument(xmlStream, monitor); - assertNotNull(doc); - - // Get the sites - SparseArray<PlatformStat> result = mStats._parseStatsDocument(doc, uri, monitor); - - assertEquals("", monitor.getCapturedDescriptions()); - assertEquals("", monitor.getCapturedLog()); - assertEquals("", monitor.getCapturedErrorLog()); - assertEquals("", monitor.getCapturedVerboseLog()); - - // check what we found - assertEquals(3, result.size()); - int len = result.size(); - - int[] keys = new int[len]; - PlatformStat[] stats = new PlatformStat[len]; - for (int i = 0; i < len; i++) { - keys[i] = result.keyAt(i); - stats[i] = result.valueAt(i); - } - - assertEquals( - "[3, 5, 42]", - Arrays.toString(keys)); - - assertEquals( - "[<Stat api=3, code=Vanilla, vers=Android 0.5, share=0.1%, accum=100.0%>, " + - "<Stat api=5, code=Coffee, vers=Android 42.0, share=25.8%, accum=99.9%>, " + - "<Stat api=42, code=Chocolate, vers=Android 32.64, share=74.1%, accum=74.1%>]", - Arrays.toString(stats)); - } - - /** - * Returns an SdkLib file resource as a {@link ByteArrayInputStream}, - * which has the advantage that we can use {@link InputStream#reset()} on it - * at any time to read it multiple times. - * <p/> - * The default for getResourceAsStream() is to return a {@link FileInputStream} that - * does not support reset(), yet we need it in the tested code. - * - * @throws IOException if some I/O read fails - */ - private ByteArrayInputStream getTestResource(String filename) throws IOException { - InputStream xmlStream = this.getClass().getResourceAsStream(filename); - - try { - byte[] data = new byte[8192]; - int offset = 0; - int n; - - while ((n = xmlStream.read(data, offset, data.length - offset)) != -1) { - offset += n; - - if (offset == data.length) { - byte[] newData = new byte[offset + 8192]; - System.arraycopy(data, 0, newData, 0, offset); - data = newData; - } - } - - return new ByteArrayInputStream(data, 0, offset); - } finally { - if (xmlStream != null) { - xmlStream.close(); - } - } - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/archives/ArchiveInstallerTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/archives/ArchiveInstallerTest.java deleted file mode 100755 index b0b3f03..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/archives/ArchiveInstallerTest.java +++ /dev/null @@ -1,414 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.archives; - -import com.android.sdklib.internal.repository.DownloadCache; -import com.android.sdklib.internal.repository.ITaskMonitor; -import com.android.sdklib.internal.repository.MockEmptySdkManager; -import com.android.sdklib.internal.repository.MockMonitor; -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; -import com.android.sdklib.internal.repository.packages.ExtraPackage; -import com.android.sdklib.internal.repository.packages.MockEmptyPackage; -import com.android.sdklib.internal.repository.packages.MockExtraPackage; -import com.android.sdklib.internal.repository.sources.SdkRepoSource; -import com.android.sdklib.internal.repository.sources.SdkSource; -import com.android.sdklib.io.IFileOp; -import com.android.sdklib.io.MockFileOp; -import com.android.sdklib.repository.PkgProps; -import com.android.utils.Pair; - -import java.io.File; -import java.util.Arrays; -import java.util.HashMap; -import java.util.Map; -import java.util.Properties; -import java.util.regex.Pattern; - -import junit.framework.TestCase; - -/** - * Unit tests for {@link ArchiveInstaller}. - */ -public class ArchiveInstallerTest extends TestCase { - - private MockMonitor mMon; - private String mSdkRoot; - private MockFileOp mFile; - private MockArchiveInstaller mArchInst; - private MockEmptySdkManager mSdkMan; - - private class MockArchiveInstaller extends ArchiveInstaller { - - private Map<Archive, File> mDownloadMap = new HashMap<Archive, File>(); - - public MockArchiveInstaller(IFileOp fileUtils) { - super(fileUtils); - } - - public void setDownloadResponse(Archive archive, File response) { - mDownloadMap.put(archive, response); - } - - @Override - protected Pair<File, File> downloadFile( - Archive archive, - String osSdkRoot, - DownloadCache cache, - ITaskMonitor monitor, - boolean forceHttp) { - File file = mDownloadMap.get(archive); - // register the file as "created" - ArchiveInstallerTest.this.mFile.recordExistingFile(file); - return Pair.of(file, null); - } - - @Override - protected boolean unzipFolder( - ArchiveReplacement archiveInfo, - File archiveFile, - File unzipDestFolder, - ITaskMonitor monitor) { - // Claim the unzip works if the input archiveFile is one we know about - // and the destination actually exists. - - if (getFileOp().isDirectory(unzipDestFolder) && - mDownloadMap.values().contains(archiveFile)) { - return true; - } - - return false; - } - - } - - @Override - protected void setUp() throws Exception { - super.setUp(); - mFile = new MockFileOp(); - mArchInst = new MockArchiveInstaller(mFile); - mSdkRoot = "/sdk"; - mSdkMan = new MockEmptySdkManager(mSdkRoot); - mMon = new MockMonitor(); - } - - // ---- - - /** Test we don't try to install a local archive. */ - public void testInstall_SkipLocalArchive() throws Exception { - MockEmptyPackage p = new MockEmptyPackage("testPkg"); - ArchiveReplacement ar = new ArchiveReplacement(p.getArchives()[0], null /*replaced*/); - - assertFalse(mArchInst.install(ar, mSdkRoot, false /*forceHttp*/, mSdkMan, - null /*UrlCache*/, mMon)); - assertTrue(mMon.getCapturedLog().indexOf("Skipping already installed archive") != -1); - } - - /** Test we can install a simple new archive. */ - public void testInstall_NewArchive() throws Exception { - SdkSource src1 = new SdkRepoSource("http://repo.example.com/url", "repo1"); - MockEmptyPackage p = createRemoteEmptyPackage(src1, "testPkg"); - ArchiveReplacement ar = new ArchiveReplacement(p.getArchives()[0], null /*replaced*/); - - // associate the File that will be "downloaded" for this archive - mArchInst.setDownloadResponse( - p.getArchives()[0], createFile("/sdk", "tmp", "download1.zip")); - - assertTrue(mArchInst.install(ar, mSdkRoot, false /*forceHttp*/, mSdkMan, - null /*UrlCache*/, mMon)); - - // check what was created - assertEquals( - "[/sdk/mock/testPkg/source.properties]", - Arrays.toString(mFile.getExistingFiles())); - - assertEquals( - "[/, /sdk, /sdk/mock, /sdk/mock/testPkg]", - Arrays.toString(mFile.getExistingFolders())); - - assertEquals( - "[</sdk/mock/testPkg/source.properties: '### Android Tool: Source of this archive.\n" + - "#...date...\n" + - "Archive.Os=ANY\n" + - "Pkg.Revision=0\n" + - "Archive.Arch=ANY\n" + - "Pkg.SourceUrl=http\\://repo.example.com/url\n" + - "'>]", - stripDate(Arrays.toString(mFile.getOutputStreams()))); - - assertEquals( - "Installing 'testPkg'\n" + - "Installed 'testPkg'\n", - mMon.getCapturedLog()); - } - - /** Test we can replace and rename an Extra package. */ - public void testInstall_InstallExtraArchive() throws Exception { - SdkSource src1 = new SdkRepoSource("http://repo.example.com/url", "repo1"); - - MockExtraPackage newPkg = createRemoteExtraPackage(src1, "vendor1", "oldPath", 2, 1); - MockExtraPackage oldPkg = new MockExtraPackage(src1, "vendor1", "oldPath", 1, 1); - - // old pkg is installed, so its directory & files exists - mFile.recordExistingFile("/sdk/extras/vendor1/oldPath/source.properties"); - mFile.recordExistingFolder("/sdk/extras/vendor1/oldPath"); - - ArchiveReplacement ar = new ArchiveReplacement( - newPkg.getArchives()[0], - oldPkg.getArchives()[0]); - - // associate the File that will be "downloaded" for this archive - mArchInst.setDownloadResponse( - newPkg.getArchives()[0], createFile("/sdk", "tmp", "download1.zip")); - - assertTrue(mArchInst.install(ar, mSdkRoot, false /*forceHttp*/, mSdkMan, - null /*UrlCache*/, mMon)); - - // check what was created - assertEquals( - "[/sdk/extras/vendor1/oldPath/source.properties]", - Arrays.toString(mFile.getExistingFiles())); - - // This created the /sdk/temp folder to put the oldPath package whilst we unzipped - // the new one. The oldPath dir was then cleaned up but we still leave the root - // temp dir around. - assertEquals( - "[/, /sdk, /sdk/extras, /sdk/extras/vendor1, /sdk/extras/vendor1/oldPath, /sdk/temp]", - Arrays.toString(mFile.getExistingFolders())); - - assertEquals( - ( - "[</sdk/extras/vendor1/oldPath/source.properties: " + - "'### Android Tool: Source of this archive.\n" + - "#...date...\n" + - "Extra.VendorDisplay=vendor1\n" + - "Pkg.Desc=desc\n" + - "Extra.Path=oldPath\n" + - "Archive.Arch=ANY\n" + - "Pkg.DescUrl=url\n" + - "Extra.NameDisplay=Vendor1 OldPath\n" + - "Archive.Os=ANY\n" + - "Pkg.SourceUrl=http\\://repo.example.com/url\n" + - "Pkg.Revision=2\n" + - "Extra.VendorId=vendor1\n" + - "'>]"), - stripDate(Arrays.toString(mFile.getOutputStreams()))); - - assertEquals( - "Installing Vendor1 OldPath, revision 2\n" + - "Installed Vendor1 OldPath, revision 2\n", - mMon.getCapturedLog()); - } - - /** Test we can replace and rename an Extra package. */ - public void testInstall_InstallRenamedExtraArchive() throws Exception { - SdkSource src1 = new SdkRepoSource("http://repo.example.com/url", "repo1"); - - MockExtraPackage newPkg = createRemoteExtraPackage( - src1, - "vendor1", - "newPath", - "oldPath", - 2, // revision - 1); // min_platform_tools_rev - ExtraPackage oldPkg = (ExtraPackage) ExtraPackage.create( - src1, // source - null, // props - "vendor1", // vendor - "oldPath", // path - 1, // revision - null, // license - null, // description - null, // descUrl - Os.ANY, // archiveOs - Arch.ANY, // archiveArch - "/sdk/extras/vendor1/oldPath" // archiveOsPath - ); - - // old pkg is installed, so its directory & files exists - mFile.recordExistingFile("/sdk/extras/vendor1/oldPath/source.properties"); - mFile.recordExistingFolder("/sdk/extras/vendor1/oldPath"); - - ArchiveReplacement ar = new ArchiveReplacement( - newPkg.getArchives()[0], - oldPkg.getArchives()[0]); - - // associate the File that will be "downloaded" for this archive - mArchInst.setDownloadResponse( - newPkg.getArchives()[0], createFile("/sdk", "tmp", "download1.zip")); - - assertTrue(mArchInst.install(ar, mSdkRoot, false /*forceHttp*/, mSdkMan, - null /*UrlCache*/, mMon)); - - // check what was created - assertEquals( - "[/sdk/extras/vendor1/newPath/source.properties]", - Arrays.toString(mFile.getExistingFiles())); - - // oldPath directory has been deleted, we only have newPath now. - // No sdk/temp dir was created since we didn't have to move the old package dir out - // of the way. - assertEquals( - "[/, /sdk, /sdk/extras, /sdk/extras/vendor1, /sdk/extras/vendor1/newPath]", - Arrays.toString(mFile.getExistingFolders())); - - assertEquals( - ( - "[</sdk/extras/vendor1/newPath/source.properties: " + - "'### Android Tool: Source of this archive.\n" + - "#...date...\n" + - "Extra.VendorDisplay=vendor1\n" + - "Pkg.Desc=desc\n" + - "Extra.OldPaths=oldPath\n" + - "Extra.Path=newPath\n" + - "Archive.Arch=ANY\n" + - "Pkg.DescUrl=url\n" + - "Extra.NameDisplay=Vendor1 NewPath\n" + - "Archive.Os=ANY\n" + - "Pkg.SourceUrl=http\\://repo.example.com/url\n" + - "Pkg.Revision=2\n" + - "Extra.VendorId=vendor1\n" + - "'>]"), - stripDate(Arrays.toString(mFile.getOutputStreams()))); - - assertEquals( - "Installing Vendor1 NewPath, revision 2\n" + - "Installed Vendor1 NewPath, revision 2\n", - mMon.getCapturedLog()); - } - - // ---- - - /** - * Helper creator method to create a {@link MockEmptyPackage} with no local - * archive associated. - */ - private static MockEmptyPackage createRemoteEmptyPackage(SdkSource source, String testHandle) { - return new MockEmptyPackage(source, testHandle, 0 /*revision*/) { - @Override - protected Archive[] initializeArchives( - Properties props, - Os archiveOs, - Arch archiveArch, - String archiveOsPath) { - // Create one remote archive for this package - return new Archive[] { - new Archive( - this, - Os.ANY, - Arch.ANY, - "http://some.source/some_url", - 1234, // size - "abcdef") // sha1 - }; - } - }; - } - - /** - * Helper creator method to create a {@link MockExtraPackage} with no local - * archive associated. - */ - private static MockExtraPackage createRemoteExtraPackage( - SdkSource source, - String vendor, - String path, - int revision, - int min_platform_tools_rev) { - return new MockExtraPackage(source, vendor, path, revision, min_platform_tools_rev) { - @Override - protected Archive[] initializeArchives( - Properties props, - Os archiveOs, - Arch archiveArch, - String archiveOsPath) { - // Create one remote archive for this package - return new Archive[] { - new Archive( - this, - Os.ANY, - Arch.ANY, - "http://some.source/some_url", - 1234, // size - "abcdef") // sha1 - }; - } - }; - } - - /** - * Helper creator method to create a {@link MockExtraPackage} with no local - * archive associated and a specific oldPaths attribute. - */ - private static MockExtraPackage createRemoteExtraPackage( - SdkSource source, - String vendor, - String newPath, - String oldPaths, - int revision, - int min_platform_tools_rev) { - Properties props = new Properties(); - props.setProperty(PkgProps.EXTRA_OLD_PATHS, oldPaths); - props.setProperty(PkgProps.MIN_PLATFORM_TOOLS_REV, - Integer.toString((min_platform_tools_rev))); - return new MockExtraPackage(source, props, vendor, newPath, revision) { - @Override - protected Archive[] initializeArchives( - Properties props2, - Os archiveOs, - Arch archiveArch, - String archiveOsPath) { - // Create one remote archive for this package - return new Archive[] { - new Archive( - this, - Os.ANY, - Arch.ANY, - "http://some.source/some_url", - 1234, // size - "abcdef") // sha1 - }; - } - }; - } - - private File createFile(String...segments) { - File f = null; - for (String segment : segments) { - if (f == null) { - f = new File(segment); - } else { - f = new File(f, segment); - } - } - - return f; - } - - /** - * Strips the second line of the string. - * The source.properties generated by Java contain the generation data on the - * second line and this is of course not suitable for unit tests. - */ - private String stripDate(String string) { - // We know it's a date if it looks like: - // \n # ... YYYY\n - Pattern p = Pattern.compile("\n#[^#][^\n]*[0-9]{4}\\w*\n", Pattern.DOTALL); - string = p.matcher(string.replaceAll("\r\n", "\n")).replaceAll("\n#...date...\n"); - return string; - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/archives/ArchiveTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/archives/ArchiveTest.java deleted file mode 100755 index c0ae718..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/archives/ArchiveTest.java +++ /dev/null @@ -1,119 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.archives; - -import com.android.sdklib.internal.repository.archives.Archive; -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; - -import junit.framework.TestCase; - -public class ArchiveTest extends TestCase { - - @Override - protected void setUp() throws Exception { - super.setUp(); - } - - public void testShortDescription() throws Exception { - Archive a = new Archive( - null, //pkg, - Os.WINDOWS, //os - Arch.ANY, //arch, - null, //url - 0, //size - null); //checksum - assertEquals("Archive for Windows", a.getShortDescription()); - - a = new Archive( - null, //pkg, - Os.LINUX, //os - Arch.ANY, //arch, - null, //url - 0, //size - null); //checksum - assertEquals("Archive for Linux", a.getShortDescription()); - - a = new Archive( - null, //pkg, - Os.MACOSX, //os - Arch.ANY, //arch, - null, //url - 0, //size - null); //checksum - assertEquals("Archive for MacOS X", a.getShortDescription()); - - a = new Archive( - null, //pkg, - Os.ANY, //os - Arch.ANY, //arch, - null, //url - 0, //size - null); //checksum - assertEquals("Archive for any OS", a.getShortDescription()); - } - - public void testLongDescription() throws Exception { - Archive a = new Archive( - null, //pkg, - Os.WINDOWS, //os - Arch.ANY, //arch, - null, //url - 900, //size - "1234567890ABCDEF"); //checksum - assertEquals( - "Archive for Windows\n" + - "Size: 900 Bytes\n" + - "SHA1: 1234567890ABCDEF", - a.getLongDescription()); - - a = new Archive(null, Os.WINDOWS, Arch.ANY, null, 1100, "1234567890ABCDEF"); - assertEquals( - "Archive for Windows\n" + - "Size: 1 KiB\n" + - "SHA1: 1234567890ABCDEF", - a.getLongDescription()); - - a = new Archive(null, Os.WINDOWS, Arch.ANY, null, 1900, "1234567890ABCDEF"); - assertEquals( - "Archive for Windows\n" + - "Size: 2 KiB\n" + - "SHA1: 1234567890ABCDEF", - a.getLongDescription()); - - a = new Archive(null, Os.WINDOWS, Arch.ANY, null, (long)2e6, "1234567890ABCDEF"); - assertEquals( - "Archive for Windows\n" + - "Size: 1.9 MiB\n" + - "SHA1: 1234567890ABCDEF", - a.getLongDescription()); - - a = new Archive(null, Os.WINDOWS, Arch.ANY, null, (long)19e6, "1234567890ABCDEF"); - assertEquals( - "Archive for Windows\n" + - "Size: 18.1 MiB\n" + - "SHA1: 1234567890ABCDEF", - a.getLongDescription()); - - a = new Archive(null, Os.WINDOWS, Arch.ANY, null, (long)18e9, "1234567890ABCDEF"); - assertEquals( - "Archive for Windows\n" + - "Size: 16.8 GiB\n" + - "SHA1: 1234567890ABCDEF", - a.getLongDescription()); - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/BrokenPackageTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/BrokenPackageTest.java deleted file mode 100755 index 92a04c4..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/BrokenPackageTest.java +++ /dev/null @@ -1,59 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.internal.repository.packages.BrokenPackage; - -import junit.framework.TestCase; - -public class BrokenPackageTest extends TestCase { - - private BrokenPackage m; - - @Override - protected void setUp() throws Exception { - super.setUp(); - - m = new BrokenPackage(null /*props*/, - "short description", - "long description", - 12, // min api level - 13, // exact api level - "os/path"); - - } - - public final void testGetShortDescription() { - assertEquals("short description", m.getShortDescription()); - } - - public final void testGetLongDescription() { - assertEquals("long description", m.getLongDescription()); - } - - public final void testGetMinApiLevel() { - assertEquals(12, m.getMinApiLevel()); - } - - public final void testGetExactApiLevel() { - assertEquals(13, m.getExactApiLevel()); - } - - public void testInstallId() { - assertEquals("", m.installId()); - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/ExtraPackageTest_v3.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/ExtraPackageTest_v3.java deleted file mode 100755 index 6102f13..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/ExtraPackageTest_v3.java +++ /dev/null @@ -1,178 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; -import com.android.sdklib.internal.repository.packages.ExtraPackage; -import com.android.sdklib.repository.PkgProps; - -import java.io.File; -import java.util.Arrays; -import java.util.Properties; - -/** - * Tests {@link ExtraPackage} using anddon-3.xsd: it has a {@code <path>} and {@code <vendor>}. - * (it lacks name-display, vendor-id and vendor-display with are in addon-4.xsd) - */ -public class ExtraPackageTest_v3 extends MinToolsPackageTest { - - private static final char PS = File.pathSeparatorChar; - - private ExtraPackage createExtraPackage(Properties props) { - ExtraPackage p = (ExtraPackage) ExtraPackage.create( - null, //source - props, - null, //vendor - null, //path - -1, //revision - null, //license - null, //description - null, //descUrl - Os.ANY, //archiveOs - Arch.ANY, //archiveArch - "/local/archive/path" //archiveOsPath - ); - return p; - } - - /** Properties used to "load" the package. When saved, they become different. */ - private Properties createLoadedProps() { - Properties props = super.createProps(); - - // ExtraPackage properties - props.setProperty(PkgProps.EXTRA_VENDOR, "vendor"); - props.setProperty(PkgProps.EXTRA_PATH, "the_path"); - props.setProperty(PkgProps.EXTRA_OLD_PATHS, "old_path1;oldpath2"); - props.setProperty(PkgProps.EXTRA_MIN_API_LEVEL, "11"); - props.setProperty(PkgProps.EXTRA_PROJECT_FILES, - "path1.jar" + PS + "dir2/jar 2.jar" + PS + "dir/3/path"); - - return props; - } - - /** Properties saved by the package. They differ from loaded ones in name and vendor. */ - private Properties createSavedProps() { - Properties props = super.createProps(); - - // ExtraPackage properties - props.setProperty(PkgProps.EXTRA_VENDOR_ID, "vendor"); - props.setProperty(PkgProps.EXTRA_VENDOR_DISPLAY, "vendor"); - props.setProperty(PkgProps.EXTRA_NAME_DISPLAY, "Vendor The Path"); - props.setProperty(PkgProps.EXTRA_PATH, "the_path"); - props.setProperty(PkgProps.EXTRA_OLD_PATHS, "old_path1;oldpath2"); - props.setProperty(PkgProps.EXTRA_MIN_API_LEVEL, "11"); - props.setProperty(PkgProps.EXTRA_PROJECT_FILES, - "path1.jar" + PS + "dir2/jar 2.jar" + PS + "dir/3/path"); - - return props; - } - - protected void testCreatedExtraPackage(ExtraPackage p) { - super.testCreatedPackage(p); - - // Package properties - // vendor becomes both vendor-id and vendor-display - assertEquals("vendor", p.getVendorId()); - assertEquals("vendor", p.getVendorDisplay()); - assertEquals("the_path", p.getPath()); - // path and vendor are combined in the default display name - assertEquals("Vendor The Path", p.getDisplayName()); - assertEquals("[old_path1, oldpath2]", Arrays.toString(p.getOldPaths())); - assertEquals(11, p.getMinApiLevel()); - assertEquals( - "[path1.jar, dir2/jar 2.jar, dir/3/path]", - Arrays.toString(p.getProjectFiles())); - } - - // ---- - - @Override - public final void testCreate() { - Properties props = createLoadedProps(); - ExtraPackage p = createExtraPackage(props); - - testCreatedExtraPackage(p); - } - - @Override - public void testSaveProperties() { - Properties props = createLoadedProps(); - ExtraPackage p = createExtraPackage(props); - - Properties props2 = new Properties(); - p.saveProperties(props2); - - assertEquals(props2, createSavedProps()); - } - - public void testSameItemAs() { - Properties props1 = createLoadedProps(); - ExtraPackage p1 = createExtraPackage(props1); - assertTrue(p1.sameItemAs(p1)); - - // different vendor, same path - Properties props2 = new Properties(props1); - props2.setProperty(PkgProps.EXTRA_VENDOR, "vendor2"); - ExtraPackage p2 = createExtraPackage(props2); - assertFalse(p1.sameItemAs(p2)); - assertFalse(p2.sameItemAs(p1)); - - // different vendor, different path - props2.setProperty(PkgProps.EXTRA_PATH, "new_path2"); - p2 = createExtraPackage(props2); - assertFalse(p1.sameItemAs(p2)); - assertFalse(p2.sameItemAs(p1)); - - // same vendor, but single path using the old paths from p1 - Properties props3 = new Properties(props1); - props3.setProperty(PkgProps.EXTRA_OLD_PATHS, ""); - props3.setProperty(PkgProps.EXTRA_PATH, "old_path1"); - ExtraPackage p3 = createExtraPackage(props3); - assertTrue(p1.sameItemAs(p3)); - assertTrue(p3.sameItemAs(p1)); - - props3.setProperty(PkgProps.EXTRA_PATH, "oldpath2"); - p3 = createExtraPackage(props3); - assertTrue(p1.sameItemAs(p3)); - assertTrue(p3.sameItemAs(p1)); - - // same vendor, different old paths but there's a path=>old_path match - Properties props4 = new Properties(props1); - props4.setProperty(PkgProps.EXTRA_OLD_PATHS, "new_path4;new_path5"); - props4.setProperty(PkgProps.EXTRA_PATH, "old_path1"); - ExtraPackage p4 = createExtraPackage(props4); - assertTrue(p1.sameItemAs(p4)); - assertTrue(p4.sameItemAs(p1)); - - // same vendor, incompatible paths - Properties props5 = new Properties(props1); - // and the only match is between old_paths, which doesn't count. - props5.setProperty(PkgProps.EXTRA_OLD_PATHS, "old_path1;new_path5"); - props5.setProperty(PkgProps.EXTRA_PATH, "new_path4"); - ExtraPackage p5 = createExtraPackage(props5); - assertFalse(p1.sameItemAs(p5)); - assertFalse(p5.sameItemAs(p1)); - } - - public void testInstallId() { - Properties props = createLoadedProps(); - ExtraPackage p = createExtraPackage(props); - - assertEquals("extra-vendor-the_path", p.installId()); - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/ExtraPackageTest_v4.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/ExtraPackageTest_v4.java deleted file mode 100755 index eff3020..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/ExtraPackageTest_v4.java +++ /dev/null @@ -1,162 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; -import com.android.sdklib.internal.repository.packages.ExtraPackage; -import com.android.sdklib.repository.PkgProps; - -import java.io.File; -import java.util.Arrays; -import java.util.Properties; - -/** - * Tests {@link ExtraPackage} using anddon-4.xsd: - * it has name-display, vendor-id and vendor-display. - */ -public class ExtraPackageTest_v4 extends MinToolsPackageTest { - - private static final char PS = File.pathSeparatorChar; - - private ExtraPackage createExtraPackage(Properties props) { - ExtraPackage p = (ExtraPackage) ExtraPackage.create( - null, //source - props, - null, //vendor - null, //path - -1, //revision - null, //license - null, //description - null, //descUrl - Os.ANY, //archiveOs - Arch.ANY, //archiveArch - "/local/archive/path" //archiveOsPath - ); - return p; - } - - @Override - protected Properties createProps() { - Properties props = super.createProps(); - - // ExtraPackage properties - props.setProperty(PkgProps.EXTRA_VENDOR_ID, "the_vendor"); - props.setProperty(PkgProps.EXTRA_VENDOR_DISPLAY, "The Company, Inc."); - props.setProperty(PkgProps.EXTRA_NAME_DISPLAY, "Some Extra Package"); - props.setProperty(PkgProps.EXTRA_PATH, "the_path"); - props.setProperty(PkgProps.EXTRA_OLD_PATHS, "old_path1;oldpath2"); - props.setProperty(PkgProps.EXTRA_MIN_API_LEVEL, "11"); - props.setProperty(PkgProps.EXTRA_PROJECT_FILES, - "path1.jar" + PS + "dir2/jar 2.jar" + PS + "dir/3/path"); - - return props; - } - - protected void testCreatedExtraPackage(ExtraPackage p) { - super.testCreatedPackage(p); - - // Package properties - assertEquals("the_vendor", p.getVendorId()); - assertEquals("The Company, Inc.", p.getVendorDisplay()); - assertEquals("Some Extra Package", p.getDisplayName()); - assertEquals("the_path", p.getPath()); - assertEquals("[old_path1, oldpath2]", Arrays.toString(p.getOldPaths())); - assertEquals(11, p.getMinApiLevel()); - assertEquals( - "[path1.jar, dir2/jar 2.jar, dir/3/path]", - Arrays.toString(p.getProjectFiles())); - } - - // ---- - - @Override - public final void testCreate() { - Properties props = createProps(); - ExtraPackage p = createExtraPackage(props); - - testCreatedExtraPackage(p); - } - - @Override - public void testSaveProperties() { - Properties props = createProps(); - ExtraPackage p = createExtraPackage(props); - - Properties props2 = new Properties(); - p.saveProperties(props2); - - assertEquals(props2, props); - } - - public void testSameItemAs() { - Properties props1 = createProps(); - ExtraPackage p1 = createExtraPackage(props1); - assertTrue(p1.sameItemAs(p1)); - - // different vendor, same path - Properties props2 = new Properties(props1); - props2.setProperty(PkgProps.EXTRA_VENDOR_ID, "vendor2"); - props2.setProperty(PkgProps.EXTRA_VENDOR_DISPLAY, "Another Vendor Name"); - ExtraPackage p2 = createExtraPackage(props2); - assertFalse(p1.sameItemAs(p2)); - assertFalse(p2.sameItemAs(p1)); - - // different vendor, different path - props2.setProperty(PkgProps.EXTRA_PATH, "new_path2"); - p2 = createExtraPackage(props2); - assertFalse(p1.sameItemAs(p2)); - assertFalse(p2.sameItemAs(p1)); - - // same vendor, but single path using the old paths from p1 - Properties props3 = new Properties(props1); - props3.setProperty(PkgProps.EXTRA_OLD_PATHS, ""); - props3.setProperty(PkgProps.EXTRA_PATH, "old_path1"); - ExtraPackage p3 = createExtraPackage(props3); - assertTrue(p1.sameItemAs(p3)); - assertTrue(p3.sameItemAs(p1)); - - props3.setProperty(PkgProps.EXTRA_PATH, "oldpath2"); - p3 = createExtraPackage(props3); - assertTrue(p1.sameItemAs(p3)); - assertTrue(p3.sameItemAs(p1)); - - // same vendor, different old paths but there's a path=>old_path match - Properties props4 = new Properties(props1); - props4.setProperty(PkgProps.EXTRA_OLD_PATHS, "new_path4;new_path5"); - props4.setProperty(PkgProps.EXTRA_PATH, "old_path1"); - ExtraPackage p4 = createExtraPackage(props4); - assertTrue(p1.sameItemAs(p4)); - assertTrue(p4.sameItemAs(p1)); - - // same vendor, incompatible paths - Properties props5 = new Properties(props1); - // and the only match is between old_paths, which doesn't count. - props5.setProperty(PkgProps.EXTRA_OLD_PATHS, "old_path1;new_path5"); - props5.setProperty(PkgProps.EXTRA_PATH, "new_path4"); - ExtraPackage p5 = createExtraPackage(props5); - assertFalse(p1.sameItemAs(p5)); - assertFalse(p5.sameItemAs(p1)); - } - - public void testInstallId() { - Properties props = createProps(); - ExtraPackage p = createExtraPackage(props); - - assertEquals("extra-the_vendor-the_path", p.installId()); - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/FullRevisionPackageTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/FullRevisionPackageTest.java deleted file mode 100755 index 9bf2703..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/FullRevisionPackageTest.java +++ /dev/null @@ -1,75 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.repository.PkgProps; - -import java.util.ArrayList; -import java.util.Arrays; -import java.util.Collections; -import java.util.Properties; - -import junit.framework.TestCase; - -public class FullRevisionPackageTest extends TestCase { - - /** - * Helper that creates the {@link Properties} from a {@link FullRevision} - * as expected by {@link FullRevisionPackage}. - */ - public static Properties createProps(FullRevision revision) { - Properties props = new Properties(); - if (revision != null) { - props.setProperty(PkgProps.PKG_REVISION, revision.toString()); - } - return props; - } - - public void testCompareTo() throws Exception { - // Test order of full revision packages. - // - // Note that Package.compareTo() is designed to return the desired - // ordering for a list display and as such a final/release package - // needs to be listed before its rc/preview package. - // - // This differs from the order used by FullRevision.compareTo(). - - ArrayList<Package> list = new ArrayList<Package>(); - - list.add(new MockToolPackage(null, new FullRevision(1, 0, 0, 0), 8)); - list.add(new MockToolPackage(null, new FullRevision(1, 0, 0, 1), 8)); - list.add(new MockToolPackage(null, new FullRevision(1, 0, 1, 0), 8)); - list.add(new MockToolPackage(null, new FullRevision(1, 0, 1, 1), 8)); - list.add(new MockToolPackage(null, new FullRevision(1, 1, 0, 0), 8)); - list.add(new MockToolPackage(null, new FullRevision(1, 1, 0, 1), 8)); - list.add(new MockToolPackage(null, new FullRevision(2, 1, 1, 0), 8)); - list.add(new MockToolPackage(null, new FullRevision(2, 1, 1, 1), 8)); - - Collections.sort(list); - - assertEquals( - "[Android SDK Tools, revision 1, " + - "Android SDK Tools, revision 1 rc1, " + - "Android SDK Tools, revision 1.0.1, " + - "Android SDK Tools, revision 1.0.1 rc1, " + - "Android SDK Tools, revision 1.1, " + - "Android SDK Tools, revision 1.1 rc1, " + - "Android SDK Tools, revision 2.1.1, " + - "Android SDK Tools, revision 2.1.1 rc1]", - Arrays.toString(list.toArray())); - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/FullRevisionTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/FullRevisionTest.java deleted file mode 100755 index 07e8186..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/FullRevisionTest.java +++ /dev/null @@ -1,158 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import java.util.Arrays; - -import junit.framework.TestCase; - -public class FullRevisionTest extends TestCase { - - public final void testFullRevision() { - FullRevision p = new FullRevision(5); - assertEquals(5, p.getMajor()); - assertEquals(FullRevision.IMPLICIT_MINOR_REV, p.getMinor()); - assertEquals(FullRevision.IMPLICIT_MICRO_REV, p.getMicro()); - assertEquals(FullRevision.NOT_A_PREVIEW, p.getPreview()); - assertFalse (p.isPreview()); - assertEquals("5", p.toShortString()); - assertEquals(p, FullRevision.parseRevision("5")); - assertEquals("5.0.0", p.toString()); - assertEquals(p, FullRevision.parseRevision("5.0.0")); - assertEquals("[5, 0, 0]", Arrays.toString(p.toIntArray(false /*includePreview*/))); - assertEquals("[5, 0, 0, 0]", Arrays.toString(p.toIntArray(true /*includePreview*/))); - - p = new FullRevision(5, 0, 0, 6); - assertEquals(5, p.getMajor()); - assertEquals(FullRevision.IMPLICIT_MINOR_REV, p.getMinor()); - assertEquals(FullRevision.IMPLICIT_MICRO_REV, p.getMicro()); - assertEquals(6, p.getPreview()); - assertTrue (p.isPreview()); - assertEquals("5 rc6", p.toShortString()); - assertEquals(p, FullRevision.parseRevision("5 rc6")); - assertEquals("5.0.0 rc6", p.toString()); - assertEquals(p, FullRevision.parseRevision("5.0.0 rc6")); - assertEquals("[5, 0, 0]", Arrays.toString(p.toIntArray(false /*includePreview*/))); - assertEquals("[5, 0, 0, 6]", Arrays.toString(p.toIntArray(true /*includePreview*/))); - - p = new FullRevision(6, 7, 0); - assertEquals(6, p.getMajor()); - assertEquals(7, p.getMinor()); - assertEquals(0, p.getMicro()); - assertEquals(0, p.getPreview()); - assertFalse (p.isPreview()); - assertEquals("6.7", p.toShortString()); - assertEquals(p, FullRevision.parseRevision("6.7")); - assertEquals("6.7.0", p.toString()); - assertEquals(p, FullRevision.parseRevision("6.7.0")); - assertEquals("[6, 7, 0]", Arrays.toString(p.toIntArray(false /*includePreview*/))); - assertEquals("[6, 7, 0, 0]", Arrays.toString(p.toIntArray(true /*includePreview*/))); - - p = new FullRevision(10, 11, 12, FullRevision.NOT_A_PREVIEW); - assertEquals(10, p.getMajor()); - assertEquals(11, p.getMinor()); - assertEquals(12, p.getMicro()); - assertEquals(0, p.getPreview()); - assertFalse (p.isPreview()); - assertEquals("10.11.12", p.toShortString()); - assertEquals("10.11.12", p.toString()); - assertEquals(p, FullRevision.parseRevision("10.11.12")); - assertEquals("[10, 11, 12]", Arrays.toString(p.toIntArray(false /*includePreview*/))); - assertEquals("[10, 11, 12, 0]", Arrays.toString(p.toIntArray(true /*includePreview*/))); - - p = new FullRevision(10, 11, 12, 13); - assertEquals(10, p.getMajor()); - assertEquals(11, p.getMinor()); - assertEquals(12, p.getMicro()); - assertEquals(13, p.getPreview()); - assertTrue (p.isPreview()); - assertEquals("10.11.12 rc13", p.toShortString()); - assertEquals("10.11.12 rc13", p.toString()); - assertEquals(p, FullRevision.parseRevision("10.11.12 rc13")); - assertEquals(p, FullRevision.parseRevision(" 10.11.12 rc13")); - assertEquals(p, FullRevision.parseRevision("10.11.12 rc13 ")); - assertEquals(p, FullRevision.parseRevision(" 10.11.12 rc13 ")); - assertEquals("[10, 11, 12]", Arrays.toString(p.toIntArray(false /*includePreview*/))); - assertEquals("[10, 11, 12, 13]", Arrays.toString(p.toIntArray(true /*includePreview*/))); - } - - public final void testParseError() { - String errorMsg = null; - try { - FullRevision.parseRevision("not a number"); - fail("FullRevision.parseRevision should thrown NumberFormatException"); - } catch (NumberFormatException e) { - errorMsg = e.getMessage(); - } - assertEquals("Invalid full revision: not a number", errorMsg); - - errorMsg = null; - try { - FullRevision.parseRevision("5 .6 .7"); - fail("FullRevision.parseRevision should thrown NumberFormatException"); - } catch (NumberFormatException e) { - errorMsg = e.getMessage(); - } - assertEquals("Invalid full revision: 5 .6 .7", errorMsg); - - errorMsg = null; - try { - FullRevision.parseRevision("5.0.0 preview 1"); - fail("FullRevision.parseRevision should thrown NumberFormatException"); - } catch (NumberFormatException e) { - errorMsg = e.getMessage(); - } - assertEquals("Invalid full revision: 5.0.0 preview 1", errorMsg); - - errorMsg = null; - try { - FullRevision.parseRevision(" 5.1.2 rc 42 "); - fail("FullRevision.parseRevision should thrown NumberFormatException"); - } catch (NumberFormatException e) { - errorMsg = e.getMessage(); - } - assertEquals("Invalid full revision: 5.1.2 rc 42 ", errorMsg); - } - - public final void testCompareTo() { - FullRevision s4 = new FullRevision(4); - FullRevision i4 = new FullRevision(4); - FullRevision g5 = new FullRevision(5, 1, 0, 6); - FullRevision y5 = new FullRevision(5); - FullRevision c5 = new FullRevision(5, 1, 0, 6); - FullRevision o5 = new FullRevision(5, 0, 0, 7); - FullRevision p5 = new FullRevision(5, 1, 0, 0); - - assertEquals(s4, i4); // 4.0.0-0 == 4.0.0-0 - assertEquals(g5, c5); // 5.1.0-6 == 5.1.0-6 - - assertFalse(y5.equals(p5)); // 5.0.0-0 != 5.1.0-0 - assertFalse(g5.equals(p5)); // 5.1.0-6 != 5.1.0-0 - assertTrue (s4.compareTo(i4) == 0); // 4.0.0-0 == 4.0.0-0 - assertTrue (s4.compareTo(y5) < 0); // 4.0.0-0 < 5.0.0-0 - assertTrue (y5.compareTo(y5) == 0); // 5.0.0-0 == 5.0.0-0 - assertTrue (y5.compareTo(p5) < 0); // 5.0.0-0 < 5.1.0-0 - assertTrue (o5.compareTo(y5) < 0); // 5.0.0-7 < 5.0.0-0 - assertTrue (p5.compareTo(p5) == 0); // 5.1.0-0 == 5.1.0-0 - assertTrue (c5.compareTo(p5) < 0); // 5.1.0-6 < 5.1.0-0 - assertTrue (p5.compareTo(c5) > 0); // 5.1.0-0 > 5.1.0-6 - assertTrue (p5.compareTo(o5) > 0); // 5.1.0-0 > 5.0.0-7 - assertTrue (c5.compareTo(o5) > 0); // 5.1.0-6 > 5.0.0-7 - assertTrue (o5.compareTo(o5) == 0); // 5.0.0-7 > 5.0.0-7 - } - -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MajorRevisionTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MajorRevisionTest.java deleted file mode 100755 index b77caad..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MajorRevisionTest.java +++ /dev/null @@ -1,75 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import junit.framework.TestCase; - -public class MajorRevisionTest extends TestCase { - - public final void testMajorRevision() { - MajorRevision p = new MajorRevision(5); - assertEquals(5, p.getMajor()); - assertEquals(FullRevision.IMPLICIT_MINOR_REV, p.getMinor()); - assertEquals(FullRevision.IMPLICIT_MICRO_REV, p.getMicro()); - assertEquals(FullRevision.NOT_A_PREVIEW, p.getPreview()); - assertFalse (p.isPreview()); - assertEquals("5", p.toShortString()); - assertEquals(p, MajorRevision.parseRevision("5")); - assertEquals("5", p.toString()); - - assertEquals(new FullRevision(5, 0, 0, 0), p); - } - - public final void testParseError() { - String errorMsg = null; - try { - MajorRevision.parseRevision("5.0.0"); - fail("MajorRevision.parseRevision should thrown NumberFormatException"); - } catch (NumberFormatException e) { - errorMsg = e.getMessage(); - } - assertEquals("For input string: \"5.0.0\"", errorMsg); - } - - public final void testCompareTo() { - MajorRevision s4 = new MajorRevision(4); - MajorRevision i4 = new MajorRevision(4); - FullRevision g5 = new FullRevision (5, 1, 0, 6); - MajorRevision y5 = new MajorRevision(5); - FullRevision c5 = new FullRevision (5, 1, 0, 6); - FullRevision o5 = new FullRevision (5, 0, 0, 7); - FullRevision p5 = new FullRevision (5, 1, 0, 0); - - assertEquals(s4, i4); // 4.0.0-0 == 4.0.0-0 - assertEquals(g5, c5); // 5.1.0-6 == 5.1.0-6 - - assertFalse(y5.equals(p5)); // 5.0.0-0 != 5.1.0-0 - assertFalse(g5.equals(p5)); // 5.1.0-6 != 5.1.0-0 - assertTrue (s4.compareTo(i4) == 0); // 4.0.0-0 == 4.0.0-0 - assertTrue (s4.compareTo(y5) < 0); // 4.0.0-0 < 5.0.0-0 - assertTrue (y5.compareTo(y5) == 0); // 5.0.0-0 == 5.0.0-0 - assertTrue (y5.compareTo(p5) < 0); // 5.0.0-0 < 5.1.0-0 - assertTrue (o5.compareTo(y5) < 0); // 5.0.0-7 < 5.0.0-0 - assertTrue (p5.compareTo(p5) == 0); // 5.1.0-0 == 5.1.0-0 - assertTrue (c5.compareTo(p5) < 0); // 5.1.0-6 < 5.1.0-0 - assertTrue (p5.compareTo(c5) > 0); // 5.1.0-0 > 5.1.0-6 - assertTrue (p5.compareTo(o5) > 0); // 5.1.0-0 > 5.0.0-7 - assertTrue (c5.compareTo(o5) > 0); // 5.1.0-6 > 5.0.0-7 - assertTrue (o5.compareTo(o5) == 0); // 5.0.0-7 > 5.0.0-7 - } - -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MinToolsPackageTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MinToolsPackageTest.java deleted file mode 100755 index adffe2e..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MinToolsPackageTest.java +++ /dev/null @@ -1,138 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.SdkManager; -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; -import com.android.sdklib.internal.repository.packages.MinToolsPackage; -import com.android.sdklib.internal.repository.packages.Package; -import com.android.sdklib.internal.repository.sources.SdkSource; -import com.android.sdklib.repository.PkgProps; - -import java.io.File; -import java.util.Properties; - -public class MinToolsPackageTest extends PackageTest { - - /** Local class used to test the abstract MinToolsPackage class */ - protected static class MockMinToolsPackage extends MinToolsPackage { - public MockMinToolsPackage( - SdkSource source, - Properties props, - int revision, - String license, - String description, - String descUrl, - Os archiveOs, - Arch archiveArch, - String archiveOsPath) { - super(source, - props, - revision, - license, - description, - descUrl, - archiveOs, - archiveArch, - archiveOsPath); - } - - @Override - public File getInstallFolder(String osSdkRoot, SdkManager sdkManager) { - throw new UnsupportedOperationException("abstract method not used in test"); //$NON-NLS-1$ - } - - @Override - public String getListDescription() { - throw new UnsupportedOperationException("abstract method not used in test"); //$NON-NLS-1$ - } - - @Override - public String getShortDescription() { - throw new UnsupportedOperationException("abstract method not used in test"); //$NON-NLS-1$ - } - - @Override - public boolean sameItemAs(Package pkg) { - throw new UnsupportedOperationException("abstract method not used in test"); //$NON-NLS-1$ - } - - @Override - public String installId() { - return ""; //$NON-NLS-1$ - } - } - - @Override - public void testCreate() { - Properties props = createProps(); - - MockMinToolsPackage p = new MockMinToolsPackage( - null, //source - props, - -1, //revision - null, //license - null, //description - null, //descUrl - Os.ANY, //archiveOs - Arch.ANY, //archiveArch - LOCAL_ARCHIVE_PATH - ); - - testCreatedPackage(p); - } - - @Override - public void testSaveProperties() { - Properties props = createProps(); - - MockMinToolsPackage p = new MockMinToolsPackage( - null, //source - props, - -1, //revision - null, //license - null, //description - null, //descUrl - Os.ANY, //archiveOs - Arch.ANY, //archiveArch - LOCAL_ARCHIVE_PATH - ); - - Properties props2 = new Properties(); - p.saveProperties(props2); - - assertEquals(props2, props); - } - - @Override - protected Properties createProps() { - Properties props = super.createProps(); - - // MinToolsPackage properties - props.setProperty(PkgProps.MIN_TOOLS_REV, "3.0.1"); - - return props; - } - - protected void testCreatedMinToolsPackage(MockMinToolsPackage p) { - super.testCreatedPackage(p); - - // MinToolsPackage properties - assertEquals("3.0.1", p.getMinToolsRevision().toShortString()); - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MockAddonPackage.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MockAddonPackage.java deleted file mode 100755 index 7a52e7d..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MockAddonPackage.java +++ /dev/null @@ -1,251 +0,0 @@ -/* - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.SdkConstants; -import com.android.sdklib.AndroidVersion; -import com.android.sdklib.IAndroidTarget; -import com.android.sdklib.ISystemImage; -import com.android.sdklib.ISystemImage.LocationType; -import com.android.sdklib.SystemImage; -import com.android.sdklib.internal.repository.sources.SdkSource; -import com.android.sdklib.io.FileOp; -import com.android.sdklib.repository.PkgProps; - -import java.util.Map; -import java.util.Properties; - -/** - * A mock {@link AddonPackage} for testing. - * - * By design, this package contains one and only one archive. - */ -public class MockAddonPackage extends AddonPackage { - - /** - * Creates a {@link MockAddonTarget} with the requested base platform and addon revision - * and then a {@link MockAddonPackage} wrapping it and a default name of "addon". - * - * By design, this package contains one and only one archive. - */ - public MockAddonPackage(MockPlatformPackage basePlatform, int revision) { - this("addon", basePlatform, revision); //$NON-NLS-1$ - } - - /** - * Creates a {@link MockAddonTarget} with the requested base platform and addon revision - * and then a {@link MockAddonPackage} wrapping it. - * - * By design, this package contains one and only one archive. - */ - public MockAddonPackage(String name, MockPlatformPackage basePlatform, int revision) { - super(new MockAddonTarget(name, basePlatform.getTarget(), revision), null /*props*/); - } - - public MockAddonPackage( - SdkSource source, - String name, - MockPlatformPackage basePlatform, - int revision) { - super(source, - new MockAddonTarget(name, basePlatform.getTarget(), revision), - createProperties(name, basePlatform.getTarget())); - } - - private static Properties createProperties(String name, IAndroidTarget baseTarget) { - String vendor = baseTarget.getVendor(); - Properties props = new Properties(); - props.setProperty(PkgProps.ADDON_NAME_ID, name); - props.setProperty(PkgProps.ADDON_NAME_DISPLAY, - String.format("The %1$s from %2$s", //$NON-NLS-1$ - name, vendor)); - props.setProperty(PkgProps.ADDON_VENDOR_ID, - String.format("vendor-id-%1$s", vendor)); //$NON-NLS-1$ - props.setProperty(PkgProps.ADDON_VENDOR_DISPLAY, - String.format("The %1$s", vendor)); //$NON-NLS-1$ - return props; - } - - /** - * A mock AddonTarget. - * This reimplements the minimum needed from the interface for our limited testing needs. - */ - static class MockAddonTarget implements IAndroidTarget { - - private final IAndroidTarget mParentTarget; - private final int mRevision; - private final String mName; - private ISystemImage[] mSystemImages; - - public MockAddonTarget(String name, IAndroidTarget parentTarget, int revision) { - mName = name; - mParentTarget = parentTarget; - mRevision = revision; - } - - @Override - public String getClasspathName() { - return getName(); - } - - @Override - public String getShortClasspathName() { - return getName(); - } - - @Override - public String getDefaultSkin() { - return null; - } - - @Override - public String getDescription() { - return getName(); - } - - @Override - public String getFullName() { - return getName(); - } - - @Override - public ISystemImage[] getSystemImages() { - if (mSystemImages == null) { - SystemImage si = new SystemImage( - FileOp.append(getLocation(), SdkConstants.OS_IMAGES_FOLDER), - LocationType.IN_PLATFORM_LEGACY, - SdkConstants.ABI_ARMEABI); - mSystemImages = new SystemImage[] { si }; - } - return mSystemImages; - } - - @Override - public ISystemImage getSystemImage(String abiType) { - if (SdkConstants.ABI_ARMEABI.equals(abiType)) { - return getSystemImages()[0]; - } - return null; - } - - @Override - public String getLocation() { - return "/sdk/add-ons/addon-" + mName; - } - - @Override - public IOptionalLibrary[] getOptionalLibraries() { - return null; - } - - @Override - public IAndroidTarget getParent() { - return mParentTarget; - } - - @Override - public String getPath(int pathId) { - throw new UnsupportedOperationException("Implement this as needed for tests"); - } - - @Override - public String[] getPlatformLibraries() { - return null; - } - - @Override - public String getProperty(String name) { - return null; - } - - @Override - public Integer getProperty(String name, Integer defaultValue) { - return defaultValue; - } - - @Override - public Boolean getProperty(String name, Boolean defaultValue) { - return defaultValue; - } - - @Override - public Map<String, String> getProperties() { - return null; - } - - @Override - public int getRevision() { - return mRevision; - } - - @Override - public String[] getSkins() { - return null; - } - - @Override - public int getUsbVendorId() { - return 0; - } - - @Override - public AndroidVersion getVersion() { - return mParentTarget.getVersion(); - } - - @Override - public String getName() { - return mName; - } - - @Override - public String getVendor() { - return mParentTarget.getVendor(); - } - - @Override - public String getVersionName() { - return String.format("mock-addon-%1$d", getVersion().getApiLevel()); - } - - @Override - public String hashString() { - return getVersionName(); - } - - /** Returns false for an addon. */ - @Override - public boolean isPlatform() { - return false; - } - - @Override - public boolean canRunOn(IAndroidTarget target) { - throw new UnsupportedOperationException("Implement this as needed for tests"); - } - - @Override - public int compareTo(IAndroidTarget o) { - throw new UnsupportedOperationException("Implement this as needed for tests"); - } - - @Override - public boolean hasRenderingLibrary() { - return false; - } - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MockBrokenPackage.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MockBrokenPackage.java deleted file mode 100755 index e78e796..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MockBrokenPackage.java +++ /dev/null @@ -1,57 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.internal.repository.packages.BrokenPackage; - - -/** - * A mock {@link BrokenPackage} for testing. - * <p/> - * By design, this package contains one and only one archive. - */ -public class MockBrokenPackage extends BrokenPackage { - - public MockBrokenPackage(int minApiLevel, int exactApiLevel) { - this(createDesription(minApiLevel, exactApiLevel), // short description - createDesription(minApiLevel, exactApiLevel), // long description - minApiLevel, - exactApiLevel); - } - - private static String createDesription(int minApiLevel, int exactApiLevel) { - String s = "Broken package"; - s += exactApiLevel == BrokenPackage.API_LEVEL_INVALID ? " (No API level)" : - String.format(" for API %d", exactApiLevel); - s += minApiLevel == BrokenPackage.MIN_API_LEVEL_NOT_SPECIFIED ? "" : - String.format(", min API %d", minApiLevel); - return s; - } - - public MockBrokenPackage( - String shortDescription, - String longDescription, - int minApiLevel, - int exactApiLevel) { - super(null /*props*/, - shortDescription, - longDescription, - minApiLevel, - exactApiLevel, - "/sdk/broken/package" /*osPath*/); - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MockEmptyPackage.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MockEmptyPackage.java deleted file mode 100755 index 70f57b4..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MockEmptyPackage.java +++ /dev/null @@ -1,179 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.SdkManager; -import com.android.sdklib.internal.repository.archives.Archive; -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; -import com.android.sdklib.internal.repository.packages.Package; -import com.android.sdklib.internal.repository.sources.SdkSource; - -import java.io.File; -import java.util.Properties; - -/** - * A mock empty package, of no particular subpackage type. - * {@link #sameItemAs(Package)} will return true if these packages have the same handle. - */ -public class MockEmptyPackage extends MajorRevisionPackage { - private final String mTestHandle; - - /** - * Creates a new {@link MockEmptyPackage} with a local archive. - * - * @param testHandle The comparison handle for {@link #sameItemAs(Package)}. - */ - public MockEmptyPackage(String testHandle) { - super( - null /*source*/, - null /*props*/, - 0 /*revision*/, - null /*license*/, - null /*description*/, - null /*descUrl*/, - Os.ANY /*archiveOs*/, - Arch.ANY /*archiveArch*/, - "/sdk/tmp/empty_pkg" /*archiveOsPath*/ - ); - mTestHandle = testHandle; - } - - /** - * Creates a new {@link MockEmptyPackage} with a local archive. - * - * @param testHandle The comparison handle for {@link #sameItemAs(Package)}. - * @param revision The revision of the package, printed in the short description. - */ - public MockEmptyPackage(String testHandle, int revision) { - super( - null /*source*/, - null /*props*/, - revision, - null /*license*/, - null /*description*/, - null /*descUrl*/, - Os.ANY /*archiveOs*/, - Arch.ANY /*archiveArch*/, - "/sdk/tmp/empty_pkg" /*archiveOsPath*/ - ); - mTestHandle = testHandle; - } - - /** - * Creates a new {@link MockEmptyPackage} with a local archive. - * - * @param source The source associate with this package. - * @param testHandle The comparison handle for {@link #sameItemAs(Package)}. - * @param revision The revision of the package, printed in the short description. - */ - public MockEmptyPackage(SdkSource source, String testHandle, int revision) { - super( - source, - null /*props*/, - revision, - null /*license*/, - null /*description*/, - null /*descUrl*/, - Os.ANY /*archiveOs*/, - Arch.ANY /*archiveArch*/, - "/sdk/tmp/empty_pkg" /*archiveOsPath*/ - ); - mTestHandle = testHandle; - } - - @Override - protected Archive[] initializeArchives( - Properties props, - Os archiveOs, - Arch archiveArch, - String archiveOsPath) { - return new Archive[] { - new Archive(this, props, archiveOs, archiveArch, archiveOsPath) { - @Override - public String toString() { - return mTestHandle; - } - } }; - } - - public Archive getLocalArchive() { - return getArchives()[0]; - } - - @Override - public File getInstallFolder(String osSdkRoot, SdkManager sdkManager) { - return new File(new File(osSdkRoot, "mock"), mTestHandle); - } - - @Override - public String installId() { - return "mock-empty-" + mTestHandle; //$NON-NLS-1$ - } - - @Override - public String getListDescription() { - return this.getClass().getSimpleName(); - } - - @Override - public String getShortDescription() { - StringBuilder sb = new StringBuilder(this.getClass().getSimpleName()); - sb.append(" '").append(mTestHandle).append('\''); - if (getRevision().getMajor() > 0) { - sb.append(" rev=").append(getRevision()); - } - return sb.toString(); - } - - /** Returns true if these packages have the same handle. */ - @Override - public boolean sameItemAs(Package pkg) { - return (pkg instanceof MockEmptyPackage) && - mTestHandle.equals(((MockEmptyPackage) pkg).mTestHandle); - } - - @Override - public int hashCode() { - final int prime = 31; - int result = super.hashCode(); - result = prime * result + ((mTestHandle == null) ? 0 : mTestHandle.hashCode()); - return result; - } - - @Override - public boolean equals(Object obj) { - if (this == obj) { - return true; - } - if (!super.equals(obj)) { - return false; - } - if (!(obj instanceof MockEmptyPackage)) { - return false; - } - MockEmptyPackage other = (MockEmptyPackage) obj; - if (mTestHandle == null) { - if (other.mTestHandle != null) { - return false; - } - } else if (!mTestHandle.equals(other.mTestHandle)) { - return false; - } - return true; - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MockExtraPackage.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MockExtraPackage.java deleted file mode 100755 index ca5a6cf..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MockExtraPackage.java +++ /dev/null @@ -1,79 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; -import com.android.sdklib.internal.repository.sources.SdkSource; -import com.android.sdklib.repository.PkgProps; - -import java.util.Properties; - -/** - * A mock {@link ExtraPackage} for testing. - * - * By design, this package contains one and only one archive. - */ -public class MockExtraPackage extends ExtraPackage { - - /** - * Creates a {@link MockExtraPackage} with the given revision and hardcoded defaults - * for everything else. - * <p/> - * By design, this creates a package with one and only one archive. - */ - public MockExtraPackage(String vendor, String path, int revision, int min_platform_tools_rev) { - this(null /*source*/, vendor, path, revision, min_platform_tools_rev); - } - - public MockExtraPackage( - SdkSource source, - Properties props, - String vendor, - String path, - int revision) { - super( - source, - props, // props, - vendor, - path, - revision, - null, // license, - "desc", // description, - "url", // descUrl, - Os.getCurrentOs(), // archiveOs, - Arch.getCurrentArch(), // archiveArch, - "foo" // archiveOsPath - ); - } - - public MockExtraPackage( - SdkSource source, - String vendor, - String path, - int revision, - int min_platform_tools_rev) { - this(source, createProps(min_platform_tools_rev), vendor, path, revision); - } - - private static Properties createProps(int min_platform_tools_rev) { - Properties props = new Properties(); - props.setProperty(PkgProps.MIN_PLATFORM_TOOLS_REV, - Integer.toString((min_platform_tools_rev))); - return props; - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MockPlatformPackage.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MockPlatformPackage.java deleted file mode 100755 index dd744ec..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MockPlatformPackage.java +++ /dev/null @@ -1,99 +0,0 @@ -/* - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.IAndroidTarget; -import com.android.sdklib.internal.repository.MockPlatformTarget; -import com.android.sdklib.internal.repository.packages.PlatformPackage; -import com.android.sdklib.internal.repository.sources.SdkSource; -import com.android.sdklib.repository.PkgProps; - -import java.util.Properties; - -/** - * A mock {@link PlatformPackage} for testing. - * - * By design, this package contains one and only one archive. - */ -public class MockPlatformPackage extends PlatformPackage { - - private final IAndroidTarget mTarget; - - /** - * Creates a {@link MockPlatformTarget} with the requested API and revision - * and then a {@link MockPlatformPackage} wrapping it. - * - * By design, this package contains one and only one archive. - */ - public MockPlatformPackage(int apiLevel, int revision) { - this(null /*source*/, new MockPlatformTarget(apiLevel, revision), null /*props*/); - } - - /** - * Creates a {@link MockPlatformTarget} with the requested API and revision - * and then a {@link MockPlatformPackage} wrapping it. - * - * Also sets the min-tools-rev of the platform using a major revision integer. - * - * By design, this package contains one and only one archive. - */ - public MockPlatformPackage(int apiLevel, int revision, int min_tools_rev) { - this(null /*source*/, - new MockPlatformTarget(apiLevel, revision), - createProps(min_tools_rev)); - } - - /** - * Creates a {@link MockPlatformTarget} with the requested API and revision - * and then a {@link MockPlatformPackage} wrapping it. - * - * Also sets the min-tools-rev of the platform using a {@link FullRevision}. - * - * By design, this package contains one and only one archive. - */ - public MockPlatformPackage(int apiLevel, int revision, FullRevision min_tools_rev) { - this(null /*source*/, - new MockPlatformTarget(apiLevel, revision), - createProps(min_tools_rev)); - } - - public MockPlatformPackage(SdkSource source, int apiLevel, int revision, int min_tools_rev) { - this(source, new MockPlatformTarget(apiLevel, revision), createProps(min_tools_rev)); - } - - /** A little trick to be able to capture the target new after passing it to the super. */ - private MockPlatformPackage(SdkSource source, IAndroidTarget target, Properties props) { - super(source, target, props); - mTarget = target; - } - - private static Properties createProps(int min_tools_rev) { - Properties props = new Properties(); - props.setProperty(PkgProps.MIN_TOOLS_REV, Integer.toString((min_tools_rev))); - return props; - } - - private static Properties createProps(FullRevision min_tools_rev) { - Properties props = new Properties(); - props.setProperty(PkgProps.MIN_TOOLS_REV, min_tools_rev.toShortString()); - return props; - } - - public IAndroidTarget getTarget() { - return mTarget; - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MockPlatformToolPackage.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MockPlatformToolPackage.java deleted file mode 100755 index b11c991..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MockPlatformToolPackage.java +++ /dev/null @@ -1,80 +0,0 @@ -/* - * Copyright (C) 2010 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; -import com.android.sdklib.internal.repository.sources.SdkSource; - -/** - * A mock {@link PlatformToolPackage} for testing. - * - * By design, this package contains one and only one archive. - */ -public class MockPlatformToolPackage extends PlatformToolPackage { - - /** - * Creates a {@link MockPlatformToolPackage} with the given revision and hardcoded defaults - * for everything else. - * <p/> - * By design, this creates a package with one and only one archive. - */ - public MockPlatformToolPackage(int revision) { - this(null /*source*/, revision); - } - - /** - * Creates a {@link MockPlatformToolPackage} with the given revision and hardcoded defaults - * for everything else. - * <p/> - * By design, this creates a package with one and only one archive. - */ - public MockPlatformToolPackage(SdkSource source, int revision) { - super( - source, // source, - null, // props, - revision, - null, // license, - "desc", // description, - "url", // descUrl, - Os.getCurrentOs(), // archiveOs, - Arch.getCurrentArch(), // archiveArch, - "foo" // archiveOsPath - ); - } - - /** - * Creates a {@link MockPlatformToolPackage} with the given revision and hardcoded defaults - * for everything else. - * <p/> - * By design, this creates a package with one and only one archive. - */ - public MockPlatformToolPackage(SdkSource source, FullRevision revision) { - super( - source, // source, - FullRevisionPackageTest.createProps(revision), // props, - revision.getMajor(), - null, // license, - "desc", // description, - "url", // descUrl, - Os.getCurrentOs(), // archiveOs, - Arch.getCurrentArch(), // archiveArch, - "foo" // archiveOsPath - ); - } -} - diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MockSourcePackage.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MockSourcePackage.java deleted file mode 100755 index 4c129a3..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MockSourcePackage.java +++ /dev/null @@ -1,60 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.AndroidVersion; -import com.android.sdklib.internal.repository.packages.SourcePackage; -import com.android.sdklib.internal.repository.packages.SystemImagePackage; -import com.android.sdklib.internal.repository.sources.SdkSource; - - -/** - * A mock {@link SystemImagePackage} for testing. - * - * By design, this package contains one and only one archive. - */ -public class MockSourcePackage extends SourcePackage { - /** - * Creates a {@link MockSourcePackage} using the given base platform version - * and package revision. - * - * By design, this package contains one and only one archive. - */ - public MockSourcePackage(AndroidVersion version, int revision) { - super(version, - revision, - null /*props*/, - String.format("/sdk/sources/android-%s", version.getApiString())); - } - - /** - * Creates a {@link MockSourcePackage} using the given version, - * sdk source and package revision. - * - * By design, this package contains one and only one archive. - */ - public MockSourcePackage( - SdkSource source, - AndroidVersion version, - int revision) { - super(source, - version, - revision, - null /*props*/, - String.format("/sdk/sources/android-%s", version.getApiString())); - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MockSystemImagePackage.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MockSystemImagePackage.java deleted file mode 100755 index 3c7baec..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MockSystemImagePackage.java +++ /dev/null @@ -1,63 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.internal.repository.packages.SystemImagePackage; -import com.android.sdklib.internal.repository.sources.SdkSource; - - -/** - * A mock {@link SystemImagePackage} for testing. - * - * By design, this package contains one and only one archive. - */ -public class MockSystemImagePackage extends SystemImagePackage { - /** - * Creates a {@link MockSystemImagePackage} using the given base platform version - * and package revision. - * - * By design, this package contains one and only one archive. - */ - public MockSystemImagePackage(MockPlatformPackage basePlatform, int revision, String abi) { - super(basePlatform.getAndroidVersion(), - revision, - abi, - null /*props*/, - String.format("/sdk/system-images/android-%s/%s", - basePlatform.getAndroidVersion().getApiString(), abi)); - } - - /** - * Creates a {@link MockSystemImagePackage} using the given base platform version, - * sdk source and package revision. - * - * By design, this package contains one and only one archive. - */ - public MockSystemImagePackage( - SdkSource source, - MockPlatformPackage basePlatform, - int revision, - String abi) { - super(source, - basePlatform.getAndroidVersion(), - revision, - abi, - null /*props*/, - String.format("/sdk/system-images/android-%s/%s", - basePlatform.getAndroidVersion().getApiString(), abi)); - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MockToolPackage.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MockToolPackage.java deleted file mode 100755 index 3c39194..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/MockToolPackage.java +++ /dev/null @@ -1,123 +0,0 @@ -/* - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; -import com.android.sdklib.internal.repository.packages.ToolPackage; -import com.android.sdklib.internal.repository.sources.SdkSource; -import com.android.sdklib.repository.PkgProps; - -import java.util.Properties; - -/** - * A mock {@link ToolPackage} for testing. - * - * By design, this package contains one and only one archive. - */ -public class MockToolPackage extends ToolPackage { - - /** - * Creates a {@link MockToolPackage} with the given revision and hardcoded defaults - * for everything else. - * <p/> - * By design, this creates a package with one and only one archive. - */ - public MockToolPackage(int revision, int min_platform_tools_rev) { - this(null /*source*/, revision, min_platform_tools_rev); - } - - /** - * Creates a {@link MockToolPackage} with the given revision and hardcoded defaults - * for everything else. - * <p/> - * By design, this creates a package with one and only one archive. - */ - public MockToolPackage(SdkSource source, int revision, int minPlatformToolsRev) { - super( - source, // source, - createProps(null /*version*/, minPlatformToolsRev), // props, - revision, - null, // license, - "desc", // description, - "url", // descUrl, - Os.getCurrentOs(), // archiveOs, - Arch.getCurrentArch(), // archiveArch, - "foo" // archiveOsPath - ); - } - - /** - * Creates a {@link MockToolPackage} with the given revision and hardcoded defaults - * for everything else. - * <p/> - * By design, this creates a package with one and only one archive. - */ - public MockToolPackage( - SdkSource source, - FullRevision revision, - int minPlatformToolsRev) { - super( - source, // source, - createProps(revision, minPlatformToolsRev), // props, - revision.getMajor(), - null, // license, - "desc", // description, - "url", // descUrl, - Os.getCurrentOs(), // archiveOs, - Arch.getCurrentArch(), // archiveArch, - "foo" // archiveOsPath - ); - } - - /** - * Creates a {@link MockToolPackage} with the given revision and hardcoded defaults - * for everything else. - * <p/> - * By design, this creates a package with one and only one archive. - */ - public MockToolPackage( - SdkSource source, - FullRevision revision, - FullRevision minPlatformToolsRev) { - super( - source, // source, - createProps(revision, minPlatformToolsRev), // props, - revision.getMajor(), - null, // license, - "desc", // description, - "url", // descUrl, - Os.getCurrentOs(), // archiveOs, - Arch.getCurrentArch(), // archiveArch, - "foo" // archiveOsPath - ); - } - - private static Properties createProps(FullRevision revision, int minPlatformToolsRev) { - Properties props = FullRevisionPackageTest.createProps(revision); - props.setProperty(PkgProps.MIN_PLATFORM_TOOLS_REV, - Integer.toString((minPlatformToolsRev))); - return props; - } - - private static Properties createProps(FullRevision revision, FullRevision minPlatformToolsRev) { - Properties props = FullRevisionPackageTest.createProps(revision); - props.setProperty(PkgProps.MIN_PLATFORM_TOOLS_REV, - minPlatformToolsRev.toShortString()); - return props; - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/PackageTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/PackageTest.java deleted file mode 100755 index f4d7b56..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/PackageTest.java +++ /dev/null @@ -1,216 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.SdkManager; -import com.android.sdklib.internal.repository.archives.Archive; -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; -import com.android.sdklib.internal.repository.packages.BrokenPackage; -import com.android.sdklib.internal.repository.packages.Package; -import com.android.sdklib.internal.repository.sources.SdkRepoSource; -import com.android.sdklib.internal.repository.sources.SdkSource; -import com.android.sdklib.repository.PkgProps; - -import java.io.File; -import java.util.ArrayList; -import java.util.Arrays; -import java.util.Collections; -import java.util.Properties; - -import junit.framework.TestCase; - -public class PackageTest extends TestCase { - - protected static final String LOCAL_ARCHIVE_PATH = "/local/archive/path"; - - /** Local class used to test the abstract Package class */ - protected static class MockPackage extends MajorRevisionPackage { - public MockPackage( - SdkSource source, - Properties props, - int revision, - String license, - String description, - String descUrl, - Os archiveOs, - Arch archiveArch, - String archiveOsPath) { - super(source, - props, - revision, - license, - description, - descUrl, - archiveOs, - archiveArch, - archiveOsPath); - } - - @Override - public File getInstallFolder(String osSdkRoot, SdkManager sdkManager) { - throw new UnsupportedOperationException("abstract method not used in test"); //$NON-NLS-1$ - } - - @Override - public String getListDescription() { - throw new UnsupportedOperationException("abstract method not used in test"); //$NON-NLS-1$ - } - - @Override - public String getShortDescription() { - throw new UnsupportedOperationException("abstract method not used in test"); //$NON-NLS-1$ - } - - @Override - public boolean sameItemAs(Package pkg) { - throw new UnsupportedOperationException("abstract method not used in test"); //$NON-NLS-1$ - } - - @Override - public String installId() { - return "mock-pkg"; //$NON-NLS-1$ - } - } - - public void testCreate() throws Exception { - Properties props = createProps(); - - Package p = new MockPackage( - null, //source - props, - -1, //revision - null, //license - null, //description - null, //descUrl - Os.ANY, //archiveOs - Arch.ANY, //archiveArch - LOCAL_ARCHIVE_PATH //archiveOsPath - ); - - testCreatedPackage(p); - } - - public void testSaveProperties() throws Exception { - Properties props = createProps(); - - Package p = new MockPackage( - null, //source - props, - -1, //revision - null, //license - null, //description - null, //descUrl - Os.ANY, //archiveOs - Arch.ANY, //archiveArch - LOCAL_ARCHIVE_PATH //archiveOsPath - ); - - Properties props2 = new Properties(); - p.saveProperties(props2); - - assertEquals(props2, props); - } - - /** - * Sets the properties used by {@link #testCreate()} and - * {@link #testSaveProperties()}. - * This is protected and used by derived classes to perform - * a similar creation test. - */ - protected Properties createProps() { - Properties props = new Properties(); - - // Package properties - props.setProperty(PkgProps.PKG_REVISION, "42"); - props.setProperty(PkgProps.PKG_LICENSE, "The License"); - props.setProperty(PkgProps.PKG_DESC, "Some description."); - props.setProperty(PkgProps.PKG_DESC_URL, "http://description/url"); - props.setProperty(PkgProps.PKG_RELEASE_NOTE, "Release Note"); - props.setProperty(PkgProps.PKG_RELEASE_URL, "http://release/note"); - props.setProperty(PkgProps.PKG_SOURCE_URL, "http://source/url"); - props.setProperty(PkgProps.PKG_OBSOLETE, "true"); - return props; - } - - /** - * Tests the values set via {@link #createProps()} after the - * package has been created in {@link #testCreate()}. - * This is protected and used by derived classes to perform - * a similar creation test. - */ - protected void testCreatedPackage(Package p) { - // Package properties - assertEquals("42", p.getRevision().toShortString()); - assertEquals("The License", p.getLicense()); - assertEquals("Some description.", p.getDescription()); - assertEquals("http://description/url", p.getDescUrl()); - assertEquals("Release Note", p.getReleaseNote()); - assertEquals("http://release/note", p.getReleaseNoteUrl()); - assertEquals(new SdkRepoSource("http://source/url", null /*uiName*/), p.getParentSource()); - assertTrue(p.isObsolete()); - - assertNotNull(p.getArchives()); - assertEquals(1, p.getArchives().length); - Archive a = p.getArchives()[0]; - assertNotNull(a); - assertEquals(Os.ANY, a.getOs()); - assertEquals(Arch.ANY, a.getArch()); - assertEquals(LOCAL_ARCHIVE_PATH, a.getLocalOsPath()); - } - - // ---- - - public void testCompareTo() throws Exception { - ArrayList<Package> list = new ArrayList<Package>(); - MockPlatformPackage p1; - - list.add(p1 = new MockPlatformPackage(1, 2)); - list.add(new MockAddonPackage(p1, 3)); - list.add(new MockSystemImagePackage(p1, 4, "x86")); - list.add(new MockBrokenPackage(BrokenPackage.MIN_API_LEVEL_NOT_SPECIFIED, 1)); - list.add(new MockExtraPackage("vendor", "path", 5, 6)); - list.add(new MockToolPackage(7, 8)); - - Collections.sort(list); - - assertEquals( - "[Android SDK Tools, revision 7, " + - "SDK Platform Android android-1, API 1, revision 2, " + - "Intel x86 Atom System Image, Android API 1, revision 4, " + - "addon, Android API 1, revision 3, " + - "Broken package for API 1, " + - "Vendor Path, revision 5]", - Arrays.toString(list.toArray())); - } - - public void testGetPropertyInt() { - Properties p = new Properties(); - - assertEquals(42, Package.getPropertyInt(p, "key", 42)); - - p.setProperty("key", ""); - assertEquals(43, Package.getPropertyInt(p, "key", 43)); - - p.setProperty("key", "I am not a number"); - assertEquals(44, Package.getPropertyInt(p, "key", 44)); - - p.setProperty("key", "6"); - assertEquals(6, Package.getPropertyInt(p, "key", 45)); - } - -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/PlatformPackageTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/PlatformPackageTest.java deleted file mode 100755 index acb57ee..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/PlatformPackageTest.java +++ /dev/null @@ -1,110 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.IAndroidTarget; -import com.android.sdklib.internal.repository.MockPlatformTarget; -import com.android.sdklib.internal.repository.archives.Archive; -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; -import com.android.sdklib.internal.repository.packages.PlatformPackage; -import com.android.sdklib.repository.PkgProps; - -import java.util.Properties; - -public class PlatformPackageTest extends MinToolsPackageTest { - - /** - * PlatformPackage implicitly generates a local archive wrapper - * that matches the current platform OS and architecture. Since this - * is not convenient for testing, this class overrides it to always - * create archives for any OS and any architecture. - */ - private static class PlatformPackageWithFakeArchive extends PlatformPackage { - protected PlatformPackageWithFakeArchive(IAndroidTarget target, Properties props) { - super(target, props); - } - - @Override - protected Archive[] initializeArchives( - Properties props, - Os archiveOs, - Arch archiveArch, - String archiveOsPath) { - assert archiveOs == Os.getCurrentOs(); - assert archiveArch == Arch.getCurrentArch(); - return super.initializeArchives(props, Os.ANY, Arch.ANY, LOCAL_ARCHIVE_PATH); - } - } - - private PlatformPackage createPlatformPackage(Properties props) { - PlatformPackage p = new PlatformPackageWithFakeArchive( - new MockPlatformTarget(5 /*apiLevel*/, 1 /*revision*/), - props); - - return p; - } - - @Override - protected Properties createProps() { - Properties props = super.createProps(); - - // PlatformPackage properties - props.setProperty(PkgProps.VERSION_API_LEVEL, "5"); - props.setProperty(PkgProps.PLATFORM_VERSION, "android-5"); - props.setProperty(PkgProps.PLATFORM_INCLUDED_ABI, "armeabi"); - - return props; - } - - protected void testCreatedPlatformPackage(PlatformPackage p) { - super.testCreatedPackage(p); - - // Package properties - assertEquals("API 5", p.getAndroidVersion().toString()); - assertEquals("armeabi", p.getIncludedAbi()); - } - - // ---- - - @Override - public final void testCreate() { - Properties props = createProps(); - PlatformPackage p = createPlatformPackage(props); - - testCreatedPlatformPackage(p); - } - - @Override - public void testSaveProperties() { - Properties props = createProps(); - PlatformPackage p = createPlatformPackage(props); - - Properties props2 = new Properties(); - p.saveProperties(props2); - - assertEquals(props2.toString(), props.toString()); - assertEquals(props2, props); - } - - public void testInstallId() { - Properties props = createProps(); - PlatformPackage p = createPlatformPackage(props); - - assertEquals("android-5", p.installId()); - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/SourcePackageTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/SourcePackageTest.java deleted file mode 100755 index d87eab3..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/SourcePackageTest.java +++ /dev/null @@ -1,125 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.AndroidVersion; -import com.android.sdklib.AndroidVersion.AndroidVersionException; -import com.android.sdklib.internal.repository.archives.Archive; -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; -import com.android.sdklib.internal.repository.packages.SourcePackage; -import com.android.sdklib.repository.PkgProps; - -import java.util.Properties; - -public class SourcePackageTest extends PackageTest { - - /** - * SourcePackageTest implicitly generates a local archive wrapper - * that matches the current platform OS and architecture. Since this - * is not convenient for testing, this class overrides it to always - * create archives for any OS and any architecture. - */ - private static class SourcePackageFakeArchive extends SourcePackage { - protected SourcePackageFakeArchive( - AndroidVersion platformVersion, - int revision, - Properties props) { - super(platformVersion, - revision, - props, - String.format("/sdk/sources/android-%s", platformVersion.getApiString())); - } - - @Override - protected Archive[] initializeArchives( - Properties props, - Os archiveOs, - Arch archiveArch, - String archiveOsPath) { - assert archiveOs == Os.getCurrentOs(); - assert archiveArch == Arch.getCurrentArch(); - return super.initializeArchives(props, Os.ANY, Arch.ANY, LOCAL_ARCHIVE_PATH); - } - } - - private SourcePackage createSourcePackageTest(Properties props) throws AndroidVersionException { - SourcePackage p = new SourcePackageFakeArchive( - new AndroidVersion(props), - 1 /*revision*/, - props); - return p; - } - - @Override - protected Properties createProps() { - Properties props = super.createProps(); - - // SourcePackageTest properties - props.setProperty(PkgProps.VERSION_API_LEVEL, "5"); - - return props; - } - - protected void testCreatedSourcePackageTest(SourcePackage p) { - super.testCreatedPackage(p); - - // SourcePackageTest properties - assertEquals("API 5", p.getAndroidVersion().toString()); - } - - // ---- - - @Override - public final void testCreate() throws Exception { - Properties props = createProps(); - SourcePackage p = createSourcePackageTest(props); - - testCreatedSourcePackageTest(p); - } - - @Override - public void testSaveProperties() throws Exception { - Properties props = createProps(); - SourcePackage p = createSourcePackageTest(props); - - Properties props2 = new Properties(); - p.saveProperties(props2); - - assertEquals(props2, props); - } - - public void testSameItemAs() throws Exception { - Properties props1 = createProps(); - SourcePackage p1 = createSourcePackageTest(props1); - assertTrue(p1.sameItemAs(p1)); - - // different version - Properties props2 = new Properties(props1); - props2.setProperty(PkgProps.VERSION_API_LEVEL, "6"); - SourcePackage p2 = createSourcePackageTest(props2); - assertFalse(p1.sameItemAs(p2)); - assertFalse(p2.sameItemAs(p1)); - } - - public void testInstallId() throws Exception { - Properties props = createProps(); - SourcePackage p = createSourcePackageTest(props); - - assertEquals("source-5", p.installId()); - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/SystemImagePackageTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/SystemImagePackageTest.java deleted file mode 100755 index c32b81f..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/packages/SystemImagePackageTest.java +++ /dev/null @@ -1,145 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.internal.repository.packages; - -import com.android.sdklib.AndroidVersion; -import com.android.sdklib.AndroidVersion.AndroidVersionException; -import com.android.sdklib.internal.repository.archives.Archive; -import com.android.sdklib.internal.repository.archives.Archive.Arch; -import com.android.sdklib.internal.repository.archives.Archive.Os; -import com.android.sdklib.internal.repository.packages.SystemImagePackage; -import com.android.sdklib.repository.PkgProps; - -import java.util.Properties; - -public class SystemImagePackageTest extends PackageTest { - - /** - * SystemImagePackage implicitly generates a local archive wrapper - * that matches the current platform OS and architecture. Since this - * is not convenient for testing, this class overrides it to always - * create archives for any OS and any architecture. - */ - private static class SysImgPackageFakeArchive extends SystemImagePackage { - protected SysImgPackageFakeArchive( - AndroidVersion platformVersion, - int revision, - String abi, - Properties props) { - super(platformVersion, - revision, - abi, - props, - String.format("/sdk/system-images/android-%s/%s", - platformVersion.getApiString(), abi)); - } - - @Override - protected Archive[] initializeArchives( - Properties props, - Os archiveOs, - Arch archiveArch, - String archiveOsPath) { - assert archiveOs == Os.getCurrentOs(); - assert archiveArch == Arch.getCurrentArch(); - return super.initializeArchives(props, Os.ANY, Arch.ANY, LOCAL_ARCHIVE_PATH); - } - } - - private SystemImagePackage createSystemImagePackage(Properties props) - throws AndroidVersionException { - SystemImagePackage p = new SysImgPackageFakeArchive( - new AndroidVersion(props), - 1 /*revision*/, - null /*abi*/, - props); - return p; - } - - @Override - protected Properties createProps() { - Properties props = super.createProps(); - - // SystemImagePackage properties - props.setProperty(PkgProps.VERSION_API_LEVEL, "5"); - props.setProperty(PkgProps.SYS_IMG_ABI, "armeabi-v7a"); - - return props; - } - - protected void testCreatedSystemImagePackage(SystemImagePackage p) { - super.testCreatedPackage(p); - - // SystemImagePackage properties - assertEquals("API 5", p.getAndroidVersion().toString()); - assertEquals("armeabi-v7a", p.getAbi()); - } - - // ---- - - @Override - public final void testCreate() throws Exception { - Properties props = createProps(); - SystemImagePackage p = createSystemImagePackage(props); - - testCreatedSystemImagePackage(p); - } - - @Override - public void testSaveProperties() throws Exception { - Properties props = createProps(); - SystemImagePackage p = createSystemImagePackage(props); - - Properties props2 = new Properties(); - p.saveProperties(props2); - - assertEquals(props2, props); - } - - public void testSameItemAs() throws Exception { - Properties props1 = createProps(); - SystemImagePackage p1 = createSystemImagePackage(props1); - assertTrue(p1.sameItemAs(p1)); - - // different abi, same version - Properties props2 = new Properties(props1); - props2.setProperty(PkgProps.SYS_IMG_ABI, "x86"); - SystemImagePackage p2 = createSystemImagePackage(props2); - assertFalse(p1.sameItemAs(p2)); - assertFalse(p2.sameItemAs(p1)); - - // different abi, different version - props2.setProperty(PkgProps.VERSION_API_LEVEL, "6"); - p2 = createSystemImagePackage(props2); - assertFalse(p1.sameItemAs(p2)); - assertFalse(p2.sameItemAs(p1)); - - // same abi, different version - Properties props3 = new Properties(props1); - props3.setProperty(PkgProps.VERSION_API_LEVEL, "6"); - SystemImagePackage p3 = createSystemImagePackage(props3); - assertFalse(p1.sameItemAs(p3)); - assertFalse(p3.sameItemAs(p1)); - } - - public void testInstallId() throws Exception { - Properties props = createProps(); - SystemImagePackage p = createSystemImagePackage(props); - - assertEquals("sysimg-5", p.installId()); - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/sources/SdkAddonSourceTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/sources/SdkAddonSourceTest.java deleted file mode 100755 index 046cd1d..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/sources/SdkAddonSourceTest.java +++ /dev/null @@ -1,750 +0,0 @@ -/* - * Copyright (C) 2009 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.sdklib.internal.repository.sources; - -import com.android.sdklib.SdkManager; -import com.android.sdklib.internal.repository.ITaskMonitor; -import com.android.sdklib.internal.repository.MockEmptySdkManager; -import com.android.sdklib.internal.repository.MockMonitor; -import com.android.sdklib.internal.repository.packages.AddonPackage; -import com.android.sdklib.internal.repository.packages.ExtraPackage; -import com.android.sdklib.internal.repository.packages.IMinToolsDependency; -import com.android.sdklib.internal.repository.packages.Package; -import com.android.sdklib.internal.repository.sources.SdkAddonSource; -import com.android.sdklib.repository.SdkAddonConstants; -import com.android.utils.Pair; - -import org.w3c.dom.Document; - -import java.io.ByteArrayInputStream; -import java.io.File; -import java.io.FileInputStream; -import java.io.IOException; -import java.io.InputStream; -import java.util.ArrayList; -import java.util.Arrays; - -import junit.framework.TestCase; - -/** - * Tests for {@link SdkAddonSource}. - */ -public class SdkAddonSourceTest extends TestCase { - - /** - * An internal helper class to give us visibility to the protected members we want - * to test. - */ - private static class MockSdkAddonSource extends SdkAddonSource { - public MockSdkAddonSource() { - super("fake-url", null /*uiName*/); - } - - public Document _findAlternateToolsXml(InputStream xml) { - return super.findAlternateToolsXml(xml); - } - - public boolean _parsePackages(Document doc, String nsUri, ITaskMonitor monitor) { - return super.parsePackages(doc, nsUri, monitor); - } - - public int _getXmlSchemaVersion(InputStream xml) { - return super.getXmlSchemaVersion(xml); - } - - public String _validateXml(InputStream xml, String url, int version, - String[] outError, Boolean[] validatorFound) { - return super.validateXml(xml, url, version, outError, validatorFound); - } - - public Document _getDocument(InputStream xml, ITaskMonitor monitor) { - return super.getDocument(xml, monitor); - } - - } - - private MockSdkAddonSource mSource; - - @Override - protected void setUp() throws Exception { - super.setUp(); - - mSource = new MockSdkAddonSource(); - } - - @Override - protected void tearDown() throws Exception { - super.tearDown(); - - mSource = null; - } - - public void testFindAlternateToolsXml_Errors() throws Exception { - // Support null as input - Document result = mSource._findAlternateToolsXml(null); - assertNull(result); - - // Support an empty input - String str = ""; - ByteArrayInputStream input = new ByteArrayInputStream(str.getBytes()); - result = mSource._findAlternateToolsXml(input); - assertNull(result); - - // Support a random string as input - str = "Some random string, not even HTML nor XML"; - input = new ByteArrayInputStream(str.getBytes()); - result = mSource._findAlternateToolsXml(input); - assertNull(result); - - // Support an HTML input, e.g. a typical 404 document as returned by DL - str = "<html><head> " + - "<meta http-equiv=\"content-type\" content=\"text/html;charset=utf-8\"> " + - "<title>404 Not Found</title> " + "<style><!--" + "body {font-family: arial,sans-serif}" + - "div.nav { ... blah blah more css here ... color: green}" + - "//--></style> " + "<script><!--" + "var rc=404;" + "//-->" + "</script> " + "</head> " + - "<body text=#000000 bgcolor=#ffffff> " + - "<table border=0 cellpadding=2 cellspacing=0 width=100%><tr><td rowspan=3 width=1% nowrap> " + - "<b><font face=times color=#0039b6 size=10>G</font><font face=times color=#c41200 size=10>o</font><font face=times color=#f3c518 size=10>o</font><font face=times color=#0039b6 size=10>g</font><font face=times color=#30a72f size=10>l</font><font face=times color=#c41200 size=10>e</font> </b> " + - "<td> </td></tr> " + - "<tr><td bgcolor=\"#3366cc\"><font face=arial,sans-serif color=\"#ffffff\"><b>Error</b></td></tr> " + - "<tr><td> </td></tr></table> " + "<blockquote> " + "<H1>Not Found</H1> " + - "The requested URL <code>/404</code> was not found on this server." + " " + "<p> " + - "</blockquote> " + - "<table width=100% cellpadding=0 cellspacing=0><tr><td bgcolor=\"#3366cc\"><img alt=\"\" width=1 height=4></td></tr></table> " + - "</body></html> "; - input = new ByteArrayInputStream(str.getBytes()); - result = mSource._findAlternateToolsXml(input); - assertNull(result); - - // Support some random XML document, totally unrelated to our sdk-repository schema - str = "<?xml version=\"1.0\" encoding=\"utf-8\"?>" + - "<manifest xmlns:android=\"http://schemas.android.com/apk/res/android\"" + - " package=\"some.cool.app\" android:versionName=\"1.6.04\" android:versionCode=\"1604\">" + - " <application android:label=\"@string/app_name\" android:icon=\"@drawable/icon\"/>" + - "</manifest>"; - input = new ByteArrayInputStream(str.getBytes()); - result = mSource._findAlternateToolsXml(input); - assertNull(result); - } - - /** - * Validate that findAlternateToolsXml doesn't work for addon even - * when trying to load a valid addon xml. - */ - public void testFindAlternateToolsXml_1() throws Exception { - InputStream xmlStream = getTestResource("/com/android/sdklib/testdata/addon_sample_1.xml"); - - Document result = mSource._findAlternateToolsXml(xmlStream); - assertNull(result); - } - - /** - * Validate we can load a valid add-on schema version 1 - */ - public void testLoadAddonXml_1() throws Exception { - InputStream xmlStream = getTestResource("/com/android/sdklib/testdata/addon_sample_1.xml"); - - // guess the version from the XML document - int version = mSource._getXmlSchemaVersion(xmlStream); - assertEquals(1, version); - - Boolean[] validatorFound = new Boolean[] { Boolean.FALSE }; - String[] validationError = new String[] { null }; - String url = "not-a-valid-url://" + SdkAddonConstants.URL_DEFAULT_FILENAME; - - String uri = mSource._validateXml(xmlStream, url, version, validationError, validatorFound); - assertEquals(Boolean.TRUE, validatorFound[0]); - assertEquals(null, validationError[0]); - assertEquals(SdkAddonConstants.getSchemaUri(1), uri); - - // Validation was successful, load the document - MockMonitor monitor = new MockMonitor(); - Document doc = mSource._getDocument(xmlStream, monitor); - assertNotNull(doc); - - // Get the packages - assertTrue(mSource._parsePackages(doc, uri, monitor)); - - assertEquals("Found My First add-on, Android API 1, revision 1\n" + - "Found My Second add-on, Android API 2, revision 42\n" + - "Found This add-on has no libraries, Android API 4, revision 3\n" + - "Found G USB Driver, revision 43 (Obsolete)\n" + - "Found Android Vendor Extra API Dep, revision 2 (Obsolete)\n" + - "Found Unknown Extra, revision 2 (Obsolete)\n", - monitor.getCapturedVerboseLog()); - assertEquals("", monitor.getCapturedLog()); - assertEquals("", monitor.getCapturedErrorLog()); - - // check the packages we found... we expected to find 11 packages with each at least - // one archive. - Package[] pkgs = mSource.getPackages(); - assertEquals(6, pkgs.length); - for (Package p : pkgs) { - assertTrue(p.getArchives().length >= 1); - } - - // Check the extra packages path, vendor, install folder - - final String osSdkPath = "SDK"; - final SdkManager sdkManager = new MockEmptySdkManager(osSdkPath); - - ArrayList<String> extraPaths = new ArrayList<String>(); - ArrayList<String> extraVendors = new ArrayList<String>(); - ArrayList<File> extraInstall = new ArrayList<File>(); - for (Package p : pkgs) { - if (p instanceof ExtraPackage) { - ExtraPackage ep = (ExtraPackage) p; - extraPaths.add(ep.getPath()); - extraVendors.add(ep.getVendorId() + "/" + ep.getVendorDisplay()); - extraInstall.add(ep.getInstallFolder(osSdkPath, sdkManager)); - } - } - assertEquals( - "[extra_api_dep, usb_driver, extra0000005f]", - Arrays.toString(extraPaths.toArray())); - assertEquals( - "[android_vendor/android_vendor, " + - "g/g, " + - "vendor0000005f/____]", - Arrays.toString(extraVendors.toArray())); - assertEquals( - ("[SDK/extras/android_vendor/extra_api_dep, " + - "SDK/extras/g/usb_driver, " + - "SDK/extras/vendor0000005f/extra0000005f]").replace('/', File.separatorChar), - Arrays.toString(extraInstall.toArray())); - } - - /** - * Validate we can still load a valid add-on schema version 2 - */ - public void testLoadAddonXml_2() throws Exception { - InputStream xmlStream = getTestResource("/com/android/sdklib/testdata/addon_sample_2.xml"); - - // guess the version from the XML document - int version = mSource._getXmlSchemaVersion(xmlStream); - assertEquals(2, version); - - Boolean[] validatorFound = new Boolean[] { Boolean.FALSE }; - String[] validationError = new String[] { null }; - String url = "not-a-valid-url://" + SdkAddonConstants.URL_DEFAULT_FILENAME; - - String uri = mSource._validateXml(xmlStream, url, version, validationError, validatorFound); - assertEquals(Boolean.TRUE, validatorFound[0]); - assertEquals(null, validationError[0]); - assertEquals(SdkAddonConstants.getSchemaUri(2), uri); - - // Validation was successful, load the document - MockMonitor monitor = new MockMonitor(); - Document doc = mSource._getDocument(xmlStream, monitor); - assertNotNull(doc); - - // Get the packages - assertTrue(mSource._parsePackages(doc, uri, monitor)); - - assertEquals("Found My First add-on, Android API 1, revision 1\n" + - "Found My Second add-on, Android API 2, revision 42\n" + - "Found This add-on has no libraries, Android API 4, revision 3\n" + - "Found G USB Driver, revision 43 (Obsolete)\n" + - "Found Android Vendor Extra API Dep, revision 2 (Obsolete)\n" + - "Found Unknown Extra, revision 2 (Obsolete)\n", - monitor.getCapturedVerboseLog()); - assertEquals("", monitor.getCapturedLog()); - assertEquals("", monitor.getCapturedErrorLog()); - - // check the packages we found... we expected to find 11 packages with each at least - // one archive. - // Note the order doesn't necessary match the one from the - // assertEquald(getCapturedVerboseLog) because packages are sorted using the - // Packages' sorting order, e.g. all platforms are sorted by descending API level, etc. - Package[] pkgs = mSource.getPackages(); - - assertEquals(6, pkgs.length); - for (Package p : pkgs) { - assertTrue(p.getArchives().length >= 1); - } - - // Check the layoutlib of the platform packages. - ArrayList<Pair<Integer, Integer>> layoutlibVers = new ArrayList<Pair<Integer,Integer>>(); - for (Package p : pkgs) { - if (p instanceof AddonPackage) { - layoutlibVers.add(((AddonPackage) p).getLayoutlibVersion()); - } - } - assertEquals( - "[Pair [first=3, second=42], " + // for #3 "This add-on has no libraries" - "Pair [first=0, second=0], " + // for #2 "My Second add-on" - "Pair [first=5, second=0]]", // for #1 "My First add-on" - Arrays.toString(layoutlibVers.toArray())); - - - // Check the extra packages path, vendor, install folder - - final String osSdkPath = "SDK"; - final SdkManager sdkManager = new MockEmptySdkManager(osSdkPath); - - ArrayList<String> extraPaths = new ArrayList<String>(); - ArrayList<String> extraVendors = new ArrayList<String>(); - ArrayList<File> extraInstall = new ArrayList<File>(); - for (Package p : pkgs) { - if (p instanceof ExtraPackage) { - ExtraPackage ep = (ExtraPackage) p; - extraPaths.add(ep.getPath()); - extraVendors.add(ep.getVendorId() + "/" + ep.getVendorDisplay()); - extraInstall.add(ep.getInstallFolder(osSdkPath, sdkManager)); - } - } - assertEquals( - "[extra_api_dep, usb_driver, extra0000005f]", - Arrays.toString(extraPaths.toArray())); - assertEquals( - "[android_vendor/android_vendor, " + - "g/g, " + - "vendor0000005f/____]", - Arrays.toString(extraVendors.toArray())); - assertEquals( - ("[SDK/extras/android_vendor/extra_api_dep, " + - "SDK/extras/g/usb_driver, " + - "SDK/extras/vendor0000005f/extra0000005f]").replace('/', File.separatorChar), - Arrays.toString(extraInstall.toArray())); - } - - /** - * Validate we can load a valid add-on schema version 3 - */ - public void testLoadAddonXml_3() throws Exception { - InputStream xmlStream = getTestResource("/com/android/sdklib/testdata/addon_sample_3.xml"); - - // guess the version from the XML document - int version = mSource._getXmlSchemaVersion(xmlStream); - assertEquals(3, version); - - Boolean[] validatorFound = new Boolean[] { Boolean.FALSE }; - String[] validationError = new String[] { null }; - String url = "not-a-valid-url://" + SdkAddonConstants.URL_DEFAULT_FILENAME; - - String uri = mSource._validateXml(xmlStream, url, version, validationError, validatorFound); - assertEquals(Boolean.TRUE, validatorFound[0]); - assertEquals(null, validationError[0]); - assertEquals(SdkAddonConstants.getSchemaUri(3), uri); - - // Validation was successful, load the document - MockMonitor monitor = new MockMonitor(); - Document doc = mSource._getDocument(xmlStream, monitor); - assertNotNull(doc); - - // Get the packages - assertTrue(mSource._parsePackages(doc, uri, monitor)); - - assertEquals("Found My First add-on, Android API 1, revision 1\n" + - "Found My Second add-on, Android API 2, revision 42\n" + - "Found This add-on has no libraries, Android API 4, revision 3\n" + - "Found G USB Driver, revision 43 (Obsolete)\n" + - "Found Android Vendor Extra API Dep, revision 2 (Obsolete)\n" + - "Found Unknown Extra, revision 2 (Obsolete)\n", - monitor.getCapturedVerboseLog()); - assertEquals("", monitor.getCapturedLog()); - assertEquals("", monitor.getCapturedErrorLog()); - - // check the packages we found... we expected to find 6 packages with each at least - // one archive. - // Note the order doesn't necessary match the one from the - // assertEquald(getCapturedVerboseLog) because packages are sorted using the - // Packages' sorting order, e.g. all platforms are sorted by descending API level, etc. - Package[] pkgs = mSource.getPackages(); - - assertEquals(6, pkgs.length); - for (Package p : pkgs) { - assertTrue(p.getArchives().length >= 1); - } - - // Check the layoutlib of the platform packages. - ArrayList<Pair<Integer, Integer>> layoutlibVers = new ArrayList<Pair<Integer,Integer>>(); - for (Package p : pkgs) { - if (p instanceof AddonPackage) { - layoutlibVers.add(((AddonPackage) p).getLayoutlibVersion()); - } - } - assertEquals( - "[Pair [first=3, second=42], " + // for #3 "This add-on has no libraries" - "Pair [first=0, second=0], " + // for #2 "My Second add-on" - "Pair [first=5, second=0]]", // for #1 "My First add-on" - Arrays.toString(layoutlibVers.toArray())); - - - // Check the extra packages: path, vendor, install folder, old-paths - - final String osSdkPath = "SDK"; - final SdkManager sdkManager = new MockEmptySdkManager(osSdkPath); - - ArrayList<String> extraPaths = new ArrayList<String>(); - ArrayList<String> extraVendors = new ArrayList<String>(); - ArrayList<File> extraInstall = new ArrayList<File>(); - ArrayList<ArrayList<String>> extraFilePaths = new ArrayList<ArrayList<String>>(); - for (Package p : pkgs) { - if (p instanceof ExtraPackage) { - ExtraPackage ep = (ExtraPackage) p; - // combine path and old-paths in the form "path [old_path1, old_path2]" - extraPaths.add(ep.getPath() + " " + Arrays.toString(ep.getOldPaths())); - extraVendors.add(ep.getVendorId() + "/" + ep.getVendorDisplay()); - extraInstall.add(ep.getInstallFolder(osSdkPath, sdkManager)); - - ArrayList<String> filePaths = new ArrayList<String>(); - for (String filePath : ep.getProjectFiles()) { - filePaths.add(filePath); - } - extraFilePaths.add(filePaths); - } - } - assertEquals( - "[extra_api_dep [path1, old_path2, oldPath3], " + - "usb_driver [], " + - "extra0000005f []]", - Arrays.toString(extraPaths.toArray())); - assertEquals( - "[android_vendor/android_vendor, " + - "g/g, " + - "vendor0000005f/____]", - Arrays.toString(extraVendors.toArray())); - assertEquals( - ("[SDK/extras/android_vendor/extra_api_dep, " + - "SDK/extras/g/usb_driver, " + - "SDK/extras/vendor0000005f/extra0000005f]").replace('/', File.separatorChar), - Arrays.toString(extraInstall.toArray())); - assertEquals( - "[[v8/veggies_8.jar, root.jar, dir1/dir 2 with space/mylib.jar], " + - "[], " + - "[]]", - Arrays.toString(extraFilePaths.toArray())); - } - - /** - * Validate we can load a valid add-on schema version 4 - */ - public void testLoadAddonXml_4() throws Exception { - InputStream xmlStream = getTestResource("/com/android/sdklib/testdata/addon_sample_4.xml"); - - // guess the version from the XML document - int version = mSource._getXmlSchemaVersion(xmlStream); - assertEquals(4, version); - - Boolean[] validatorFound = new Boolean[] { Boolean.FALSE }; - String[] validationError = new String[] { null }; - String url = "not-a-valid-url://" + SdkAddonConstants.URL_DEFAULT_FILENAME; - - String uri = mSource._validateXml(xmlStream, url, version, validationError, validatorFound); - assertEquals(Boolean.TRUE, validatorFound[0]); - assertEquals(null, validationError[0]); - assertEquals(SdkAddonConstants.getSchemaUri(4), uri); - - // Validation was successful, load the document - MockMonitor monitor = new MockMonitor(); - Document doc = mSource._getDocument(xmlStream, monitor); - assertNotNull(doc); - - // Get the packages - assertTrue(mSource._parsePackages(doc, uri, monitor)); - - assertEquals("Found My First add-on, Android API 1, revision 1\n" + - "Found My Second add-on, Android API 2, revision 42\n" + - "Found This add-on has no libraries, Android API 4, revision 3\n" + - "Found Random name, not an id!, revision 43 (Obsolete)\n" + - "Found Yet another extra, by Android, revision 2\n" + - "Found . -..- - .-. .-, revision 2 (Obsolete)\n", - monitor.getCapturedVerboseLog()); - assertEquals("", monitor.getCapturedLog()); - assertEquals("", monitor.getCapturedErrorLog()); - - // check the packages we found... we expected to find 6 packages with each at least - // one archive. - // Note the order doesn't necessary match the one from the - // assertEquald(getCapturedVerboseLog) because packages are sorted using the - // Packages' sorting order, e.g. all platforms are sorted by descending API level, etc. - Package[] pkgs = mSource.getPackages(); - - assertEquals(6, pkgs.length); - for (Package p : pkgs) { - assertTrue(p.getArchives().length >= 1); - } - - // Check the addon packages: vendor/name id vs display - ArrayList<String> addonNames = new ArrayList<String>(); - ArrayList<String> addonVendors = new ArrayList<String>(); - for (Package p : pkgs) { - if (p instanceof AddonPackage) { - AddonPackage ap = (AddonPackage) p; - addonNames.add(ap.getNameId() + "/" + ap.getDisplayName()); - addonVendors.add(ap.getVendorId() + "/" + ap.getDisplayVendor()); - } - } - // Addons are sorted by addon/vendor id and thus their order differs from the - // XML or the parsed package list. - assertEquals( - "[no_libs/This add-on has no libraries, " + - "My_Second_add-on/My Second add-on, " + - "My_First_add-on/My First add-on]", - Arrays.toString(addonNames.toArray())); - assertEquals( - "[Joe_Bar/Joe Bar, " + - "John_Deer/John Deer, " + - "John_Doe/John Doe]", - Arrays.toString(addonVendors.toArray())); - - // Check the layoutlib of the platform packages. - ArrayList<Pair<Integer, Integer>> layoutlibVers = new ArrayList<Pair<Integer,Integer>>(); - for (Package p : pkgs) { - if (p instanceof AddonPackage) { - layoutlibVers.add(((AddonPackage) p).getLayoutlibVersion()); - } - } - assertEquals( - "[Pair [first=3, second=42], " + // for #3 "This add-on has no libraries" - "Pair [first=0, second=0], " + // for #2 "My Second add-on" - "Pair [first=5, second=0]]", // for #1 "My First add-on" - Arrays.toString(layoutlibVers.toArray())); - - - // Check the extra packages: path, vendor, install folder, old-paths - final String osSdkPath = "SDK"; - final SdkManager sdkManager = new MockEmptySdkManager(osSdkPath); - - ArrayList<String> extraPaths = new ArrayList<String>(); - ArrayList<String> extraVendors = new ArrayList<String>(); - ArrayList<File> extraInstall = new ArrayList<File>(); - ArrayList<ArrayList<String>> extraFilePaths = new ArrayList<ArrayList<String>>(); - for (Package p : pkgs) { - if (p instanceof ExtraPackage) { - ExtraPackage ep = (ExtraPackage) p; - // combine path and old-paths in the form "path [old_path1, old_path2]" - extraPaths.add(ep.getPath() + " " + Arrays.toString(ep.getOldPaths())); - extraVendors.add(ep.getVendorId() + "/" + ep.getVendorDisplay()); - extraInstall.add(ep.getInstallFolder(osSdkPath, sdkManager)); - - ArrayList<String> filePaths = new ArrayList<String>(); - for (String filePath : ep.getProjectFiles()) { - filePaths.add(filePath); - } - extraFilePaths.add(filePaths); - } - } - // Extras are sorted by vendor-id/path and thus their order differs from the - // XML or the parsed package list. - assertEquals( - "[extra0000005f [], " + // for extra #3 - "extra_api_dep [path1, old_path2, oldPath3], " + // for extra #2 - "usb_driver []]", // for extra #1 - Arrays.toString(extraPaths.toArray())); - assertEquals( - "[____/____, " + - "android_vendor/Android Vendor, " + - "cyclop/The big bus]", - Arrays.toString(extraVendors.toArray())); - assertEquals( - ("[SDK/extras/____/extra0000005f, " + - "SDK/extras/android_vendor/extra_api_dep, " + - "SDK/extras/cyclop/usb_driver]").replace('/', File.separatorChar), - Arrays.toString(extraInstall.toArray())); - assertEquals( - "[[], " + - "[v8/veggies_8.jar, root.jar, dir1/dir 2 with space/mylib.jar], " + - "[]]", - Arrays.toString(extraFilePaths.toArray())); - } - - /** - * Validate we can load a valid add-on schema version 5 - */ - public void testLoadAddonXml_5() throws Exception { - InputStream xmlStream = getTestResource("/com/android/sdklib/testdata/addon_sample_5.xml"); - - // guess the version from the XML document - int version = mSource._getXmlSchemaVersion(xmlStream); - assertEquals(5, version); - - Boolean[] validatorFound = new Boolean[] { Boolean.FALSE }; - String[] validationError = new String[] { null }; - String url = "not-a-valid-url://" + SdkAddonConstants.URL_DEFAULT_FILENAME; - - String uri = mSource._validateXml(xmlStream, url, version, validationError, validatorFound); - assertEquals(Boolean.TRUE, validatorFound[0]); - assertEquals(null, validationError[0]); - assertEquals(SdkAddonConstants.getSchemaUri(5), uri); - - // Validation was successful, load the document - MockMonitor monitor = new MockMonitor(); - Document doc = mSource._getDocument(xmlStream, monitor); - assertNotNull(doc); - - // Get the packages - assertTrue(mSource._parsePackages(doc, uri, monitor)); - - assertEquals("Found My First add-on, Android API 1, revision 1\n" + - "Found My Second add-on, Android API 2, revision 42\n" + - "Found This add-on has no libraries, Android API 4, revision 3\n" + - "Found Random name, not an id!, revision 43 (Obsolete)\n" + - "Found Yet another extra, by Android, revision 2\n" + - "Found . -..- - .-. .-, revision 2 (Obsolete)\n", - monitor.getCapturedVerboseLog()); - assertEquals("", monitor.getCapturedLog()); - assertEquals("", monitor.getCapturedErrorLog()); - - // check the packages we found... we expected to find 6 packages with each at least - // one archive. - // Note the order doesn't necessary match the one from the - // assertEquald(getCapturedVerboseLog) because packages are sorted using the - // Packages' sorting order, e.g. all platforms are sorted by descending API level, etc. - Package[] pkgs = mSource.getPackages(); - - assertEquals(6, pkgs.length); - for (Package p : pkgs) { - assertTrue(p.getArchives().length >= 1); - } - - // Check the addon packages: vendor/name id vs display - ArrayList<String> addonNames = new ArrayList<String>(); - ArrayList<String> addonVendors = new ArrayList<String>(); - for (Package p : pkgs) { - if (p instanceof AddonPackage) { - AddonPackage ap = (AddonPackage) p; - addonNames.add(ap.getNameId() + "/" + ap.getDisplayName()); - addonVendors.add(ap.getVendorId() + "/" + ap.getDisplayVendor()); - } - } - // Addons are sorted by addon/vendor id and thus their order differs from the - // XML or the parsed package list. - assertEquals( - "[no_libs/This add-on has no libraries, " + - "My_Second_add-on/My Second add-on, " + - "My_First_add-on/My First add-on]", - Arrays.toString(addonNames.toArray())); - assertEquals( - "[Joe_Bar/Joe Bar, " + - "John_Deer/John Deer, " + - "John_Doe/John Doe]", - Arrays.toString(addonVendors.toArray())); - - // Check the layoutlib of the platform packages. - ArrayList<Pair<Integer, Integer>> layoutlibVers = new ArrayList<Pair<Integer,Integer>>(); - for (Package p : pkgs) { - if (p instanceof AddonPackage) { - layoutlibVers.add(((AddonPackage) p).getLayoutlibVersion()); - } - } - assertEquals( - "[Pair [first=3, second=42], " + // for #3 "This add-on has no libraries" - "Pair [first=0, second=0], " + // for #2 "My Second add-on" - "Pair [first=5, second=0]]", // for #1 "My First add-on" - Arrays.toString(layoutlibVers.toArray())); - - - // Check the extra packages: path, vendor, install folder, old-paths - final String osSdkPath = "SDK"; - final SdkManager sdkManager = new MockEmptySdkManager(osSdkPath); - - ArrayList<String> extraPaths = new ArrayList<String>(); - ArrayList<String> extraVendors = new ArrayList<String>(); - ArrayList<File> extraInstall = new ArrayList<File>(); - ArrayList<ArrayList<String>> extraFilePaths = new ArrayList<ArrayList<String>>(); - for (Package p : pkgs) { - if (p instanceof ExtraPackage) { - ExtraPackage ep = (ExtraPackage) p; - // combine path and old-paths in the form "path [old_path1, old_path2]" - extraPaths.add(ep.getPath() + " " + Arrays.toString(ep.getOldPaths())); - extraVendors.add(ep.getVendorId() + "/" + ep.getVendorDisplay()); - extraInstall.add(ep.getInstallFolder(osSdkPath, sdkManager)); - - ArrayList<String> filePaths = new ArrayList<String>(); - for (String filePath : ep.getProjectFiles()) { - filePaths.add(filePath); - } - extraFilePaths.add(filePaths); - } - } - // Extras are sorted by vendor-id/path and thus their order differs from the - // XML or the parsed package list. - assertEquals( - "[extra0000005f [], " + // for extra #3 - "extra_api_dep [path1, old_path2, oldPath3], " + // for extra #2 - "usb_driver []]", // for extra #1 - Arrays.toString(extraPaths.toArray())); - assertEquals( - "[____/____, " + - "android_vendor/Android Vendor, " + - "cyclop/The big bus]", - Arrays.toString(extraVendors.toArray())); - assertEquals( - ("[SDK/extras/____/extra0000005f, " + - "SDK/extras/android_vendor/extra_api_dep, " + - "SDK/extras/cyclop/usb_driver]").replace('/', File.separatorChar), - Arrays.toString(extraInstall.toArray())); - assertEquals( - "[[], " + - "[v8/veggies_8.jar, root.jar, dir1/dir 2 with space/mylib.jar], " + - "[]]", - Arrays.toString(extraFilePaths.toArray())); - - - // Check the min-tools-rev - ArrayList<String> minToolsRevs = new ArrayList<String>(); - for (Package p : pkgs) { - if (p instanceof IMinToolsDependency) { - minToolsRevs.add(p.getListDescription() + ": " + - ((IMinToolsDependency) p).getMinToolsRevision().toShortString()); - } - } - assertEquals( - "[. -..- - .-. .- (Obsolete): 3.0.1, " + - "Yet another extra, by Android: 3, " + - "Random name, not an id! (Obsolete): 3.2.1 rc42]", - Arrays.toString(minToolsRevs.toArray())); - } - - /** - * Returns an SdkLib file resource as a {@link ByteArrayInputStream}, - * which has the advantage that we can use {@link InputStream#reset()} on it - * at any time to read it multiple times. - * <p/> - * The default for getResourceAsStream() is to return a {@link FileInputStream} that - * does not support reset(), yet we need it in the tested code. - * - * @throws IOException if some I/O read fails - */ - private ByteArrayInputStream getTestResource(String filename) throws IOException { - InputStream xmlStream = this.getClass().getResourceAsStream(filename); - - try { - byte[] data = new byte[8192]; - int offset = 0; - int n; - - while ((n = xmlStream.read(data, offset, data.length - offset)) != -1) { - offset += n; - - if (offset == data.length) { - byte[] newData = new byte[offset + 8192]; - System.arraycopy(data, 0, newData, 0, offset); - data = newData; - } - } - - return new ByteArrayInputStream(data, 0, offset); - } finally { - if (xmlStream != null) { - xmlStream.close(); - } - } - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/sources/SdkRepoSourceTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/sources/SdkRepoSourceTest.java deleted file mode 100755 index 9df0bfd..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/sources/SdkRepoSourceTest.java +++ /dev/null @@ -1,1063 +0,0 @@ -/* - * Copyright (C) 2009 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.sdklib.internal.repository.sources; - -import com.android.sdklib.SdkManager; -import com.android.sdklib.internal.repository.ITaskMonitor; -import com.android.sdklib.internal.repository.MockEmptySdkManager; -import com.android.sdklib.internal.repository.MockMonitor; -import com.android.sdklib.internal.repository.packages.ExtraPackage; -import com.android.sdklib.internal.repository.packages.IMinPlatformToolsDependency; -import com.android.sdklib.internal.repository.packages.IMinToolsDependency; -import com.android.sdklib.internal.repository.packages.Package; -import com.android.sdklib.internal.repository.packages.PlatformPackage; -import com.android.sdklib.internal.repository.packages.PlatformToolPackage; -import com.android.sdklib.internal.repository.packages.SourcePackage; -import com.android.sdklib.internal.repository.packages.SystemImagePackage; -import com.android.sdklib.internal.repository.packages.ToolPackage; -import com.android.sdklib.internal.repository.sources.SdkRepoSource; -import com.android.sdklib.repository.SdkRepoConstants; -import com.android.utils.Pair; - -import org.w3c.dom.Document; -import org.xml.sax.ErrorHandler; -import org.xml.sax.SAXException; -import org.xml.sax.SAXParseException; - -import java.io.ByteArrayInputStream; -import java.io.File; -import java.io.FileInputStream; -import java.io.IOException; -import java.io.InputStream; -import java.util.ArrayList; -import java.util.Arrays; - -import junit.framework.TestCase; - -/** - * Tests for {@link SdkRepoSource} - */ -public class SdkRepoSourceTest extends TestCase { - - /** - * An internal helper class to give us visibility to the protected members we want - * to test. - */ - private static class MockSdkRepoSource extends SdkRepoSource { - public MockSdkRepoSource() { - super("fake-url", null /*uiName*/); - } - - /** - * Returns a pair of Document (which can be null) and the captured stdout/stderr output - * (which is the empty string by default). - */ - public Pair<Document, String> _findAlternateToolsXml(InputStream xml) throws IOException { - - final StringBuilder output = new StringBuilder(); - Document doc = super.findAlternateToolsXml(xml, new ErrorHandler() { - @Override - public void warning(SAXParseException exception) throws SAXException { - output.append("WARN: " + exception.getMessage()).append('\n'); - } - - @Override - public void fatalError(SAXParseException exception) throws SAXException { - output.append("FATAL: " + exception.getMessage()).append('\n'); - } - - @Override - public void error(SAXParseException exception) throws SAXException { - output.append("ERROR: " + exception.getMessage()).append('\n'); - } - }); - - return Pair.of(doc, output.toString()); - } - - public boolean _parsePackages(Document doc, String nsUri, ITaskMonitor monitor) { - return super.parsePackages(doc, nsUri, monitor); - } - - public int _getXmlSchemaVersion(InputStream xml) { - return super.getXmlSchemaVersion(xml); - } - - public String _validateXml(InputStream xml, String url, int version, - String[] outError, Boolean[] validatorFound) { - return super.validateXml(xml, url, version, outError, validatorFound); - } - - public Document _getDocument(InputStream xml, ITaskMonitor monitor) { - return super.getDocument(xml, monitor); - } - - } - - private MockSdkRepoSource mSource; - - @Override - protected void setUp() throws Exception { - super.setUp(); - - mSource = new MockSdkRepoSource(); - } - - @Override - protected void tearDown() throws Exception { - super.tearDown(); - - mSource = null; - } - - public void testFindAlternateToolsXml_Errors() throws Exception { - // Support null as input - Pair<Document, String> result = mSource._findAlternateToolsXml(null); - assertEquals(Pair.of((Document) null, ""), result); - - // Support an empty input - String str = ""; - ByteArrayInputStream input = new ByteArrayInputStream(str.getBytes()); - result = mSource._findAlternateToolsXml(input); - assertEquals( - Pair.of((Document) null, "FATAL: Premature end of file.\n"), - result); - - // Support a random string as input - str = "Some random string, not even HTML nor XML"; - input = new ByteArrayInputStream(str.getBytes()); - result = mSource._findAlternateToolsXml(input); - assertEquals( - Pair.of((Document) null, "FATAL: Content is not allowed in prolog.\n"), - result); - - // Support an HTML input, e.g. a typical 404 document as returned by DL - str = "<html><head> " + - "<meta http-equiv=\"content-type\" content=\"text/html;charset=utf-8\"> " + - "<title>404 Not Found</title> " + "<style><!--" + "body {font-family: arial,sans-serif}" + - "div.nav { ... blah blah more css here ... color: green}" + - "//--></style> " + "<script><!--" + "var rc=404;" + "//-->" + "</script> " + "</head> " + - "<body text=#000000 bgcolor=#ffffff> " + - "<table border=0 cellpadding=2 cellspacing=0 width=100%><tr><td rowspan=3 width=1% nowrap> " + - "<b><font face=times color=#0039b6 size=10>G</font><font face=times color=#c41200 size=10>o</font><font face=times color=#f3c518 size=10>o</font><font face=times color=#0039b6 size=10>g</font><font face=times color=#30a72f size=10>l</font><font face=times color=#c41200 size=10>e</font> </b> " + - "<td> </td></tr> " + - "<tr><td bgcolor=\"#3366cc\"><font face=arial,sans-serif color=\"#ffffff\"><b>Error</b></td></tr> " + - "<tr><td> </td></tr></table> " + "<blockquote> " + "<H1>Not Found</H1> " + - "The requested URL <code>/404</code> was not found on this server." + " " + "<p> " + - "</blockquote> " + - "<table width=100% cellpadding=0 cellspacing=0><tr><td bgcolor=\"#3366cc\"><img alt=\"\" width=1 height=4></td></tr></table> " + - "</body></html> "; - input = new ByteArrayInputStream(str.getBytes()); - result = mSource._findAlternateToolsXml(input); - assertEquals( - Pair.of((Document) null, "FATAL: The element type \"meta\" must be terminated by the matching end-tag \"</meta>\".\n"), - result); - - // Support some random XML document, totally unrelated to our sdk-repository schema - str = "<?xml version=\"1.0\" encoding=\"utf-8\"?>" + - "<manifest xmlns:android=\"http://schemas.android.com/apk/res/android\"" + - " package=\"some.cool.app\" android:versionName=\"1.6.04\" android:versionCode=\"1604\">" + - " <application android:label=\"@string/app_name\" android:icon=\"@drawable/icon\"/>" + - "</manifest>"; - input = new ByteArrayInputStream(str.getBytes()); - result = mSource._findAlternateToolsXml(input); - assertEquals(Pair.of((Document) null, ""), result); - } - - /** - * Validate we can load a new schema version 3 using the "alternate future tool" mode. - */ - public void testFindAlternateToolsXml_3() throws Exception { - InputStream xmlStream = getTestResource( - "/com/android/sdklib/testdata/repository_sample_3.xml"); - - Pair<Document, String> result = mSource._findAlternateToolsXml(xmlStream); - assertNotNull(result.getFirst()); - assertEquals("", result.getSecond()); - MockMonitor monitor = new MockMonitor(); - assertTrue(mSource._parsePackages(result.getFirst(), SdkRepoConstants.NS_URI, monitor)); - - assertEquals("Found Android SDK Tools, revision 1\n" + - "Found Android SDK Tools, revision 42\n" + - "Found Android SDK Platform-tools, revision 3\n", - monitor.getCapturedVerboseLog()); - assertEquals("", monitor.getCapturedLog()); - assertEquals("", monitor.getCapturedErrorLog()); - - // check the packages we found... we expected to find 2 tool packages and 1 - // platform-tools package, with at least 1 archive each. - Package[] pkgs = mSource.getPackages(); - assertEquals(3, pkgs.length); - for (Package p : pkgs) { - assertTrue((p instanceof ToolPackage) || (p instanceof PlatformToolPackage)); - assertTrue(p.getArchives().length >= 1); - } - } - - /** - * Validate we can still load an old repository in schema version 1 - */ - public void testLoadXml_1() throws Exception { - InputStream xmlStream = getTestResource( - "/com/android/sdklib/testdata/repository_sample_1.xml"); - - // guess the version from the XML document - int version = mSource._getXmlSchemaVersion(xmlStream); - assertEquals(1, version); - - Boolean[] validatorFound = new Boolean[] { Boolean.FALSE }; - String[] validationError = new String[] { null }; - String url = "not-a-valid-url://" + SdkRepoConstants.URL_DEFAULT_FILENAME; - - String uri = mSource._validateXml(xmlStream, url, version, validationError, validatorFound); - assertEquals(Boolean.TRUE, validatorFound[0]); - assertEquals(null, validationError[0]); - assertEquals(SdkRepoConstants.getSchemaUri(1), uri); - - // Validation was successful, load the document - MockMonitor monitor = new MockMonitor(); - Document doc = mSource._getDocument(xmlStream, monitor); - assertNotNull(doc); - - // Get the packages - assertTrue(mSource._parsePackages(doc, uri, monitor)); - - assertEquals("Found SDK Platform Android 1.0, API 1, revision 3\n" + - "Found Documentation for Android SDK, API 1, revision 1\n" + - "Found My First add-on, Android API 1, revision 1\n" + - "Found SDK Platform Android 1.1, API 2, revision 12\n" + - "Found My Second add-on, Android API 2, revision 42\n" + - "Found SDK Platform Android Pastry Preview, revision 3\n" + - "Found Android SDK Tools, revision 1\n" + - "Found Documentation for Android SDK, API 2, revision 42\n" + - "Found Android SDK Tools, revision 42\n" + - "Found This add-on has no libraries, Android API 4, revision 3\n" + - "Found Usb Driver, revision 43\n", - monitor.getCapturedVerboseLog()); - assertEquals("", monitor.getCapturedLog()); - assertEquals("", monitor.getCapturedErrorLog()); - - // check the packages we found... we expected to find 11 packages with each at least - // one archive. - Package[] pkgs = mSource.getPackages(); - assertEquals(11, pkgs.length); - for (Package p : pkgs) { - assertTrue(p.getArchives().length >= 1); - } - - // Check the extra packages path, vendor, install folder - - final String osSdkPath = "SDK"; - final SdkManager sdkManager = new MockEmptySdkManager(osSdkPath); - - ArrayList<String> extraPaths = new ArrayList<String>(); - ArrayList<String> extraVendors = new ArrayList<String>(); - ArrayList<File> extraInstall = new ArrayList<File>(); - for (Package p : pkgs) { - if (p instanceof ExtraPackage) { - ExtraPackage ep = (ExtraPackage) p; - extraPaths.add(ep.getPath()); - extraVendors.add(ep.getVendorId() + "/" + ep.getVendorDisplay()); - extraInstall.add(ep.getInstallFolder(osSdkPath, sdkManager)); - } - } - assertEquals( - "[usb_driver]", - Arrays.toString(extraPaths.toArray())); - assertEquals( - "[/]", - Arrays.toString(extraVendors.toArray())); - assertEquals( - "[SDK/extras/usb_driver]".replace('/', File.separatorChar), - Arrays.toString(extraInstall.toArray())); - } - - /** - * Validate we can still load an old repository in schema version 2 - */ - public void testLoadXml_2() throws Exception { - InputStream xmlStream = getTestResource( - "/com/android/sdklib/testdata/repository_sample_2.xml"); - - // guess the version from the XML document - int version = mSource._getXmlSchemaVersion(xmlStream); - assertEquals(2, version); - - Boolean[] validatorFound = new Boolean[] { Boolean.FALSE }; - String[] validationError = new String[] { null }; - String url = "not-a-valid-url://" + SdkRepoConstants.URL_DEFAULT_FILENAME; - - String uri = mSource._validateXml(xmlStream, url, version, validationError, validatorFound); - assertEquals(Boolean.TRUE, validatorFound[0]); - assertEquals(null, validationError[0]); - assertEquals(SdkRepoConstants.getSchemaUri(2), uri); - - // Validation was successful, load the document - MockMonitor monitor = new MockMonitor(); - Document doc = mSource._getDocument(xmlStream, monitor); - assertNotNull(doc); - - // Get the packages - assertTrue(mSource._parsePackages(doc, uri, monitor)); - - assertEquals("Found SDK Platform Android 1.0, API 1, revision 3\n" + - "Found Documentation for Android SDK, API 1, revision 1\n" + - "Found My First add-on, Android API 1, revision 1\n" + - "Found SDK Platform Android 1.1, API 2, revision 12\n" + - "Found My Second add-on, Android API 2, revision 42\n" + - "Found SDK Platform Android Pastry Preview, revision 3\n" + - "Found Android SDK Tools, revision 1\n" + - "Found Documentation for Android SDK, API 2, revision 42\n" + - "Found Android SDK Tools, revision 42\n" + - "Found This add-on has no libraries, Android API 4, revision 3\n" + - "Found Usb Driver, revision 43 (Obsolete)\n" + - "Found Extra API Dep, revision 2 (Obsolete)\n" + - "Found Samples for SDK API 14, revision 24 (Obsolete)\n", - monitor.getCapturedVerboseLog()); - assertEquals("", monitor.getCapturedLog()); - assertEquals("", monitor.getCapturedErrorLog()); - - // check the packages we found... we expected to find 13 packages with each at least - // one archive. - Package[] pkgs = mSource.getPackages(); - assertEquals(13, pkgs.length); - for (Package p : pkgs) { - assertTrue(p.getArchives().length >= 1); - } - - // Check the extra packages path, vendor, install folder - - final String osSdkPath = "SDK"; - final SdkManager sdkManager = new MockEmptySdkManager(osSdkPath); - - ArrayList<String> extraPaths = new ArrayList<String>(); - ArrayList<String> extraVendors = new ArrayList<String>(); - ArrayList<File> extraInstall = new ArrayList<File>(); - for (Package p : pkgs) { - if (p instanceof ExtraPackage) { - ExtraPackage ep = (ExtraPackage) p; - extraPaths.add(ep.getPath()); - extraVendors.add(ep.getVendorId() + "/" + ep.getVendorDisplay()); - extraInstall.add(ep.getInstallFolder(osSdkPath, sdkManager)); - } - } - assertEquals( - "[extra_api_dep, usb_driver]", - Arrays.toString(extraPaths.toArray())); - assertEquals( - "[/, /]", - Arrays.toString(extraVendors.toArray())); - assertEquals( - "[SDK/extras/extra_api_dep, SDK/extras/usb_driver]".replace('/', File.separatorChar), - Arrays.toString(extraInstall.toArray())); - } - - /** - * Validate what we can load from repository in schema version 3 - */ - public void testLoadXml_3() throws Exception { - InputStream xmlStream = getTestResource( - "/com/android/sdklib/testdata/repository_sample_3.xml"); - - // guess the version from the XML document - int version = mSource._getXmlSchemaVersion(xmlStream); - assertEquals(3, version); - - Boolean[] validatorFound = new Boolean[] { Boolean.FALSE }; - String[] validationError = new String[] { null }; - String url = "not-a-valid-url://" + SdkRepoConstants.URL_DEFAULT_FILENAME; - - String uri = mSource._validateXml(xmlStream, url, version, validationError, validatorFound); - assertEquals(Boolean.TRUE, validatorFound[0]); - assertEquals(null, validationError[0]); - assertEquals(SdkRepoConstants.getSchemaUri(3), uri); - - // Validation was successful, load the document - MockMonitor monitor = new MockMonitor(); - Document doc = mSource._getDocument(xmlStream, monitor); - assertNotNull(doc); - - // Get the packages - assertTrue(mSource._parsePackages(doc, uri, monitor)); - - assertEquals("Found SDK Platform Android 1.0, API 1, revision 3\n" + - "Found Documentation for Android SDK, API 1, revision 1\n" + - "Found SDK Platform Android 1.1, API 2, revision 12\n" + - "Found SDK Platform Android Pastry Preview, revision 3\n" + - "Found Android SDK Tools, revision 1\n" + - "Found Documentation for Android SDK, API 2, revision 42\n" + - "Found Android SDK Tools, revision 42\n" + - "Found Android SDK Platform-tools, revision 3\n" + - "Found A USB Driver, revision 43 (Obsolete)\n" + - "Found Android Vendor Extra API Dep, revision 2 (Obsolete)\n" + - "Found Samples for SDK API 14, revision 24 (Obsolete)\n", - monitor.getCapturedVerboseLog()); - assertEquals("", monitor.getCapturedLog()); - assertEquals("", monitor.getCapturedErrorLog()); - - // check the packages we found... we expected to find 13 packages with each at least - // one archive. - Package[] pkgs = mSource.getPackages(); - assertEquals(11, pkgs.length); - for (Package p : pkgs) { - assertTrue(p.getArchives().length >= 1); - } - - // Check the extra packages path, vendor, install folder - - final String osSdkPath = "SDK"; - final SdkManager sdkManager = new MockEmptySdkManager(osSdkPath); - - ArrayList<String> extraPaths = new ArrayList<String>(); - ArrayList<String> extraVendors = new ArrayList<String>(); - ArrayList<File> extraInstall = new ArrayList<File>(); - for (Package p : pkgs) { - if (p instanceof ExtraPackage) { - ExtraPackage ep = (ExtraPackage) p; - extraPaths.add(ep.getPath()); - extraVendors.add(ep.getVendorId() + "/" + ep.getVendorDisplay()); - extraInstall.add(ep.getInstallFolder(osSdkPath, sdkManager)); - } - } - assertEquals( - "[extra_api_dep, usb_driver]", - Arrays.toString(extraPaths.toArray())); - assertEquals( - "[android_vendor/android_vendor, a/a]", - Arrays.toString(extraVendors.toArray())); - assertEquals( - "[SDK/extras/android_vendor/extra_api_dep, SDK/extras/a/usb_driver]" - .replace('/', File.separatorChar), - Arrays.toString(extraInstall.toArray())); - } - - /** - * Validate what we can load from repository in schema version 4 - */ - public void testLoadXml_4() throws Exception { - InputStream xmlStream = getTestResource( - "/com/android/sdklib/testdata/repository_sample_4.xml"); - - // guess the version from the XML document - int version = mSource._getXmlSchemaVersion(xmlStream); - assertEquals(4, version); - - Boolean[] validatorFound = new Boolean[] { Boolean.FALSE }; - String[] validationError = new String[] { null }; - String url = "not-a-valid-url://" + SdkRepoConstants.URL_DEFAULT_FILENAME; - - String uri = mSource._validateXml(xmlStream, url, version, validationError, validatorFound); - assertEquals(Boolean.TRUE, validatorFound[0]); - assertEquals(null, validationError[0]); - assertEquals(SdkRepoConstants.getSchemaUri(4), uri); - - // Validation was successful, load the document - MockMonitor monitor = new MockMonitor(); - Document doc = mSource._getDocument(xmlStream, monitor); - assertNotNull(doc); - - // Get the packages - assertTrue(mSource._parsePackages(doc, uri, monitor)); - - assertEquals("Found SDK Platform Android 1.0, API 1, revision 3\n" + - "Found Documentation for Android SDK, API 1, revision 1\n" + - "Found SDK Platform Android 1.1, API 2, revision 12\n" + - "Found SDK Platform Android Pastry Preview, revision 3\n" + - "Found Android SDK Tools, revision 1\n" + - "Found Documentation for Android SDK, API 2, revision 42\n" + - "Found Android SDK Tools, revision 42\n" + - "Found Android SDK Platform-tools, revision 3\n" + - "Found A USB Driver, revision 43 (Obsolete)\n" + - "Found Android Vendor Extra API Dep, revision 2 (Obsolete)\n" + - "Found Samples for SDK API 14, revision 24 (Obsolete)\n", - monitor.getCapturedVerboseLog()); - assertEquals("", monitor.getCapturedLog()); - assertEquals("", monitor.getCapturedErrorLog()); - - // check the packages we found... we expected to find 13 packages with each at least - // one archive. - // Note the order doesn't necessary match the one from the - // assertEquald(getCapturedVerboseLog) because packages are sorted using the - // Packages' sorting order, e.g. all platforms are sorted by descending API level, etc. - Package[] pkgs = mSource.getPackages(); - - assertEquals(11, pkgs.length); - for (Package p : pkgs) { - assertTrue(p.getArchives().length >= 1); - } - - // Check the layoutlib of the platform packages. - ArrayList<Pair<Integer, Integer>> layoutlibVers = new ArrayList<Pair<Integer,Integer>>(); - for (Package p : pkgs) { - if (p instanceof PlatformPackage) { - layoutlibVers.add(((PlatformPackage) p).getLayoutlibVersion()); - } - } - assertEquals( - "[Pair [first=1, second=0], " + // platform API 5 preview - "Pair [first=5, second=31415], " + // platform API 2 - "Pair [first=5, second=0]]", // platform API 1 - Arrays.toString(layoutlibVers.toArray())); - - // Check the extra packages path, vendor, install folder and project-files - - final String osSdkPath = "SDK"; - final SdkManager sdkManager = new MockEmptySdkManager(osSdkPath); - - ArrayList<String> extraPaths = new ArrayList<String>(); - ArrayList<String> extraVendors = new ArrayList<String>(); - ArrayList<File> extraInstall = new ArrayList<File>(); - ArrayList<ArrayList<String>> extraFilePaths = new ArrayList<ArrayList<String>>(); - for (Package p : pkgs) { - if (p instanceof ExtraPackage) { - ExtraPackage ep = (ExtraPackage) p; - extraPaths.add(ep.getPath()); - extraVendors.add(ep.getVendorId() + "/" + ep.getVendorDisplay()); - extraInstall.add(ep.getInstallFolder(osSdkPath, sdkManager)); - - ArrayList<String> filePaths = new ArrayList<String>(); - for (String filePath : ep.getProjectFiles()) { - filePaths.add(filePath); - } - extraFilePaths.add(filePaths); - } - } - assertEquals( - "[extra_api_dep, usb_driver]", - Arrays.toString(extraPaths.toArray())); - assertEquals( - "[android_vendor/android_vendor, a/a]", - Arrays.toString(extraVendors.toArray())); - assertEquals( - "[SDK/extras/android_vendor/extra_api_dep, SDK/extras/a/usb_driver]" - .replace('/', File.separatorChar), - Arrays.toString(extraInstall.toArray())); - assertEquals( - "[[v8/veggies_8.jar, readme.txt, dir1/dir 2 with space/mylib.jar], " + - "[]]", - Arrays.toString(extraFilePaths.toArray())); - } - - /** - * Validate what we can load from repository in schema version 5 - */ - public void testLoadXml_5() throws Exception { - InputStream xmlStream = getTestResource( - "/com/android/sdklib/testdata/repository_sample_5.xml"); - - // guess the version from the XML document - int version = mSource._getXmlSchemaVersion(xmlStream); - assertEquals(5, version); - - Boolean[] validatorFound = new Boolean[] { Boolean.FALSE }; - String[] validationError = new String[] { null }; - String url = "not-a-valid-url://" + SdkRepoConstants.URL_DEFAULT_FILENAME; - - String uri = mSource._validateXml(xmlStream, url, version, validationError, validatorFound); - assertEquals(Boolean.TRUE, validatorFound[0]); - assertEquals(null, validationError[0]); - assertEquals(SdkRepoConstants.getSchemaUri(5), uri); - - // Validation was successful, load the document - MockMonitor monitor = new MockMonitor(); - Document doc = mSource._getDocument(xmlStream, monitor); - assertNotNull(doc); - - // Get the packages - assertTrue(mSource._parsePackages(doc, uri, monitor)); - - assertEquals("Found SDK Platform Android 1.0, API 1, revision 3\n" + - "Found Documentation for Android SDK, API 1, revision 1\n" + - "Found Sources for Android SDK, API 1, revision 1\n" + - "Found SDK Platform Android 1.1, API 2, revision 12\n" + - "Found Intel x86 Atom System Image, Android API 2, revision 1\n" + - "Found ARM EABI v7a System Image, Android API 2, revision 2\n" + - "Found Sources for Android SDK, API 2, revision 2\n" + - "Found SDK Platform Android Pastry Preview, revision 3\n" + - "Found Android SDK Tools, revision 1\n" + - "Found Documentation for Android SDK, API 2, revision 42\n" + - "Found Android SDK Tools, revision 42\n" + - "Found Android SDK Platform-tools, revision 3\n" + - "Found A USB Driver, revision 43 (Obsolete)\n" + - "Found Android Vendor Extra API Dep, revision 2 (Obsolete)\n" + - "Found Samples for SDK API 14, revision 24 (Obsolete)\n" + - "Found ARM EABI System Image, Android API 42, revision 12\n" + - "Found Sources for Android SDK, API 42, revision 12\n", - monitor.getCapturedVerboseLog()); - assertEquals("", monitor.getCapturedLog()); - assertEquals("", monitor.getCapturedErrorLog()); - - // check the packages we found... we expected to find 13 packages with each at least - // one archive. - // Note the order doesn't necessary match the one from the - // assertEquald(getCapturedVerboseLog) because packages are sorted using the - // Packages' sorting order, e.g. all platforms are sorted by descending API level, etc. - Package[] pkgs = mSource.getPackages(); - - assertEquals(17, pkgs.length); - for (Package p : pkgs) { - assertTrue(p.getArchives().length >= 1); - } - - // Check the layoutlib & included-abi of the platform packages. - ArrayList<Pair<Integer, Integer>> layoutlibVers = new ArrayList<Pair<Integer,Integer>>(); - ArrayList<String> includedAbi = new ArrayList<String>(); - for (Package p : pkgs) { - if (p instanceof PlatformPackage) { - layoutlibVers.add(((PlatformPackage) p).getLayoutlibVersion()); - String abi = ((PlatformPackage) p).getIncludedAbi(); - includedAbi.add(abi == null ? "(null)" : abi); - } - } - assertEquals( - "[Pair [first=1, second=0], " + // platform API 5 preview - "Pair [first=5, second=31415], " + // platform API 2 - "Pair [first=5, second=0]]", // platform API 1 - Arrays.toString(layoutlibVers.toArray())); - assertEquals( - "[(null), " + // platform API 5 preview - "x86, " + // platform API 2 - "armeabi]", // platform API 1 - Arrays.toString(includedAbi.toArray())); - - // Check the extra packages path, vendor, install folder, project-files, old-paths - - final String osSdkPath = "SDK"; - final SdkManager sdkManager = new MockEmptySdkManager(osSdkPath); - - ArrayList<String> extraPaths = new ArrayList<String>(); - ArrayList<String> extraVendors = new ArrayList<String>(); - ArrayList<File> extraInstall = new ArrayList<File>(); - ArrayList<ArrayList<String>> extraFilePaths = new ArrayList<ArrayList<String>>(); - for (Package p : pkgs) { - if (p instanceof ExtraPackage) { - ExtraPackage ep = (ExtraPackage) p; - // combine path and old-paths in the form "path [old_path1, old_path2]" - extraPaths.add(ep.getPath() + " " + Arrays.toString(ep.getOldPaths())); - extraVendors.add(ep.getVendorId() + "/" + ep.getVendorDisplay()); - extraInstall.add(ep.getInstallFolder(osSdkPath, sdkManager)); - - ArrayList<String> filePaths = new ArrayList<String>(); - for (String filePath : ep.getProjectFiles()) { - filePaths.add(filePath); - } - extraFilePaths.add(filePaths); - } - } - assertEquals( - "[extra_api_dep [path1, old_path2, oldPath3], " + - "usb_driver []]", - Arrays.toString(extraPaths.toArray())); - assertEquals( - "[android_vendor/android_vendor, " + - "a/a]", - Arrays.toString(extraVendors.toArray())); - assertEquals( - ("[SDK/extras/android_vendor/extra_api_dep, " + - "SDK/extras/a/usb_driver]").replace('/', File.separatorChar), - Arrays.toString(extraInstall.toArray())); - assertEquals( - "[[v8/veggies_8.jar, readme.txt, dir1/dir 2 with space/mylib.jar], " + - "[]]", - Arrays.toString(extraFilePaths.toArray())); - - // Check the system-image packages - ArrayList<String> sysImgVersionAbi = new ArrayList<String>(); - for (Package p : pkgs) { - if (p instanceof SystemImagePackage) { - SystemImagePackage sip = (SystemImagePackage) p; - String v = sip.getAndroidVersion().getApiString(); - String a = sip.getAbi(); - sysImgVersionAbi.add(String.format("%1$s %2$s", v, a)); //$NON-NLS-1$ - } - } - assertEquals( - "[42 armeabi, " + - "2 armeabi-v7a, " + - "2 x86]", - Arrays.toString(sysImgVersionAbi.toArray())); - - // Check the source packages - ArrayList<String> sourceVersion = new ArrayList<String>(); - for (Package p : pkgs) { - if (p instanceof SourcePackage) { - SourcePackage sp = (SourcePackage) p; - String v = sp.getAndroidVersion().getApiString(); - sourceVersion.add(v); - } - } - assertEquals( - "[42, 2, 1]", - Arrays.toString(sourceVersion.toArray())); - } - - /** - * Validate what we can load from repository in schema version 6 - */ - public void testLoadXml_6() throws Exception { - InputStream xmlStream = getTestResource( - "/com/android/sdklib/testdata/repository_sample_6.xml"); - - // guess the version from the XML document - int version = mSource._getXmlSchemaVersion(xmlStream); - assertEquals(6, version); - - Boolean[] validatorFound = new Boolean[] { Boolean.FALSE }; - String[] validationError = new String[] { null }; - String url = "not-a-valid-url://" + SdkRepoConstants.URL_DEFAULT_FILENAME; - - String uri = mSource._validateXml(xmlStream, url, version, validationError, validatorFound); - assertEquals(Boolean.TRUE, validatorFound[0]); - assertEquals(null, validationError[0]); - assertEquals(SdkRepoConstants.getSchemaUri(6), uri); - - // Validation was successful, load the document - MockMonitor monitor = new MockMonitor(); - Document doc = mSource._getDocument(xmlStream, monitor); - assertNotNull(doc); - - // Get the packages - assertTrue(mSource._parsePackages(doc, uri, monitor)); - - assertEquals("Found SDK Platform Android 1.0, API 1, revision 3\n" + - "Found Documentation for Android SDK, API 1, revision 1\n" + - "Found Sources for Android SDK, API 1, revision 1\n" + - "Found SDK Platform Android 1.1, API 2, revision 12\n" + - "Found Intel x86 Atom System Image, Android API 2, revision 1\n" + - "Found ARM EABI v7a System Image, Android API 2, revision 2\n" + - "Found Sources for Android SDK, API 2, revision 2\n" + - "Found SDK Platform Android Pastry Preview, revision 3\n" + - "Found Android SDK Tools, revision 1\n" + - "Found Documentation for Android SDK, API 2, revision 42\n" + - "Found Android SDK Tools, revision 42\n" + - "Found Android SDK Platform-tools, revision 3\n" + - "Found Samples for SDK API 14, revision 24 (Obsolete)\n" + - "Found ARM EABI System Image, Android API 42, revision 12\n" + - "Found MIPS System Image, Android API 42, revision 12\n" + - "Found Sources for Android SDK, API 42, revision 12\n", - monitor.getCapturedVerboseLog()); - assertEquals("", monitor.getCapturedLog()); - assertEquals("", monitor.getCapturedErrorLog()); - - // check the packages we found... we expected to find 13 packages with each at least - // one archive. - // Note the order doesn't necessary match the one from the - // assertEquald(getCapturedVerboseLog) because packages are sorted using the - // Packages' sorting order, e.g. all platforms are sorted by descending API level, etc. - Package[] pkgs = mSource.getPackages(); - - assertEquals(16, pkgs.length); - for (Package p : pkgs) { - assertTrue(p.getArchives().length >= 1); - } - - // Check the layoutlib & included-abi of the platform packages. - ArrayList<Pair<Integer, Integer>> layoutlibVers = new ArrayList<Pair<Integer,Integer>>(); - ArrayList<String> includedAbi = new ArrayList<String>(); - for (Package p : pkgs) { - if (p instanceof PlatformPackage) { - layoutlibVers.add(((PlatformPackage) p).getLayoutlibVersion()); - String abi = ((PlatformPackage) p).getIncludedAbi(); - includedAbi.add(abi == null ? "(null)" : abi); - } - } - assertEquals( - "[Pair [first=1, second=0], " + // platform API 5 preview - "Pair [first=5, second=31415], " + // platform API 2 - "Pair [first=5, second=0]]", // platform API 1 - Arrays.toString(layoutlibVers.toArray())); - assertEquals( - "[(null), " + // platform API 5 preview - "x86, " + // platform API 2 - "armeabi]", // platform API 1 - Arrays.toString(includedAbi.toArray())); - - // Check the extra packages path, vendor, install folder, project-files, old-paths - - final String osSdkPath = "SDK"; - final SdkManager sdkManager = new MockEmptySdkManager(osSdkPath); - - ArrayList<String> extraPaths = new ArrayList<String>(); - ArrayList<String> extraVendors = new ArrayList<String>(); - ArrayList<File> extraInstall = new ArrayList<File>(); - ArrayList<ArrayList<String>> extraFilePaths = new ArrayList<ArrayList<String>>(); - for (Package p : pkgs) { - if (p instanceof ExtraPackage) { - ExtraPackage ep = (ExtraPackage) p; - // combine path and old-paths in the form "path [old_path1, old_path2]" - extraPaths.add(ep.getPath() + " " + Arrays.toString(ep.getOldPaths())); - extraVendors.add(ep.getVendorId() + "/" + ep.getVendorDisplay()); - extraInstall.add(ep.getInstallFolder(osSdkPath, sdkManager)); - - ArrayList<String> filePaths = new ArrayList<String>(); - for (String filePath : ep.getProjectFiles()) { - filePaths.add(filePath); - } - extraFilePaths.add(filePaths); - } - } - - // There are no extra packages anymore in repository-6 - assertEquals("[]", Arrays.toString(extraPaths.toArray())); - assertEquals("[]", Arrays.toString(extraVendors.toArray())); - assertEquals("[]", Arrays.toString(extraInstall.toArray())); - assertEquals("[]", Arrays.toString(extraFilePaths.toArray())); - - // Check the system-image packages - ArrayList<String> sysImgVersionAbi = new ArrayList<String>(); - for (Package p : pkgs) { - if (p instanceof SystemImagePackage) { - SystemImagePackage sip = (SystemImagePackage) p; - String v = sip.getAndroidVersion().getApiString(); - String a = sip.getAbi(); - sysImgVersionAbi.add(String.format("%1$s %2$s", v, a)); //$NON-NLS-1$ - } - } - assertEquals( - "[42 armeabi, " + - "42 mips, " + - "2 armeabi-v7a, " + - "2 x86]", - Arrays.toString(sysImgVersionAbi.toArray())); - - // Check the source packages - ArrayList<String> sourceVersion = new ArrayList<String>(); - for (Package p : pkgs) { - if (p instanceof SourcePackage) { - SourcePackage sp = (SourcePackage) p; - String v = sp.getAndroidVersion().getApiString(); - sourceVersion.add(v); - } - } - assertEquals( - "[42, 2, 1]", - Arrays.toString(sourceVersion.toArray())); - } - - /** - * Validate what we can load from repository in schema version 6 - */ - public void testLoadXml_7() throws Exception { - InputStream xmlStream = getTestResource( - "/com/android/sdklib/testdata/repository_sample_7.xml"); - - // guess the version from the XML document - int version = mSource._getXmlSchemaVersion(xmlStream); - assertEquals(7, version); - - Boolean[] validatorFound = new Boolean[] { Boolean.FALSE }; - String[] validationError = new String[] { null }; - String url = "not-a-valid-url://" + SdkRepoConstants.URL_DEFAULT_FILENAME; - - String uri = mSource._validateXml(xmlStream, url, version, validationError, validatorFound); - assertEquals(Boolean.TRUE, validatorFound[0]); - assertEquals(null, validationError[0]); - assertEquals(SdkRepoConstants.getSchemaUri(7), uri); - - // Validation was successful, load the document - MockMonitor monitor = new MockMonitor(); - Document doc = mSource._getDocument(xmlStream, monitor); - assertNotNull(doc); - - // Get the packages - assertTrue(mSource._parsePackages(doc, uri, monitor)); - - assertEquals("Found SDK Platform Android 1.0, API 1, revision 3\n" + - "Found Documentation for Android SDK, API 1, revision 1\n" + - "Found Sources for Android SDK, API 1, revision 1\n" + - "Found SDK Platform Android 1.1, API 2, revision 12\n" + - "Found Intel x86 Atom System Image, Android API 2, revision 1\n" + - "Found ARM EABI v7a System Image, Android API 2, revision 2\n" + - "Found Sources for Android SDK, API 2, revision 2\n" + - "Found SDK Platform Android Pastry Preview, revision 3\n" + - "Found Android SDK Tools, revision 1.2.3 rc4\n" + - "Found Documentation for Android SDK, API 2, revision 42\n" + - "Found Android SDK Tools, revision 42\n" + - "Found Android SDK Platform-tools, revision 3 rc5\n" + - "Found Samples for SDK API 14, revision 24 (Obsolete)\n" + - "Found Samples for SDK API 14, revision 25 (Obsolete)\n" + - "Found ARM EABI System Image, Android API 42, revision 12\n" + - "Found MIPS System Image, Android API 42, revision 12\n" + - "Found Sources for Android SDK, API 42, revision 12\n", - monitor.getCapturedVerboseLog()); - assertEquals("", monitor.getCapturedLog()); - assertEquals("", monitor.getCapturedErrorLog()); - - // check the packages we found... we expected to find 13 packages with each at least - // one archive. - // Note the order doesn't necessary match the one from the - // assertEquald(getCapturedVerboseLog) because packages are sorted using the - // Packages' sorting order, e.g. all platforms are sorted by descending API level, etc. - Package[] pkgs = mSource.getPackages(); - - assertEquals(17, pkgs.length); - for (Package p : pkgs) { - assertTrue(p.getArchives().length >= 1); - } - - // Check the layoutlib & included-abi of the platform packages. - ArrayList<Pair<Integer, Integer>> layoutlibVers = new ArrayList<Pair<Integer,Integer>>(); - ArrayList<String> includedAbi = new ArrayList<String>(); - for (Package p : pkgs) { - if (p instanceof PlatformPackage) { - layoutlibVers.add(((PlatformPackage) p).getLayoutlibVersion()); - String abi = ((PlatformPackage) p).getIncludedAbi(); - includedAbi.add(abi == null ? "(null)" : abi); - } - } - assertEquals( - "[Pair [first=1, second=0], " + // platform API 5 preview - "Pair [first=5, second=31415], " + // platform API 2 - "Pair [first=5, second=0]]", // platform API 1 - Arrays.toString(layoutlibVers.toArray())); - assertEquals( - "[(null), " + // platform API 5 preview - "x86, " + // platform API 2 - "armeabi]", // platform API 1 - Arrays.toString(includedAbi.toArray())); - - // Check the extra packages path, vendor, install folder, project-files, old-paths - - final String osSdkPath = "SDK"; - final SdkManager sdkManager = new MockEmptySdkManager(osSdkPath); - - ArrayList<String> extraPaths = new ArrayList<String>(); - ArrayList<String> extraVendors = new ArrayList<String>(); - ArrayList<File> extraInstall = new ArrayList<File>(); - ArrayList<ArrayList<String>> extraFilePaths = new ArrayList<ArrayList<String>>(); - for (Package p : pkgs) { - if (p instanceof ExtraPackage) { - ExtraPackage ep = (ExtraPackage) p; - // combine path and old-paths in the form "path [old_path1, old_path2]" - extraPaths.add(ep.getPath() + " " + Arrays.toString(ep.getOldPaths())); - extraVendors.add(ep.getVendorId() + "/" + ep.getVendorDisplay()); - extraInstall.add(ep.getInstallFolder(osSdkPath, sdkManager)); - - ArrayList<String> filePaths = new ArrayList<String>(); - for (String filePath : ep.getProjectFiles()) { - filePaths.add(filePath); - } - extraFilePaths.add(filePaths); - } - } - - // There are no extra packages anymore in repository-6 - assertEquals("[]", Arrays.toString(extraPaths.toArray())); - assertEquals("[]", Arrays.toString(extraVendors.toArray())); - assertEquals("[]", Arrays.toString(extraInstall.toArray())); - assertEquals("[]", Arrays.toString(extraFilePaths.toArray())); - - - // Check the system-image packages - ArrayList<String> sysImgVersionAbi = new ArrayList<String>(); - for (Package p : pkgs) { - if (p instanceof SystemImagePackage) { - SystemImagePackage sip = (SystemImagePackage) p; - String v = sip.getAndroidVersion().getApiString(); - String a = sip.getAbi(); - sysImgVersionAbi.add(String.format("%1$s %2$s", v, a)); //$NON-NLS-1$ - } - } - assertEquals( - "[42 armeabi, " + - "42 mips, " + - "2 armeabi-v7a, " + - "2 x86]", - Arrays.toString(sysImgVersionAbi.toArray())); - - - // Check the source packages - ArrayList<String> sourceVersion = new ArrayList<String>(); - for (Package p : pkgs) { - if (p instanceof SourcePackage) { - SourcePackage sp = (SourcePackage) p; - String v = sp.getAndroidVersion().getApiString(); - sourceVersion.add(v); - } - } - assertEquals( - "[42, 2, 1]", - Arrays.toString(sourceVersion.toArray())); - - - // Check the min-tools-rev - ArrayList<String> minToolsRevs = new ArrayList<String>(); - for (Package p : pkgs) { - if (p instanceof IMinToolsDependency) { - minToolsRevs.add(p.getListDescription() + ": " + - ((IMinToolsDependency) p).getMinToolsRevision().toShortString()); - } - } - assertEquals( - "[SDK Platform Android Pastry Preview: 0, " + - "SDK Platform Android 1.1: 0, " + - "SDK Platform Android 1.0: 2.0.1, " + - "Samples for SDK API 14 (Obsolete): 5, " + - "Samples for SDK API 14 (Obsolete): 5.1.2 rc3]", - Arrays.toString(minToolsRevs.toArray())); - - - // Check the min-platform-tools-rev - ArrayList<String> minPlatToolsRevs = new ArrayList<String>(); - for (Package p : pkgs) { - if (p instanceof IMinPlatformToolsDependency) { - minPlatToolsRevs.add(p.getListDescription() + ": " + - ((IMinPlatformToolsDependency) p).getMinPlatformToolsRevision().toShortString()); - } - } - assertEquals( - "[Android SDK Tools: 4, " + - "Android SDK Tools: 4 rc5]", - Arrays.toString(minPlatToolsRevs.toArray())); - } - - /** - * Returns an SdkLib file resource as a {@link ByteArrayInputStream}, - * which has the advantage that we can use {@link InputStream#reset()} on it - * at any time to read it multiple times. - * <p/> - * The default for getResourceAsStream() is to return a {@link FileInputStream} that - * does not support reset(), yet we need it in the tested code. - * - * @throws IOException if some I/O read fails - */ - private ByteArrayInputStream getTestResource(String filename) throws IOException { - InputStream xmlStream = this.getClass().getResourceAsStream(filename); - - try { - byte[] data = new byte[8192]; - int offset = 0; - int n; - - while ((n = xmlStream.read(data, offset, data.length - offset)) != -1) { - offset += n; - - if (offset == data.length) { - byte[] newData = new byte[offset + 8192]; - System.arraycopy(data, 0, newData, 0, offset); - data = newData; - } - } - - return new ByteArrayInputStream(data, 0, offset); - } finally { - if (xmlStream != null) { - xmlStream.close(); - } - } - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/sources/SdkSourcePropertiesTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/sources/SdkSourcePropertiesTest.java deleted file mode 100755 index 6313e69..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/sources/SdkSourcePropertiesTest.java +++ /dev/null @@ -1,140 +0,0 @@ -/* - * Copyright (C) 2012 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.sdklib.internal.repository.sources; - - -import com.android.sdklib.internal.repository.sources.SdkSourceProperties; - -import junit.framework.TestCase; - -public class SdkSourcePropertiesTest extends TestCase { - - private static class MockSdkSourceProperties extends SdkSourceProperties { - private int mLoadCount; - private int mSaveCount; - - public MockSdkSourceProperties() { - clear(); - } - - public int getLoadCount() { - return mLoadCount; - } - - public int getSaveCount() { - return mSaveCount; - } - - @Override - protected boolean loadProperties() { - // Don't actually load anthing. - mLoadCount++; - return false; - } - - @Override - protected void saveLocked() { - // Don't actually save anything. - mSaveCount++; - } - } - - @Override - protected void setUp() throws Exception { - super.setUp(); - } - - public final void testSdkSourceProperties() { - MockSdkSourceProperties m = new MockSdkSourceProperties(); - - assertEquals(0, m.getLoadCount()); - assertEquals(0, m.getSaveCount()); - assertEquals( - "<SdkSourceProperties>", - m.toString()); - - assertNull(m.getProperty(SdkSourceProperties.KEY_DISABLED, "http://example.com/1", null)); - assertEquals("None", - m.getProperty(SdkSourceProperties.KEY_NAME, "http://example.com/2", "None")); - assertEquals(1, m.getLoadCount()); - assertEquals(0, m.getSaveCount()); - assertEquals( - "<SdkSourceProperties\n" + - "@version@ = 1>", - m.toString()); - - m.setProperty(SdkSourceProperties.KEY_DISABLED, "http://example.com/1", "disabled"); - assertEquals("disabled", - m.getProperty(SdkSourceProperties.KEY_DISABLED, "http://example.com/1", "None")); - assertNull(m.getProperty(SdkSourceProperties.KEY_NAME, "http://example.com/1", null)); - assertEquals( - "<SdkSourceProperties\n" + - "@disabled@http://example.com/1 = disabled\n" + - "@version@ = 1>", - m.toString()); - - m.setProperty(SdkSourceProperties.KEY_NAME, "http://example.com/2", "Site Name"); - assertEquals("Site Name", - m.getProperty(SdkSourceProperties.KEY_NAME, "http://example.com/2", null)); - assertNull(m.getProperty(SdkSourceProperties.KEY_DISABLED, "http://example.com/2", null)); - assertEquals(1, m.getLoadCount()); - assertEquals(0, m.getSaveCount()); - assertEquals( - "<SdkSourceProperties\n" + - "@disabled@http://example.com/1 = disabled\n" + - "@name@http://example.com/2 = Site Name\n" + - "@version@ = 1>", - m.toString()); - - m.save(); - assertEquals(1, m.getSaveCount()); - - // saving a 2nd time doesn't do anything if no property has been modified - m.save(); - assertEquals(1, m.getSaveCount()); - - // setting things to the same value doesn't actually mark the properties as modified - m.setProperty(SdkSourceProperties.KEY_DISABLED, "http://example.com/1", "disabled"); - m.setProperty(SdkSourceProperties.KEY_NAME, "http://example.com/2", "Site Name"); - m.save(); - assertEquals(1, m.getSaveCount()); - - m.setProperty(SdkSourceProperties.KEY_DISABLED, "http://example.com/1", "not disabled"); - m.setProperty(SdkSourceProperties.KEY_NAME, "http://example.com/2", "New Name"); - assertEquals( - "<SdkSourceProperties\n" + - "@disabled@http://example.com/1 = not disabled\n" + - "@name@http://example.com/2 = New Name\n" + - "@version@ = 1>", - m.toString()); - m.save(); - assertEquals(2, m.getSaveCount()); - - // setting a value to null deletes it - m.setProperty(SdkSourceProperties.KEY_NAME, "http://example.com/2", null); - assertEquals( - "<SdkSourceProperties\n" + - "@disabled@http://example.com/1 = not disabled\n" + - "@version@ = 1>", - m.toString()); - - m.save(); - assertEquals(1, m.getLoadCount()); - assertEquals(3, m.getSaveCount()); - } - -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/sources/SdkSysImgSourceTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/sources/SdkSysImgSourceTest.java deleted file mode 100755 index c080d11..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/internal/repository/sources/SdkSysImgSourceTest.java +++ /dev/null @@ -1,211 +0,0 @@ -/* - * Copyright (C) 2012 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.sdklib.internal.repository.sources; - -import com.android.sdklib.internal.repository.ITaskMonitor; -import com.android.sdklib.internal.repository.MockMonitor; -import com.android.sdklib.internal.repository.packages.Package; -import com.android.sdklib.internal.repository.packages.SystemImagePackage; -import com.android.sdklib.repository.SdkSysImgConstants; - -import org.w3c.dom.Document; - -import java.io.ByteArrayInputStream; -import java.io.FileInputStream; -import java.io.IOException; -import java.io.InputStream; -import java.util.ArrayList; -import java.util.Arrays; - -import junit.framework.TestCase; - -/** - * Tests for {@link SdkSysImgSource}. - */ -public class SdkSysImgSourceTest extends TestCase { - - /** - * An internal helper class to give us visibility to the protected members we want - * to test. - */ - private static class MockSdkSysImgSource extends SdkSysImgSource { - public MockSdkSysImgSource() { - super("fake-url", null /*uiName*/); - } - - public Document _findAlternateToolsXml(InputStream xml) { - return super.findAlternateToolsXml(xml); - } - - public boolean _parsePackages(Document doc, String nsUri, ITaskMonitor monitor) { - return super.parsePackages(doc, nsUri, monitor); - } - - public int _getXmlSchemaVersion(InputStream xml) { - return super.getXmlSchemaVersion(xml); - } - - public String _validateXml(InputStream xml, String url, int version, - String[] outError, Boolean[] validatorFound) { - return super.validateXml(xml, url, version, outError, validatorFound); - } - - public Document _getDocument(InputStream xml, ITaskMonitor monitor) { - return super.getDocument(xml, monitor); - } - - } - - private MockSdkSysImgSource mSource; - - @Override - protected void setUp() throws Exception { - super.setUp(); - - mSource = new MockSdkSysImgSource(); - } - - @Override - protected void tearDown() throws Exception { - super.tearDown(); - - mSource = null; - } - - /** - * Validate that findAlternateToolsXml doesn't work for this source even - * when trying to load a valid xml. That's because finding alternate tools - * is not supported by this kind of source. - */ - public void testFindAlternateToolsXml_1() throws Exception { - InputStream xmlStream = - getTestResource("/com/android/sdklib/testdata/sys_img_sample_1.xml"); - - Document result = mSource._findAlternateToolsXml(xmlStream); - assertNull(result); - } - - /** - * Validate we can load a valid schema version 1 - */ - public void testLoadSysImgXml_1() throws Exception { - InputStream xmlStream = - getTestResource("/com/android/sdklib/testdata/sys_img_sample_1.xml"); - - // guess the version from the XML document - int version = mSource._getXmlSchemaVersion(xmlStream); - assertEquals(1, version); - - Boolean[] validatorFound = new Boolean[] { Boolean.FALSE }; - String[] validationError = new String[] { null }; - String url = "not-a-valid-url://" + SdkSysImgConstants.URL_DEFAULT_FILENAME; - - String uri = mSource._validateXml(xmlStream, url, version, validationError, validatorFound); - assertEquals(Boolean.TRUE, validatorFound[0]); - assertEquals(null, validationError[0]); - assertEquals(SdkSysImgConstants.getSchemaUri(1), uri); - - // Validation was successful, load the document - MockMonitor monitor = new MockMonitor(); - Document doc = mSource._getDocument(xmlStream, monitor); - assertNotNull(doc); - - // Get the packages - assertTrue(mSource._parsePackages(doc, uri, monitor)); - - assertEquals( - "Found Intel x86 Atom System Image, Android API 2, revision 1\n" + - "Found ARM EABI v7a System Image, Android API 2, revision 2\n" + - "Found ARM EABI System Image, Android API 42, revision 12\n" + - "Found MIPS System Image, Android API 42, revision 12\n", - monitor.getCapturedVerboseLog()); - assertEquals("", monitor.getCapturedLog()); - assertEquals("", monitor.getCapturedErrorLog()); - - // check the packages we found... - // Note the order doesn't necessary match the one from the - // assertEquald(getCapturedVerboseLog) because packages are sorted using the - // Packages' sorting order, e.g. all platforms are sorted by descending API level, etc. - - Package[] pkgs = mSource.getPackages(); - - assertEquals(4, pkgs.length); - for (Package p : pkgs) { - // We expected to find packages with each at least one archive. - assertTrue(p.getArchives().length >= 1); - // And only system images are supported by this source - assertTrue(p instanceof SystemImagePackage); - } - - // Check the system-image packages - ArrayList<String> sysImgVersionAbi = new ArrayList<String>(); - for (Package p : pkgs) { - if (p instanceof SystemImagePackage) { - SystemImagePackage sip = (SystemImagePackage) p; - String v = sip.getAndroidVersion().getApiString(); - String a = sip.getAbi(); - sysImgVersionAbi.add(String.format("%1$s %2$s", v, a)); //$NON-NLS-1$ - } - } - assertEquals( - "[42 armeabi, " + - "42 mips, " + - "2 armeabi-v7a, " + - "2 x86]", - Arrays.toString(sysImgVersionAbi.toArray())); - - } - - - //----- - - /** - * Returns an SdkLib file resource as a {@link ByteArrayInputStream}, - * which has the advantage that we can use {@link InputStream#reset()} on it - * at any time to read it multiple times. - * <p/> - * The default for getResourceAsStream() is to return a {@link FileInputStream} that - * does not support reset(), yet we need it in the tested code. - * - * @throws IOException if some I/O read fails - */ - private ByteArrayInputStream getTestResource(String filename) throws IOException { - InputStream xmlStream = this.getClass().getResourceAsStream(filename); - - try { - byte[] data = new byte[8192]; - int offset = 0; - int n; - - while ((n = xmlStream.read(data, offset, data.length - offset)) != -1) { - offset += n; - - if (offset == data.length) { - byte[] newData = new byte[offset + 8192]; - System.arraycopy(data, 0, newData, 0, offset); - data = newData; - } - } - - return new ByteArrayInputStream(data, 0, offset); - } finally { - if (xmlStream != null) { - xmlStream.close(); - } - } - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/io/MockFileOp.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/io/MockFileOp.java deleted file mode 100755 index cbe5fdd..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/io/MockFileOp.java +++ /dev/null @@ -1,469 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.io; - -import com.android.SdkConstants; -import com.android.annotations.NonNull; - -import java.io.ByteArrayOutputStream; -import java.io.File; -import java.io.FileInputStream; -import java.io.FileNotFoundException; -import java.io.IOException; -import java.io.OutputStream; -import java.util.ArrayList; -import java.util.HashSet; -import java.util.Iterator; -import java.util.List; -import java.util.Properties; -import java.util.Set; -import java.util.TreeSet; -import java.util.regex.Matcher; -import java.util.regex.Pattern; - - -/** - * Mock version of {@link FileOp} that wraps some common {@link File} - * operations on files and folders. - * <p/> - * This version does not perform any file operation. Instead it records a textual - * representation of all the file operations performed. - * <p/> - * To avoid cross-platform path issues (e.g. Windows path), the methods here should - * always use rooted (aka absolute) unix-looking paths, e.g. "/dir1/dir2/file3". - * When processing {@link File}, you can convert them using {@link #getAgnosticAbsPath(File)}. - */ -public class MockFileOp implements IFileOp { - - private final Set<String> mExistinfFiles = new TreeSet<String>(); - private final Set<String> mExistinfFolders = new TreeSet<String>(); - private final List<StringOutputStream> mOutputStreams = new ArrayList<StringOutputStream>(); - - public MockFileOp() { - } - - /** Resets the internal state, as if the object had been newly created. */ - public void reset() { - mExistinfFiles.clear(); - mExistinfFolders.clear(); - } - - public String getAgnosticAbsPath(File file) { - return getAgnosticAbsPath(file.getAbsolutePath()); - } - - public String getAgnosticAbsPath(String path) { - if (SdkConstants.CURRENT_PLATFORM == SdkConstants.PLATFORM_WINDOWS) { - // Try to convert the windows-looking path to a unix-looking one - path = path.replace('\\', '/'); - path = path.replace("C:", ""); //$NON-NLS-1$ //$NON-NLS-2$ - } - return path; - } - - /** - * Records a new absolute file path. - * Parent folders are not automatically created. - */ - public void recordExistingFile(File file) { - mExistinfFiles.add(getAgnosticAbsPath(file)); - } - - /** - * Records a new absolute file path. - * Parent folders are not automatically created. - * <p/> - * The syntax should always look "unix-like", e.g. "/dir/file". - * On Windows that means you'll want to use {@link #getAgnosticAbsPath(File)}. - * @param absFilePath A unix-like file path, e.g. "/dir/file" - */ - public void recordExistingFile(String absFilePath) { - mExistinfFiles.add(absFilePath); - } - - /** - * Records a new absolute folder path. - * Parent folders are not automatically created. - */ - public void recordExistingFolder(File folder) { - mExistinfFolders.add(getAgnosticAbsPath(folder)); - } - - /** - * Records a new absolute folder path. - * Parent folders are not automatically created. - * <p/> - * The syntax should always look "unix-like", e.g. "/dir/file". - * On Windows that means you'll want to use {@link #getAgnosticAbsPath(File)}. - * @param absFolderPath A unix-like folder path, e.g. "/dir/file" - */ - public void recordExistingFolder(String absFolderPath) { - mExistinfFolders.add(absFolderPath); - } - - /** - * Returns the list of paths added using {@link #recordExistingFile(String)} - * and eventually updated by {@link #delete(File)} operations. - * <p/> - * The returned list is sorted by alphabetic absolute path string. - */ - public String[] getExistingFiles() { - return mExistinfFiles.toArray(new String[mExistinfFiles.size()]); - } - - /** - * Returns the list of folder paths added using {@link #recordExistingFolder(String)} - * and eventually updated {@link #delete(File)} or {@link #mkdirs(File)} operations. - * <p/> - * The returned list is sorted by alphabetic absolute path string. - */ - public String[] getExistingFolders() { - return mExistinfFolders.toArray(new String[mExistinfFolders.size()]); - } - - /** - * Returns the {@link StringOutputStream#toString()} as an array, in creation order. - * Array can be empty but not null. - */ - public String[] getOutputStreams() { - int n = mOutputStreams.size(); - String[] result = new String[n]; - for (int i = 0; i < n; i++) { - result[i] = mOutputStreams.get(i).toString(); - } - return result; - } - - /** - * Helper to delete a file or a directory. - * For a directory, recursively deletes all of its content. - * Files that cannot be deleted right away are marked for deletion on exit. - * The argument can be null. - */ - @Override - public void deleteFileOrFolder(File fileOrFolder) { - if (fileOrFolder != null) { - if (isDirectory(fileOrFolder)) { - // Must delete content recursively first - for (File item : listFiles(fileOrFolder)) { - deleteFileOrFolder(item); - } - } - delete(fileOrFolder); - } - } - - /** - * {@inheritDoc} - * <p/> - * <em>Note: this mock version does nothing.</em> - */ - @Override - public void setExecutablePermission(File file) throws IOException { - // pass - } - - /** - * {@inheritDoc} - * <p/> - * <em>Note: this mock version does nothing.</em> - */ - @Override - public void setReadOnly(File file) { - // pass - } - - /** - * {@inheritDoc} - * <p/> - * <em>Note: this mock version does nothing.</em> - */ - @Override - public void copyFile(File source, File dest) throws IOException { - // pass - } - - /** - * Checks whether 2 binary files are the same. - * - * @param source the source file to copy - * @param destination the destination file to write - * @throws FileNotFoundException if the source files don't exist. - * @throws IOException if there's a problem reading the files. - */ - @Override - public boolean isSameFile(File source, File destination) throws IOException { - throw new UnsupportedOperationException("MockFileUtils.isSameFile is not supported."); //$NON-NLS-1$ - } - - /** Invokes {@link File#isFile()} on the given {@code file}. */ - @Override - public boolean isFile(File file) { - String path = getAgnosticAbsPath(file); - return mExistinfFiles.contains(path); - } - - /** Invokes {@link File#isDirectory()} on the given {@code file}. */ - @Override - public boolean isDirectory(File file) { - String path = getAgnosticAbsPath(file); - if (mExistinfFolders.contains(path)) { - return true; - } - - // If we defined a file or folder as a child of the requested file path, - // then the directory exists implicitely. - Pattern pathRE = Pattern.compile( - Pattern.quote(path + (path.endsWith("/") ? "" : '/')) + //$NON-NLS-1$ //$NON-NLS-2$ - ".*"); //$NON-NLS-1$ - - for (String folder : mExistinfFolders) { - if (pathRE.matcher(folder).matches()) { - return true; - } - } - for (String filePath : mExistinfFiles) { - if (pathRE.matcher(filePath).matches()) { - return true; - } - } - - return false; - } - - /** Invokes {@link File#exists()} on the given {@code file}. */ - @Override - public boolean exists(File file) { - return isFile(file) || isDirectory(file); - } - - /** Invokes {@link File#length()} on the given {@code file}. */ - @Override - public long length(File file) { - throw new UnsupportedOperationException("MockFileUtils.length is not supported."); //$NON-NLS-1$ - } - - @Override - public boolean delete(File file) { - String path = getAgnosticAbsPath(file); - - if (mExistinfFiles.remove(path)) { - return true; - } - - boolean hasSubfiles = false; - for (String folder : mExistinfFolders) { - if (folder.startsWith(path) && !folder.equals(path)) { - // the File.delete operation is not recursive and would fail to remove - // a root dir that is not empty. - return false; - } - } - if (!hasSubfiles) { - for (String filePath : mExistinfFiles) { - if (filePath.startsWith(path) && !filePath.equals(path)) { - // the File.delete operation is not recursive and would fail to remove - // a root dir that is not empty. - return false; - } - } - } - - return mExistinfFolders.remove(path); - } - - /** Invokes {@link File#mkdirs()} on the given {@code file}. */ - @Override - public boolean mkdirs(File file) { - for (; file != null; file = file.getParentFile()) { - String path = getAgnosticAbsPath(file); - mExistinfFolders.add(path); - } - return true; - } - - /** - * Invokes {@link File#listFiles()} on the given {@code file}. - * The returned list is sorted by alphabetic absolute path string. - */ - @Override - public File[] listFiles(File file) { - TreeSet<File> files = new TreeSet<File>(); - - String path = getAgnosticAbsPath(file); - Pattern pathRE = Pattern.compile( - Pattern.quote(path + (path.endsWith("/") ? "" : '/')) + //$NON-NLS-1$ //$NON-NLS-2$ - ".*"); //$NON-NLS-1$ - - for (String folder : mExistinfFolders) { - if (pathRE.matcher(folder).matches()) { - files.add(new File(folder)); - } - } - for (String filePath : mExistinfFiles) { - if (pathRE.matcher(filePath).matches()) { - files.add(new File(filePath)); - } - } - return files.toArray(new File[files.size()]); - } - - /** Invokes {@link File#renameTo(File)} on the given files. */ - @Override - public boolean renameTo(File oldFile, File newFile) { - boolean renamed = false; - - String oldPath = getAgnosticAbsPath(oldFile); - String newPath = getAgnosticAbsPath(newFile); - Pattern pathRE = Pattern.compile( - "^(" + Pattern.quote(oldPath) + //$NON-NLS-1$ - ")($|/.*)"); //$NON-NLS-1$ - - Set<String> newStrings = new HashSet<String>(); - for (Iterator<String> it = mExistinfFolders.iterator(); it.hasNext(); ) { - String folder = it.next(); - Matcher m = pathRE.matcher(folder); - if (m.matches()) { - it.remove(); - String newFolder = newPath + m.group(2); - newStrings.add(newFolder); - renamed = true; - } - } - mExistinfFolders.addAll(newStrings); - newStrings.clear(); - - for (Iterator<String> it = mExistinfFiles.iterator(); it.hasNext(); ) { - String filePath = it.next(); - Matcher m = pathRE.matcher(filePath); - if (m.matches()) { - it.remove(); - String newFilePath = newPath + m.group(2); - newStrings.add(newFilePath); - renamed = true; - } - } - mExistinfFiles.addAll(newStrings); - - return renamed; - } - - /** - * {@inheritDoc} - * <p/> - * <em>TODO: we might want to overload this to read mock properties instead of a real file.</em> - */ - @Override - public @NonNull Properties loadProperties(@NonNull File file) { - Properties props = new Properties(); - FileInputStream fis = null; - try { - fis = new FileInputStream(file); - props.load(fis); - } catch (IOException ignore) { - } finally { - if (fis != null) { - try { - fis.close(); - } catch (Exception ignore) {} - } - } - return props; - } - - /** - * {@inheritDoc} - * <p/> - * <em>Note that this uses the mock version of {@link #newFileOutputStream(File)} and thus - * records the write rather than actually performing it.</em> - */ - @Override - public boolean saveProperties(@NonNull File file, @NonNull Properties props, - @NonNull String comments) { - OutputStream fos = null; - try { - fos = newFileOutputStream(file); - - props.store(fos, comments); - return true; - } catch (IOException ignore) { - } finally { - if (fos != null) { - try { - fos.close(); - } catch (IOException e) { - } - } - } - - return false; - } - - /** - * Returns an OutputStream that will capture the bytes written and associate - * them with the given file. - */ - @Override - public OutputStream newFileOutputStream(File file) throws FileNotFoundException { - StringOutputStream os = new StringOutputStream(file); - mOutputStreams.add(os); - return os; - } - - /** - * An {@link OutputStream} that will capture the stream as an UTF-8 string once properly closed - * and associate it to the given {@link File}. - */ - public class StringOutputStream extends ByteArrayOutputStream { - private String mData; - private final File mFile; - - public StringOutputStream(File file) { - mFile = file; - recordExistingFile(file); - } - - public File getFile() { - return mFile; - } - - /** Can be null if the stream has never been properly closed. */ - public String getData() { - return mData; - } - - /** Once the stream is properly closed, convert the byte array to an UTF-8 string */ - @Override - public void close() throws IOException { - super.close(); - mData = new String(toByteArray(), "UTF-8"); //$NON-NLS-1$ - } - - /** Returns a string representation suitable for unit tests validation. */ - @Override - public synchronized String toString() { - StringBuilder sb = new StringBuilder(); - sb.append('<').append(getAgnosticAbsPath(mFile)).append(": "); //$NON-NLS-1$ - if (mData == null) { - sb.append("(stream not closed properly)>"); //$NON-NLS-1$ - } else { - sb.append('\'').append(mData).append("'>"); //$NON-NLS-1$ - } - return sb.toString(); - } - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/io/MockFileOpTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/io/MockFileOpTest.java deleted file mode 100755 index 8fb1784..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/io/MockFileOpTest.java +++ /dev/null @@ -1,191 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.io; - -import java.io.File; -import java.io.OutputStream; -import java.util.Arrays; - -import junit.framework.TestCase; - -/** - * Unit-test for the {@link MockFileOp}, which is a mock of {@link FileOp} that doesn't - * touch the file system. Just testing the test. - */ -public class MockFileOpTest extends TestCase { - - private MockFileOp m; - - @Override - protected void setUp() throws Exception { - super.setUp(); - m = new MockFileOp(); - } - - private File createFile(String...segments) { - File f = null; - for (String segment : segments) { - if (f == null) { - f = new File(segment); - } else { - f = new File(f, segment); - } - } - - return f; - } - - public void testIsFile() { - File f1 = createFile("/dir1", "file1"); - assertFalse(m.isFile(f1)); - - m.recordExistingFile("/dir1/file1"); - assertTrue(m.isFile(f1)); - - assertEquals( - "[/dir1/file1]", - Arrays.toString(m.getExistingFiles())); - } - - public void testIsDirectory() { - File d4 = createFile("/dir1", "dir2", "dir3", "dir4"); - File f7 = createFile("/dir1", "dir2", "dir6", "file7"); - assertFalse(m.isDirectory(d4)); - - m.recordExistingFolder("/dir1/dir2/dir3/dir4"); - m.recordExistingFile("/dir1/dir2/dir6/file7"); - assertTrue(m.isDirectory(d4)); - assertFalse(m.isDirectory(f7)); - - // any intermediate directory exists implicitly - assertTrue(m.isDirectory(createFile("/"))); - assertTrue(m.isDirectory(createFile("/dir1"))); - assertTrue(m.isDirectory(createFile("/dir1", "dir2"))); - assertTrue(m.isDirectory(createFile("/dir1", "dir2", "dir3"))); - assertTrue(m.isDirectory(createFile("/dir1", "dir2", "dir6"))); - - assertEquals( - "[/dir1/dir2/dir3/dir4]", - Arrays.toString(m.getExistingFolders())); - } - - public void testDelete() { - m.recordExistingFolder("/dir1"); - m.recordExistingFile("/dir1/file1"); - m.recordExistingFile("/dir1/file2"); - - assertEquals( - "[/dir1/file1, /dir1/file2]", - Arrays.toString(m.getExistingFiles())); - - assertTrue(m.delete(createFile("/dir1", "file1"))); - assertFalse(m.delete(createFile("/dir1", "file3"))); - assertFalse(m.delete(createFile("/dir2", "file2"))); - assertEquals( - "[/dir1/file2]", - Arrays.toString(m.getExistingFiles())); - - // deleting a directory with files in it fails - assertFalse(m.delete(createFile("/dir1"))); - // but it works if the directory is empty - assertTrue(m.delete(createFile("/dir1", "file2"))); - assertTrue(m.delete(createFile("/dir1"))); - } - - public void testListFiles() { - m.recordExistingFolder("/dir1"); - m.recordExistingFile("/dir1/file1"); - m.recordExistingFile("/dir1/file2"); - m.recordExistingFile("/dir1/dir2/file3"); - m.recordExistingFile("/dir4/file4"); - - assertEquals( - "[]", - m.getAgnosticAbsPath(Arrays.toString(m.listFiles(createFile("/not_a_dir"))))); - - assertEquals( - "[/dir1/dir2/file3]", - m.getAgnosticAbsPath(Arrays.toString(m.listFiles(createFile("/dir1", "dir2"))))); - - assertEquals( - "[/dir1/dir2/file3, /dir1/file1, /dir1/file2]", - m.getAgnosticAbsPath(Arrays.toString(m.listFiles(createFile("/dir1"))))); - } - - public void testMkDirs() { - assertEquals("[]", Arrays.toString(m.getExistingFolders())); - - assertTrue(m.mkdirs(createFile("/dir1"))); - assertEquals("[/, /dir1]", Arrays.toString(m.getExistingFolders())); - - m.recordExistingFolder("/dir1"); - assertEquals("[/, /dir1]", Arrays.toString(m.getExistingFolders())); - - assertTrue(m.mkdirs(createFile("/dir1/dir2/dir3"))); - assertEquals( - "[/, /dir1, /dir1/dir2, /dir1/dir2/dir3]", - Arrays.toString(m.getExistingFolders())); - } - - public void testRenameTo() { - m.recordExistingFile("/dir1/dir2/dir6/file7"); - m.recordExistingFolder("/dir1/dir2/dir3/dir4"); - - assertEquals("[/dir1/dir2/dir6/file7]", Arrays.toString(m.getExistingFiles())); - assertEquals("[/dir1/dir2/dir3/dir4]", Arrays.toString(m.getExistingFolders())); - - assertTrue(m.renameTo(createFile("/dir1", "dir2"), createFile("/dir1", "newDir2"))); - assertEquals("[/dir1/newDir2/dir6/file7]", Arrays.toString(m.getExistingFiles())); - assertEquals("[/dir1/newDir2/dir3/dir4]", Arrays.toString(m.getExistingFolders())); - - assertTrue(m.renameTo( - createFile("/dir1", "newDir2", "dir6", "file7"), - createFile("/dir1", "newDir2", "dir6", "newFile7"))); - assertTrue(m.renameTo( - createFile("/dir1", "newDir2", "dir3", "dir4"), - createFile("/dir1", "newDir2", "dir3", "newDir4"))); - assertEquals("[/dir1/newDir2/dir6/newFile7]", Arrays.toString(m.getExistingFiles())); - assertEquals("[/dir1/newDir2/dir3/newDir4]", Arrays.toString(m.getExistingFolders())); - } - - public void testNewFileOutputStream() throws Exception { - assertEquals("[]", Arrays.toString(m.getOutputStreams())); - - File f = createFile("/dir1", "dir2", "simple ascii"); - OutputStream os = m.newFileOutputStream(f); - assertNotNull(os); - os.write("regular ascii".getBytes("UTF-8")); - os.close(); - - f = createFile("/dir1", "dir2", "utf-8 test"); - os = m.newFileOutputStream(f); - assertNotNull(os); - os.write("nihongo in UTF-8: 日本語".getBytes("UTF-8")); - os.close(); - - f = createFile("/dir1", "dir2", "forgot to close"); - os = m.newFileOutputStream(f); - assertNotNull(os); - os.write("wrote stuff but not closing the stream".getBytes("UTF-8")); - - assertEquals( - "[</dir1/dir2/simple ascii: 'regular ascii'>, " + - "</dir1/dir2/utf-8 test: 'nihongo in UTF-8: 日本語'>, " + - "</dir1/dir2/forgot to close: (stream not closed properly)>]", - Arrays.toString(m.getOutputStreams())); - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/mock/MockLog.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/mock/MockLog.java deleted file mode 100644 index f2e30d2..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/mock/MockLog.java +++ /dev/null @@ -1,76 +0,0 @@ -/* - * Copyright (C) 2008 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.mock; - -import com.android.annotations.NonNull; -import com.android.utils.ILogger; - -import java.util.ArrayList; -import java.util.Formatter; -import java.util.List; - -/** - * An instance of {@link ILogger} that captures all messages to an internal list. - * Messages can be retrieved later using {@link #toString()}. - * Useful for unit-tests. - */ -public class MockLog implements ILogger { - private ArrayList<String> mMessages = new ArrayList<String>(); - - private void add(String code, String format, Object... args) { - Formatter formatter = new Formatter(); - mMessages.add(formatter.format(code + format, args).toString()); - formatter.close(); - } - - @Override - public void warning(@NonNull String format, Object... args) { - add("W ", format, args); - } - - @Override - public void info(@NonNull String format, Object... args) { - add("P ", format, args); - } - - @Override - public void verbose(@NonNull String format, Object... args) { - add("V ", format, args); - } - - @Override - public void error(Throwable t, String format, Object... args) { - if (t != null) { - add("T", "%s", t.toString()); - } - add("E ", format, args); - } - - @Override - public String toString() { - return mMessages.toString(); - } - - @NonNull - public List<String> getMessages() { - return mMessages; - } - - public void clear() { - mMessages.clear(); - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/repository/CaptureErrorHandler.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/repository/CaptureErrorHandler.java deleted file mode 100755 index dccec59..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/repository/CaptureErrorHandler.java +++ /dev/null @@ -1,79 +0,0 @@ -/* - * Copyright (C) 2011 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.sdklib.repository; - -import org.xml.sax.ErrorHandler; -import org.xml.sax.SAXException; -import org.xml.sax.SAXParseException; - -/** - * A SAX error handler that captures the errors and warnings. - * This allows us to capture *all* errors and just not get an exception on the first one. - */ -class CaptureErrorHandler implements ErrorHandler { - - private String mWarnings = ""; - private String mErrors = ""; - - public String getErrors() { - return mErrors; - } - - public String getWarnings() { - return mWarnings; - } - - /** - * Verifies if the handler captures some errors or warnings. - * Prints them on stderr. - * Also fails the unit test if any error was generated. - */ - public void verify() { - if (mWarnings.length() > 0) { - System.err.println(mWarnings); - } - - if (mErrors.length() > 0) { - System.err.println(mErrors); - junit.framework.Assert.fail(mErrors); - } - } - - /** - * @throws SAXException - */ - @Override - public void error(SAXParseException ex) throws SAXException { - mErrors += "Error: " + ex.getMessage() + "\n"; - } - - /** - * @throws SAXException - */ - @Override - public void fatalError(SAXParseException ex) throws SAXException { - mErrors += "Fatal Error: " + ex.getMessage() + "\n"; - } - - /** - * @throws SAXException - */ - @Override - public void warning(SAXParseException ex) throws SAXException { - mWarnings += "Warning: " + ex.getMessage() + "\n"; - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/repository/ValidateAddonXmlTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/repository/ValidateAddonXmlTest.java deleted file mode 100755 index ea56e0b..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/repository/ValidateAddonXmlTest.java +++ /dev/null @@ -1,212 +0,0 @@ -/* - * Copyright (C) 2011 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.sdklib.repository; - -import com.android.annotations.Nullable; - -import org.xml.sax.SAXException; -import org.xml.sax.SAXParseException; - -import java.io.InputStream; -import java.io.StringReader; - -import javax.xml.XMLConstants; -import javax.xml.transform.Source; -import javax.xml.transform.stream.StreamSource; -import javax.xml.validation.Schema; -import javax.xml.validation.SchemaFactory; -import javax.xml.validation.Validator; - -import junit.framework.TestCase; - -/** - * Tests local validation of an SDK Addon sample XMLs using an XML Schema validator. - */ -public class ValidateAddonXmlTest extends TestCase { - - private static String OPEN_TAG_ADDON = - "<r:sdk-addon xmlns:r=\"http://schemas.android.com/sdk/android/addon/" + - Integer.toString(SdkAddonConstants.NS_LATEST_VERSION) + - "\">"; - private static String CLOSE_TAG_ADDON = "</r:sdk-addon>"; - - // --- Helpers ------------ - - /** - * Helper method that returns a validator for our Addon XSD - * - * @param version The version number, in range {@code 1..NS_LATEST_VERSION} - * @param handler A {@link CaptureErrorHandler}. If null the default will be used, - * which will most likely print errors to stderr. - */ - private Validator getAddonValidator(int version, @Nullable CaptureErrorHandler handler) - throws SAXException { - Validator validator = null; - InputStream xsdStream = SdkAddonConstants.getXsdStream(version); - if (xsdStream != null) { - SchemaFactory factory = SchemaFactory.newInstance(XMLConstants.W3C_XML_SCHEMA_NS_URI); - Schema schema = factory.newSchema(new StreamSource(xsdStream)); - validator = schema.newValidator(); - if (handler != null) { - validator.setErrorHandler(handler); - } - } - - return validator; - } - - /** An helper that validates a string against an expected regexp. */ - private void assertRegex(String expectedRegexp, String actualString) { - assertNotNull(actualString); - assertTrue( - String.format("Regexp Assertion Failed:\nExpected: %s\nActual: %s\n", - expectedRegexp, actualString), - actualString.matches(expectedRegexp)); - } - - // --- Tests ------------ - - /** Validates that NS_LATEST_VERSION points to the max available XSD schema. */ - public void testAddonLatestVersionNumber() throws Exception { - CaptureErrorHandler handler = new CaptureErrorHandler(); - - // There should be a schema matching NS_LATEST_VERSION - assertNotNull(getAddonValidator(SdkAddonConstants.NS_LATEST_VERSION, handler)); - - // There should NOT be a schema with NS_LATEST_VERSION+1 - assertNull( - String.format( - "There's an ADDON XSD at version %d but SdkAddonConstants.NS_LATEST_VERSION is still set to %d.", - SdkAddonConstants.NS_LATEST_VERSION + 1, - SdkAddonConstants.NS_LATEST_VERSION), - getAddonValidator(SdkAddonConstants.NS_LATEST_VERSION + 1, handler)); - } - - /** Validate a valid sample using namespace version 1 using an InputStream */ - public void testValidateLocalAddonFile1() throws Exception { - InputStream xmlStream = this.getClass().getResourceAsStream( - "/com/android/sdklib/testdata/addon_sample_1.xml"); - Source source = new StreamSource(xmlStream); - - CaptureErrorHandler handler = new CaptureErrorHandler(); - Validator validator = getAddonValidator(1, handler); - validator.validate(source); - handler.verify(); - } - - /** Validate a valid sample using namespace version 2 using an InputStream */ - public void testValidateLocalAddonFile2() throws Exception { - InputStream xmlStream = this.getClass().getResourceAsStream( - "/com/android/sdklib/testdata/addon_sample_2.xml"); - Source source = new StreamSource(xmlStream); - - CaptureErrorHandler handler = new CaptureErrorHandler(); - Validator validator = getAddonValidator(2, handler); - validator.validate(source); - handler.verify(); - } - - /** Validate a valid sample using namespace version 3 using an InputStream */ - public void testValidateLocalAddonFile3() throws Exception { - InputStream xmlStream = this.getClass().getResourceAsStream( - "/com/android/sdklib/testdata/addon_sample_3.xml"); - Source source = new StreamSource(xmlStream); - - CaptureErrorHandler handler = new CaptureErrorHandler(); - Validator validator = getAddonValidator(3, handler); - validator.validate(source); - handler.verify(); - } - - /** Validate a valid sample using namespace version 4 using an InputStream */ - public void testValidateLocalAddonFile4() throws Exception { - InputStream xmlStream = this.getClass().getResourceAsStream( - "/com/android/sdklib/testdata/addon_sample_4.xml"); - Source source = new StreamSource(xmlStream); - - CaptureErrorHandler handler = new CaptureErrorHandler(); - Validator validator = getAddonValidator(4, handler); - validator.validate(source); - handler.verify(); - } - - // IMPORTANT: each time you add a test here, you should add a corresponding - // test in SdkAddonSourceTest to validate the XML content is parsed correctly. - - // ---- - - /** - * An addon does not support a codename. - * There used to be a typo in the repository.XSD versions 1-2 & the addon XSD versions 1-2 - * where addons had an optional element 'codename'. This was a typo and it's been fixed. - */ - public void testAddonCodename() throws Exception { - // we define a license named "lic1" and then reference "lic2" instead - String document = "<?xml version=\"1.0\"?>" + - OPEN_TAG_ADDON + - "<r:license id=\"lic1\"> some license </r:license> " + - "<r:add-on> <r:uses-license ref=\"lic1\" /> <r:revision>1</r:revision> " + - "<r:name-id>AddonName</r:name-id> <r:name-display>The Addon Name</r:name-display> " + - "<r:vendor-id>AddonVendor</r:vendor-id> <r:vendor-display>The Addon Vendor</r:vendor-display> " + - "<r:api-level>42</r:api-level> " + - "<r:codename>Addons do not support codenames</r:codenames> " + - "<r:libs><r:lib><r:name>com.example.LibName</r:name></r:lib></r:libs> " + - "<r:archives> <r:archive os=\"any\"> <r:size>1</r:size> <r:checksum>2822ae37115ebf13412bbef91339ee0d9454525e</r:checksum> " + - "<r:url>url</r:url> </r:archive> </r:archives> </r:add-on>" + - CLOSE_TAG_ADDON; - - Source source = new StreamSource(new StringReader(document)); - - // don't capture the validator errors, we want it to fail and catch the exception - Validator validator = getAddonValidator(SdkAddonConstants.NS_LATEST_VERSION, null); - try { - validator.validate(source); - } catch (SAXParseException e) { - // We expect a parse error referring to this grammar rule - assertRegex("cvc-complex-type.2.4.a: Invalid content was found starting with element 'r:codename'.*", - e.getMessage()); - return; - } - // If we get here, the validator has not failed as we expected it to. - fail(); - } - - /** A document with a slash in an extra path. */ - public void testExtraPathWithSlash() throws Exception { - String document = "<?xml version=\"1.0\"?>" + - OPEN_TAG_ADDON + - "<r:extra> <r:revision>1</r:revision> <r:path>path/cannot\\contain\\segments</r:path> " + - "<r:archives> <r:archive os=\"any\"> <r:size>1</r:size> <r:checksum>2822ae37115ebf13412bbef91339ee0d9454525e</r:checksum> " + - "<r:url>url</r:url> </r:archive> </r:archives> </r:extra>" + - CLOSE_TAG_ADDON; - - Source source = new StreamSource(new StringReader(document)); - - // don't capture the validator errors, we want it to fail and catch the exception - Validator validator = getAddonValidator(SdkAddonConstants.NS_LATEST_VERSION, null); - try { - validator.validate(source); - } catch (SAXParseException e) { - // We expect a parse error referring to this grammar rule - assertRegex("cvc-pattern-valid: Value 'path/cannot\\\\contain\\\\segments' is not facet-valid with respect to pattern.*", - e.getMessage()); - return; - } - // If we get here, the validator has not failed as we expected it to. - fail(); - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/repository/ValidateAddonsListXmlTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/repository/ValidateAddonsListXmlTest.java deleted file mode 100755 index 0461c67..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/repository/ValidateAddonsListXmlTest.java +++ /dev/null @@ -1,108 +0,0 @@ -/* - * Copyright (C) 2012 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.sdklib.repository; - -import com.android.annotations.Nullable; - -import org.xml.sax.SAXException; - -import java.io.InputStream; - -import javax.xml.XMLConstants; -import javax.xml.transform.Source; -import javax.xml.transform.stream.StreamSource; -import javax.xml.validation.Schema; -import javax.xml.validation.SchemaFactory; -import javax.xml.validation.Validator; - -import junit.framework.TestCase; - -/** - * Tests local validation of an SDK Addon-List sample XMLs using an XML Schema validator. - */ -public class ValidateAddonsListXmlTest extends TestCase { - - // --- Helpers ------------ - - /** - * Helper method that returns a validator for our Addons-List XSD - * - * @param version The version number, in range {@code 1..NS_LATEST_VERSION} - * @param handler A {@link CaptureErrorHandler}. If null the default will be used, - * which will most likely print errors to stderr. - */ - private Validator getValidator(int version, @Nullable CaptureErrorHandler handler) - throws SAXException { - Validator validator = null; - InputStream xsdStream = SdkAddonsListConstants.getXsdStream(version); - if (xsdStream != null) { - SchemaFactory factory = SchemaFactory.newInstance(XMLConstants.W3C_XML_SCHEMA_NS_URI); - Schema schema = factory.newSchema(new StreamSource(xsdStream)); - validator = schema.newValidator(); - if (handler != null) { - validator.setErrorHandler(handler); - } - } - - return validator; - } - - // --- Tests ------------ - - /** Validates that NS_LATEST_VERSION points to the max available XSD schema. */ - public void testAddonLatestVersionNumber() throws Exception { - CaptureErrorHandler handler = new CaptureErrorHandler(); - - // There should be a schema matching NS_LATEST_VERSION - assertNotNull(getValidator(SdkAddonsListConstants.NS_LATEST_VERSION, handler)); - - // There should NOT be a schema with NS_LATEST_VERSION+1 - assertNull( - String.format( - "There's an ADDON XSD at version %d but SdkAddonsListConstants.NS_LATEST_VERSION is still set to %d.", - SdkAddonsListConstants.NS_LATEST_VERSION + 1, - SdkAddonsListConstants.NS_LATEST_VERSION), - getValidator(SdkAddonsListConstants.NS_LATEST_VERSION + 1, handler)); - } - - /** Validate a valid sample using namespace version 1 using an InputStream */ - public void testValidateLocalAddonFile1() throws Exception { - InputStream xmlStream = this.getClass().getResourceAsStream( - "/com/android/sdklib/testdata/addons_list_sample_1.xml"); - Source source = new StreamSource(xmlStream); - - CaptureErrorHandler handler = new CaptureErrorHandler(); - Validator validator = getValidator(1, handler); - validator.validate(source); - handler.verify(); - } - - /** Validate a valid sample using namespace version 2 using an InputStream */ - public void testValidateLocalAddonFile2() throws Exception { - InputStream xmlStream = this.getClass().getResourceAsStream( - "/com/android/sdklib/testdata/addons_list_sample_2.xml"); - Source source = new StreamSource(xmlStream); - - CaptureErrorHandler handler = new CaptureErrorHandler(); - Validator validator = getValidator(2, handler); - validator.validate(source); - handler.verify(); - } - - // IMPORTANT: each time you add a test here, you should add a corresponding - // test in AddonsListFetcherTest to validate the XML content is parsed correctly. -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/repository/ValidateRepositoryXmlTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/repository/ValidateRepositoryXmlTest.java deleted file mode 100755 index bdc450c..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/repository/ValidateRepositoryXmlTest.java +++ /dev/null @@ -1,351 +0,0 @@ -/* - * Copyright (C) 2009 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.sdklib.repository; - -import com.android.annotations.Nullable; - -import org.xml.sax.SAXException; -import org.xml.sax.SAXParseException; - -import java.io.InputStream; -import java.io.StringReader; - -import javax.xml.XMLConstants; -import javax.xml.transform.Source; -import javax.xml.transform.stream.StreamSource; -import javax.xml.validation.Schema; -import javax.xml.validation.SchemaFactory; -import javax.xml.validation.Validator; - -import junit.framework.TestCase; - -/** - * Tests local validation of an SDK Repository sample XMLs using an XML Schema validator. - * - * References: - * http://www.ibm.com/developerworks/xml/library/x-javaxmlvalidapi.html - */ -public class ValidateRepositoryXmlTest extends TestCase { - - private static String OPEN_TAG_REPO = - "<r:sdk-repository xmlns:r=\"http://schemas.android.com/sdk/android/repository/" + - Integer.toString(SdkRepoConstants.NS_LATEST_VERSION) + - "\">"; - private static String CLOSE_TAG_REPO = "</r:sdk-repository>"; - - // --- Helpers ------------ - - /** - * Helper method that returns a validator for our Repository XSD - * - * @param version The version number, in range {@code 1..NS_LATEST_VERSION} - * @param handler A {@link CaptureErrorHandler}. If null the default will be used, - * which will most likely print errors to stderr. - */ - private Validator getRepoValidator(int version, @Nullable CaptureErrorHandler handler) - throws SAXException { - Validator validator = null; - InputStream xsdStream = SdkRepoConstants.getXsdStream(version); - if (xsdStream != null) { - SchemaFactory factory = SchemaFactory.newInstance(XMLConstants.W3C_XML_SCHEMA_NS_URI); - Schema schema = factory.newSchema(new StreamSource(xsdStream)); - validator = schema.newValidator(); - - if (handler != null) { - validator.setErrorHandler(handler); - } - } - - return validator; - } - - /** An helper that validates a string against an expected regexp. */ - private void assertRegex(String expectedRegexp, String actualString) { - assertNotNull(actualString); - assertTrue( - String.format("Regexp Assertion Failed:\nExpected: %s\nActual: %s\n", - expectedRegexp, actualString), - actualString.matches(expectedRegexp)); - } - - // --- Tests ------------ - - /** Validates that NS_LATEST_VERSION points to the max available XSD schema. */ - public void testRepoLatestVersionNumber() throws Exception { - CaptureErrorHandler handler = new CaptureErrorHandler(); - - // There should be a schema matching NS_LATEST_VERSION - assertNotNull(getRepoValidator(SdkRepoConstants.NS_LATEST_VERSION, handler)); - - // There should NOT be a schema with NS_LATEST_VERSION+1 - assertNull( - String.format( - "There's a REPO XSD at version %d but SdkRepoConstants.NS_LATEST_VERSION is still set to %d.", - SdkRepoConstants.NS_LATEST_VERSION + 1, - SdkRepoConstants.NS_LATEST_VERSION), - getRepoValidator(SdkRepoConstants.NS_LATEST_VERSION + 1, handler)); - } - - /** Validate a valid sample using namespace version 1 using an InputStream */ - public void testValidateLocalRepositoryFile1() throws Exception { - InputStream xmlStream = this.getClass().getResourceAsStream( - "/com/android/sdklib/testdata/repository_sample_1.xml"); - Source source = new StreamSource(xmlStream); - - CaptureErrorHandler handler = new CaptureErrorHandler(); - Validator validator = getRepoValidator(1, handler); - validator.validate(source); - handler.verify(); - } - - /** Validate a valid sample using namespace version 2 using an InputStream */ - public void testValidateLocalRepositoryFile2() throws Exception { - InputStream xmlStream = this.getClass().getResourceAsStream( - "/com/android/sdklib/testdata/repository_sample_2.xml"); - Source source = new StreamSource(xmlStream); - - CaptureErrorHandler handler = new CaptureErrorHandler(); - Validator validator = getRepoValidator(2, handler); - validator.validate(source); - handler.verify(); - } - - /** Validate a valid sample using namespace version 3 using an InputStream */ - public void testValidateLocalRepositoryFile3() throws Exception { - InputStream xmlStream = this.getClass().getResourceAsStream( - "/com/android/sdklib/testdata/repository_sample_3.xml"); - Source source = new StreamSource(xmlStream); - - CaptureErrorHandler handler = new CaptureErrorHandler(); - Validator validator = getRepoValidator(3, handler); - validator.validate(source); - handler.verify(); - } - - /** Validate a valid sample using namespace version 4 using an InputStream */ - public void testValidateLocalRepositoryFile4() throws Exception { - InputStream xmlStream = this.getClass().getResourceAsStream( - "/com/android/sdklib/testdata/repository_sample_4.xml"); - Source source = new StreamSource(xmlStream); - - CaptureErrorHandler handler = new CaptureErrorHandler(); - Validator validator = getRepoValidator(4, handler); - validator.validate(source); - handler.verify(); - - } - - /** Validate a valid sample using namespace version 5 using an InputStream */ - public void testValidateLocalRepositoryFile5() throws Exception { - InputStream xmlStream = this.getClass().getResourceAsStream( - "/com/android/sdklib/testdata/repository_sample_5.xml"); - Source source = new StreamSource(xmlStream); - - CaptureErrorHandler handler = new CaptureErrorHandler(); - Validator validator = getRepoValidator(5, handler); - validator.validate(source); - handler.verify(); - - } - - /** Validate a valid sample using namespace version 5 using an InputStream */ - public void testValidateLocalRepositoryFile6() throws Exception { - InputStream xmlStream = this.getClass().getResourceAsStream( - "/com/android/sdklib/testdata/repository_sample_6.xml"); - Source source = new StreamSource(xmlStream); - - CaptureErrorHandler handler = new CaptureErrorHandler(); - Validator validator = getRepoValidator(6, handler); - validator.validate(source); - handler.verify(); - - } - - /** Validate a valid sample using namespace version 5 using an InputStream */ - public void testValidateLocalRepositoryFile7() throws Exception { - InputStream xmlStream = this.getClass().getResourceAsStream( - "/com/android/sdklib/testdata/repository_sample_7.xml"); - Source source = new StreamSource(xmlStream); - - CaptureErrorHandler handler = new CaptureErrorHandler(); - Validator validator = getRepoValidator(7, handler); - validator.validate(source); - handler.verify(); - - } - - // IMPORTANT: each time you add a test here, you should add a corresponding - // test in SdkRepoSourceTest to validate the XML content is parsed correctly. - - - // --- - - /** A document should at least have a root to be valid */ - public void testEmptyXml() throws Exception { - String document = "<?xml version=\"1.0\"?>"; - - Source source = new StreamSource(new StringReader(document)); - - CaptureErrorHandler handler = new CaptureErrorHandler(); - Validator validator = getRepoValidator(SdkRepoConstants.NS_LATEST_VERSION, handler); - - try { - validator.validate(source); - } catch (SAXParseException e) { - // We expect to get this specific exception message - assertRegex("Premature end of file.*", e.getMessage()); - return; - } - // We shouldn't get here - handler.verify(); - fail(); - } - - /** A document with a root element containing no platform, addon, etc., is valid. */ - public void testEmptyRootXml() throws Exception { - String document = "<?xml version=\"1.0\"?>" + - OPEN_TAG_REPO + - CLOSE_TAG_REPO; - - Source source = new StreamSource(new StringReader(document)); - - CaptureErrorHandler handler = new CaptureErrorHandler(); - Validator validator = getRepoValidator(SdkRepoConstants.NS_LATEST_VERSION, handler); - validator.validate(source); - handler.verify(); - } - - /** A document with an unknown element. */ - public void testUnknownContentXml() throws Exception { - String document = "<?xml version=\"1.0\"?>" + - OPEN_TAG_REPO + - "<r:unknown />" + - CLOSE_TAG_REPO; - - Source source = new StreamSource(new StringReader(document)); - - // don't capture the validator errors, we want it to fail and catch the exception - Validator validator = getRepoValidator(SdkRepoConstants.NS_LATEST_VERSION, null); - try { - validator.validate(source); - } catch (SAXParseException e) { - // We expect a parse expression referring to this grammar rule - assertRegex("cvc-complex-type.2.4.a: Invalid content was found.*", e.getMessage()); - return; - } - // If we get here, the validator has not failed as we expected it to. - fail(); - } - - /** A document with an incomplete element. */ - public void testIncompleteContentXml() throws Exception { - String document = "<?xml version=\"1.0\"?>" + - OPEN_TAG_REPO + - "<r:platform> <r:api-level>1</r:api-level> <r:libs /> </r:platform>" + - CLOSE_TAG_REPO; - - Source source = new StreamSource(new StringReader(document)); - - // don't capture the validator errors, we want it to fail and catch the exception - Validator validator = getRepoValidator(SdkRepoConstants.NS_LATEST_VERSION, null); - try { - validator.validate(source); - } catch (SAXParseException e) { - // We expect a parse error referring to this grammar rule - assertRegex("cvc-complex-type.2.4.a: Invalid content was found.*", e.getMessage()); - return; - } - // If we get here, the validator has not failed as we expected it to. - fail(); - } - - /** A document with a wrong type element. */ - public void testWrongTypeContentXml() throws Exception { - String document = "<?xml version=\"1.0\"?>" + - OPEN_TAG_REPO + - "<r:platform> <r:api-level>NotAnInteger</r:api-level> <r:libs /> </r:platform>" + - CLOSE_TAG_REPO; - - Source source = new StreamSource(new StringReader(document)); - - // don't capture the validator errors, we want it to fail and catch the exception - Validator validator = getRepoValidator(SdkRepoConstants.NS_LATEST_VERSION, null); - try { - validator.validate(source); - } catch (SAXParseException e) { - // We expect a parse error referring to this grammar rule - assertRegex("cvc-datatype-valid.1.2.1: 'NotAnInteger' is not a valid value.*", - e.getMessage()); - return; - } - // If we get here, the validator has not failed as we expected it to. - fail(); - } - - /** A document with an unknown license id. */ - public void testLicenseIdNotFound() throws Exception { - // we define a license named "lic1" and then reference "lic2" instead - String document = "<?xml version=\"1.0\"?>" + - OPEN_TAG_REPO + - "<r:license id=\"lic1\"> some license </r:license> " + - "<r:tool> <r:uses-license ref=\"lic2\" /> <r:revision> <r:major>1</r:major> </r:revision> " + - "<r:min-platform-tools-rev> <r:major>1</r:major> </r:min-platform-tools-rev> " + - "<r:archives> <r:archive os=\"any\"> <r:size>1</r:size> <r:checksum>2822ae37115ebf13412bbef91339ee0d9454525e</r:checksum> " + - "<r:url>url</r:url> </r:archive> </r:archives> </r:tool>" + - CLOSE_TAG_REPO; - - Source source = new StreamSource(new StringReader(document)); - - // don't capture the validator errors, we want it to fail and catch the exception - Validator validator = getRepoValidator(SdkRepoConstants.NS_LATEST_VERSION, null); - try { - validator.validate(source); - } catch (SAXParseException e) { - // We expect a parse error referring to this grammar rule - assertRegex("cvc-id.1: There is no ID/IDREF binding for IDREF 'lic2'.*", - e.getMessage()); - return; - } - // If we get here, the validator has not failed as we expected it to. - fail(); - } - - /** The latest XSD repository-6 should fail when an 'extra' is present. */ - public void testExtraPathWithSlash() throws Exception { - String document = "<?xml version=\"1.0\"?>" + - OPEN_TAG_REPO + - "<r:extra> <r:revision>1</r:revision> <r:path>path</r:path> " + - "<r:archives> <r:archive os=\"any\"> <r:size>1</r:size> <r:checksum>2822ae37115ebf13412bbef91339ee0d9454525e</r:checksum> " + - "<r:url>url</r:url> </r:archive> </r:archives> </r:extra>" + - CLOSE_TAG_REPO; - - Source source = new StreamSource(new StringReader(document)); - - // don't capture the validator errors, we want it to fail and catch the exception - Validator validator = getRepoValidator(SdkRepoConstants.NS_LATEST_VERSION, null); - try { - validator.validate(source); - } catch (SAXParseException e) { - // We expect a parse error referring to this grammar rule - assertRegex("cvc-complex-type.2.4.a: Invalid content was found starting with element 'r:extra'.*", - e.getMessage()); - return; - } - // If we get here, the validator has not failed as we expected it to. - fail(); - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/repository/ValidateSysImgXmlTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/repository/ValidateSysImgXmlTest.java deleted file mode 100755 index fe7b1e8..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/repository/ValidateSysImgXmlTest.java +++ /dev/null @@ -1,101 +0,0 @@ -/* - * Copyright (C) 2012 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.sdklib.repository; - -import com.android.annotations.Nullable; - -import org.xml.sax.SAXException; - -import java.io.InputStream; - -import javax.xml.XMLConstants; -import javax.xml.transform.Source; -import javax.xml.transform.stream.StreamSource; -import javax.xml.validation.Schema; -import javax.xml.validation.SchemaFactory; -import javax.xml.validation.Validator; - -import junit.framework.TestCase; - -/** - * Tests local validation of an SDK Repository sample XMLs using an XML Schema validator. - * - * References: - * http://www.ibm.com/developerworks/xml/library/x-javaxmlvalidapi.html - */ -public class ValidateSysImgXmlTest extends TestCase { - - // --- Helpers ------------ - - /** - * Helper method that returns a validator for our Repository XSD - * - * @param version The version number, in range {@code 1..NS_LATEST_VERSION} - * @param handler A {@link CaptureErrorHandler}. If null the default will be used, - * which will most likely print errors to stderr. - */ - private Validator getValidator(int version, @Nullable CaptureErrorHandler handler) - throws SAXException { - Validator validator = null; - InputStream xsdStream = SdkSysImgConstants.getXsdStream(version); - if (xsdStream != null) { - SchemaFactory factory = SchemaFactory.newInstance(XMLConstants.W3C_XML_SCHEMA_NS_URI); - Schema schema = factory.newSchema(new StreamSource(xsdStream)); - validator = schema.newValidator(); - - if (handler != null) { - validator.setErrorHandler(handler); - } - } - - return validator; - } - - // --- Tests ------------ - - /** Validates that NS_LATEST_VERSION points to the max available XSD schema. */ - public void testSysImgLatestVersionNumber() throws Exception { - CaptureErrorHandler handler = new CaptureErrorHandler(); - - // There should be a schema matching NS_LATEST_VERSION - assertNotNull(getValidator(SdkSysImgConstants.NS_LATEST_VERSION, handler)); - - // There should NOT be a schema with NS_LATEST_VERSION+1 - assertNull( - String.format( - "There's a REPO XSD at version %d but SdkSysImgConstants.NS_LATEST_VERSION is still set to %d.", - SdkSysImgConstants.NS_LATEST_VERSION + 1, - SdkSysImgConstants.NS_LATEST_VERSION), - getValidator(SdkSysImgConstants.NS_LATEST_VERSION + 1, handler)); - } - - /** Validate a valid sample using namespace version 1 using an InputStream */ - public void testValidateLocalRepositoryFile1() throws Exception { - InputStream xmlStream = this.getClass().getResourceAsStream( - "/com/android/sdklib/testdata/sys_img_sample_1.xml"); - Source source = new StreamSource(xmlStream); - - CaptureErrorHandler handler = new CaptureErrorHandler(); - Validator validator = getValidator(1, handler); - validator.validate(source); - handler.verify(); - } - - // IMPORTANT: each time you add a test here, you should add a corresponding - // test in SdkSysImgSourceTest to validate the XML content is parsed correctly. - -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/AndroidManifest-activityalias.xml b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/AndroidManifest-activityalias.xml deleted file mode 100644 index 6f63897..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/AndroidManifest-activityalias.xml +++ /dev/null @@ -1,23 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<manifest xmlns:android="http://schemas.android.com/apk/res/android" - package="com.android.testapp" android:versionCode="42" - android:versionName="1.42"> - - <application android:icon="@drawable/icon"> - <activity android:name="com.android.testapp.MainActivity" - android:label="@string/app_name"> - </activity> - - <activity-alias android:name="com.android.testapp.AliasActivity" - android:label="@string/app_name" - android:targetActivity="com.android.testapp.MainActivity"> - <intent-filter> - <action android:name="android.intent.action.MAIN" /> - <category android:name="android.intent.category.LAUNCHER" /> - </intent-filter> - </activity-alias> - </application> - - <uses-sdk android:minSdkVersion="7" android:targetSdkVersion="8" /> - -</manifest> diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/AndroidManifest-instrumentation.xml b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/AndroidManifest-instrumentation.xml deleted file mode 100644 index f1dce67..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/AndroidManifest-instrumentation.xml +++ /dev/null @@ -1,19 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<manifest xmlns:android="http://schemas.android.com/apk/res/android" - package="com.android.AndroidProject.tests"> - - <!-- - This declares that this app uses the instrumentation test runner targeting - the package of com.android.samples. To run the tests use the command: - "adb shell am instrument -w com.android.samples.tests/android.test.InstrumentationTestRunner" - --> - <instrumentation android:name="android.test.InstrumentationTestRunner" - android:targetPackage="com.android.AndroidProject" - android:label="Sample test for deployment."/> - - <application> - <uses-library android:name="android.test.runner" /> - </application> - <uses-sdk android:minSdkVersion="foo"/> - -</manifest> diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/AndroidManifest-testapp.xml b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/AndroidManifest-testapp.xml deleted file mode 100644 index f55b4e0..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/AndroidManifest-testapp.xml +++ /dev/null @@ -1,29 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<manifest xmlns:android="http://schemas.android.com/apk/res/android" - package="com.android.testapp" android:versionCode="42" - android:versionName="1.42"> - <application android:icon="@drawable/icon"> - <activity android:name="com.android.testapp.MainActivity" - android:label="@string/app_name"> - <intent-filter> - <action android:name="android.intent.action.MAIN" /> - <category android:name="android.intent.category.LAUNCHER" /> - <category android:name="android.intent.category.DEFAULT" /> - </intent-filter> - </activity> - <uses-library android:name="android.test.runner" - android:required="false" /> - <uses-library android:name="android.test.runner2" /> - </application> - <uses-sdk android:minSdkVersion="7" android:targetSdkVersion="8" /> - <supports-screens android:resizeable="true" - android:smallScreens="true" android:anyDensity="true" - android:largeScreens="true" android:normalScreens="true" /> - <uses-configuration android:reqKeyboardType="twelvekey" - android:reqTouchScreen="finger" android:reqFiveWayNav="true" - android:reqHardKeyboard="true" android:reqNavigation="nonav" /> - <uses-feature android:glEsVersion="0x00020001" /> - <uses-feature android:name="com.foo.feature" /> - <instrumentation android:name="android.test.InstrumentationTestRunner" - android:targetPackage="com.example.android.apis" android:label="Tests for Api Demos." /> -</manifest> diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/AndroidManifest-testapp2.xml b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/AndroidManifest-testapp2.xml deleted file mode 100644 index d5bcac7..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/AndroidManifest-testapp2.xml +++ /dev/null @@ -1,8 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<manifest xmlns:android="http://schemas.android.com/apk/res/android" - package="com.android.testapp" android:versionCode="42" - android:versionName="1.42"> - <application android:icon="@drawable/icon"/> - <uses-sdk android:minSdkVersion="7" android:targetSdkVersion="8" /> - <supports-screens android:largeScreens="false" /> -</manifest> diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/addon_sample_1.xml b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/addon_sample_1.xml deleted file mode 100755 index d761d73..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/addon_sample_1.xml +++ /dev/null @@ -1,164 +0,0 @@ -<?xml version="1.0"?> -<!-- - * Copyright (C) 2010 The Android Open Source Project - * - * Licensed under the Apache License, version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<sdk:sdk-addon - xmlns:sdk="http://schemas.android.com/sdk/android/addon/1"> - - <!-- Define a couple of licenses. These will be referenced by uses-license later. --> - - <sdk:license type="text" id="license1"> - This is the license - for this platform. - </sdk:license> - - <sdk:license id="license2"> - Licenses are only of type 'text' right now, so this is implied. - </sdk:license> - - <!-- Inner elements must be either platform, add-on, doc or tool. - There can be 0 or more of each, in any order. --> - - <sdk:add-on> - <sdk:name>My First add-on</sdk:name> - <sdk:api-level>1</sdk:api-level> - <sdk:vendor>John Doe</sdk:vendor> - <sdk:revision>1</sdk:revision> - <sdk:uses-license ref="license2" /> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/myfirstaddon</sdk:desc-url> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/add-ons/first.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <!-- The libs node is mandatory, however it can be empty. --> - <sdk:libs> - <sdk:lib> - <sdk:name>android.blah.somelib</sdk:name> - <sdk:description>The description for this library.</sdk:description> - </sdk:lib> - <sdk:lib> - <!-- sdk:description is optional, name is not --> - <sdk:name>com.android.mymaps</sdk:name> - </sdk:lib> - </sdk:libs> - </sdk:add-on> - - <sdk:add-on> - <sdk:name>My Second add-on</sdk:name> - <sdk:api-level>2</sdk:api-level> - <sdk:vendor>John Deer</sdk:vendor> - <sdk:revision>42</sdk:revision> - <sdk:archives> - <sdk:archive os="windows"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/second-42-win.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/second-42-linux.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:libs> - <sdk:lib> - <sdk:name>android.blah.somelib</sdk:name> - <sdk:description>The description for this library.</sdk:description> - </sdk:lib> - <sdk:lib> - <sdk:name>com.android.mymaps</sdk:name> - </sdk:lib> - </sdk:libs> - <sdk:uses-license ref="license2" /> - </sdk:add-on> - - <sdk:add-on> - <sdk:uses-license ref="license2" /> - <sdk:name>This add-on has no libraries</sdk:name> - <sdk:api-level>4</sdk:api-level> - <sdk:vendor>Joe Bar</sdk:vendor> - <sdk:revision>3</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/imnotanarchiveimadoctorjim.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <!-- The libs node is mandatory, however it can be empty. --> - <sdk:libs /> - </sdk:add-on> - - <sdk:extra> - <sdk:vendor>g</sdk:vendor> - <sdk:path>usb_driver</sdk:path> - <sdk:uses-license ref="license2" /> - <sdk:revision>43</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/extraduff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>An Extra package for the USB driver, it will install in $SDK/usb_driver</sdk:description> - <sdk:desc-url>http://www.example.com/extra.html</sdk:desc-url> - <sdk:min-tools-rev>3</sdk:min-tools-rev> - <sdk:obsolete/> - </sdk:extra> - - <sdk:extra> - <sdk:vendor>android_vendor</sdk:vendor> - <sdk:path>extra_api_dep</sdk:path> - <sdk:uses-license ref="license2" /> - <sdk:revision>2</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/extra_mega_duff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>Some extra package that has a min-api-level of 42</sdk:description> - <sdk:desc-url>http://www.example.com/extra.html</sdk:desc-url> - <sdk:min-tools-rev>3</sdk:min-tools-rev> - <sdk:min-api-level>42</sdk:min-api-level> - <sdk:obsolete></sdk:obsolete> - </sdk:extra> - - <sdk:extra> - <sdk:vendor>____</sdk:vendor> - <sdk:path>____</sdk:path> - <sdk:uses-license ref="license2" /> - <sdk:revision>2</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/extra_mega_duff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>Some extra package that has a min-api-level of 42</sdk:description> - <sdk:desc-url>http://www.example.com/extra.html</sdk:desc-url> - <sdk:min-tools-rev>3</sdk:min-tools-rev> - <sdk:min-api-level>42</sdk:min-api-level> - <sdk:obsolete></sdk:obsolete> - </sdk:extra> - -</sdk:sdk-addon> diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/addon_sample_2.xml b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/addon_sample_2.xml deleted file mode 100755 index 1033c15..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/addon_sample_2.xml +++ /dev/null @@ -1,179 +0,0 @@ -<?xml version="1.0"?> -<!-- - * Copyright (C) 2010 The Android Open Source Project - * - * Licensed under the Apache License, version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<sdk:sdk-addon - xmlns:sdk="http://schemas.android.com/sdk/android/addon/2"> - - <!-- Define a couple of licenses. These will be referenced by uses-license later. --> - - <sdk:license type="text" id="license1"> - This is the license - for this platform. - </sdk:license> - - <sdk:license id="license2"> - Licenses are only of type 'text' right now, so this is implied. - </sdk:license> - - <!-- Inner elements must be either platform, add-on, doc or tool. - There can be 0 or more of each, in any order. --> - - <sdk:add-on> - <sdk:name>My First add-on</sdk:name> - <sdk:api-level>1</sdk:api-level> - <sdk:vendor>John Doe</sdk:vendor> - <sdk:revision>1</sdk:revision> - <sdk:uses-license ref="license2" /> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/myfirstaddon</sdk:desc-url> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/add-ons/first.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <!-- The libs node is mandatory, however it can be empty. --> - <sdk:libs> - <sdk:lib> - <sdk:name>android.blah.somelib</sdk:name> - <sdk:description>The description for this library.</sdk:description> - </sdk:lib> - <sdk:lib> - <!-- sdk:description is optional, name is not --> - <sdk:name>com.android.mymaps</sdk:name> - </sdk:lib> - </sdk:libs> - <sdk:layoutlib> - <sdk:api>5</sdk:api> - <sdk:revision>0</sdk:revision> - </sdk:layoutlib> - </sdk:add-on> - - <sdk:add-on> - <sdk:name>My Second add-on</sdk:name> - <sdk:api-level>2</sdk:api-level> - <sdk:vendor>John Deer</sdk:vendor> - <sdk:revision>42</sdk:revision> - <sdk:archives> - <sdk:archive os="windows"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/second-42-win.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/second-42-linux.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:libs> - <sdk:lib> - <sdk:name>android.blah.somelib</sdk:name> - <sdk:description>The description for this library.</sdk:description> - </sdk:lib> - <sdk:lib> - <sdk:name>com.android.mymaps</sdk:name> - </sdk:lib> - </sdk:libs> - <sdk:uses-license ref="license2" /> - <!-- No layoutlib element in this package. It's optional. --> - </sdk:add-on> - - <sdk:add-on> - <sdk:uses-license ref="license2" /> - <sdk:name>This add-on has no libraries</sdk:name> - <sdk:api-level>4</sdk:api-level> - <sdk:vendor>Joe Bar</sdk:vendor> - <sdk:revision>3</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/imnotanarchiveimadoctorjim.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <!-- The libs node is mandatory, however it can be empty. --> - <sdk:libs /> - <sdk:layoutlib> - <sdk:api>3</sdk:api> - <sdk:revision>42</sdk:revision> - </sdk:layoutlib> - </sdk:add-on> - - <sdk:extra> - <sdk:vendor>g</sdk:vendor> - <sdk:path>usb_driver</sdk:path> - <sdk:uses-license ref="license2" /> - <sdk:revision>43</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/extraduff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>An Extra package for the USB driver, it will install in $SDK/usb_driver</sdk:description> - <sdk:desc-url>http://www.example.com/extra.html</sdk:desc-url> - <sdk:min-tools-rev>3</sdk:min-tools-rev> - <sdk:obsolete/> - </sdk:extra> - - <sdk:extra> - <sdk:vendor>android_vendor</sdk:vendor> - <sdk:path>extra_api_dep</sdk:path> - <sdk:uses-license ref="license2" /> - <sdk:revision>2</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/extra_mega_duff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>Some extra package that has a min-api-level of 42</sdk:description> - <sdk:desc-url>http://www.example.com/extra.html</sdk:desc-url> - <sdk:min-tools-rev>3</sdk:min-tools-rev> - <sdk:min-api-level>42</sdk:min-api-level> - <sdk:obsolete></sdk:obsolete> - <sdk:project-files> - <sdk:path>v8/veggies_8.jar</sdk:path> - <sdk:path>root.jar</sdk:path> - <sdk:path>dir1/dir 2 with space/mylib.jar</sdk:path> - </sdk:project-files> - </sdk:extra> - - <sdk:extra> - <sdk:vendor>____</sdk:vendor> - <sdk:path>____</sdk:path> - <sdk:uses-license ref="license2" /> - <sdk:revision>2</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/extra_mega_duff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>Some extra package that has a min-api-level of 42</sdk:description> - <sdk:desc-url>http://www.example.com/extra.html</sdk:desc-url> - <sdk:min-tools-rev>3</sdk:min-tools-rev> - <sdk:min-api-level>42</sdk:min-api-level> - <sdk:obsolete></sdk:obsolete> - <!-- No project-files element in this package. --> - </sdk:extra> - -</sdk:sdk-addon> diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/addon_sample_3.xml b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/addon_sample_3.xml deleted file mode 100755 index 568cec1..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/addon_sample_3.xml +++ /dev/null @@ -1,180 +0,0 @@ -<?xml version="1.0"?> -<!-- - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<sdk:sdk-addon - xmlns:sdk="http://schemas.android.com/sdk/android/addon/3"> - - <!-- Define a couple of licenses. These will be referenced by uses-license later. --> - - <sdk:license type="text" id="license1"> - This is the license - for this platform. - </sdk:license> - - <sdk:license id="license2"> - Licenses are only of type 'text' right now, so this is implied. - </sdk:license> - - <!-- Inner elements must be either platform, add-on, doc or tool. - There can be 0 or more of each, in any order. --> - - <sdk:add-on> - <sdk:name>My First add-on</sdk:name> - <sdk:api-level>1</sdk:api-level> - <sdk:vendor>John Doe</sdk:vendor> - <sdk:revision>1</sdk:revision> - <sdk:uses-license ref="license2" /> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/myfirstaddon</sdk:desc-url> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/add-ons/first.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <!-- The libs node is mandatory, however it can be empty. --> - <sdk:libs> - <sdk:lib> - <sdk:name>android.blah.somelib</sdk:name> - <sdk:description>The description for this library.</sdk:description> - </sdk:lib> - <sdk:lib> - <!-- sdk:description is optional, name is not --> - <sdk:name>com.android.mymaps</sdk:name> - </sdk:lib> - </sdk:libs> - <sdk:layoutlib> - <sdk:api>5</sdk:api> - <sdk:revision>0</sdk:revision> - </sdk:layoutlib> - </sdk:add-on> - - <sdk:add-on> - <sdk:name>My Second add-on</sdk:name> - <sdk:api-level>2</sdk:api-level> - <sdk:vendor>John Deer</sdk:vendor> - <sdk:revision>42</sdk:revision> - <sdk:archives> - <sdk:archive os="windows"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/second-42-win.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/second-42-linux.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:libs> - <sdk:lib> - <sdk:name>android.blah.somelib</sdk:name> - <sdk:description>The description for this library.</sdk:description> - </sdk:lib> - <sdk:lib> - <sdk:name>com.android.mymaps</sdk:name> - </sdk:lib> - </sdk:libs> - <sdk:uses-license ref="license2" /> - <!-- No layoutlib element in this package. It's optional. --> - </sdk:add-on> - - <sdk:add-on> - <sdk:uses-license ref="license2" /> - <sdk:name>This add-on has no libraries</sdk:name> - <sdk:api-level>4</sdk:api-level> - <sdk:vendor>Joe Bar</sdk:vendor> - <sdk:revision>3</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/imnotanarchiveimadoctorjim.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <!-- The libs node is mandatory, however it can be empty. --> - <sdk:libs /> - <sdk:layoutlib> - <sdk:api>3</sdk:api> - <sdk:revision>42</sdk:revision> - </sdk:layoutlib> - </sdk:add-on> - - <sdk:extra> - <sdk:vendor>g</sdk:vendor> - <sdk:path>usb_driver</sdk:path> - <sdk:uses-license ref="license2" /> - <sdk:revision>43</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/extraduff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>An Extra package for the USB driver, it will install in $SDK/usb_driver</sdk:description> - <sdk:desc-url>http://www.example.com/extra.html</sdk:desc-url> - <sdk:min-tools-rev>3</sdk:min-tools-rev> - <sdk:obsolete/> - </sdk:extra> - - <sdk:extra> - <sdk:vendor>android_vendor</sdk:vendor> - <sdk:path>extra_api_dep</sdk:path> - <sdk:uses-license ref="license2" /> - <sdk:revision>2</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/extra_mega_duff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>Some extra package that has a min-api-level of 42</sdk:description> - <sdk:desc-url>http://www.example.com/extra.html</sdk:desc-url> - <sdk:min-tools-rev>3</sdk:min-tools-rev> - <sdk:min-api-level>42</sdk:min-api-level> - <sdk:obsolete></sdk:obsolete> - <sdk:project-files> - <sdk:path>v8/veggies_8.jar</sdk:path> - <sdk:path>root.jar</sdk:path> - <sdk:path>dir1/dir 2 with space/mylib.jar</sdk:path> - </sdk:project-files> - <sdk:old-paths>path1;old_path2;oldPath3</sdk:old-paths> - </sdk:extra> - - <sdk:extra> - <sdk:vendor>____</sdk:vendor> - <sdk:path>____</sdk:path> - <sdk:uses-license ref="license2" /> - <sdk:revision>2</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/extra_mega_duff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>Some extra package that has a min-api-level of 42</sdk:description> - <sdk:desc-url>http://www.example.com/extra.html</sdk:desc-url> - <sdk:min-tools-rev>3</sdk:min-tools-rev> - <sdk:min-api-level>42</sdk:min-api-level> - <sdk:obsolete></sdk:obsolete> - <!-- No project-files element in this package. --> - </sdk:extra> - -</sdk:sdk-addon> diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/addon_sample_4.xml b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/addon_sample_4.xml deleted file mode 100755 index 6fba439..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/addon_sample_4.xml +++ /dev/null @@ -1,203 +0,0 @@ -<?xml version="1.0"?> -<!-- - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<sdk:sdk-addon - xmlns:sdk="http://schemas.android.com/sdk/android/addon/4"> - - <!-- Define a couple of licenses. These will be referenced by uses-license later. --> - - <sdk:license type="text" id="license1"> - This is the license - for this platform. - </sdk:license> - - <sdk:license id="license2"> - Licenses are only of type 'text' right now, so this is implied. - </sdk:license> - - <!-- Inner elements must be either platform, add-on, doc or tool. - There can be 0 or more of each, in any order. --> - - <sdk:add-on> - <sdk:name-id>My_First_add-on</sdk:name-id> - <sdk:name-display>My First add-on</sdk:name-display> - - <sdk:vendor-id>John_Doe</sdk:vendor-id> - <sdk:vendor-display>John Doe</sdk:vendor-display> - - <sdk:api-level>1</sdk:api-level> - <sdk:revision>1</sdk:revision> - <sdk:uses-license ref="license2" /> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/myfirstaddon</sdk:desc-url> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/add-ons/first.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <!-- The libs node is mandatory, however it can be empty. --> - <sdk:libs> - <sdk:lib> - <sdk:name>android.blah.somelib</sdk:name> - <sdk:description>The description for this library.</sdk:description> - </sdk:lib> - <sdk:lib> - <!-- sdk:description is optional, name is not --> - <sdk:name>com.android.mymaps</sdk:name> - </sdk:lib> - </sdk:libs> - <sdk:layoutlib> - <sdk:api>5</sdk:api> - <sdk:revision>0</sdk:revision> - </sdk:layoutlib> - </sdk:add-on> - - <sdk:add-on> - <sdk:name-id>My_Second_add-on</sdk:name-id> - <sdk:name-display>My Second add-on</sdk:name-display> - - <sdk:vendor-id>John_Deer</sdk:vendor-id> - <sdk:vendor-display>John Deer</sdk:vendor-display> - - <sdk:api-level>2</sdk:api-level> - <sdk:revision>42</sdk:revision> - <sdk:archives> - <sdk:archive os="windows"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/second-42-win.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/second-42-linux.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:libs> - <sdk:lib> - <sdk:name>android.blah.somelib</sdk:name> - <sdk:description>The description for this library.</sdk:description> - </sdk:lib> - <sdk:lib> - <sdk:name>com.android.mymaps</sdk:name> - </sdk:lib> - </sdk:libs> - <sdk:uses-license ref="license2" /> - <!-- No layoutlib element in this package. It's optional. --> - </sdk:add-on> - - <sdk:add-on> - <sdk:name-id>no_libs</sdk:name-id> - <sdk:name-display>This add-on has no libraries</sdk:name-display> - - <sdk:vendor-id>Joe_Bar</sdk:vendor-id> - <sdk:vendor-display>Joe Bar</sdk:vendor-display> - - <sdk:uses-license ref="license2" /> - <sdk:api-level>4</sdk:api-level> - <sdk:revision>3</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/imnotanarchiveimadoctorjim.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <!-- The libs node is mandatory, however it can be empty. --> - <sdk:libs /> - <sdk:layoutlib> - <sdk:api>3</sdk:api> - <sdk:revision>42</sdk:revision> - </sdk:layoutlib> - </sdk:add-on> - - <sdk:extra> - <sdk:name-display>Random name, not an id!</sdk:name-display> - - <sdk:vendor-id>cyclop</sdk:vendor-id> - <sdk:vendor-display>The big bus</sdk:vendor-display> - - <sdk:path>usb_driver</sdk:path> - <sdk:uses-license ref="license2" /> - <sdk:revision>43</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/extraduff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>An Extra package for the USB driver, it will install in $SDK/usb_driver</sdk:description> - <sdk:desc-url>http://www.example.com/extra.html</sdk:desc-url> - <sdk:min-tools-rev>3</sdk:min-tools-rev> - <sdk:obsolete/> - </sdk:extra> - - <sdk:extra> - <sdk:name-display>Yet another extra, by Android</sdk:name-display> - - <sdk:vendor-id>android_vendor</sdk:vendor-id> - <sdk:vendor-display>Android Vendor</sdk:vendor-display> - - <sdk:path>extra_api_dep</sdk:path> - <sdk:uses-license ref="license2" /> - <sdk:revision>2</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/extra_mega_duff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>Some extra package that has a min-api-level of 42</sdk:description> - <sdk:desc-url>http://www.example.com/extra.html</sdk:desc-url> - <sdk:min-tools-rev>3</sdk:min-tools-rev> - <sdk:min-api-level>42</sdk:min-api-level> - <sdk:project-files> - <sdk:path>v8/veggies_8.jar</sdk:path> - <sdk:path>root.jar</sdk:path> - <sdk:path>dir1/dir 2 with space/mylib.jar</sdk:path> - </sdk:project-files> - <sdk:old-paths>path1;old_path2;oldPath3</sdk:old-paths> - </sdk:extra> - - <sdk:extra> - <sdk:name-display>. -..- - .-. .-</sdk:name-display> - - <sdk:vendor-id>____</sdk:vendor-id> - <sdk:vendor-display>____</sdk:vendor-display> - - <sdk:path>____</sdk:path> - <sdk:uses-license ref="license2" /> - <sdk:revision>2</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/extra_mega_duff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>Some extra package that has a min-api-level of 42</sdk:description> - <sdk:desc-url>http://www.example.com/extra.html</sdk:desc-url> - <sdk:min-tools-rev>3</sdk:min-tools-rev> - <sdk:min-api-level>42</sdk:min-api-level> - <sdk:obsolete></sdk:obsolete> - <!-- No project-files element in this package. --> - </sdk:extra> - -</sdk:sdk-addon> diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/addon_sample_5.xml b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/addon_sample_5.xml deleted file mode 100755 index 47b37be..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/addon_sample_5.xml +++ /dev/null @@ -1,214 +0,0 @@ -<?xml version="1.0"?> -<!-- - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<sdk:sdk-addon - xmlns:sdk="http://schemas.android.com/sdk/android/addon/5"> - - <!-- Define a couple of licenses. These will be referenced by uses-license later. --> - - <sdk:license type="text" id="license1"> - This is the license - for this platform. - </sdk:license> - - <sdk:license id="license2"> - Licenses are only of type 'text' right now, so this is implied. - </sdk:license> - - <!-- Inner elements must be either platform, add-on, doc or tool. - There can be 0 or more of each, in any order. --> - - <sdk:add-on> - <sdk:name-id>My_First_add-on</sdk:name-id> - <sdk:name-display>My First add-on</sdk:name-display> - - <sdk:vendor-id>John_Doe</sdk:vendor-id> - <sdk:vendor-display>John Doe</sdk:vendor-display> - - <sdk:api-level>1</sdk:api-level> - <sdk:revision>1</sdk:revision> - <sdk:uses-license ref="license2" /> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/myfirstaddon</sdk:desc-url> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/add-ons/first.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <!-- The libs node is mandatory, however it can be empty. --> - <sdk:libs> - <sdk:lib> - <sdk:name>android.blah.somelib</sdk:name> - <sdk:description>The description for this library.</sdk:description> - </sdk:lib> - <sdk:lib> - <!-- sdk:description is optional, name is not --> - <sdk:name>com.android.mymaps</sdk:name> - </sdk:lib> - </sdk:libs> - <sdk:layoutlib> - <sdk:api>5</sdk:api> - <sdk:revision>0</sdk:revision> - </sdk:layoutlib> - </sdk:add-on> - - <sdk:add-on> - <sdk:name-id>My_Second_add-on</sdk:name-id> - <sdk:name-display>My Second add-on</sdk:name-display> - - <sdk:vendor-id>John_Deer</sdk:vendor-id> - <sdk:vendor-display>John Deer</sdk:vendor-display> - - <sdk:api-level>2</sdk:api-level> - <sdk:revision>42</sdk:revision> - <sdk:archives> - <sdk:archive os="windows"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/second-42-win.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/second-42-linux.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:libs> - <sdk:lib> - <sdk:name>android.blah.somelib</sdk:name> - <sdk:description>The description for this library.</sdk:description> - </sdk:lib> - <sdk:lib> - <sdk:name>com.android.mymaps</sdk:name> - </sdk:lib> - </sdk:libs> - <sdk:uses-license ref="license2" /> - <!-- No layoutlib element in this package. It's optional. --> - </sdk:add-on> - - <sdk:add-on> - <sdk:name-id>no_libs</sdk:name-id> - <sdk:name-display>This add-on has no libraries</sdk:name-display> - - <sdk:vendor-id>Joe_Bar</sdk:vendor-id> - <sdk:vendor-display>Joe Bar</sdk:vendor-display> - - <sdk:uses-license ref="license2" /> - <sdk:api-level>4</sdk:api-level> - <sdk:revision>3</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/imnotanarchiveimadoctorjim.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <!-- The libs node is mandatory, however it can be empty. --> - <sdk:libs /> - <sdk:layoutlib> - <sdk:api>3</sdk:api> - <sdk:revision>42</sdk:revision> - </sdk:layoutlib> - </sdk:add-on> - - <sdk:extra> - <sdk:name-display>Random name, not an id!</sdk:name-display> - - <sdk:vendor-id>cyclop</sdk:vendor-id> - <sdk:vendor-display>The big bus</sdk:vendor-display> - - <sdk:path>usb_driver</sdk:path> - <sdk:uses-license ref="license2" /> - <sdk:revision>43</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/extraduff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>An Extra package for the USB driver, it will install in $SDK/usb_driver</sdk:description> - <sdk:desc-url>http://www.example.com/extra.html</sdk:desc-url> - <sdk:min-tools-rev> - <sdk:major>3</sdk:major> - <sdk:minor>2</sdk:minor> - <sdk:micro>1</sdk:micro> - <sdk:preview>42</sdk:preview> - </sdk:min-tools-rev> - <sdk:obsolete/> - </sdk:extra> - - <sdk:extra> - <sdk:name-display>Yet another extra, by Android</sdk:name-display> - - <sdk:vendor-id>android_vendor</sdk:vendor-id> - <sdk:vendor-display>Android Vendor</sdk:vendor-display> - - <sdk:path>extra_api_dep</sdk:path> - <sdk:uses-license ref="license2" /> - <sdk:revision>2</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/extra_mega_duff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>Some extra package that has a min-api-level of 42</sdk:description> - <sdk:desc-url>http://www.example.com/extra.html</sdk:desc-url> - <sdk:min-tools-rev> - <sdk:major>3</sdk:major> - </sdk:min-tools-rev> - <sdk:min-api-level>42</sdk:min-api-level> - <sdk:project-files> - <sdk:path>v8/veggies_8.jar</sdk:path> - <sdk:path>root.jar</sdk:path> - <sdk:path>dir1/dir 2 with space/mylib.jar</sdk:path> - </sdk:project-files> - <sdk:old-paths>path1;old_path2;oldPath3</sdk:old-paths> - </sdk:extra> - - <sdk:extra> - <sdk:name-display>. -..- - .-. .-</sdk:name-display> - - <sdk:vendor-id>____</sdk:vendor-id> - <sdk:vendor-display>____</sdk:vendor-display> - - <sdk:path>____</sdk:path> - <sdk:uses-license ref="license2" /> - <sdk:revision>2</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/extra_mega_duff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>Some extra package that has a min-api-level of 42</sdk:description> - <sdk:desc-url>http://www.example.com/extra.html</sdk:desc-url> - <sdk:min-tools-rev> - <sdk:major>3</sdk:major> - <!-- no minor, assumed to be 0 --> - <sdk:micro>1</sdk:micro> - </sdk:min-tools-rev> - <sdk:min-api-level>42</sdk:min-api-level> - <sdk:obsolete></sdk:obsolete> - <!-- No project-files element in this package. --> - </sdk:extra> - -</sdk:sdk-addon> diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/addons_list_sample_1.xml b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/addons_list_sample_1.xml deleted file mode 100755 index 5ea5cb8..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/addons_list_sample_1.xml +++ /dev/null @@ -1,43 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- - * Copyright (C) 2010 The Android Open Source Project - * - * Licensed under the Apache License, version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<sdk:sdk-addons-list - xmlns:sdk="http://schemas.android.com/sdk/android/addons-list/1"> - - <sdk:addon-site> - <sdk:url>http://www.example.com/my_addons.xml</sdk:url> - <sdk:name> <!-- we'll ignore leading/trailing spacing --> - My Example Add-ons. - </sdk:name> - </sdk:addon-site> - - <sdk:addon-site> - <sdk:url>http://www.example.co.jp/addons.xml</sdk:url> - <!-- this file is UTF-8 so we support character sets --> - <sdk:name>ありがとうございます。</sdk:name> - </sdk:addon-site> - - <sdk:addon-site> - <sdk:url>http://www.example.com/</sdk:url> - <sdk:name>Example of directory URL.</sdk:name> - </sdk:addon-site> - - <sdk:addon-site> - <sdk:url>relative_url.xml</sdk:url> - <sdk:name>Relative URL.</sdk:name> - </sdk:addon-site> - -</sdk:sdk-addons-list> diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/addons_list_sample_2.xml b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/addons_list_sample_2.xml deleted file mode 100755 index ef72b2c..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/addons_list_sample_2.xml +++ /dev/null @@ -1,53 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<sdk:sdk-addons-list - xmlns:sdk="http://schemas.android.com/sdk/android/addons-list/2"> - - <sdk:addon-site> - <sdk:url>http://www.example.com/my_addons.xml</sdk:url> - <sdk:name> <!-- we'll ignore leading/trailing spacing --> - My Example Add-ons. - </sdk:name> - </sdk:addon-site> - - <sdk:addon-site> - <sdk:url>http://www.example.co.jp/addons.xml</sdk:url> - <!-- this file is UTF-8 so we support character sets --> - <sdk:name>ありがとうございます。</sdk:name> - </sdk:addon-site> - - <sdk:addon-site> - <sdk:url>http://www.example.com/</sdk:url> - <sdk:name>Example of directory URL.</sdk:name> - </sdk:addon-site> - - <sdk:sys-img-site> - <sdk:url>http://www.example.com/</sdk:url> - <sdk:name>Example of sys-img URL using the default xml filename.</sdk:name> - </sdk:sys-img-site> - - <sdk:sys-img-site> - <sdk:url>http://www.example.com/specific_file.xml</sdk:url> - <sdk:name>Example of sys-img URL using a specific xml filename.</sdk:name> - </sdk:sys-img-site> - - <sdk:addon-site> - <sdk:url>relative/url.xml</sdk:url> - <sdk:name>Relative URL.</sdk:name> - </sdk:addon-site> - -</sdk:sdk-addons-list> diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/repository_sample_1.xml b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/repository_sample_1.xml deleted file mode 100755 index 7e2bc36..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/repository_sample_1.xml +++ /dev/null @@ -1,274 +0,0 @@ -<?xml version="1.0"?> -<!-- - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<sdk:sdk-repository - xmlns:sdk="http://schemas.android.com/sdk/android/repository/1"> - - <!-- Define a couple of licenses. These will be referenced by uses-license later. --> - - <sdk:license type="text" id="license1"> - This is the license - for this platform. - </sdk:license> - - <sdk:license id="license2"> - Licenses are only of type 'text' right now, so this is implied. - </sdk:license> - - <!-- Inner elements must be either platform, add-on, doc or tool. - There can be 0 or more of each, in any order. --> - - <sdk:platform> - <sdk:version>1.0</sdk:version> - <sdk:api-level>1</sdk:api-level> - <sdk:revision>3</sdk:revision> - <sdk:uses-license ref="license1" /> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/platform1.html</sdk:desc-url> - <sdk:release-note>This is an optional release note - for this package. It's a free multi-line text. - </sdk:release-note> - <sdk:release-url>http://some/url/for/the/release/note.html</sdk:release-url> - <sdk:min-tools-rev>2</sdk:min-tools-rev> - <!-- The archives node is mandatory and it cannot be empty. --> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/files/plat1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:platform> - - <sdk:doc> - <sdk:api-level>1</sdk:api-level> - <sdk:revision>1</sdk:revision> - <!-- the license element is not mandatory. --> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/docs.html</sdk:desc-url> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/docs/docs1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:doc> - - <sdk:add-on> - <sdk:name>My First add-on</sdk:name> - <sdk:api-level>1</sdk:api-level> - <sdk:vendor>John Doe</sdk:vendor> - <sdk:revision>1</sdk:revision> - <sdk:uses-license ref="license2" /> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/myfirstaddon</sdk:desc-url> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/add-ons/first.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <!-- The libs node is mandatory, however it can be empty. --> - <sdk:libs> - <sdk:lib> - <sdk:name>android.blah.somelib</sdk:name> - <sdk:description>The description for this library.</sdk:description> - </sdk:lib> - <sdk:lib> - <!-- sdk:description is optional, name is not --> - <sdk:name>com.android.mymaps</sdk:name> - </sdk:lib> - </sdk:libs> - </sdk:add-on> - - <sdk:platform> - <sdk:version>1.1</sdk:version> - <sdk:api-level>2</sdk:api-level> - <sdk:revision>12</sdk:revision> - <sdk:uses-license ref="license1" /> - <!-- sdk:description and sdk:desc-url are optional --> - <sdk:archives> - <sdk:archive os="windows"> - <!-- arch attribute is optional --> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-win.zip</sdk:url> - </sdk:archive> - <sdk:archive os="macosx" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-mac.zip</sdk:url> - </sdk:archive> - <sdk:archive os="macosx" arch="ppc"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-mac.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux" arch="x86"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-linux.tar.bz2</sdk:url> - </sdk:archive> - <sdk:archive os="linux" arch="x86_64"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-linux.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:platform> - - <sdk:add-on> - <sdk:name>My Second add-on</sdk:name> - <sdk:api-level>2</sdk:api-level> - <sdk:vendor>John Deer</sdk:vendor> - <sdk:revision>42</sdk:revision> - <sdk:archives> - <sdk:archive os="windows"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/second-42-win.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/second-42-linux.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:libs> - <sdk:lib> - <sdk:name>android.blah.somelib</sdk:name> - <sdk:description>The description for this library.</sdk:description> - </sdk:lib> - <sdk:lib> - <sdk:name>com.android.mymaps</sdk:name> - </sdk:lib> - </sdk:libs> - <sdk:uses-license ref="license2" /> - </sdk:add-on> - - <sdk:platform> - <sdk:version>Pastry</sdk:version> - <sdk:api-level>5</sdk:api-level> - <sdk:codename>Pastry</sdk:codename> - <sdk:revision>3</sdk:revision> - <sdk:uses-license ref="license1" /> - <sdk:description>Preview version for Pastry</sdk:description> - <sdk:desc-url>http://www.example.com/platform1.html</sdk:desc-url> - <!-- The archives node is mandatory and it cannot be empty. --> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/files/plat1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:platform> - - <sdk:tool> - <sdk:revision>1</sdk:revision> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/tools.html</sdk:desc-url> - <sdk:uses-license ref="license1" /> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/files/tools1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:tool> - - <sdk:doc> - <sdk:api-level>2</sdk:api-level> - <sdk:revision>42</sdk:revision> - <sdk:uses-license ref="license2" /> - <sdk:archives> - <sdk:archive os="windows"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/docs/2.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/docs2-linux.tar.bz2</sdk:url> - </sdk:archive> - <sdk:archive os="macosx"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/docs2-mac.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:doc> - - <sdk:tool> - <sdk:revision>42</sdk:revision> - <sdk:uses-license ref="license1" /> - <sdk:archives> - <sdk:archive os="windows"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/tools/2.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/tools2-linux.tar.bz2</sdk:url> - </sdk:archive> - <sdk:archive os="macosx"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/tools2-mac.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:tool> - - <sdk:add-on> - <sdk:uses-license ref="license2" /> - <sdk:name>This add-on has no libraries</sdk:name> - <sdk:api-level>4</sdk:api-level> - <sdk:vendor>Joe Bar</sdk:vendor> - <sdk:revision>3</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/imnotanarchiveimadoctorjim.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <!-- The libs node is mandatory, however it can be empty. --> - <sdk:libs /> - </sdk:add-on> - - <sdk:extra> - <sdk:path>usb_driver</sdk:path> - <sdk:uses-license ref="license2" /> - <sdk:revision>43</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/extraduff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>An Extra package for the USB driver, it will install in $SDK/usb_driver</sdk:description> - <sdk:desc-url>http://www.example.com/extra.html</sdk:desc-url> - <sdk:min-tools-rev>3</sdk:min-tools-rev> - </sdk:extra> - -</sdk:sdk-repository> diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/repository_sample_2.xml b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/repository_sample_2.xml deleted file mode 100755 index 6b2d679..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/repository_sample_2.xml +++ /dev/null @@ -1,309 +0,0 @@ -<?xml version="1.0"?> -<!-- - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<sdk:sdk-repository - xmlns:sdk="http://schemas.android.com/sdk/android/repository/2"> - - <!-- Define a couple of licenses. These will be referenced by uses-license later. --> - - <sdk:license type="text" id="license1"> - This is the license - for this platform. - </sdk:license> - - <sdk:license id="license2"> - Licenses are only of type 'text' right now, so this is implied. - </sdk:license> - - <!-- Inner elements must be either platform, add-on, doc or tool. - There can be 0 or more of each, in any order. --> - - <sdk:platform> - <sdk:version>1.0</sdk:version> - <sdk:api-level>1</sdk:api-level> - <sdk:revision>3</sdk:revision> - <sdk:uses-license ref="license1" /> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/platform1.html</sdk:desc-url> - <sdk:release-note>This is an optional release note - for this package. It's a free multi-line text. - </sdk:release-note> - <sdk:release-url>http://some/url/for/the/release/note.html</sdk:release-url> - <sdk:min-tools-rev>2</sdk:min-tools-rev> - <!-- The archives node is mandatory and it cannot be empty. --> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/files/plat1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:platform> - - <sdk:doc> - <sdk:api-level>1</sdk:api-level> - <sdk:revision>1</sdk:revision> - <!-- the license element is not mandatory. --> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/docs.html</sdk:desc-url> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/docs/docs1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:doc> - - <sdk:add-on> - <sdk:name>My First add-on</sdk:name> - <sdk:api-level>1</sdk:api-level> - <sdk:vendor>John Doe</sdk:vendor> - <sdk:revision>1</sdk:revision> - <sdk:uses-license ref="license2" /> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/myfirstaddon</sdk:desc-url> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/add-ons/first.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <!-- The libs node is mandatory, however it can be empty. --> - <sdk:libs> - <sdk:lib> - <sdk:name>android.blah.somelib</sdk:name> - <sdk:description>The description for this library.</sdk:description> - </sdk:lib> - <sdk:lib> - <!-- sdk:description is optional, name is not --> - <sdk:name>com.android.mymaps</sdk:name> - </sdk:lib> - </sdk:libs> - </sdk:add-on> - - <sdk:platform> - <sdk:version>1.1</sdk:version> - <sdk:api-level>2</sdk:api-level> - <sdk:revision>12</sdk:revision> - <sdk:uses-license ref="license1" /> - <!-- sdk:description and sdk:desc-url are optional --> - <sdk:archives> - <sdk:archive os="windows"> - <!-- arch attribute is optional --> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-win.zip</sdk:url> - </sdk:archive> - <sdk:archive os="macosx" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-mac.zip</sdk:url> - </sdk:archive> - <sdk:archive os="macosx" arch="ppc"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-mac.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux" arch="x86"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-linux.tar.bz2</sdk:url> - </sdk:archive> - <sdk:archive os="linux" arch="x86_64"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-linux.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:platform> - - <sdk:add-on> - <sdk:name>My Second add-on</sdk:name> - <sdk:api-level>2</sdk:api-level> - <sdk:vendor>John Deer</sdk:vendor> - <sdk:revision>42</sdk:revision> - <sdk:archives> - <sdk:archive os="windows"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/second-42-win.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/second-42-linux.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:libs> - <sdk:lib> - <sdk:name>android.blah.somelib</sdk:name> - <sdk:description>The description for this library.</sdk:description> - </sdk:lib> - <sdk:lib> - <sdk:name>com.android.mymaps</sdk:name> - </sdk:lib> - </sdk:libs> - <sdk:uses-license ref="license2" /> - </sdk:add-on> - - <sdk:platform> - <sdk:version>Pastry</sdk:version> - <sdk:api-level>5</sdk:api-level> - <sdk:codename>Pastry</sdk:codename> - <sdk:revision>3</sdk:revision> - <sdk:uses-license ref="license1" /> - <sdk:description>Preview version for Pastry</sdk:description> - <sdk:desc-url>http://www.example.com/platform1.html</sdk:desc-url> - <!-- The archives node is mandatory and it cannot be empty. --> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/files/plat1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:platform> - - <sdk:tool> - <sdk:revision>1</sdk:revision> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/tools.html</sdk:desc-url> - <sdk:uses-license ref="license1" /> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/files/tools1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:tool> - - <sdk:doc> - <sdk:api-level>2</sdk:api-level> - <sdk:revision>42</sdk:revision> - <sdk:uses-license ref="license2" /> - <sdk:archives> - <sdk:archive os="windows"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/docs/2.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/docs2-linux.tar.bz2</sdk:url> - </sdk:archive> - <sdk:archive os="macosx"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/docs2-mac.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:doc> - - <sdk:tool> - <sdk:revision>42</sdk:revision> - <sdk:uses-license ref="license1" /> - <sdk:archives> - <sdk:archive os="windows"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/tools/2.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/tools2-linux.tar.bz2</sdk:url> - </sdk:archive> - <sdk:archive os="macosx"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/tools2-mac.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:tool> - - <sdk:add-on> - <sdk:uses-license ref="license2" /> - <sdk:name>This add-on has no libraries</sdk:name> - <sdk:api-level>4</sdk:api-level> - <sdk:vendor>Joe Bar</sdk:vendor> - <sdk:revision>3</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/imnotanarchiveimadoctorjim.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <!-- The libs node is mandatory, however it can be empty. --> - <sdk:libs /> - </sdk:add-on> - - <sdk:extra> - <sdk:path>usb_driver</sdk:path> - <sdk:uses-license ref="license2" /> - <sdk:revision>43</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/extraduff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>An Extra package for the USB driver, it will install in $SDK/usb_driver</sdk:description> - <sdk:desc-url>http://www.example.com/extra.html</sdk:desc-url> - <sdk:min-tools-rev>3</sdk:min-tools-rev> - <sdk:obsolete/> - </sdk:extra> - - <sdk:extra> - <sdk:path>extra_api_dep</sdk:path> - <sdk:uses-license ref="license2" /> - <sdk:revision>2</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/extra_mega_duff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>Some extra package that has a min-api-level of 42</sdk:description> - <sdk:desc-url>http://www.example.com/extra.html</sdk:desc-url> - <sdk:min-tools-rev>3</sdk:min-tools-rev> - <sdk:min-api-level>42</sdk:min-api-level> - <sdk:obsolete></sdk:obsolete> - </sdk:extra> - - <sdk:sample> - <sdk:api-level>14</sdk:api-level> - <sdk:revision>24</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65537</sdk:size> - <sdk:checksum type="sha1">3822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/sample_duff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>Some sample package</sdk:description> - <sdk:desc-url>http://www.example.com/sample.html</sdk:desc-url> - <sdk:min-tools-rev>5</sdk:min-tools-rev> - <sdk:obsolete>This is obsolete</sdk:obsolete> - </sdk:sample> - -</sdk:sdk-repository> diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/repository_sample_3.xml b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/repository_sample_3.xml deleted file mode 100755 index 05a9c79..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/repository_sample_3.xml +++ /dev/null @@ -1,261 +0,0 @@ -<?xml version="1.0"?> -<!-- - * Copyright (C) 2010 The Android Open Source Project - * - * Licensed under the Apache License, version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<sdk:sdk-repository - xmlns:sdk="http://schemas.android.com/sdk/android/repository/3"> - - <!-- Define a couple of licenses. These will be referenced by uses-license later. --> - - <sdk:license type="text" id="license1"> - This is the license - for this platform. - </sdk:license> - - <sdk:license id="license2"> - Licenses are only of type 'text' right now, so this is implied. - </sdk:license> - - <!-- Inner elements must be either platform, add-on, doc or tool. - There can be 0 or more of each, in any order. --> - - <sdk:platform> - <sdk:version>1.0</sdk:version> - <sdk:api-level>1</sdk:api-level> - <sdk:revision>3</sdk:revision> - <sdk:uses-license ref="license1" /> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/platform1.html</sdk:desc-url> - <sdk:release-note>This is an optional release note - for this package. It's a free multi-line text. - </sdk:release-note> - <sdk:release-url>http://some/url/for/the/release/note.html</sdk:release-url> - <sdk:min-tools-rev>2</sdk:min-tools-rev> - <!-- The archives node is mandatory and it cannot be empty. --> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/files/plat1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:platform> - - <sdk:doc> - <sdk:api-level>1</sdk:api-level> - <sdk:revision>1</sdk:revision> - <!-- the license element is not mandatory. --> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/docs.html</sdk:desc-url> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/docs/docs1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:doc> - - <sdk:platform> - <sdk:version>1.1</sdk:version> - <sdk:api-level>2</sdk:api-level> - <sdk:revision>12</sdk:revision> - <sdk:uses-license ref="license1" /> - <!-- sdk:description and sdk:desc-url are optional --> - <sdk:archives> - <sdk:archive os="windows"> - <!-- arch attribute is optional --> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-win.zip</sdk:url> - </sdk:archive> - <sdk:archive os="macosx" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-mac.zip</sdk:url> - </sdk:archive> - <sdk:archive os="macosx" arch="ppc"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-mac.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux" arch="x86"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-linux.tar.bz2</sdk:url> - </sdk:archive> - <sdk:archive os="linux" arch="x86_64"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-linux.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:platform> - - <sdk:platform> - <sdk:version>Pastry</sdk:version> - <sdk:api-level>5</sdk:api-level> - <sdk:codename>Pastry</sdk:codename> - <sdk:revision>3</sdk:revision> - <sdk:uses-license ref="license1" /> - <sdk:description>Preview version for Pastry</sdk:description> - <sdk:desc-url>http://www.example.com/platform1.html</sdk:desc-url> - <!-- The archives node is mandatory and it cannot be empty. --> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/files/plat1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:platform> - - <sdk:tool> - <sdk:revision>1</sdk:revision> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/tools.html</sdk:desc-url> - <sdk:uses-license ref="license1" /> - <sdk:min-platform-tools-rev>4</sdk:min-platform-tools-rev> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/files/tools1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:tool> - - <sdk:doc> - <sdk:api-level>2</sdk:api-level> - <sdk:revision>42</sdk:revision> - <sdk:uses-license ref="license2" /> - <sdk:archives> - <sdk:archive os="windows"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/docs/2.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/docs2-linux.tar.bz2</sdk:url> - </sdk:archive> - <sdk:archive os="macosx"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/docs2-mac.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:doc> - - <sdk:tool> - <sdk:revision>42</sdk:revision> - <sdk:uses-license ref="license1" /> - <sdk:min-platform-tools-rev>3</sdk:min-platform-tools-rev> - <sdk:archives> - <sdk:archive os="windows"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/tools/2.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/tools2-linux.tar.bz2</sdk:url> - </sdk:archive> - <sdk:archive os="macosx"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/tools2-mac.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:tool> - - <sdk:platform-tool> - <sdk:revision>3</sdk:revision> - <sdk:uses-license ref="license1" /> - <sdk:archives> - <sdk:archive os="windows"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">3822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-tools/2.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">3822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-tools2-linux.tar.bz2</sdk:url> - </sdk:archive> - <sdk:archive os="macosx"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">3822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-tools2-mac.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:platform-tool> - - <sdk:extra> - <sdk:vendor>a</sdk:vendor> - <sdk:path>usb_driver</sdk:path> - <sdk:uses-license ref="license2" /> - <sdk:revision>43</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/extraduff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>An Extra package for the USB driver, it will install in $SDK/usb_driver</sdk:description> - <sdk:desc-url>http://www.example.com/extra.html</sdk:desc-url> - <sdk:min-tools-rev>3</sdk:min-tools-rev> - <sdk:obsolete/> - </sdk:extra> - - <sdk:extra> - <sdk:vendor>android_vendor</sdk:vendor> - <sdk:path>extra_api_dep</sdk:path> - <sdk:uses-license ref="license2" /> - <sdk:revision>2</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/extra_mega_duff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>Some extra package that has a min-api-level of 42</sdk:description> - <sdk:desc-url>http://www.example.com/extra.html</sdk:desc-url> - <sdk:min-tools-rev>3</sdk:min-tools-rev> - <sdk:min-api-level>42</sdk:min-api-level> - <sdk:obsolete></sdk:obsolete> - </sdk:extra> - - <sdk:sample> - <sdk:api-level>14</sdk:api-level> - <sdk:revision>24</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65537</sdk:size> - <sdk:checksum type="sha1">3822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/sample_duff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>Some sample package</sdk:description> - <sdk:desc-url>http://www.example.com/sample.html</sdk:desc-url> - <sdk:min-tools-rev>5</sdk:min-tools-rev> - <sdk:obsolete>This is obsolete</sdk:obsolete> - </sdk:sample> - -</sdk:sdk-repository> diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/repository_sample_4.xml b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/repository_sample_4.xml deleted file mode 100755 index f68b033..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/repository_sample_4.xml +++ /dev/null @@ -1,278 +0,0 @@ -<?xml version="1.0"?> -<!-- - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<sdk:sdk-repository - xmlns:sdk="http://schemas.android.com/sdk/android/repository/4"> - - <!-- Define a couple of licenses. These will be referenced by uses-license later. --> - - <sdk:license type="text" id="license1"> - This is the license - for this platform. - </sdk:license> - - <sdk:license id="license2"> - Licenses are only of type 'text' right now, so this is implied. - </sdk:license> - - <!-- Inner elements must be either platform, add-on, doc or tool. - There can be 0 or more of each, in any order. --> - - <sdk:platform> - <sdk:version>1.0</sdk:version> - <sdk:api-level>1</sdk:api-level> - <sdk:revision>3</sdk:revision> - <sdk:uses-license ref="license1" /> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/platform1.html</sdk:desc-url> - <sdk:release-note>This is an optional release note - for this package. It's a free multi-line text. - </sdk:release-note> - <sdk:release-url>http://some/url/for/the/release/note.html</sdk:release-url> - <sdk:min-tools-rev>2</sdk:min-tools-rev> - <!-- The archives node is mandatory and it cannot be empty. --> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/files/plat1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:layoutlib> - <sdk:api>5</sdk:api> - <sdk:revision>0</sdk:revision> - </sdk:layoutlib> - </sdk:platform> - - <sdk:doc> - <sdk:api-level>1</sdk:api-level> - <sdk:revision>1</sdk:revision> - <!-- the license element is not mandatory. --> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/docs.html</sdk:desc-url> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/docs/docs1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:doc> - - <sdk:platform> - <sdk:version>1.1</sdk:version> - <sdk:api-level>2</sdk:api-level> - <sdk:revision>12</sdk:revision> - <sdk:uses-license ref="license1" /> - <!-- sdk:description and sdk:desc-url are optional --> - <sdk:archives> - <sdk:archive os="windows"> - <!-- arch attribute is optional --> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-win.zip</sdk:url> - </sdk:archive> - <sdk:archive os="macosx" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-mac.zip</sdk:url> - </sdk:archive> - <sdk:archive os="macosx" arch="ppc"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-mac.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux" arch="x86"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-linux.tar.bz2</sdk:url> - </sdk:archive> - <sdk:archive os="linux" arch="x86_64"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-linux.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:layoutlib> - <sdk:api>5</sdk:api> - <sdk:revision>31415</sdk:revision> - </sdk:layoutlib> - </sdk:platform> - - <sdk:platform> - <sdk:version>Pastry</sdk:version> - <sdk:api-level>5</sdk:api-level> - <sdk:codename>Pastry</sdk:codename> - <sdk:revision>3</sdk:revision> - <sdk:uses-license ref="license1" /> - <sdk:description>Preview version for Pastry</sdk:description> - <sdk:desc-url>http://www.example.com/platform1.html</sdk:desc-url> - <!-- The archives node is mandatory and it cannot be empty. --> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/files/plat1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:layoutlib> - <sdk:api>1</sdk:api> - </sdk:layoutlib> - </sdk:platform> - - <sdk:tool> - <sdk:revision>1</sdk:revision> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/tools.html</sdk:desc-url> - <sdk:uses-license ref="license1" /> - <sdk:min-platform-tools-rev>4</sdk:min-platform-tools-rev> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/files/tools1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:tool> - - <sdk:doc> - <sdk:api-level>2</sdk:api-level> - <sdk:revision>42</sdk:revision> - <sdk:uses-license ref="license2" /> - <sdk:archives> - <sdk:archive os="windows"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/docs/2.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/docs2-linux.tar.bz2</sdk:url> - </sdk:archive> - <sdk:archive os="macosx"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/docs2-mac.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:doc> - - <sdk:tool> - <sdk:revision>42</sdk:revision> - <sdk:uses-license ref="license1" /> - <sdk:min-platform-tools-rev>3</sdk:min-platform-tools-rev> - <sdk:archives> - <sdk:archive os="windows"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/tools/2.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/tools2-linux.tar.bz2</sdk:url> - </sdk:archive> - <sdk:archive os="macosx"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/tools2-mac.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:tool> - - <sdk:platform-tool> - <sdk:revision>3</sdk:revision> - <sdk:uses-license ref="license1" /> - <sdk:archives> - <sdk:archive os="windows"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">3822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-tools/2.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">3822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-tools2-linux.tar.bz2</sdk:url> - </sdk:archive> - <sdk:archive os="macosx"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">3822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-tools2-mac.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:platform-tool> - - <sdk:extra> - <sdk:vendor>a</sdk:vendor> - <sdk:path>usb_driver</sdk:path> - <sdk:uses-license ref="license2" /> - <sdk:revision>43</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/extraduff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>An Extra package for the USB driver, it will install in $SDK/usb_driver</sdk:description> - <sdk:desc-url>http://www.example.com/extra.html</sdk:desc-url> - <sdk:min-tools-rev>3</sdk:min-tools-rev> - <sdk:obsolete/> - <!-- no project-files in this USB driver package. --> - </sdk:extra> - - <sdk:extra> - <sdk:vendor>android_vendor</sdk:vendor> - <sdk:path>extra_api_dep</sdk:path> - <sdk:uses-license ref="license2" /> - <sdk:revision>2</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/extra_mega_duff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>Some extra package that has a min-api-level of 42</sdk:description> - <sdk:desc-url>http://www.example.com/extra.html</sdk:desc-url> - <sdk:min-tools-rev>3</sdk:min-tools-rev> - <sdk:min-api-level>42</sdk:min-api-level> - <sdk:obsolete></sdk:obsolete> - <sdk:project-files> - <sdk:path>v8/veggies_8.jar</sdk:path> - <sdk:path>readme.txt</sdk:path> - <sdk:path>dir1/dir 2 with space/mylib.jar</sdk:path> - </sdk:project-files> - </sdk:extra> - - <sdk:sample> - <sdk:api-level>14</sdk:api-level> - <sdk:revision>24</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65537</sdk:size> - <sdk:checksum type="sha1">3822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/sample_duff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>Some sample package</sdk:description> - <sdk:desc-url>http://www.example.com/sample.html</sdk:desc-url> - <sdk:min-tools-rev>5</sdk:min-tools-rev> - <sdk:obsolete>This is obsolete</sdk:obsolete> - </sdk:sample> - -</sdk:sdk-repository> diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/repository_sample_5.xml b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/repository_sample_5.xml deleted file mode 100755 index 471550e..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/repository_sample_5.xml +++ /dev/null @@ -1,356 +0,0 @@ -<?xml version="1.0"?> -<!-- - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<sdk:sdk-repository - xmlns:sdk="http://schemas.android.com/sdk/android/repository/5"> - - <!-- Define a couple of licenses. These will be referenced by uses-license later. --> - - <sdk:license type="text" id="license1"> - This is the license - for this platform. - </sdk:license> - - <sdk:license id="license2"> - Licenses are only of type 'text' right now, so this is implied. - </sdk:license> - - <!-- Inner elements must be either platform, add-on, doc or tool. - There can be 0 or more of each, in any order. --> - - <sdk:platform> - <sdk:version>1.0</sdk:version> - <sdk:api-level>1</sdk:api-level> - <sdk:revision>3</sdk:revision> - <sdk:uses-license ref="license1" /> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/platform1.html</sdk:desc-url> - <sdk:release-note>This is an optional release note - for this package. It's a free multi-line text. - </sdk:release-note> - <sdk:release-url>http://some/url/for/the/release/note.html</sdk:release-url> - <sdk:min-tools-rev>2</sdk:min-tools-rev> - <!-- The archives node is mandatory and it cannot be empty. --> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/files/plat1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:layoutlib> - <sdk:api>5</sdk:api> - <sdk:revision>0</sdk:revision> - </sdk:layoutlib> - <sdk:included-abi>armeabi</sdk:included-abi> - </sdk:platform> - - <sdk:doc> - <sdk:api-level>1</sdk:api-level> - <sdk:revision>1</sdk:revision> - <!-- the license element is not mandatory. --> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/docs.html</sdk:desc-url> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/docs/docs1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:doc> - - <sdk:source> - <sdk:api-level>1</sdk:api-level> - <sdk:revision>1</sdk:revision> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65535</sdk:size> - <sdk:checksum type="sha1">1234ae37115ebf13412bbef91339ee0d94541234</sdk:checksum> - <sdk:url>http://www.example.com/plat1/sources1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:source> - - <sdk:platform> - <sdk:version>1.1</sdk:version> - <sdk:api-level>2</sdk:api-level> - <sdk:revision>12</sdk:revision> - <sdk:uses-license ref="license1" /> - <!-- sdk:description and sdk:desc-url are optional --> - <sdk:archives> - <sdk:archive os="windows"> - <!-- arch attribute is optional --> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-win.zip</sdk:url> - </sdk:archive> - <sdk:archive os="macosx" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-mac.zip</sdk:url> - </sdk:archive> - <sdk:archive os="macosx" arch="ppc"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-mac.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux" arch="x86"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-linux.tar.bz2</sdk:url> - </sdk:archive> - <sdk:archive os="linux" arch="x86_64"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-linux.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:layoutlib> - <sdk:api>5</sdk:api> - <sdk:revision>31415</sdk:revision> - </sdk:layoutlib> - <sdk:included-abi>x86</sdk:included-abi> - </sdk:platform> - - <sdk:system-image> - <sdk:api-level>2</sdk:api-level> - <sdk:revision>1</sdk:revision> - <sdk:abi>x86</sdk:abi> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65535</sdk:size> - <sdk:checksum type="sha1">1234ae37115ebf13412bbef91339ee0d94541234</sdk:checksum> - <sdk:url>http://www.example.com/plat1/x86/image1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:system-image> - - <sdk:system-image> - <sdk:api-level>2</sdk:api-level> - <sdk:revision>2</sdk:revision> - <sdk:abi>armeabi-v7a</sdk:abi> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65534</sdk:size> - <sdk:checksum type="sha1">1234ae37115ebf13412bbef91339ee0d94541234</sdk:checksum> - <sdk:url>http://www.example.com/plat1/armv7/image2.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:system-image> - - <sdk:source> - <sdk:api-level>2</sdk:api-level> - <sdk:revision>2</sdk:revision> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65534</sdk:size> - <sdk:checksum type="sha1">1234ae37115ebf13412bbef91339ee0d94541234</sdk:checksum> - <sdk:url>http://www.example.com/plat1/sources2.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:source> - - <sdk:platform> - <sdk:version>Pastry</sdk:version> - <sdk:api-level>5</sdk:api-level> - <sdk:codename>Pastry</sdk:codename> - <sdk:revision>3</sdk:revision> - <sdk:uses-license ref="license1" /> - <sdk:description>Preview version for Pastry</sdk:description> - <sdk:desc-url>http://www.example.com/platform1.html</sdk:desc-url> - <!-- The archives node is mandatory and it cannot be empty. --> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/files/plat1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:layoutlib> - <sdk:api>1</sdk:api> - </sdk:layoutlib> - </sdk:platform> - - <sdk:tool> - <sdk:revision>1</sdk:revision> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/tools.html</sdk:desc-url> - <sdk:uses-license ref="license1" /> - <sdk:min-platform-tools-rev>4</sdk:min-platform-tools-rev> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/files/tools1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:tool> - - <sdk:doc> - <sdk:api-level>2</sdk:api-level> - <sdk:revision>42</sdk:revision> - <sdk:uses-license ref="license2" /> - <sdk:archives> - <sdk:archive os="windows"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/docs/2.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/docs2-linux.tar.bz2</sdk:url> - </sdk:archive> - <sdk:archive os="macosx"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/docs2-mac.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:doc> - - <sdk:tool> - <sdk:revision>42</sdk:revision> - <sdk:uses-license ref="license1" /> - <sdk:min-platform-tools-rev>3</sdk:min-platform-tools-rev> - <sdk:archives> - <sdk:archive os="windows"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/tools/2.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/tools2-linux.tar.bz2</sdk:url> - </sdk:archive> - <sdk:archive os="macosx"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/tools2-mac.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:tool> - - <sdk:platform-tool> - <sdk:revision>3</sdk:revision> - <sdk:uses-license ref="license1" /> - <sdk:archives> - <sdk:archive os="windows"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">3822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-tools/2.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">3822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-tools2-linux.tar.bz2</sdk:url> - </sdk:archive> - <sdk:archive os="macosx"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">3822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-tools2-mac.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:platform-tool> - - <sdk:extra> - <sdk:vendor>a</sdk:vendor> - <sdk:path>usb_driver</sdk:path> - <sdk:uses-license ref="license2" /> - <sdk:revision>43</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/extraduff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>An Extra package for the USB driver, it will install in $SDK/usb_driver</sdk:description> - <sdk:desc-url>http://www.example.com/extra.html</sdk:desc-url> - <sdk:min-tools-rev>3</sdk:min-tools-rev> - <sdk:obsolete/> - <!-- no project-files in this USB driver package. --> - </sdk:extra> - - <sdk:extra> - <sdk:vendor>android_vendor</sdk:vendor> - <sdk:path>extra_api_dep</sdk:path> - <sdk:uses-license ref="license2" /> - <sdk:revision>2</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/extra_mega_duff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>Some extra package that has a min-api-level of 42</sdk:description> - <sdk:desc-url>http://www.example.com/extra.html</sdk:desc-url> - <sdk:min-tools-rev>3</sdk:min-tools-rev> - <sdk:min-api-level>42</sdk:min-api-level> - <sdk:obsolete></sdk:obsolete> - <sdk:project-files> - <sdk:path>v8/veggies_8.jar</sdk:path> - <sdk:path>readme.txt</sdk:path> - <sdk:path>dir1/dir 2 with space/mylib.jar</sdk:path> - </sdk:project-files> - <sdk:old-paths>path1;old_path2;oldPath3</sdk:old-paths> - </sdk:extra> - - <sdk:sample> - <sdk:api-level>14</sdk:api-level> - <sdk:revision>24</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65537</sdk:size> - <sdk:checksum type="sha1">3822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/sample_duff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>Some sample package</sdk:description> - <sdk:desc-url>http://www.example.com/sample.html</sdk:desc-url> - <sdk:min-tools-rev>5</sdk:min-tools-rev> - <sdk:obsolete>This is obsolete</sdk:obsolete> - </sdk:sample> - - <sdk:system-image> - <sdk:api-level>42</sdk:api-level> - <sdk:revision>12</sdk:revision> - <sdk:abi>armeabi</sdk:abi> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>1234</sdk:size> - <sdk:checksum type="sha1">12345637115ebf13412bbef91339ee0d94541234</sdk:checksum> - <sdk:url>http://www.example.com/plat42/86/image12.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:system-image> - - <sdk:source> - <sdk:api-level>42</sdk:api-level> - <sdk:revision>12</sdk:revision> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>1234</sdk:size> - <sdk:checksum type="sha1">12345637115ebf13412bbef91339ee0d94541234</sdk:checksum> - <sdk:url>http://www.example.com/plat42/source12.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:source> - -</sdk:sdk-repository> diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/repository_sample_6.xml b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/repository_sample_6.xml deleted file mode 100755 index 12be591..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/repository_sample_6.xml +++ /dev/null @@ -1,325 +0,0 @@ -<?xml version="1.0"?> -<!-- - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<sdk:sdk-repository - xmlns:sdk="http://schemas.android.com/sdk/android/repository/6"> - - <!-- Define a couple of licenses. These will be referenced by uses-license later. --> - - <sdk:license type="text" id="license1"> - This is the license - for this platform. - </sdk:license> - - <sdk:license id="license2"> - Licenses are only of type 'text' right now, so this is implied. - </sdk:license> - - <!-- Inner elements must be either platform, add-on, doc or tool. - There can be 0 or more of each, in any order. --> - - <sdk:platform> - <sdk:version>1.0</sdk:version> - <sdk:api-level>1</sdk:api-level> - <sdk:revision>3</sdk:revision> - <sdk:uses-license ref="license1" /> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/platform1.html</sdk:desc-url> - <sdk:release-note>This is an optional release note - for this package. It's a free multi-line text. - </sdk:release-note> - <sdk:release-url>http://some/url/for/the/release/note.html</sdk:release-url> - <sdk:min-tools-rev>2</sdk:min-tools-rev> - <!-- The archives node is mandatory and it cannot be empty. --> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/files/plat1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:layoutlib> - <sdk:api>5</sdk:api> - <sdk:revision>0</sdk:revision> - </sdk:layoutlib> - <sdk:included-abi>armeabi</sdk:included-abi> - </sdk:platform> - - <sdk:doc> - <sdk:api-level>1</sdk:api-level> - <sdk:revision>1</sdk:revision> - <!-- the license element is not mandatory. --> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/docs.html</sdk:desc-url> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/docs/docs1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:doc> - - <sdk:source> - <sdk:api-level>1</sdk:api-level> - <sdk:revision>1</sdk:revision> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65535</sdk:size> - <sdk:checksum type="sha1">1234ae37115ebf13412bbef91339ee0d94541234</sdk:checksum> - <sdk:url>http://www.example.com/plat1/sources1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:source> - - <sdk:platform> - <sdk:version>1.1</sdk:version> - <sdk:api-level>2</sdk:api-level> - <sdk:revision>12</sdk:revision> - <sdk:uses-license ref="license1" /> - <!-- sdk:description and sdk:desc-url are optional --> - <sdk:archives> - <sdk:archive os="windows"> - <!-- arch attribute is optional --> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-win.zip</sdk:url> - </sdk:archive> - <sdk:archive os="macosx" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-mac.zip</sdk:url> - </sdk:archive> - <sdk:archive os="macosx" arch="ppc"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-mac.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux" arch="x86"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-linux.tar.bz2</sdk:url> - </sdk:archive> - <sdk:archive os="linux" arch="x86_64"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-linux.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:layoutlib> - <sdk:api>5</sdk:api> - <sdk:revision>31415</sdk:revision> - </sdk:layoutlib> - <sdk:included-abi>x86</sdk:included-abi> - </sdk:platform> - - <sdk:system-image> - <sdk:api-level>2</sdk:api-level> - <sdk:revision>1</sdk:revision> - <sdk:abi>x86</sdk:abi> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65535</sdk:size> - <sdk:checksum type="sha1">1234ae37115ebf13412bbef91339ee0d94541234</sdk:checksum> - <sdk:url>http://www.example.com/plat1/x86/image1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:system-image> - - <sdk:system-image> - <sdk:api-level>2</sdk:api-level> - <sdk:revision>2</sdk:revision> - <sdk:abi>armeabi-v7a</sdk:abi> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65534</sdk:size> - <sdk:checksum type="sha1">1234ae37115ebf13412bbef91339ee0d94541234</sdk:checksum> - <sdk:url>http://www.example.com/plat1/armv7/image2.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:system-image> - - <sdk:source> - <sdk:api-level>2</sdk:api-level> - <sdk:revision>2</sdk:revision> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65534</sdk:size> - <sdk:checksum type="sha1">1234ae37115ebf13412bbef91339ee0d94541234</sdk:checksum> - <sdk:url>http://www.example.com/plat1/sources2.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:source> - - <sdk:platform> - <sdk:version>Pastry</sdk:version> - <sdk:api-level>5</sdk:api-level> - <sdk:codename>Pastry</sdk:codename> - <sdk:revision>3</sdk:revision> - <sdk:uses-license ref="license1" /> - <sdk:description>Preview version for Pastry</sdk:description> - <sdk:desc-url>http://www.example.com/platform1.html</sdk:desc-url> - <!-- The archives node is mandatory and it cannot be empty. --> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/files/plat1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:layoutlib> - <sdk:api>1</sdk:api> - </sdk:layoutlib> - </sdk:platform> - - <sdk:tool> - <sdk:revision>1</sdk:revision> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/tools.html</sdk:desc-url> - <sdk:uses-license ref="license1" /> - <sdk:min-platform-tools-rev>4</sdk:min-platform-tools-rev> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/files/tools1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:tool> - - <sdk:doc> - <sdk:api-level>2</sdk:api-level> - <sdk:revision>42</sdk:revision> - <sdk:uses-license ref="license2" /> - <sdk:archives> - <sdk:archive os="windows"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/docs/2.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/docs2-linux.tar.bz2</sdk:url> - </sdk:archive> - <sdk:archive os="macosx"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/docs2-mac.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:doc> - - <sdk:tool> - <sdk:revision>42</sdk:revision> - <sdk:uses-license ref="license1" /> - <sdk:min-platform-tools-rev>3</sdk:min-platform-tools-rev> - <sdk:archives> - <sdk:archive os="windows"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/tools/2.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/tools2-linux.tar.bz2</sdk:url> - </sdk:archive> - <sdk:archive os="macosx"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/tools2-mac.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:tool> - - <sdk:platform-tool> - <sdk:revision>3</sdk:revision> - <sdk:uses-license ref="license1" /> - <sdk:archives> - <sdk:archive os="windows"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">3822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-tools/2.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">3822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-tools2-linux.tar.bz2</sdk:url> - </sdk:archive> - <sdk:archive os="macosx"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">3822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-tools2-mac.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:platform-tool> - - <sdk:sample> - <sdk:api-level>14</sdk:api-level> - <sdk:revision>24</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65537</sdk:size> - <sdk:checksum type="sha1">3822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/sample_duff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>Some sample package</sdk:description> - <sdk:desc-url>http://www.example.com/sample.html</sdk:desc-url> - <sdk:min-tools-rev>5</sdk:min-tools-rev> - <sdk:obsolete>This is obsolete</sdk:obsolete> - </sdk:sample> - - <sdk:system-image> - <sdk:api-level>42</sdk:api-level> - <sdk:revision>12</sdk:revision> - <sdk:abi>armeabi</sdk:abi> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>1234</sdk:size> - <sdk:checksum type="sha1">12345637115ebf13412bbef91339ee0d94541234</sdk:checksum> - <sdk:url>http://www.example.com/plat42/86/image12.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:system-image> - - <sdk:system-image> - <sdk:api-level>42</sdk:api-level> - <sdk:revision>12</sdk:revision> - <sdk:abi>mips</sdk:abi> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>12345</sdk:size> - <sdk:checksum type="sha1">12345637115ebf13412bbef91339ee0d94541234</sdk:checksum> - <sdk:url>http://www.example.com/plat42/mips/image12.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:system-image> - - <sdk:source> - <sdk:api-level>42</sdk:api-level> - <sdk:revision>12</sdk:revision> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>1234</sdk:size> - <sdk:checksum type="sha1">12345637115ebf13412bbef91339ee0d94541234</sdk:checksum> - <sdk:url>http://www.example.com/plat42/source12.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:source> - -</sdk:sdk-repository> diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/repository_sample_7.xml b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/repository_sample_7.xml deleted file mode 100755 index 401521b..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/repository_sample_7.xml +++ /dev/null @@ -1,371 +0,0 @@ -<?xml version="1.0"?> -<!-- - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<sdk:sdk-repository - xmlns:sdk="http://schemas.android.com/sdk/android/repository/7"> - - <!-- Define a couple of licenses. These will be referenced by uses-license later. --> - - <sdk:license type="text" id="license1"> - This is the license - for this platform. - </sdk:license> - - <sdk:license id="license2"> - Licenses are only of type 'text' right now, so this is implied. - </sdk:license> - - <!-- Inner elements must be either platform, add-on, doc or tool. - There can be 0 or more of each, in any order. --> - - <sdk:platform> - <sdk:version>1.0</sdk:version> - <sdk:api-level>1</sdk:api-level> - <sdk:revision>3</sdk:revision> - <sdk:uses-license ref="license1" /> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/platform1.html</sdk:desc-url> - <sdk:release-note>This is an optional release note - for this package. It's a free multi-line text. - </sdk:release-note> - <sdk:release-url>http://some/url/for/the/release/note.html</sdk:release-url> - <sdk:min-tools-rev> - <sdk:major>2</sdk:major> - <!-- minor is missing and equivalent to 0 --> - <sdk:micro>1</sdk:micro> - </sdk:min-tools-rev> - <!-- The archives node is mandatory and it cannot be empty. --> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/files/plat1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:layoutlib> - <sdk:api>5</sdk:api> - <sdk:revision>0</sdk:revision> - </sdk:layoutlib> - <sdk:included-abi>armeabi</sdk:included-abi> - </sdk:platform> - - <sdk:doc> - <sdk:api-level>1</sdk:api-level> - <sdk:revision>1</sdk:revision> - <!-- the license element is not mandatory. --> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/docs.html</sdk:desc-url> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/docs/docs1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:doc> - - <sdk:source> - <sdk:api-level>1</sdk:api-level> - <sdk:revision>1</sdk:revision> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65535</sdk:size> - <sdk:checksum type="sha1">1234ae37115ebf13412bbef91339ee0d94541234</sdk:checksum> - <sdk:url>http://www.example.com/plat1/sources1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:source> - - <sdk:platform> - <sdk:version>1.1</sdk:version> - <sdk:api-level>2</sdk:api-level> - <sdk:revision>12</sdk:revision> - <sdk:uses-license ref="license1" /> - <!-- sdk:description and sdk:desc-url are optional --> - <sdk:archives> - <sdk:archive os="windows"> - <!-- arch attribute is optional --> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-win.zip</sdk:url> - </sdk:archive> - <sdk:archive os="macosx" arch="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-mac.zip</sdk:url> - </sdk:archive> - <sdk:archive os="macosx" arch="ppc"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-mac.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux" arch="x86"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-linux.tar.bz2</sdk:url> - </sdk:archive> - <sdk:archive os="linux" arch="x86_64"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-2-12-linux.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:layoutlib> - <sdk:api>5</sdk:api> - <sdk:revision>31415</sdk:revision> - </sdk:layoutlib> - <sdk:included-abi>x86</sdk:included-abi> - </sdk:platform> - - <sdk:system-image> - <sdk:api-level>2</sdk:api-level> - <sdk:revision>1</sdk:revision> - <sdk:abi>x86</sdk:abi> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65535</sdk:size> - <sdk:checksum type="sha1">1234ae37115ebf13412bbef91339ee0d94541234</sdk:checksum> - <sdk:url>http://www.example.com/plat1/x86/image1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:system-image> - - <sdk:system-image> - <sdk:api-level>2</sdk:api-level> - <sdk:revision>2</sdk:revision> - <sdk:abi>armeabi-v7a</sdk:abi> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65534</sdk:size> - <sdk:checksum type="sha1">1234ae37115ebf13412bbef91339ee0d94541234</sdk:checksum> - <sdk:url>http://www.example.com/plat1/armv7/image2.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:system-image> - - <sdk:source> - <sdk:api-level>2</sdk:api-level> - <sdk:revision>2</sdk:revision> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65534</sdk:size> - <sdk:checksum type="sha1">1234ae37115ebf13412bbef91339ee0d94541234</sdk:checksum> - <sdk:url>http://www.example.com/plat1/sources2.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:source> - - <sdk:platform> - <sdk:version>Pastry</sdk:version> - <sdk:api-level>5</sdk:api-level> - <sdk:codename>Pastry</sdk:codename> - <sdk:revision>3</sdk:revision> - <sdk:uses-license ref="license1" /> - <sdk:description>Preview version for Pastry</sdk:description> - <sdk:desc-url>http://www.example.com/platform1.html</sdk:desc-url> - <!-- The archives node is mandatory and it cannot be empty. --> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/files/plat1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:layoutlib> - <sdk:api>1</sdk:api> - </sdk:layoutlib> - </sdk:platform> - - <sdk:tool> - <sdk:revision> - <sdk:major>1</sdk:major> - <sdk:minor>2</sdk:minor> - <sdk:micro>3</sdk:micro> - <sdk:preview>4</sdk:preview> - </sdk:revision> - <sdk:description>Some optional description</sdk:description> - <sdk:desc-url>http://www.example.com/tools.html</sdk:desc-url> - <sdk:uses-license ref="license1" /> - <sdk:min-platform-tools-rev> - <sdk:major>4</sdk:major> - </sdk:min-platform-tools-rev> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>http://www.example.com/files/tools1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:tool> - - <sdk:doc> - <sdk:api-level>2</sdk:api-level> - <sdk:revision>42</sdk:revision> - <sdk:uses-license ref="license2" /> - <sdk:archives> - <sdk:archive os="windows"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/docs/2.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/docs2-linux.tar.bz2</sdk:url> - </sdk:archive> - <sdk:archive os="macosx"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/docs2-mac.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:doc> - - <sdk:tool> - <sdk:revision> - <sdk:major>42</sdk:major> - </sdk:revision> - <sdk:uses-license ref="license1" /> - <sdk:min-platform-tools-rev> - <sdk:major>4</sdk:major> - <sdk:minor>0</sdk:minor> - <sdk:micro>0</sdk:micro> - <sdk:preview>5</sdk:preview> - </sdk:min-platform-tools-rev> - <sdk:archives> - <sdk:archive os="windows"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/tools/2.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/tools2-linux.tar.bz2</sdk:url> - </sdk:archive> - <sdk:archive os="macosx"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">2822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/tools2-mac.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:tool> - - <sdk:platform-tool> - <sdk:revision> - <sdk:major>3</sdk:major> - <sdk:minor>0</sdk:minor> - <sdk:micro>0</sdk:micro> - <sdk:preview>5</sdk:preview> - </sdk:revision> - <sdk:uses-license ref="license1" /> - <sdk:archives> - <sdk:archive os="windows"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">3822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-tools/2.zip</sdk:url> - </sdk:archive> - <sdk:archive os="linux"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">3822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-tools2-linux.tar.bz2</sdk:url> - </sdk:archive> - <sdk:archive os="macosx"> - <sdk:size>65536</sdk:size> - <sdk:checksum type="sha1">3822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/platform-tools2-mac.tar.bz2</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:platform-tool> - - <sdk:sample> - <sdk:api-level>14</sdk:api-level> - <sdk:revision>24</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65537</sdk:size> - <sdk:checksum type="sha1">3822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/sample_duff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>Some sample package</sdk:description> - <sdk:desc-url>http://www.example.com/sample.html</sdk:desc-url> - <sdk:min-tools-rev> - <sdk:major>5</sdk:major> - </sdk:min-tools-rev> - <sdk:obsolete>This is obsolete</sdk:obsolete> - </sdk:sample> - - <sdk:sample> - <sdk:api-level>14</sdk:api-level> - <sdk:revision>25</sdk:revision> - <sdk:archives> - <sdk:archive os="any" arch="any"> - <sdk:size>65537</sdk:size> - <sdk:checksum type="sha1">3822ae37115ebf13412bbef91339ee0d9454525e</sdk:checksum> - <sdk:url>distrib/sample_duff.zip</sdk:url> - </sdk:archive> - </sdk:archives> - <sdk:description>Some sample package</sdk:description> - <sdk:desc-url>http://www.example.com/sample.html</sdk:desc-url> - <sdk:min-tools-rev> - <sdk:major>5</sdk:major> - <sdk:minor>1</sdk:minor> - <sdk:micro>2</sdk:micro> - <sdk:preview>3</sdk:preview> - </sdk:min-tools-rev> - <sdk:obsolete>This is obsolete</sdk:obsolete> - </sdk:sample> - - <sdk:system-image> - <sdk:api-level>42</sdk:api-level> - <sdk:revision>12</sdk:revision> - <sdk:abi>armeabi</sdk:abi> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>1234</sdk:size> - <sdk:checksum type="sha1">12345637115ebf13412bbef91339ee0d94541234</sdk:checksum> - <sdk:url>http://www.example.com/plat42/86/image12.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:system-image> - - <sdk:system-image> - <sdk:api-level>42</sdk:api-level> - <sdk:revision>12</sdk:revision> - <sdk:abi>mips</sdk:abi> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>12345</sdk:size> - <sdk:checksum type="sha1">12345637115ebf13412bbef91339ee0d94541234</sdk:checksum> - <sdk:url>http://www.example.com/plat42/mips/image12.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:system-image> - - <sdk:source> - <sdk:api-level>42</sdk:api-level> - <sdk:revision>12</sdk:revision> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>1234</sdk:size> - <sdk:checksum type="sha1">12345637115ebf13412bbef91339ee0d94541234</sdk:checksum> - <sdk:url>http://www.example.com/plat42/source12.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:source> - -</sdk:sdk-repository> diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/stats_sample_1.xml b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/stats_sample_1.xml deleted file mode 100755 index 344b8a5..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/stats_sample_1.xml +++ /dev/null @@ -1,48 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<sdk:sdk-stats - xmlns:sdk="http://schemas.android.com/sdk/android/stats/1"> - - <sdk:platform> - <sdk:api-level>3</sdk:api-level> - <sdk:codename>Vanilla</sdk:codename> - <sdk:version>Android 0.5</sdk:version> - <sdk:share>0.1</sdk:share> - </sdk:platform> - - <sdk:platform> - <sdk:api-level>5</sdk:api-level> - <sdk:codename>Coffee</sdk:codename> - <sdk:version>Android 42.0</sdk:version> - <sdk:share>25.8</sdk:share> - </sdk:platform> - - <sdk:platform> - <sdk:api-level>42</sdk:api-level> - <sdk:codename>Chocolate</sdk:codename> - <sdk:version>Android 32.64</sdk:version> - <sdk:share>74.1</sdk:share> - </sdk:platform> - - <sdk:platform> - <sdk:api-level>5</sdk:api-level> - <sdk:codename>Ignored</sdk:codename> - <sdk:version>API 5 was already seen above</sdk:version> - <sdk:share>99.9</sdk:share> - </sdk:platform> - -</sdk:sdk-stats> diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/sys_img_sample_1.xml b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/sys_img_sample_1.xml deleted file mode 100755 index 6196db4..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/testdata/sys_img_sample_1.xml +++ /dev/null @@ -1,83 +0,0 @@ -<?xml version="1.0"?> -<!-- - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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. ---> -<sdk:sdk-sys-img - xmlns:sdk="http://schemas.android.com/sdk/android/sys-img/1"> - - <!-- Define a couple of licenses. These will be referenced by uses-license later. --> - - <sdk:license type="text" id="license1"> - This is the license - for this platform. - </sdk:license> - - <sdk:license id="license2"> - Licenses are only of type 'text' right now, so this is implied. - </sdk:license> - - <sdk:system-image> - <sdk:api-level>2</sdk:api-level> - <sdk:revision>1</sdk:revision> - <sdk:abi>x86</sdk:abi> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65535</sdk:size> - <sdk:checksum type="sha1">1234ae37115ebf13412bbef91339ee0d94541234</sdk:checksum> - <sdk:url>http://www.example.com/plat1/x86/image1.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:system-image> - - <sdk:system-image> - <sdk:api-level>2</sdk:api-level> - <sdk:revision>2</sdk:revision> - <sdk:abi>armeabi-v7a</sdk:abi> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>65534</sdk:size> - <sdk:checksum type="sha1">1234ae37115ebf13412bbef91339ee0d94541234</sdk:checksum> - <sdk:url>http://www.example.com/plat1/armv7/image2.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:system-image> - - <sdk:system-image> - <sdk:api-level>42</sdk:api-level> - <sdk:revision>12</sdk:revision> - <sdk:abi>armeabi</sdk:abi> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>1234</sdk:size> - <sdk:checksum type="sha1">12345637115ebf13412bbef91339ee0d94541234</sdk:checksum> - <sdk:url>http://www.example.com/plat42/86/image12.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:system-image> - - <sdk:system-image> - <sdk:api-level>42</sdk:api-level> - <sdk:revision>12</sdk:revision> - <sdk:abi>mips</sdk:abi> - <sdk:archives> - <sdk:archive os="any"> - <sdk:size>12345</sdk:size> - <sdk:checksum type="sha1">12345637115ebf13412bbef91339ee0d94541234</sdk:checksum> - <sdk:url>http://www.example.com/plat42/mips/image12.zip</sdk:url> - </sdk:archive> - </sdk:archives> - </sdk:system-image> - -</sdk:sdk-sys-img> diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/util/BSPatchTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/util/BSPatchTest.java deleted file mode 100755 index 6c6c405..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/util/BSPatchTest.java +++ /dev/null @@ -1,533 +0,0 @@ -/* - * Copyright (C) 2012 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.util; - -import org.apache.commons.compress.compressors.bzip2.BZip2CompressorInputStream; - -import java.io.ByteArrayInputStream; -import java.io.IOException; -import java.io.InputStream; -import java.util.Arrays; - -import junit.framework.TestCase; - - -public class BSPatchTest extends TestCase { - - // $ bsdiff file1 file2 diff-1-2.patch - // $ hexdump -v -e '1/1 "0x%02x, "' diff-1-2.patch - - public void testBSPatch1() throws Exception { - byte[] file1 = toSignedBytes(new short[] { - 0x62, 0x73, 0x64, 0x69, 0x66, 0x66, 0x20, 0x69, 0x73, 0x20, - 0x61, 0x20, 0x74, 0x6f, 0x6f, 0x6c, 0x20, 0x66, 0x6f, 0x72, - 0x20, 0x62, 0x75, 0x69, 0x6c, 0x64, 0x69, 0x6e, 0x67, 0x20, - 0x61, 0x6e, 0x64, 0x20, 0x61, 0x70, 0x70, 0x6c, 0x79, 0x69, - 0x6e, 0x67, 0x20, 0x70, 0x61, 0x74, 0x63, 0x68, 0x65, 0x73, - 0x20, 0x74, 0x6f, 0x20, 0x62, 0x69, 0x6e, 0x61, 0x72, 0x79, - 0x20, 0x66, 0x69, 0x6c, 0x65, 0x73, 0x2e, 0x0a - }); - - byte[] file2 = toSignedBytes(new short[] { - 0x62, 0x73, 0x64, 0x69, 0x66, 0x66, 0x20, 0x61, 0x6e, 0x64, - 0x20, 0x62, 0x73, 0x70, 0x61, 0x74, 0x63, 0x68, 0x20, 0x61, - 0x72, 0x65, 0x20, 0x74, 0x6f, 0x6f, 0x6c, 0x73, 0x20, 0x66, - 0x6f, 0x72, 0x20, 0x62, 0x75, 0x69, 0x6c, 0x64, 0x69, 0x6e, - 0x67, 0x20, 0x61, 0x6e, 0x64, 0x20, 0x61, 0x70, 0x70, 0x6c, - 0x79, 0x69, 0x6e, 0x67, 0x20, 0x70, 0x61, 0x74, 0x63, 0x68, - 0x65, 0x73, 0x20, 0x74, 0x6f, 0x20, 0x62, 0x69, 0x6e, 0x61, - 0x72, 0x79, 0x20, 0x66, 0x69, 0x6c, 0x65, 0x73, 0x2e, 0x0a, - }); - - byte[] patch = toSignedBytes(new short[] { - 0x42, 0x53, 0x44, 0x49, 0x46, 0x46, 0x34, 0x30, 0x35, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x27, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x50, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x42, 0x5a, 0x68, 0x39, 0x31, 0x41, 0x59, 0x26, - 0x53, 0x59, 0x93, 0x0d, 0x6a, 0xae, 0x00, 0x00, 0x0c, 0x68, - 0x40, 0x58, 0xa8, 0x02, 0x00, 0x04, 0x00, 0x40, 0x00, 0x20, - 0x00, 0x21, 0x88, 0x19, 0x08, 0x32, 0x62, 0x1b, 0xde, 0xbc, - 0x24, 0x08, 0xe9, 0x45, 0x3c, 0x5d, 0xc9, 0x14, 0xe1, 0x42, - 0x42, 0x4c, 0x35, 0xaa, 0xb8, 0x42, 0x5a, 0x68, 0x39, 0x31, - 0x41, 0x59, 0x26, 0x53, 0x59, 0x05, 0xb6, 0xa3, 0x63, 0x00, - 0x00, 0x00, 0x48, 0x00, 0x40, 0x00, 0x00, 0x80, 0x20, 0x00, - 0x21, 0x00, 0x82, 0x83, 0x17, 0x72, 0x45, 0x38, 0x50, 0x90, - 0x05, 0xb6, 0xa3, 0x63, 0x42, 0x5a, 0x68, 0x39, 0x31, 0x41, - 0x59, 0x26, 0x53, 0x59, 0xdb, 0x41, 0x22, 0x6f, 0x00, 0x00, - 0x01, 0x91, 0x80, 0x40, 0x00, 0x3e, 0x45, 0xdc, 0x00, 0x20, - 0x00, 0x22, 0x9a, 0x19, 0x32, 0x7a, 0x7a, 0xa1, 0x00, 0x00, - 0x21, 0xe2, 0xf8, 0x98, 0x42, 0x13, 0x3c, 0xec, 0x35, 0x5f, - 0x17, 0x72, 0x45, 0x38, 0x50, 0x90, 0xdb, 0x41, 0x22, 0x6f - }); - - byte[] expected = file2; - byte[] actual = patchFile(file1, patch); - - assertEquals(toDiffString(expected, actual), - Arrays.toString(expected), Arrays.toString(actual)); - } - - public void testBSPatch2() throws Exception { - byte[] file1 = toSignedBytes(new short[] { - 0x62, 0x73, 0x64, 0x69, 0x66, 0x66, 0x20, 0x61, 0x6e, 0x64, - 0x20, 0x62, 0x73, 0x70, 0x61, 0x74, 0x63, 0x68, 0x20, 0x61, - 0x72, 0x65, 0x20, 0x74, 0x6f, 0x6f, 0x6c, 0x73, 0x20, 0x66, - 0x6f, 0x72, 0x20, 0x62, 0x75, 0x69, 0x6c, 0x64, 0x69, 0x6e, - 0x67, 0x20, 0x61, 0x6e, 0x64, 0x20, 0x61, 0x70, 0x70, 0x6c, - 0x79, 0x69, 0x6e, 0x67, 0x20, 0x70, 0x61, 0x74, 0x63, 0x68, - 0x65, 0x73, 0x20, 0x74, 0x6f, 0x20, 0x62, 0x69, 0x6e, 0x61, - 0x72, 0x79, 0x20, 0x66, 0x69, 0x6c, 0x65, 0x73, 0x2e, 0x0a, - 0x68, 0x74, 0x74, 0x70, 0x3a, 0x2f, 0x2f, 0x77, 0x77, 0x77, - 0x2e, 0x64, 0x61, 0x65, 0x6d, 0x6f, 0x6e, 0x6f, 0x6c, 0x6f, - 0x67, 0x79, 0x2e, 0x6e, 0x65, 0x74, 0x2f, 0x62, 0x73, 0x64, - 0x69, 0x66, 0x66, 0x2f, 0x0a, 0x44, 0x65, 0x73, 0x63, 0x72, - 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x3a, 0x20, 0x67, 0x65, - 0x6e, 0x65, 0x72, 0x61, 0x74, 0x65, 0x2f, 0x61, 0x70, 0x70, - 0x6c, 0x79, 0x20, 0x61, 0x20, 0x70, 0x61, 0x74, 0x63, 0x68, - 0x20, 0x62, 0x65, 0x74, 0x77, 0x65, 0x65, 0x6e, 0x20, 0x74, - 0x77, 0x6f, 0x20, 0x62, 0x69, 0x6e, 0x61, 0x72, 0x79, 0x20, - 0x66, 0x69, 0x6c, 0x65, 0x73, 0x2e, 0x0a - }); - - byte[] file2 = toSignedBytes(new short[] { - 0x62, 0x73, 0x64, 0x69, 0x66, 0x66, 0x20, 0x61, 0x6e, 0x64, - 0x20, 0x62, 0x73, 0x70, 0x61, 0x74, 0x63, 0x68, 0x20, 0x61, - 0x72, 0x65, 0x20, 0x74, 0x6f, 0x6f, 0x6c, 0x73, 0x20, 0x66, - 0x6f, 0x72, 0x20, 0x62, 0x75, 0x69, 0x6c, 0x64, 0x69, 0x6e, - 0x67, 0x20, 0x61, 0x6e, 0x64, 0x20, 0x61, 0x70, 0x70, 0x6c, - 0x79, 0x69, 0x6e, 0x67, 0x20, 0x70, 0x61, 0x74, 0x63, 0x68, - 0x65, 0x73, 0x20, 0x74, 0x6f, 0x20, 0x62, 0x69, 0x6e, 0x61, - 0x72, 0x79, 0x20, 0x66, 0x69, 0x6c, 0x65, 0x73, 0x2e, 0x0a, - 0x44, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, - 0x6e, 0x3a, 0x20, 0x67, 0x65, 0x6e, 0x65, 0x72, 0x61, 0x74, - 0x65, 0x2f, 0x61, 0x70, 0x70, 0x6c, 0x79, 0x20, 0x61, 0x20, - 0x70, 0x61, 0x74, 0x63, 0x68, 0x20, 0x62, 0x65, 0x74, 0x77, - 0x65, 0x65, 0x6e, 0x20, 0x74, 0x77, 0x6f, 0x20, 0x62, 0x69, - 0x6e, 0x61, 0x72, 0x79, 0x20, 0x66, 0x69, 0x6c, 0x65, 0x73, - 0x2e, 0x0a, 0x68, 0x74, 0x74, 0x70, 0x3a, 0x2f, 0x2f, 0x77, - 0x77, 0x77, 0x2e, 0x64, 0x61, 0x65, 0x6d, 0x6f, 0x6e, 0x6f, - 0x6c, 0x6f, 0x67, 0x79, 0x2e, 0x6e, 0x65, 0x74, 0x2f, 0x62, - 0x73, 0x64, 0x69, 0x66, 0x66, 0x2f, 0x0a, 0x42, 0x53, 0x44, - 0x20, 0x6c, 0x69, 0x63, 0x65, 0x6e, 0x73, 0x65, 0x2c, 0x20, - 0x43, 0x6f, 0x70, 0x79, 0x72, 0x69, 0x67, 0x68, 0x74, 0x20, - 0x32, 0x30, 0x30, 0x33, 0x2d, 0x32, 0x30, 0x30, 0x35, 0x20, - 0x43, 0x6f, 0x6c, 0x69, 0x6e, 0x20, 0x50, 0x65, 0x72, 0x63, - 0x69, 0x76, 0x61, 0x6c, 0x0a, - }); - - byte[] patch = toSignedBytes(new short[] { - 0x42, 0x53, 0x44, 0x49, 0x46, 0x46, 0x34, 0x30, 0x3e, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x27, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0xe1, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x42, 0x5a, 0x68, 0x39, 0x31, 0x41, 0x59, 0x26, - 0x53, 0x59, 0x3f, 0xa6, 0x07, 0x42, 0x00, 0x00, 0x14, 0x5d, - 0x40, 0x58, 0x08, 0x08, 0x00, 0xc8, 0x02, 0x00, 0x00, 0xa0, - 0x00, 0x40, 0x00, 0x20, 0x00, 0x21, 0xa4, 0x69, 0x84, 0xfd, - 0x41, 0x03, 0x40, 0xd0, 0x22, 0xef, 0xe1, 0x49, 0x33, 0x02, - 0xce, 0x2e, 0xe6, 0x8b, 0xb9, 0x22, 0x9c, 0x28, 0x48, 0x1f, - 0xd3, 0x03, 0xa1, 0x00, 0x42, 0x5a, 0x68, 0x39, 0x31, 0x41, - 0x59, 0x26, 0x53, 0x59, 0x58, 0xc3, 0x04, 0xf0, 0x00, 0x00, - 0x00, 0x40, 0x10, 0x40, 0x00, 0x00, 0x02, 0x20, 0x00, 0x21, - 0x00, 0x82, 0x83, 0x17, 0x72, 0x45, 0x38, 0x50, 0x90, 0x58, - 0xc3, 0x04, 0xf0, 0x42, 0x5a, 0x68, 0x39, 0x31, 0x41, 0x59, - 0x26, 0x53, 0x59, 0x26, 0xc7, 0xbc, 0x09, 0x00, 0x00, 0x08, - 0x5f, 0x80, 0x00, 0x10, 0x40, 0x06, 0x5a, 0x00, 0x1c, 0x00, - 0x48, 0x00, 0x2a, 0xe5, 0xdd, 0x20, 0x20, 0x00, 0x31, 0x46, - 0x86, 0x80, 0x00, 0x00, 0x1a, 0xa6, 0x26, 0x40, 0xfd, 0x50, - 0x34, 0x79, 0x27, 0x92, 0x78, 0xda, 0x4d, 0x37, 0xa9, 0x20, - 0x8d, 0x8c, 0x41, 0x90, 0xea, 0x1c, 0x3a, 0xb3, 0xaa, 0x63, - 0x64, 0xa4, 0x27, 0x6d, 0x5b, 0x2a, 0xfc, 0x25, 0x1b, 0xab, - 0xd2, 0xff, 0x8b, 0xb9, 0x22, 0x9c, 0x28, 0x48, 0x13, 0x63, - 0xde, 0x04, 0x80 - }); - - byte[] expected = file2; - byte[] actual = patchFile(file1, patch); - - assertEquals(toDiffString(expected, actual), - Arrays.toString(expected), Arrays.toString(actual)); - } - - public void testBSPatch3() throws Exception { - byte[] file1 = toSignedBytes(new short[] { - 0x68, 0x74, 0x74, 0x70, 0x3a, 0x2f, 0x2f, 0x77, 0x77, 0x77, - 0x2e, 0x64, 0x61, 0x65, 0x6d, 0x6f, 0x6e, 0x6f, 0x6c, 0x6f, - 0x67, 0x79, 0x2e, 0x6e, 0x65, 0x74, 0x2f, 0x62, 0x73, 0x64, - 0x69, 0x66, 0x66, 0x2f, 0x0a, 0x42, 0x69, 0x6e, 0x61, 0x72, - 0x79, 0x20, 0x64, 0x69, 0x66, 0x66, 0x2f, 0x70, 0x61, 0x74, - 0x63, 0x68, 0x20, 0x75, 0x74, 0x69, 0x6c, 0x69, 0x74, 0x79, - 0x0a, 0x53, 0x48, 0x41, 0x31, 0x3a, 0x20, 0x37, 0x32, 0x63, - 0x35, 0x37, 0x34, 0x33, 0x34, 0x62, 0x64, 0x64, 0x34, 0x63, - 0x33, 0x38, 0x33, 0x63, 0x36, 0x39, 0x62, 0x62, 0x30, 0x66, - 0x61, 0x64, 0x34, 0x32, 0x33, 0x35, 0x37, 0x38, 0x35, 0x32, - 0x32, 0x63, 0x64, 0x30, 0x64, 0x33, 0x61, 0x0a, 0x53, 0x48, - 0x41, 0x32, 0x35, 0x36, 0x3a, 0x20, 0x61, 0x62, 0x62, 0x64, - 0x32, 0x32, 0x30, 0x39, 0x33, 0x38, 0x35, 0x65, 0x38, 0x65, - 0x38, 0x38, 0x30, 0x61, 0x64, 0x64, 0x30, 0x62, 0x37, 0x38, - 0x31, 0x37, 0x37, 0x38, 0x64, 0x65, 0x64, 0x34, 0x39, 0x65, - 0x31, 0x30, 0x61, 0x36, 0x66, 0x30, 0x63, 0x37, 0x39, 0x39, - 0x64, 0x33, 0x32, 0x36, 0x61, 0x36, 0x61, 0x65, 0x36, 0x37, - 0x30, 0x33, 0x36, 0x39, 0x36, 0x38, 0x66, 0x62, 0x31, 0x64, - 0x0a, 0x44, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, - 0x6f, 0x6e, 0x3a, 0x20, 0x67, 0x65, 0x6e, 0x65, 0x72, 0x61, - 0x74, 0x65, 0x2f, 0x61, 0x70, 0x70, 0x6c, 0x79, 0x20, 0x61, - 0x20, 0x70, 0x61, 0x74, 0x63, 0x68, 0x20, 0x62, 0x65, 0x74, - 0x77, 0x65, 0x65, 0x6e, 0x20, 0x74, 0x77, 0x6f, 0x20, 0x62, - 0x69, 0x6e, 0x61, 0x72, 0x79, 0x20, 0x66, 0x69, 0x6c, 0x65, - 0x73, 0x0a, 0x20, 0x62, 0x73, 0x64, 0x69, 0x66, 0x66, 0x20, - 0x61, 0x6e, 0x64, 0x20, 0x62, 0x73, 0x70, 0x61, 0x74, 0x63, - 0x68, 0x20, 0x61, 0x72, 0x65, 0x20, 0x74, 0x6f, 0x6f, 0x6c, - 0x73, 0x20, 0x66, 0x6f, 0x72, 0x20, 0x62, 0x75, 0x69, 0x6c, - 0x64, 0x69, 0x6e, 0x67, 0x20, 0x61, 0x6e, 0x64, 0x20, 0x61, - 0x70, 0x70, 0x6c, 0x79, 0x69, 0x6e, 0x67, 0x20, 0x70, 0x61, - 0x74, 0x63, 0x68, 0x65, 0x73, 0x20, 0x74, 0x6f, 0x20, 0x62, - 0x69, 0x6e, 0x61, 0x72, 0x79, 0x20, 0x66, 0x69, 0x6c, 0x65, - 0x73, 0x2e, 0x0a - }); - - byte[] file2 = toSignedBytes(new short[] { - 0x42, 0x69, 0x6e, 0x61, 0x72, 0x79, 0x20, 0x64, 0x69, 0x66, - 0x66, 0x2f, 0x70, 0x61, 0x74, 0x63, 0x68, 0x20, 0x75, 0x74, - 0x69, 0x6c, 0x69, 0x74, 0x79, 0x0a, 0x48, 0x6f, 0x6d, 0x65, - 0x70, 0x61, 0x67, 0x65, 0x3a, 0x20, 0x20, 0x20, 0x20, 0x68, - 0x74, 0x74, 0x70, 0x3a, 0x2f, 0x2f, 0x77, 0x77, 0x77, 0x2e, - 0x64, 0x61, 0x65, 0x6d, 0x6f, 0x6e, 0x6f, 0x6c, 0x6f, 0x67, - 0x79, 0x2e, 0x6e, 0x65, 0x74, 0x2f, 0x62, 0x73, 0x64, 0x69, - 0x66, 0x66, 0x2f, 0x0a, 0x53, 0x48, 0x41, 0x31, 0x3a, 0x20, - 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x37, 0x32, 0x63, - 0x35, 0x37, 0x34, 0x33, 0x34, 0x62, 0x64, 0x64, 0x34, 0x63, - 0x33, 0x38, 0x33, 0x63, 0x36, 0x39, 0x62, 0x62, 0x30, 0x66, - 0x61, 0x64, 0x34, 0x32, 0x33, 0x35, 0x37, 0x38, 0x35, 0x32, - 0x32, 0x63, 0x64, 0x30, 0x64, 0x33, 0x61, 0x0a, 0x53, 0x48, - 0x41, 0x32, 0x35, 0x36, 0x3a, 0x20, 0x20, 0x20, 0x20, 0x20, - 0x20, 0x61, 0x62, 0x62, 0x64, 0x32, 0x32, 0x30, 0x39, 0x33, - 0x38, 0x35, 0x65, 0x38, 0x65, 0x38, 0x38, 0x30, 0x61, 0x64, - 0x64, 0x30, 0x62, 0x37, 0x38, 0x31, 0x37, 0x37, 0x38, 0x64, - 0x65, 0x64, 0x34, 0x39, 0x65, 0x31, 0x30, 0x61, 0x36, 0x66, - 0x30, 0x63, 0x37, 0x39, 0x39, 0x64, 0x33, 0x32, 0x36, 0x61, - 0x36, 0x61, 0x65, 0x36, 0x37, 0x30, 0x33, 0x36, 0x39, 0x36, - 0x38, 0x66, 0x62, 0x31, 0x64, 0x0a, 0x44, 0x65, 0x73, 0x63, - 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x3a, 0x20, 0x67, - 0x65, 0x6e, 0x65, 0x72, 0x61, 0x74, 0x65, 0x2f, 0x61, 0x70, - 0x70, 0x6c, 0x79, 0x20, 0x61, 0x20, 0x70, 0x61, 0x74, 0x63, - 0x68, 0x20, 0x62, 0x65, 0x74, 0x77, 0x65, 0x65, 0x6e, 0x20, - 0x74, 0x77, 0x6f, 0x20, 0x62, 0x69, 0x6e, 0x61, 0x72, 0x79, - 0x20, 0x66, 0x69, 0x6c, 0x65, 0x73, 0x0a, 0x20, 0x20, 0x20, - 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, - 0x62, 0x73, 0x64, 0x69, 0x66, 0x66, 0x20, 0x61, 0x6e, 0x64, - 0x20, 0x62, 0x73, 0x70, 0x61, 0x74, 0x63, 0x68, 0x20, 0x61, - 0x72, 0x65, 0x20, 0x74, 0x6f, 0x6f, 0x6c, 0x73, 0x20, 0x66, - 0x6f, 0x72, 0x20, 0x62, 0x75, 0x69, 0x6c, 0x64, 0x69, 0x6e, - 0x67, 0x20, 0x61, 0x6e, 0x64, 0x20, 0x61, 0x70, 0x70, 0x6c, - 0x79, 0x69, 0x6e, 0x67, 0x20, 0x70, 0x61, 0x74, 0x63, 0x68, - 0x65, 0x73, 0x20, 0x74, 0x6f, 0x20, 0x62, 0x69, 0x6e, 0x61, - 0x72, 0x79, 0x20, 0x66, 0x69, 0x6c, 0x65, 0x73, 0x2e, 0x0a, - }); - - byte[] patch = toSignedBytes(new short[] { - 0x42, 0x53, 0x44, 0x49, 0x46, 0x46, 0x34, 0x30, 0x48, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x2b, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x68, 0x01, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x42, 0x5a, 0x68, 0x39, 0x31, 0x41, 0x59, 0x26, - 0x53, 0x59, 0xea, 0x1c, 0x55, 0x4e, 0x00, 0x00, 0x07, 0xfa, - 0x40, 0x7c, 0x0e, 0x00, 0x10, 0x88, 0x00, 0x10, 0x02, 0x20, - 0x00, 0x40, 0x00, 0x20, 0x00, 0x21, 0x29, 0xa8, 0x00, 0x6d, - 0x42, 0x98, 0x00, 0x09, 0x9a, 0x99, 0xcc, 0xb7, 0x2b, 0xcd, - 0xf7, 0x1e, 0x00, 0x86, 0x22, 0x21, 0x09, 0x25, 0x14, 0xc5, - 0x0e, 0xd4, 0x61, 0xf1, 0x77, 0x24, 0x53, 0x85, 0x09, 0x0e, - 0xa1, 0xc5, 0x54, 0xe0, 0x42, 0x5a, 0x68, 0x39, 0x31, 0x41, - 0x59, 0x26, 0x53, 0x59, 0xb2, 0xea, 0xe3, 0xb5, 0x00, 0x00, - 0x00, 0xc8, 0x00, 0xc0, 0x00, 0x00, 0x02, 0x00, 0x08, 0x20, - 0x00, 0x21, 0x26, 0x41, 0x98, 0xa8, 0x0e, 0x2e, 0xe4, 0x8a, - 0x70, 0xa1, 0x21, 0x65, 0xd5, 0xc7, 0x6a, 0x42, 0x5a, 0x68, - 0x39, 0x31, 0x41, 0x59, 0x26, 0x53, 0x59, 0x99, 0x1b, 0x67, - 0xdb, 0x00, 0x00, 0x07, 0xff, 0x80, 0x40, 0x00, 0x10, 0x00, - 0x40, 0x00, 0x20, 0x10, 0x20, 0x40, 0x08, 0x00, 0x22, 0x82, - 0xc0, 0x00, 0x20, 0x00, 0x31, 0x00, 0x00, 0x06, 0x81, 0x33, - 0x50, 0xc3, 0x00, 0x20, 0x73, 0xb3, 0x44, 0x9c, 0xfd, 0xde, - 0x1f, 0x68, 0xbb, 0x92, 0x29, 0xc2, 0x84, 0x84, 0xc8, 0xdb, - 0x3e, 0xd8 - }); - - byte[] expected = file2; - byte[] actual = patchFile(file1, patch); - - assertEquals(toDiffString(expected, actual), - Arrays.toString(expected), Arrays.toString(actual)); - } - - private String toDiffString(byte[] a1, byte[] a2) { - StringBuilder sb = new StringBuilder(); - int n1 = a1.length; - int n2 = a2.length; - boolean was_same = false; - - for (int i = 0; i < n1; i++) { - boolean same = i > 1 && - i+2 < n1 && - i+2 < n2 && - a1[i+0] == a2[i+0] && - a1[i+1] == a2[i+1] && - a1[i+2] == a2[i+2]; - if (!same) { - if (i >= n2) { - sb.append(String.format("[%1$3d] %2$02x %2$c | -- -\n", i, a1[i])); - } else { - sb.append(String.format("[%1$3d] %2$02x %2$c | %3$02x %3$c\n", i, a1[i], a2[i])); - } - } else if (!was_same) { - sb.append(String.format("[%1$3d] ...\n", i)); - } - was_same = same; - } - for (int i = n1; i < n2; i++) { - sb.append(String.format("[%1$3d] -- - | %2$02x %2$c\n", i, a2[i])); - } - - return sb.toString(); - } - - /** - * Work around the lack of unsigned bytes in java by providing an initialization - * array where each short is in the range 0..0xFF and converting it to signed bytes. - * - * unsigned byte: 0..127 => signed java byte: 0..127 - * unsigned byte: 128..255 => signed java byte: -128..-1 - * - * unsigned to signed java: (unsigned - 256) if unsigned > 127 - * signed java to unsigned: (256 + signed) if signed < 0 - */ - private byte[] toSignedBytes(short[] s) { - int n = s.length; - byte[] b = new byte[n]; - for (int i = 0; i < n; i++) { - short v = s[i]; - b[i] = v < 128 ? (byte)v : (byte)(v - 256); - } - return b; - } - - @SuppressWarnings("unused") - private byte toSigned(int unsigned) { - return unsigned < 128 ? (byte)unsigned : (byte)(unsigned - 256); - } - - private short toUnsigned(byte signed) { - if (signed >= 0) { - return signed; - } else { - return (short) ((short) 256 + signed); - } - } - - /** - * Patches the binary "file1" using the bsdiff/bspatch "patch" data. - * This implements bspatch.c in Java. - * - * Reference: http://www.daemonology.net/bsdiff/ <br/> - * Based on bspatch.c as identified by <br/> - * {@code $FreeBSD: src/usr.bin/bsdiff/bspatch/bspatch.c,v 1.1 2005/08/06 01:59:06 cperciva Exp $} - * (BSD license, Copyright 2003-2005 Colin Percival) - * - * @param file1 The base file to be patched. - * @param patch The binary patch to apply to base file. - * @return A new byte array representing the patched file. - * @throws PatchException when the patch header is invalid. - * @throws IOException if the BZIP2 decoder fails. - */ - private byte[] patchFile(byte[] file1, byte[] patch) throws PatchException, IOException { - /* - File format: - 0 8 "BSDIFF40" - 8 8 X - 16 8 Y - 24 8 sizeof(newfile) - 32 X bzip2(control block) - 32+X Y bzip2(diff block) - 32+X+Y ??? bzip2(extra block) - with control block a set of triples (x,y,z) meaning "add x bytes - from oldfile to x bytes from the diff block; copy y bytes from the - extra block; seek forwards in oldfile by z bytes". - */ - - /* Read header */ - if (patch.length < 32) { - throw new PatchException("Header.len < 32"); - } - byte[] header = patch; - - /* Check for appropriate magic */ - if (header[0] != 'B' || header[1] != 'S' || header[2] != 'D' || header[3] != 'I' || - header[4] != 'F' || header[5] != 'F' || header[6] != '4' || header[7] != '0') { - throw new PatchException("Invalid header signature"); - } - - /* Read lengths from header */ - long bzctrllen = offtin(header, 8); - long bzdatalen = offtin(header, 16); - long newsize = offtin(header, 24); - if (bzctrllen < 0 || bzdatalen < 0 || newsize < 0) { - throw new PatchException("Invalid header lengths"); - } - - // Note: bspatch uses long lengths everywhere; - // however new byte[] doesn't support that and we don't expect to - // have 2GB+ file sizes to diff any time soon so let's - // do a first implementation that only supports 2^32 sizes. - - /* Read embedded files using Apache Common Compress' BZIP2 */ - InputStream cpfbz2 = readBzip2Data(patch, 32, bzctrllen); - InputStream dpfbz2 = readBzip2Data(patch, 32 + bzctrllen, bzdatalen); - InputStream epfbz2 = readBzip2Data(patch, 32 + bzctrllen + bzdatalen, -1); - - int oldsize = file1.length; - byte[] old = file1; - - byte[] _new = new byte[(int) newsize]; - - long ctrl[] = new long[3]; - byte buf[] = new byte[8]; - long oldpos = 0; - long newpos = 0; - while (newpos < newsize) { - long lenread; - - /* Read control data */ - for(int i = 0; i <= 2; i++) { - lenread = BZ2_bzRead(cpfbz2, buf, 0, 8); - if (lenread < 8) { - throw new PatchException("Failed to read control data") ; - } - ctrl[i] = offtin(buf, 0); - }; - - /* Sanity-check */ - if (newpos + ctrl[0] > newsize) { - throw new PatchException("Sanity check failed") ; - } - - /* Read diff string */ - lenread = BZ2_bzRead(dpfbz2, _new, newpos, ctrl[0]); - if (lenread < ctrl[0]) { - throw new PatchException("Failed to read diff data") ; - } - - /* Add old data to diff string */ - for (int i = 0; i < ctrl[0]; i++) { - if (oldpos + i >= 0 && oldpos + i < oldsize) { - _new[(int) (newpos + i)] += old[(int) (oldpos + i)]; - } - } - - /* Adjust pointers */ - newpos += ctrl[0]; - oldpos += ctrl[0]; - - /* Sanity-check */ - if (newpos + ctrl[1] > newsize) { - throw new PatchException("Sanity check failed") ; - } - - /* Read extra string */ - lenread = BZ2_bzRead(epfbz2, _new, newpos, ctrl[1]); - if (lenread < ctrl[1]) { - throw new PatchException("Failed to read extra data") ; - } - - /* Adjust pointers */ - newpos += ctrl[1]; - oldpos += ctrl[2]; - } - - /* Clean up the bzip2 reads */ - cpfbz2.close(); - dpfbz2.close(); - epfbz2.close(); - - /* Write the new file */ - // nop - - return _new; - } - - private long offtin(byte[] header, int offset) { - long y = 0; - - offset += 7; - y = header[offset] & 0x7F; - boolean sign = (header[offset] & 0x80) != 0; - for (int i = 6; i >= 0; i--) { - y = y * 256 + toUnsigned(header[--offset]); - } - - if (sign) { - y = -y; - } - - return y; - } - - /** - * Decode a BZIP2 data block starting at the given offset. - * - * @param data The binary data of the file. - * @param offset The index where the file begins - * @param length The length to read. Use -1 to mean "up to the end". - * @return A new decoded byte array. - * @throws IOException when the BZIP2 decompression fails. - */ - private InputStream readBzip2Data(byte[] data, long offset, long length) throws IOException { - if (length == -1) { - length = data.length - offset; - } - ByteArrayInputStream is = new ByteArrayInputStream(data, (int) offset, (int) length); - BZip2CompressorInputStream bis = new BZip2CompressorInputStream(is); - return bis; - } - - /** - * Reads the {@code length} next bytes from the bzip2 input stream. - * - * @param bzip2is The input stream to read from. - * @param dest The destination buffer to fill. - * @param length The length to read in bytes. - * @return The number of bytes read. - * @throws IOException If there's not enough data to read. - */ - private long BZ2_bzRead(InputStream bzip2is, byte[] dest, long offset, long length) - throws IOException { - for (long i = 0; i < length; ) { - int len = bzip2is.read(dest, (int) (offset + i), (int) (length - i)); - if (len == -1) { - throw new IOException("Bzip2 EOF"); - } - i += len; - } - return length; - } - - - @SuppressWarnings("serial") - static class PatchException extends Exception { - public PatchException() { - super("Corrupt patch"); - } - public PatchException(String msg) { - super("Corrupt patch: " + msg); - } - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/util/CommandLineParserTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/util/CommandLineParserTest.java deleted file mode 100644 index 7d8a01f..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/util/CommandLineParserTest.java +++ /dev/null @@ -1,246 +0,0 @@ -/* - * Copyright (C) 2008 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.util; - -import com.android.utils.ILogger; -import com.android.utils.StdLogger; - -import java.util.Arrays; -import java.util.List; - -import junit.framework.TestCase; - - -public class CommandLineParserTest extends TestCase { - - private StdLogger mLog; - - /** - * A mock version of the {@link CommandLineParser} class that does not - * exits and captures its stdout/stderr output. - */ - public static class MockCommandLineProcessor extends CommandLineParser { - private boolean mExitCalled; - private boolean mHelpCalled; - private String mStdOut = ""; - private String mStdErr = ""; - - public MockCommandLineProcessor(ILogger logger) { - super(logger, - new String[][] { - { "verb1", "action1", "Some action" }, - { "verb1", "action2", "Another action" }, - { "verb2", NO_VERB_OBJECT, "Action with string array" }, - }); - define(Mode.STRING, false /*mandatory*/, - "verb1", "action1", "1", "first", "non-mandatory flag", null); - define(Mode.STRING, true /*mandatory*/, - "verb1", "action1", "2", "second", "mandatory flag", null); - - define(Mode.STRING, true /*mandatory*/, - "verb2", NO_VERB_OBJECT, "1", "first", "1st mandatory flag", null); - define(Mode.STRING_ARRAY, true /*mandatory*/, - "verb2", NO_VERB_OBJECT, "2", "second", "2nd mandatory flag", null); - define(Mode.STRING, true /*mandatory*/, - "verb2", NO_VERB_OBJECT, "3", "third", "3rd mandatory flag", null); - } - - @Override - public void printHelpAndExitForAction(String verb, String directObject, - String errorFormat, Object... args) { - mHelpCalled = true; - super.printHelpAndExitForAction(verb, directObject, errorFormat, args); - } - - @Override - protected void exit() { - mExitCalled = true; - } - - @Override - protected void stdout(String format, Object... args) { - String s = String.format(format, args); - mStdOut += s + "\n"; - // don't call super to avoid printing stuff - } - - @Override - protected void stderr(String format, Object... args) { - String s = String.format(format, args); - mStdErr += s + "\n"; - // don't call super to avoid printing stuff - } - - public boolean wasHelpCalled() { - return mHelpCalled; - } - - public boolean wasExitCalled() { - return mExitCalled; - } - - public String getStdOut() { - return mStdOut; - } - - public String getStdErr() { - return mStdErr; - } - } - - @Override - protected void setUp() throws Exception { - mLog = new StdLogger(StdLogger.Level.VERBOSE); - super.setUp(); - } - - @Override - protected void tearDown() throws Exception { - super.tearDown(); - } - - public void testPrintHelpAndExit() { - MockCommandLineProcessor c = new MockCommandLineProcessor(mLog); - assertFalse(c.wasExitCalled()); - assertFalse(c.wasHelpCalled()); - assertTrue(c.getStdOut().equals("")); - assertTrue(c.getStdErr().equals("")); - c.printHelpAndExit(null); - assertTrue(c.getStdOut().indexOf("-v") != -1); - assertTrue(c.getStdOut().indexOf("--verbose") != -1); - assertTrue(c.getStdErr().equals("")); - assertTrue(c.wasExitCalled()); - - c = new MockCommandLineProcessor(mLog); - assertFalse(c.wasExitCalled()); - assertTrue(c.getStdOut().equals("")); - assertTrue(c.getStdErr().indexOf("Missing parameter") == -1); - - c.printHelpAndExit("Missing %s", "parameter"); - assertTrue(c.wasExitCalled()); - assertFalse(c.getStdOut().equals("")); - assertTrue(c.getStdErr().indexOf("Missing parameter") != -1); - } - - public void testVerbose() { - MockCommandLineProcessor c = new MockCommandLineProcessor(mLog); - - assertFalse(c.isVerbose()); - c.parseArgs(new String[] { "-v" }); - assertTrue(c.isVerbose()); - assertTrue(c.wasExitCalled()); - assertTrue(c.wasHelpCalled()); - assertTrue(c.getStdErr().indexOf("Missing verb name.") != -1); - - c = new MockCommandLineProcessor(mLog); - c.parseArgs(new String[] { "--verbose" }); - assertTrue(c.isVerbose()); - assertTrue(c.wasExitCalled()); - assertTrue(c.wasHelpCalled()); - assertTrue(c.getStdErr().indexOf("Missing verb name.") != -1); - } - - public void testHelp() { - MockCommandLineProcessor c = new MockCommandLineProcessor(mLog); - - c.parseArgs(new String[] { "-h" }); - assertTrue(c.wasExitCalled()); - assertTrue(c.wasHelpCalled()); - assertTrue(c.getStdErr().indexOf("Missing verb name.") == -1); - - c = new MockCommandLineProcessor(mLog); - c.parseArgs(new String[] { "--help" }); - assertTrue(c.wasExitCalled()); - assertTrue(c.wasHelpCalled()); - assertTrue(c.getStdErr().indexOf("Missing verb name.") == -1); - } - - public void testMandatory() { - MockCommandLineProcessor c = new MockCommandLineProcessor(mLog); - - c.parseArgs(new String[] { "verb1", "action1", "-1", "value1", "-2", "value2" }); - assertFalse(c.wasExitCalled()); - assertFalse(c.wasHelpCalled()); - assertEquals("", c.getStdErr()); - assertEquals("value1", c.getValue("verb1", "action1", "first")); - assertEquals("value2", c.getValue("verb1", "action1", "second")); - - c = new MockCommandLineProcessor(mLog); - c.parseArgs(new String[] { "verb1", "action1", "-2", "value2" }); - assertFalse(c.wasExitCalled()); - assertFalse(c.wasHelpCalled()); - assertEquals("", c.getStdErr()); - assertEquals(null, c.getValue("verb1", "action1", "first")); - assertEquals("value2", c.getValue("verb1", "action1", "second")); - - c = new MockCommandLineProcessor(mLog); - c.parseArgs(new String[] { "verb1", "action1" }); - assertTrue(c.wasExitCalled()); - assertTrue(c.wasHelpCalled()); - assertTrue(c.getStdErr().indexOf("must be defined") != -1); - assertEquals(null, c.getValue("verb1", "action1", "first")); - assertEquals(null, c.getValue("verb1", "action1", "second")); - } - - public void testStringArray() { - MockCommandLineProcessor c = new MockCommandLineProcessor(mLog); - - c.parseArgs(new String[] { "verb2", - "-1", "value1", - "-2", "value2_a", "value2_b", "value2_c", "value2_d", - "-3", "value3" }); - assertFalse(c.wasExitCalled()); - assertFalse(c.wasHelpCalled()); - assertEquals("", c.getStdErr()); - assertEquals("value1", c.getValue("verb2", null, "first")); - assertTrue(c.getValue("verb2", null, "second") instanceof List<?>); - assertEquals("[value2_a, value2_b, value2_c, value2_d]", - Arrays.toString(((List<?>) c.getValue("verb2", null, "second")).toArray())); - assertEquals("value3", c.getValue("verb2", null, "third")); - } - - public void testStringArray_DashDash() { - MockCommandLineProcessor c = new MockCommandLineProcessor(mLog); - - // Use -- to tell argument -2 it can absorb any argument, including dashed ones. - // Logically -2 must be the last argument and -1/-3 must be placed before it. - c.parseArgs(new String[] { "verb2", - "-1", "value1", - "-3", "value3", - "-2", "value2_a", "--", "-value2_b", "--value2_c", "value2_d" }); - assertFalse(c.wasExitCalled()); - assertFalse(c.wasHelpCalled()); - assertEquals("", c.getStdErr()); - assertEquals("value1", c.getValue("verb2", null, "first")); - assertTrue(c.getValue("verb2", null, "second") instanceof List<?>); - assertEquals("[value2_a, --, -value2_b, --value2_c, value2_d]", - Arrays.toString(((List<?>) c.getValue("verb2", null, "second")).toArray())); - assertEquals("value3", c.getValue("verb2", null, "third")); - } - - public void testStringArray_EmptyStringArray() { - MockCommandLineProcessor c = new MockCommandLineProcessor(mLog); - - c.parseArgs(new String[] { "verb2", - "-1", "value1", - "-2", - "-3", "value3" }); - assertTrue(c.wasExitCalled()); - assertTrue(c.wasHelpCalled()); - assertEquals("Invalid usage for flag -2: No values provided.", c.getStdErr().trim()); - } -} diff --git a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/util/LineUtilTest.java b/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/util/LineUtilTest.java deleted file mode 100755 index 213efc2..0000000 --- a/sdkmanager/libs/sdklib/src/test/java/com/android/sdklib/util/LineUtilTest.java +++ /dev/null @@ -1,82 +0,0 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 - * - * 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.sdklib.util; - -import com.android.sdklib.util.LineUtil; - -import junit.framework.TestCase; - - -public class LineUtilTest extends TestCase { - - public void testReflowLine() { - boolean gotNpe = false; - try { - LineUtil.reflowLine(null); - } catch(NullPointerException e) { - gotNpe = true; - } finally { - assertTrue(gotNpe); - } - - assertEquals("", LineUtil.reflowLine("")); - - assertEquals("1234567", LineUtil.reflowLine("1234567")); - - assertEquals( - "-- verbose, -v: This description for this flag fits in exactly 78 characters.", - LineUtil.reflowLine("-- verbose, -v: This description for this flag fits in exactly 78 characters.")); - - assertEquals( - "--verbose, -v : This description for this flag fits in more than 78\n" + - " characters and needs to wrap up at the colon.", - LineUtil.reflowLine("--verbose, -v : This description for this flag fits in more than 78 characters and needs to wrap up at the colon.")); - - assertEquals( - "If the line needs to wrap but there's no colon marker, the line will just wrap\n" + - " with 4 spaces.", - LineUtil.reflowLine("If the line needs to wrap but there's no colon marker, the line will just wrap with 4 spaces.")); - - assertEquals( - "--blah: More than 78 characters and lots of\n" + - " spaces. ", - LineUtil.reflowLine("--blah: More than 78 characters and lots of spaces. ")); - - assertEquals( - "In this case the colon is at the very end of the string and it's not going to\n" + - " wrap as expected:", - LineUtil.reflowLine("In this case the colon is at the very end of the string and it's not going to wrap as expected:")); - - assertEquals( - "--flag:In-this-case-there-is-no-whitespace-and-wrapping-will-cut-just-at-the-7\n" + - " 8-mark.", - LineUtil.reflowLine("--flag:In-this-case-there-is-no-whitespace-and-wrapping-will-cut-just-at-the-78-mark.")); - - assertEquals( - "Desc: This line is split in 2.\n" + - " The second line must align at the colon and yet still wrap as expected\n" + - " if it doesn't fit properly.\n" + - " The end.", - LineUtil.reflowLine("Desc: This line is split in 2.\nThe second line must align at the colon and yet still wrap as expected if it doesn't fit properly.\nThe end.")); - - assertEquals( - "Desc: This line is split in 2\n" + - " even though it doesn't need to wrap.", - LineUtil.reflowLine("Desc: This line is split in 2\n\n\n\n\n\neven though it doesn't need to wrap.")); - - } -} |