From f5787fb31f9b287458c8f90e0fb8745026da7342 Mon Sep 17 00:00:00 2001 From: Michael Vetter Date: Fri, 27 Feb 2026 20:45:14 +0100 Subject: [PATCH] cleanup: refactor account_eval_password to use glib Move from popen() to g_spawn_command_line_sync(). Which is nicer and gets rid of a resource leak that was present here. --- src/config/account.c | 65 +++++++++++++++----------------------------- 1 file changed, 22 insertions(+), 43 deletions(-) diff --git a/src/config/account.c b/src/config/account.c index afda435b..dd6eb6ad 100644 --- a/src/config/account.c +++ b/src/config/account.c @@ -39,6 +39,7 @@ #include #include #include +#include #include @@ -160,53 +161,31 @@ account_eval_password(ProfAccount* account) assert(account != NULL); assert(account->eval_password != NULL); - errno = 0; + gchar* stdout_buf = NULL; + GError* error = NULL; + gint exit_status = 0; - FILE* stream = popen(account->eval_password, "r"); - if (stream == NULL) { - const char* errmsg = strerror(errno); - if (errmsg) { - log_error("Could not execute `eval_password` command (%s).", - errmsg); - } else { - log_error("Failed to allocate memory for `eval_password` command."); + if (!g_spawn_command_line_sync(account->eval_password, &stdout_buf, NULL, &exit_status, &error)) { + log_error("Failed to execute `eval_password` command: %s", error->message); + g_error_free(error); + return FALSE; + } + + if (WIFEXITED(exit_status) && WEXITSTATUS(exit_status) == 0) { + account->password = stdout_buf; + g_strstrip(account->password); + if (account->password[0] == '\0') { + log_error("Empty password returned by `eval_password` command."); + g_free(account->password); + account->password = NULL; + return FALSE; } + return TRUE; + } else { + log_error("`eval_password` command failed with status %d", exit_status); + g_free(stdout_buf); return FALSE; } - - account->password = g_malloc(READ_BUF_SIZE); - if (!account->password) { - log_error("Failed to allocate enough memory to read `eval_password` " - "output."); - return FALSE; - } - - account->password = fgets(account->password, READ_BUF_SIZE, stream); - if (!account->password) { - log_error("Failed to read password from stream."); - return FALSE; - } - - int exit_status = pclose(stream); - if (exit_status > 0) { - log_error("Command for `eval_password` returned error status (%s).", - exit_status); - return FALSE; - } else if (exit_status < 0) { - log_error("Failed to close stream for `eval_password` command output " - "(%s).", - strerror(errno)); - return FALSE; - }; - - // Remove leading and trailing whitespace from output. - g_strstrip(account->password); - if (!account->password) { - log_error("Empty password returned by `eval_password` command."); - return FALSE; - } - - return TRUE; } void