Skip to content

Commit 9a219e7

Browse files
Fix granting permission not working reliably with su
1 parent 6a444d7 commit 9a219e7

File tree

1 file changed

+70
-8
lines changed

1 file changed

+70
-8
lines changed

app/src/main/java/com/dp/logcatapp/fragments/logcatlive/LogcatLiveFragment.kt

+70-8
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,11 @@ import com.google.android.material.floatingactionbutton.FloatingActionButton
3939
import com.google.android.material.snackbar.Snackbar
4040
import kotlinx.coroutines.*
4141
import kotlinx.coroutines.Dispatchers.Default
42+
import java.io.BufferedReader
43+
import java.io.BufferedWriter
44+
import java.io.InputStreamReader
45+
import java.io.OutputStreamWriter
46+
import java.util.*
4247

4348
class LogcatLiveFragment : BaseFragment(), ServiceConnection, LogsReceivedListener {
4449
companion object {
@@ -678,17 +683,11 @@ class LogcatLiveFragment : BaseFragment(), ServiceConnection, LogsReceivedListen
678683
dialog.show(fragmentManager, AskingForRootAccessDialogFragment.TAG)
679684

680685
val result = withContext(Dispatchers.IO) {
681-
val cmd = "pm grant ${BuildConfig.APPLICATION_ID} ${Manifest.permission.READ_LOGS}"
682-
try {
683-
val process = Runtime.getRuntime().exec(arrayOf("su", "-c", cmd))
684-
process.waitFor()
685-
} catch (e: Exception) {
686-
-1
687-
}
686+
grantPermissionWithSu()
688687
}
689688

690689
dialog.dismissAllowingStateLoss()
691-
if (result == 0) {
690+
if (result) {
692691
RestartAppMessageDialogFragment.newInstance().show(fragmentManager,
693692
RestartAppMessageDialogFragment.TAG)
694693
} else {
@@ -699,6 +698,69 @@ class LogcatLiveFragment : BaseFragment(), ServiceConnection, LogsReceivedListen
699698
}
700699
}
701700

701+
private fun BufferedWriter.writeCmd(cmd: String) {
702+
write(cmd)
703+
newLine()
704+
flush()
705+
}
706+
707+
private suspend fun grantPermissionWithSu() = coroutineScope {
708+
try {
709+
val processBuilder = ProcessBuilder("su")
710+
val process = processBuilder.start()
711+
712+
val stdoutWriter = BufferedWriter(OutputStreamWriter(process.outputStream))
713+
val stdinReader = BufferedReader(InputStreamReader(process.inputStream))
714+
val stderrReader = BufferedReader(InputStreamReader(process.errorStream))
715+
716+
val marker = "RESULT>>>${UUID.randomUUID()}>>>"
717+
val stdoutResult = async {
718+
var result = false
719+
720+
try {
721+
while (true) {
722+
val line = stdinReader.readLine()?.trim() ?: break
723+
724+
val index = line.indexOf(marker)
725+
if (index != -1) {
726+
result = line.substring(index + marker.length) == "0"
727+
break
728+
}
729+
}
730+
} catch (e: Exception) {
731+
}
732+
733+
result
734+
}
735+
736+
val stderrReaderResult = async {
737+
try {
738+
while (true) {
739+
stderrReader.readLine()?.trim() ?: break
740+
}
741+
} catch (e: Exception) {
742+
}
743+
}
744+
745+
val cmd = "pm grant ${BuildConfig.APPLICATION_ID} ${Manifest.permission.READ_LOGS}"
746+
stdoutWriter.writeCmd(cmd)
747+
stdoutWriter.writeCmd("echo \"$marker$?\"")
748+
749+
val finalResult = stdoutResult.await()
750+
751+
stdoutWriter.writeCmd("exit")
752+
753+
process.waitFor()
754+
process.destroy()
755+
756+
stderrReaderResult.await()
757+
758+
finalResult
759+
} catch (e: Exception) {
760+
false
761+
}
762+
}
763+
702764
private class LogFilter(filterInfo: FilterInfo) : Filter {
703765
val type = filterInfo.type
704766
val content = filterInfo.content

0 commit comments

Comments
 (0)