summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--packages/SettingsProvider/src/com/android/providers/settings/SettingsState.java2
-rw-r--r--services/core/java/com/android/server/audio/AdiDeviceState.java5
-rw-r--r--services/core/java/com/android/server/audio/AudioDeviceBroker.java14
-rw-r--r--services/core/java/com/android/server/audio/AudioDeviceInventory.java31
4 files changed, 41 insertions, 11 deletions
diff --git a/packages/SettingsProvider/src/com/android/providers/settings/SettingsState.java b/packages/SettingsProvider/src/com/android/providers/settings/SettingsState.java
index 7cec99d4189f..8f459c647316 100644
--- a/packages/SettingsProvider/src/com/android/providers/settings/SettingsState.java
+++ b/packages/SettingsProvider/src/com/android/providers/settings/SettingsState.java
@@ -95,7 +95,9 @@ final class SettingsState {
static final int SETTINGS_VERSION_NEW_ENCODING = 121;
+ // LINT.IfChange
public static final int MAX_LENGTH_PER_STRING = 32768;
+ // LINT.ThenChange(/services/core/java/com/android/server/audio/AudioDeviceInventory.java:settings_max_length_per_string)
private static final long WRITE_SETTINGS_DELAY_MILLIS = 200;
private static final long MAX_WRITE_SETTINGS_DELAY_MILLIS = 2000;
diff --git a/services/core/java/com/android/server/audio/AdiDeviceState.java b/services/core/java/com/android/server/audio/AdiDeviceState.java
index ffdab7dfbfa4..9ae43a03515a 100644
--- a/services/core/java/com/android/server/audio/AdiDeviceState.java
+++ b/services/core/java/com/android/server/audio/AdiDeviceState.java
@@ -235,9 +235,10 @@ public final class AdiDeviceState {
* {@link AdiDeviceState#toPersistableString()}.
*/
public static int getPeristedMaxSize() {
- return 36; /* (mDeviceType)2 + (mDeviceAddress)17 + (mInternalDeviceType)9 + (mSAEnabled)1
+ return 39; /* (mDeviceType)2 + (mDeviceAddress)17 + (mInternalDeviceType)9 + (mSAEnabled)1
+ (mHasHeadTracker)1 + (mHasHeadTrackerEnabled)1
- + (SETTINGS_FIELD_SEPARATOR)5 */
+ + (mAudioDeviceCategory)1 + (SETTINGS_FIELD_SEPARATOR)6
+ + (SETTING_DEVICE_SEPARATOR)1 */
}
@Nullable
diff --git a/services/core/java/com/android/server/audio/AudioDeviceBroker.java b/services/core/java/com/android/server/audio/AudioDeviceBroker.java
index 9cf15184027b..80917533cce1 100644
--- a/services/core/java/com/android/server/audio/AudioDeviceBroker.java
+++ b/services/core/java/com/android/server/audio/AudioDeviceBroker.java
@@ -2686,11 +2686,15 @@ public class AudioDeviceBroker {
return;
}
final SettingsAdapter settingsAdapter = mAudioService.getSettings();
- boolean res = settingsAdapter.putSecureStringForUser(mAudioService.getContentResolver(),
- Settings.Secure.AUDIO_DEVICE_INVENTORY,
- deviceSettings, UserHandle.USER_CURRENT);
- if (!res) {
- Log.e(TAG, "error saving AdiDeviceState: " + deviceSettings);
+ try {
+ boolean res = settingsAdapter.putSecureStringForUser(mAudioService.getContentResolver(),
+ Settings.Secure.AUDIO_DEVICE_INVENTORY,
+ deviceSettings, UserHandle.USER_CURRENT);
+ if (!res) {
+ Log.e(TAG, "error saving AdiDeviceState: " + deviceSettings);
+ }
+ } catch (IllegalArgumentException e) {
+ Log.e(TAG, "error saving AdiDeviceState: " + deviceSettings, e);
}
}
diff --git a/services/core/java/com/android/server/audio/AudioDeviceInventory.java b/services/core/java/com/android/server/audio/AudioDeviceInventory.java
index d077ebc9c86c..34cfdfaa7974 100644
--- a/services/core/java/com/android/server/audio/AudioDeviceInventory.java
+++ b/services/core/java/com/android/server/audio/AudioDeviceInventory.java
@@ -30,7 +30,6 @@ import static android.media.AudioSystem.isBluetoothOutDevice;
import static android.media.AudioSystem.isBluetoothScoOutDevice;
import static android.media.audio.Flags.automaticBtDeviceType;
-
import static com.android.internal.annotations.VisibleForTesting.Visibility.PACKAGE;
import android.annotation.NonNull;
@@ -81,7 +80,6 @@ import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
-import java.util.HashMap;
import java.util.HashSet;
import java.util.Iterator;
import java.util.LinkedHashMap;
@@ -104,6 +102,14 @@ public class AudioDeviceInventory {
private static final String SETTING_DEVICE_SEPARATOR_CHAR = "|";
private static final String SETTING_DEVICE_SEPARATOR = "\\|";
+ /** Max String length that can be persisted within the Settings. */
+ // LINT.IfChange(settings_max_length_per_string)
+ private static final int MAX_SETTINGS_LENGTH_PER_STRING = 32768;
+ // LINT.ThenChange(/packages/SettingsProvider/src/com/android/providers/settings/SettingsState.java)
+
+ private static final int MAX_DEVICE_INVENTORY_ENTRIES =
+ MAX_SETTINGS_LENGTH_PER_STRING / AdiDeviceState.getPeristedMaxSize();
+
// lock to synchronize all access to mConnectedDevices and mApmConnectedDevices
private final Object mDevicesLock = new Object();
@@ -113,7 +119,8 @@ public class AudioDeviceInventory {
private final Object mDeviceInventoryLock = new Object();
@GuardedBy("mDeviceInventoryLock")
- private final HashMap<Pair<Integer, String>, AdiDeviceState> mDeviceInventory = new HashMap<>();
+ private final LinkedHashMap<Pair<Integer, String>, AdiDeviceState> mDeviceInventory =
+ new LinkedHashMap<>();
Collection<AdiDeviceState> getImmutableDeviceInventory() {
final List<AdiDeviceState> newList;
@@ -136,6 +143,7 @@ public class AudioDeviceInventory {
oldState.setSAEnabled(newState.isSAEnabled());
return oldState;
});
+ checkDeviceInventorySize_l();
}
mDeviceBroker.postSynchronizeAdiDevicesInInventory(deviceState);
}
@@ -173,6 +181,8 @@ public class AudioDeviceInventory {
ads.setAudioDeviceCategory(category);
mDeviceInventory.put(ads.getDeviceId(), ads);
+ checkDeviceInventorySize_l();
+
mDeviceBroker.postUpdatedAdiDeviceState(ads);
mDeviceBroker.postPersistAudioDeviceSettings();
}
@@ -200,6 +210,7 @@ public class AudioDeviceInventory {
}
return oldState;
});
+ checkDeviceInventorySize_l();
}
if (updatedCategory.get()) {
mDeviceBroker.postUpdatedAdiDeviceState(deviceState);
@@ -272,6 +283,18 @@ public class AudioDeviceInventory {
}
}
+ @GuardedBy("mDeviceInventoryLock")
+ private void checkDeviceInventorySize_l() {
+ if (mDeviceInventory.size() > MAX_DEVICE_INVENTORY_ENTRIES) {
+ // remove the first element
+ Iterator<Entry<Pair<Integer, String>, AdiDeviceState>> iterator =
+ mDeviceInventory.entrySet().iterator();
+ if (iterator.hasNext()) {
+ iterator.remove();
+ }
+ }
+ }
+
@GuardedBy({"mDevicesLock", "mDeviceInventoryLock"})
private boolean synchronizeBleDeviceInInventory(AdiDeviceState updatedDevice) {
for (DeviceInfo di : mConnectedDevices.values()) {
@@ -2806,7 +2829,7 @@ public class AudioDeviceInventory {
deviceCatalogSize = mDeviceInventory.size();
final StringBuilder settingsBuilder = new StringBuilder(
- deviceCatalogSize * AdiDeviceState.getPeristedMaxSize());
+ deviceCatalogSize * AdiDeviceState.getPeristedMaxSize());
Iterator<AdiDeviceState> iterator = mDeviceInventory.values().iterator();
if (iterator.hasNext()) {