From a27460b58a64665c74116fba44465ccad9c62c81 Mon Sep 17 00:00:00 2001 From: Mygod Date: Fri, 3 Jul 2020 13:00:43 +0800 Subject: [PATCH] Support TetherTimeoutMonitor.setEnabled properly --- .../vpnhotspot/manage/TetheringFragment.kt | 16 ++++++++++++++-- .../vpnhotspot/net/TetherOffloadManager.kt | 16 +--------------- .../net/monitor/TetherTimeoutMonitor.kt | 12 +++++------- .../vpnhotspot/net/wifi/WifiApDialogFragment.kt | 7 +++++-- .../be/mygod/vpnhotspot/root/MiscCommands.kt | 17 +++++++++++++++++ 5 files changed, 42 insertions(+), 26 deletions(-) diff --git a/mobile/src/main/java/be/mygod/vpnhotspot/manage/TetheringFragment.kt b/mobile/src/main/java/be/mygod/vpnhotspot/manage/TetheringFragment.kt index 10b6e0c3..95867425 100644 --- a/mobile/src/main/java/be/mygod/vpnhotspot/manage/TetheringFragment.kt +++ b/mobile/src/main/java/be/mygod/vpnhotspot/manage/TetheringFragment.kt @@ -1,3 +1,5 @@ +@file:Suppress("DEPRECATION") + package be.mygod.vpnhotspot.manage import android.Manifest @@ -27,6 +29,7 @@ import be.mygod.vpnhotspot.net.TetherType import be.mygod.vpnhotspot.net.TetheringManager import be.mygod.vpnhotspot.net.TetheringManager.localOnlyTetheredIfaces import be.mygod.vpnhotspot.net.TetheringManager.tetheredIfaces +import be.mygod.vpnhotspot.net.monitor.TetherTimeoutMonitor import be.mygod.vpnhotspot.net.wifi.WifiApDialogFragment import be.mygod.vpnhotspot.net.wifi.WifiApManager import be.mygod.vpnhotspot.root.RootManager @@ -214,11 +217,20 @@ class TetheringFragment : Fragment(), ServiceConnection, Toolbar.OnMenuItemClick override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View? { AlertDialogFragment.setResultListener(this) { which, ret -> if (which == DialogInterface.BUTTON_POSITIVE) viewLifecycleOwner.lifecycleScope.launchWhenCreated { + val configuration = ret!!.configuration + @Suppress("DEPRECATION") + if (Build.VERSION.SDK_INT in 28 until 30 && + configuration.isAutoShutdownEnabled != TetherTimeoutMonitor.enabled) try { + TetherTimeoutMonitor.setEnabled(configuration.isAutoShutdownEnabled) + } catch (e: Exception) { + Timber.w(e) + SmartSnackbar.make(e).show() + } val success = try { - WifiApManager.setConfiguration(ret!!.configuration) + WifiApManager.setConfiguration(configuration) } catch (e: InvocationTargetException) { try { - RootManager.use { it.execute(WifiApCommands.SetConfiguration(ret!!.configuration)) } + RootManager.use { it.execute(WifiApCommands.SetConfiguration(configuration)) } } catch (_: CancellationException) { } catch (eRoot: Exception) { eRoot.addSuppressed(e) diff --git a/mobile/src/main/java/be/mygod/vpnhotspot/net/TetherOffloadManager.kt b/mobile/src/main/java/be/mygod/vpnhotspot/net/TetherOffloadManager.kt index ab8337ea..b3aa399a 100644 --- a/mobile/src/main/java/be/mygod/vpnhotspot/net/TetherOffloadManager.kt +++ b/mobile/src/main/java/be/mygod/vpnhotspot/net/TetherOffloadManager.kt @@ -3,9 +3,7 @@ package be.mygod.vpnhotspot.net import android.provider.Settings import androidx.annotation.RequiresApi import be.mygod.vpnhotspot.App.Companion.app -import be.mygod.vpnhotspot.root.RootManager import be.mygod.vpnhotspot.root.SettingsGlobalPut -import be.mygod.vpnhotspot.util.Services /** * It's hard to change tethering rules with Tethering hardware acceleration enabled for now. @@ -19,17 +17,5 @@ import be.mygod.vpnhotspot.util.Services object TetherOffloadManager { private const val TETHER_OFFLOAD_DISABLED = "tether_offload_disabled" val enabled get() = Settings.Global.getInt(app.contentResolver, TETHER_OFFLOAD_DISABLED, 0) == 0 - suspend fun setEnabled(value: Boolean) { - val int = if (value) 0 else 1 - try { - check(Settings.Global.putInt(Services.context.contentResolver, TETHER_OFFLOAD_DISABLED, int)) - } catch (e: SecurityException) { - try { - RootManager.use { it.execute(SettingsGlobalPut(TETHER_OFFLOAD_DISABLED, int.toString())) } - } catch (eRoot: Exception) { - eRoot.addSuppressed(e) - throw eRoot - } - } - } + suspend fun setEnabled(value: Boolean) = SettingsGlobalPut.int(TETHER_OFFLOAD_DISABLED, if (value) 0 else 1) } diff --git a/mobile/src/main/java/be/mygod/vpnhotspot/net/monitor/TetherTimeoutMonitor.kt b/mobile/src/main/java/be/mygod/vpnhotspot/net/monitor/TetherTimeoutMonitor.kt index 3d87fb1d..f3e0ee1b 100644 --- a/mobile/src/main/java/be/mygod/vpnhotspot/net/monitor/TetherTimeoutMonitor.kt +++ b/mobile/src/main/java/be/mygod/vpnhotspot/net/monitor/TetherTimeoutMonitor.kt @@ -6,6 +6,7 @@ import android.provider.Settings import androidx.annotation.RequiresApi import be.mygod.vpnhotspot.App.Companion.app import be.mygod.vpnhotspot.net.wifi.WifiApManager +import be.mygod.vpnhotspot.root.SettingsGlobalPut import kotlinx.coroutines.* import timber.log.Timber import kotlin.coroutines.CoroutineContext @@ -32,13 +33,10 @@ class TetherTimeoutMonitor(private val timeout: Long = 0, @Deprecated("Use SoftApConfigurationCompat instead") @get:RequiresApi(28) - @set:RequiresApi(28) - var enabled - get() = Settings.Global.getInt(app.contentResolver, SOFT_AP_TIMEOUT_ENABLED, 1) == 1 - set(value) { - // TODO: WRITE_SECURE_SETTINGS permission - check(Settings.Global.putInt(app.contentResolver, SOFT_AP_TIMEOUT_ENABLED, if (value) 1 else 0)) - } + val enabled get() = Settings.Global.getInt(app.contentResolver, SOFT_AP_TIMEOUT_ENABLED, 1) == 1 + @Deprecated("Use SoftApConfigurationCompat instead") + suspend fun setEnabled(value: Boolean) = SettingsGlobalPut.int(SOFT_AP_TIMEOUT_ENABLED, if (value) 1 else 0) + val defaultTimeout: Int get() { val delay = if (Build.VERSION.SDK_INT >= 28) try { if (Build.VERSION.SDK_INT < 30) Resources.getSystem().run { diff --git a/mobile/src/main/java/be/mygod/vpnhotspot/net/wifi/WifiApDialogFragment.kt b/mobile/src/main/java/be/mygod/vpnhotspot/net/wifi/WifiApDialogFragment.kt index 2a2867d5..301a652b 100644 --- a/mobile/src/main/java/be/mygod/vpnhotspot/net/wifi/WifiApDialogFragment.kt +++ b/mobile/src/main/java/be/mygod/vpnhotspot/net/wifi/WifiApDialogFragment.kt @@ -146,8 +146,11 @@ class WifiApDialogFragment : AlertDialogFragment= 30) { + dialogView.timeoutWrapper.helperText = "Default timeout: ${TetherTimeoutMonitor.defaultTimeout}ms" + if (!arg.readOnly) dialogView.timeout.addTextChangedListener(this@WifiApDialogFragment) + } else dialogView.timeoutWrapper.isGone = true if (Build.VERSION.SDK_INT >= 23 || arg.p2pMode) dialogView.band.apply { bandOptions = mutableListOf().apply { if (arg.p2pMode) { diff --git a/mobile/src/main/java/be/mygod/vpnhotspot/root/MiscCommands.kt b/mobile/src/main/java/be/mygod/vpnhotspot/root/MiscCommands.kt index 2d772236..c3339e2c 100644 --- a/mobile/src/main/java/be/mygod/vpnhotspot/root/MiscCommands.kt +++ b/mobile/src/main/java/be/mygod/vpnhotspot/root/MiscCommands.kt @@ -4,11 +4,13 @@ import android.content.Context import android.os.Build import android.os.Parcelable import android.os.RemoteException +import android.provider.Settings import androidx.annotation.RequiresApi import be.mygod.librootkotlinx.* import be.mygod.vpnhotspot.App.Companion.app import be.mygod.vpnhotspot.net.Routing import be.mygod.vpnhotspot.net.TetheringManager +import be.mygod.vpnhotspot.util.Services import kotlinx.android.parcel.Parcelize import kotlinx.coroutines.* import kotlinx.coroutines.channels.produce @@ -171,6 +173,21 @@ class StopTethering(private val type: Int) : RootCommandNoResult { @Parcelize class SettingsGlobalPut(val name: String, val value: String) : RootCommandNoResult { + companion object { + suspend fun int(name: String, value: Int) { + try { + check(Settings.Global.putInt(Services.context.contentResolver, name, value)) + } catch (e: SecurityException) { + try { + RootManager.use { it.execute(SettingsGlobalPut(name, value.toString())) } + } catch (eRoot: Exception) { + eRoot.addSuppressed(e) + throw eRoot + } + } + } + } + @Suppress("BlockingMethodInNonBlockingContext") override suspend fun execute() = withContext(Dispatchers.IO) { val process = ProcessBuilder("settings", "put", "global", name, value).redirectErrorStream(true).start()