From 957634c7c434b6c8d696ca8f4098e96a201fdfb0 Mon Sep 17 00:00:00 2001 From: David Härdeman Date: Fri, 26 Jun 2020 23:07:28 +0200 Subject: Allow commands to return success or not rather than just dying --- minecctl/minecctl-rcon.c | 66 ++++++++++++++++++++++++++++++------------------ minecctl/minecctl-rcon.h | 14 +++++----- minecctl/minecctl.c | 17 +++++-------- minecctl/minecctl.h | 2 +- minecctl/server.c | 9 +++++++ minecctl/server.h | 2 ++ 6 files changed, 68 insertions(+), 42 deletions(-) diff --git a/minecctl/minecctl-rcon.c b/minecctl/minecctl-rcon.c index eb8d335..c387b38 100644 --- a/minecctl/minecctl-rcon.c +++ b/minecctl/minecctl-rcon.c @@ -154,7 +154,7 @@ error: return -1; } -static void +static bool send_cmd(int sfd, const char *cmd) { char buf[4096]; @@ -163,12 +163,18 @@ send_cmd(int sfd, const char *cmd) send_msg(sfd, buf, sizeof(buf), RCON_PACKET_COMMAND, cmd, &rtype, &reply); - if (rtype != RCON_PACKET_RESPONSE) + if (rtype != RCON_PACKET_RESPONSE) { die("Invalid return code: %" PRIi32, rtype); - else if (use_colors) + return false; + } + + + if (use_colors) info("%s%s%s", ANSI_GREY, reply, ANSI_NORMAL); else info("%s", reply); + + return true; } static void @@ -234,7 +240,7 @@ get_one_status(int fd, char *buf, size_t len, const char *cmd, return false; } -void +bool do_status(struct cfg *cfg) { char buf[4096]; char tbuf[4096]; @@ -248,7 +254,7 @@ do_status(struct cfg *cfg) { server = server_get_default(cfg); fd = rcon_login(cfg, server); if (fd < 0) - return; + return false; if (get_one_status(fd, buf, sizeof(buf), "seed", 1, "Seed : [ %[^]]]", &reply, tbuf)) @@ -298,11 +304,14 @@ do_status(struct cfg *cfg) { info("Banned IPs: %u", bannedips); else if (streq(reply, "There are no bans")) info("Banned IPs: 0"); + + return true; } -void +bool do_ping(_unused_ struct cfg *cfg) { die("Not implemented"); + return false; } static bool @@ -326,14 +335,15 @@ get_player_count(int fd, unsigned *current, unsigned *max) return true; } -static void +static bool stop_one_server(struct cfg *cfg, struct server *server) { int fd; + bool rv; fd = rcon_login(cfg, server); if (fd < 0) - return; + return false; if (cfg->force_stop) { unsigned current; @@ -341,28 +351,30 @@ stop_one_server(struct cfg *cfg, struct server *server) if (!get_player_count(fd, ¤t, NULL)) { error("%s: unable to get player count, not stopping", server->name); - return; + return false; } else if (current > 0) { error("%s: has active players (use -f to force)", server->name); - return; + return false; } } info("%s: sending stop command", server->name); - send_cmd(fd, "stop"); + rv = send_cmd(fd, "stop"); close(fd); + + return rv; } -void +bool do_stop(struct cfg *cfg) { struct server *server; server = server_get_default(cfg); - stop_one_server(cfg, server); + return stop_one_server(cfg, server); } -void +bool do_stop_all(struct cfg *cfg) { struct server *server; @@ -370,9 +382,11 @@ do_stop_all(struct cfg *cfg) { server_read_config(cfg, server); stop_one_server(cfg, server); } + + return true; } -void +bool do_pcount(struct cfg *cfg) { int fd; unsigned current, max; @@ -381,15 +395,18 @@ do_pcount(struct cfg *cfg) { server = server_get_default(cfg); fd = rcon_login(cfg, server); if (fd < 0) - return; + return false; - if (get_player_count(fd, ¤t, &max)) + if (get_player_count(fd, ¤t, &max)) { info("Players: %u/%u", current, max); - else + return true; + } else { die("Failed to get player count"); + return false; + } } -void +bool do_console(struct cfg *cfg) { char *prompt; @@ -400,7 +417,7 @@ do_console(struct cfg *cfg) server = server_get_default(cfg); fd = rcon_login(cfg, server); if (fd < 0) - return; + return false; prompt = alloca(strlen(program_invocation_short_name) + STRLEN(" (") + strlen(server->name) + STRLEN("): ") + 1); @@ -431,13 +448,14 @@ do_console(struct cfg *cfg) /* The server waits for us to close the connection */ break; - xfree(cmd); + free(cmd); } xfree(cmd); + return true; } -void +bool do_command(struct cfg *cfg) { int fd; struct server *server; @@ -445,8 +463,8 @@ do_command(struct cfg *cfg) { server = server_get_default(cfg); fd = rcon_login(cfg, server); if (fd < 0) - return; + return false; - send_cmd(fd, cfg->cmdstr); + return send_cmd(fd, cfg->cmdstr); } diff --git a/minecctl/minecctl-rcon.h b/minecctl/minecctl-rcon.h index 181dc43..348845f 100644 --- a/minecctl/minecctl-rcon.h +++ b/minecctl/minecctl-rcon.h @@ -1,18 +1,18 @@ #ifndef foominecctlrconhfoo #define foominecctlrconhfoo -void do_status(struct cfg *cfg); +bool do_status(struct cfg *cfg); -void do_ping(struct cfg *cfg); +bool do_ping(struct cfg *cfg); -void do_stop(struct cfg *cfg); +bool do_stop(struct cfg *cfg); -void do_stop_all(struct cfg *cfg); +bool do_stop_all(struct cfg *cfg); -void do_pcount(struct cfg *cfg); +bool do_pcount(struct cfg *cfg); -void do_console(struct cfg *cfg); +bool do_console(struct cfg *cfg); -void do_command(struct cfg *cfg); +bool do_command(struct cfg *cfg); #endif diff --git a/minecctl/minecctl.c b/minecctl/minecctl.c index c00a994..95e3e35 100644 --- a/minecctl/minecctl.c +++ b/minecctl/minecctl.c @@ -166,7 +166,7 @@ error: return false; } -static void +static bool do_list(struct cfg *cfg) { struct server *server; @@ -175,6 +175,8 @@ do_list(struct cfg *cfg) list_for_each_entry(server, &cfg->servers, list) if (server->filename) info("%s", server->name); + + return true; } static inline void @@ -378,8 +380,7 @@ main(int argc, char **argv) struct cfg cfg = { .servers = LIST_HEAD_INIT(cfg.servers), }; - struct server *server, *tmp; - int rv = EXIT_FAILURE; + bool success = false; debug_mask = DBG_ERROR | DBG_INFO; @@ -402,18 +403,14 @@ main(int argc, char **argv) dump_config(&cfg); - /* FIXME: Should return bool */ - cfg.cmd(&cfg); - - rv = EXIT_SUCCESS; + success = cfg.cmd(&cfg); out: - list_for_each_entry_safe(server, tmp, &cfg.servers, list) - server_free(server); + server_free_all(&cfg); free_password(&cfg.rcon_password); xfree(cfg.rcon_addrstr); xfree(cfg.mc_addrstr); xfree(cfg.cmdstr); - exit(rv); + exit(success ? EXIT_SUCCESS : EXIT_FAILURE); } diff --git a/minecctl/minecctl.h b/minecctl/minecctl.h index 0b8b2cf..60b71b4 100644 --- a/minecctl/minecctl.h +++ b/minecctl/minecctl.h @@ -11,7 +11,7 @@ struct cfg { bool force_stop; /* bookkeeping */ - void (*cmd)(struct cfg *cfg); + bool (*cmd)(struct cfg *cfg); struct list_head servers; }; diff --git a/minecctl/server.c b/minecctl/server.c index d19b921..da59c8f 100644 --- a/minecctl/server.c +++ b/minecctl/server.c @@ -161,6 +161,15 @@ server_load_all_known(struct cfg *cfg) closedir(dir); } +void +server_free_all(struct cfg *cfg) +{ + struct server *server, *tmp; + + list_for_each_entry_safe(server, tmp, &cfg->servers, list) + server_free(server); +} + void server_free(struct server *server) { diff --git a/minecctl/server.h b/minecctl/server.h index 08faa9f..89ee44c 100644 --- a/minecctl/server.h +++ b/minecctl/server.h @@ -21,6 +21,8 @@ bool server_set_default(struct cfg *cfg, const char *name); void server_load_all_known(struct cfg *cfg); +void server_free_all(struct cfg *cfg); + void server_free(struct server *server); struct server *server_new(); -- cgit v1.2.3