Merge "Don't allow connection to profiles in TURNING_OFF state." into froyo
diff --git a/Android.mk b/Android.mk
index 5a4c547..cecc26a 100644
--- a/Android.mk
+++ b/Android.mk
@@ -381,6 +381,8 @@
-hdf android.hasSamples 1 \
-samplecode $(sample_dir)/ApiDemos \
resources/samples/ApiDemos "API Demos" \
+ -samplecode $(sample_dir)/BackupRestore \
+ resources/samples/BackupRestore "Backup and Restore" \
-samplecode $(sample_dir)/BluetoothChat \
resources/samples/BluetoothChat "Bluetooth Chat" \
-samplecode $(sample_dir)/BusinessCard \
diff --git a/api/current.xml b/api/current.xml
index 692cb16..21b75eb 100644
--- a/api/current.xml
+++ b/api/current.xml
@@ -71656,7 +71656,7 @@
<exception name="IOException" type="java.io.IOException">
</exception>
</method>
-<method name="setZoomCallback"
+<method name="setZoomChangeListener"
return="void"
abstract="false"
native="false"
@@ -71666,7 +71666,7 @@
deprecated="not deprecated"
visibility="public"
>
-<parameter name="cb" type="android.hardware.Camera.ZoomCallback">
+<parameter name="listener" type="android.hardware.Camera.OnZoomChangeListener">
</parameter>
</method>
<method name="startPreview"
@@ -71831,6 +71831,31 @@
</parameter>
</method>
</interface>
+<interface name="Camera.OnZoomChangeListener"
+ abstract="true"
+ static="true"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<method name="onZoomChange"
+ return="void"
+ abstract="true"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="zoomValue" type="int">
+</parameter>
+<parameter name="stopped" type="boolean">
+</parameter>
+<parameter name="camera" type="android.hardware.Camera">
+</parameter>
+</method>
+</interface>
<class name="Camera.Parameters"
extends="java.lang.Object"
abstract="false"
@@ -73255,31 +73280,6 @@
>
</field>
</class>
-<interface name="Camera.ZoomCallback"
- abstract="true"
- static="true"
- final="false"
- deprecated="not deprecated"
- visibility="public"
->
-<method name="onZoomUpdate"
- return="void"
- abstract="true"
- native="false"
- synchronized="false"
- static="false"
- final="false"
- deprecated="not deprecated"
- visibility="public"
->
-<parameter name="zoomValue" type="int">
-</parameter>
-<parameter name="stopped" type="boolean">
-</parameter>
-<parameter name="camera" type="android.hardware.Camera">
-</parameter>
-</method>
-</interface>
<class name="GeomagneticField"
extends="java.lang.Object"
abstract="false"
@@ -85230,7 +85230,7 @@
</parameter>
<parameter name="mimeTypes" type="java.lang.String[]">
</parameter>
-<parameter name="callback" type="android.media.MediaScannerConnection.ScanResultListener">
+<parameter name="callback" type="android.media.MediaScannerConnection.OnScanCompletedListener">
</parameter>
</method>
</class>
@@ -85241,7 +85241,7 @@
deprecated="not deprecated"
visibility="public"
>
-<implements name="android.media.MediaScannerConnection.ScanResultListener">
+<implements name="android.media.MediaScannerConnection.OnScanCompletedListener">
</implements>
<method name="onMediaScannerConnected"
return="void"
@@ -85270,7 +85270,7 @@
</parameter>
</method>
</interface>
-<interface name="MediaScannerConnection.ScanResultListener"
+<interface name="MediaScannerConnection.OnScanCompletedListener"
abstract="true"
static="true"
final="false"
diff --git a/cmds/bmgr/src/com/android/commands/bmgr/Bmgr.java b/cmds/bmgr/src/com/android/commands/bmgr/Bmgr.java
index 5612158..8263e75 100644
--- a/cmds/bmgr/src/com/android/commands/bmgr/Bmgr.java
+++ b/cmds/bmgr/src/com/android/commands/bmgr/Bmgr.java
@@ -373,7 +373,7 @@
}
RestoreSet[] sets = null;
int err = mRestore.getAvailableRestoreSets(observer);
- if (err != 0) {
+ if (err == 0) {
observer.waitForCompletion();
sets = observer.sets;
for (RestoreSet s : sets) {
diff --git a/cmds/pm/src/com/android/commands/pm/Pm.java b/cmds/pm/src/com/android/commands/pm/Pm.java
index 659d70f..9b8b0ac 100644
--- a/cmds/pm/src/com/android/commands/pm/Pm.java
+++ b/cmds/pm/src/com/android/commands/pm/Pm.java
@@ -16,6 +16,8 @@
package com.android.commands.pm;
+import com.android.internal.content.PackageHelper;
+
import android.content.ComponentName;
import android.content.pm.ApplicationInfo;
import android.content.pm.FeatureInfo;
@@ -33,6 +35,7 @@
import android.net.Uri;
import android.os.RemoteException;
import android.os.ServiceManager;
+import android.provider.Settings;
import java.io.File;
import java.lang.reflect.Field;
@@ -107,6 +110,16 @@
return;
}
+ if ("setInstallLocation".equals(op)) {
+ runSetInstallLocation();
+ return;
+ }
+
+ if ("getInstallLocation".equals(op)) {
+ runGetInstallLocation();
+ return;
+ }
+
try {
if (args.length == 1) {
if (args[0].equalsIgnoreCase("-l")) {
@@ -575,6 +588,51 @@
return Integer.toString(result);
}
+ private void runSetInstallLocation() {
+ int loc;
+
+ String arg = nextArg();
+ if (arg == null) {
+ System.err.println("Error: no install location specified.");
+ showUsage();
+ return;
+ }
+ try {
+ loc = Integer.parseInt(arg);
+ } catch (NumberFormatException e) {
+ System.err.println("Error: install location has to be a number.");
+ showUsage();
+ return;
+ }
+ try {
+ if (!mPm.setInstallLocation(loc)) {
+ System.err.println("Error: install location has to be a number.");
+ showUsage();
+ }
+ } catch (RemoteException e) {
+ System.err.println(e.toString());
+ System.err.println(PM_NOT_RUNNING_ERR);
+ }
+ }
+
+ private void runGetInstallLocation() {
+ try {
+ int loc = mPm.getInstallLocation();
+ String locStr = "invalid";
+ if (loc == PackageHelper.APP_INSTALL_AUTO) {
+ locStr = "auto";
+ } else if (loc == PackageHelper.APP_INSTALL_INTERNAL) {
+ locStr = "internal";
+ } else if (loc == PackageHelper.APP_INSTALL_EXTERNAL) {
+ locStr = "external";
+ }
+ System.out.println(loc + "[" + locStr + "]");
+ } catch (RemoteException e) {
+ System.err.println(e.toString());
+ System.err.println(PM_NOT_RUNNING_ERR);
+ }
+ }
+
private void runInstall() {
int installFlags = 0;
String installerPackageName = null;
@@ -832,6 +890,7 @@
System.err.println(" pm uninstall [-k] PACKAGE");
System.err.println(" pm enable PACKAGE_OR_COMPONENT");
System.err.println(" pm disable PACKAGE_OR_COMPONENT");
+ System.err.println(" pm setInstallLocation [0/auto] [1/internal] [2/external]");
System.err.println("");
System.err.println("The list packages command prints all packages. Options:");
System.err.println(" -f: see their associated file.");
@@ -867,10 +926,17 @@
System.err.println(" -k: keep the data and cache directories around.");
System.err.println("after the package removal.");
System.err.println("");
- System.err.println("The mountsd command simulates mounting/unmounting sdcard.Options:");
- System.err.println(" -m: true or false.");
- System.err.println("");
System.err.println("The enable and disable commands change the enabled state of");
System.err.println("a given package or component (written as \"package/class\").");
+ System.err.println("");
+ System.err.println("The getInstallLocation command gets the current install location");
+ System.err.println(" 0 [auto]: Let system decide the best location");
+ System.err.println(" 1 [internal]: Install on internal device storage");
+ System.err.println(" 2 [external]: Install on external media");
+ System.err.println("");
+ System.err.println("The setInstallLocation command changes the default install location");
+ System.err.println(" 0 [auto]: Let system decide the best location");
+ System.err.println(" 1 [internal]: Install on internal device storage");
+ System.err.println(" 2 [external]: Install on external media");
}
}
diff --git a/core/java/android/app/ContextImpl.java b/core/java/android/app/ContextImpl.java
index b07b690..950f34f 100644
--- a/core/java/android/app/ContextImpl.java
+++ b/core/java/android/app/ContextImpl.java
@@ -1482,8 +1482,9 @@
mPackageInfo = packageInfo;
mResources = mPackageInfo.getResources(mainThread);
- if (container != null && container.getCompatibilityInfo().applicationScale !=
- mResources.getCompatibilityInfo().applicationScale) {
+ if (mResources != null && container != null
+ && container.getCompatibilityInfo().applicationScale !=
+ mResources.getCompatibilityInfo().applicationScale) {
if (DEBUG) {
Log.d(TAG, "loaded context has different scaling. Using container's" +
" compatiblity info:" + container.getDisplayMetrics());
diff --git a/core/java/android/app/IntentService.java b/core/java/android/app/IntentService.java
index 1d6c125..7c2d3a0 100644
--- a/core/java/android/app/IntentService.java
+++ b/core/java/android/app/IntentService.java
@@ -24,11 +24,24 @@
import android.os.Message;
/**
- * An abstract {@link Service} that serializes the handling of the Intents passed upon service
- * start and handles them on a handler thread.
+ * IntentService is a base class for {@link Service}s that handle asynchronous
+ * requests (expressed as {@link Intent}s) on demand. Clients send requests
+ * through {@link android.content.Context#startService(Intent)} calls; the
+ * service is started as needed, handles each Intent in turn using a worker
+ * thread, and stops itself when it runs out of work.
*
- * <p>To use this class extend it and implement {@link #onHandleIntent}. The {@link Service} will
- * automatically be stopped when the last enqueued {@link Intent} is handled.
+ * <p>This "work queue processor" pattern is commonly used to offload tasks
+ * from an application's main thread. The IntentService class exists to
+ * simplify this pattern and take care of the mechanics. To use it, extend
+ * IntentService and implement {@link #onHandleIntent(Intent)}. IntentService
+ * will receive the Intents, launch a worker thread, and stop the service as
+ * appropriate.
+ *
+ * <p>All requests are handled on a single worker thread -- they may take as
+ * long as necessary (and will not block the application's main loop), but
+ * only one request will be processed at a time.
+ *
+ * @see android.os.AsyncTask
*/
public abstract class IntentService extends Service {
private volatile Looper mServiceLooper;
@@ -48,26 +61,42 @@
}
}
+ /**
+ * Creates an IntentService. Invoked by your subclass's constructor.
+ *
+ * @param name Used to name the worker thread, important only for debugging.
+ */
public IntentService(String name) {
super();
mName = name;
}
/**
- * Control redelivery of intents. If called with true,
+ * Sets intent redelivery preferences. Usually called from the constructor
+ * with your preferred semantics.
+ *
+ * <p>If enabled is true,
* {@link #onStartCommand(Intent, int, int)} will return
- * {@link Service#START_REDELIVER_INTENT} instead of
- * {@link Service#START_NOT_STICKY}, so that if this service's process
- * is killed while it is executing the Intent in
- * {@link #onHandleIntent(Intent)}, then when later restarted the same Intent
- * will be re-delivered to it, to retry its execution.
+ * {@link Service#START_REDELIVER_INTENT}, so if this process dies before
+ * {@link #onHandleIntent(Intent)} returns, the process will be restarted
+ * and the intent redelivered. If multiple Intents have been sent, only
+ * the most recent one is guaranteed to be redelivered.
+ *
+ * <p>If enabled is false (the default),
+ * {@link #onStartCommand(Intent, int, int)} will return
+ * {@link Service#START_NOT_STICKY}, and if the process dies, the Intent
+ * dies along with it.
*/
public void setIntentRedelivery(boolean enabled) {
mRedelivery = enabled;
}
-
+
@Override
public void onCreate() {
+ // TODO: It would be nice to have an option to hold a partial wakelock
+ // during processing, and to have a static startService(Context, Intent)
+ // method that would launch the service & hand off a wakelock.
+
super.onCreate();
HandlerThread thread = new HandlerThread("IntentService[" + mName + "]");
thread.start();
@@ -89,7 +118,7 @@
onStart(intent, startId);
return mRedelivery ? START_REDELIVER_INTENT : START_NOT_STICKY;
}
-
+
@Override
public void onDestroy() {
mServiceLooper.quit();
@@ -101,9 +130,14 @@
}
/**
- * Invoked on the Handler thread with the {@link Intent} that is passed to {@link #onStart}.
- * Note that this will be invoked from a different thread than the one that handles the
- * {@link #onStart} call.
+ * This method is invoked on the worker thread with a request to process.
+ * Only one Intent is processed at a time, but the processing happens on a
+ * worker thread that runs independently from other application logic.
+ * So, if this code takes a long time, it will hold up other requests to
+ * the same IntentService, but it will not hold up anything else.
+ *
+ * @param intent The value passed to {@link
+ * android.content.Context#startService(Intent)}.
*/
protected abstract void onHandleIntent(Intent intent);
}
diff --git a/core/java/android/app/SearchDialog.java b/core/java/android/app/SearchDialog.java
index 9d217ec..7625c04 100644
--- a/core/java/android/app/SearchDialog.java
+++ b/core/java/android/app/SearchDialog.java
@@ -123,6 +123,9 @@
// that modifies the contents of the text field. But if the user then edits
// the suggestion, the resulting string is saved.
private String mUserQuery;
+ // The query passed in when opening the SearchDialog. Used in the browser
+ // case to determine whether the user has edited the query.
+ private String mInitialQuery;
// A weak map of drawables we've gotten from other packages, so we don't load them
// more than once.
@@ -253,6 +256,7 @@
return false;
}
+ mInitialQuery = initialQuery == null ? "" : initialQuery;
// finally, load the user's initial text (which may trigger suggestions)
setUserQuery(initialQuery);
if (selectInitialQuery) {
@@ -329,6 +333,7 @@
mAppSearchData = null;
mSearchable = null;
mUserQuery = null;
+ mInitialQuery = null;
}
/**
@@ -687,13 +692,16 @@
if (mSearchable == null) {
return;
}
- updateWidgetState();
if (!mSearchAutoComplete.isPerformingCompletion()) {
// The user changed the query, remember it.
mUserQuery = s == null ? "" : s.toString();
}
+ updateWidgetState();
// Always want to show the microphone if the context is voice.
+ // Also show the microphone if this is a browser search and the
+ // query matches the initial query.
updateVoiceButton(mSearchAutoComplete.isEmpty()
+ || (isBrowserSearch() && mInitialQuery.equals(mUserQuery))
|| (mAppSearchData != null && mAppSearchData.getBoolean(
SearchManager.CONTEXT_IS_VOICE)));
}
@@ -724,8 +732,9 @@
// enable the button if we have one or more non-space characters
boolean enabled = !mSearchAutoComplete.isEmpty();
if (isBrowserSearch()) {
- // In the browser, we hide the search button when there is no text
- if (enabled) {
+ // In the browser, we hide the search button when there is no text,
+ // or if the text matches the initial query.
+ if (enabled && !mInitialQuery.equals(mUserQuery)) {
mSearchAutoComplete.setBackgroundResource(
com.android.internal.R.drawable.textfield_search);
mGoButton.setVisibility(View.VISIBLE);
diff --git a/core/java/android/content/Context.java b/core/java/android/content/Context.java
index ee87290..3a2aa55 100644
--- a/core/java/android/content/Context.java
+++ b/core/java/android/content/Context.java
@@ -25,7 +25,6 @@
import android.database.sqlite.SQLiteDatabase.CursorFactory;
import android.graphics.Bitmap;
import android.graphics.drawable.Drawable;
-import android.media.MediaScannerConnection.ScanResultListener;
import android.net.Uri;
import android.os.Bundle;
import android.os.Handler;
@@ -444,7 +443,7 @@
* are not automatically scanned by the media scanner, you can explicitly
* add them to the media database with
* {@link android.media.MediaScannerConnection#scanFile(Context, String[], String[],
- * ScanResultListener) MediaScannerConnection.scanFile}.
+ * OnScanCompletedListener) MediaScannerConnection.scanFile}.
* Note that this is not the same as
* {@link android.os.Environment#getExternalStoragePublicDirectory
* Environment.getExternalStoragePublicDirectory()}, which provides
diff --git a/core/java/android/content/SyncStorageEngine.java b/core/java/android/content/SyncStorageEngine.java
index 984c070..98a4993 100644
--- a/core/java/android/content/SyncStorageEngine.java
+++ b/core/java/android/content/SyncStorageEngine.java
@@ -330,11 +330,11 @@
@Override public void handleMessage(Message msg) {
if (msg.what == MSG_WRITE_STATUS) {
- synchronized (mAccounts) {
+ synchronized (mAuthorities) {
writeStatusLocked();
}
} else if (msg.what == MSG_WRITE_STATISTICS) {
- synchronized (mAccounts) {
+ synchronized (mAuthorities) {
writeStatisticsLocked();
}
}
diff --git a/core/java/android/content/pm/IPackageManager.aidl b/core/java/android/content/pm/IPackageManager.aidl
index f90ef63..9939478 100644
--- a/core/java/android/content/pm/IPackageManager.aidl
+++ b/core/java/android/content/pm/IPackageManager.aidl
@@ -316,4 +316,7 @@
void movePackage(String packageName, IPackageMoveObserver observer, int flags);
boolean addPermissionAsync(in PermissionInfo info);
+
+ boolean setInstallLocation(int loc);
+ int getInstallLocation();
}
diff --git a/core/java/android/hardware/Camera.java b/core/java/android/hardware/Camera.java
index abebdeb9..2495619 100644
--- a/core/java/android/hardware/Camera.java
+++ b/core/java/android/hardware/Camera.java
@@ -78,7 +78,7 @@
private PreviewCallback mPreviewCallback;
private PictureCallback mPostviewCallback;
private AutoFocusCallback mAutoFocusCallback;
- private ZoomCallback mZoomCallback;
+ private OnZoomChangeListener mZoomListener;
private ErrorCallback mErrorCallback;
private boolean mOneShot;
private boolean mWithBuffer;
@@ -96,7 +96,7 @@
mJpegCallback = null;
mPreviewCallback = null;
mPostviewCallback = null;
- mZoomCallback = null;
+ mZoomListener = null;
Looper looper;
if ((looper = Looper.myLooper()) != null) {
@@ -270,16 +270,18 @@
}
/**
- * Adds a pre-allocated buffer to the callback buffer queue. Applications
- * can add one or more buffers to the queue. When a preview frame arrives
- * and there is still available buffer, buffer will be filled and it is
- * removed from the queue. Then preview callback is invoked with the buffer.
- * If a frame arrives and there is no buffer left, the frame is discarded.
- * Applications should add the buffers back when they finish the processing.
+ * Adds a pre-allocated buffer to the preview callback buffer queue.
+ * Applications can add one or more buffers to the queue. When a preview
+ * frame arrives and there is still available buffer, buffer will be filled
+ * and it is removed from the queue. Then preview callback is invoked with
+ * the buffer. If a frame arrives and there is no buffer left, the frame is
+ * discarded. Applications should add the buffers back when they finish the
+ * processing.
*
- * Preview width and height can be determined from getPreviewSize, and bitsPerPixel can be
- * found from {@link android.hardware.Camera.Parameters#getPreviewFormat()}
- * and {@link android.graphics.ImageFormat#getBitsPerPixel(int)}.
+ * The image format of the callback buffer can be read from {@link
+ * android.hardware.Camera.Parameters#getPreviewFormat()}. bitsPerPixel can
+ * be read from {@link android.graphics.ImageFormat#getBitsPerPixel(int)}.
+ * Preview width and height can be determined from getPreviewSize.
*
* Alternatively, a buffer from a previous callback may be passed in or used
* to determine the size of new preview frame buffers.
@@ -350,8 +352,8 @@
return;
case CAMERA_MSG_ZOOM:
- if (mZoomCallback != null) {
- mZoomCallback.onZoomUpdate(msg.arg1, msg.arg2 != 0, mCamera);
+ if (mZoomListener != null) {
+ mZoomListener.onZoomChange(msg.arg1, msg.arg2 != 0, mCamera);
}
return;
@@ -526,15 +528,15 @@
}
/**
- * Zooms to the requested value smoothly. Driver will generate {@link
- * ZoomCallback} for the zoom value and whether zoom is stopped at the
- * time. For example, suppose the current zoom is 0 and startSmoothZoom is
- * called with value 3. Three ZoomCallback will be generated with zoom value
- * 1, 2, and 3. The applications can call {@link #stopSmoothZoom} to stop
- * the zoom earlier. The applications should not call startSmoothZoom again
- * or change the zoom value before zoom stops. If the passing zoom value
- * equals to the current zoom value, no zoom callback will be generated.
- * This method is supported if {@link
+ * Zooms to the requested value smoothly. Driver will notify {@link
+ * OnZoomChangeListener} of the zoom value and whether zoom is stopped at
+ * the time. For example, suppose the current zoom is 0 and startSmoothZoom
+ * is called with value 3. Method onZoomChange will be called three times
+ * with zoom value 1, 2, and 3. The applications can call {@link
+ * #stopSmoothZoom} to stop the zoom earlier. The applications should not
+ * call startSmoothZoom again or change the zoom value before zoom stops. If
+ * the passing zoom value equals to the current zoom value, no zoom callback
+ * will be generated. This method is supported if {@link
* android.hardware.Camera.Parameters#isSmoothZoomSupported} is true.
*
* @param value zoom value. The valid range is 0 to {@link
@@ -546,8 +548,8 @@
/**
* Stops the smooth zoom. The applications should wait for the {@link
- * ZoomCallback} to know when the zoom is actually stopped. This method is
- * supported if {@link
+ * OnZoomChangeListener} to know when the zoom is actually stopped. This
+ * method is supported if {@link
* android.hardware.Camera.Parameters#isSmoothZoomSupported} is true.
*
* @throws RuntimeException if the method fails.
@@ -570,35 +572,34 @@
public native final void setDisplayOrientation(int degrees);
/**
- * Handles the zoom callback.
- *
+ * Interface for a callback to be invoked when zoom value changes.
*/
- public interface ZoomCallback
+ public interface OnZoomChangeListener
{
/**
- * Callback for zoom updates
+ * Called when the zoom value has changed.
*
* @param zoomValue the current zoom value. In smooth zoom mode, camera
- * generates this callback for every new zoom value.
+ * calls this for every new zoom value.
* @param stopped whether smooth zoom is stopped. If the value is true,
* this is the last zoom update for the application.
*
* @param camera the Camera service object
* @see #startSmoothZoom(int)
*/
- void onZoomUpdate(int zoomValue, boolean stopped, Camera camera);
+ void onZoomChange(int zoomValue, boolean stopped, Camera camera);
};
/**
- * Registers a callback to be invoked when the zoom value is updated by the
+ * Registers a listener to be notified when the zoom value is updated by the
* camera driver during smooth zoom.
*
- * @param cb the callback to run
+ * @param listener the listener to notify
* @see #startSmoothZoom(int)
*/
- public final void setZoomCallback(ZoomCallback cb)
+ public final void setZoomChangeListener(OnZoomChangeListener listener)
{
- mZoomCallback = cb;
+ mZoomListener = listener;
}
// These match the enum in include/ui/Camera.h
@@ -992,7 +993,7 @@
/**
* Gets the supported preview sizes.
*
- * @return a List of Size object. This method will always return a list
+ * @return a list of Size object. This method will always return a list
* with at least one element.
*/
public List<Size> getSupportedPreviewSizes() {
@@ -1027,7 +1028,7 @@
/**
* Gets the supported jpeg thumbnail sizes.
*
- * @return a List of Size object. This method will always return a list
+ * @return a list of Size object. This method will always return a list
* with at least two elements. Size 0,0 (no thumbnail) is always
* supported.
*/
@@ -1098,8 +1099,8 @@
/**
* Gets the supported preview frame rates.
*
- * @return a List of Integer objects (preview frame rates). null if
- * preview frame rate setting is not supported.
+ * @return a list of supported preview frame rates. null if preview
+ * frame rate setting is not supported.
*/
public List<Integer> getSupportedPreviewFrameRates() {
String str = get(KEY_PREVIEW_FRAME_RATE + SUPPORTED_VALUES_SUFFIX);
@@ -1130,11 +1131,11 @@
}
/**
- * Returns the image format for preview pictures got from
+ * Returns the image format for preview frames got from
* {@link PreviewCallback}.
*
- * @return the {@link android.graphics.ImageFormat} int representing
- * the preview picture format.
+ * @return the preview format.
+ * @see android.graphics.ImageFormat
*/
public int getPreviewFormat() {
return pixelFormatForCameraFormat(get(KEY_PREVIEW_FORMAT));
@@ -1143,8 +1144,9 @@
/**
* Gets the supported preview formats.
*
- * @return a List of Integer objects. This method will always return a
- * list with at least one element.
+ * @return a list of supported preview formats. This method will always
+ * return a list with at least one element.
+ * @see android.graphics.ImageFormat
*/
public List<Integer> getSupportedPreviewFormats() {
String str = get(KEY_PREVIEW_FORMAT + SUPPORTED_VALUES_SUFFIX);
@@ -1182,8 +1184,8 @@
/**
* Gets the supported picture sizes.
*
- * @return a List of Size objects. This method will always return a list
- * with at least one element.
+ * @return a list of supported picture sizes. This method will always
+ * return a list with at least one element.
*/
public List<Size> getSupportedPictureSizes() {
String str = get(KEY_PICTURE_SIZE + SUPPORTED_VALUES_SUFFIX);
@@ -1212,7 +1214,8 @@
/**
* Returns the image format for pictures.
*
- * @return the ImageFormat int representing the picture format
+ * @return the picture format
+ * @see android.graphics.ImageFormat
*/
public int getPictureFormat() {
return pixelFormatForCameraFormat(get(KEY_PICTURE_FORMAT));
@@ -1221,8 +1224,9 @@
/**
* Gets the supported picture formats.
*
- * @return a List of Integer objects (values are ImageFormat.XXX). This
- * method will always return a list with at least one element.
+ * @return supported picture formats. This method will always return a
+ * list with at least one element.
+ * @see android.graphics.ImageFormat
*/
public List<Integer> getSupportedPictureFormats() {
String str = get(KEY_PICTURE_FORMAT + SUPPORTED_VALUES_SUFFIX);
@@ -1361,8 +1365,17 @@
/**
* Gets the current white balance setting.
*
- * @return one of WHITE_BALANCE_XXX string constant. null if white
- * balance setting is not supported.
+ * @return current white balance. null if white balance setting is not
+ * supported.
+ * @see #WHITE_BALANCE_AUTO
+ * @see #WHITE_BALANCE_INCANDESCENT
+ * @see #WHITE_BALANCE_FLUORESCENT
+ * @see #WHITE_BALANCE_WARM_FLUORESCENT
+ * @see #WHITE_BALANCE_DAYLIGHT
+ * @see #WHITE_BALANCE_CLOUDY_DAYLIGHT
+ * @see #WHITE_BALANCE_TWILIGHT
+ * @see #WHITE_BALANCE_SHADE
+ *
*/
public String getWhiteBalance() {
return get(KEY_WHITE_BALANCE);
@@ -1371,7 +1384,8 @@
/**
* Sets the white balance.
*
- * @param value WHITE_BALANCE_XXX string constant.
+ * @param value new white balance.
+ * @see #getWhiteBalance()
*/
public void setWhiteBalance(String value) {
set(KEY_WHITE_BALANCE, value);
@@ -1380,8 +1394,9 @@
/**
* Gets the supported white balance.
*
- * @return a List of WHITE_BALANCE_XXX string constants. null if white
- * balance setting is not supported.
+ * @return a list of supported white balance. null if white balance
+ * setting is not supported.
+ * @see #getWhiteBalance()
*/
public List<String> getSupportedWhiteBalance() {
String str = get(KEY_WHITE_BALANCE + SUPPORTED_VALUES_SUFFIX);
@@ -1391,8 +1406,17 @@
/**
* Gets the current color effect setting.
*
- * @return one of EFFECT_XXX string constant. null if color effect
+ * @return current color effect. null if color effect
* setting is not supported.
+ * @see #EFFECT_NONE
+ * @see #EFFECT_MONO
+ * @see #EFFECT_NEGATIVE
+ * @see #EFFECT_SOLARIZE
+ * @see #EFFECT_SEPIA
+ * @see #EFFECT_POSTERIZE
+ * @see #EFFECT_WHITEBOARD
+ * @see #EFFECT_BLACKBOARD
+ * @see #EFFECT_AQUA
*/
public String getColorEffect() {
return get(KEY_EFFECT);
@@ -1401,7 +1425,8 @@
/**
* Sets the current color effect setting.
*
- * @param value EFFECT_XXX string constants.
+ * @param value new color effect.
+ * @see #getColorEffect()
*/
public void setColorEffect(String value) {
set(KEY_EFFECT, value);
@@ -1410,8 +1435,9 @@
/**
* Gets the supported color effects.
*
- * @return a List of EFFECT_XXX string constants. null if color effect
+ * @return a list of supported color effects. null if color effect
* setting is not supported.
+ * @see #getColorEffect()
*/
public List<String> getSupportedColorEffects() {
String str = get(KEY_EFFECT + SUPPORTED_VALUES_SUFFIX);
@@ -1422,8 +1448,12 @@
/**
* Gets the current antibanding setting.
*
- * @return one of ANTIBANDING_XXX string constant. null if antibanding
- * setting is not supported.
+ * @return current antibanding. null if antibanding setting is not
+ * supported.
+ * @see #ANTIBANDING_AUTO
+ * @see #ANTIBANDING_50HZ
+ * @see #ANTIBANDING_60HZ
+ * @see #ANTIBANDING_OFF
*/
public String getAntibanding() {
return get(KEY_ANTIBANDING);
@@ -1432,7 +1462,8 @@
/**
* Sets the antibanding.
*
- * @param antibanding ANTIBANDING_XXX string constant.
+ * @param antibanding new antibanding value.
+ * @see #getAntibanding()
*/
public void setAntibanding(String antibanding) {
set(KEY_ANTIBANDING, antibanding);
@@ -1441,8 +1472,9 @@
/**
* Gets the supported antibanding values.
*
- * @return a List of ANTIBANDING_XXX string constants. null if
- * antibanding setting is not supported.
+ * @return a list of supported antibanding values. null if antibanding
+ * setting is not supported.
+ * @see #getAntibanding()
*/
public List<String> getSupportedAntibanding() {
String str = get(KEY_ANTIBANDING + SUPPORTED_VALUES_SUFFIX);
@@ -1454,6 +1486,21 @@
*
* @return one of SCENE_MODE_XXX string constant. null if scene mode
* setting is not supported.
+ * @see #SCENE_MODE_AUTO
+ * @see #SCENE_MODE_ACTION
+ * @see #SCENE_MODE_PORTRAIT
+ * @see #SCENE_MODE_LANDSCAPE
+ * @see #SCENE_MODE_NIGHT
+ * @see #SCENE_MODE_NIGHT_PORTRAIT
+ * @see #SCENE_MODE_THEATRE
+ * @see #SCENE_MODE_BEACH
+ * @see #SCENE_MODE_SNOW
+ * @see #SCENE_MODE_SUNSET
+ * @see #SCENE_MODE_STEADYPHOTO
+ * @see #SCENE_MODE_FIREWORKS
+ * @see #SCENE_MODE_SPORTS
+ * @see #SCENE_MODE_PARTY
+ * @see #SCENE_MODE_CANDLELIGHT
*/
public String getSceneMode() {
return get(KEY_SCENE_MODE);
@@ -1466,7 +1513,8 @@
* applications should call getParameters to know if some parameters are
* changed.
*
- * @param value SCENE_MODE_XXX string constants.
+ * @param value scene mode.
+ * @see #getSceneMode()
*/
public void setSceneMode(String value) {
set(KEY_SCENE_MODE, value);
@@ -1475,8 +1523,9 @@
/**
* Gets the supported scene modes.
*
- * @return a List of SCENE_MODE_XXX string constant. null if scene mode
- * setting is not supported.
+ * @return a list of supported scene modes. null if scene mode setting
+ * is not supported.
+ * @see #getSceneMode()
*/
public List<String> getSupportedSceneModes() {
String str = get(KEY_SCENE_MODE + SUPPORTED_VALUES_SUFFIX);
@@ -1486,8 +1535,13 @@
/**
* Gets the current flash mode setting.
*
- * @return one of FLASH_MODE_XXX string constant. null if flash mode
- * setting is not supported.
+ * @return current flash mode. null if flash mode setting is not
+ * supported.
+ * @see #FLASH_MODE_OFF
+ * @see #FLASH_MODE_AUTO
+ * @see #FLASH_MODE_ON
+ * @see #FLASH_MODE_RED_EYE
+ * @see #FLASH_MODE_TORCH
*/
public String getFlashMode() {
return get(KEY_FLASH_MODE);
@@ -1496,7 +1550,8 @@
/**
* Sets the flash mode.
*
- * @param value FLASH_MODE_XXX string constants.
+ * @param value flash mode.
+ * @see #getFlashMode()
*/
public void setFlashMode(String value) {
set(KEY_FLASH_MODE, value);
@@ -1505,8 +1560,9 @@
/**
* Gets the supported flash modes.
*
- * @return a List of FLASH_MODE_XXX string constants. null if flash mode
- * setting is not supported.
+ * @return a list of supported flash modes. null if flash mode setting
+ * is not supported.
+ * @see #getFlashMode()
*/
public List<String> getSupportedFlashModes() {
String str = get(KEY_FLASH_MODE + SUPPORTED_VALUES_SUFFIX);
@@ -1516,11 +1572,15 @@
/**
* Gets the current focus mode setting.
*
- * @return one of FOCUS_MODE_XXX string constant. If the camera does not
- * support auto-focus, this should return {@link
- * #FOCUS_MODE_FIXED}. If the focus mode is not FOCUS_MODE_FIXED
- * or {@link #FOCUS_MODE_INFINITY}, applications should call
- * {@link #autoFocus(AutoFocusCallback)} to start the focus.
+ * @return current focus mode. If the camera does not support
+ * auto-focus, this should return {@link #FOCUS_MODE_FIXED}. If
+ * the focus mode is not FOCUS_MODE_FIXED or {@link
+ * #FOCUS_MODE_INFINITY}, applications should call {@link
+ * #autoFocus(AutoFocusCallback)} to start the focus.
+ * @see #FOCUS_MODE_AUTO
+ * @see #FOCUS_MODE_INFINITY
+ * @see #FOCUS_MODE_MACRO
+ * @see #FOCUS_MODE_FIXED
*/
public String getFocusMode() {
return get(KEY_FOCUS_MODE);
@@ -1529,7 +1589,8 @@
/**
* Sets the focus mode.
*
- * @param value FOCUS_MODE_XXX string constants.
+ * @param value focus mode.
+ * @see #getFocusMode()
*/
public void setFocusMode(String value) {
set(KEY_FOCUS_MODE, value);
@@ -1538,8 +1599,9 @@
/**
* Gets the supported focus modes.
*
- * @return a List of FOCUS_MODE_XXX string constants. This method will
- * always return a list with at least one element.
+ * @return a list of supported focus modes. This method will always
+ * return a list with at least one element.
+ * @see #getFocusMode()
*/
public List<String> getSupportedFocusModes() {
String str = get(KEY_FOCUS_MODE + SUPPORTED_VALUES_SUFFIX);
diff --git a/core/java/android/os/Environment.java b/core/java/android/os/Environment.java
index f7e7d39..812391c 100644
--- a/core/java/android/os/Environment.java
+++ b/core/java/android/os/Environment.java
@@ -166,9 +166,11 @@
* Standard directory in which to place files that have been downloaded by
* the user. Note that this is primarily a convention for the top-level
* public directory, you are free to download files anywhere in your own
- * private directories.
+ * private directories. Also note that though the constant here is
+ * named DIRECTORY_DOWNLOADS (plural), the actual file name is non-plural for
+ * backwards compatibility reasons.
*/
- public static String DIRECTORY_DOWNLOADS = "Downloads";
+ public static String DIRECTORY_DOWNLOADS = "Download";
/**
* The traditional location for pictures and videos when mounting the
diff --git a/core/java/android/os/INetworkManagementService.aidl b/core/java/android/os/INetworkManagementService.aidl
index 7f16b4c..212c5fb 100644
--- a/core/java/android/os/INetworkManagementService.aidl
+++ b/core/java/android/os/INetworkManagementService.aidl
@@ -193,7 +193,7 @@
/**
* Configures bandwidth throttling on an interface
*/
- void setInterfaceThrottle(String iface, int maxKbits, int rxKbps, int txKbps);
+ void setInterfaceThrottle(String iface, int rxKbps, int txKbps);
/**
* Returns the currently configured RX throttle values
diff --git a/core/java/android/provider/Settings.java b/core/java/android/provider/Settings.java
index b8e5747..c07ac31 100644
--- a/core/java/android/provider/Settings.java
+++ b/core/java/android/provider/Settings.java
@@ -1611,21 +1611,6 @@
public static final String NOTIFICATION_LIGHT_PULSE = "notification_light_pulse";
/**
- * Let user pick default install location.
- * @hide
- */
- public static final String SET_INSTALL_LOCATION = "set_install_location";
-
- /**
- * Default install location value.
- * 0 = auto, let system decide
- * 1 = internal
- * 2 = sdcard
- * @hide
- */
- public static final String DEFAULT_INSTALL_LOCATION = "default_install_location";
-
- /**
* Show pointer location on screen?
* 0 = no
* 1 = yes
@@ -3295,6 +3280,21 @@
* @hide
*/
public static final String UI_NIGHT_MODE = "ui_night_mode";
+
+ /**
+ * Let user pick default install location.
+ * @hide
+ */
+ public static final String SET_INSTALL_LOCATION = "set_install_location";
+
+ /**
+ * Default install location value.
+ * 0 = auto, let system decide
+ * 1 = internal
+ * 2 = sdcard
+ * @hide
+ */
+ public static final String DEFAULT_INSTALL_LOCATION = "default_install_location";
/**
* @hide
diff --git a/core/java/android/text/method/PasswordTransformationMethod.java b/core/java/android/text/method/PasswordTransformationMethod.java
index fad4f64..b769b76 100644
--- a/core/java/android/text/method/PasswordTransformationMethod.java
+++ b/core/java/android/text/method/PasswordTransformationMethod.java
@@ -51,6 +51,8 @@
sp.removeSpan(vr[i]);
}
+ removeVisibleSpans(sp);
+
sp.setSpan(new ViewReference(view), 0, 0,
Spannable.SPAN_POINT_POINT);
}
@@ -100,10 +102,7 @@
int pref = TextKeyListener.getInstance().getPrefs(v.getContext());
if ((pref & TextKeyListener.SHOW_PASSWORD) != 0) {
if (count > 0) {
- Visible[] old = sp.getSpans(0, sp.length(), Visible.class);
- for (int i = 0; i < old.length; i++) {
- sp.removeSpan(old[i]);
- }
+ removeVisibleSpans(sp);
if (count == 1) {
sp.setSpan(new Visible(sp, this), start, start + count,
@@ -125,14 +124,18 @@
if (sourceText instanceof Spannable) {
Spannable sp = (Spannable) sourceText;
- Visible[] old = sp.getSpans(0, sp.length(), Visible.class);
- for (int i = 0; i < old.length; i++) {
- sp.removeSpan(old[i]);
- }
+ removeVisibleSpans(sp);
}
}
}
+ private static void removeVisibleSpans(Spannable sp) {
+ Visible[] old = sp.getSpans(0, sp.length(), Visible.class);
+ for (int i = 0; i < old.length; i++) {
+ sp.removeSpan(old[i]);
+ }
+ }
+
private static class PasswordCharSequence
implements CharSequence, GetChars
{
diff --git a/core/java/android/view/ViewRoot.java b/core/java/android/view/ViewRoot.java
index ed83bca..e56a6fe 100644
--- a/core/java/android/view/ViewRoot.java
+++ b/core/java/android/view/ViewRoot.java
@@ -766,7 +766,7 @@
// make sure touch mode code executes by setting cached value
// to opposite of the added touch mode.
mAttachInfo.mInTouchMode = !mAddedTouchMode;
- ensureTouchModeLocally(mAddedTouchMode);
+ ensureTouchModeLocally(mAddedTouchMode, false);
} else {
if (!mAttachInfo.mContentInsets.equals(mPendingContentInsets)) {
mAttachInfo.mContentInsets.set(mPendingContentInsets);
@@ -852,7 +852,11 @@
}
boolean windowShouldResize = mLayoutRequested && windowResizesToFitContent
- && (mWidth != host.mMeasuredWidth || mHeight != host.mMeasuredHeight);
+ && ((mWidth != host.mMeasuredWidth || mHeight != host.mMeasuredHeight)
+ || (lp.width == ViewGroup.LayoutParams.WRAP_CONTENT &&
+ frame.width() < desiredWindowWidth && frame.width() != mWidth)
+ || (lp.height == ViewGroup.LayoutParams.WRAP_CONTENT &&
+ frame.height() < desiredWindowHeight && frame.height() != mHeight));
final boolean computesInternalInsets =
attachInfo.mTreeObserver.hasComputeInternalInsetsListeners();
@@ -979,7 +983,7 @@
}
boolean focusChangedDueToTouchMode = ensureTouchModeLocally(
- (relayoutResult&WindowManagerImpl.RELAYOUT_IN_TOUCH_MODE) != 0);
+ (relayoutResult&WindowManagerImpl.RELAYOUT_IN_TOUCH_MODE) != 0, true);
if (focusChangedDueToTouchMode || mWidth != host.mMeasuredWidth
|| mHeight != host.mMeasuredHeight || contentInsetsChanged) {
childWidthMeasureSpec = getRootMeasureSpec(mWidth, lp.width);
@@ -1039,6 +1043,13 @@
startTime = SystemClock.elapsedRealtime();
}
host.layout(0, 0, host.mMeasuredWidth, host.mMeasuredHeight);
+ if (mFirst) {
+ if (mAddedTouchMode) {
+ enterTouchMode();
+ } else {
+ leaveTouchMode();
+ }
+ }
if (Config.DEBUG && ViewDebug.consistencyCheckEnabled) {
if (!host.dispatchConsistencyCheck(ViewDebug.CONSISTENCY_LAYOUT)) {
@@ -1888,7 +1899,7 @@
mAttachInfo.mHasWindowFocus = hasWindowFocus;
if (hasWindowFocus) {
boolean inTouchMode = msg.arg2 != 0;
- ensureTouchModeLocally(inTouchMode);
+ ensureTouchModeLocally(inTouchMode, true);
if (mGlWanted) {
checkEglErrors();
@@ -1998,16 +2009,17 @@
}
// handle the change
- return ensureTouchModeLocally(inTouchMode);
+ return ensureTouchModeLocally(inTouchMode, true);
}
/**
* Ensure that the touch mode for this window is set, and if it is changing,
* take the appropriate action.
* @param inTouchMode Whether we want to be in touch mode.
+ * @param dispatchFocus
* @return True if the touch mode changed and focus changed was changed as a result
*/
- private boolean ensureTouchModeLocally(boolean inTouchMode) {
+ private boolean ensureTouchModeLocally(boolean inTouchMode, boolean dispatchFocus) {
if (DBG) Log.d("touchmode", "ensureTouchModeLocally(" + inTouchMode + "), current "
+ "touch mode is " + mAttachInfo.mInTouchMode);
@@ -2016,7 +2028,7 @@
mAttachInfo.mInTouchMode = inTouchMode;
mAttachInfo.mTreeObserver.dispatchOnTouchModeChanged(inTouchMode);
- return (inTouchMode) ? enterTouchMode() : leaveTouchMode();
+ return dispatchFocus && (inTouchMode) ? enterTouchMode() : leaveTouchMode();
}
private boolean enterTouchMode() {
diff --git a/core/java/android/view/WindowManager.java b/core/java/android/view/WindowManager.java
index 88d0c25..0aa1fde 100644
--- a/core/java/android/view/WindowManager.java
+++ b/core/java/android/view/WindowManager.java
@@ -405,8 +405,16 @@
name = "FLAG_LAYOUT_IN_SCREEN"),
@ViewDebug.FlagToString(mask = FLAG_DITHER, equals = FLAG_DITHER,
name = "FLAG_DITHER"),
+ @ViewDebug.FlagToString(mask = FLAG_TURN_SCREEN_ON, equals = FLAG_TURN_SCREEN_ON,
+ name = "FLAG_TURN_SCREEN_ON"),
@ViewDebug.FlagToString(mask = FLAG_KEEP_SCREEN_ON, equals = FLAG_KEEP_SCREEN_ON,
name = "FLAG_KEEP_SCREEN_ON"),
+ @ViewDebug.FlagToString(mask = FLAG_SHOW_WHEN_LOCKED, equals = FLAG_SHOW_WHEN_LOCKED,
+ name = "FLAG_SHOW_WHEN_LOCKED"),
+ @ViewDebug.FlagToString(mask = FLAG_ALLOW_LOCK_WHILE_SCREEN_ON, equals = FLAG_ALLOW_LOCK_WHILE_SCREEN_ON,
+ name = "FLAG_ALLOW_LOCK_WHILE_SCREEN_ON"),
+ @ViewDebug.FlagToString(mask = FLAG_DISMISS_KEYGUARD, equals = FLAG_DISMISS_KEYGUARD,
+ name = "FLAG_DISMISS_KEYGUARD"),
@ViewDebug.FlagToString(mask = FLAG_FULLSCREEN, equals = FLAG_FULLSCREEN,
name = "FLAG_FULLSCREEN"),
@ViewDebug.FlagToString(mask = FLAG_FORCE_NOT_FULLSCREEN,
diff --git a/core/java/android/webkit/HTML5VideoViewProxy.java b/core/java/android/webkit/HTML5VideoViewProxy.java
index 42e1539..eee8025 100644
--- a/core/java/android/webkit/HTML5VideoViewProxy.java
+++ b/core/java/android/webkit/HTML5VideoViewProxy.java
@@ -129,9 +129,10 @@
// is invoked.
mTimer.cancel();
mTimer = null;
- mCurrentProxy.playbackEnded();
+ if (mVideoView.isPlaying()) {
+ mVideoView.stopPlayback();
+ }
mCurrentProxy = null;
- mVideoView.stopPlayback();
mLayout.removeView(mVideoView);
mVideoView = null;
if (mProgressView != null) {
diff --git a/core/java/android/webkit/WebView.java b/core/java/android/webkit/WebView.java
index 5cfbe73..0526362 100644
--- a/core/java/android/webkit/WebView.java
+++ b/core/java/android/webkit/WebView.java
@@ -6153,7 +6153,7 @@
case UPDATE_ZOOM_RANGE: {
WebViewCore.RestoreState restoreState
= (WebViewCore.RestoreState) msg.obj;
- // mScrollX contains the new contentWidth
+ // mScrollX contains the new minPrefWidth
updateZoomRange(restoreState, getViewWidth(),
restoreState.mScrollX, false);
break;
@@ -6176,7 +6176,7 @@
boolean hasRestoreState = restoreState != null;
if (hasRestoreState) {
updateZoomRange(restoreState, viewSize.x,
- draw.mWidthHeight.x, true);
+ draw.mMinPrefWidth, true);
if (!mDrawHistory) {
mInZoomOverview = false;
@@ -6238,12 +6238,10 @@
// sMaxViewportWidth so that if the page doesn't behave
// well, the WebView won't go insane. limit the lower
// bound to match the default scale for mobile sites.
- // we choose the content width to be mZoomOverviewWidth.
- // this works for most of the sites. But some sites may
- // cause the page layout wider than it needs.
mZoomOverviewWidth = Math.min(sMaxViewportWidth, Math
- .max((int) (viewWidth / mDefaultScale),
- draw.mWidthHeight.x));
+ .max((int) (viewWidth / mDefaultScale), Math
+ .max(draw.mMinPrefWidth,
+ draw.mViewPoint.x)));
}
if (!mMinZoomScaleFixed) {
mMinZoomScale = (float) viewWidth / mZoomOverviewWidth;
@@ -6893,13 +6891,12 @@
new InvokeListBox(array, enabledArray, selectedArray));
}
- // viewWidth/contentWidth/updateZoomOverview are only used for mobile sites
private void updateZoomRange(WebViewCore.RestoreState restoreState,
- int viewWidth, int contentWidth, boolean updateZoomOverview) {
+ int viewWidth, int minPrefWidth, boolean updateZoomOverview) {
if (restoreState.mMinScale == 0) {
if (restoreState.mMobileSite) {
- if (contentWidth > Math.max(0, viewWidth)) {
- mMinZoomScale = (float) viewWidth / contentWidth;
+ if (minPrefWidth > Math.max(0, viewWidth)) {
+ mMinZoomScale = (float) viewWidth / minPrefWidth;
mMinZoomScaleFixed = false;
if (updateZoomOverview) {
WebSettings settings = getSettings();
diff --git a/core/java/android/webkit/WebViewCore.java b/core/java/android/webkit/WebViewCore.java
index 445e7ff..625e7ba 100644
--- a/core/java/android/webkit/WebViewCore.java
+++ b/core/java/android/webkit/WebViewCore.java
@@ -1705,6 +1705,7 @@
Region mInvalRegion;
Point mViewPoint;
Point mWidthHeight;
+ int mMinPrefWidth;
RestoreState mRestoreState; // only non-null if it is for the first
// picture set after the first layout
boolean mFocusSizeChanged;
@@ -1724,6 +1725,13 @@
// layout.
draw.mFocusSizeChanged = nativeFocusBoundsChanged();
draw.mViewPoint = new Point(mCurrentViewWidth, mCurrentViewHeight);
+ if (mSettings.getUseWideViewPort()) {
+ draw.mMinPrefWidth = Math.max(
+ mViewportWidth == -1 ? WebView.DEFAULT_VIEWPORT_WIDTH
+ : (mViewportWidth == 0 ? mCurrentViewWidth
+ : mViewportWidth),
+ nativeGetContentMinPrefWidth());
+ }
if (mRestoreState != null) {
draw.mRestoreState = mRestoreState;
mRestoreState = null;
@@ -1752,9 +1760,9 @@
final DrawFilter mZoomFilter =
new PaintFlagsDrawFilter(ZOOM_BITS, Paint.LINEAR_TEXT_FLAG);
- final DrawFilter mScrollFilter = null;
- // If we need to trade more speed for less quality on slower devices
- // use this: new PaintFlagsDrawFilter(SCROLL_BITS, 0);
+ // If we need to trade better quality for speed, set mScrollFilter to null
+ final DrawFilter mScrollFilter =
+ new PaintFlagsDrawFilter(SCROLL_BITS, 0);
/* package */ void drawContentPicture(Canvas canvas, int color,
boolean animatingZoom,
@@ -2077,7 +2085,7 @@
restoreState.mDefaultScale = adjust;
// as mViewportWidth is not 0, it is not mobile site.
restoreState.mMobileSite = false;
- // for non-mobile site, we don't need contentWidth, set it as 0
+ // for non-mobile site, we don't need minPrefWidth, set it as 0
restoreState.mScrollX = 0;
Message.obtain(mWebView.mPrivateHandler,
WebView.UPDATE_ZOOM_RANGE, restoreState).sendToTarget();
diff --git a/core/java/android/widget/AbsListView.java b/core/java/android/widget/AbsListView.java
index 4aae05e..48e7f79 100644
--- a/core/java/android/widget/AbsListView.java
+++ b/core/java/android/widget/AbsListView.java
@@ -2856,13 +2856,13 @@
final int firstPosition = mFirstPosition;
- if (firstPosition == 0 && firstTop >= listPadding.top && deltaY > 0) {
+ if (firstPosition == 0 && firstTop >= listPadding.top && deltaY >= 0) {
// Don't need to move views down if the top of the first position
// is already visible
return true;
}
- if (firstPosition + childCount == mItemCount && lastBottom <= end && deltaY < 0) {
+ if (firstPosition + childCount == mItemCount && lastBottom <= end && deltaY <= 0) {
// Don't need to move views up if the bottom of the last position
// is already visible
return true;
diff --git a/core/java/com/android/internal/widget/ContactHeaderWidget.java b/core/java/com/android/internal/widget/ContactHeaderWidget.java
index 333257e..f421466 100644
--- a/core/java/com/android/internal/widget/ContactHeaderWidget.java
+++ b/core/java/com/android/internal/widget/ContactHeaderWidget.java
@@ -489,7 +489,7 @@
resetAsyncQueryHandler();
}
- mQueryHandler.startQuery(TOKEN_CONTACT_INFO, null, contactUri, ContactQuery.COLUMNS,
+ mQueryHandler.startQuery(TOKEN_CONTACT_INFO, contactUri, contactUri, ContactQuery.COLUMNS,
null, null, null);
}
diff --git a/core/res/res/drawable-hdpi/ic_lock_idle_alarm.png b/core/res/res/drawable-hdpi/ic_lock_idle_alarm.png
index 41ad27d..6b4f66d 100644
--- a/core/res/res/drawable-hdpi/ic_lock_idle_alarm.png
+++ b/core/res/res/drawable-hdpi/ic_lock_idle_alarm.png
Binary files differ
diff --git a/core/res/res/drawable-mdpi/ic_lock_idle_alarm.png b/core/res/res/drawable-mdpi/ic_lock_idle_alarm.png
index ee77526..d29c6c3 100644
--- a/core/res/res/drawable-mdpi/ic_lock_idle_alarm.png
+++ b/core/res/res/drawable-mdpi/ic_lock_idle_alarm.png
Binary files differ
diff --git a/core/res/res/layout/keyguard_screen_tab_unlock.xml b/core/res/res/layout/keyguard_screen_tab_unlock.xml
index a4b2357..945d283 100644
--- a/core/res/res/layout/keyguard_screen_tab_unlock.xml
+++ b/core/res/res/layout/keyguard_screen_tab_unlock.xml
@@ -152,5 +152,19 @@
android:layout_marginBottom="80dip"
/>
+ <!-- emergency call button shown when sim is PUKd and tab_selector is
+ hidden -->
+ <Button
+ android:id="@+id/emergencyCallButton"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:drawableLeft="@drawable/ic_emergency"
+ android:layout_centerInParent="true"
+ android:layout_alignParentBottom="true"
+ android:layout_marginBottom="80dip"
+ style="@style/Widget.Button.Transparent"
+ android:drawablePadding="8dip"
+ />
+
</RelativeLayout>
diff --git a/core/res/res/layout/keyguard_screen_tab_unlock_land.xml b/core/res/res/layout/keyguard_screen_tab_unlock_land.xml
index e1c9772..6b76004e 100644
--- a/core/res/res/layout/keyguard_screen_tab_unlock_land.xml
+++ b/core/res/res/layout/keyguard_screen_tab_unlock_land.xml
@@ -153,4 +153,16 @@
android:layout_marginRight="80dip"
/>
+ <!-- emergency call button shown when sim is PUKd and tab_selector is
+ hidden -->
+ <Button
+ android:id="@+id/emergencyCallButton"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:drawableLeft="@drawable/ic_emergency"
+ style="@style/Widget.Button.Transparent"
+ android:drawablePadding="8dip"
+ android:layout_marginRight="80dip"
+ />
+
</LinearLayout>
diff --git a/core/res/res/values/attrs_manifest.xml b/core/res/res/values/attrs_manifest.xml
index 959a9db..3585bf1 100644
--- a/core/res/res/values/attrs_manifest.xml
+++ b/core/res/res/values/attrs_manifest.xml
@@ -527,6 +527,9 @@
<!-- The screen layout has changed. This might be caused by a
different display being activated. -->
<flag name="screenLayout" value="0x0100" />
+ <!-- The global user interface mode has changed. For example,
+ going in or out of car mode, night mode changing, etc. -->
+ <flag name="uiMode" value="0x0200" />
<!-- The font scaling factor has changed, that is the user has
selected a new global font size. -->
<flag name="fontScale" value="0x40000000" />
diff --git a/core/res/res/values/strings.xml b/core/res/res/values/strings.xml
index bf7425f..48d1ad7 100644
--- a/core/res/res/values/strings.xml
+++ b/core/res/res/values/strings.xml
@@ -1612,8 +1612,8 @@
<string name="factorytest_reboot">Reboot</string>
<!-- Do not translate. WebView User Agent string -->
- <string name="web_user_agent"><xliff:g id="x">Mozilla/5.0 (Linux; U; Android %s)
- AppleWebKit/530.17 (KHTML, like Gecko) Version/4.0 Mobile Safari/530.17</xliff:g></string>
+ <string name="web_user_agent" translatable="false"><xliff:g id="x">Mozilla/5.0 (Linux; U; Android %s)
+ AppleWebKit/533.1 (KHTML, like Gecko) Version/4.0 Mobile Safari/533.1</xliff:g></string>
<!-- Title for a JavaScript dialog. "The page at <url of current page> says:" -->
<string name="js_dialog_title">The page at \'<xliff:g id="title">%s</xliff:g>\' says:</string>
diff --git a/core/tests/ConnectivityManagerTest/src/com/android/connectivitymanagertest/functional/ConnectivityManagerMobileTest.java b/core/tests/ConnectivityManagerTest/src/com/android/connectivitymanagertest/functional/ConnectivityManagerMobileTest.java
index 7641afe..ae3daad 100644
--- a/core/tests/ConnectivityManagerTest/src/com/android/connectivitymanagertest/functional/ConnectivityManagerMobileTest.java
+++ b/core/tests/ConnectivityManagerTest/src/com/android/connectivitymanagertest/functional/ConnectivityManagerMobileTest.java
@@ -470,10 +470,7 @@
}
// Prepare for state validation
- NetworkInfo networkInfo = cmActivity.mCM.getNetworkInfo(ConnectivityManager.TYPE_MOBILE);
- cmActivity.setStateTransitionCriteria(ConnectivityManager.TYPE_MOBILE,
- networkInfo.getState(),NetworkState.DO_NOTHING,State.DISCONNECTED);
- networkInfo = cmActivity.mCM.getNetworkInfo(ConnectivityManager.TYPE_WIFI);
+ NetworkInfo networkInfo = cmActivity.mCM.getNetworkInfo(ConnectivityManager.TYPE_WIFI);
assertEquals(State.DISCONNECTED, networkInfo.getState());
cmActivity.setStateTransitionCriteria(ConnectivityManager.TYPE_WIFI,
networkInfo.getState(), NetworkState.TO_CONNECTION, State.CONNECTED);
@@ -482,7 +479,9 @@
cmActivity.setAirplaneMode(getInstrumentation().getContext(), false);
waitForNetworkState(ConnectivityManager.TYPE_WIFI, State.CONNECTED,
- STATE_TRANSITION_LONG_TIMEOUT);
+ STATE_TRANSITION_LONG_TIMEOUT);
+ waitForNetworkState(ConnectivityManager.TYPE_MOBILE, State.DISCONNECTED,
+ STATE_TRANSITION_LONG_TIMEOUT);
// validate the state transition
if (!cmActivity.validateNetworkStates(ConnectivityManager.TYPE_WIFI)) {
@@ -491,12 +490,6 @@
cmActivity.getTransitionFailureReason(ConnectivityManager.TYPE_WIFI));
assertTrue(false);
}
- if (!cmActivity.validateNetworkStates(ConnectivityManager.TYPE_MOBILE)) {
- Log.v(LOG_TAG, "Mobile state transition validation failed.");
- Log.v(LOG_TAG, "reason: " +
- cmActivity.getTransitionFailureReason(ConnectivityManager.TYPE_MOBILE));
- assertTrue(false);
- }
}
// Test case 8: test wifi state change while connecting/disconnecting to/from an AP
diff --git a/core/tests/coretests/apks/Android.mk b/core/tests/coretests/apks/Android.mk
new file mode 100644
index 0000000..4670e21
--- /dev/null
+++ b/core/tests/coretests/apks/Android.mk
@@ -0,0 +1,5 @@
+LOCAL_PATH:= $(call my-dir)
+include $(CLEAR_VARS)
+
+# build sub packages
+include $(call all-makefiles-under,$(LOCAL_PATH))
diff --git a/core/tests/coretests/apks/install_loc_auto/Android.mk b/core/tests/coretests/apks/install_loc_auto/Android.mk
new file mode 100644
index 0000000..2deb978
--- /dev/null
+++ b/core/tests/coretests/apks/install_loc_auto/Android.mk
@@ -0,0 +1,11 @@
+LOCAL_PATH:= $(call my-dir)
+include $(CLEAR_VARS)
+
+LOCAL_MODULE_TAGS := tests
+
+LOCAL_SRC_FILES := $(call all-subdir-java-files)
+
+LOCAL_PACKAGE_NAME := FrameworkCoreTests_install_loc_auto
+
+include $(BUILD_PACKAGE)
+
diff --git a/core/tests/coretests/apks/install_loc_auto/AndroidManifest.xml b/core/tests/coretests/apks/install_loc_auto/AndroidManifest.xml
new file mode 100644
index 0000000..5a903e2
--- /dev/null
+++ b/core/tests/coretests/apks/install_loc_auto/AndroidManifest.xml
@@ -0,0 +1,22 @@
+<?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.
+-->
+<manifest xmlns:android="http://schemas.android.com/apk/res/android"
+ android:installLocation="auto"
+ package="com.android.frameworks.coretests.install_loc">
+
+ <application android:hasCode="false">
+ </application>
+</manifest>
diff --git a/core/tests/coretests/apks/install_loc_auto/res/values/strings.xml b/core/tests/coretests/apks/install_loc_auto/res/values/strings.xml
new file mode 100644
index 0000000..3b8b3b1
--- /dev/null
+++ b/core/tests/coretests/apks/install_loc_auto/res/values/strings.xml
@@ -0,0 +1,6 @@
+<?xml version="1.0" encoding="utf-8"?>
+
+<!-- Just need this dummy file to have something to build. -->
+<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="dummy">dummy</string>
+</resources>
diff --git a/core/tests/coretests/apks/install_loc_internal/Android.mk b/core/tests/coretests/apks/install_loc_internal/Android.mk
new file mode 100644
index 0000000..784bf0a
--- /dev/null
+++ b/core/tests/coretests/apks/install_loc_internal/Android.mk
@@ -0,0 +1,11 @@
+LOCAL_PATH:= $(call my-dir)
+include $(CLEAR_VARS)
+
+LOCAL_MODULE_TAGS := tests
+
+LOCAL_SRC_FILES := $(call all-subdir-java-files)
+
+LOCAL_PACKAGE_NAME := FrameworkCoreTests_install_loc_internal
+
+include $(BUILD_PACKAGE)
+
diff --git a/core/tests/coretests/apks/install_loc_internal/AndroidManifest.xml b/core/tests/coretests/apks/install_loc_internal/AndroidManifest.xml
new file mode 100644
index 0000000..2568f37
--- /dev/null
+++ b/core/tests/coretests/apks/install_loc_internal/AndroidManifest.xml
@@ -0,0 +1,22 @@
+<?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.
+-->
+<manifest xmlns:android="http://schemas.android.com/apk/res/android"
+ android:installLocation="internalOnly"
+ package="com.android.frameworks.coretests.install_loc">
+
+ <application android:hasCode="false">
+ </application>
+</manifest>
diff --git a/core/tests/coretests/apks/install_loc_internal/res/values/strings.xml b/core/tests/coretests/apks/install_loc_internal/res/values/strings.xml
new file mode 100644
index 0000000..3b8b3b1
--- /dev/null
+++ b/core/tests/coretests/apks/install_loc_internal/res/values/strings.xml
@@ -0,0 +1,6 @@
+<?xml version="1.0" encoding="utf-8"?>
+
+<!-- Just need this dummy file to have something to build. -->
+<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="dummy">dummy</string>
+</resources>
diff --git a/core/tests/coretests/apks/install_loc_sdcard/Android.mk b/core/tests/coretests/apks/install_loc_sdcard/Android.mk
new file mode 100644
index 0000000..4eea322
--- /dev/null
+++ b/core/tests/coretests/apks/install_loc_sdcard/Android.mk
@@ -0,0 +1,11 @@
+LOCAL_PATH:= $(call my-dir)
+include $(CLEAR_VARS)
+
+LOCAL_MODULE_TAGS := tests
+
+LOCAL_SRC_FILES := $(call all-subdir-java-files)
+
+LOCAL_PACKAGE_NAME := FrameworkCoreTests_install_loc_sdcard
+
+include $(BUILD_PACKAGE)
+
diff --git a/core/tests/coretests/apks/install_loc_sdcard/AndroidManifest.xml b/core/tests/coretests/apks/install_loc_sdcard/AndroidManifest.xml
new file mode 100644
index 0000000..647f4e5
--- /dev/null
+++ b/core/tests/coretests/apks/install_loc_sdcard/AndroidManifest.xml
@@ -0,0 +1,22 @@
+<?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.
+-->
+<manifest xmlns:android="http://schemas.android.com/apk/res/android"
+ android:installLocation="preferExternal"
+ package="com.android.frameworks.coretests.install_loc">
+
+ <application android:hasCode="false">
+ </application>
+</manifest>
diff --git a/core/tests/coretests/apks/install_loc_sdcard/res/values/strings.xml b/core/tests/coretests/apks/install_loc_sdcard/res/values/strings.xml
new file mode 100644
index 0000000..3b8b3b1
--- /dev/null
+++ b/core/tests/coretests/apks/install_loc_sdcard/res/values/strings.xml
@@ -0,0 +1,6 @@
+<?xml version="1.0" encoding="utf-8"?>
+
+<!-- Just need this dummy file to have something to build. -->
+<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="dummy">dummy</string>
+</resources>
diff --git a/core/tests/coretests/apks/install_loc_unspecified/Android.mk b/core/tests/coretests/apks/install_loc_unspecified/Android.mk
new file mode 100644
index 0000000..206c99f
--- /dev/null
+++ b/core/tests/coretests/apks/install_loc_unspecified/Android.mk
@@ -0,0 +1,11 @@
+LOCAL_PATH:= $(call my-dir)
+include $(CLEAR_VARS)
+
+LOCAL_MODULE_TAGS := tests
+
+LOCAL_SRC_FILES := $(call all-subdir-java-files)
+
+LOCAL_PACKAGE_NAME := FrameworkCoreTests_install_loc_unspecified
+
+include $(BUILD_PACKAGE)
+
diff --git a/core/tests/coretests/apks/install_loc_unspecified/AndroidManifest.xml b/core/tests/coretests/apks/install_loc_unspecified/AndroidManifest.xml
new file mode 100644
index 0000000..07b1eb3
--- /dev/null
+++ b/core/tests/coretests/apks/install_loc_unspecified/AndroidManifest.xml
@@ -0,0 +1,21 @@
+<?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.
+-->
+<manifest xmlns:android="http://schemas.android.com/apk/res/android"
+ package="com.android.frameworks.coretests.install_loc">
+
+ <application android:hasCode="false">
+ </application>
+</manifest>
diff --git a/core/tests/coretests/apks/install_loc_unspecified/res/values/strings.xml b/core/tests/coretests/apks/install_loc_unspecified/res/values/strings.xml
new file mode 100644
index 0000000..3b8b3b1
--- /dev/null
+++ b/core/tests/coretests/apks/install_loc_unspecified/res/values/strings.xml
@@ -0,0 +1,6 @@
+<?xml version="1.0" encoding="utf-8"?>
+
+<!-- Just need this dummy file to have something to build. -->
+<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="dummy">dummy</string>
+</resources>
diff --git a/core/tests/coretests/res/raw/install b/core/tests/coretests/res/raw/install
index 2ee1f3c..06981f4 100644
--- a/core/tests/coretests/res/raw/install
+++ b/core/tests/coretests/res/raw/install
Binary files differ
diff --git a/core/tests/coretests/res/raw/install_app1_cert1 b/core/tests/coretests/res/raw/install_app1_cert1
index 67eb2de..f880c0b 100644
--- a/core/tests/coretests/res/raw/install_app1_cert1
+++ b/core/tests/coretests/res/raw/install_app1_cert1
Binary files differ
diff --git a/core/tests/coretests/res/raw/install_app1_cert1_cert2 b/core/tests/coretests/res/raw/install_app1_cert1_cert2
index dbafdc5..ed89fbb 100644
--- a/core/tests/coretests/res/raw/install_app1_cert1_cert2
+++ b/core/tests/coretests/res/raw/install_app1_cert1_cert2
Binary files differ
diff --git a/core/tests/coretests/res/raw/install_app1_cert2 b/core/tests/coretests/res/raw/install_app1_cert2
index e26c2eb..5551c7e 100644
--- a/core/tests/coretests/res/raw/install_app1_cert2
+++ b/core/tests/coretests/res/raw/install_app1_cert2
Binary files differ
diff --git a/core/tests/coretests/res/raw/install_app1_cert3 b/core/tests/coretests/res/raw/install_app1_cert3
index fa10be7..0d1a4dc 100644
--- a/core/tests/coretests/res/raw/install_app1_cert3
+++ b/core/tests/coretests/res/raw/install_app1_cert3
Binary files differ
diff --git a/core/tests/coretests/res/raw/install_app1_cert3_cert4 b/core/tests/coretests/res/raw/install_app1_cert3_cert4
index c2f6c81..29ff3b6 100644
--- a/core/tests/coretests/res/raw/install_app1_cert3_cert4
+++ b/core/tests/coretests/res/raw/install_app1_cert3_cert4
Binary files differ
diff --git a/core/tests/coretests/res/raw/install_app1_unsigned b/core/tests/coretests/res/raw/install_app1_unsigned
index 18be5f8..01b39e2 100644
--- a/core/tests/coretests/res/raw/install_app1_unsigned
+++ b/core/tests/coretests/res/raw/install_app1_unsigned
Binary files differ
diff --git a/core/tests/coretests/res/raw/install_app2_cert1 b/core/tests/coretests/res/raw/install_app2_cert1
index b345732..12bfc6f 100644
--- a/core/tests/coretests/res/raw/install_app2_cert1
+++ b/core/tests/coretests/res/raw/install_app2_cert1
Binary files differ
diff --git a/core/tests/coretests/res/raw/install_app2_cert1_cert2 b/core/tests/coretests/res/raw/install_app2_cert1_cert2
index 1faa257..39095ba 100644
--- a/core/tests/coretests/res/raw/install_app2_cert1_cert2
+++ b/core/tests/coretests/res/raw/install_app2_cert1_cert2
Binary files differ
diff --git a/core/tests/coretests/res/raw/install_app2_cert2 b/core/tests/coretests/res/raw/install_app2_cert2
index c3d5979..f6d965b 100644
--- a/core/tests/coretests/res/raw/install_app2_cert2
+++ b/core/tests/coretests/res/raw/install_app2_cert2
Binary files differ
diff --git a/core/tests/coretests/res/raw/install_app2_cert3 b/core/tests/coretests/res/raw/install_app2_cert3
index ac0d9da..3d8b6f1 100644
--- a/core/tests/coretests/res/raw/install_app2_cert3
+++ b/core/tests/coretests/res/raw/install_app2_cert3
Binary files differ
diff --git a/core/tests/coretests/res/raw/install_app2_unsigned b/core/tests/coretests/res/raw/install_app2_unsigned
index 8d24e88..b69d9fe 100644
--- a/core/tests/coretests/res/raw/install_app2_unsigned
+++ b/core/tests/coretests/res/raw/install_app2_unsigned
Binary files differ
diff --git a/core/tests/coretests/res/raw/install_decl_perm b/core/tests/coretests/res/raw/install_decl_perm
index 6f22321..af05d81 100644
--- a/core/tests/coretests/res/raw/install_decl_perm
+++ b/core/tests/coretests/res/raw/install_decl_perm
Binary files differ
diff --git a/core/tests/coretests/res/raw/install_loc_auto b/core/tests/coretests/res/raw/install_loc_auto
index d5d2739..63bf35c 100644
--- a/core/tests/coretests/res/raw/install_loc_auto
+++ b/core/tests/coretests/res/raw/install_loc_auto
Binary files differ
diff --git a/core/tests/coretests/res/raw/install_loc_internal b/core/tests/coretests/res/raw/install_loc_internal
index eb6279a..5178803 100644
--- a/core/tests/coretests/res/raw/install_loc_internal
+++ b/core/tests/coretests/res/raw/install_loc_internal
Binary files differ
diff --git a/core/tests/coretests/res/raw/install_loc_sdcard b/core/tests/coretests/res/raw/install_loc_sdcard
index c774989..013a414 100644
--- a/core/tests/coretests/res/raw/install_loc_sdcard
+++ b/core/tests/coretests/res/raw/install_loc_sdcard
Binary files differ
diff --git a/core/tests/coretests/res/raw/install_loc_unspecified b/core/tests/coretests/res/raw/install_loc_unspecified
index ab226c6..06981f4 100644
--- a/core/tests/coretests/res/raw/install_loc_unspecified
+++ b/core/tests/coretests/res/raw/install_loc_unspecified
Binary files differ
diff --git a/core/tests/coretests/res/raw/install_shared1_cert1 b/core/tests/coretests/res/raw/install_shared1_cert1
index d702dab..714f9ff 100644
--- a/core/tests/coretests/res/raw/install_shared1_cert1
+++ b/core/tests/coretests/res/raw/install_shared1_cert1
Binary files differ
diff --git a/core/tests/coretests/res/raw/install_shared1_cert12 b/core/tests/coretests/res/raw/install_shared1_cert12
deleted file mode 100644
index b580b60..0000000
--- a/core/tests/coretests/res/raw/install_shared1_cert12
+++ /dev/null
Binary files differ
diff --git a/core/tests/coretests/res/raw/install_shared1_cert1_cert2 b/core/tests/coretests/res/raw/install_shared1_cert1_cert2
index b580b60..83725e0 100644
--- a/core/tests/coretests/res/raw/install_shared1_cert1_cert2
+++ b/core/tests/coretests/res/raw/install_shared1_cert1_cert2
Binary files differ
diff --git a/core/tests/coretests/res/raw/install_shared1_cert2 b/core/tests/coretests/res/raw/install_shared1_cert2
index a2de801..6a3157e 100644
--- a/core/tests/coretests/res/raw/install_shared1_cert2
+++ b/core/tests/coretests/res/raw/install_shared1_cert2
Binary files differ
diff --git a/core/tests/coretests/res/raw/install_shared1_unsigned b/core/tests/coretests/res/raw/install_shared1_unsigned
index 35680be..2a2e5f5 100644
--- a/core/tests/coretests/res/raw/install_shared1_unsigned
+++ b/core/tests/coretests/res/raw/install_shared1_unsigned
Binary files differ
diff --git a/core/tests/coretests/res/raw/install_shared2_cert1 b/core/tests/coretests/res/raw/install_shared2_cert1
index 9064de7..7006edc 100644
--- a/core/tests/coretests/res/raw/install_shared2_cert1
+++ b/core/tests/coretests/res/raw/install_shared2_cert1
Binary files differ
diff --git a/core/tests/coretests/res/raw/install_shared2_cert12 b/core/tests/coretests/res/raw/install_shared2_cert12
deleted file mode 100644
index 26a250d..0000000
--- a/core/tests/coretests/res/raw/install_shared2_cert12
+++ /dev/null
Binary files differ
diff --git a/core/tests/coretests/res/raw/install_shared2_cert1_cert2 b/core/tests/coretests/res/raw/install_shared2_cert1_cert2
index 26a250d..b7b084c 100644
--- a/core/tests/coretests/res/raw/install_shared2_cert1_cert2
+++ b/core/tests/coretests/res/raw/install_shared2_cert1_cert2
Binary files differ
diff --git a/core/tests/coretests/res/raw/install_shared2_cert2 b/core/tests/coretests/res/raw/install_shared2_cert2
index 7981308..0f04388 100644
--- a/core/tests/coretests/res/raw/install_shared2_cert2
+++ b/core/tests/coretests/res/raw/install_shared2_cert2
Binary files differ
diff --git a/core/tests/coretests/res/raw/install_shared2_unsigned b/core/tests/coretests/res/raw/install_shared2_unsigned
index ad909fd..2794282 100644
--- a/core/tests/coretests/res/raw/install_shared2_unsigned
+++ b/core/tests/coretests/res/raw/install_shared2_unsigned
Binary files differ
diff --git a/core/tests/coretests/res/raw/install_use_perm_good b/core/tests/coretests/res/raw/install_use_perm_good
index d5216f8..a7eb32f 100644
--- a/core/tests/coretests/res/raw/install_use_perm_good
+++ b/core/tests/coretests/res/raw/install_use_perm_good
Binary files differ
diff --git a/core/tests/coretests/src/android/content/pm/PackageManagerTests.java b/core/tests/coretests/src/android/content/pm/PackageManagerTests.java
index c699c10..7fa64ca 100755
--- a/core/tests/coretests/src/android/content/pm/PackageManagerTests.java
+++ b/core/tests/coretests/src/android/content/pm/PackageManagerTests.java
@@ -24,6 +24,7 @@
import android.content.Intent;
import android.content.IntentFilter;
import android.content.pm.ApplicationInfo;
+import android.content.pm.IPackageMoveObserver;
import android.content.pm.PackageInfo;
import android.content.pm.PackageManager;
import android.content.pm.PackageParser;
@@ -327,14 +328,14 @@
boolean checkSd = false;
int setLoc = 0;
try {
- setLoc = Settings.System.getInt(mContext.getContentResolver(), Settings.System.SET_INSTALL_LOCATION);
+ setLoc = Settings.System.getInt(mContext.getContentResolver(), Settings.Secure.SET_INSTALL_LOCATION);
} catch (SettingNotFoundException e) {
failStr(e);
}
if (setLoc == 1) {
int userPref = APP_INSTALL_AUTO;
try {
- userPref = Settings.System.getInt(mContext.getContentResolver(), Settings.System.DEFAULT_INSTALL_LOCATION);
+ userPref = Settings.System.getInt(mContext.getContentResolver(), Settings.Secure.DEFAULT_INSTALL_LOCATION);
} catch (SettingNotFoundException e) {
failStr(e);
}
@@ -1218,8 +1219,15 @@
private class PackageMoveObserver extends IPackageMoveObserver.Stub {
public int returnCode;
private boolean doneFlag = false;
-
+ public String packageName;
+ public PackageMoveObserver(String pkgName) {
+ packageName = pkgName;
+ }
public void packageMoved(String packageName, int returnCode) {
+ Log.i("DEBUG_MOVE::", "pkg = " + packageName + ", " + "ret = " + returnCode);
+ if (!packageName.equals(this.packageName)) {
+ return;
+ }
synchronized(this) {
this.returnCode = returnCode;
doneFlag = true;
@@ -1234,7 +1242,7 @@
public boolean invokeMovePackage(String pkgName, int flags,
GenericReceiver receiver) throws Exception {
- PackageMoveObserver observer = new PackageMoveObserver();
+ PackageMoveObserver observer = new PackageMoveObserver(pkgName);
final boolean received = false;
mContext.registerReceiver(receiver, receiver.filter);
try {
@@ -1269,13 +1277,33 @@
mContext.unregisterReceiver(receiver);
}
}
+ private boolean invokeMovePackageFail(String pkgName, int flags, int errCode) throws Exception {
+ PackageMoveObserver observer = new PackageMoveObserver(pkgName);
+ try {
+ // Wait on observer
+ synchronized(observer) {
+ getPm().movePackage(pkgName, observer, flags);
+ long waitTime = 0;
+ while((!observer.isDone()) && (waitTime < MAX_WAIT_TIME) ) {
+ observer.wait(WAIT_TIME_INCR);
+ waitTime += WAIT_TIME_INCR;
+ }
+ if(!observer.isDone()) {
+ throw new Exception("Timed out waiting for pkgmove callback");
+ }
+ assertEquals(errCode, observer.returnCode);
+ }
+ } finally {
+ }
+ return true;
+ }
private int getInstallLoc() {
boolean userSetting = false;
int origDefaultLoc = PackageInfo.INSTALL_LOCATION_AUTO;
try {
- userSetting = Settings.System.getInt(mContext.getContentResolver(), Settings.System.SET_INSTALL_LOCATION) != 0;
- origDefaultLoc = Settings.System.getInt(mContext.getContentResolver(), Settings.System.DEFAULT_INSTALL_LOCATION);
+ userSetting = Settings.System.getInt(mContext.getContentResolver(), Settings.Secure.SET_INSTALL_LOCATION) != 0;
+ origDefaultLoc = Settings.System.getInt(mContext.getContentResolver(), Settings.Secure.DEFAULT_INSTALL_LOCATION);
} catch (SettingNotFoundException e1) {
}
return origDefaultLoc;
@@ -1283,33 +1311,39 @@
private void setInstallLoc(int loc) {
Settings.System.putInt(mContext.getContentResolver(),
- Settings.System.DEFAULT_INSTALL_LOCATION, loc);
+ Settings.Secure.DEFAULT_INSTALL_LOCATION, loc);
}
/*
+ * Tests for moving apps between internal and external storage
+ */
+ /*
* Utility function that reads a apk bundled as a raw resource
* copies it into own data directory and invokes
* PackageManager api to install first and then replace it
* again.
*/
- public void moveFromRawResource(int installFlags, int moveFlags,
- int expRetCode) {
+
+ private void moveFromRawResource(String outFileName,
+ int rawResId, int installFlags, int moveFlags, boolean cleanUp,
+ boolean fail, int result) {
int origDefaultLoc = getInstallLoc();
- setInstallLoc(PackageHelper.APP_INSTALL_AUTO);
- // Install first
- InstallParams ip = sampleInstallFromRawResource(installFlags, false);
- ApplicationInfo oldAppInfo = null;
+ InstallParams ip = null;
try {
- oldAppInfo = getPm().getApplicationInfo(ip.pkg.packageName, 0);
- } catch (NameNotFoundException e) {
- failStr("Pkg hasnt been installed correctly");
- }
-
- // Create receiver based on expRetCode
- MoveReceiver receiver = new MoveReceiver(ip.pkg.packageName);
- try {
- boolean retCode = invokeMovePackage(ip.pkg.packageName, moveFlags,
- receiver);
- if (expRetCode == PackageManager.MOVE_SUCCEEDED) {
+ setInstallLoc(PackageHelper.APP_INSTALL_AUTO);
+ // Install first
+ ip = installFromRawResource("install.apk", rawResId, installFlags, false,
+ false, -1, PackageInfo.INSTALL_LOCATION_UNSPECIFIED);
+ ApplicationInfo oldAppInfo = getPm().getApplicationInfo(ip.pkg.packageName, 0);
+ if (fail) {
+ assertTrue(invokeMovePackageFail(ip.pkg.packageName, moveFlags, result));
+ ApplicationInfo info = getPm().getApplicationInfo(ip.pkg.packageName, 0);
+ assertNotNull(info);
+ assertEquals(oldAppInfo.flags, info.flags);
+ } else {
+ // Create receiver based on expRetCode
+ MoveReceiver receiver = new MoveReceiver(ip.pkg.packageName);
+ boolean retCode = invokeMovePackage(ip.pkg.packageName, moveFlags,
+ receiver);
assertTrue(retCode);
ApplicationInfo info = getPm().getApplicationInfo(ip.pkg.packageName, 0);
assertNotNull(info);
@@ -1318,40 +1352,91 @@
} else if ((moveFlags & PackageManager.MOVE_EXTERNAL_MEDIA) != 0){
assertTrue((info.flags & ApplicationInfo.FLAG_EXTERNAL_STORAGE) != 0);
}
- } else {
- assertFalse(retCode);
- ApplicationInfo info = getPm().getApplicationInfo(ip.pkg.packageName, 0);
- assertNotNull(info);
- assertEquals(oldAppInfo.flags, info.flags);
}
+ } catch (NameNotFoundException e) {
+ failStr("Pkg hasnt been installed correctly");
} catch (Exception e) {
failStr("Failed with exception : " + e);
} finally {
- cleanUpInstall(ip);
+ if (ip != null) {
+ cleanUpInstall(ip);
+ }
// Restore default install location
setInstallLoc(origDefaultLoc);
}
}
+ private void sampleMoveFromRawResource(int installFlags, int moveFlags, boolean fail,
+ int result) {
+ moveFromRawResource("install.apk",
+ R.raw.install, installFlags, moveFlags, true,
+ fail, result);
+ }
public void testMoveAppInternalToExternal() {
- moveFromRawResource(0, PackageManager.MOVE_EXTERNAL_MEDIA,
- PackageManager.MOVE_SUCCEEDED);
+ int installFlags = PackageManager.INSTALL_INTERNAL;
+ int moveFlags = PackageManager.MOVE_EXTERNAL_MEDIA;
+ boolean fail = false;
+ int result = PackageManager.MOVE_SUCCEEDED;
+ sampleMoveFromRawResource(installFlags, moveFlags, fail, result);
}
public void testMoveAppInternalToInternal() {
- moveFromRawResource(0, PackageManager.MOVE_INTERNAL,
- PackageManager.MOVE_FAILED_INVALID_LOCATION);
+ int installFlags = PackageManager.INSTALL_INTERNAL;
+ int moveFlags = PackageManager.MOVE_INTERNAL;
+ boolean fail = true;
+ int result = PackageManager.MOVE_FAILED_INVALID_LOCATION;
+ sampleMoveFromRawResource(installFlags, moveFlags, fail, result);
}
public void testMoveAppExternalToExternal() {
- moveFromRawResource(PackageManager.INSTALL_EXTERNAL, PackageManager.MOVE_EXTERNAL_MEDIA,
- PackageManager.MOVE_FAILED_INVALID_LOCATION);
+ int installFlags = PackageManager.INSTALL_EXTERNAL;
+ int moveFlags = PackageManager.MOVE_EXTERNAL_MEDIA;
+ boolean fail = true;
+ int result = PackageManager.MOVE_FAILED_INVALID_LOCATION;
+ sampleMoveFromRawResource(installFlags, moveFlags, fail, result);
}
public void testMoveAppExternalToInternal() {
- moveFromRawResource(PackageManager.INSTALL_EXTERNAL, PackageManager.MOVE_INTERNAL,
- PackageManager.MOVE_SUCCEEDED);
+ int installFlags = PackageManager.INSTALL_EXTERNAL;
+ int moveFlags = PackageManager.MOVE_INTERNAL;
+ boolean fail = false;
+ int result = PackageManager.MOVE_SUCCEEDED;
+ sampleMoveFromRawResource(installFlags, moveFlags, fail, result);
}
-
+ public void testMoveAppForwardLocked() {
+ int installFlags = PackageManager.INSTALL_FORWARD_LOCK;
+ int moveFlags = PackageManager.MOVE_EXTERNAL_MEDIA;
+ boolean fail = true;
+ int result = PackageManager.MOVE_FAILED_FORWARD_LOCKED;
+ sampleMoveFromRawResource(installFlags, moveFlags, fail, result);
+ }
+ public void testMoveAppFailInternalToExternalDelete() {
+ int installFlags = 0;
+ int moveFlags = PackageManager.MOVE_EXTERNAL_MEDIA;
+ boolean fail = true;
+ final int result = PackageManager.MOVE_FAILED_DOESNT_EXIST;
+
+ int rawResId = R.raw.install;
+ int origDefaultLoc = getInstallLoc();
+ InstallParams ip = null;
+ try {
+ PackageManager pm = getPm();
+ setInstallLoc(PackageHelper.APP_INSTALL_AUTO);
+ // Install first
+ ip = installFromRawResource("install.apk", R.raw.install, installFlags, false,
+ false, -1, PackageInfo.INSTALL_LOCATION_UNSPECIFIED);
+ // Delete the package now retaining data.
+ pm.deletePackage(ip.pkg.packageName, null, PackageManager.DONT_DELETE_DATA);
+ assertTrue(invokeMovePackageFail(ip.pkg.packageName, moveFlags, result));
+ } catch (Exception e) {
+ failStr(e);
+ } finally {
+ if (ip != null) {
+ cleanUpInstall(ip);
+ }
+ // Restore default install location
+ setInstallLoc(origDefaultLoc);
+ }
+ }
/*
* Test that an install error code is returned when media is unmounted
* and package installed on sdcard via package manager flag.
@@ -1799,7 +1884,7 @@
rFlags,
true,
false, -1,
- PackageInfo.INSTALL_LOCATION_AUTO);
+ PackageInfo.INSTALL_LOCATION_PREFER_EXTERNAL);
}
/*
* The following set of tests check install location for existing
@@ -1878,7 +1963,7 @@
*/
private boolean getUserSettingSetInstallLocation() {
try {
- return Settings.System.getInt(mContext.getContentResolver(), Settings.System.SET_INSTALL_LOCATION) != 0;
+ return Settings.System.getInt(mContext.getContentResolver(), Settings.Secure.SET_INSTALL_LOCATION) != 0;
} catch (SettingNotFoundException e1) {
}
@@ -1887,7 +1972,7 @@
private void setUserSettingSetInstallLocation(boolean value) {
Settings.System.putInt(mContext.getContentResolver(),
- Settings.System.SET_INSTALL_LOCATION, value ? 1 : 0);
+ Settings.Secure.SET_INSTALL_LOCATION, value ? 1 : 0);
}
private void setUserX(boolean enable, int userSetting, int iloc) {
boolean origUserSetting = getUserSettingSetInstallLocation();
diff --git a/docs/html/guide/samples/index.jd b/docs/html/guide/samples/index.jd
index 7923532..2f3ac5e 100644
--- a/docs/html/guide/samples/index.jd
+++ b/docs/html/guide/samples/index.jd
@@ -41,6 +41,10 @@
<dd>A variety of small applications that demonstrate an extensive collection of
framework topics.</dd>
+ <dt><a href="{@docRoot}resources/samples/BackupRestore/index.html">Backup and Restore</a></dt>
+ <dd>An simple example that illustrates a few different ways for an application to
+ implement support for the Android data backup and restore mechanism.</dd>
+
<dt><a href="{@docRoot}resources/samples/BluetoothChat/index.html">Bluetooth Chat</a></dt>
<dd>An application for two-way text messaging over Bluetooth.</dd>
diff --git a/docs/html/guide/topics/manifest/activity-element.jd b/docs/html/guide/topics/manifest/activity-element.jd
index 41c27c6..de8ca6d 100644
--- a/docs/html/guide/topics/manifest/activity-element.jd
+++ b/docs/html/guide/topics/manifest/activity-element.jd
@@ -8,7 +8,8 @@
android:<a href="#clear">clearTaskOnLaunch</a>=["true" | "false"]
android:<a href="#config">configChanges</a>=["mcc", "mnc", "locale",
"touchscreen", "keyboard", "keyboardHidden",
- "navigation", "orientation", "fontScale"]
+ "navigation", "orientation", "screenLayout",
+ "fontScale", "uiMode"]
android:<a href="#enabled">enabled</a>=["true" | "false"]
android:<a href="#exclude">excludeFromRecents</a>=["true" | "false"]
android:<a href="#exported">exported</a>=["true" | "false"]
@@ -152,13 +153,19 @@
</p></dd>
<dt><a name="config"></a>{@code android:configChanges}</dt>
-<dd>Lists configuration changes that the activity will handle itself. When
-changes that are not listed occur, the activity is shut down and restarted.
-When a listed change occurs, the activity remains running and its <code>{@link android.app.Activity#onConfigurationChanged onConfigurationChanged()}</code>
-method is called.
+<dd>Lists configuration changes that the activity will handle itself. When a configuration
+change occurs at runtime, the activity is shut down and restarted by default, but declaring a
+configuration with this attribute will prevent the activity from being restarted. Instead, the
+activity remains running and its <code>{@link android.app.Activity#onConfigurationChanged
+onConfigurationChanged()}</code> method is called.
+
+<p class="note"><strong>Note:</strong> Using this attribute should be
+avoided and used only as a last-resort. Please read <a
+href="{@docRoot}guide/topics/resources/runtime-changes.html">Handling Runtime Changes</a> for more
+information about how to properly handle a restart due to a configuration change.</p>
<p>
-Any or all of the following strings can be used to set this attribute. Values are
+Any or all of the following strings are valid values for this attribute. Multiple values are
separated by '{@code |}' — for example, "{@code locale|navigation|orientation}".
</p>
@@ -168,39 +175,48 @@
<th>Description</th>
</tr><tr>
<td>"{@code mcc}"</td>
- <td>The IMSI mobile country code (MCC) has changed —
- that is, a SIM has been detected and updated the MCC.</td>
+ <td>The IMSI mobile country code (MCC) has changed —
+ a SIM has been detected and updated the MCC.</td>
</tr><tr>
<td>"{@code mnc}"</td>
- <td>The IMSI mobile network code (MNC) has changed —
- that is, a SIM has been detected and updated the MNC.</td>
+ <td>The IMSI mobile network code (MNC) has changed —
+ a SIM has been detected and updated the MNC.</td>
</tr><tr>
<td>"{@code locale}"</td>
- <td>The locale has changed — for example, the user has selected a new
+ <td>The locale has changed — the user has selected a new
language that text should be displayed in.</td>
</tr><tr>
<td>"{@code touchscreen}"</td>
<td>The touchscreen has changed. (This should never normally happen.)</td>
</tr><tr>
<td>"{@code keyboard}"</td>
- <td>The keyboard type has changed — for example, the user has
+ <td>The keyboard type has changed — for example, the user has
plugged in an external keyboard.</td>
</tr><tr>
<td>"{@code keyboardHidden}"</td>
- <td>The keyboard accessibility has changed — for example, the
- user has slid the keyboard out to expose it.</td>
+ <td>The keyboard accessibility has changed — for example, the
+ user has revealed the hardware keyboard.</td>
</tr><tr>
<td>"{@code navigation}"</td>
- <td>The navigation type has changed. (This should never normally happen.)</td>
+ <td>The navigation type (trackball/dpad) has changed. (This should never normally happen.)</td>
</tr><tr>
- <td>"{@code orientation}"</td>
- <td>The screen orientation has changed — that is, the user has rotated
+ <td>"{@code orientation}"</td>
+ <td>The screen orientation has changed — the user has rotated
the device.</td>
</tr><tr>
+ <td>"{@code screenLayout}"</td>
+ <td>The screen layout has changed — this might be caused by a
+ different display being activated.</td>
+ </tr><tr>
<td>"{@code fontScale}"</td>
- <td>The font scaling factor has changed — that is, the user has selected
+ <td>The font scaling factor has changed — the user has selected
a new global font size.</td>
-</tr>
+ </tr><tr>
+ <td>"{@code uiMode}"</td>
+ <td>The user interface mode has changed — this can be caused when the user places the
+device into a desk/car dock or when the the night mode changes. See {@link
+android.app.UiModeManager}. <em>Introduced in API Level 8</em>.</td>
+ </tr>
</table>
<p>
diff --git a/docs/html/resources/resources_toc.cs b/docs/html/resources/resources_toc.cs
index 5958f71..43ab562 100644
--- a/docs/html/resources/resources_toc.cs
+++ b/docs/html/resources/resources_toc.cs
@@ -188,6 +188,9 @@
<li><a href="<?cs var:toroot ?>resources/samples/ApiDemos/index.html">
<span class="en">API Demos</span>
</a></li>
+ <li><a href="<?cs var:toroot ?>resources/samples/BackupRestore/index.html">
+ <span class="en">Backup and Restore</span>
+ </a> <span class="new">new!</span></li>
<li><a href="<?cs var:toroot ?>resources/samples/BluetoothChat/index.html">
<span class="en">Bluetooth Chat</span>
</a></li>
diff --git a/docs/html/resources/samples/index.jd b/docs/html/resources/samples/index.jd
index 044c69de..2718d0c 100644
--- a/docs/html/resources/samples/index.jd
+++ b/docs/html/resources/samples/index.jd
@@ -22,6 +22,10 @@
<dd>A variety of small applications that demonstrate an extensive collection of
framework topics.</dd>
+ <dt><a href="BackupRestore/index.html">Backup and Restore</a></dt>
+ <dd>An simple example that illustrates a few different ways for an application to
+ implement support for the Android data backup and restore mechanism.</dd>
+
<dt><a href="BluetoothChat/index.html">Bluetooth Chat</a></dt>
<dd>An application for two-way text messaging over Bluetooth.</dd>
diff --git a/include/media/stagefright/HTTPDataSource.h b/include/media/stagefright/HTTPDataSource.h
index b5d1e7a..83be475 100644
--- a/include/media/stagefright/HTTPDataSource.h
+++ b/include/media/stagefright/HTTPDataSource.h
@@ -54,7 +54,7 @@
private:
enum {
- kBufferSize = 32 * 1024,
+ kBufferSize = 64 * 1024,
// If we encounter a socket-read error we'll try reconnecting
// and restarting the read for at most this many times.
diff --git a/media/java/android/media/MediaScannerConnection.java b/media/java/android/media/MediaScannerConnection.java
index 65b67a1..503b5f4 100644
--- a/media/java/android/media/MediaScannerConnection.java
+++ b/media/java/android/media/MediaScannerConnection.java
@@ -30,11 +30,11 @@
/**
- * MediaScannerConnection provides a way for applications to pass a
+ * MediaScannerConnection provides a way for applications to pass a
* newly created or downloaded media file to the media scanner service.
- * The media scanner service will read metadata from the file and add
+ * The media scanner service will read metadata from the file and add
* the file to the media content provider.
- * The MediaScannerConnectionClient provides an interface for the
+ * The MediaScannerConnectionClient provides an interface for the
* media scanner service to return the Uri for a newly scanned file
* to the client of the MediaScannerConnection class.
*/
@@ -46,7 +46,7 @@
private MediaScannerConnectionClient mClient;
private IMediaScannerService mService;
private boolean mConnected; // true if connect() has been called since last disconnect()
-
+
private IMediaScannerListener.Stub mListener = new IMediaScannerListener.Stub() {
public void scanCompleted(String path, Uri uri) {
MediaScannerConnectionClient client = mClient;
@@ -60,36 +60,36 @@
* Interface for notifying clients of the result of scanning a
* requested media file.
*/
- public interface ScanResultListener {
+ public interface OnScanCompletedListener {
/**
* Called to notify the client when the media scanner has finished
* scanning a file.
* @param path the path to the file that has been scanned.
- * @param uri the Uri for the file if the scanning operation succeeded
- * and the file was added to the media database, or null if scanning failed.
- */
+ * @param uri the Uri for the file if the scanning operation succeeded
+ * and the file was added to the media database, or null if scanning failed.
+ */
public void onScanCompleted(String path, Uri uri);
}
-
+
/**
* An interface for notifying clients of MediaScannerConnection
* when a connection to the MediaScanner service has been established
* and when the scanning of a file has completed.
*/
- public interface MediaScannerConnectionClient extends ScanResultListener {
+ public interface MediaScannerConnectionClient extends OnScanCompletedListener {
/**
- * Called to notify the client when a connection to the
+ * Called to notify the client when a connection to the
* MediaScanner service has been established.
- */
+ */
public void onMediaScannerConnected();
-
+
/**
* Called to notify the client when the media scanner has finished
* scanning a file.
* @param path the path to the file that has been scanned.
- * @param uri the Uri for the file if the scanning operation succeeded
- * and the file was added to the media database, or null if scanning failed.
- */
+ * @param uri the Uri for the file if the scanning operation succeeded
+ * and the file was added to the media database, or null if scanning failed.
+ */
public void onScanCompleted(String path, Uri uri);
}
@@ -140,7 +140,7 @@
}
}
}
-
+
/**
* Returns whether we are connected to the media scanner service
* @return true if we are connected, false otherwise
@@ -151,9 +151,9 @@
/**
* Requests the media scanner to scan a file.
- * Success or failure of the scanning operation cannot be determined until
+ * Success or failure of the scanning operation cannot be determined until
* {@link MediaScannerConnectionClient#onScanCompleted(String, Uri)} is called.
- *
+ *
* @param path the path to the file to be scanned.
* @param mimeType an optional mimeType for the file.
* If mimeType is null, then the mimeType will be inferred from the file extension.
@@ -175,31 +175,31 @@
}
}
}
-
+
static class ClientProxy implements MediaScannerConnectionClient {
final String[] mPaths;
final String[] mMimeTypes;
- final ScanResultListener mClient;
+ final OnScanCompletedListener mClient;
MediaScannerConnection mConnection;
int mNextPath;
-
- ClientProxy(String[] paths, String[] mimeTypes, ScanResultListener client) {
+
+ ClientProxy(String[] paths, String[] mimeTypes, OnScanCompletedListener client) {
mPaths = paths;
mMimeTypes = mimeTypes;
mClient = client;
}
-
+
public void onMediaScannerConnected() {
scanNextPath();
}
-
+
public void onScanCompleted(String path, Uri uri) {
if (mClient != null) {
mClient.onScanCompleted(path, uri);
}
scanNextPath();
}
-
+
void scanNextPath() {
if (mNextPath >= mPaths.length) {
mConnection.disconnect();
@@ -210,7 +210,7 @@
mNextPath++;
}
}
-
+
/**
* Convenience for constructing a {@link MediaScannerConnection}, calling
* {@link #connect} on it, and calling {@link #scanFile} with the given
@@ -218,7 +218,7 @@
* established.
* @param context The caller's Context, required for establishing a connection to
* the media scanner service.
- * Success or failure of the scanning operation cannot be determined until
+ * Success or failure of the scanning operation cannot be determined until
* {@link MediaScannerConnectionClient#onScanCompleted(String, Uri)} is called.
* @param paths Array of paths to be scanned.
* @param mimeTypes Optional array of MIME types for each path.
@@ -229,13 +229,13 @@
* @see scanFile(String, String)
*/
public static void scanFile(Context context, String[] paths, String[] mimeTypes,
- ScanResultListener callback) {
+ OnScanCompletedListener callback) {
ClientProxy client = new ClientProxy(paths, mimeTypes, callback);
MediaScannerConnection connection = new MediaScannerConnection(context, client);
client.mConnection = connection;
connection.connect();
}
-
+
/**
* Part of the ServiceConnection interface. Do not call.
*/
diff --git a/media/libstagefright/AwesomePlayer.cpp b/media/libstagefright/AwesomePlayer.cpp
index 27add0a..63dfa67 100644
--- a/media/libstagefright/AwesomePlayer.cpp
+++ b/media/libstagefright/AwesomePlayer.cpp
@@ -668,7 +668,9 @@
}
status_t AwesomePlayer::getPosition(int64_t *positionUs) {
- if (mVideoSource != NULL) {
+ if (mSeeking) {
+ *positionUs = mSeekTimeUs;
+ } else if (mVideoSource != NULL) {
Mutex::Autolock autoLock(mMiscStateLock);
*positionUs = mVideoTimeUs;
} else if (mAudioPlayer != NULL) {
@@ -710,7 +712,6 @@
mWatchForAudioSeekComplete = true;
mWatchForAudioEOS = true;
- mSeeking = false;
mSeekNotificationSent = false;
}
}
@@ -1001,6 +1002,8 @@
notifyListener_l(MEDIA_SEEK_COMPLETE);
mSeekNotificationSent = true;
}
+
+ mSeeking = false;
}
status_t finalStatus;
@@ -1088,7 +1091,7 @@
}
dataSource = new CachingDataSource(
- mConnectingDataSource, 32 * 1024, 20);
+ mConnectingDataSource, 64 * 1024, 10);
mConnectingDataSource.clear();
} else {
diff --git a/media/libstagefright/DataSource.cpp b/media/libstagefright/DataSource.cpp
index 284e3bc..86e4bfe 100644
--- a/media/libstagefright/DataSource.cpp
+++ b/media/libstagefright/DataSource.cpp
@@ -105,7 +105,7 @@
if (httpSource->connect() != OK) {
return NULL;
}
- source = new CachingDataSource(httpSource, 32 * 1024, 20);
+ source = new CachingDataSource(httpSource, 64 * 1024, 10);
} else {
// Assume it's a filename.
source = new FileSource(uri);
diff --git a/media/libstagefright/HTTPDataSource.cpp b/media/libstagefright/HTTPDataSource.cpp
index 61ffa8d..48f8e7a 100644
--- a/media/libstagefright/HTTPDataSource.cpp
+++ b/media/libstagefright/HTTPDataSource.cpp
@@ -35,7 +35,8 @@
// connected.
static bool PerformRedirectIfNecessary(
HTTPStream *http, const String8 &headers,
- string *host, string *path, int *port) {
+ string *host, string *path, int *port,
+ status_t *result) {
String8 request;
request.append("GET ");
request.append(path->c_str());
@@ -52,6 +53,8 @@
err = http->receive_header(&http_status);
}
+ *result = err;
+
if (err != OK) {
return false;
}
@@ -181,6 +184,7 @@
host.c_str(), port, path.c_str());
int numRedirectsRemaining = 5;
+ status_t result;
do {
status_t err = mHttp->connect(host.c_str(), port);
@@ -194,9 +198,19 @@
return err;
}
- } while (PerformRedirectIfNecessary(mHttp, mHeaders, &host, &path, &port)
+ } while (PerformRedirectIfNecessary(
+ mHttp, mHeaders, &host, &path, &port, &result)
&& numRedirectsRemaining-- > 0);
+ if (result != OK) {
+ // An error occurred while attempting to follow redirections/connect.
+ Mutex::Autolock autoLock(mStateLock);
+
+ mState = DISCONNECTED;
+
+ return result;
+ }
+
string value;
if (mHttp->find_header_value("Content-Length", &value)) {
char *end;
@@ -282,7 +296,7 @@
char range[128];
if (offset > 0) {
- sprintf(range, "Range: bytes=%d-\r\n\r\n", offset);
+ sprintf(range, "Range: bytes=%d-\r\n", offset);
} else {
range[0] = '\0';
}
@@ -313,6 +327,7 @@
}
if ((http_status / 100) != 2) {
+ LOGE("HTTP request failed, http status = %d", http_status);
return UNKNOWN_ERROR;
}
@@ -349,6 +364,10 @@
memcpy(data, (const char *)mBuffer + (offset - mBufferOffset), copy);
+ if (copy < size) {
+ LOGV("short read (1), returning %d vs. %d requested", copy, size);
+ }
+
return copy;
}
diff --git a/media/libstagefright/OMXCodec.cpp b/media/libstagefright/OMXCodec.cpp
index 2346639..6037088 100644
--- a/media/libstagefright/OMXCodec.cpp
+++ b/media/libstagefright/OMXCodec.cpp
@@ -535,26 +535,6 @@
return err;
}
}
- } else if (!strncasecmp(mMIME, "audio/", 6)) {
- if ((mQuirks & kSupportsMultipleFramesPerInputBuffer)
- && !strcmp(mComponentName, "OMX.TI.AAC.decode")) {
- OMX_PARAM_PORTDEFINITIONTYPE def;
- InitOMXParams(&def);
- def.nPortIndex = kPortIndexInput;
-
- status_t err = mOMX->getParameter(
- mNode, OMX_IndexParamPortDefinition, &def, sizeof(def));
- CHECK_EQ(err, OK);
-
- const size_t kMinBufferSize = 100 * 1024;
- if (def.nBufferSize < kMinBufferSize) {
- def.nBufferSize = kMinBufferSize;
- }
-
- err = mOMX->setParameter(
- mNode, OMX_IndexParamPortDefinition, &def, sizeof(def));
- CHECK_EQ(err, OK);
- }
}
if (!strcasecmp(mMIME, MEDIA_MIMETYPE_IMAGE_JPEG)
diff --git a/media/tests/MediaFrameworkTest/src/com/android/mediaframeworktest/functional/MediaMimeTest.java b/media/tests/MediaFrameworkTest/src/com/android/mediaframeworktest/functional/MediaMimeTest.java
index 8489a67..728e68d 100644
--- a/media/tests/MediaFrameworkTest/src/com/android/mediaframeworktest/functional/MediaMimeTest.java
+++ b/media/tests/MediaFrameworkTest/src/com/android/mediaframeworktest/functional/MediaMimeTest.java
@@ -49,7 +49,6 @@
private final String TAG = "MediaMimeTest";
private Context mContext;
private final String MP3_FILE = "/sdcard/media_api/music/SHORTMP3.mp3";
- private final String MEDIA_PLAYBACK_NAME = "com.android.music.MediaPlaybackActivityStarter";
public MediaMimeTest() {
super("com.android.mediaframeworktest", MediaFrameworkTest.class);
@@ -129,7 +128,6 @@
ResolveInfo ri = resolveMime(mime);
assertNotNull(ri);
- assertEquals(MEDIA_PLAYBACK_NAME, ri.activityInfo.name.toString());
}
// Helper method to check that NO activity handles the given mime type.
diff --git a/packages/DefaultContainerService/src/com/android/defcontainer/DefaultContainerService.java b/packages/DefaultContainerService/src/com/android/defcontainer/DefaultContainerService.java
index 14c8806..57f9ce7 100644
--- a/packages/DefaultContainerService/src/com/android/defcontainer/DefaultContainerService.java
+++ b/packages/DefaultContainerService/src/com/android/defcontainer/DefaultContainerService.java
@@ -339,25 +339,19 @@
checkBoth = true;
break check_inner;
}
- // Check if user option is enabled
- boolean setInstallLoc = Settings.System.getInt(getApplicationContext()
+ // Pick user preference
+ int installPreference = Settings.System.getInt(getApplicationContext()
.getContentResolver(),
- Settings.System.SET_INSTALL_LOCATION, 0) != 0;
- if (setInstallLoc) {
- // Pick user preference
- int installPreference = Settings.System.getInt(getApplicationContext()
- .getContentResolver(),
- Settings.System.DEFAULT_INSTALL_LOCATION,
- PackageHelper.APP_INSTALL_AUTO);
- if (installPreference == PackageHelper.APP_INSTALL_INTERNAL) {
- checkInt = true;
- checkBoth = true;
- break check_inner;
- } else if (installPreference == PackageHelper.APP_INSTALL_EXTERNAL) {
- checkExt = true;
- checkBoth = true;
- break check_inner;
- }
+ Settings.Secure.DEFAULT_INSTALL_LOCATION,
+ PackageHelper.APP_INSTALL_AUTO);
+ if (installPreference == PackageHelper.APP_INSTALL_INTERNAL) {
+ checkInt = true;
+ checkBoth = true;
+ break check_inner;
+ } else if (installPreference == PackageHelper.APP_INSTALL_EXTERNAL) {
+ checkExt = true;
+ checkBoth = true;
+ break check_inner;
}
// Fall back to default policy if nothing else is specified.
checkInt = true;
diff --git a/packages/SettingsProvider/res/values/defaults.xml b/packages/SettingsProvider/res/values/defaults.xml
index 34302c4..185d72a9 100644
--- a/packages/SettingsProvider/res/values/defaults.xml
+++ b/packages/SettingsProvider/res/values/defaults.xml
@@ -56,10 +56,6 @@
<bool name="def_mount_ums_autostart">false</bool>
<bool name="def_mount_ums_prompt">true</bool>
<bool name="def_mount_ums_notify_enabled">true</bool>
- <!-- Enable User preference for setting install location -->
- <bool name="set_install_location">true</bool>
- <!-- Default install location if user preference for setting install location is turned on. -->
- <integer name="def_install_location">2</integer>
<!-- user interface sound effects -->
<integer name="def_power_sounds_enabled">1</integer>
diff --git a/packages/SettingsProvider/src/com/android/providers/settings/DatabaseHelper.java b/packages/SettingsProvider/src/com/android/providers/settings/DatabaseHelper.java
index d0e9dd9..0c0bf93 100644
--- a/packages/SettingsProvider/src/com/android/providers/settings/DatabaseHelper.java
+++ b/packages/SettingsProvider/src/com/android/providers/settings/DatabaseHelper.java
@@ -39,6 +39,8 @@
import android.util.Config;
import android.util.Log;
import android.util.Xml;
+
+import com.android.internal.content.PackageHelper;
import com.android.internal.telephony.RILConstants;
import com.android.internal.util.XmlUtils;
import com.android.internal.widget.LockPatternUtils;
@@ -61,7 +63,7 @@
// database gets upgraded properly. At a minimum, please confirm that 'upgradeVersion'
// is properly propagated through your change. Not doing so will result in a loss of user
// settings.
- private static final int DATABASE_VERSION = 55;
+ private static final int DATABASE_VERSION = 56;
private Context mContext;
@@ -608,21 +610,8 @@
if (upgradeVersion == 50) {
/*
- * New settings for set install location UI.
+ * Install location no longer initiated here.
*/
- db.beginTransaction();
- SQLiteStatement stmt = null;
- try {
- stmt = db.compileStatement("INSERT INTO system(name,value)"
- + " VALUES(?,?);");
- loadBooleanSetting(stmt, Settings.System.SET_INSTALL_LOCATION,
- R.bool.set_install_location);
- db.setTransactionSuccessful();
- } finally {
- db.endTransaction();
- if (stmt != null) stmt.close();
- }
-
upgradeVersion = 51;
}
@@ -663,21 +652,8 @@
if (upgradeVersion == 53) {
/*
- * New settings for set install location UI.
+ * New settings for set install location UI no longer initiated here.
*/
- db.beginTransaction();
- SQLiteStatement stmt = null;
- try {
- stmt = db.compileStatement("INSERT INTO system(name,value)"
- + " VALUES(?,?);");
- loadIntegerSetting(stmt, Settings.System.DEFAULT_INSTALL_LOCATION,
- R.integer.def_install_location);
- db.setTransactionSuccessful();
- } finally {
- db.endTransaction();
- if (stmt != null) stmt.close();
- }
-
upgradeVersion = 54;
}
@@ -696,6 +672,28 @@
upgradeVersion = 55;
}
+ if (upgradeVersion == 55) {
+ /* Move the install location settings. */
+ String[] settingsToMove = {
+ Secure.SET_INSTALL_LOCATION,
+ Secure.DEFAULT_INSTALL_LOCATION
+ };
+ moveFromSystemToSecure(db, settingsToMove);
+ db.beginTransaction();
+ SQLiteStatement stmt = null;
+ try {
+ stmt = db.compileStatement("INSERT INTO system(name,value)"
+ + " VALUES(?,?);");
+ loadSetting(stmt, Secure.SET_INSTALL_LOCATION, 0);
+ loadSetting(stmt, Secure.DEFAULT_INSTALL_LOCATION,
+ PackageHelper.APP_INSTALL_AUTO);
+ db.setTransactionSuccessful();
+ } finally {
+ db.endTransaction();
+ if (stmt != null) stmt.close();
+ }
+ upgradeVersion = 56;
+ }
// *** Remember to update DATABASE_VERSION above!
if (upgradeVersion != currentVersion) {
@@ -1021,10 +1019,9 @@
loadBooleanSetting(stmt, Settings.System.NOTIFICATION_LIGHT_PULSE,
R.bool.def_notification_pulse);
- loadBooleanSetting(stmt, Settings.System.SET_INSTALL_LOCATION,
- R.bool.set_install_location);
- loadIntegerSetting(stmt, Settings.System.DEFAULT_INSTALL_LOCATION,
- R.integer.def_install_location);
+ loadSetting(stmt, Settings.Secure.SET_INSTALL_LOCATION, 0);
+ loadSetting(stmt, Settings.Secure.DEFAULT_INSTALL_LOCATION,
+ PackageHelper.APP_INSTALL_AUTO);
loadUISoundEffectsSettings(stmt);
diff --git a/services/java/com/android/server/NetworkManagementService.java b/services/java/com/android/server/NetworkManagementService.java
index 6d16aed..552bed4 100644
--- a/services/java/com/android/server/NetworkManagementService.java
+++ b/services/java/com/android/server/NetworkManagementService.java
@@ -564,11 +564,11 @@
return getInterfaceCounter(iface, false);
}
- public void setInterfaceThrottle(String iface, int maxKbps, int rxKbps, int txKbps) {
+ public void setInterfaceThrottle(String iface, int rxKbps, int txKbps) {
mContext.enforceCallingOrSelfPermission(
android.Manifest.permission.CHANGE_NETWORK_STATE, "NetworkManagementService");
mConnector.doCommand(String.format(
- "interface setthrottle %s %d %d %d", iface, maxKbps, rxKbps, txKbps));
+ "interface setthrottle %s %d %d", iface, rxKbps, txKbps));
}
private int getInterfaceThrottle(String iface, boolean rx) {
diff --git a/services/java/com/android/server/PackageManagerService.java b/services/java/com/android/server/PackageManagerService.java
index b1bd263..e6663d4 100644
--- a/services/java/com/android/server/PackageManagerService.java
+++ b/services/java/com/android/server/PackageManagerService.java
@@ -31,8 +31,9 @@
import android.app.IActivityManager;
import android.app.admin.IDevicePolicyManager;
import android.app.backup.IBackupManager;
-import android.content.ComponentName;
import android.content.Context;
+import android.content.ComponentName;
+import android.content.IIntentReceiver;
import android.content.Intent;
import android.content.IntentFilter;
import android.content.IntentSender;
@@ -83,6 +84,7 @@
import android.os.ServiceManager;
import android.os.SystemClock;
import android.os.SystemProperties;
+import android.provider.Settings;
import android.security.SystemKeyStore;
import android.util.*;
import android.view.Display;
@@ -582,11 +584,11 @@
}
sendPackageBroadcast(Intent.ACTION_PACKAGE_ADDED,
res.pkg.applicationInfo.packageName,
- extras);
+ extras, null);
if (update) {
sendPackageBroadcast(Intent.ACTION_PACKAGE_REPLACED,
res.pkg.applicationInfo.packageName,
- extras);
+ extras, null);
}
if (res.removedInfo.args != null) {
// Remove the replaced package's older resources safely now
@@ -954,7 +956,20 @@
+ ((SystemClock.uptimeMillis()-startTime)/1000f)
+ " seconds");
- updatePermissionsLP(null, null, true, false);
+ // If the platform SDK has changed since the last time we booted,
+ // we need to re-grant app permission to catch any new ones that
+ // appear. This is really a hack, and means that apps can in some
+ // cases get permissions that the user didn't initially explicitly
+ // allow... it would be nice to have some better way to handle
+ // this situation.
+ final boolean regrantPermissions = mSettings.mInternalSdkPlatform
+ != mSdkVersion;
+ if (regrantPermissions) Slog.i(TAG, "Platform changed from "
+ + mSettings.mInternalSdkPlatform + " to " + mSdkVersion
+ + "; regranting permissions for internal storage");
+ mSettings.mInternalSdkPlatform = mSdkVersion;
+
+ updatePermissionsLP(null, null, true, regrantPermissions);
mSettings.writeLP();
@@ -4458,7 +4473,8 @@
}
};
- private static final void sendPackageBroadcast(String action, String pkg, Bundle extras) {
+ private static final void sendPackageBroadcast(String action, String pkg,
+ Bundle extras, IIntentReceiver finishedReceiver) {
IActivityManager am = ActivityManagerNative.getDefault();
if (am != null) {
try {
@@ -4468,9 +4484,8 @@
intent.putExtras(extras);
}
intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT);
- am.broadcastIntent(
- null, intent,
- null, null, 0, null, null, null, false, false);
+ am.broadcastIntent(null, intent, null, finishedReceiver,
+ 0, null, null, null, finishedReceiver != null, false);
} catch (RemoteException ex) {
}
}
@@ -4592,12 +4607,14 @@
Bundle extras = new Bundle(1);
extras.putInt(Intent.EXTRA_UID, removedUid);
extras.putBoolean(Intent.EXTRA_DATA_REMOVED, false);
- sendPackageBroadcast(Intent.ACTION_PACKAGE_REMOVED, removedPackage, extras);
+ sendPackageBroadcast(Intent.ACTION_PACKAGE_REMOVED, removedPackage,
+ extras, null);
}
if (addedPackage != null) {
Bundle extras = new Bundle(1);
extras.putInt(Intent.EXTRA_UID, addedUid);
- sendPackageBroadcast(Intent.ACTION_PACKAGE_ADDED, addedPackage, extras);
+ sendPackageBroadcast(Intent.ACTION_PACKAGE_ADDED, addedPackage,
+ extras, null);
}
}
@@ -6039,8 +6056,8 @@
extras.putInt(Intent.EXTRA_UID, info.removedUid >= 0 ? info.removedUid : info.uid);
extras.putBoolean(Intent.EXTRA_REPLACING, true);
- sendPackageBroadcast(Intent.ACTION_PACKAGE_ADDED, packageName, extras);
- sendPackageBroadcast(Intent.ACTION_PACKAGE_REPLACED, packageName, extras);
+ sendPackageBroadcast(Intent.ACTION_PACKAGE_ADDED, packageName, extras, null);
+ sendPackageBroadcast(Intent.ACTION_PACKAGE_REPLACED, packageName, extras, null);
}
}
// Force a gc here.
@@ -6071,10 +6088,10 @@
extras.putBoolean(Intent.EXTRA_REPLACING, true);
}
if (removedPackage != null) {
- sendPackageBroadcast(Intent.ACTION_PACKAGE_REMOVED, removedPackage, extras);
+ sendPackageBroadcast(Intent.ACTION_PACKAGE_REMOVED, removedPackage, extras, null);
}
if (removedUid >= 0) {
- sendPackageBroadcast(Intent.ACTION_UID_REMOVED, null, extras);
+ sendPackageBroadcast(Intent.ACTION_UID_REMOVED, null, extras, null);
}
}
}
@@ -6776,7 +6793,7 @@
extras.putStringArray(Intent.EXTRA_CHANGED_COMPONENT_NAME_LIST, nameList);
extras.putBoolean(Intent.EXTRA_DONT_KILL_APP, killFlag);
extras.putInt(Intent.EXTRA_UID, packageUid);
- sendPackageBroadcast(Intent.ACTION_PACKAGE_CHANGED, packageName, extras);
+ sendPackageBroadcast(Intent.ACTION_PACKAGE_CHANGED, packageName, extras, null);
}
public String getInstallerPackageName(String packageName) {
@@ -7707,6 +7724,12 @@
final HashMap<String, PackageSetting> mDisabledSysPackages =
new HashMap<String, PackageSetting>();
+ // These are the last platform API version we were using for
+ // the apps installed on internal and external storage. It is
+ // used to grant newer permissions one time during a system upgrade.
+ int mInternalSdkPlatform;
+ int mExternalSdkPlatform;
+
// The user's preferred activities associated with particular intent
// filters.
private final IntentResolver<PreferredActivity, PreferredActivity> mPreferredActivities =
@@ -8291,6 +8314,11 @@
serializer.startTag(null, "packages");
+ serializer.startTag(null, "last-platform-version");
+ serializer.attribute(null, "internal", Integer.toString(mInternalSdkPlatform));
+ serializer.attribute(null, "external", Integer.toString(mExternalSdkPlatform));
+ serializer.endTag(null, "last-platform-version");
+
serializer.startTag(null, "permission-trees");
for (BasePermission bp : mPermissionTrees.values()) {
writePermission(serializer, bp);
@@ -8684,6 +8712,19 @@
if (nname != null && oname != null) {
mRenamedPackages.put(nname, oname);
}
+ } else if (tagName.equals("last-platform-version")) {
+ mInternalSdkPlatform = mExternalSdkPlatform = 0;
+ try {
+ String internal = parser.getAttributeValue(null, "internal");
+ if (internal != null) {
+ mInternalSdkPlatform = Integer.parseInt(internal);
+ }
+ String external = parser.getAttributeValue(null, "external");
+ if (external != null) {
+ mInternalSdkPlatform = Integer.parseInt(external);
+ }
+ } catch (NumberFormatException e) {
+ }
} else {
Slog.w(TAG, "Unknown element under <packages>: "
+ parser.getName());
@@ -9475,7 +9516,7 @@
}
private void sendResourcesChangedBroadcast(boolean mediaStatus,
- ArrayList<String> pkgList, int uidArr[]) {
+ ArrayList<String> pkgList, int uidArr[], IIntentReceiver finishedReceiver) {
int size = pkgList.size();
if (size > 0) {
// Send broadcasts here
@@ -9487,7 +9528,7 @@
}
String action = mediaStatus ? Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE
: Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE;
- sendPackageBroadcast(action, null, extras);
+ sendPackageBroadcast(action, null, extras, finishedReceiver);
}
}
@@ -9553,15 +9594,28 @@
}
}
synchronized (mPackages) {
+ // If the platform SDK has changed since the last time we booted,
+ // we need to re-grant app permission to catch any new ones that
+ // appear. This is really a hack, and means that apps can in some
+ // cases get permissions that the user didn't initially explicitly
+ // allow... it would be nice to have some better way to handle
+ // this situation.
+ final boolean regrantPermissions = mSettings.mExternalSdkPlatform
+ != mSdkVersion;
+ if (regrantPermissions) Slog.i(TAG, "Platform changed from "
+ + mSettings.mExternalSdkPlatform + " to " + mSdkVersion
+ + "; regranting permissions for external storage");
+ mSettings.mExternalSdkPlatform = mSdkVersion;
+
// Make sure group IDs have been assigned, and any permission
// changes in other apps are accounted for
- updatePermissionsLP(null, null, true, false);
+ updatePermissionsLP(null, null, true, regrantPermissions);
// Persist settings
mSettings.writeLP();
}
// Send a broadcast to let everyone know we are done processing
if (pkgList.size() > 0) {
- sendResourcesChangedBroadcast(true, pkgList, uidArr);
+ sendResourcesChangedBroadcast(true, pkgList, uidArr, null);
}
if (doGc) {
Runtime.getRuntime().gc();
@@ -9599,10 +9653,15 @@
}
// Send broadcasts
if (pkgList.size() > 0) {
- sendResourcesChangedBroadcast(false, pkgList, uidArr);
+ sendResourcesChangedBroadcast(false, pkgList, uidArr, new IIntentReceiver.Stub() {
+ public void performReceive(Intent intent, int resultCode, String data, Bundle extras,
+ boolean ordered, boolean sticky) throws RemoteException {
+ // Force gc now that everyone is done cleaning up, to release
+ // references on assets.
+ Runtime.getRuntime().gc();
+ }
+ });
}
- // Force gc
- Runtime.getRuntime().gc();
// Just unmount all valid containers.
for (SdInstallArgs args : keys) {
synchronized (mInstallLock) {
@@ -9613,9 +9672,6 @@
public void movePackage(final String packageName,
final IPackageMoveObserver observer, final int flags) {
- if (packageName == null) {
- return;
- }
mContext.enforceCallingOrSelfPermission(
android.Manifest.permission.MOVE_PACKAGE, null);
int returnCode = PackageManager.MOVE_SUCCEEDED;
@@ -9625,30 +9681,31 @@
PackageParser.Package pkg = mPackages.get(packageName);
if (pkg == null) {
returnCode = PackageManager.MOVE_FAILED_DOESNT_EXIST;
- }
- // Disable moving fwd locked apps and system packages
- if (pkg.applicationInfo != null &&
- (pkg.applicationInfo.flags & ApplicationInfo.FLAG_SYSTEM) != 0) {
- Slog.w(TAG, "Cannot move system application");
- returnCode = PackageManager.MOVE_FAILED_SYSTEM_PACKAGE;
- } else if (pkg.applicationInfo != null &&
- (pkg.applicationInfo.flags & ApplicationInfo.FLAG_FORWARD_LOCK) != 0) {
- Slog.w(TAG, "Cannot move forward locked app.");
- returnCode = PackageManager.MOVE_FAILED_FORWARD_LOCKED;
} else {
- // Find install location first
- if ((flags & PackageManager.MOVE_EXTERNAL_MEDIA) != 0 &&
- (flags & PackageManager.MOVE_INTERNAL) != 0) {
- Slog.w(TAG, "Ambigous flags specified for move location.");
- returnCode = PackageManager.MOVE_FAILED_INVALID_LOCATION;
+ // Disable moving fwd locked apps and system packages
+ if (pkg.applicationInfo != null &&
+ (pkg.applicationInfo.flags & ApplicationInfo.FLAG_SYSTEM) != 0) {
+ Slog.w(TAG, "Cannot move system application");
+ returnCode = PackageManager.MOVE_FAILED_SYSTEM_PACKAGE;
+ } else if (pkg.applicationInfo != null &&
+ (pkg.applicationInfo.flags & ApplicationInfo.FLAG_FORWARD_LOCK) != 0) {
+ Slog.w(TAG, "Cannot move forward locked app.");
+ returnCode = PackageManager.MOVE_FAILED_FORWARD_LOCKED;
} else {
- newFlags = (flags & PackageManager.MOVE_EXTERNAL_MEDIA) != 0 ?
- PackageManager.INSTALL_EXTERNAL : 0;
- currFlags = (pkg.applicationInfo.flags & ApplicationInfo.FLAG_EXTERNAL_STORAGE) != 0 ?
- PackageManager.INSTALL_EXTERNAL : 0;
- if (newFlags == currFlags) {
- Slog.w(TAG, "No move required. Trying to move to same location");
+ // Find install location first
+ if ((flags & PackageManager.MOVE_EXTERNAL_MEDIA) != 0 &&
+ (flags & PackageManager.MOVE_INTERNAL) != 0) {
+ Slog.w(TAG, "Ambigous flags specified for move location.");
returnCode = PackageManager.MOVE_FAILED_INVALID_LOCATION;
+ } else {
+ newFlags = (flags & PackageManager.MOVE_EXTERNAL_MEDIA) != 0 ?
+ PackageManager.INSTALL_EXTERNAL : PackageManager.INSTALL_INTERNAL;
+ currFlags = (pkg.applicationInfo.flags & ApplicationInfo.FLAG_EXTERNAL_STORAGE) != 0 ?
+ PackageManager.INSTALL_EXTERNAL : PackageManager.INSTALL_INTERNAL;
+ if (newFlags == currFlags) {
+ Slog.w(TAG, "No move required. Trying to move to same location");
+ returnCode = PackageManager.MOVE_FAILED_INVALID_LOCATION;
+ }
}
}
}
@@ -9672,67 +9729,87 @@
public void run() {
mHandler.removeCallbacks(this);
int returnCode = currentStatus;
- boolean moveSucceeded = (returnCode == PackageManager.MOVE_SUCCEEDED);
- if (moveSucceeded) {
- int uid = -1;
+ if (currentStatus == PackageManager.MOVE_SUCCEEDED) {
+ int uidArr[] = null;
+ ArrayList<String> pkgList = null;
synchronized (mPackages) {
- uid = mPackages.get(mp.packageName).applicationInfo.uid;
- }
- ArrayList<String> pkgList = new ArrayList<String>();
- pkgList.add(mp.packageName);
- int uidArr[] = new int[] { uid };
- // Send resources unavailable broadcast
- sendResourcesChangedBroadcast(false, pkgList, uidArr);
-
- // Update package code and resource paths
- synchronized (mInstallLock) {
- synchronized (mPackages) {
- PackageParser.Package pkg = mPackages.get(mp.packageName);
- if (pkg != null) {
- String oldCodePath = pkg.mPath;
- String newCodePath = mp.targetArgs.getCodePath();
- String newResPath = mp.targetArgs.getResourcePath();
- pkg.mPath = newCodePath;
- // Move dex files around
- if (moveDexFilesLI(pkg)
- != PackageManager.INSTALL_SUCCEEDED) {
- // Moving of dex files failed. Set
- // error code and abort move.
- pkg.mPath = pkg.mScanPath;
- returnCode = PackageManager.MOVE_FAILED_INSUFFICIENT_STORAGE;
- moveSucceeded = false;
- } else {
- pkg.mScanPath = newCodePath;
- pkg.applicationInfo.sourceDir = newCodePath;
- pkg.applicationInfo.publicSourceDir = newResPath;
- PackageSetting ps = (PackageSetting) pkg.mExtras;
- ps.codePath = new File(pkg.applicationInfo.sourceDir);
- ps.codePathString = ps.codePath.getPath();
- ps.resourcePath = new File(pkg.applicationInfo.publicSourceDir);
- ps.resourcePathString = ps.resourcePath.getPath();
- // Set the application info flag correctly.
- if ((mp.flags & PackageManager.INSTALL_EXTERNAL) != 0) {
- pkg.applicationInfo.flags |= ApplicationInfo.FLAG_EXTERNAL_STORAGE;
- } else {
- pkg.applicationInfo.flags &= ~ApplicationInfo.FLAG_EXTERNAL_STORAGE;
- }
- ps.setFlags(pkg.applicationInfo.flags);
- mAppDirs.remove(oldCodePath);
- mAppDirs.put(newCodePath, pkg);
- // Persist settings
- mSettings.writeLP();
- }
- }
+ PackageParser.Package pkg = mPackages.get(mp.packageName);
+ if (pkg == null ) {
+ Slog.w(TAG, " Package " + mp.packageName +
+ " doesn't exist. Aborting move");
+ returnCode = PackageManager.MOVE_FAILED_DOESNT_EXIST;
+ } else if (!mp.srcArgs.getCodePath().equals(pkg.applicationInfo.sourceDir)) {
+ Slog.w(TAG, "Package " + mp.packageName + " code path changed from " +
+ mp.srcArgs.getCodePath() + " to " + pkg.applicationInfo.sourceDir +
+ " Aborting move and returning error");
+ returnCode = PackageManager.MOVE_FAILED_INTERNAL_ERROR;
+ } else {
+ uidArr = new int[] { pkg.applicationInfo.uid };
+ pkgList = new ArrayList<String>();
+ pkgList.add(mp.packageName);
}
}
- // Send resources available broadcast
- sendResourcesChangedBroadcast(true, pkgList, uidArr);
+ if (returnCode == PackageManager.MOVE_SUCCEEDED) {
+ // Send resources unavailable broadcast
+ sendResourcesChangedBroadcast(false, pkgList, uidArr, null);
+ // Update package code and resource paths
+ synchronized (mInstallLock) {
+ synchronized (mPackages) {
+ PackageParser.Package pkg = mPackages.get(mp.packageName);
+ // Recheck for package again.
+ if (pkg == null ) {
+ Slog.w(TAG, " Package " + mp.packageName +
+ " doesn't exist. Aborting move");
+ returnCode = PackageManager.MOVE_FAILED_DOESNT_EXIST;
+ } else if (!mp.srcArgs.getCodePath().equals(pkg.applicationInfo.sourceDir)) {
+ Slog.w(TAG, "Package " + mp.packageName + " code path changed from " +
+ mp.srcArgs.getCodePath() + " to " + pkg.applicationInfo.sourceDir +
+ " Aborting move and returning error");
+ returnCode = PackageManager.MOVE_FAILED_INTERNAL_ERROR;
+ } else {
+ String oldCodePath = pkg.mPath;
+ String newCodePath = mp.targetArgs.getCodePath();
+ String newResPath = mp.targetArgs.getResourcePath();
+ pkg.mPath = newCodePath;
+ // Move dex files around
+ if (moveDexFilesLI(pkg)
+ != PackageManager.INSTALL_SUCCEEDED) {
+ // Moving of dex files failed. Set
+ // error code and abort move.
+ pkg.mPath = pkg.mScanPath;
+ returnCode = PackageManager.MOVE_FAILED_INSUFFICIENT_STORAGE;
+ } else {
+ pkg.mScanPath = newCodePath;
+ pkg.applicationInfo.sourceDir = newCodePath;
+ pkg.applicationInfo.publicSourceDir = newResPath;
+ PackageSetting ps = (PackageSetting) pkg.mExtras;
+ ps.codePath = new File(pkg.applicationInfo.sourceDir);
+ ps.codePathString = ps.codePath.getPath();
+ ps.resourcePath = new File(pkg.applicationInfo.publicSourceDir);
+ ps.resourcePathString = ps.resourcePath.getPath();
+ // Set the application info flag correctly.
+ if ((mp.flags & PackageManager.INSTALL_EXTERNAL) != 0) {
+ pkg.applicationInfo.flags |= ApplicationInfo.FLAG_EXTERNAL_STORAGE;
+ } else {
+ pkg.applicationInfo.flags &= ~ApplicationInfo.FLAG_EXTERNAL_STORAGE;
+ }
+ ps.setFlags(pkg.applicationInfo.flags);
+ mAppDirs.remove(oldCodePath);
+ mAppDirs.put(newCodePath, pkg);
+ // Persist settings
+ mSettings.writeLP();
+ }
+ }
+ }
+ // Send resources available broadcast
+ sendResourcesChangedBroadcast(true, pkgList, uidArr, null);
+ }
+ }
}
- if (!moveSucceeded){
+ if (returnCode != PackageManager.MOVE_SUCCEEDED){
// Clean up failed installation
if (mp.targetArgs != null) {
- mp.targetArgs.doPostInstall(
- returnCode);
+ mp.targetArgs.doPostInstall(PackageManager.INSTALL_FAILED_INTERNAL_ERROR);
}
} else {
// Force a gc to clear things up.
@@ -9753,4 +9830,26 @@
}
});
}
+
+ public boolean setInstallLocation(int loc) {
+ mContext.enforceCallingOrSelfPermission(
+ android.Manifest.permission.WRITE_SECURE_SETTINGS, null);
+ if (getInstallLocation() == loc) {
+ return true;
+ }
+ if (loc == PackageHelper.APP_INSTALL_AUTO ||
+ loc == PackageHelper.APP_INSTALL_INTERNAL ||
+ loc == PackageHelper.APP_INSTALL_EXTERNAL) {
+ android.provider.Settings.System.putInt(mContext.getContentResolver(),
+ android.provider.Settings.Secure.DEFAULT_INSTALL_LOCATION, loc);
+ return true;
+ }
+ return false;
+ }
+
+ public int getInstallLocation() {
+ return android.provider.Settings.System.getInt(mContext.getContentResolver(),
+ android.provider.Settings.Secure.DEFAULT_INSTALL_LOCATION, PackageHelper.APP_INSTALL_AUTO);
+ }
}
+
diff --git a/services/java/com/android/server/am/ActivityManagerService.java b/services/java/com/android/server/am/ActivityManagerService.java
index 3b655fa..bc26fa0 100644
--- a/services/java/com/android/server/am/ActivityManagerService.java
+++ b/services/java/com/android/server/am/ActivityManagerService.java
@@ -1369,7 +1369,7 @@
return;
}
} else {
- procs = service.mLruProcesses;
+ procs = new ArrayList<ProcessRecord>(service.mLruProcesses);
}
}
dumpApplicationMemoryUsage(fd, pw, procs, " ", args);
@@ -10202,7 +10202,7 @@
return numPers;
}
- private static final void dumpApplicationMemoryUsage(FileDescriptor fd,
+ static final void dumpApplicationMemoryUsage(FileDescriptor fd,
PrintWriter pw, List list, String prefix, String[] args) {
final boolean isCheckinRequest = scanArgs(args, "--checkin");
long uptime = SystemClock.uptimeMillis();
diff --git a/services/java/com/android/server/status/StatusBarPolicy.java b/services/java/com/android/server/status/StatusBarPolicy.java
index 55840e2..465ff2e 100644
--- a/services/java/com/android/server/status/StatusBarPolicy.java
+++ b/services/java/com/android/server/status/StatusBarPolicy.java
@@ -818,7 +818,7 @@
final ContentResolver cr = mContext.getContentResolver();
if (Settings.System.getInt(cr,
- Settings.System.POWER_SOUNDS_ENABLED, 1) == 1)
+ Settings.System.POWER_SOUNDS_ENABLED, 1) == 1)
{
final String soundPath = Settings.System.getString(cr,
Settings.System.LOW_BATTERY_SOUND);
@@ -972,7 +972,8 @@
int iconLevel = -1;
int[] iconList;
- if (!hasService()) {
+ // Display signal strength while in "emergency calls only" mode
+ if (!hasService() && !mServiceState.isEmergencyOnly()) {
//Slog.d(TAG, "updateSignalStrength: no service");
if (Settings.System.getInt(mContext.getContentResolver(),
Settings.System.AIRPLANE_MODE_ON, 0) == 1) {
diff --git a/telephony/java/android/telephony/ServiceState.java b/telephony/java/android/telephony/ServiceState.java
index 48a40fa..6c66559 100644
--- a/telephony/java/android/telephony/ServiceState.java
+++ b/telephony/java/android/telephony/ServiceState.java
@@ -113,6 +113,8 @@
private String mOperatorNumeric;
private boolean mIsManualNetworkSelection;
+ private boolean mIsEmergencyOnly;
+
//***** CDMA
private int mRadioTechnology;
private boolean mCssIndicator;
@@ -170,6 +172,7 @@
mCdmaDefaultRoamingIndicator = s.mCdmaDefaultRoamingIndicator;
mCdmaEriIconIndex = s.mCdmaEriIconIndex;
mCdmaEriIconMode = s.mCdmaEriIconMode;
+ mIsEmergencyOnly = s.mIsEmergencyOnly;
}
/**
@@ -190,6 +193,7 @@
mCdmaDefaultRoamingIndicator = in.readInt();
mCdmaEriIconIndex = in.readInt();
mCdmaEriIconMode = in.readInt();
+ mIsEmergencyOnly = in.readInt() != 0;
}
public void writeToParcel(Parcel out, int flags) {
@@ -207,6 +211,7 @@
out.writeInt(mCdmaDefaultRoamingIndicator);
out.writeInt(mCdmaEriIconIndex);
out.writeInt(mCdmaEriIconMode);
+ out.writeInt(mIsEmergencyOnly ? 1 : 0);
}
public int describeContents() {
@@ -250,6 +255,13 @@
/**
* @hide
*/
+ public boolean isEmergencyOnly() {
+ return mIsEmergencyOnly;
+ }
+
+ /**
+ * @hide
+ */
public int getCdmaRoamingIndicator(){
return this.mCdmaRoamingIndicator;
}
@@ -330,7 +342,8 @@
+ ((null == mOperatorAlphaShort) ? 0 : mOperatorAlphaShort.hashCode())
+ ((null == mOperatorNumeric) ? 0 : mOperatorNumeric.hashCode())
+ mCdmaRoamingIndicator
- + mCdmaDefaultRoamingIndicator);
+ + mCdmaDefaultRoamingIndicator
+ + (mIsEmergencyOnly ? 1 : 0));
}
@Override
@@ -359,7 +372,8 @@
&& equalsHandlesNulls(mSystemId, s.mSystemId)
&& equalsHandlesNulls(mCdmaRoamingIndicator, s.mCdmaRoamingIndicator)
&& equalsHandlesNulls(mCdmaDefaultRoamingIndicator,
- s.mCdmaDefaultRoamingIndicator));
+ s.mCdmaDefaultRoamingIndicator)
+ && mIsEmergencyOnly == s.mIsEmergencyOnly);
}
@Override
@@ -418,7 +432,8 @@
+ " " + mNetworkId
+ " " + mSystemId
+ "RoamInd: " + mCdmaRoamingIndicator
- + "DefRoamInd: " + mCdmaDefaultRoamingIndicator);
+ + "DefRoamInd: " + mCdmaDefaultRoamingIndicator
+ + "EmergOnly: " + mIsEmergencyOnly);
}
public void setStateOutOfService() {
@@ -436,6 +451,7 @@
mCdmaDefaultRoamingIndicator = -1;
mCdmaEriIconIndex = -1;
mCdmaEriIconMode = -1;
+ mIsEmergencyOnly = false;
}
// TODO - can't this be combined with the above func..
@@ -454,6 +470,7 @@
mCdmaDefaultRoamingIndicator = -1;
mCdmaEriIconIndex = -1;
mCdmaEriIconMode = -1;
+ mIsEmergencyOnly = false;
}
public void setState(int state) {
@@ -464,6 +481,14 @@
mRoaming = roaming;
}
+
+ /**
+ * @hide
+ */
+ public void setEmergencyOnly(boolean emergencyOnly) {
+ mIsEmergencyOnly = emergencyOnly;
+ }
+
/**
* @hide
*/
@@ -542,6 +567,7 @@
mSystemId = m.getInt("systemId");
mCdmaRoamingIndicator = m.getInt("cdmaRoamingIndicator");
mCdmaDefaultRoamingIndicator = m.getInt("cdmaDefaultRoamingIndicator");
+ mIsEmergencyOnly = m.getBoolean("emergencyOnly");
}
/**
@@ -563,6 +589,7 @@
m.putInt("systemId", mSystemId);
m.putInt("cdmaRoamingIndicator", mCdmaRoamingIndicator);
m.putInt("cdmaDefaultRoamingIndicator", mCdmaDefaultRoamingIndicator);
+ m.putBoolean("emergencyOnly", Boolean.valueOf(mIsEmergencyOnly));
}
//***** CDMA
diff --git a/telephony/java/com/android/internal/telephony/gsm/GsmServiceStateTracker.java b/telephony/java/com/android/internal/telephony/gsm/GsmServiceStateTracker.java
index e4fcf6c..50b8eba 100644
--- a/telephony/java/com/android/internal/telephony/gsm/GsmServiceStateTracker.java
+++ b/telephony/java/com/android/internal/telephony/gsm/GsmServiceStateTracker.java
@@ -102,7 +102,6 @@
* Mark when service state is in emergency call only mode
*/
private boolean mEmergencyOnly = false;
- private boolean mNewEmergencyOnly = false;
private RegistrantList gprsAttachedRegistrants = new RegistrantList();
private RegistrantList gprsDetachedRegistrants = new RegistrantList();
@@ -591,8 +590,8 @@
if (rule != curSpnRule
|| !TextUtils.equals(spn, curSpn)
|| !TextUtils.equals(plmn, curPlmn)) {
- boolean showSpn = mEmergencyOnly
- || (rule & SIMRecords.SPN_RULE_SHOW_SPN) == SIMRecords.SPN_RULE_SHOW_SPN;
+ boolean showSpn = !mEmergencyOnly
+ && (rule & SIMRecords.SPN_RULE_SHOW_SPN) == SIMRecords.SPN_RULE_SHOW_SPN;
boolean showPlmn =
(rule & SIMRecords.SPN_RULE_SHOW_PLMN) == SIMRecords.SPN_RULE_SHOW_PLMN;
@@ -672,9 +671,9 @@
newSS.setState (regCodeToServiceState(regState));
if (regState == 10 || regState == 12 || regState == 13 || regState == 14) {
- mNewEmergencyOnly = true;
+ mEmergencyOnly = true;
} else {
- mNewEmergencyOnly = false;
+ mEmergencyOnly = false;
}
// LAC and CID are -1 if not avail
@@ -741,6 +740,7 @@
roaming = false;
}
newSS.setRoaming(roaming);
+ newSS.setEmergencyOnly(mEmergencyOnly);
pollStateDone();
}
}
@@ -886,8 +886,6 @@
boolean hasLocationChanged = !newCellLoc.equals(cellLoc);
- boolean hasEmergencyOnlyChanged = mNewEmergencyOnly != mEmergencyOnly;
-
// Add an event log when connection state changes
if (ss.getState() != newSS.getState() || gprsState != newGPRSState) {
EventLog.writeEvent(EventLogTags.GSM_SERVICE_STATE_CHANGE,
@@ -905,8 +903,6 @@
cellLoc = newCellLoc;
newCellLoc = tcl;
- mEmergencyOnly = mNewEmergencyOnly;
-
// Add an event log when network type switched
// TODO: we may add filtering to reduce the event logged,
// i.e. check preferred network setting, only switch to 2G, etc
@@ -937,6 +933,8 @@
if (hasChanged) {
String operatorNumeric;
+ updateSpnDisplay();
+
phone.setSystemProperty(TelephonyProperties.PROPERTY_OPERATOR_ALPHA,
ss.getOperatorAlphaLong());
@@ -1005,10 +1003,6 @@
phone.notifyServiceStateChanged(ss);
}
- if (hasChanged || hasEmergencyOnlyChanged) {
- updateSpnDisplay();
- }
-
if (hasGprsAttached) {
gprsAttachedRegistrants.notifyRegistrants();
}