diff --git a/app/src/main/java/org/thoughtcrime/securesms/dependencies/ApplicationDependencyProvider.java b/app/src/main/java/org/thoughtcrime/securesms/dependencies/ApplicationDependencyProvider.java index 5c37dead97..79e3304c42 100644 --- a/app/src/main/java/org/thoughtcrime/securesms/dependencies/ApplicationDependencyProvider.java +++ b/app/src/main/java/org/thoughtcrime/securesms/dependencies/ApplicationDependencyProvider.java @@ -275,7 +275,7 @@ public class ApplicationDependencyProvider implements AppDependencies.Provider { public @NonNull Network provideLibsignalNetwork(@NonNull SignalServiceConfiguration config) { Network network = new Network(BuildConfig.LIBSIGNAL_NET_ENV, StandardUserAgentInterceptor.USER_AGENT); LibSignalNetworkExtensions.applyConfiguration(network, config); - LibSignalNetworkExtensions.buildAndSetRemoteConfig(network, RemoteConfig.libsignalEnforceMinTlsVersion()); + network.setRemoteConfig(RemoteConfig.getLibsignalConfigs()); return network; } diff --git a/app/src/main/java/org/thoughtcrime/securesms/util/RemoteConfig.kt b/app/src/main/java/org/thoughtcrime/securesms/util/RemoteConfig.kt index d4fd4d7753..e9f58ac8c8 100644 --- a/app/src/main/java/org/thoughtcrime/securesms/util/RemoteConfig.kt +++ b/app/src/main/java/org/thoughtcrime/securesms/util/RemoteConfig.kt @@ -60,6 +60,20 @@ object RemoteConfig { @VisibleForTesting val configsByKey: MutableMap> = mutableMapOf() + @JvmStatic + val libsignalConfigs: Map + get() { + if (!initialized) { + Log.w(TAG, "Tried to read libsignalConfigs before initialization. Initializing now.") + initLock.withLock { + if (!initialized) { + init() + } + } + } + return computeLibsignalConfigs(REMOTE_VALUES) + } + @GuardedBy("initLock") @Volatile @VisibleForTesting @@ -161,7 +175,7 @@ object RemoteConfig { val allKeys: Set = remote.keys + localDisk.keys + localMemory.keys allKeys - .filter { remoteCapable.contains(it) } + .filter { remoteCapable.contains(it) || it.startsWith("android.libsignal.") } .forEach { key: String -> val remoteValue = remote[key] val diskValue = localDisk[key] @@ -200,8 +214,14 @@ object RemoteConfig { } } + // Libsignal does not support sticky flags and is okay with any flag that is not known to the server being + // forgotten about. + val libsignalConfigsKnownToServer = remote.keys.filter { it.startsWith("android.libsignal.") }.toSet() + allKeys - .filterNot { remoteCapable.contains(it) } + .filterNot { key -> + remoteCapable.contains(key) || libsignalConfigsKnownToServer.contains(key) + } .filterNot { key -> sticky.contains(key) && localDisk[key] == java.lang.Boolean.TRUE } .forEach { key: String -> newDisk.remove(key) @@ -276,6 +296,28 @@ object RemoteConfig { } } + private fun computeLibsignalConfigs(config: Map): Map { + return config + .filterKeys { it.startsWith("android.libsignal.") } + .mapNotNull { (key, value) -> + val newKey = key.removePrefix("android.libsignal.") + when (value) { + is String -> newKey to value + // The server is currently synthesizing "true" / "false" values + // for RemoteConfigs that are otherwise empty string values. + // Libsignal expects that disabled values are simply absent from the + // map, so we map true to "true" and otherwise omit disabled values. + is Boolean -> if (value) newKey to "true" else null + else -> { + val type = value?.let { value::class.simpleName } + Log.w(TAG, "[libsignal] Unexpected type for $newKey! Was a $type") + newKey to value.toString() + } + } + } + .toMap() + } + @VisibleForTesting class UpdateResult( val memory: Map, diff --git a/app/src/test/java/org/thoughtcrime/securesms/util/RemoteConfig_StaticValuesTest.kt b/app/src/test/java/org/thoughtcrime/securesms/util/RemoteConfig_StaticValuesTest.kt index ce88a0c540..73a197cd7c 100644 --- a/app/src/test/java/org/thoughtcrime/securesms/util/RemoteConfig_StaticValuesTest.kt +++ b/app/src/test/java/org/thoughtcrime/securesms/util/RemoteConfig_StaticValuesTest.kt @@ -46,6 +46,7 @@ class RemoteConfig_StaticValuesTest { "debugMemoryValues", "debugDiskValues", "debugPendingDiskValues", + "libsignalConfigs", "CRASH_PROMPT_CONFIG", "PROMPT_BATTERY_SAVER", "PROMPT_FOR_NOTIFICATION_LOGS", diff --git a/libsignal-service/src/main/java/org/whispersystems/signalservice/internal/websocket/LibSignalNetworkExtensions.kt b/libsignal-service/src/main/java/org/whispersystems/signalservice/internal/websocket/LibSignalNetworkExtensions.kt index fffb973ca3..743a6d8cae 100644 --- a/libsignal-service/src/main/java/org/whispersystems/signalservice/internal/websocket/LibSignalNetworkExtensions.kt +++ b/libsignal-service/src/main/java/org/whispersystems/signalservice/internal/websocket/LibSignalNetworkExtensions.kt @@ -14,14 +14,6 @@ import java.io.IOException private const val TAG = "LibSignalNetworkExtensions" -fun Network.buildAndSetRemoteConfig(enforceMinTls: Boolean) { - val libsignalRemoteConfig: HashMap = HashMap() - if (enforceMinTls) { - libsignalRemoteConfig["enforceMinimumTls"] = "" - } - this.setRemoteConfig(libsignalRemoteConfig) -} - /** * Helper method to apply settings from the SignalServiceConfiguration. */