rework crash report text, crash report: show mods

This commit is contained in:
Bixilon 2022-10-30 14:33:15 +01:00
parent fc2cbdf9d9
commit 87130b4d63
No known key found for this signature in database
GPG Key ID: 5CAD791931B09AC4
15 changed files with 474 additions and 106 deletions

View File

@ -19,20 +19,16 @@ import de.bixilon.kutil.exception.ExceptionUtil.toStackTrace
import de.bixilon.kutil.exception.ExceptionUtil.tryCatch import de.bixilon.kutil.exception.ExceptionUtil.tryCatch
import de.bixilon.kutil.file.FileUtil.slashPath import de.bixilon.kutil.file.FileUtil.slashPath
import de.bixilon.kutil.file.watcher.FileWatcherService import de.bixilon.kutil.file.watcher.FileWatcherService
import de.bixilon.kutil.os.PlatformInfo
import de.bixilon.kutil.shutdown.AbstractShutdownReason import de.bixilon.kutil.shutdown.AbstractShutdownReason
import de.bixilon.kutil.shutdown.ShutdownManager import de.bixilon.kutil.shutdown.ShutdownManager
import de.bixilon.kutil.time.TimeUtil.millis import de.bixilon.kutil.time.TimeUtil.millis
import de.bixilon.kutil.unit.UnitFormatter.formatBytes
import de.bixilon.kutil.unsafe.UnsafeUtil import de.bixilon.kutil.unsafe.UnsafeUtil
import de.bixilon.minosoft.gui.eros.controller.JavaFXWindowController import de.bixilon.minosoft.gui.eros.controller.JavaFXWindowController
import de.bixilon.minosoft.gui.eros.util.JavaFXInitializer import de.bixilon.minosoft.gui.eros.util.JavaFXInitializer
import de.bixilon.minosoft.gui.eros.util.JavaFXUtil import de.bixilon.minosoft.gui.eros.util.JavaFXUtil
import de.bixilon.minosoft.properties.MinosoftProperties
import de.bixilon.minosoft.protocol.network.connection.play.PlayConnection import de.bixilon.minosoft.protocol.network.connection.play.PlayConnection
import de.bixilon.minosoft.terminal.CommandLineArguments
import de.bixilon.minosoft.terminal.RunConfiguration import de.bixilon.minosoft.terminal.RunConfiguration
import de.bixilon.minosoft.util.SystemInformation import de.bixilon.minosoft.util.crash.CrashReportUtil
import de.bixilon.minosoft.util.logging.Log import de.bixilon.minosoft.util.logging.Log
import de.bixilon.minosoft.util.logging.LogLevels import de.bixilon.minosoft.util.logging.LogLevels
import de.bixilon.minosoft.util.logging.LogMessageType import de.bixilon.minosoft.util.logging.LogMessageType
@ -48,7 +44,6 @@ import javafx.stage.Stage
import javafx.stage.Window import javafx.stage.Window
import java.io.File import java.io.File
import java.io.FileOutputStream import java.io.FileOutputStream
import java.lang.management.ManagementFactory
import java.nio.charset.StandardCharsets import java.nio.charset.StandardCharsets
import java.text.SimpleDateFormat import java.text.SimpleDateFormat
@ -89,40 +84,6 @@ class ErosCrashReport : JavaFXWindowController() {
companion object { companion object {
var alreadyCrashed = false var alreadyCrashed = false
private set private set
private val CRASH_REPORT_COMMENTS = listOf(
"Let's blame Bixilon for this",
"But it worked once",
"It works on my computer",
"Not a bug, it's a feature",
"My bad",
"Whoops",
"Don't try to crash this!",
"Makes not sense!",
"Let's hack the game",
"You're evil",
"Maybe in another life.",
"This sucks",
"Chill ur life",
"Chill your life",
"Chill your base",
"Damn!",
"Developing is hard.",
"Please don't kill me for this",
"Trying my best",
"That happens when you develop while playing games!",
"Written while driving in a FlixBus",
"Coded while traveling in the ICE 272 towards Hamburg-Altona",
"Sorry, the ICE 693 drive towards Munich was really long",
"Coded while playing bedwars",
"I am #1 in bedwars swordless",
"Der AB kam vor der CD",
"You can't do this",
"Sing me a happy song!",
"This message should not be visible...",
"lmfao",
"Your fault",
"Technoblade never dies", // In memorial to technoblade. RIP Technoblade 30.6.2022
)
/** /**
@ -135,7 +96,7 @@ class ErosCrashReport : JavaFXWindowController() {
} }
alreadyCrashed = true alreadyCrashed = true
val details = try { val details = try {
createCrashText(if (hideException) null else this) CrashReportUtil.createCrashReport(if (hideException) null else this)
} catch (error: Throwable) { } catch (error: Throwable) {
error.toStackTrace() error.toStackTrace()
} }
@ -208,70 +169,5 @@ class ErosCrashReport : JavaFXWindowController() {
stage.show() stage.show()
} }
} }
private fun createCrashText(exception: Throwable?): String {
var connections = """
-- Connections --"""
fun addConnection(connection: PlayConnection) {
connections += """
#${connection.connectionId}:
Version: ${connection.version}
Account: ${connection.account.username}
Address: ${connection.address}
Brand: ${connection.serverInfo.brand}
Events: ${connection.size}
State: ${connection.state}
Connected: ${connection.network.connected}
Protocol state: ${connection.network.state}
Compression threshold: ${connection.network.compressionThreshold}
Encrypted: ${connection.network.encrypted}
Was connected: ${connection.wasConnected}
Rendering: ${connection.rendering != null}
Error: ${connection.error}
""".removeSuffix("\n")
}
for (connection in PlayConnection.ACTIVE_CONNECTIONS.toSynchronizedSet()) {
addConnection(connection)
}
for (connection in PlayConnection.ERRORED_CONNECTIONS.toSynchronizedSet()) {
addConnection(connection)
}
val stackTraceText = if (exception == null) "" else """
-- Stacktrace --
${exception.toStackTrace()}"""
return """
----- Minosoft Crash Report -----
// ${CRASH_REPORT_COMMENTS.random()}
-- General Information --
Time: ${SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(millis())} (${millis() / 1000L})
Crash thread: ${Thread.currentThread().name}
$stackTraceText
$connections
-- Runtime Details --
Start arguments: ${CommandLineArguments.ARGUMENTS}
JVM flags: ${ManagementFactory.getRuntimeMXBean().inputArguments}
Home directory: ${RunConfiguration.HOME_DIRECTORY}
Disable Eros: ${RunConfiguration.DISABLE_EROS}
Disable rendering: ${RunConfiguration.DISABLE_RENDERING}
-- System Details --
Operating system: ${SystemInformation.OS_TEXT}
Detected operating system: ${PlatformInfo.OS}
Detected architecture: ${PlatformInfo.ARCHITECTURE}
Java version: ${Runtime.version()} ${System.getProperty("sun.arch.data.model")}bit
Memory: ${SystemInformation.SYSTEM_MEMORY.formatBytes()}
CPU: ${SystemInformation.PROCESSOR_TEXT}
-- Git Info --
${tryCatch { MinosoftProperties.git?.format() }}
""".removeSuffix("\n")
}
} }
} }

View File

@ -15,6 +15,7 @@ package de.bixilon.minosoft.protocol.network.connection.play
import de.bixilon.kutil.collections.CollectionUtil.synchronizedMapOf import de.bixilon.kutil.collections.CollectionUtil.synchronizedMapOf
import de.bixilon.kutil.collections.CollectionUtil.synchronizedSetOf import de.bixilon.kutil.collections.CollectionUtil.synchronizedSetOf
import de.bixilon.kutil.collections.CollectionUtil.toSynchronizedSet
import de.bixilon.kutil.concurrent.worker.task.TaskWorker import de.bixilon.kutil.concurrent.worker.task.TaskWorker
import de.bixilon.kutil.concurrent.worker.task.WorkerTask import de.bixilon.kutil.concurrent.worker.task.WorkerTask
import de.bixilon.kutil.latch.CountUpAndDownLatch import de.bixilon.kutil.latch.CountUpAndDownLatch
@ -254,5 +255,12 @@ class PlayConnection(
companion object { companion object {
val ACTIVE_CONNECTIONS: MutableSet<PlayConnection> = synchronizedSetOf() val ACTIVE_CONNECTIONS: MutableSet<PlayConnection> = synchronizedSetOf()
val ERRORED_CONNECTIONS: MutableSet<PlayConnection> = synchronizedSetOf() val ERRORED_CONNECTIONS: MutableSet<PlayConnection> = synchronizedSetOf()
fun collectConnections(): Array<PlayConnection> {
val result = ACTIVE_CONNECTIONS.toSynchronizedSet()
result += ERRORED_CONNECTIONS.toSynchronizedSet()
return result.toTypedArray()
}
} }
} }

View File

@ -0,0 +1,54 @@
/*
* Minosoft
* Copyright (C) 2020-2022 Moritz Zwerger
*
* This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along with this program. If not, see <https://www.gnu.org/licenses/>.
*
* This software is not affiliated with Mojang AB, the original developer of Minecraft.
*/
package de.bixilon.minosoft.util.crash
import de.bixilon.minosoft.util.crash.CrashReportUtil.removeTrailingNewline
import de.bixilon.minosoft.util.crash.section.AbstractCrashSection
class CrashReportBuilder {
private val sections: MutableList<AbstractCrashSection> = mutableListOf()
operator fun plusAssign(section: AbstractCrashSection) {
sections += section
}
fun build(): String {
val builder = StringBuilder()
builder += """----- Minosoft Crash Report -----"""
builder.append("// ").append(CrashReportUtil.CRASH_REPORT_COMMENTS.random())
for (section in sections) {
if (section.isEmpty) {
continue
}
builder.append('\n')
builder.append('\n')
builder.append("-- ")
builder.append(section.name)
builder.append(" --")
builder.append('\n')
section.append(builder, CrashReportUtil.INTENT)
builder.removeTrailingNewline()
}
return builder.toString()
}
private operator fun StringBuilder.plusAssign(string: String) {
append(string)
append('\n')
}
}

View File

@ -0,0 +1,87 @@
/*
* Minosoft
* Copyright (C) 2020-2022 Moritz Zwerger
*
* This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along with this program. If not, see <https://www.gnu.org/licenses/>.
*
* This software is not affiliated with Mojang AB, the original developer of Minecraft.
*/
package de.bixilon.minosoft.util.crash
import de.bixilon.kutil.exception.ExceptionUtil.catchAll
import de.bixilon.minosoft.properties.MinosoftProperties
import de.bixilon.minosoft.util.crash.section.*
object CrashReportUtil {
const val INTENT = " "
val CRASH_REPORT_COMMENTS = listOf(
"Let's blame Bixilon for this",
"But it worked once",
"It works on my computer",
"Not a bug, it's a feature",
"My bad",
"Whoops",
"Don't try to crash this!",
"Makes not sense!",
"Let's hack the game",
"You're evil",
"Maybe in another life.",
"This sucks",
"Chill ur life",
"Chill your life",
"Chill your base",
"Damn!",
"Developing is hard.",
"Please don't kill me for this",
"Trying my best",
"That happens when you develop while playing games!",
"Written while driving in a FlixBus",
"Coded while traveling in the ICE 272 towards Hamburg-Altona",
"Sorry, the ICE 693 drive towards Munich was really long",
"Coded while playing bedwars",
"I am #1 in bedwars swordless",
"Der AB kam vor der CD",
"You can't do this",
"Sing me a happy song!",
"This message should not be visible...",
"lmfao",
"Your fault",
"Technoblade never dies", // In memorial to technoblade. RIP Technoblade 30.6.2022
)
fun createCrashReport(error: Throwable?): String {
val builder = CrashReportBuilder()
builder += GeneralSection()
error?.let { builder += ThrowableSection(it) }
builder += RuntimeSection()
builder += SystemSection()
builder += ModCrashSection()
builder += ConnectionCrashSection()
catchAll { builder += PropertiesSection(MinosoftProperties) }
catchAll { MinosoftProperties.git?.let { builder += GitSection(it) } }
return builder.build()
}
fun StringBuilder.removeTrailingNewline() {
if (isEmpty()) {
return
}
val lastIndex = this.lastIndex
if (this[lastIndex] == '\n') {
deleteCharAt(lastIndex)
}
}
}

View File

@ -0,0 +1,22 @@
/*
* Minosoft
* Copyright (C) 2020-2022 Moritz Zwerger
*
* This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along with this program. If not, see <https://www.gnu.org/licenses/>.
*
* This software is not affiliated with Mojang AB, the original developer of Minecraft.
*/
package de.bixilon.minosoft.util.crash.section
interface AbstractCrashSection {
val name: String
val isEmpty: Boolean
fun append(builder: StringBuilder, intent: String)
}

View File

@ -0,0 +1,42 @@
/*
* Minosoft
* Copyright (C) 2020-2022 Moritz Zwerger
*
* This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along with this program. If not, see <https://www.gnu.org/licenses/>.
*
* This software is not affiliated with Mojang AB, the original developer of Minecraft.
*/
package de.bixilon.minosoft.util.crash.section
import de.bixilon.minosoft.util.crash.CrashReportUtil
import de.bixilon.minosoft.util.crash.CrashReportUtil.removeTrailingNewline
abstract class ArrayCrashSection<T>(
override val name: String,
val entries: Array<T>,
) : AbstractCrashSection {
override val isEmpty: Boolean get() = entries.isEmpty()
abstract fun format(entry: T, builder: StringBuilder, intent: String)
override fun append(builder: StringBuilder, intent: String) {
for ((index, entry) in entries.withIndex()) {
builder.append(intent)
builder.append('#')
builder.append(index)
builder.append('\n')
format(entry, builder, intent + CrashReportUtil.INTENT)
builder.removeTrailingNewline()
builder.append('\n')
}
}
fun StringBuilder.appendProperty(intent: String, name: String, value: Any?) {
append(intent).append(name).append(": ").append(value).append('\n')
}
}

View File

@ -0,0 +1,37 @@
/*
* Minosoft
* Copyright (C) 2020-2022 Moritz Zwerger
*
* This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along with this program. If not, see <https://www.gnu.org/licenses/>.
*
* This software is not affiliated with Mojang AB, the original developer of Minecraft.
*/
package de.bixilon.minosoft.util.crash.section
import de.bixilon.minosoft.protocol.network.connection.play.PlayConnection
class ConnectionCrashSection(
connections: Array<PlayConnection> = PlayConnection.collectConnections(),
) : ArrayCrashSection<PlayConnection>("Connections", connections) {
override fun format(entry: PlayConnection, builder: StringBuilder, intent: String) {
builder.appendProperty(intent, "Id", entry.connectionId)
builder.appendProperty(intent, "Version", entry.version)
builder.appendProperty(intent, "Account", entry.account.username)
builder.appendProperty(intent, "Address", entry.address)
builder.appendProperty(intent, "Brand", entry.serverInfo.brand)
builder.appendProperty(intent, "Events", entry.size)
builder.appendProperty(intent, "State", entry.state)
builder.appendProperty(intent, "Protocol state", entry.network.state)
builder.appendProperty(intent, "Compression threshold", entry.network.compressionThreshold)
builder.appendProperty(intent, "Encrypted", entry.network.encrypted)
builder.appendProperty(intent, "Was connected", entry.wasConnected)
builder.appendProperty(intent, "Rendering", entry.rendering != null)
builder.appendProperty(intent, "Error", entry.error)
}
}

View File

@ -0,0 +1,32 @@
/*
* Minosoft
* Copyright (C) 2020-2022 Moritz Zwerger
*
* This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along with this program. If not, see <https://www.gnu.org/licenses/>.
*
* This software is not affiliated with Mojang AB, the original developer of Minecraft.
*/
package de.bixilon.minosoft.util.crash.section
open class CrashSection(
override val name: String,
val entries: Array<Pair<String, Any?>>,
) : AbstractCrashSection {
override val isEmpty: Boolean
get() = entries.isEmpty()
override fun append(builder: StringBuilder, intent: String) {
for ((name, value) in entries) {
builder.append(intent)
builder.append(name)
builder.append(": ")
builder.append(value)
builder.append('\n')
}
}
}

View File

@ -0,0 +1,24 @@
/*
* Minosoft
* Copyright (C) 2020-2022 Moritz Zwerger
*
* This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along with this program. If not, see <https://www.gnu.org/licenses/>.
*
* This software is not affiliated with Mojang AB, the original developer of Minecraft.
*/
package de.bixilon.minosoft.util.crash.section
import de.bixilon.kutil.time.TimeUtil.millis
import java.text.SimpleDateFormat
class GeneralSection : CrashSection(
"General information", arrayOf(
"Time" to SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(millis()) + "(${millis() / 1000L})",
"Thread" to Thread.currentThread().name,
)
)

View File

@ -0,0 +1,24 @@
/*
* Minosoft
* Copyright (C) 2020-2022 Moritz Zwerger
*
* This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along with this program. If not, see <https://www.gnu.org/licenses/>.
*
* This software is not affiliated with Mojang AB, the original developer of Minecraft.
*/
package de.bixilon.minosoft.util.crash.section
import de.bixilon.minosoft.properties.git.GitP
class GitSection(git: GitP) : CrashSection(
"Git", arrayOf(
"Commit" to git.commit,
"Branch" to git.branch,
"Dirty" to git.dirty,
)
)

View File

@ -0,0 +1,32 @@
/*
* Minosoft
* Copyright (C) 2020-2022 Moritz Zwerger
*
* This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along with this program. If not, see <https://www.gnu.org/licenses/>.
*
* This software is not affiliated with Mojang AB, the original developer of Minecraft.
*/
package de.bixilon.minosoft.util.crash.section
import de.bixilon.minosoft.modding.loader.ModLoader
import de.bixilon.minosoft.modding.loader.mod.MinosoftMod
class ModCrashSection(
connections: Array<MinosoftMod> = ModLoader.mods.mods.values.toTypedArray(),
) : ArrayCrashSection<MinosoftMod>("Mods", connections) {
override fun format(entry: MinosoftMod, builder: StringBuilder, intent: String) {
builder.appendProperty(intent, "Path", entry.path)
builder.appendProperty(intent, "Phase", entry.phase)
builder.appendProperty(intent, "Name", entry.manifest?.name)
builder.appendProperty(intent, "Version", entry.manifest?.version)
builder.appendProperty(intent, "Author(s)", entry.manifest?.authors)
builder.appendProperty(intent, "Website", entry.manifest?.website)
builder.appendProperty(intent, "Main", entry.manifest?.main)
}
}

View File

@ -0,0 +1,23 @@
/*
* Minosoft
* Copyright (C) 2020-2022 Moritz Zwerger
*
* This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along with this program. If not, see <https://www.gnu.org/licenses/>.
*
* This software is not affiliated with Mojang AB, the original developer of Minecraft.
*/
package de.bixilon.minosoft.util.crash.section
import de.bixilon.minosoft.properties.MinosoftP
class PropertiesSection(val properties: MinosoftP) : CrashSection(
"Properties", arrayOf(
"Version name" to properties.general.name,
"Stable" to properties.general.stable,
)
)

View File

@ -0,0 +1,27 @@
/*
* Minosoft
* Copyright (C) 2020-2022 Moritz Zwerger
*
* This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along with this program. If not, see <https://www.gnu.org/licenses/>.
*
* This software is not affiliated with Mojang AB, the original developer of Minecraft.
*/
package de.bixilon.minosoft.util.crash.section
import de.bixilon.minosoft.terminal.CommandLineArguments
import de.bixilon.minosoft.terminal.RunConfiguration
import java.lang.management.ManagementFactory
class RuntimeSection : CrashSection(
"Runtime details", arrayOf(
"Start arguments" to CommandLineArguments.ARGUMENTS,
"JVM flags" to ManagementFactory.getRuntimeMXBean().inputArguments,
"Environment" to System.getenv(),
"Home directory" to RunConfiguration.HOME_DIRECTORY,
)
)

View File

@ -0,0 +1,29 @@
/*
* Minosoft
* Copyright (C) 2020-2022 Moritz Zwerger
*
* This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along with this program. If not, see <https://www.gnu.org/licenses/>.
*
* This software is not affiliated with Mojang AB, the original developer of Minecraft.
*/
package de.bixilon.minosoft.util.crash.section
import de.bixilon.kutil.os.PlatformInfo
import de.bixilon.kutil.unit.UnitFormatter.formatBytes
import de.bixilon.minosoft.util.SystemInformation
class SystemSection : CrashSection(
"System information", arrayOf(
"Operating system" to SystemInformation.OS_TEXT,
"Platform os" to PlatformInfo.OS,
"Platform architecture" to PlatformInfo.ARCHITECTURE,
"Java" to "${Runtime.version()} ${System.getProperty("sun.arch.data.model")}bit",
"Memory" to SystemInformation.SYSTEM_MEMORY.formatBytes(),
"Processor" to SystemInformation.PROCESSOR_TEXT,
)
)

View File

@ -0,0 +1,31 @@
/*
* Minosoft
* Copyright (C) 2020-2022 Moritz Zwerger
*
* This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along with this program. If not, see <https://www.gnu.org/licenses/>.
*
* This software is not affiliated with Mojang AB, the original developer of Minecraft.
*/
package de.bixilon.minosoft.util.crash.section
import de.bixilon.kutil.exception.ExceptionUtil.toStackTrace
class ThrowableSection(val error: Throwable) : AbstractCrashSection {
override val name: String get() = "Stacktrace"
override val isEmpty: Boolean get() = false
override fun append(builder: StringBuilder, intent: String) {
val stacktrace = error.toStackTrace().lines()
for (line in stacktrace) {
builder.append(intent)
builder.append(line)
builder.append('\n')
}
}
}