From 680affd1fea519a288a1d6e20d77c3404031c260 Mon Sep 17 00:00:00 2001 From: Stenzek Date: Thu, 25 May 2023 19:56:04 +1000 Subject: [PATCH] Common: Add ByteSwap.h Provides a C++23-like std::byteswap implementation. --- common/ByteSwap.h | 56 +++++++++++++++++++++++++++ common/CMakeLists.txt | 1 + common/common.vcxproj | 1 + common/common.vcxproj.filters | 3 ++ tests/ctest/common/CMakeLists.txt | 1 + tests/ctest/common/byteswap_tests.cpp | 26 +++++++++++++ 6 files changed, 88 insertions(+) create mode 100644 common/ByteSwap.h create mode 100644 tests/ctest/common/byteswap_tests.cpp diff --git a/common/ByteSwap.h b/common/ByteSwap.h new file mode 100644 index 0000000000..b1196a3773 --- /dev/null +++ b/common/ByteSwap.h @@ -0,0 +1,56 @@ +/* PCSX2 - PS2 Emulator for PCs + * Copyright (C) 2023 PCSX2 Dev Team + * + * PCSX2 is free software: you can redistribute it and/or modify it under the terms + * of the GNU Lesser General Public License as published by the Free Software Found- + * ation, either version 3 of the License, or (at your option) any later version. + * + * PCSX2 is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; + * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR + * PURPOSE. See the GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along with PCSX2. + * If not, see . + */ + +#pragma once + +#include +#include + +#ifdef _MSC_VER +#include +#endif + +template +T ByteSwap(T value) +{ + if constexpr (std::is_signed_v) + { + return static_cast(ByteSwap(std::make_unsigned_t(value))); + } + else if constexpr (std::is_same_v) + { +#ifdef _MSC_VER + return _byteswap_ushort(value); +#else + return __builtin_bswap16(value); +#endif + } + else if constexpr (std::is_same_v) + { +#ifdef _MSC_VER + return _byteswap_ulong(value); +#else + return __builtin_bswap32(value); +#endif + } + else if constexpr (std::is_same_v) + { +#ifdef _MSC_VER + return _byteswap_uint64(value); +#else + return __builtin_bswap64(value); +#endif + } +} diff --git a/common/CMakeLists.txt b/common/CMakeLists.txt index eeee867614..f679aaff7e 100644 --- a/common/CMakeLists.txt +++ b/common/CMakeLists.txt @@ -64,6 +64,7 @@ target_sources(common PRIVATE AlignedMalloc.h Assertions.h boost_spsc_queue.hpp + ByteSwap.h Console.h CrashHandler.h DynamicLibrary.h diff --git a/common/common.vcxproj b/common/common.vcxproj index 14d76822a2..291418bf61 100644 --- a/common/common.vcxproj +++ b/common/common.vcxproj @@ -104,6 +104,7 @@ + diff --git a/common/common.vcxproj.filters b/common/common.vcxproj.filters index 19e1d6b590..ab75569ef9 100644 --- a/common/common.vcxproj.filters +++ b/common/common.vcxproj.filters @@ -351,6 +351,9 @@ Header Files + + Header Files + diff --git a/tests/ctest/common/CMakeLists.txt b/tests/ctest/common/CMakeLists.txt index 80d10dd400..7d2c00d27f 100644 --- a/tests/ctest/common/CMakeLists.txt +++ b/tests/ctest/common/CMakeLists.txt @@ -1,4 +1,5 @@ add_pcsx2_test(common_test + byteswap_tests.cpp path_tests.cpp string_util_tests.cpp x86emitter/codegen_tests.cpp diff --git a/tests/ctest/common/byteswap_tests.cpp b/tests/ctest/common/byteswap_tests.cpp new file mode 100644 index 0000000000..501c94b117 --- /dev/null +++ b/tests/ctest/common/byteswap_tests.cpp @@ -0,0 +1,26 @@ +/* PCSX2 - PS2 Emulator for PCs + * Copyright (C) 2023 PCSX2 Dev Team + * + * PCSX2 is free software: you can redistribute it and/or modify it under the terms + * of the GNU Lesser General Public License as published by the Free Software Found- + * ation, either version 3 of the License, or (at your option) any later version. + * + * PCSX2 is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; + * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR + * PURPOSE. See the GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along with PCSX2. + * If not, see . + */ + +#include "common/Pcsx2Defs.h" +#include "common/ByteSwap.h" +#include + +TEST(ByteSwap, ByteSwap) +{ + ASSERT_EQ(ByteSwap(static_cast(0xabcd)), 0xcdabu); + ASSERT_EQ(ByteSwap(static_cast(0xabcdef01)), 0x01efcdabu); + ASSERT_EQ(ByteSwap(static_cast(0xabcdef0123456789ULL)), 0x8967452301efcdabu); + ASSERT_EQ(ByteSwap(static_cast(0x80123456)), 0x56341280); +}