From 501b884661b4dbd054fc0671fc8c648886f18f4e Mon Sep 17 00:00:00 2001 From: lizzie Date: Fri, 3 Apr 2026 03:47:48 +0000 Subject: [PATCH] Revert "[dynarmic] Remove last FPT LUT table, removing around 30kb worth of unused functions (#3718)" This reverts commit 24fe223692af988770bcc336d5b1138a2ba91399. --- src/dynarmic/src/dynarmic/CMakeLists.txt | 1 + .../emit_arm64_vector_floating_point.cpp | 3 +- .../backend/x64/emit_x64_floating_point.cpp | 1 + .../x64/emit_x64_vector_floating_point.cpp | 57 +++++++------------ .../src/dynarmic/common/lut_from_list.h | 55 ++++++++++++++++++ 5 files changed, 81 insertions(+), 36 deletions(-) create mode 100644 src/dynarmic/src/dynarmic/common/lut_from_list.h diff --git a/src/dynarmic/src/dynarmic/CMakeLists.txt b/src/dynarmic/src/dynarmic/CMakeLists.txt index f79d18c15a..5d6c05b7c9 100644 --- a/src/dynarmic/src/dynarmic/CMakeLists.txt +++ b/src/dynarmic/src/dynarmic/CMakeLists.txt @@ -59,6 +59,7 @@ add_library(dynarmic STATIC common/fp/util.h common/llvm_disassemble.cpp common/llvm_disassemble.h + common/lut_from_list.h common/math_util.cpp common/math_util.h common/safe_ops.h diff --git a/src/dynarmic/src/dynarmic/backend/arm64/emit_arm64_vector_floating_point.cpp b/src/dynarmic/src/dynarmic/backend/arm64/emit_arm64_vector_floating_point.cpp index 557d6284ed..9aff36944b 100644 --- a/src/dynarmic/src/dynarmic/backend/arm64/emit_arm64_vector_floating_point.cpp +++ b/src/dynarmic/src/dynarmic/backend/arm64/emit_arm64_vector_floating_point.cpp @@ -1,4 +1,4 @@ -// SPDX-FileCopyrightText: Copyright 2026 Eden Emulator Project +// SPDX-FileCopyrightText: Copyright 2025 Eden Emulator Project // SPDX-License-Identifier: GPL-3.0-or-later /* This file is part of the dynarmic project. @@ -25,6 +25,7 @@ #include "dynarmic/common/fp/info.h" #include "dynarmic/common/fp/op.h" #include "dynarmic/common/fp/rounding_mode.h" +#include "dynarmic/common/lut_from_list.h" #include "dynarmic/ir/basic_block.h" #include "dynarmic/ir/microinstruction.h" #include "dynarmic/ir/opcodes.h" diff --git a/src/dynarmic/src/dynarmic/backend/x64/emit_x64_floating_point.cpp b/src/dynarmic/src/dynarmic/backend/x64/emit_x64_floating_point.cpp index 6a3ab005f3..be9a1450a7 100644 --- a/src/dynarmic/src/dynarmic/backend/x64/emit_x64_floating_point.cpp +++ b/src/dynarmic/src/dynarmic/backend/x64/emit_x64_floating_point.cpp @@ -25,6 +25,7 @@ #include "dynarmic/common/fp/info.h" #include "dynarmic/common/fp/op.h" #include "dynarmic/common/fp/rounding_mode.h" +#include "dynarmic/common/lut_from_list.h" #include "dynarmic/interface/optimization_flags.h" #include "dynarmic/ir/basic_block.h" #include "dynarmic/ir/microinstruction.h" diff --git a/src/dynarmic/src/dynarmic/backend/x64/emit_x64_vector_floating_point.cpp b/src/dynarmic/src/dynarmic/backend/x64/emit_x64_vector_floating_point.cpp index 046ecc78d6..d219124208 100644 --- a/src/dynarmic/src/dynarmic/backend/x64/emit_x64_vector_floating_point.cpp +++ b/src/dynarmic/src/dynarmic/backend/x64/emit_x64_vector_floating_point.cpp @@ -26,6 +26,7 @@ #include "dynarmic/common/fp/op.h" #include "dynarmic/common/fp/rounding_mode.h" #include "dynarmic/common/fp/util.h" +#include "dynarmic/common/lut_from_list.h" #include "dynarmic/interface/optimization_flags.h" #include "dynarmic/ir/basic_block.h" #include "dynarmic/ir/microinstruction.h" @@ -2107,42 +2108,28 @@ void EmitFPVectorToFixed(BlockOfCode& code, EmitContext& ctx, IR::Inst* inst) { return; } - using FPT = mcl::unsigned_integer_of_size; // WORKAROUND: For issue 678 on MSVC - auto const func = [rounding]() -> void(*)(VectorArray& output, const VectorArray& input, FP::FPCR fpcr, FP::FPSR& fpsr) { - switch (rounding) { - case FP::RoundingMode::ToNearest_TieEven: - return [](VectorArray& output, const VectorArray& input, FP::FPCR fpcr, FP::FPSR& fpsr) { + using fbits_list = mp::lift_sequence>; + using rounding_list = mp::list< + mp::lift_value, + mp::lift_value, + mp::lift_value, + mp::lift_value, + mp::lift_value>; + + static const auto lut = Common::GenerateLookupTableFromList([](I) { + using FPT = mcl::unsigned_integer_of_size; // WORKAROUND: For issue 678 on MSVC + return std::pair{ + mp::lower_to_tuple_v, + Common::FptrCast([](VectorArray& output, const VectorArray& input, FP::FPCR fpcr, FP::FPSR& fpsr) { + constexpr size_t fbits = mp::get<0, I>::value; + constexpr FP::RoundingMode rounding_mode = mp::get<1, I>::value; for (size_t i = 0; i < output.size(); ++i) - output[i] = FPT(FP::FPToFixed(fsize, input[i], fsize, unsigned_, fpcr, FP::RoundingMode::ToNearest_TieEven, fpsr)); - }; - case FP::RoundingMode::TowardsPlusInfinity: - return [](VectorArray& output, const VectorArray& input, FP::FPCR fpcr, FP::FPSR& fpsr) { - for (size_t i = 0; i < output.size(); ++i) - output[i] = FPT(FP::FPToFixed(fsize, input[i], fsize, unsigned_, fpcr, FP::RoundingMode::TowardsPlusInfinity, fpsr)); - }; - case FP::RoundingMode::TowardsMinusInfinity: - return [](VectorArray& output, const VectorArray& input, FP::FPCR fpcr, FP::FPSR& fpsr) { - for (size_t i = 0; i < output.size(); ++i) - output[i] = FPT(FP::FPToFixed(fsize, input[i], fsize, unsigned_, fpcr, FP::RoundingMode::TowardsMinusInfinity, fpsr)); - }; - case FP::RoundingMode::TowardsZero: - return [](VectorArray& output, const VectorArray& input, FP::FPCR fpcr, FP::FPSR& fpsr) { - for (size_t i = 0; i < output.size(); ++i) - output[i] = FPT(FP::FPToFixed(fsize, input[i], fsize, unsigned_, fpcr, FP::RoundingMode::TowardsZero, fpsr)); - }; - case FP::RoundingMode::ToNearest_TieAwayFromZero: - return [](VectorArray& output, const VectorArray& input, FP::FPCR fpcr, FP::FPSR& fpsr) { - for (size_t i = 0; i < output.size(); ++i) - output[i] = FPT(FP::FPToFixed(fsize, input[i], fsize, unsigned_, fpcr, FP::RoundingMode::ToNearest_TieAwayFromZero, fpsr)); - }; - case FP::RoundingMode::ToOdd: - return [](VectorArray& output, const VectorArray& input, FP::FPCR fpcr, FP::FPSR& fpsr) { - for (size_t i = 0; i < output.size(); ++i) - output[i] = FPT(FP::FPToFixed(fsize, input[i], fsize, unsigned_, fpcr, FP::RoundingMode::ToOdd, fpsr)); - }; - } - }(); - EmitTwoOpFallback<3>(code, ctx, inst, func); + output[i] = FPT(FP::FPToFixed(fsize, input[i], fbits, unsigned_, fpcr, rounding_mode, fpsr)); + }) + }; + }, mp::cartesian_product{}); + + EmitTwoOpFallback<3>(code, ctx, inst, lut.at(std::make_tuple(fbits, rounding))); } void EmitX64::EmitFPVectorToSignedFixed16(EmitContext& ctx, IR::Inst* inst) { diff --git a/src/dynarmic/src/dynarmic/common/lut_from_list.h b/src/dynarmic/src/dynarmic/common/lut_from_list.h new file mode 100644 index 0000000000..633b62aeda --- /dev/null +++ b/src/dynarmic/src/dynarmic/common/lut_from_list.h @@ -0,0 +1,55 @@ +// SPDX-FileCopyrightText: Copyright 2025 Eden Emulator Project +// SPDX-License-Identifier: GPL-3.0-or-later + +/* This file is part of the dynarmic project. + * Copyright (c) 2018 MerryMage + * SPDX-License-Identifier: 0BSD + */ + +#pragma once + +#include +#include +#include + +#include +#include +#include + +#ifdef _MSC_VER +# include +#endif + +namespace Dynarmic::Common { + +// prevents this function from printing 56,000 character warning messages +#ifdef __GNUC__ +#pragma GCC diagnostic push +#pragma GCC diagnostic ignored "-Wno-stack-usage" +#endif +#ifdef __clang__ +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wno-stack-usage" +#endif + +template +inline auto GenerateLookupTableFromList(Function f, mcl::mp::list) { +#ifdef _MSC_VER + using PairT = std::invoke_result_t>>; +#else + using PairT = std::common_type_t...>; +#endif + using MapT = mcl::mp::apply; + static_assert(mcl::is_instance_of_template_v); + const std::initializer_list pair_array{f(Values{})...}; + return MapT(pair_array.begin(), pair_array.end()); +} + +#ifdef __GNUC__ +#pragma GCC diagnostic pop +#endif +#ifdef __clang__ +#pragma clang diagnostic pop +#endif + +} // namespace Dynarmic::Common