diff options
Diffstat (limited to 'services')
5 files changed, 93 insertions, 63 deletions
diff --git a/services/audioflinger/AudioFlinger.cpp b/services/audioflinger/AudioFlinger.cpp index 060a632..133dabd 100644 --- a/services/audioflinger/AudioFlinger.cpp +++ b/services/audioflinger/AudioFlinger.cpp @@ -1832,7 +1832,7 @@ uint32_t AudioFlinger::PlaybackThread::activeSleepTimeUs() AudioFlinger::MixerThread::MixerThread(const sp<AudioFlinger>& audioFlinger, AudioStreamOut* output, int id, uint32_t device) : PlaybackThread(audioFlinger, output, id, device), - mAudioMixer(0) + mAudioMixer(0), mPrevMixerStatus(MIXER_IDLE) { mType = ThreadBase::MIXER; mAudioMixer = new AudioMixer(mFrameCount, mSampleRate); @@ -1945,6 +1945,7 @@ bool AudioFlinger::MixerThread::threadLoop() LOGV("MixerThread %p TID %d waking up\n", this, gettid()); acquireWakeLock_l(); + mPrevMixerStatus = MIXER_IDLE; if (mMasterMute == false) { char value[PROPERTY_VALUE_MAX]; property_get("ro.audio.silent", value, "0"); @@ -2103,11 +2104,11 @@ uint32_t AudioFlinger::MixerThread::prepareTracks_l(const SortedVector< wp<Track // make sure that we have enough frames to mix one full buffer. // enforce this condition only once to enable draining the buffer in case the client // app does not call stop() and relies on underrun to stop: - // hence the test on (track->mRetryCount >= kMaxTrackRetries) meaning the track was mixed + // hence the test on (mPrevMixerStatus == MIXER_TRACKS_READY) meaning the track was mixed // during last round uint32_t minFrames = 1; if (!track->isStopped() && !track->isPausing() && - (track->mRetryCount >= kMaxTrackRetries)) { + (mPrevMixerStatus == MIXER_TRACKS_READY)) { if (t->sampleRate() == (int)mSampleRate) { minFrames = mFrameCount; } else { @@ -2229,7 +2230,13 @@ uint32_t AudioFlinger::MixerThread::prepareTracks_l(const SortedVector< wp<Track // reset retry count track->mRetryCount = kMaxTrackRetries; - mixerStatus = MIXER_TRACKS_READY; + // If one track is ready, set the mixer ready if: + // - the mixer was not ready during previous round OR + // - no other track is not ready + if (mPrevMixerStatus != MIXER_TRACKS_READY || + mixerStatus != MIXER_TRACKS_ENABLED) { + mixerStatus = MIXER_TRACKS_READY; + } } else { //LOGV("track %d u=%08x, s=%08x [NOT READY] on thread %p", track->name(), cblk->user, cblk->server, this); if (track->isStopped()) { @@ -2247,7 +2254,11 @@ uint32_t AudioFlinger::MixerThread::prepareTracks_l(const SortedVector< wp<Track tracksToRemove->add(track); // indicate to client process that the track was disabled because of underrun android_atomic_or(CBLK_DISABLED_ON, &cblk->flags); - } else if (mixerStatus != MIXER_TRACKS_READY) { + // If one track is not ready, mark the mixer also not ready if: + // - the mixer was ready during previous round OR + // - no other track is ready + } else if (mPrevMixerStatus == MIXER_TRACKS_READY || + mixerStatus != MIXER_TRACKS_READY) { mixerStatus = MIXER_TRACKS_ENABLED; } } @@ -2281,6 +2292,7 @@ uint32_t AudioFlinger::MixerThread::prepareTracks_l(const SortedVector< wp<Track memset(mMixBuffer, 0, mFrameCount * mChannelCount * sizeof(int16_t)); } + mPrevMixerStatus = mixerStatus; return mixerStatus; } @@ -3016,6 +3028,7 @@ bool AudioFlinger::DuplicatingThread::threadLoop() LOGV("DuplicatingThread %p TID %d waking up\n", this, gettid()); acquireWakeLock_l(); + mPrevMixerStatus = MIXER_IDLE; if (mMasterMute == false) { char value[PROPERTY_VALUE_MAX]; property_get("ro.audio.silent", value, "0"); diff --git a/services/audioflinger/AudioFlinger.h b/services/audioflinger/AudioFlinger.h index 6cafa7e..9bd2c7f 100644 --- a/services/audioflinger/AudioFlinger.h +++ b/services/audioflinger/AudioFlinger.h @@ -836,7 +836,9 @@ private: virtual uint32_t idleSleepTimeUs(); virtual uint32_t suspendSleepTimeUs(); - AudioMixer* mAudioMixer; + AudioMixer* mAudioMixer; + uint32_t mPrevMixerStatus; // previous status (mixer_state) returned by + // prepareTracks_l() }; class DirectOutputThread : public PlaybackThread { diff --git a/services/java/com/android/server/BackupManagerService.java b/services/java/com/android/server/BackupManagerService.java index 4ef8837..4d5e0a6 100644 --- a/services/java/com/android/server/BackupManagerService.java +++ b/services/java/com/android/server/BackupManagerService.java @@ -195,7 +195,7 @@ class BackupManagerService extends IBackupManager.Stub { boolean mProvisioned; boolean mAutoRestore; PowerManager.WakeLock mWakelock; - HandlerThread mHandlerThread = new HandlerThread("backup", Process.THREAD_PRIORITY_BACKGROUND); + HandlerThread mHandlerThread; BackupHandler mBackupHandler; PendingIntent mRunBackupIntent, mRunInitIntent; BroadcastReceiver mRunBackupReceiver, mRunInitReceiver; @@ -1310,14 +1310,10 @@ class BackupManagerService extends IBackupManager.Stub { } if (added) { synchronized (mBackupParticipants) { - for (String pkgName : pkgList) { - if (replacing) { - // The package was just upgraded - updatePackageParticipantsLocked(pkgName); - } else { - // The package was just added - addPackageParticipantsLocked(pkgName); - } + if (replacing) { + updatePackageParticipantsLocked(pkgList); + } else { + addPackageParticipantsLocked(pkgList); } } } else { @@ -1325,9 +1321,7 @@ class BackupManagerService extends IBackupManager.Stub { // The package is being updated. We'll receive a PACKAGE_ADDED shortly. } else { synchronized (mBackupParticipants) { - for (String pkgName : pkgList) { - removePackageParticipantsLocked(pkgName); - } + removePackageParticipantsLocked(pkgList); } } } @@ -1349,26 +1343,26 @@ class BackupManagerService extends IBackupManager.Stub { } }; - // Add the backup agents in the given package to our set of known backup participants. - // If 'packageName' is null, adds all backup agents in the whole system. - void addPackageParticipantsLocked(String packageName) { + // Add the backup agents in the given packages to our set of known backup participants. + // If 'packageNames' is null, adds all backup agents in the whole system. + void addPackageParticipantsLocked(String[] packageNames) { // Look for apps that define the android:backupAgent attribute - if (DEBUG) Slog.v(TAG, "addPackageParticipantsLocked: " + packageName); List<PackageInfo> targetApps = allAgentPackages(); - addPackageParticipantsLockedInner(packageName, targetApps); + if (packageNames != null) { + if (DEBUG) Slog.v(TAG, "addPackageParticipantsLocked: #" + packageNames.length); + for (String packageName : packageNames) { + addPackageParticipantsLockedInner(packageName, targetApps); + } + } else { + if (DEBUG) Slog.v(TAG, "addPackageParticipantsLocked: all"); + addPackageParticipantsLockedInner(null, targetApps); + } } private void addPackageParticipantsLockedInner(String packageName, List<PackageInfo> targetPkgs) { if (MORE_DEBUG) { - Slog.v(TAG, "Adding " + targetPkgs.size() + " backup participants:"); - for (PackageInfo p : targetPkgs) { - Slog.v(TAG, " " + p + " agent=" + p.applicationInfo.backupAgentName - + " uid=" + p.applicationInfo.uid - + " killAfterRestore=" - + (((p.applicationInfo.flags & ApplicationInfo.FLAG_KILL_AFTER_RESTORE) != 0) ? "true" : "false") - ); - } + Slog.v(TAG, "Examining " + packageName + " for backup agent"); } for (PackageInfo pkg : targetPkgs) { @@ -1380,6 +1374,7 @@ class BackupManagerService extends IBackupManager.Stub { mBackupParticipants.put(uid, set); } set.add(pkg.applicationInfo); + if (MORE_DEBUG) Slog.v(TAG, "Agent found; added"); // If we've never seen this app before, schedule a backup for it if (!mEverStoredApps.contains(pkg.packageName)) { @@ -1391,34 +1386,32 @@ class BackupManagerService extends IBackupManager.Stub { } } - // Remove the given package's entry from our known active set. If - // 'packageName' is null, *all* participating apps will be removed. - void removePackageParticipantsLocked(String packageName) { - if (DEBUG) Slog.v(TAG, "removePackageParticipantsLocked: " + packageName); - List<String> allApps = new ArrayList<String>(); - if (packageName != null) { - allApps.add(packageName); - } else { - // all apps with agents - List<PackageInfo> knownPackages = allAgentPackages(); - for (PackageInfo pkg : knownPackages) { - allApps.add(pkg.packageName); - } + // Remove the given packages' entries from our known active set. + void removePackageParticipantsLocked(String[] packageNames) { + if (packageNames == null) { + Slog.w(TAG, "removePackageParticipants with null list"); + return; + } + + if (DEBUG) Slog.v(TAG, "removePackageParticipantsLocked: #" + packageNames.length); + List<PackageInfo> knownPackages = allAgentPackages(); + for (String pkg : packageNames) { + removePackageParticipantsLockedInner(pkg, knownPackages); } - removePackageParticipantsLockedInner(packageName, allApps); } private void removePackageParticipantsLockedInner(String packageName, - List<String> allPackageNames) { + List<PackageInfo> allPackages) { if (MORE_DEBUG) { Slog.v(TAG, "removePackageParticipantsLockedInner (" + packageName - + ") removing " + allPackageNames.size() + " entries"); - for (String p : allPackageNames) { - Slog.v(TAG, " - " + p); + + ") removing from " + allPackages.size() + " entries"); + for (PackageInfo p : allPackages) { + Slog.v(TAG, " - " + p.packageName); } } - for (String pkg : allPackageNames) { - if (packageName == null || pkg.equals(packageName)) { + for (PackageInfo pkg : allPackages) { + if (packageName == null || pkg.packageName.equals(packageName)) { + /* int uid = -1; try { PackageInfo info = mPackageManager.getPackageInfo(packageName, 0); @@ -1427,22 +1420,28 @@ class BackupManagerService extends IBackupManager.Stub { // we don't know this package name, so just skip it for now continue; } + */ + final int uid = pkg.applicationInfo.uid; + if (MORE_DEBUG) Slog.i(TAG, " found pkg " + packageName + " uid=" + uid); HashSet<ApplicationInfo> set = mBackupParticipants.get(uid); if (set != null) { // Find the existing entry with the same package name, and remove it. // We can't just remove(app) because the instances are different. for (ApplicationInfo entry: set) { + if (MORE_DEBUG) Slog.i(TAG, " checking against " + entry.packageName); if (entry.packageName.equals(pkg)) { if (MORE_DEBUG) Slog.v(TAG, " removing participant " + pkg); set.remove(entry); - removeEverBackedUp(pkg); + removeEverBackedUp(pkg.packageName); break; } } if (set.size() == 0) { mBackupParticipants.delete(uid); } + } else { + if (MORE_DEBUG) Slog.i(TAG, " ... not found in uid mapping"); } } } @@ -1477,21 +1476,20 @@ class BackupManagerService extends IBackupManager.Stub { // Reset the given package's known backup participants. Unlike add/remove, the update // action cannot be passed a null package name. - void updatePackageParticipantsLocked(String packageName) { - if (packageName == null) { - Slog.e(TAG, "updatePackageParticipants called with null package name"); + void updatePackageParticipantsLocked(String[] packageNames) { + if (packageNames == null) { + Slog.e(TAG, "updatePackageParticipants called with null package list"); return; } - if (DEBUG) Slog.v(TAG, "updatePackageParticipantsLocked: " + packageName); + if (DEBUG) Slog.v(TAG, "updatePackageParticipantsLocked: #" + packageNames.length); - // brute force but small code size - List<PackageInfo> allApps = allAgentPackages(); - List<String> allAppNames = new ArrayList<String>(); - for (PackageInfo pkg : allApps) { - allAppNames.add(pkg.packageName); + if (packageNames.length > 0) { + List<PackageInfo> allApps = allAgentPackages(); + for (String packageName : packageNames) { + removePackageParticipantsLockedInner(packageName, allApps); + addPackageParticipantsLockedInner(packageName, allApps); + } } - removePackageParticipantsLockedInner(packageName, allAppNames); - addPackageParticipantsLockedInner(packageName, allApps); } // Called from the backup task: record that the given app has been successfully diff --git a/services/java/com/android/server/DevicePolicyManagerService.java b/services/java/com/android/server/DevicePolicyManagerService.java index e8ca3ce..d8e3d59 100644 --- a/services/java/com/android/server/DevicePolicyManagerService.java +++ b/services/java/com/android/server/DevicePolicyManagerService.java @@ -60,6 +60,7 @@ import android.util.PrintWriterPrinter; import android.util.Printer; import android.util.Slog; import android.util.Xml; +import android.view.IWindowManager; import android.view.WindowManagerPolicy; import java.io.File; @@ -96,6 +97,7 @@ public class DevicePolicyManagerService extends IDevicePolicyManager.Stub { final PowerManager.WakeLock mWakeLock; IPowerManager mIPowerManager; + IWindowManager mIWindowManager; int mActivePasswordQuality = DevicePolicyManager.PASSWORD_QUALITY_UNSPECIFIED; int mActivePasswordLength = 0; @@ -506,6 +508,14 @@ public class DevicePolicyManagerService extends IDevicePolicyManager.Stub { return mIPowerManager; } + private IWindowManager getWindowManager() { + if (mIWindowManager == null) { + IBinder b = ServiceManager.getService(Context.WINDOW_SERVICE); + mIWindowManager = IWindowManager.Stub.asInterface(b); + } + return mIWindowManager; + } + ActiveAdmin getActiveAdminUncheckedLocked(ComponentName who) { ActiveAdmin admin = mAdminMap.get(who); if (admin != null @@ -1649,8 +1659,11 @@ public class DevicePolicyManagerService extends IDevicePolicyManager.Stub { DeviceAdminInfo.USES_POLICY_FORCE_LOCK); long ident = Binder.clearCallingIdentity(); try { + // Power off the display mIPowerManager.goToSleepWithReason(SystemClock.uptimeMillis(), WindowManagerPolicy.OFF_BECAUSE_OF_ADMIN); + // Ensure the device is locked + getWindowManager().lockNow(); } catch (RemoteException e) { } finally { Binder.restoreCallingIdentity(ident); diff --git a/services/java/com/android/server/wm/WindowManagerService.java b/services/java/com/android/server/wm/WindowManagerService.java index f5c2de9..9fb064f 100644 --- a/services/java/com/android/server/wm/WindowManagerService.java +++ b/services/java/com/android/server/wm/WindowManagerService.java @@ -9411,6 +9411,10 @@ public class WindowManagerService extends IWindowManager.Stub return mPolicy.hasNavigationBar(); } + public void lockNow() { + mPolicy.lockNow(); + } + void dumpInput(FileDescriptor fd, PrintWriter pw, boolean dumpAll) { pw.println("WINDOW MANAGER INPUT (dumpsys window input)"); mInputManager.dump(pw); |