summaryrefslogtreecommitdiff
path: root/util.h
diff options
context:
space:
mode:
authorMikhail Burakov <mburakov@mailbox.org>2024-11-18 06:34:31 +0100
committerMikhail Burakov <mburakov@mailbox.org>2024-11-18 06:34:31 +0100
commit5be09d7edff924e7486d743e9d15edf07f555341 (patch)
tree064680d394732b0d1c00bfbbbb1ce3d5ed3d6e5e /util.h
parent8a93cfdc03683eedc270bae957288af853f22a61 (diff)
WIPnext
Diffstat (limited to 'util.h')
-rw-r--r--util.h48
1 files changed, 41 insertions, 7 deletions
diff --git a/util.h b/util.h
index 62e7c4e..bba74a2 100644
--- a/util.h
+++ b/util.h
@@ -18,15 +18,49 @@
#ifndef STREAMER_UTIL_H_
#define STREAMER_UTIL_H_
-#define MIN(a, b) ((a) < (b) ? (a) : (b))
-#define MAX(a, b) ((a) > (b) ? (a) : (b))
-
-#define LENGTH(x) (sizeof(x) / sizeof *(x))
-
#define STR_IMPL(x) #x
#define STR(x) STR_IMPL(x)
+#define FROM_HERE __FILE__ ":" STR(__LINE__) " "
+
+template <class T>
+struct Defer {
+ Defer(T&& op) : op_{op} {}
+ ~Defer() { op_(); }
+ const T& op_;
+};
+
+template <class T>
+Defer(T&&) -> Defer<T>;
+
+template <auto dflt, auto closer>
+struct PodCloser {
+ struct pointer {
+ decltype(dflt) value_;
+ pointer() : value_{dflt} {}
+ pointer(decltype(nullptr)) : value_{dflt} {}
+ pointer(decltype(dflt) value) : value_{value} {}
+ explicit operator bool() const { return value_ != dflt; }
+ friend bool operator==(pointer, pointer) = default;
+ operator decltype(dflt)() const { return value_; }
+ };
+ void operator()(const pointer ptr) {
+ if (ptr.value_ != dflt) closer(ptr.value_);
+ }
+};
+
+template <class T>
+struct ClassOf;
+
+template <class R, class C>
+struct ClassOf<R C::*> {
+ using T = C;
+};
-#define LOG(x, ...) \
- fprintf(stderr, __FILE__ ":" STR(__LINE__) " " x "\n", ##__VA_ARGS__)
+template <auto fun, class T, class... Args>
+inline auto Trampoline(T* head, Args... tail) {
+ using C = ClassOf<decltype(fun)>::T;
+ auto self = static_cast<C*>(head);
+ return (self->*fun)(tail...);
+}
#endif // STREAMER_UTIL_H_