From c178e5e5eb485cadf122dc43e2db9afda9ef85f1 Mon Sep 17 00:00:00 2001 From: TheBrokenRail Date: Sun, 2 Oct 2022 00:47:11 -0400 Subject: [PATCH] Logging Improvements --- dependencies/zenity/src | 2 +- docs/COMMAND_LINE.md | 3 ++ launcher/src/bootstrap.c | 61 ++++++++++++++----------------- launcher/src/crash-report.c | 48 +++++++++++++----------- launcher/src/crash-report.h | 1 + libreborn/include/libreborn/log.h | 13 ++++++- libreborn/src/util/exec.c | 9 +++++ libreborn/src/util/log.c | 19 ++++++++++ 8 files changed, 98 insertions(+), 58 deletions(-) diff --git a/dependencies/zenity/src b/dependencies/zenity/src index 435bc15..5878701 160000 --- a/dependencies/zenity/src +++ b/dependencies/zenity/src @@ -1 +1 @@ -Subproject commit 435bc154ef8dcec8a3f126ed7f5198b7db32ea29 +Subproject commit 58787016ce6f72bdc4dff75721c8936779f6c20c diff --git a/docs/COMMAND_LINE.md b/docs/COMMAND_LINE.md index 7e86ef6..8f322bc 100644 --- a/docs/COMMAND_LINE.md +++ b/docs/COMMAND_LINE.md @@ -5,6 +5,9 @@ ### ``--version`` (Or ``-v``) If you run MCPI-Reborn with ``--version`` it will print its version to ``stdout``. +### ``--debug`` +This sets ``MCPI_DEBUG``. + ### Client Mode Only #### ``--print-available-feature-flags`` diff --git a/launcher/src/bootstrap.c b/launcher/src/bootstrap.c index aa2488e..75598c9 100644 --- a/launcher/src/bootstrap.c +++ b/launcher/src/bootstrap.c @@ -98,23 +98,11 @@ static void exit_handler(__attribute__((unused)) int signal_id) { // Pre-Bootstrap void pre_bootstrap(int argc, char *argv[]) { - // Disable stdout Buffering - setvbuf(stdout, NULL, _IONBF, 0); - - // --debug - for (int i = 1; i < argc; i++) { - if (strcmp(argv[i], "--debug") == 0) { - set_and_print_env("MCPI_DEBUG", "1"); - break; - } - } - // Set Debug Tag reborn_debug_tag = "(Launcher) "; - // Set Default Native Component Environment -#define set_variable_default(name) set_and_print_env("MCPI_NATIVE_" name, getenv(name)); - for_each_special_environmental_variable(set_variable_default); + // Disable stdout Buffering + setvbuf(stdout, NULL, _IONBF, 0); // Print Version for (int i = 1; i < argc; i++) { @@ -126,31 +114,26 @@ void pre_bootstrap(int argc, char *argv[]) { } } + // Setup Logging + setup_log_file(); + + // --debug + for (int i = 1; i < argc; i++) { + if (strcmp(argv[i], "--debug") == 0) { + set_and_print_env("MCPI_DEBUG", "1"); + break; + } + } + + // Set Default Native Component Environment +#define set_variable_default(name) set_and_print_env("MCPI_NATIVE_" name, getenv(name)); + for_each_special_environmental_variable(set_variable_default); + // GTK Dark Mode #ifndef MCPI_SERVER_MODE set_and_print_env("GTK_THEME", "Adwaita:dark"); #endif - // Debug Zenity -#ifndef MCPI_SERVER_MODE - { - const char *is_debug = getenv("MCPI_DEBUG"); - if (is_debug != NULL && strlen(is_debug) > 0) { - set_and_print_env("ZENITY_DEBUG", "1"); - } - } -#endif - - // AppImage -#ifdef MCPI_IS_APPIMAGE_BUILD - { - char *owd = getenv("OWD"); - if (owd != NULL && chdir(owd) != 0) { - ERR("AppImage: Unable To Fix Current Directory: %s", strerror(errno)); - } - } -#endif - // Get Binary Directory char *binary_directory = get_binary_directory(); @@ -177,6 +160,16 @@ void pre_bootstrap(int argc, char *argv[]) { // Setup Crash Reports setup_crash_report(); + // AppImage +#ifdef MCPI_IS_APPIMAGE_BUILD + { + char *owd = getenv("OWD"); + if (owd != NULL && chdir(owd) != 0) { + ERR("AppImage: Unable To Fix Current Directory: %s", strerror(errno)); + } + } +#endif + // Install Signal Handlers struct sigaction act_sigint; memset((void *) &act_sigint, 0, sizeof (struct sigaction)); diff --git a/launcher/src/crash-report.c b/launcher/src/crash-report.c index 415ca57..1205ce2 100644 --- a/launcher/src/crash-report.c +++ b/launcher/src/crash-report.c @@ -24,6 +24,9 @@ static void show_report(const char *log_filename) { if (pid == 0) { // Child setsid(); + ALLOC_CHECK(freopen("/dev/null", "w", stdout)); + ALLOC_CHECK(freopen("/dev/null", "w", stderr)); + ALLOC_CHECK(freopen("/dev/null", "r", stdin)); const char *command[] = { "zenity", "--title", DIALOG_TITLE, @@ -37,7 +40,6 @@ static void show_report(const char *log_filename) { "--font", "Monospace", NULL }; - reborn_debug_tag = CHILD_PROCESS_TAG; safe_execvpe(command, (const char *const *) environ); } } @@ -53,6 +55,21 @@ static void exit_handler(__attribute__((unused)) int signal) { #define PIPE_READ 0 #define PIPE_WRITE 1 #define MCPI_LOGS_DIR "/tmp/.minecraft-pi-logs" +static char log_filename[] = MCPI_LOGS_DIR "/XXXXXX"; +static int log_file_fd = -1; +void setup_log_file() { + // Create Temporary File + log_file_fd = mkstemp(log_filename); + if (log_file_fd == -1) { + ERR("Unable To Create Log File: %s", strerror(errno)); + } + + // Setup Environment + char *log_file_fd_env = NULL; + safe_asprintf(&log_file_fd_env, "%i", log_file_fd); + set_and_print_env("MCPI_LOG_FILE_FD", log_file_fd_env); + free(log_file_fd_env); +} void setup_crash_report() { // Store Output int output_pipe[2]; @@ -126,13 +143,6 @@ void setup_crash_report() { } } - // Create Temporary File - char log_filename[] = MCPI_LOGS_DIR "/XXXXXX"; - int log_file_fd = mkstemp(log_filename); - if (log_file_fd == -1) { - ERR("Unable To Create Log File: %s", strerror(errno)); - } - // Setup Polling int number_fds = 3; struct pollfd poll_fds[number_fds]; @@ -144,8 +154,8 @@ void setup_crash_report() { } // Poll Data - int number_open_fds = number_fds; - while (number_open_fds > 0) { + int status; + while (waitpid(ret, &status, WNOHANG) != ret) { int poll_ret = poll(poll_fds, number_fds, -1); if (poll_ret == -1) { if (errno == EINTR) { @@ -183,7 +193,7 @@ void setup_crash_report() { // Print To Terminal buf[bytes_read] = '\0'; - fprintf(i == 0 ? stdout : stderr, "%s", buf); + fprintf(poll_fds[i].fd == output_pipe[PIPE_READ] ? stdout : stderr, "%s", buf); // Write To log if (write(log_file_fd, (void *) buf, bytes_read) == -1) { @@ -192,24 +202,20 @@ void setup_crash_report() { } } else { // File Descriptor No Longer Accessible - if (poll_fds[i].events != 0 && close(poll_fds[i].fd) == -1) { - ERR("Unable To Close File Descriptor: %s", strerror(errno)); - } poll_fds[i].events = 0; - number_open_fds--; } } } } - // Close Input Pipe - close(input_pipe[PIPE_WRITE]); - - // Get Return Code - int status; - waitpid(ret, &status, 0); + // Untrack Process untrack_child(ret); + // Close Pipes + close(output_pipe[PIPE_READ]); + close(error_pipe[PIPE_READ]); + close(input_pipe[PIPE_WRITE]); + // Check If Is Crash int is_crash = !is_exit_status_success(status); diff --git a/launcher/src/crash-report.h b/launcher/src/crash-report.h index 4042a60..1d667ad 100644 --- a/launcher/src/crash-report.h +++ b/launcher/src/crash-report.h @@ -4,6 +4,7 @@ extern "C" { #endif +void setup_log_file(); void setup_crash_report(); #ifdef __cplusplus diff --git a/libreborn/include/libreborn/log.h b/libreborn/include/libreborn/log.h index 22e9846..ba896f5 100644 --- a/libreborn/include/libreborn/log.h +++ b/libreborn/include/libreborn/log.h @@ -3,13 +3,22 @@ #include #include -// Debug Tag +#ifdef __cplusplus +extern "C" { +#endif + +// Debug extern const char *reborn_debug_tag; +int reborn_get_debug_fd(); // Logging #define INFO(format, ...) { fprintf(stderr, "[INFO]: " format "\n", ##__VA_ARGS__); } #define WARN(format, ...) { fprintf(stderr, "[WARN]: " format "\n", ##__VA_ARGS__); } -#define RAW_DEBUG(tag, format, ...) { const char *debug = getenv("MCPI_DEBUG"); if (debug != NULL) { fprintf(stderr, "[DEBUG]: %s" format "\n", tag, ##__VA_ARGS__); } } +#define RAW_DEBUG(tag, format, ...) { int debug_fd = reborn_get_debug_fd(); if (debug_fd != -1) { dprintf(debug_fd, "[DEBUG]: %s" format "\n", tag, ##__VA_ARGS__); } } #define DEBUG(format, ...) RAW_DEBUG(reborn_debug_tag, format, ##__VA_ARGS__) #define ERR(format, ...) { fprintf(stderr, "[ERR]: (%s:%i): " format "\n", __FILE__, __LINE__, ##__VA_ARGS__); exit(EXIT_FAILURE); } #define IMPOSSIBLE() ERR("This Should Never Be Called") + +#ifdef __cplusplus +} +#endif diff --git a/libreborn/src/util/exec.c b/libreborn/src/util/exec.c index b1aa21e..e692b6e 100644 --- a/libreborn/src/util/exec.c +++ b/libreborn/src/util/exec.c @@ -87,6 +87,15 @@ char *run_command(const char *const command[], int *exit_status) { close(output_pipe[0]); close(output_pipe[1]); + // Setup stderr + if (getenv("MCPI_DEBUG") == NULL) { + const char *log_file_fd_env = getenv("MCPI_LOG_FILE_FD"); + if (log_file_fd_env == NULL) { + IMPOSSIBLE(); + } + dup2(atoi(log_file_fd_env), STDERR_FILENO); + } + // Setup Environment setup_exec_environment(0); diff --git a/libreborn/src/util/log.c b/libreborn/src/util/log.c index 83bfd4f..139e253 100644 --- a/libreborn/src/util/log.c +++ b/libreborn/src/util/log.c @@ -1,4 +1,23 @@ +#include + #include // Debug Tag const char *reborn_debug_tag = ""; + +// Debug FD +int reborn_get_debug_fd() { + if (getenv("MCPI_DEBUG") != NULL) { + return STDERR_FILENO; + } else { + static int debug_fd = -1; + if (debug_fd == -1) { + const char *log_file_fd_env = getenv("MCPI_LOG_FILE_FD"); + if (log_file_fd_env == NULL) { + return -1; + } + debug_fd = atoi(log_file_fd_env); + } + return debug_fd; + } +}