DND related restrictions

- Apps without dnd access cannot call adjuststeamvolume if that will
change the ringer mode
- DND muted streams cannot be unmuted when DND total silence is enabled.

Bug: 27624414
Bug: 25395278
Change-Id: Id10988c42fc6cb6407aa2abcf66cc5c384fe533a
This commit is contained in:
Julia Reynolds
2016-04-08 15:27:35 -04:00
parent dfe0b4df7e
commit ed783798c3

View File

@@ -1290,7 +1290,7 @@ public class AudioService extends IAudioService.Stub {
// Check if the ringer mode handles this adjustment. If it does we don't
// need to adjust the volume further.
final int result = checkForRingerModeChange(aliasIndex, direction, step,
streamState.mIsMuted);
streamState.mIsMuted, callingPackage, flags);
adjustVolume = (result & FLAG_ADJUST_VOLUME) != 0;
// If suppressing a volume adjustment in silent mode, display the UI hint
if ((result & AudioManager.FLAG_SHOW_SILENT_HINT) != 0) {
@@ -1302,8 +1302,7 @@ public class AudioService extends IAudioService.Stub {
}
}
// If the ringermode is suppressing media, prevent changes
if (streamTypeAlias == AudioSystem.STREAM_MUSIC
&& (mRingerModeMutedStreams & (1 << AudioSystem.STREAM_MUSIC)) != 0) {
if (!volumeAdjustmentAllowedByDnd(streamTypeAlias, flags)) {
adjustVolume = false;
}
int oldIndex = mStreamStates[streamType].getIndex(device);
@@ -1551,6 +1550,10 @@ public class AudioService extends IAudioService.Stub {
throw new SecurityException("Not allowed to change Do Not Disturb state");
}
if (!volumeAdjustmentAllowedByDnd(streamTypeAlias, flags)) {
return;
}
synchronized (mSafeMediaVolumeState) {
// reset any pending volume command
mPendingVolumeCommand = null;
@@ -1601,6 +1604,19 @@ public class AudioService extends IAudioService.Stub {
sendVolumeUpdate(streamType, oldIndex, index, flags);
}
// No ringer affected streams can be changed in total silence mode except those that
// will cause the device to exit total silence mode.
private boolean volumeAdjustmentAllowedByDnd(int streamTypeAlias, int flags) {
if (mNm.getZenMode() == Settings.Global.ZEN_MODE_NO_INTERRUPTIONS
&& isStreamMutedByRingerMode(streamTypeAlias)) {
if (!(((flags & AudioManager.FLAG_ALLOW_RINGER_MODES) != 0) ||
(streamTypeAlias == getUiSoundsStreamType()))) {
return false;
}
}
return true;
}
/** @see AudioManager#forceVolumeControlStream(int) */
public void forceVolumeControlStream(int streamType, IBinder cb) {
synchronized(mForceControlStreamLock) {
@@ -3366,7 +3382,8 @@ public class AudioService extends IAudioService.Stub {
* adjusting volume. If so, this will set the proper ringer mode and volume
* indices on the stream states.
*/
private int checkForRingerModeChange(int oldIndex, int direction, int step, boolean isMuted) {
private int checkForRingerModeChange(int oldIndex, int direction, int step, boolean isMuted,
String caller, int flags) {
final boolean isTv = mPlatformType == AudioSystem.PLATFORM_TELEVISION;
int result = FLAG_ADJUST_VOLUME;
int ringerMode = getRingerModeInternal();
@@ -3455,6 +3472,12 @@ public class AudioService extends IAudioService.Stub {
break;
}
if (isAndroidNPlus(caller) && wouldToggleZenMode(ringerMode)
&& !mNm.isNotificationPolicyAccessGrantedForPackage(caller)
&& (flags & AudioManager.FLAG_FROM_KEY) == 0) {
throw new SecurityException("Not allowed to change Do Not Disturb state");
}
setRingerMode(ringerMode, TAG + ".checkForRingerModeChange", false /*external*/);
mPrevVolDirection = direction;