summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSteven Le Rouzic <steven.lerouzic@gmail.com>2025-03-18 22:31:59 +0100
committerSteven Le Rouzic <steven.lerouzic@gmail.com>2025-03-18 22:39:35 +0100
commit4884b594330dea41d04d776d14a5cb18d9a354bc (patch)
treeb159defa21f10017baab0800c3848b3e9706940c
parenta7475b6af21717f59c1b3d0dcb0fd6c1198a9fdc (diff)
Make status implementation more correct wrt type punning
-rw-r--r--asl/base/utility.hpp7
-rw-r--r--asl/containers/buffer.hpp4
-rw-r--r--asl/types/status.cpp21
-rw-r--r--asl/types/status.hpp8
-rw-r--r--todo.txt4
5 files changed, 26 insertions, 18 deletions
diff --git a/asl/base/utility.hpp b/asl/base/utility.hpp
index 206a5b1..85c873d 100644
--- a/asl/base/utility.hpp
+++ b/asl/base/utility.hpp
@@ -35,6 +35,13 @@ template<typename T, typename U>
return static_cast<return_type>(x);
}
+template<typename T>
+[[nodiscard]] constexpr T* launder(T* ptr) noexcept // NOLINT
+ requires (!asl::is_func<T> && !asl::is_void<T>)
+{
+ return __builtin_launder(ptr);
+}
+
} // namespace std
namespace asl
diff --git a/asl/containers/buffer.hpp b/asl/containers/buffer.hpp
index c3d865f..f5ba975 100644
--- a/asl/containers/buffer.hpp
+++ b/asl/containers/buffer.hpp
@@ -110,7 +110,9 @@ private:
constexpr void set_size_inline(isize_t new_size)
{
ASL_ASSERT(new_size >= 0 && new_size <= kInlineCapacity);
- const size_t size_encoded = (load_size_encoded() & size_t{0x00ff'ffff'ffff'ffff}) | (bit_cast<size_t>(new_size) << 56U);
+ const size_t size_encoded =
+ (load_size_encoded() & size_t{0x00ff'ffff'ffff'ffff})
+ | (bit_cast<size_t>(new_size) << 56U);
store_size_encoded(size_encoded);
}
diff --git a/asl/types/status.cpp b/asl/types/status.cpp
index 43f3b9e..246d017 100644
--- a/asl/types/status.cpp
+++ b/asl/types/status.cpp
@@ -15,7 +15,7 @@ using Allocator = asl::DefaultAllocator;
// NOLINTNEXTLINE(*-non-const-global-variables)
static Allocator g_allocator{};
-namespace
+namespace asl
{
struct StatusInternal
@@ -33,7 +33,7 @@ struct StatusInternal
}
};
-} // anonymous namespace
+} // namespace asl
asl::status::status(status_code code, string_view msg)
: m_payload{alloc_new<StatusInternal>(g_allocator, msg, code)}
@@ -49,34 +49,29 @@ asl::status::status(status_code code, string_view fmt, span<format_internals::ty
asl::status_code asl::status::code_internal() const
{
ASL_ASSERT(!is_inline());
- // NOLINTNEXTLINE(*-reinterpret-cast)
- return reinterpret_cast<const StatusInternal*>(m_payload)->code;
+ return m_payload->code;
}
asl::string_view asl::status::message_internal() const
{
ASL_ASSERT(!is_inline());
- // NOLINTNEXTLINE(*-reinterpret-cast)
- return reinterpret_cast<const StatusInternal*>(m_payload)->msg;
+ return m_payload->msg;
}
void asl::status::ref()
{
ASL_ASSERT(!is_inline());
- // NOLINTNEXTLINE(*-reinterpret-cast)
- auto* internal = reinterpret_cast<StatusInternal*>(m_payload);
- atomic_fetch_increment(&internal->ref_count, memory_order::relaxed);
+ atomic_fetch_increment(&m_payload->ref_count, memory_order::relaxed);
}
void asl::status::unref()
{
ASL_ASSERT(!is_inline());
- // NOLINTNEXTLINE(*-reinterpret-cast)
- auto* internal = reinterpret_cast<StatusInternal*>(m_payload);
- if (atomic_fetch_decrement(&internal->ref_count, memory_order::release) == 1)
+ if (atomic_fetch_decrement(&m_payload->ref_count, memory_order::release) == 1)
{
atomic_fence(memory_order::acquire);
- alloc_delete(g_allocator, internal);
+ alloc_delete(g_allocator, m_payload);
+ m_payload = nullptr;
}
}
diff --git a/asl/types/status.hpp b/asl/types/status.hpp
index df96cd8..de95670 100644
--- a/asl/types/status.hpp
+++ b/asl/types/status.hpp
@@ -22,15 +22,17 @@ enum class status_code : uint8_t
invalid_argument = 4,
};
+struct StatusInternal;
+
class status
{
- void* m_payload{};
+ StatusInternal* m_payload{};
- static constexpr void* status_to_payload(status_code code)
+ static constexpr StatusInternal* status_to_payload(status_code code)
{
return code == status_code::ok
? nullptr
- : bit_cast<void*>((static_cast<uintptr_t>(code) << 1) | 1);
+ : bit_cast<StatusInternal*>((static_cast<uintptr_t>(code) << 1) | 1);
}
static constexpr status_code payload_to_status(void* payload)
diff --git a/todo.txt b/todo.txt
index 8b13789..2dfd0c1 100644
--- a/todo.txt
+++ b/todo.txt
@@ -1 +1,3 @@
-
+review unions
+review reinterpret_cast
+review as_bytes & static_cast in general