From bf774366bd7938b488fedff6879e1e3bdb37b674 Mon Sep 17 00:00:00 2001 From: Ivan Chikish Date: Wed, 18 Dec 2024 13:52:58 +0300 Subject: [PATCH] [C++] Fix warnings, refactor listeners socket Use RTTI on listener socket. --- Makefile | 2 ++ src/daemon.cpp | 97 +++++++++++++++++++++++++++++++------------------- src/device.cpp | 2 +- src/keyd.cpp | 10 +++--- 4 files changed, 69 insertions(+), 42 deletions(-) diff --git a/Makefile b/Makefile index ebe7493..22a376b 100644 --- a/Makefile +++ b/Makefile @@ -39,6 +39,8 @@ CXXFLAGS:=-DVERSION=\"v$(VERSION)\ \($(COMMIT)\)\" \ -D_FORTIFY_SOURCE=2 \ -D_DEFAULT_SOURCE \ -Werror=format-security \ + -fno-exceptions \ + -fno-rtti \ $(CXXFLAGS) platform=$(shell uname -s) diff --git a/src/daemon.cpp b/src/daemon.cpp index 992543f..d1be256 100644 --- a/src/daemon.cpp +++ b/src/daemon.cpp @@ -27,8 +27,52 @@ static std::unique_ptr configs; static uint8_t keystate[256]; -static int listeners[32]; -static size_t nr_listeners = 0; +struct listener +{ + listener() = default; + explicit listener(int fd) + : fd(fd) + { + } + + listener(const listener&) = delete; + listener& operator=(const listener&) = delete; + + listener(listener&& r) + { + if (fd != -1) + close(fd); + std::swap(fd, r.fd); + r.fd = -1; + } + + listener& operator=(listener&& r) + { + std::swap(fd, r.fd); + return *this; + } + + ~listener() + { + if (fd != -1) + close(fd); + } + + operator int() const + { + return fd; + } + +private: + int fd = -1; +}; + +static std::vector listeners = [] { + std::vector v; + v.reserve(32); + return v; +}(); + static struct keyboard *active_kbd = NULL; static void cleanup() @@ -65,16 +109,10 @@ static void add_listener(int con) tv.tv_usec = 50000; tv.tv_sec = 0; - if (nr_listeners == ARRAY_SIZE(listeners)) { - char s[] = "Max listeners exceeded\n"; - xwrite(con, &s, sizeof s); - - close(con); - return; - } - setsockopt(con, SOL_SOCKET, SO_SNDTIMEO, &tv, sizeof tv); + ::listener listener(con); + if (active_kbd) { size_t i; struct config *config = &active_kbd->config; @@ -83,13 +121,16 @@ static void add_listener(int con) if (active_kbd->layer_state[i].active) { struct layer *layer = &config->layers[i]; - write(con, layer->type == LT_LAYOUT ? "/" : "+", 1); - write(con, layer->name.c_str(), layer->name.size()); - write(con, "\n", 1); + if (size_t r = write(listener, layer->type == LT_LAYOUT ? "/" : "+", 1); r != 1) + return; + if (size_t r = write(listener, layer->name.c_str(), layer->name.size()); r != layer->name.size()) + return; + if (size_t r = write(listener, "\n", 1); r != 1) + return; } } } - listeners[nr_listeners++] = con; + listeners.emplace_back(std::move(con)); } static void activate_leds(const struct keyboard *kbd) @@ -109,35 +150,19 @@ static void activate_leds(const struct keyboard *kbd) static void on_layer_change(const struct keyboard *kbd, const struct layer *layer, uint8_t state) { - size_t i; std::string buf = "/" + layer->name + "\n"; - int keep[ARRAY_SIZE(listeners)]; - size_t n = 0; - if (kbd->config.layer_indicator) { activate_leds(kbd); } - if (!nr_listeners) - return; - if (layer->type != LT_LAYOUT) buf[0] = state ? '+' : '-'; - for (i = 0; i < nr_listeners; i++) { - size_t nw = write(listeners[i], buf.c_str(), buf.size()); - - if (nw == buf.size()) - keep[n++] = listeners[i]; - else - close(listeners[i]); - } - - if (n != nr_listeners) { - nr_listeners = n; - memcpy(listeners, keep, n * sizeof(int)); - } + std::erase_if(listeners, [&](::listener& listener) { + size_t nw = write(listener, buf.c_str(), buf.size()); + return nw != buf.size(); + }); } static void load_configs() @@ -280,7 +305,7 @@ static void send_fail(int con, const char *fmt, ...) va_end(args); } -static int input(char *buf, size_t sz, uint32_t timeout) +static int input(char *buf, [[maybe_unused]] size_t sz, uint32_t timeout) { size_t i; uint32_t codepoint; @@ -549,7 +574,7 @@ static int event_handler(struct event *ev) return timeout; } -int run_daemon(int argc, char *argv[]) +int run_daemon(int, char *[]) { ipcfd = ipc_create_server(/* SOCKET_PATH */); if (ipcfd < 0) diff --git a/src/device.cpp b/src/device.cpp index cba1bff..ddab5d2 100644 --- a/src/device.cpp +++ b/src/device.cpp @@ -349,7 +349,7 @@ int device_grab(struct device *dev) usleep(100); } - if (ioctl(dev->fd, EVIOCGRAB, (void *) 1) < 0) { + if (ioctl(dev->fd, EVIOCGRAB, 1) < 0) { perror("EVIOCGRAB"); return -1; } diff --git a/src/keyd.cpp b/src/keyd.cpp index c40894c..78a16a7 100644 --- a/src/keyd.cpp +++ b/src/keyd.cpp @@ -37,14 +37,14 @@ static int ipc_exec(enum ipc_msg_type_e type, const char *data, size_t sz, uint3 return type == IPC_FAIL; } -static int version(int argc, char *argv[]) +static int version(int, char *[]) { printf("keyd " VERSION "\n"); return 0; } -static int help(int argc, char *argv[]) +static int help(int, char *[]) { printf("usage: keyd [-v] [-h] [command] []\n\n" "Commands:\n" @@ -60,7 +60,7 @@ static int help(int argc, char *argv[]) return 0; } -static int list_keys(int argc, char *argv[]) +static int list_keys(int, char *[]) { size_t i; @@ -161,7 +161,7 @@ static int input(int argc, char *argv[]) return ipc_exec(IPC_INPUT, buf, sz, timeout); } -static int layer_listen(int argc, char *argv[]) +static int layer_listen(int, char *[]) { struct ipc_message msg = {}; @@ -186,7 +186,7 @@ static int layer_listen(int argc, char *argv[]) } } -static int reload(int argc, char *argv[]) +static int reload(int, char *[]) { ipc_exec(IPC_RELOAD, NULL, 0, 0);