From 309fd8221a8d62227cf8d0633bec57c0834e5934 Mon Sep 17 00:00:00 2001
From: patrick96
Date: Sun, 12 Sep 2021 15:42:30 +0200
Subject: [PATCH] Create wrapper for uv_pipe_t
---
include/components/controller.hpp | 2 +-
include/components/eventloop.hpp | 81 +++++++++++++++++--------------
src/components/controller.cpp | 33 ++-----------
src/components/eventloop.cpp | 2 +-
4 files changed, 49 insertions(+), 69 deletions(-)
diff --git a/include/components/controller.hpp b/include/components/controller.hpp
index b3dcf28d..4370d3c3 100644
--- a/include/components/controller.hpp
+++ b/include/components/controller.hpp
@@ -3,8 +3,8 @@
#include
#include
-#include
#include
+#include
#include "common.hpp"
#include "components/eventloop.hpp"
diff --git a/include/components/eventloop.hpp b/include/components/eventloop.hpp
index 9f3cdf40..89694e84 100644
--- a/include/components/eventloop.hpp
+++ b/include/components/eventloop.hpp
@@ -13,12 +13,13 @@ POLYBAR_NS
* Runs any libuv function with an integer error code return value and throws an
* exception on error.
*/
-#define UV(fun, ...) \
- do { \
- int res = fun(__VA_ARGS__); \
- if (res < 0) { \
- throw std::runtime_error("libuv error for '" #fun "': "s + uv_strerror(res)); \
- } \
+#define UV(fun, ...) \
+ do { \
+ int res = fun(__VA_ARGS__); \
+ if (res < 0) { \
+ throw std::runtime_error( \
+ __FILE__ ":"s + std::to_string(__LINE__) + ": libuv error for '" #fun "': "s + uv_strerror(res)); \
+ } \
} while (0);
template
@@ -31,6 +32,10 @@ struct cb_helper {
}
};
+/**
+ * \tparam H Type of the handle
+ * \tparam I Type of the handle passed to the callback. Often the same as H, but not always (e.g. uv_read_start)
+ */
template
struct UVHandleGeneric {
UVHandleGeneric(std::function fun) {
@@ -81,43 +86,45 @@ struct FSEventHandle : public UVHandle {
};
struct PipeHandle : public UVHandleGeneric {
- PipeHandle(uv_loop_t* loop, std::function fun)
- : UVHandleGeneric([&](ssize_t nread, const uv_buf_t* buf) {
- if (nread > 0) {
- string payload = string(buf->base, nread);
- logger::make().notice("Bytes read: %d: '%s'", nread, payload);
- fun(std::move(payload));
- } else if (nread < 0) {
- if (nread != UV_EOF) {
- logger::make().err("Read error: %s", uv_err_name(nread));
- uv_close((uv_handle_t*)handle.get(), nullptr);
- } else {
- UV(
- uv_read_start, (uv_stream_t*)handle.get(),
- [](uv_handle_t*, size_t, uv_buf_t* buf) {
- buf->base = new char[BUFSIZ];
- buf->len = BUFSIZ;
- },
- &cb.callback);
- }
- }
+ std::function func;
- if (buf->base) {
- delete[] buf->base;
- }
- }) {
+ int fd;
+
+ PipeHandle(uv_loop_t* loop, std::function fun)
+ : UVHandleGeneric([&](ssize_t nread, const uv_buf_t* buf) { read_cb(nread, buf); }), func(fun) {
UV(uv_pipe_init, loop, handle.get(), false);
}
void start(int fd) {
+ this->fd = fd;
UV(uv_pipe_open, handle.get(), fd);
- UV(
- uv_read_start, (uv_stream_t*)handle.get(),
- [](uv_handle_t*, size_t, uv_buf_t* buf) {
- buf->base = new char[BUFSIZ];
- buf->len = BUFSIZ;
- },
- &cb.callback);
+ UV(uv_read_start, (uv_stream_t*)handle.get(), alloc_cb, &cb.callback);
+ }
+
+ static void alloc_cb(uv_handle_t*, size_t, uv_buf_t* buf) {
+ buf->base = new char[BUFSIZ];
+ buf->len = BUFSIZ;
+ }
+
+ void read_cb(ssize_t nread, const uv_buf_t* buf) {
+ auto log = logger::make();
+ if (nread > 0) {
+ string payload = string(buf->base, nread);
+ log.notice("Bytes read: %d: '%s'", nread, payload);
+ func(payload);
+ } else if (nread < 0) {
+ if (nread != UV_EOF) {
+ log.err("Read error: %s", uv_err_name(nread));
+ uv_close((uv_handle_t*)handle.get(), nullptr);
+ } else {
+ // TODO this causes constant EOFs
+ start(this->fd);
+ }
+ }
+
+ if (buf->base) {
+ delete[] buf->base;
+ }
}
};
diff --git a/src/components/controller.cpp b/src/components/controller.cpp
index 0f7a32f7..18d52fc9 100644
--- a/src/components/controller.cpp
+++ b/src/components/controller.cpp
@@ -237,30 +237,6 @@ void controller::notifier_handler() {
}
}
-static void ipc_alloc_cb(uv_handle_t*, size_t, uv_buf_t* buf) {
- buf->base = new char[BUFSIZ];
- buf->len = BUFSIZ;
-}
-
-static void ipc_read_cb_wrapper(uv_stream_t* stream, ssize_t nread, const uv_buf_t* buf) {
- if (nread > 0) {
- string payload = string(buf->base, nread);
- logger::make().notice("Bytes read: %d: '%s'", nread, payload);
- static_cast(stream->data)->ipc_cb(std::move(payload));
- } else if (nread < 0) {
- if (nread != UV_EOF) {
- fprintf(stderr, "Read error %s\n", uv_err_name(nread));
- uv_close((uv_handle_t*)stream, nullptr);
- } else {
- uv_read_start(stream, ipc_alloc_cb, ipc_read_cb_wrapper);
- }
- }
-
- if (buf->base) {
- delete[] buf->base;
- }
-}
-
static void notifier_cb_wrapper(uv_async_t* handle) {
static_cast(handle->data)->notifier_handler();
}
@@ -284,7 +260,7 @@ void controller::read_events(bool confwatch) {
m_bar->start();
}
- auto ipc_handle = std::unique_ptr(nullptr);
+ auto ipc_handle = std::unique_ptr(nullptr);
auto screenshot_timer_handle = std::unique_ptr(nullptr);
try {
@@ -304,11 +280,8 @@ void controller::read_events(bool confwatch) {
}
if (m_ipc) {
- ipc_handle = std::make_unique();
- UV(uv_pipe_init, loop, ipc_handle.get(), false);
- ipc_handle->data = this;
- UV(uv_pipe_open, ipc_handle.get(), m_ipc->get_file_descriptor());
- UV(uv_read_start, (uv_stream_t*)ipc_handle.get(), ipc_alloc_cb, ipc_read_cb_wrapper);
+ ipc_handle = std::make_unique(loop, [this](const string payload) { ipc_cb(payload); });
+ ipc_handle->start(m_ipc->get_file_descriptor());
}
m_notifier = std::make_unique();
diff --git a/src/components/eventloop.cpp b/src/components/eventloop.cpp
index da7dad97..c70254bc 100644
--- a/src/components/eventloop.cpp
+++ b/src/components/eventloop.cpp
@@ -30,7 +30,7 @@ eventloop::~eventloop() {
close_loop(m_loop.get());
UV(uv_loop_close, m_loop.get());
} catch (const std::exception& e) {
- // TODO log error
+ logger::make().err("%s", e.what());
}
m_loop.reset();