From 6184a66a231354c7e5b1b3ef2fa8fd6e479d5a68 Mon Sep 17 00:00:00 2001 From: Daan Timmer <8293597+daantimmer@users.noreply.github.com> Date: Wed, 8 Jan 2025 13:26:39 +0100 Subject: [PATCH] feat: make all hal::Can::Id functions constexpr and add static assert tests (#803) * feat: make all hal::Can::Id functions constexpr and add static assert tests * chore: separate implementation from declaration * Update hal/interfaces/Can.hpp --- hal/interfaces/CMakeLists.txt | 1 - hal/interfaces/Can.cpp | 38 ---------------- hal/interfaces/Can.hpp | 72 +++++++++++++++++++++++------- hal/interfaces/test/TestCan.cpp | 79 ++++++++++++++++++++------------- 4 files changed, 104 insertions(+), 86 deletions(-) delete mode 100644 hal/interfaces/Can.cpp diff --git a/hal/interfaces/CMakeLists.txt b/hal/interfaces/CMakeLists.txt index fd314bdbe..081faaae4 100644 --- a/hal/interfaces/CMakeLists.txt +++ b/hal/interfaces/CMakeLists.txt @@ -16,7 +16,6 @@ target_sources(hal.interfaces PRIVATE AsyncGpio.cpp AsyncGpio.hpp BackupRam.hpp - Can.cpp Can.hpp CommunicationConfigurator.hpp DigitalToAnalogPin.hpp diff --git a/hal/interfaces/Can.cpp b/hal/interfaces/Can.cpp deleted file mode 100644 index 27e29c6c7..000000000 --- a/hal/interfaces/Can.cpp +++ /dev/null @@ -1,38 +0,0 @@ -#include "hal/interfaces/Can.hpp" - -namespace hal -{ - bool Can::Id::Is11BitId() const - { - return (id & indicator29Bit) == 0; - } - - bool Can::Id::Is29BitId() const - { - return !Is11BitId(); - } - - uint32_t Can::Id::Get11BitId() const - { - assert(Is11BitId()); - - return id; - } - - uint32_t Can::Id::Get29BitId() const - { - assert(Is29BitId()); - - return id ^ indicator29Bit; - } - - bool Can::Id::operator==(const Id& other) const - { - return id == other.id; - } - - bool Can::Id::operator!=(const Id& other) const - { - return !(*this == other); - } -} diff --git a/hal/interfaces/Can.hpp b/hal/interfaces/Can.hpp index 6b8d8b710..8977a712a 100644 --- a/hal/interfaces/Can.hpp +++ b/hal/interfaces/Can.hpp @@ -3,6 +3,7 @@ #include "infra/util/BoundedVector.hpp" #include "infra/util/Function.hpp" +#include #include namespace hal @@ -10,27 +11,20 @@ namespace hal class Can { public: - class Id + class [[nodiscard]] Id { public: - static constexpr Id Create11BitId(uint32_t id) - { - return Can::Id(id); - } + static constexpr Id Create11BitId(uint32_t id); + static constexpr Id Create29BitId(uint32_t id); - static constexpr Id Create29BitId(uint32_t id) - { - return Can::Id(id | indicator29Bit); - } + [[nodiscard]] constexpr bool Is11BitId() const; + [[nodiscard]] constexpr bool Is29BitId() const; - bool Is11BitId() const; - bool Is29BitId() const; + [[nodiscard]] constexpr uint32_t Get11BitId() const; + [[nodiscard]] constexpr uint32_t Get29BitId() const; - uint32_t Get11BitId() const; - uint32_t Get29BitId() const; - - bool operator==(const Id& other) const; - bool operator!=(const Id& other) const; + [[nodiscard]] constexpr bool operator==(const Id& other) const; + [[nodiscard]] constexpr bool operator!=(const Id& other) const; private: constexpr explicit Id(uint32_t id) @@ -38,7 +32,7 @@ namespace hal {} private: - static const uint32_t indicator29Bit = static_cast(1) << 31; + static constexpr uint32_t indicator29Bit{ 1u << 31 }; uint32_t id; }; @@ -56,6 +50,50 @@ namespace hal virtual void SendData(Id id, const Message& data, const infra::Function& actionOnCompletion) = 0; virtual void ReceiveData(const infra::Function& receivedAction) = 0; }; + + //// Implementation //// + + constexpr Can::Id Can::Id::Create11BitId(uint32_t id) + { + return Can::Id(id); + } + + constexpr Can::Id Can::Id::Create29BitId(uint32_t id) + { + return Can::Id(id | indicator29Bit); + } + + constexpr bool Can::Id::Is11BitId() const + { + return (id & indicator29Bit) == 0; + } + + constexpr bool Can::Id::Is29BitId() const + { + return !Is11BitId(); + } + + constexpr uint32_t Can::Id::Get11BitId() const + { + assert(Is11BitId()); + return id; + } + + constexpr uint32_t Can::Id::Get29BitId() const + { + assert(Is29BitId()); + return id ^ indicator29Bit; + } + + constexpr bool Can::Id::operator==(const Id& other) const + { + return id == other.id; + } + + constexpr bool Can::Id::operator!=(const Id& other) const + { + return !(*this == other); + } } #endif diff --git a/hal/interfaces/test/TestCan.cpp b/hal/interfaces/test/TestCan.cpp index 35f681179..8b93f95c2 100644 --- a/hal/interfaces/test/TestCan.cpp +++ b/hal/interfaces/test/TestCan.cpp @@ -1,46 +1,65 @@ #include "hal/interfaces/Can.hpp" +#include "gmock/gmock.h" #include "gtest/gtest.h" +static_assert(hal::Can::Id::Create11BitId(0).Is11BitId()); +static_assert(!hal::Can::Id::Create11BitId(0).Is29BitId()); +static_assert(hal::Can::Id::Create11BitId(0).Get11BitId() == 0); + +static_assert(!hal::Can::Id::Create29BitId(0).Is11BitId()); +static_assert(hal::Can::Id::Create29BitId(0).Is29BitId()); +static_assert(hal::Can::Id::Create29BitId(0).Get29BitId() == 0); + +static_assert(hal::Can::Id::Create11BitId(0) == hal::Can::Id::Create11BitId(0)); +static_assert(hal::Can::Id::Create11BitId(0) != hal::Can::Id::Create11BitId(1)); +static_assert(hal::Can::Id::Create11BitId(0) != hal::Can::Id::Create29BitId(0)); + +static_assert(hal::Can::Id::Create29BitId(2) == hal::Can::Id::Create29BitId(2)); +static_assert(hal::Can::Id::Create29BitId(2) != hal::Can::Id::Create29BitId(1)); +static_assert(hal::Can::Id::Create29BitId(2) != hal::Can::Id::Create11BitId(2)); + TEST(CanTest, generate_11_bit_id) { - auto id = hal::Can::Id::Create11BitId(0); + const auto id = hal::Can::Id::Create11BitId(0); - EXPECT_TRUE(id.Is11BitId()); - EXPECT_EQ(0, id.Get11BitId()); + EXPECT_THAT(id.Is11BitId(), testing::IsTrue()); + EXPECT_THAT(id.Is29BitId(), testing::IsFalse()); + EXPECT_THAT(id.Get11BitId(), testing::Eq(0)); } TEST(CanTest, generate_29_bit_id) { - auto id = hal::Can::Id::Create29BitId(0); + const auto id = hal::Can::Id::Create29BitId(0); - EXPECT_TRUE(id.Is29BitId()); - EXPECT_EQ(0, id.Get29BitId()); + EXPECT_THAT(id.Is29BitId(), testing::IsTrue()); + EXPECT_THAT(id.Is11BitId(), testing::IsFalse()); + EXPECT_THAT(id.Get29BitId(), testing::Eq(0)); } TEST(CanTest, test_equality_mixed) { - auto id11_0 = hal::Can::Id::Create11BitId(0); - auto id11_1 = hal::Can::Id::Create11BitId(1); - auto id29_0 = hal::Can::Id::Create29BitId(0); - auto id29_1 = hal::Can::Id::Create29BitId(1); - - EXPECT_TRUE(id11_0 == hal::Can::Id::Create11BitId(0)); - EXPECT_TRUE(id11_0 != id11_1); - EXPECT_TRUE(id11_0 != id29_0); - EXPECT_TRUE(id11_0 != id29_1); - - EXPECT_TRUE(id11_1 != id11_0); - EXPECT_TRUE(id11_1 == hal::Can::Id::Create11BitId(1)); - EXPECT_TRUE(id11_1 != id29_0); - EXPECT_TRUE(id11_1 != id29_1); - - EXPECT_TRUE(id29_0 != id11_0); - EXPECT_TRUE(id29_0 != id11_1); - EXPECT_TRUE(id29_0 == hal::Can::Id::Create29BitId(0)); - EXPECT_TRUE(id29_0 != id29_1); - - EXPECT_TRUE(id29_1 != id11_0); - EXPECT_TRUE(id29_1 != id11_1); - EXPECT_TRUE(id29_1 != id29_0); - EXPECT_TRUE(id29_1 == hal::Can::Id::Create29BitId(1)); + const auto id11_0 = hal::Can::Id::Create11BitId(0); + const auto id11_1 = hal::Can::Id::Create11BitId(1); + const auto id29_0 = hal::Can::Id::Create29BitId(0); + const auto id29_1 = hal::Can::Id::Create29BitId(1); + + EXPECT_THAT(id11_0, testing::Eq(hal::Can::Id::Create11BitId(0))); + EXPECT_THAT(id11_0, testing::Ne(id11_1)); + EXPECT_THAT(id11_0, testing::Ne(id29_0)); + EXPECT_THAT(id11_0, testing::Ne(id29_1)); + + EXPECT_THAT(id11_1, testing::Ne(id11_0)); + EXPECT_THAT(id11_1, testing::Eq(hal::Can::Id::Create11BitId(1))); + EXPECT_THAT(id11_1, testing::Ne(id29_0)); + EXPECT_THAT(id11_1, testing::Ne(id29_1)); + + EXPECT_THAT(id29_0, testing::Ne(id11_0)); + EXPECT_THAT(id29_0, testing::Ne(id11_1)); + EXPECT_THAT(id29_0, testing::Eq(hal::Can::Id::Create29BitId(0))); + EXPECT_THAT(id29_0, testing::Ne(id29_1)); + + EXPECT_THAT(id29_1, testing::Ne(id11_0)); + EXPECT_THAT(id29_1, testing::Ne(id11_1)); + EXPECT_THAT(id29_1, testing::Ne(id29_0)); + EXPECT_THAT(id29_1, testing::Eq(hal::Can::Id::Create29BitId(1))); }