From aa73023bee1aebc745188e54039d3bf567be97e3 Mon Sep 17 00:00:00 2001 From: Steven Le Rouzic Date: Thu, 20 Feb 2025 23:47:02 +0100 Subject: Use intrusive list in logging, and add defer --- asl/base/BUILD.bazel | 2 ++ asl/base/defer.hpp | 50 ++++++++++++++++++++++++++++++++++++++++++++++++ asl/base/defer_tests.cpp | 32 +++++++++++++++++++++++++++++++ asl/base/utility.hpp | 3 +++ 4 files changed, 87 insertions(+) create mode 100644 asl/base/defer.hpp create mode 100644 asl/base/defer_tests.cpp (limited to 'asl/base') diff --git a/asl/base/BUILD.bazel b/asl/base/BUILD.bazel index 317c20b..3dc715b 100644 --- a/asl/base/BUILD.bazel +++ b/asl/base/BUILD.bazel @@ -4,6 +4,7 @@ cc_library( "annotations.hpp", "assert.hpp", "config.hpp", + "defer.hpp", "float.hpp", "functional.hpp", "integers.hpp", @@ -28,6 +29,7 @@ cc_library( "//asl/types:box", ], ) for name in [ + "defer", "float", "functional", "integers", diff --git a/asl/base/defer.hpp b/asl/base/defer.hpp new file mode 100644 index 0000000..b6d52af --- /dev/null +++ b/asl/base/defer.hpp @@ -0,0 +1,50 @@ +#pragma once + +#include "asl/base/utility.hpp" +#include "asl/base/functional.hpp" + +namespace asl +{ + +// @Todo Add invokable check +template +class DeferCallback +{ + Callback m_callback; + bool m_moved = false; + +public: + template + explicit DeferCallback(T&& callback) : m_callback(ASL_FWD(callback)) + { + } + + ASL_DELETE_COPY(DeferCallback); + + DeferCallback(DeferCallback&& other) : + m_callback(ASL_MOVE(other.m_callback)), m_moved(exchange(other.m_moved, true)) + { + } + + DeferCallback& operator=(DeferCallback&&) = delete; + + ~DeferCallback() + { + if (!m_moved) { invoke(m_callback); } + } +}; + +struct DeferFactory +{ + // @Todo Add invokable check + template + DeferCallback operator<<(Callback&& callback) const + { + return DeferCallback(ASL_FWD(callback)); + } +}; + +} // namespace asl + +#define ASL_DEFER auto ASL_CONCAT(_defer_, __COUNTER__) = ::asl::DeferFactory{} << + diff --git a/asl/base/defer_tests.cpp b/asl/base/defer_tests.cpp new file mode 100644 index 0000000..b5139d5 --- /dev/null +++ b/asl/base/defer_tests.cpp @@ -0,0 +1,32 @@ +#include "asl/base/defer.hpp" +#include "asl/testing/testing.hpp" + +ASL_TEST(defer) +{ + uint32_t a = 0; + + { + ASL_DEFER [&a]() { a |= 1; }; + ASL_TEST_EXPECT(a == 0); + + { + ASL_DEFER [&a]() { a |= 2; }; + ASL_DEFER [&a]() { a |= 4; }; + ASL_TEST_EXPECT(a == 0); + } + + ASL_TEST_EXPECT(a == 6); + + { + ASL_DEFER [&a]() { a |= 8; }; + ASL_TEST_EXPECT(a == 6); + } + + ASL_TEST_EXPECT(a == 14); + + ASL_DEFER [&a]() { a |= 16; }; + ASL_TEST_EXPECT(a == 14); + } + + ASL_TEST_EXPECT(a == 31); +} diff --git a/asl/base/utility.hpp b/asl/base/utility.hpp index c03554f..b3fb36b 100644 --- a/asl/base/utility.hpp +++ b/asl/base/utility.hpp @@ -92,4 +92,7 @@ constexpr bool is_pow2(isize_t v) ASL_DEFAULT_COPY(T) \ ASL_DEFAULT_MOVE(T) +#define ASL_CONCAT2(A, B) A##B +#define ASL_CONCAT(A, B) ASL_CONCAT2(A, B) + } // namespace asl -- cgit