aboutsummaryrefslogtreecommitdiffstats
path: root/eclipse/plugins
diff options
context:
space:
mode:
authorSiva Velusamy <vsiva@google.com>2012-07-30 12:19:35 -0700
committerandroid code review <noreply-gerritcodereview@google.com>2012-07-30 12:19:35 -0700
commit627cba9137377a38d3523ac129f502281244b405 (patch)
treed5041ef8d7a9454d128693d5afbde1a1fd584180 /eclipse/plugins
parent6a2d4d7796030c038ed0a59f1a68ae4d2108209f (diff)
parent3685081c34cb5d240e38e714d6a0004cf4381928 (diff)
downloadsdk-627cba9137377a38d3523ac129f502281244b405.tar.gz
sdk-627cba9137377a38d3523ac129f502281244b405.tar.bz2
sdk-627cba9137377a38d3523ac129f502281244b405.zip
Merge "Use minSdk for device/avd compatibility checks"
Diffstat (limited to 'eclipse/plugins')
-rw-r--r--eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/internal/launch/AndroidLaunchController.java86
-rw-r--r--eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/internal/launch/DeviceChooserDialog.java67
-rw-r--r--eclipse/plugins/com.android.ide.eclipse.ndk/src/com/android/ide/eclipse/ndk/internal/launch/NdkGdbLaunchDelegate.java9
3 files changed, 107 insertions, 55 deletions
diff --git a/eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/internal/launch/AndroidLaunchController.java b/eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/internal/launch/AndroidLaunchController.java
index 1f004f5a7..b8caadb08 100644
--- a/eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/internal/launch/AndroidLaunchController.java
+++ b/eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/internal/launch/AndroidLaunchController.java
@@ -31,6 +31,7 @@ import com.android.ddmlib.Log;
import com.android.ddmlib.TimeoutException;
import com.android.ide.eclipse.adt.AdtPlugin;
import com.android.ide.eclipse.adt.internal.actions.AvdManagerAction;
+import com.android.ide.eclipse.adt.internal.editors.manifest.ManifestInfo;
import com.android.ide.eclipse.adt.internal.launch.AndroidLaunchConfiguration.TargetMode;
import com.android.ide.eclipse.adt.internal.launch.DelayedLaunchInfo.InstallRetryMode;
import com.android.ide.eclipse.adt.internal.launch.DeviceChooserDialog.DeviceChooserResponse;
@@ -324,9 +325,15 @@ public final class AndroidLaunchController implements IDebugBridgeChangeListener
config.mTargetMode = TargetMode.MANUAL;
}
- // get the project target
+ // get the sdk against which the project is built
IAndroidTarget projectTarget = currentSdk.getTarget(project);
+ // get the min required android version
+ ManifestInfo mi = ManifestInfo.get(project);
+ final int minApiLevel = mi.getMinSdkVersion();
+ final String minApiCodeName = mi.getMinSdkCodeName();
+ final AndroidVersion minApiVersion = new AndroidVersion(minApiLevel, minApiCodeName);
+
// FIXME: check errors on missing sdk, AVD manager, or project target.
// device chooser response object.
@@ -370,17 +377,22 @@ public final class AndroidLaunchController implements IDebugBridgeChangeListener
AvdInfo preferredAvd = null;
if (config.mAvdName != null) {
preferredAvd = avdManager.getAvd(config.mAvdName, true /*validAvdOnly*/);
- if (projectTarget.canRunOn(preferredAvd.getTarget()) == false) {
+ IAndroidTarget preferredAvdTarget = preferredAvd.getTarget();
+ if (preferredAvdTarget != null
+ && !preferredAvdTarget.getVersion().canRun(minApiVersion)) {
preferredAvd = null;
AdtPlugin.printErrorToConsole(project, String.format(
- "Preferred AVD '%1$s' is not compatible with the project target '%2$s'. Looking for a compatible AVD...",
- config.mAvdName, projectTarget.getName()));
+ "Preferred AVD '%1$s' (API Level: %2$d) cannot run application with minApi %3$s. Looking for a compatible AVD...",
+ config.mAvdName,
+ preferredAvdTarget.getVersion().getApiLevel(),
+ minApiVersion));
}
}
if (preferredAvd != null) {
- // look for a matching device
+ // We have a preferred avd that can actually run the application.
+ // Now see if the AVD is running, and if so use it, otherwise launch it.
for (IDevice d : devices) {
String deviceAvd = d.getAvdName();
@@ -416,38 +428,31 @@ public final class AndroidLaunchController implements IDebugBridgeChangeListener
// a device which target is the same as the project's target) and use it as the
// new default.
- int reqApiLevel = 0;
- try {
- reqApiLevel = Integer.parseInt(requiredApiVersionNumber);
-
- if (reqApiLevel > 0 && reqApiLevel < projectTarget.getVersion().getApiLevel()) {
- int maxDist = projectTarget.getVersion().getApiLevel() - reqApiLevel;
- IAndroidTarget candidate = null;
-
- for (IAndroidTarget target : currentSdk.getTargets()) {
- if (target.canRunOn(projectTarget)) {
- int currDist = target.getVersion().getApiLevel() - reqApiLevel;
- if (currDist >= 0 && currDist < maxDist) {
- maxDist = currDist;
- candidate = target;
- if (maxDist == 0) {
- // Found a perfect match
- break;
- }
+ if (minApiCodeName != null && minApiLevel < projectTarget.getVersion().getApiLevel()) {
+ int maxDist = projectTarget.getVersion().getApiLevel() - minApiLevel;
+ IAndroidTarget candidate = null;
+
+ for (IAndroidTarget target : currentSdk.getTargets()) {
+ if (target.canRunOn(projectTarget)) {
+ int currDist = target.getVersion().getApiLevel() - minApiLevel;
+ if (currDist >= 0 && currDist < maxDist) {
+ maxDist = currDist;
+ candidate = target;
+ if (maxDist == 0) {
+ // Found a perfect match
+ break;
}
}
}
+ }
- if (candidate != null) {
- // We found a better SDK target candidate, that is closer to the
- // API level from minSdkVersion than the one currently used by the
- // project. Below (in the for...devices loop) we'll try to find
- // a device/AVD for it.
- projectTarget = candidate;
- }
+ if (candidate != null) {
+ // We found a better SDK target candidate, that is closer to the
+ // API level from minSdkVersion than the one currently used by the
+ // project. Below (in the for...devices loop) we'll try to find
+ // a device/AVD for it.
+ projectTarget = candidate;
}
- } catch (NumberFormatException e) {
- // pass
}
HashMap<IDevice, AvdInfo> compatibleRunningAvds = new HashMap<IDevice, AvdInfo>();
@@ -578,7 +583,7 @@ public final class AndroidLaunchController implements IDebugBridgeChangeListener
boolean includeDevices = config.mTargetMode != TargetMode.ALL_EMULATORS;
boolean includeAvds = config.mTargetMode != TargetMode.ALL_DEVICES;
Collection<IDevice> compatibleDevices = findCompatibleDevices(devices,
- requiredApiVersionNumber, includeDevices, includeAvds);
+ minApiVersion, includeDevices, includeAvds);
if (compatibleDevices.size() == 0) {
AdtPlugin.printErrorToConsole(project,
"No active compatible AVD's or devices found. "
@@ -601,7 +606,8 @@ public final class AndroidLaunchController implements IDebugBridgeChangeListener
// or the AVD to launch.
DeviceChooserDialog dialog = new DeviceChooserDialog(
AdtPlugin.getDisplay().getActiveShell(),
- response, launchInfo.getPackageName(), desiredProjectTarget);
+ response, launchInfo.getPackageName(),
+ desiredProjectTarget, minApiVersion);
if (dialog.open() == Dialog.OK) {
DeviceChoiceCache.put(launch.getLaunchConfiguration().getName(), response);
continueLaunch.set(true);
@@ -634,22 +640,14 @@ public final class AndroidLaunchController implements IDebugBridgeChangeListener
/**
* Returns devices that can run a app of provided API level.
* @param devices list of devices to filter from
- * @param requiredApiVersionNumber minimum required API level that should be supported
+ * @param requiredVersion minimum required API that should be supported
* @param includeDevices include physical devices in the filtered list
* @param includeAvds include emulators in the filtered list
* @return set of compatible devices, may be an empty set
*/
private Collection<IDevice> findCompatibleDevices(IDevice[] devices,
- String requiredApiVersionNumber, boolean includeDevices, boolean includeAvds) {
+ AndroidVersion requiredVersion, boolean includeDevices, boolean includeAvds) {
Set<IDevice> compatibleDevices = new HashSet<IDevice>(devices.length);
- int minApi;
- try {
- minApi = Integer.parseInt(requiredApiVersionNumber);
- } catch (NumberFormatException e) {
- minApi = 1;
- }
- AndroidVersion requiredVersion = new AndroidVersion(minApi, null);
-
AvdManager avdManager = Sdk.getCurrent().getAvdManager();
for (IDevice d: devices) {
boolean isEmulator = d.isEmulator();
diff --git a/eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/internal/launch/DeviceChooserDialog.java b/eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/internal/launch/DeviceChooserDialog.java
index 781deafe6..5638d5192 100644
--- a/eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/internal/launch/DeviceChooserDialog.java
+++ b/eclipse/plugins/com.android.ide.eclipse.adt/src/com/android/ide/eclipse/adt/internal/launch/DeviceChooserDialog.java
@@ -57,6 +57,9 @@ import org.eclipse.swt.widgets.Label;
import org.eclipse.swt.widgets.Shell;
import org.eclipse.swt.widgets.Table;
+import java.util.ArrayList;
+import java.util.List;
+
/**
* A dialog that lets the user choose a device to deploy an application.
* The user can either choose an exiting running device (including running emulators)
@@ -80,6 +83,7 @@ public class DeviceChooserDialog extends Dialog implements IDeviceChangeListener
private final DeviceChooserResponse mResponse;
private final String mPackageName;
private final IAndroidTarget mProjectTarget;
+ private final AndroidVersion mMinApiVersion;
private final Sdk mSdk;
private Button mDeviceRadioButton;
@@ -92,16 +96,32 @@ public class DeviceChooserDialog extends Dialog implements IDeviceChangeListener
* Basic Content Provider for a table full of {@link IDevice} objects. The input is
* a {@link AndroidDebugBridge}.
*/
- private static class ContentProvider implements IStructuredContentProvider {
+ private class ContentProvider implements IStructuredContentProvider {
@Override
public Object[] getElements(Object inputElement) {
if (inputElement instanceof AndroidDebugBridge) {
- return ((AndroidDebugBridge)inputElement).getDevices();
+ return findCompatibleDevices(((AndroidDebugBridge)inputElement).getDevices());
}
return new Object[0];
}
+ private Object[] findCompatibleDevices(IDevice[] devices) {
+ if (devices == null) {
+ return null;
+ }
+
+ List<IDevice> compatibleDevices = new ArrayList<IDevice>(devices.length);
+ for (IDevice device : devices) {
+ AndroidVersion deviceVersion = Sdk.getDeviceVersion(device);
+ if (deviceVersion == null || deviceVersion.canRun(mMinApiVersion)) {
+ compatibleDevices.add(device);
+ }
+ }
+
+ return compatibleDevices.toArray();
+ }
+
@Override
public void dispose() {
// pass
@@ -113,7 +133,6 @@ public class DeviceChooserDialog extends Dialog implements IDeviceChangeListener
}
}
-
/**
* A Label Provider for the {@link TableViewer} in {@link DeviceChooserDialog}.
* It provides labels and images for {@link IDevice} objects.
@@ -136,7 +155,7 @@ public class DeviceChooserDialog extends Dialog implements IDeviceChangeListener
if (deviceVersion == null) {
return mWarningImage;
} else {
- if (deviceVersion.canRun(mProjectTarget.getVersion()) == false) {
+ if (!deviceVersion.canRun(mMinApiVersion)) {
return mNoMatchImage;
}
@@ -152,6 +171,17 @@ public class DeviceChooserDialog extends Dialog implements IDeviceChangeListener
if (info == null) {
return mWarningImage;
}
+ IAndroidTarget avdTarget = info.getTarget();
+ if (avdTarget == null) {
+ return mWarningImage;
+ }
+
+ // for platform targets, we only need to check the min api level
+ if (mProjectTarget.isPlatform()
+ && avdTarget.getVersion().canRun(mMinApiVersion))
+ return mMatchImage;
+
+ // for add on targets, check if required libraries are available
return mProjectTarget.canRunOn(info.getTarget()) ?
mMatchImage : mNoMatchImage;
}
@@ -259,12 +289,13 @@ public class DeviceChooserDialog extends Dialog implements IDeviceChangeListener
}
public DeviceChooserDialog(Shell parent, DeviceChooserResponse response, String packageName,
- IAndroidTarget projectTarget) {
+ IAndroidTarget projectTarget, AndroidVersion minApiVersion) {
super(parent);
mResponse = response;
mPackageName = packageName;
mProjectTarget = projectTarget;
+ mMinApiVersion = minApiVersion;
mSdk = Sdk.getCurrent();
AndroidDebugBridge.addDeviceChangeListener(this);
@@ -340,9 +371,16 @@ public class DeviceChooserDialog extends Dialog implements IDeviceChangeListener
Composite top = new Composite(parent, SWT.NONE);
top.setLayout(new GridLayout(1, true));
+ String msg;
+ if (mProjectTarget.isPlatform()) {
+ msg = String.format("Select a device with min API level %s.",
+ mMinApiVersion.getApiString());
+ } else {
+ msg = String.format("Select a device compatible with target %s.",
+ mProjectTarget.getFullName());
+ }
Label label = new Label(top, SWT.NONE);
- label.setText(String.format("Select a device compatible with target %s.",
- mProjectTarget.getFullName()));
+ label.setText(msg);
mDeviceRadioButton = new Button(top, SWT.RADIO);
mDeviceRadioButton.setText("Choose a running Android device");
@@ -736,12 +774,23 @@ public class DeviceChooserDialog extends Dialog implements IDeviceChangeListener
@Override
public boolean accept(AvdInfo avd) {
+ IAndroidTarget avdTarget = avd.getTarget();
+
if (mDevices != null) {
for (IDevice d : mDevices) {
- if (mProjectTarget.canRunOn(avd.getTarget()) == false ||
- avd.getName().equals(d.getAvdName())) {
+ if (avd.getName().equals(d.getAvdName())) {
return false;
}
+
+ if (avdTarget == null) {
+ return true;
+ }
+
+ if (mProjectTarget.isPlatform()) {
+ return avdTarget.getVersion().canRun(mMinApiVersion);
+ }
+
+ return mProjectTarget.canRunOn(avd.getTarget());
}
}
diff --git a/eclipse/plugins/com.android.ide.eclipse.ndk/src/com/android/ide/eclipse/ndk/internal/launch/NdkGdbLaunchDelegate.java b/eclipse/plugins/com.android.ide.eclipse.ndk/src/com/android/ide/eclipse/ndk/internal/launch/NdkGdbLaunchDelegate.java
index 1c463ab5b..57d96d7b1 100644
--- a/eclipse/plugins/com.android.ide.eclipse.ndk/src/com/android/ide/eclipse/ndk/internal/launch/NdkGdbLaunchDelegate.java
+++ b/eclipse/plugins/com.android.ide.eclipse.ndk/src/com/android/ide/eclipse/ndk/internal/launch/NdkGdbLaunchDelegate.java
@@ -17,16 +17,17 @@
package com.android.ide.eclipse.ndk.internal.launch;
import com.android.ddmlib.AdbCommandRejectedException;
+import com.android.ddmlib.AndroidDebugBridge;
import com.android.ddmlib.Client;
import com.android.ddmlib.IDevice;
import com.android.ddmlib.IDevice.DeviceUnixSocketNamespace;
-import com.android.ddmlib.AndroidDebugBridge;
import com.android.ddmlib.IShellOutputReceiver;
import com.android.ddmlib.InstallException;
import com.android.ddmlib.ShellCommandUnresponsiveException;
import com.android.ddmlib.SyncException;
import com.android.ddmlib.TimeoutException;
import com.android.ide.eclipse.adt.AdtPlugin;
+import com.android.ide.eclipse.adt.internal.editors.manifest.ManifestInfo;
import com.android.ide.eclipse.adt.internal.launch.DeviceChoiceCache;
import com.android.ide.eclipse.adt.internal.launch.DeviceChooserDialog;
import com.android.ide.eclipse.adt.internal.launch.DeviceChooserDialog.DeviceChooserResponse;
@@ -119,6 +120,10 @@ public class NdkGdbLaunchDelegate extends GdbLaunchDelegate {
}
final ManifestData manifestData = AndroidManifestHelper.parseForData(project);
+ final ManifestInfo manifestInfo = ManifestInfo.get(project);
+ final AndroidVersion minSdkVersion = new AndroidVersion(
+ manifestInfo.getMinSdkVersion(),
+ manifestInfo.getMinSdkCodeName());
// Get the activity name to launch
String activityName = getActivityToLaunch(
@@ -159,7 +164,7 @@ public class NdkGdbLaunchDelegate extends GdbLaunchDelegate {
AdtPlugin.getDisplay().getActiveShell(),
response,
manifestData.getPackage(),
- projectTarget);
+ projectTarget, minSdkVersion);
if (dialog.open() == Dialog.OK) {
DeviceChoiceCache.put(configName, response);
continueLaunch[0] = true;