From 06bdde635fa68dc2a24ecc14c703e27a0ca54d79 Mon Sep 17 00:00:00 2001 From: dec05eba Date: Sat, 2 May 2026 00:26:53 +0200 Subject: [PATCH] gsr-game-tracker: dont let applications slip through --- tools/gsr-game-tracker/main.c | 49 +++++++++++++++++++++++++++-------- 1 file changed, 38 insertions(+), 11 deletions(-) diff --git a/tools/gsr-game-tracker/main.c b/tools/gsr-game-tracker/main.c index 584c5c0..43496da 100644 --- a/tools/gsr-game-tracker/main.c +++ b/tools/gsr-game-tracker/main.c @@ -8,6 +8,7 @@ #include #include #include +#include #include #include #include @@ -50,9 +51,7 @@ static void add_game(pid_t pid) { } } -static void remove_game(pid_t pid) { - int slot = find_slot_by_pid(pid); - if (slot < 0) return; +static void remove_game_by_slot(int slot) { games[slot] = 0; if (--game_count == 0) { printf("Game exited\n"); @@ -60,12 +59,18 @@ static void remove_game(pid_t pid) { } } +static void remove_game(pid_t pid) { + int slot = find_slot_by_pid(pid); + if (slot < 0) return; + remove_game_by_slot(slot); +} + static ssize_t read_file(const char *path, char *buf, size_t size) { int fd = open(path, O_RDONLY); if (fd < 0) return -1; ssize_t n = read(fd, buf, size - 1); close(fd); - if (n > 0) buf[n] = '\0'; + if (n >= 0) buf[n] = '\0'; return n; } @@ -180,8 +185,7 @@ static void check_process(pid_t pid) { size_t process_basename_len = 0; const char *process_basename = process_get_basename(argv0, argv0_len, &process_basename_len); - if (cmd_n > 0 - && (is_wine_binary(process_basename, process_basename_len) + if ((is_wine_binary(process_basename, process_basename_len) || has_game_arch_suffix(process_basename, process_basename_len) || has_wine_env || is_process_name_native_game(process_basename, process_basename_len)) @@ -231,6 +235,8 @@ static void process_netlink_msg(const char *buf, size_t len) { continue; if (cn->len < sizeof(struct proc_event)) continue; + if ((size_t)(nl->nlmsg_len - NLMSG_HDRLEN - sizeof(struct cn_msg)) < cn->len) + continue; handle_proc_event((const struct proc_event *)cn->data); } } @@ -283,6 +289,13 @@ static int setup_netlink(void) { return sock; } +static void sweep_dead_games(void) { + for (int i = 0; i < MAX_GAMES; i++) { + if (games[i] && kill(games[i], 0) < 0 && errno == ESRCH) + remove_game_by_slot(games[i]); + } +} + static void scan_existing_processes(void) { DIR *d = opendir("/proc"); if (!d) return; @@ -312,13 +325,27 @@ int main(void) { scan_existing_processes(); for (;;) { - ssize_t n = recv(sock, recv_buf, sizeof(recv_buf), 0); + ssize_t n = recv(sock, recv_buf, sizeof(recv_buf), MSG_TRUNC); if (n < 0) { - if (errno == EINTR) continue; - if (errno == ENOBUFS) { scan_existing_processes(); continue; } - perror("recv"); - break; + if (errno == EINTR) { + continue; + } else if (errno == ENOBUFS) { + sweep_dead_games(); + scan_existing_processes(); + continue; + } else { + perror("recv"); + break; + } } + + if ((size_t)n > sizeof(recv_buf)) { + /* Datagram larger than recv_buf was truncated; we may have lost events. */ + sweep_dead_games(); + scan_existing_processes(); + continue; + } + process_netlink_msg(recv_buf, (size_t)n); }