Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

PPU LLVM: improve accuracy of VSL/VSR #11382

Merged
merged 3 commits into from Jan 15, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
6 changes: 3 additions & 3 deletions rpcs3/Emu/Cell/PPUInterpreter.cpp
Expand Up @@ -74,7 +74,7 @@ struct ppu_exec_select
static ppu_intrp_func_t select(bs_t<ppu_exec_bit> selected, F func)
{
// Make sure there is no flag duplication, otherwise skip flag
if constexpr (((Flags0 != Flag) && ...) && (Flag != fix_vnan || ((Flags0 != set_vnan) && ...)) && (Flag != fix_nj || ((Flags0 != use_nj) && ...)))
if constexpr (((Flags0 != Flag) && ...))
{
// Test only relevant flags at runtime initialization (compile both variants)
if (selected & Flag)
Expand Down Expand Up @@ -7583,11 +7583,11 @@ ppu_interpreter_rt_base::ppu_interpreter_rt_base() noexcept
if (g_cfg.core.ppu_set_sat_bit)
selected += set_sat;
if (g_cfg.core.ppu_use_nj_bit)
selected += use_nj;
selected += use_nj + fix_nj;
if (g_cfg.core.ppu_llvm_nj_fixup)
selected += fix_nj;
if (g_cfg.core.ppu_set_vnan)
selected += set_vnan;
selected += set_vnan + fix_vnan;
if (g_cfg.core.ppu_fix_vnan)
selected += fix_vnan;
if (g_cfg.core.ppu_set_fpcc)
Expand Down
10 changes: 4 additions & 6 deletions rpcs3/Emu/Cell/PPUTranslator.cpp
Expand Up @@ -1518,9 +1518,8 @@ void PPUTranslator::VSEL(ppu_opcode_t op)

void PPUTranslator::VSL(ppu_opcode_t op)
{
// TODO (very rare)
const auto [a, b] = get_vrs<u128>(op.va, op.vb);
set_vr(op.vd, a << (b & 7));
const auto [a, b] = get_vrs<u8[16]>(op.va, op.vb);
set_vr(op.vd, fshl(a, zshuffle(a, 16, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14), b));
}

void PPUTranslator::VSLB(ppu_opcode_t op)
Expand Down Expand Up @@ -1612,9 +1611,8 @@ void PPUTranslator::VSPLTW(ppu_opcode_t op)

void PPUTranslator::VSR(ppu_opcode_t op)
{
// TODO (very rare)
const auto [a, b] = get_vrs<u128>(op.va, op.vb);
set_vr(op.vd, a >> (b & 7));
const auto [a, b] = get_vrs<u8[16]>(op.va, op.vb);
set_vr(op.vd, fshr(zshuffle(a, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16), a, b));
}

void PPUTranslator::VSRAB(ppu_opcode_t op)
Expand Down
2 changes: 1 addition & 1 deletion rpcs3/Emu/system_config.h
Expand Up @@ -58,7 +58,7 @@ struct cfg_root : cfg::node
cfg::_bool ppu_llvm_nj_fixup{ this, "PPU LLVM Java Mode Handling", true }; // Partially respect current Java Mode for alti-vec ops by PPU LLVM
cfg::_bool use_accurate_dfma{ this, "Use Accurate DFMA", true }; // Enable accurate double-precision FMA for CPUs which do not support it natively
cfg::_bool ppu_set_sat_bit{ this, "PPU Set Saturation Bit", false }; // Accuracy. If unset, completely disable saturation flag handling.
cfg::_bool ppu_use_nj_bit{ this, "PPU Use Non-Java Mode Bit", false }; // Accuracy. If unset, ignore NJ flag completely.
cfg::_bool ppu_use_nj_bit{ this, "PPU Accurate Non-Java Mode", false }; // Accuracy. If set, accurately emulate NJ flag. Implies NJ fixup.
cfg::_bool ppu_fix_vnan{ this, "PPU Fixup Vector NaN Values", false }; // Accuracy. Partial.
cfg::_bool ppu_set_vnan{ this, "PPU Accurate Vector NaN Values", false }; // Accuracy. Implies ppu_fix_vnan.
cfg::_bool ppu_set_fpcc{ this, "PPU Set FPCC Bits", false }; // Accuracy.
Expand Down
2 changes: 1 addition & 1 deletion rpcs3/rpcs3qt/emu_settings_type.h
Expand Up @@ -199,7 +199,7 @@ inline static const QMap<emu_settings_type, cfg_location> settings_location =
{ emu_settings_type::PPUNJFixup, { "Core", "PPU LLVM Java Mode Handling"}},
{ emu_settings_type::AccurateDFMA, { "Core", "Use Accurate DFMA"}},
{ emu_settings_type::AccuratePPUSAT, { "Core", "PPU Set Saturation Bit"}},
{ emu_settings_type::AccuratePPUNJ, { "Core", "PPU Use Non-Java Mode Bit"}},
{ emu_settings_type::AccuratePPUNJ, { "Core", "PPU Accurate Non-Java Mode"}},
{ emu_settings_type::FixupPPUVNAN, { "Core", "PPU Fixup Vector NaN Values"}},
{ emu_settings_type::AccuratePPUVNAN, { "Core", "PPU Accurate Vector NaN Values"}},
{ emu_settings_type::AccuratePPUFPCC, { "Core", "PPU Set FPCC Bits"}},
Expand Down
22 changes: 22 additions & 0 deletions rpcs3/rpcs3qt/settings_dialog.cpp
Expand Up @@ -330,6 +330,28 @@ settings_dialog::settings_dialog(std::shared_ptr<gui_settings> gui_settings, std

m_emu_settings->EnhanceRadioButton(ppu_bg, emu_settings_type::PPUDecoder);

connect(ppu_bg, &QButtonGroup::idToggled, [this](int id, bool checked)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ugh... Need to put this before EnhanceRadioButton

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Damn. Why though? It seems working.

Copy link
Contributor

@Megamouse Megamouse Jan 15, 2022

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

initial state when opening the dialog.
Enhance toggles the active button

{
if (!checked) return;

switch (id)
{
case static_cast<int>(ppu_decoder_type::_static):
ui->accuratePPUFPCC->setEnabled(true);
ui->accuratePPUNJ->setEnabled(true);
ui->accuratePPUVNAN->setEnabled(true);
break;
case static_cast<int>(ppu_decoder_type::dynamic):
case static_cast<int>(ppu_decoder_type::llvm):
ui->accuratePPUFPCC->setEnabled(false);
ui->accuratePPUNJ->setEnabled(false);
ui->accuratePPUVNAN->setEnabled(false);
break;
default:
break;
}
});

// SPU tool tips
SubscribeTooltip(ui->spu__static, tooltips.settings.spu__static);
SubscribeTooltip(ui->spu_dynamic, tooltips.settings.spu_dynamic);
Expand Down