LogViewerActivity: destroy process when coroutine scope is cancelled
Signed-off-by: Jason A. Donenfeld <Jason@zx2c4.com>
This commit is contained in:
parent
bd1679b7e0
commit
44c2afbfba
@ -193,49 +193,54 @@ class LogViewerActivity : AppCompatActivity() {
|
|||||||
private suspend fun streamingLog() = withContext(Dispatchers.IO) {
|
private suspend fun streamingLog() = withContext(Dispatchers.IO) {
|
||||||
val builder = ProcessBuilder().command("logcat", "-b", "all", "-v", "threadtime", "*:V")
|
val builder = ProcessBuilder().command("logcat", "-b", "all", "-v", "threadtime", "*:V")
|
||||||
builder.environment()["LC_ALL"] = "C"
|
builder.environment()["LC_ALL"] = "C"
|
||||||
val process = try {
|
var process: Process? = null
|
||||||
builder.start()
|
try {
|
||||||
} catch (e: IOException) {
|
process = try {
|
||||||
e.printStackTrace()
|
builder.start()
|
||||||
return@withContext
|
} catch (e: IOException) {
|
||||||
}
|
e.printStackTrace()
|
||||||
val stdout = BufferedReader(InputStreamReader(process!!.inputStream, StandardCharsets.UTF_8))
|
return@withContext
|
||||||
var haveScrolled = false
|
}
|
||||||
val start = System.nanoTime()
|
val stdout = BufferedReader(InputStreamReader(process!!.inputStream, StandardCharsets.UTF_8))
|
||||||
var startPeriod = start
|
var haveScrolled = false
|
||||||
while (true) {
|
val start = System.nanoTime()
|
||||||
val line = stdout.readLine() ?: break
|
var startPeriod = start
|
||||||
rawLogLines.append(line)
|
while (true) {
|
||||||
rawLogLines.append('\n')
|
val line = stdout.readLine() ?: break
|
||||||
val logLine = parseLine(line)
|
rawLogLines.append(line)
|
||||||
withContext(Dispatchers.Main.immediate) {
|
rawLogLines.append('\n')
|
||||||
if (logLine != null) {
|
val logLine = parseLine(line)
|
||||||
recyclerView?.let {
|
withContext(Dispatchers.Main.immediate) {
|
||||||
val shouldScroll = haveScrolled && !it.canScrollVertically(1)
|
if (logLine != null) {
|
||||||
logLines.add(logLine)
|
recyclerView?.let {
|
||||||
if (haveScrolled) logAdapter.notifyDataSetChanged()
|
val shouldScroll = haveScrolled && !it.canScrollVertically(1)
|
||||||
if (shouldScroll)
|
logLines.add(logLine)
|
||||||
it.scrollToPosition(logLines.size - 1)
|
if (haveScrolled) logAdapter.notifyDataSetChanged()
|
||||||
}
|
if (shouldScroll)
|
||||||
} else {
|
it.scrollToPosition(logLines.size - 1)
|
||||||
/* I'd prefer for the next line to be:
|
}
|
||||||
|
} else {
|
||||||
|
/* I'd prefer for the next line to be:
|
||||||
* logLines.lastOrNull()?.msg += "\n$line"
|
* logLines.lastOrNull()?.msg += "\n$line"
|
||||||
* However, as of writing, that causes the kotlin compiler to freak out and crash, spewing bytecode.
|
* However, as of writing, that causes the kotlin compiler to freak out and crash, spewing bytecode.
|
||||||
*/
|
*/
|
||||||
logLines.lastOrNull()?.apply { msg += "\n$line" }
|
logLines.lastOrNull()?.apply { msg += "\n$line" }
|
||||||
if (haveScrolled) logAdapter.notifyDataSetChanged()
|
if (haveScrolled) logAdapter.notifyDataSetChanged()
|
||||||
}
|
}
|
||||||
if (!haveScrolled) {
|
if (!haveScrolled) {
|
||||||
val end = System.nanoTime()
|
val end = System.nanoTime()
|
||||||
val scroll = (end - start) > 1000000000L * 2.5 || !stdout.ready()
|
val scroll = (end - start) > 1000000000L * 2.5 || !stdout.ready()
|
||||||
if (logLines.isNotEmpty() && (scroll || (end - startPeriod) > 1000000000L / 4)) {
|
if (logLines.isNotEmpty() && (scroll || (end - startPeriod) > 1000000000L / 4)) {
|
||||||
logAdapter.notifyDataSetChanged()
|
logAdapter.notifyDataSetChanged()
|
||||||
recyclerView?.scrollToPosition(logLines.size - 1)
|
recyclerView?.scrollToPosition(logLines.size - 1)
|
||||||
startPeriod = end
|
startPeriod = end
|
||||||
|
}
|
||||||
|
if (scroll) haveScrolled = true
|
||||||
}
|
}
|
||||||
if (scroll) haveScrolled = true
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
} finally {
|
||||||
|
process?.destroy()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user