Merge "Update device password expiration/alarm behavior"
diff --git a/Android.mk b/Android.mk
index 0fe1164..efa7d69 100644
--- a/Android.mk
+++ b/Android.mk
@@ -407,8 +407,6 @@
resources/samples/CubeLiveWallpaper "Live Wallpaper" \
-samplecode $(sample_dir)/Home \
resources/samples/Home "Home" \
- -samplecode $(sample_dir)/HeavyWeight \
- resources/samples/HeavyWeight "Heavy Weight App" \
-samplecode $(sample_dir)/JetBoy \
resources/samples/JetBoy "JetBoy" \
-samplecode $(sample_dir)/LunarLander \
diff --git a/core/java/android/widget/TextView.java b/core/java/android/widget/TextView.java
index 75ba704..d164d11 100644
--- a/core/java/android/widget/TextView.java
+++ b/core/java/android/widget/TextView.java
@@ -9061,6 +9061,7 @@
return mInBatchEditControllers;
}
+ @ViewDebug.ExportedProperty(category = "text")
private CharSequence mText;
private CharSequence mTransformed;
private BufferType mBufferType = BufferType.NORMAL;
diff --git a/core/java/com/android/internal/widget/LockPatternUtils.java b/core/java/com/android/internal/widget/LockPatternUtils.java
index 90423be..bf59753 100644
--- a/core/java/com/android/internal/widget/LockPatternUtils.java
+++ b/core/java/com/android/internal/widget/LockPatternUtils.java
@@ -95,6 +95,7 @@
private final static String PATTERN_EVER_CHOSEN_KEY = "lockscreen.patterneverchosen";
public final static String PASSWORD_TYPE_KEY = "lockscreen.password_type";
private final static String LOCK_PASSWORD_SALT_KEY = "lockscreen.password_salt";
+ private final static String DISABLE_LOCKSCREEN_KEY = "lockscreen.disabled";
private final static String PASSWORD_HISTORY_KEY = "lockscreen.passwordhistory";
@@ -355,6 +356,26 @@
}
/**
+ * Disable showing lock screen at all when the DevicePolicyManager allows it.
+ * This is only meaningful if pattern, pin or password are not set.
+ *
+ * @param disable Disables lock screen when true
+ */
+ public void setLockScreenDisabled(boolean disable) {
+ setLong(DISABLE_LOCKSCREEN_KEY, disable ? 1 : 0);
+ }
+
+ /**
+ * Determine if LockScreen can be disabled. This is used, for example, to tell if we should
+ * show LockScreen or go straight to the home screen.
+ *
+ * @return true if lock screen is can be disabled
+ */
+ public boolean isLockScreenDisabled() {
+ return !isSecure() && getLong(DISABLE_LOCKSCREEN_KEY, 0) != 0;
+ }
+
+ /**
* Save a lock pattern.
* @param pattern The new pattern to save.
*/
diff --git a/core/res/AndroidManifest.xml b/core/res/AndroidManifest.xml
index 2de8590..ddc63dd 100644
--- a/core/res/AndroidManifest.xml
+++ b/core/res/AndroidManifest.xml
@@ -60,7 +60,7 @@
<protected-broadcast android:name="android.app.action.EXIT_CAR_MODE" />
<protected-broadcast android:name="android.app.action.ENTER_DESK_MODE" />
<protected-broadcast android:name="android.app.action.EXIT_DESK_MODE" />
-
+
<protected-broadcast android:name="android.backup.intent.RUN" />
<protected-broadcast android:name="android.backup.intent.CLEAR" />
<protected-broadcast android:name="android.backup.intent.INIT" />
@@ -1278,7 +1278,7 @@
android:description="@string/permlab_copyProtectedData"
android:protectionLevel="signature" />
- <!-- C2DM permission.
+ <!-- C2DM permission.
@hide Used internally.
-->
<permission android:name="android.intent.category.MASTER_CLEAR.permission.C2D_MESSAGE"
@@ -1332,7 +1332,6 @@
</activity>
<activity android:name="android.accounts.GrantCredentialsPermissionActivity"
- android:permission="android.permission.ACCOUNT_MANAGER"
android:excludeFromRecents="true"
android:exported="true">
</activity>
diff --git a/policy/src/com/android/internal/policy/impl/KeyguardViewMediator.java b/policy/src/com/android/internal/policy/impl/KeyguardViewMediator.java
index 42b73b9..72af34d 100644
--- a/policy/src/com/android/internal/policy/impl/KeyguardViewMediator.java
+++ b/policy/src/com/android/internal/policy/impl/KeyguardViewMediator.java
@@ -281,7 +281,7 @@
mUpdateMonitor.registerSimStateCallback(this);
mLockPatternUtils = new LockPatternUtils(mContext);
- mKeyguardViewProperties
+ mKeyguardViewProperties
= new LockPatternKeyguardViewProperties(mLockPatternUtils, mUpdateMonitor);
mKeyguardViewManager = new KeyguardViewManager(
@@ -589,6 +589,11 @@
return;
}
+ if (mLockPatternUtils.isLockScreenDisabled()) {
+ if (DEBUG) Log.d(TAG, "doKeyguard: not showing because lockscreen is off");
+ return;
+ }
+
if (DEBUG) Log.d(TAG, "doKeyguard: showing the lock screen");
showLocked();
}
@@ -1005,7 +1010,7 @@
Log.d(TAG, "playSounds: whichSound = " + whichSound + "; soundPath was null");
}
}
- }
+ }
/**
* Handle message sent by {@link #showLocked}.
diff --git a/services/java/com/android/server/BackupManagerService.java b/services/java/com/android/server/BackupManagerService.java
index bebd013..2651fd3 100644
--- a/services/java/com/android/server/BackupManagerService.java
+++ b/services/java/com/android/server/BackupManagerService.java
@@ -198,22 +198,26 @@
public long token;
public PackageInfo pkgInfo;
public int pmToken; // in post-install restore, the PM's token for this transaction
+ public boolean needFullBackup;
RestoreParams(IBackupTransport _transport, IRestoreObserver _obs,
- long _token, PackageInfo _pkg, int _pmToken) {
+ long _token, PackageInfo _pkg, int _pmToken, boolean _needFullBackup) {
transport = _transport;
observer = _obs;
token = _token;
pkgInfo = _pkg;
pmToken = _pmToken;
+ needFullBackup = _needFullBackup;
}
- RestoreParams(IBackupTransport _transport, IRestoreObserver _obs, long _token) {
+ RestoreParams(IBackupTransport _transport, IRestoreObserver _obs, long _token,
+ boolean _needFullBackup) {
transport = _transport;
observer = _obs;
token = _token;
pkgInfo = null;
pmToken = 0;
+ needFullBackup = _needFullBackup;
}
}
@@ -323,7 +327,8 @@
RestoreParams params = (RestoreParams)msg.obj;
Slog.d(TAG, "MSG_RUN_RESTORE observer=" + params.observer);
(new PerformRestoreTask(params.transport, params.observer,
- params.token, params.pkgInfo, params.pmToken)).run();
+ params.token, params.pkgInfo, params.pmToken,
+ params.needFullBackup)).run();
break;
}
@@ -1560,6 +1565,7 @@
private PackageInfo mTargetPackage;
private File mStateDir;
private int mPmToken;
+ private boolean mNeedFullBackup;
class RestoreRequest {
public PackageInfo app;
@@ -1572,12 +1578,14 @@
}
PerformRestoreTask(IBackupTransport transport, IRestoreObserver observer,
- long restoreSetToken, PackageInfo targetPackage, int pmToken) {
+ long restoreSetToken, PackageInfo targetPackage, int pmToken,
+ boolean needFullBackup) {
mTransport = transport;
mObserver = observer;
mToken = restoreSetToken;
mTargetPackage = targetPackage;
mPmToken = pmToken;
+ mNeedFullBackup = needFullBackup;
try {
mStateDir = new File(mBaseStateDir, transport.transportDirName());
@@ -1655,7 +1663,8 @@
// Pull the Package Manager metadata from the restore set first
pmAgent = new PackageManagerBackupAgent(
mPackageManager, agentPackages);
- processOneRestore(omPackage, 0, IBackupAgent.Stub.asInterface(pmAgent.onBind()));
+ processOneRestore(omPackage, 0, IBackupAgent.Stub.asInterface(pmAgent.onBind()),
+ mNeedFullBackup);
// Verify that the backup set includes metadata. If not, we can't do
// signature/version verification etc, so we simply do not proceed with
@@ -1752,7 +1761,8 @@
// And then finally run the restore on this agent
try {
- processOneRestore(packageInfo, metaInfo.versionCode, agent);
+ processOneRestore(packageInfo, metaInfo.versionCode, agent,
+ mNeedFullBackup);
++count;
} finally {
// unbind and tidy up even on timeout or failure, just in case
@@ -1822,7 +1832,8 @@
}
// Do the guts of a restore of one application, using mTransport.getRestoreData().
- void processOneRestore(PackageInfo app, int appVersionCode, IBackupAgent agent) {
+ void processOneRestore(PackageInfo app, int appVersionCode, IBackupAgent agent,
+ boolean needFullBackup) {
// !!! TODO: actually run the restore through mTransport
final String packageName = app.packageName;
@@ -1901,6 +1912,14 @@
try { if (newState != null) newState.close(); } catch (IOException e) {}
backupData = newState = null;
mCurrentOperations.delete(token);
+
+ // If we know a priori that we'll need to perform a full post-restore backup
+ // pass, clear the new state file data. This means we're discarding work that
+ // was just done by the app's agent, but this way the agent doesn't need to
+ // take any special action based on global device state.
+ if (needFullBackup) {
+ newStateName.delete();
+ }
}
}
}
@@ -2386,7 +2405,7 @@
mWakelock.acquire();
Message msg = mBackupHandler.obtainMessage(MSG_RUN_RESTORE);
msg.obj = new RestoreParams(getTransport(mCurrentTransport), null,
- restoreSet, pkg, token);
+ restoreSet, pkg, token, true);
mBackupHandler.sendMessage(msg);
} else {
// Auto-restore disabled or no way to attempt a restore; just tell the Package
@@ -2517,7 +2536,7 @@
long oldId = Binder.clearCallingIdentity();
mWakelock.acquire();
Message msg = mBackupHandler.obtainMessage(MSG_RUN_RESTORE);
- msg.obj = new RestoreParams(mRestoreTransport, observer, token);
+ msg.obj = new RestoreParams(mRestoreTransport, observer, token, true);
mBackupHandler.sendMessage(msg);
Binder.restoreCallingIdentity(oldId);
return 0;
@@ -2582,7 +2601,7 @@
long oldId = Binder.clearCallingIdentity();
mWakelock.acquire();
Message msg = mBackupHandler.obtainMessage(MSG_RUN_RESTORE);
- msg.obj = new RestoreParams(mRestoreTransport, observer, token, app, 0);
+ msg.obj = new RestoreParams(mRestoreTransport, observer, token, app, 0, false);
mBackupHandler.sendMessage(msg);
Binder.restoreCallingIdentity(oldId);
return 0;
diff --git a/tests/DumpRenderTree2/src/com/android/dumprendertree2/FsUtils.java b/tests/DumpRenderTree2/src/com/android/dumprendertree2/FsUtils.java
index a79aead..d1aba437 100644
--- a/tests/DumpRenderTree2/src/com/android/dumprendertree2/FsUtils.java
+++ b/tests/DumpRenderTree2/src/com/android/dumprendertree2/FsUtils.java
@@ -39,9 +39,12 @@
import org.apache.http.util.EntityUtils;
import java.io.BufferedReader;
+import java.io.BufferedWriter;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
+import java.io.FileReader;
+import java.io.FileWriter;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
@@ -49,6 +52,7 @@
import java.net.MalformedURLException;
import java.net.SocketTimeoutException;
import java.net.URL;
+import java.util.ArrayList;
import java.util.LinkedList;
import java.util.List;
@@ -274,4 +278,37 @@
Log.e(LOG_TAG, "Couldn't close stream!", e);
}
}
+
+ public static List<String> loadTestListFromStorage(String path) {
+ List<String> list = new ArrayList<String>();
+ if (path != null && !path.isEmpty()) {
+ try {
+ File file = new File(path);
+ Log.d(LOG_TAG, "test list loaded from " + path);
+ BufferedReader reader = new BufferedReader(new FileReader(file));
+ String line = null;
+ while ((line = reader.readLine()) != null) {
+ list.add(line);
+ }
+ reader.close();
+ } catch (IOException ioe) {
+ Log.e(LOG_TAG, "failed to load test list", ioe);
+ }
+ }
+ return list;
+ }
+
+ public static void saveTestListToStorage(File file, int start, List<String> testList) {
+ try {
+ BufferedWriter writer = new BufferedWriter(
+ new FileWriter(file));
+ for (String line : testList.subList(start, testList.size())) {
+ writer.write(line + '\n');
+ }
+ writer.flush();
+ writer.close();
+ } catch (IOException e) {
+ Log.e(LOG_TAG, "failed to write test list", e);
+ }
+ }
}
diff --git a/tests/DumpRenderTree2/src/com/android/dumprendertree2/LayoutTestsExecutor.java b/tests/DumpRenderTree2/src/com/android/dumprendertree2/LayoutTestsExecutor.java
index 7efb03f..ce546ec 100644
--- a/tests/DumpRenderTree2/src/com/android/dumprendertree2/LayoutTestsExecutor.java
+++ b/tests/DumpRenderTree2/src/com/android/dumprendertree2/LayoutTestsExecutor.java
@@ -21,17 +21,15 @@
import android.content.Context;
import android.content.Intent;
import android.content.ServiceConnection;
-import android.net.Uri;
import android.net.http.SslError;
import android.os.Bundle;
-import android.os.Environment;
import android.os.Handler;
import android.os.IBinder;
import android.os.Message;
import android.os.Messenger;
import android.os.PowerManager;
-import android.os.Process;
import android.os.PowerManager.WakeLock;
+import android.os.Process;
import android.os.RemoteException;
import android.util.Log;
import android.view.Window;
@@ -48,10 +46,7 @@
import android.webkit.WebView;
import android.webkit.WebViewClient;
-import java.io.File;
import java.lang.Thread.UncaughtExceptionHandler;
-import java.net.MalformedURLException;
-import java.net.URL;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
@@ -79,7 +74,7 @@
private static final String LOG_TAG = "LayoutTestsExecutor";
- public static final String EXTRA_TESTS_LIST = "TestsList";
+ public static final String EXTRA_TESTS_FILE = "TestsList";
public static final String EXTRA_TEST_INDEX = "TestIndex";
private static final int MSG_ACTUAL_RESULT_OBTAINED = 0;
@@ -305,7 +300,7 @@
requestWindowFeature(Window.FEATURE_PROGRESS);
Intent intent = getIntent();
- mTestsList = intent.getStringArrayListExtra(EXTRA_TESTS_LIST);
+ mTestsList = FsUtils.loadTestListFromStorage(intent.getStringExtra(EXTRA_TESTS_FILE));
mCurrentTestIndex = intent.getIntExtra(EXTRA_TEST_INDEX, -1);
mTotalTestCount = mCurrentTestIndex + mTestsList.size();
@@ -735,4 +730,5 @@
Log.i(LOG_TAG, mCurrentTestRelativePath + ": waitUntilDone() called");
mLayoutTestControllerHandler.sendEmptyMessage(MSG_WAIT_UNTIL_DONE);
}
+
}
diff --git a/tests/DumpRenderTree2/src/com/android/dumprendertree2/TestsListActivity.java b/tests/DumpRenderTree2/src/com/android/dumprendertree2/TestsListActivity.java
index 9db4d2b..e374c1b 100644
--- a/tests/DumpRenderTree2/src/com/android/dumprendertree2/TestsListActivity.java
+++ b/tests/DumpRenderTree2/src/com/android/dumprendertree2/TestsListActivity.java
@@ -16,6 +16,8 @@
package com.android.dumprendertree2;
+import com.android.dumprendertree2.scriptsupport.OnEverythingFinishedCallback;
+
import android.app.Activity;
import android.app.ProgressDialog;
import android.content.Intent;
@@ -28,8 +30,7 @@
import android.webkit.WebView;
import android.widget.Toast;
-import com.android.dumprendertree2.scriptsupport.OnEverythingFinishedCallback;
-
+import java.io.File;
import java.util.ArrayList;
/**
@@ -189,12 +190,12 @@
intent.setAction(Intent.ACTION_RUN);
if (startFrom < mTotalTestCount) {
- intent.putStringArrayListExtra(LayoutTestsExecutor.EXTRA_TESTS_LIST,
- new ArrayList<String>(mTestsList.subList(startFrom, mTotalTestCount)));
+ File testListFile = new File(getExternalFilesDir(null), "test_list.txt");
+ FsUtils.saveTestListToStorage(testListFile, startFrom, mTestsList);
+ intent.putExtra(LayoutTestsExecutor.EXTRA_TESTS_FILE, testListFile.getAbsolutePath());
intent.putExtra(LayoutTestsExecutor.EXTRA_TEST_INDEX, startFrom);
} else {
- intent.putStringArrayListExtra(LayoutTestsExecutor.EXTRA_TESTS_LIST,
- new ArrayList<String>());
+ intent.putExtra(LayoutTestsExecutor.EXTRA_TESTS_FILE, "");
}
startActivity(intent);