diff options
Diffstat (limited to '')
-rw-r--r-- | src/citra/citra.cpp | 14 | ||||
-rw-r--r-- | src/citra/emu_window/emu_window_sdl2.cpp | 4 | ||||
-rw-r--r-- | src/citra_qt/debugger/graphics_vertex_shader.cpp | 12 | ||||
-rw-r--r-- | src/common/common_types.h | 6 | ||||
-rw-r--r-- | src/common/logging/backend.cpp | 1 | ||||
-rw-r--r-- | src/common/logging/log.h | 1 | ||||
-rw-r--r-- | src/core/CMakeLists.txt | 6 | ||||
-rw-r--r-- | src/core/hle/service/hid/hid.cpp | 2 | ||||
-rw-r--r-- | src/core/hle/service/ndm/ndm.cpp | 47 | ||||
-rw-r--r-- | src/core/hle/service/ndm/ndm.h | 52 | ||||
-rw-r--r-- | src/core/hle/service/ndm/ndm_u.cpp (renamed from src/core/hle/service/ndm_u.cpp) | 23 | ||||
-rw-r--r-- | src/core/hle/service/ndm/ndm_u.h (renamed from src/core/hle/service/ndm_u.h) | 15 | ||||
-rw-r--r-- | src/core/hle/service/service.cpp | 5 | ||||
-rw-r--r-- | src/core/hw/gpu.h | 8 | ||||
-rw-r--r-- | src/core/hw/lcd.h | 8 | ||||
-rw-r--r-- | src/video_core/pica.h | 12 | ||||
-rw-r--r-- | src/video_core/shader/shader.cpp | 16 | ||||
-rw-r--r-- | src/video_core/shader/shader_interpreter.cpp | 7 | ||||
-rw-r--r-- | src/video_core/shader/shader_jit_x64.cpp | 68 | ||||
-rw-r--r-- | src/video_core/shader/shader_jit_x64.h | 5 |
20 files changed, 222 insertions, 90 deletions
diff --git a/src/citra/citra.cpp b/src/citra/citra.cpp index 415b98a05..40e40f192 100644 --- a/src/citra/citra.cpp +++ b/src/citra/citra.cpp @@ -19,6 +19,8 @@ #include "common/logging/log.h" #include "common/logging/backend.h" #include "common/logging/filter.h" +#include "common/make_unique.h" +#include "common/scope_exit.h" #include "core/settings.h" #include "core/system.h" @@ -64,6 +66,7 @@ int main(int argc, char **argv) { Log::SetFilter(&log_filter); MicroProfileOnThreadCreate("EmuThread"); + SCOPE_EXIT({ MicroProfileShutdown(); }); if (boot_filename.empty()) { LOG_CRITICAL(Frontend, "Failed to load ROM: No ROM specified"); @@ -76,12 +79,13 @@ int main(int argc, char **argv) { GDBStub::ToggleServer(Settings::values.use_gdbstub); GDBStub::SetServerPort(static_cast<u32>(Settings::values.gdbstub_port)); - EmuWindow_SDL2* emu_window = new EmuWindow_SDL2; + std::unique_ptr<EmuWindow_SDL2> emu_window = Common::make_unique<EmuWindow_SDL2>(); VideoCore::g_hw_renderer_enabled = Settings::values.use_hw_renderer; VideoCore::g_shader_jit_enabled = Settings::values.use_shader_jit; - System::Init(emu_window); + System::Init(emu_window.get()); + SCOPE_EXIT({ System::Shutdown(); }); Loader::ResultStatus load_result = Loader::LoadFile(boot_filename); if (Loader::ResultStatus::Success != load_result) { @@ -93,11 +97,5 @@ int main(int argc, char **argv) { Core::RunLoop(); } - System::Shutdown(); - - delete emu_window; - - MicroProfileShutdown(); - return 0; } diff --git a/src/citra/emu_window/emu_window_sdl2.cpp b/src/citra/emu_window/emu_window_sdl2.cpp index 1fed82e78..924189f4c 100644 --- a/src/citra/emu_window/emu_window_sdl2.cpp +++ b/src/citra/emu_window/emu_window_sdl2.cpp @@ -73,6 +73,10 @@ EmuWindow_SDL2::EmuWindow_SDL2() { SDL_GL_SetAttribute(SDL_GL_CONTEXT_MINOR_VERSION, 3); SDL_GL_SetAttribute(SDL_GL_CONTEXT_PROFILE_MASK, SDL_GL_CONTEXT_PROFILE_CORE); SDL_GL_SetAttribute(SDL_GL_DOUBLEBUFFER, 1); + SDL_GL_SetAttribute(SDL_GL_RED_SIZE, 8); + SDL_GL_SetAttribute(SDL_GL_GREEN_SIZE, 8); + SDL_GL_SetAttribute(SDL_GL_BLUE_SIZE, 8); + SDL_GL_SetAttribute(SDL_GL_ALPHA_SIZE, 0); std::string window_title = Common::StringFromFormat("Citra | %s-%s", Common::g_scm_branch, Common::g_scm_desc); render_window = SDL_CreateWindow(window_title.c_str(), diff --git a/src/citra_qt/debugger/graphics_vertex_shader.cpp b/src/citra_qt/debugger/graphics_vertex_shader.cpp index 4b676f1b1..d648d4640 100644 --- a/src/citra_qt/debugger/graphics_vertex_shader.cpp +++ b/src/citra_qt/debugger/graphics_vertex_shader.cpp @@ -179,9 +179,17 @@ QVariant GraphicsVertexShaderModel::data(const QModelIndex& index, int role) con AlignToColumn(kOutputColumnWidth); print_input(output, src1, swizzle.negate_src1, SelectorToString(swizzle.src1_selector)); AlignToColumn(kInputOperandColumnWidth); - print_input(output, src2, swizzle.negate_src2, SelectorToString(swizzle.src2_selector)); + if (src_is_inverted) { + print_input(output, src2, swizzle.negate_src2, SelectorToString(swizzle.src2_selector)); + } else { + print_input(output, src2, swizzle.negate_src2, SelectorToString(swizzle.src2_selector), true, instr.mad.AddressRegisterName()); + } AlignToColumn(kInputOperandColumnWidth); - print_input(output, src3, swizzle.negate_src3, SelectorToString(swizzle.src3_selector)); + if (src_is_inverted) { + print_input(output, src3, swizzle.negate_src3, SelectorToString(swizzle.src3_selector), true, instr.mad.AddressRegisterName()); + } else { + print_input(output, src3, swizzle.negate_src3, SelectorToString(swizzle.src3_selector)); + } AlignToColumn(kInputOperandColumnWidth); break; } diff --git a/src/common/common_types.h b/src/common/common_types.h index fa3e0b8d6..9f51dff18 100644 --- a/src/common/common_types.h +++ b/src/common/common_types.h @@ -53,9 +53,9 @@ typedef u32 PAddr; ///< Represents a pointer in the ARM11 physical address space // An inheritable class to disallow the copy constructor and operator= functions class NonCopyable { protected: - NonCopyable() = default; + constexpr NonCopyable() = default; ~NonCopyable() = default; - NonCopyable(NonCopyable&) = delete; - NonCopyable& operator=(NonCopyable&) = delete; + NonCopyable(const NonCopyable&) = delete; + NonCopyable& operator=(const NonCopyable&) = delete; }; diff --git a/src/common/logging/backend.cpp b/src/common/logging/backend.cpp index 54291429a..4c86151ab 100644 --- a/src/common/logging/backend.cpp +++ b/src/common/logging/backend.cpp @@ -42,6 +42,7 @@ namespace Log { SUB(Service, AM) \ SUB(Service, PTM) \ SUB(Service, LDR) \ + SUB(Service, NDM) \ SUB(Service, NIM) \ SUB(Service, NWM) \ SUB(Service, CAM) \ diff --git a/src/common/logging/log.h b/src/common/logging/log.h index 4b01805ae..e4c39c308 100644 --- a/src/common/logging/log.h +++ b/src/common/logging/log.h @@ -57,6 +57,7 @@ enum class Class : ClassType { Service_AM, ///< The AM (Application manager) service Service_PTM, ///< The PTM (Power status & misc.) service Service_LDR, ///< The LDR (3ds dll loader) service + Service_NDM, ///< The NDM (Network daemon manager) service Service_NIM, ///< The NIM (Network interface manager) service Service_NWM, ///< The NWM (Network wlan manager) service Service_CAM, ///< The CAM (Camera) service diff --git a/src/core/CMakeLists.txt b/src/core/CMakeLists.txt index 35b61dada..3473e2f5b 100644 --- a/src/core/CMakeLists.txt +++ b/src/core/CMakeLists.txt @@ -87,7 +87,8 @@ set(SRCS hle/service/ir/ir_user.cpp hle/service/ldr_ro.cpp hle/service/mic_u.cpp - hle/service/ndm_u.cpp + hle/service/ndm/ndm.cpp + hle/service/ndm/ndm_u.cpp hle/service/news/news.cpp hle/service/news/news_s.cpp hle/service/news/news_u.cpp @@ -218,7 +219,8 @@ set(HEADERS hle/service/ir/ir_user.h hle/service/ldr_ro.h hle/service/mic_u.h - hle/service/ndm_u.h + hle/service/ndm/ndm.h + hle/service/ndm/ndm_u.h hle/service/news/news.h hle/service/news/news_s.h hle/service/news/news_u.h diff --git a/src/core/hle/service/hid/hid.cpp b/src/core/hle/service/hid/hid.cpp index 3015a9605..cb4fd38e2 100644 --- a/src/core/hle/service/hid/hid.cpp +++ b/src/core/hle/service/hid/hid.cpp @@ -68,7 +68,7 @@ void Update() { mem->pad.current_state.hex = state.hex; mem->pad.index = next_pad_index; - next_touch_index = (next_touch_index + 1) % mem->pad.entries.size(); + next_pad_index = (next_pad_index + 1) % mem->pad.entries.size(); // Get the previous Pad state u32 last_entry_index = (mem->pad.index - 1) % mem->pad.entries.size(); diff --git a/src/core/hle/service/ndm/ndm.cpp b/src/core/hle/service/ndm/ndm.cpp new file mode 100644 index 000000000..47076a7b8 --- /dev/null +++ b/src/core/hle/service/ndm/ndm.cpp @@ -0,0 +1,47 @@ +// Copyright 2016 Citra Emulator Project +// Licensed under GPLv2 or any later version +// Refer to the license.txt file included. + +#include "common/common_types.h" +#include "common/logging/log.h" +#include "core/hle/service/service.h" +#include "core/hle/service/ndm/ndm.h" +#include "core/hle/service/ndm/ndm_u.h" + +namespace Service { +namespace NDM { + +void SuspendDaemons(Service::Interface* self) { + u32* cmd_buff = Kernel::GetCommandBuffer(); + + LOG_WARNING(Service_NDM, "(STUBBED) bit_mask=0x%08X ", cmd_buff[1]); + + cmd_buff[1] = RESULT_SUCCESS.raw; // No error +} + +void ResumeDaemons(Service::Interface* self) { + u32* cmd_buff = Kernel::GetCommandBuffer(); + + LOG_WARNING(Service_NDM, "(STUBBED) bit_mask=0x%08X ", cmd_buff[1]); + + cmd_buff[1] = RESULT_SUCCESS.raw; // No error +} + +void OverrideDefaultDaemons(Service::Interface* self) { + u32* cmd_buff = Kernel::GetCommandBuffer(); + + LOG_WARNING(Service_NDM, "(STUBBED) bit_mask=0x%08X ", cmd_buff[1]); + + cmd_buff[1] = RESULT_SUCCESS.raw; // No error +} + +void Init() { + AddService(new NDM_U_Interface); +} + +void Shutdown() { + +} + +}// namespace NDM +}// namespace Service diff --git a/src/core/hle/service/ndm/ndm.h b/src/core/hle/service/ndm/ndm.h new file mode 100644 index 000000000..734730f8c --- /dev/null +++ b/src/core/hle/service/ndm/ndm.h @@ -0,0 +1,52 @@ +// Copyright 2016 Citra Emulator Project +// Licensed under GPLv2 or any later version +// Refer to the license.txt file included. + +#pragma once + +#include "common/common_types.h" + +namespace Service { + +class Interface; + +namespace NDM { + +/** + * SuspendDaemons + * Inputs: + * 0 : Command header (0x00020082) + * 1 : Daemon bit mask + * Outputs: + * 1 : Result, 0 on success, otherwise error code + */ +void SuspendDaemons(Service::Interface* self); + +/** + * ResumeDaemons + * Inputs: + * 0 : Command header (0x00020082) + * 1 : Daemon bit mask + * Outputs: + * 1 : Result, 0 on success, otherwise error code + */ +void ResumeDaemons(Service::Interface* self); + +/** + * OverrideDefaultDaemons + * Inputs: + * 0 : Command header (0x00020082) + * 1 : Daemon bit mask + * Outputs: + * 1 : Result, 0 on success, otherwise error code + */ +void OverrideDefaultDaemons(Service::Interface* self); + +/// Initialize NDM service +void Init(); + +/// Shutdown NDM service +void Shutdown(); + +}// namespace NDM +}// namespace Service diff --git a/src/core/hle/service/ndm_u.cpp b/src/core/hle/service/ndm/ndm_u.cpp index 8fdf1ef90..bf95cc7aa 100644 --- a/src/core/hle/service/ndm_u.cpp +++ b/src/core/hle/service/ndm/ndm_u.cpp @@ -2,12 +2,11 @@ // Licensed under GPLv2 or any later version // Refer to the license.txt file included. -#include "core/hle/service/ndm_u.h" +#include "core/hle/service/ndm/ndm.h" +#include "core/hle/service/ndm/ndm_u.h" -//////////////////////////////////////////////////////////////////////////////////////////////////// -// Namespace NDM_U - -namespace NDM_U { +namespace Service { +namespace NDM { const Interface::FunctionInfo FunctionTable[] = { {0x00010042, nullptr, "EnterExclusiveState"}, @@ -15,8 +14,8 @@ const Interface::FunctionInfo FunctionTable[] = { {0x00030000, nullptr, "QueryExclusiveMode"}, {0x00040002, nullptr, "LockState"}, {0x00050002, nullptr, "UnlockState"}, - {0x00060040, nullptr, "SuspendDaemons"}, - {0x00070040, nullptr, "ResumeDaemons"}, + {0x00060040, SuspendDaemons, "SuspendDaemons"}, + {0x00070040, ResumeDaemons, "ResumeDaemons"}, {0x00080040, nullptr, "DisableWifiUsage"}, {0x00090000, nullptr, "EnableWifiUsage"}, {0x000A0000, nullptr, "GetCurrentState"}, @@ -29,17 +28,15 @@ const Interface::FunctionInfo FunctionTable[] = { {0x00110000, nullptr, "GetScanInterval"}, {0x00120040, nullptr, "SetRetryInterval"}, {0x00130000, nullptr, "GetRetryInterval"}, - {0x00140040, nullptr, "OverrideDefaultDaemons"}, + {0x00140040, OverrideDefaultDaemons, "OverrideDefaultDaemons"}, {0x00150000, nullptr, "ResetDefaultDaemons"}, {0x00160000, nullptr, "GetDefaultDaemons"}, {0x00170000, nullptr, "ClearHalfAwakeMacFilter"}, }; -//////////////////////////////////////////////////////////////////////////////////////////////////// -// Interface class - -Interface::Interface() { +NDM_U_Interface::NDM_U_Interface() { Register(FunctionTable); } -} // namespace +} // namespace NDM +} // namespace Service diff --git a/src/core/hle/service/ndm_u.h b/src/core/hle/service/ndm/ndm_u.h index 51c4b3902..d567abc84 100644 --- a/src/core/hle/service/ndm_u.h +++ b/src/core/hle/service/ndm/ndm_u.h @@ -6,20 +6,17 @@ #include "core/hle/service/service.h" -//////////////////////////////////////////////////////////////////////////////////////////////////// -// Namespace NDM +namespace Service { +namespace NDM { -// No idea what this is - -namespace NDM_U { - -class Interface : public Service::Interface { +class NDM_U_Interface : public Service::Interface { public: - Interface(); + NDM_U_Interface(); std::string GetPortName() const override { return "ndm:u"; } }; -} // namespace +} // namespace NDM +} // namespace Service diff --git a/src/core/hle/service/service.cpp b/src/core/hle/service/service.cpp index 0de0b13a3..35b648409 100644 --- a/src/core/hle/service/service.cpp +++ b/src/core/hle/service/service.cpp @@ -16,7 +16,6 @@ #include "core/hle/service/http_c.h" #include "core/hle/service/ldr_ro.h" #include "core/hle/service/mic_u.h" -#include "core/hle/service/ndm_u.h" #include "core/hle/service/ns_s.h" #include "core/hle/service/nwm_uds.h" #include "core/hle/service/pm_app.h" @@ -35,6 +34,7 @@ #include "core/hle/service/cfg/cfg.h" #include "core/hle/service/hid/hid.h" #include "core/hle/service/ir/ir.h" +#include "core/hle/service/ndm/ndm.h" #include "core/hle/service/news/news.h" #include "core/hle/service/nim/nim.h" #include "core/hle/service/ptm/ptm.h" @@ -114,6 +114,7 @@ void Init() { Service::HID::Init(); Service::IR::Init(); Service::NEWS::Init(); + Service::NDM::Init(); Service::NIM::Init(); Service::PTM::Init(); @@ -126,7 +127,6 @@ void Init() { AddService(new HTTP_C::Interface); AddService(new LDR_RO::Interface); AddService(new MIC_U::Interface); - AddService(new NDM_U::Interface); AddService(new NS_S::Interface); AddService(new NWM_UDS::Interface); AddService(new PM_APP::Interface); @@ -141,6 +141,7 @@ void Init() { void Shutdown() { Service::PTM::Shutdown(); + Service::NDM::Shutdown(); Service::NIM::Shutdown(); Service::NEWS::Shutdown(); Service::IR::Shutdown(); diff --git a/src/core/hw/gpu.h b/src/core/hw/gpu.h index 2e3a9f779..a00adbf53 100644 --- a/src/core/hw/gpu.h +++ b/src/core/hw/gpu.h @@ -263,17 +263,17 @@ struct Regs { INSERT_PADDING_WORDS(0x9c3); - static inline size_t NumIds() { + static constexpr size_t NumIds() { return sizeof(Regs) / sizeof(u32); } - u32& operator [] (int index) const { - u32* content = (u32*)this; + const u32& operator [] (int index) const { + const u32* content = reinterpret_cast<const u32*>(this); return content[index]; } u32& operator [] (int index) { - u32* content = (u32*)this; + u32* content = reinterpret_cast<u32*>(this); return content[index]; } diff --git a/src/core/hw/lcd.h b/src/core/hw/lcd.h index bcce6d8cf..3dd877fbf 100644 --- a/src/core/hw/lcd.h +++ b/src/core/hw/lcd.h @@ -38,17 +38,17 @@ struct Regs { u32 backlight_bottom; INSERT_PADDING_WORDS(0x16F); - static inline size_t NumIds() { + static constexpr size_t NumIds() { return sizeof(Regs) / sizeof(u32); } - u32& operator [] (int index) const { - u32* content = (u32*)this; + const u32& operator [] (int index) const { + const u32* content = reinterpret_cast<const u32*>(this); return content[index]; } u32& operator [] (int index) { - u32* content = (u32*)this; + u32* content = reinterpret_cast<u32*>(this); return content[index]; } diff --git a/src/video_core/pica.h b/src/video_core/pica.h index 2e0c33201..337cff8ce 100644 --- a/src/video_core/pica.h +++ b/src/video_core/pica.h @@ -117,8 +117,8 @@ struct Regs { INSERT_PADDING_WORDS(0x11); union { - BitField< 0, 16, u32> x; - BitField<16, 16, u32> y; + BitField< 0, 10, s32> x; + BitField<16, 10, s32> y; } viewport_corner; INSERT_PADDING_WORDS(0x17); @@ -1221,17 +1221,17 @@ struct Regs { // Used for debugging purposes, so performance is not an issue here static std::string GetCommandName(int index); - static inline size_t NumIds() { + static constexpr size_t NumIds() { return sizeof(Regs) / sizeof(u32); } - u32& operator [] (int index) const { - u32* content = (u32*)this; + const u32& operator [] (int index) const { + const u32* content = reinterpret_cast<const u32*>(this); return content[index]; } u32& operator [] (int index) { - u32* content = (u32*)this; + u32* content = reinterpret_cast<u32*>(this); return content[index]; } diff --git a/src/video_core/shader/shader.cpp b/src/video_core/shader/shader.cpp index 5e8930476..509558fc0 100644 --- a/src/video_core/shader/shader.cpp +++ b/src/video_core/shader/shader.cpp @@ -32,6 +32,12 @@ namespace Shader { static std::unordered_map<u64, CompiledShader*> shader_map; static JitCompiler jit; static CompiledShader* jit_shader; + +static void ClearCache() { + shader_map.clear(); + jit.Clear(); + LOG_INFO(HW_GPU, "Shader JIT cache cleared"); +} #endif // ARCHITECTURE_x86_64 void Setup(UnitState<false>& state) { @@ -45,6 +51,12 @@ void Setup(UnitState<false>& state) { if (iter != shader_map.end()) { jit_shader = iter->second; } else { + // Check if remaining JIT code space is enough for at least one more (massive) shader + if (jit.GetSpaceLeft() < jit_shader_size) { + // If not, clear the cache of all previously compiled shaders + ClearCache(); + } + jit_shader = jit.Compile(); shader_map.emplace(cache_key, jit_shader); } @@ -54,7 +66,7 @@ void Setup(UnitState<false>& state) { void Shutdown() { #ifdef ARCHITECTURE_x86_64 - shader_map.clear(); + ClearCache(); #endif // ARCHITECTURE_x86_64 } @@ -135,7 +147,7 @@ OutputVertex Run(UnitState<false>& state, const InputVertex& input, int num_attr std::fmin(std::fabs(ret.color[i].ToFloat32()), 1.0f)); } - LOG_TRACE(Render_Software, "Output vertex: pos(%.2f, %.2f, %.2f, %.2f), quat(%.2f, %.2f, %.2f, %.2f), " + LOG_TRACE(HW_GPU, "Output vertex: pos(%.2f, %.2f, %.2f, %.2f), quat(%.2f, %.2f, %.2f, %.2f), " "col(%.2f, %.2f, %.2f, %.2f), tc0(%.2f, %.2f), view(%.2f, %.2f, %.2f)", ret.pos.x.ToFloat32(), ret.pos.y.ToFloat32(), ret.pos.z.ToFloat32(), ret.pos.w.ToFloat32(), ret.quat.x.ToFloat32(), ret.quat.y.ToFloat32(), ret.quat.z.ToFloat32(), ret.quat.w.ToFloat32(), diff --git a/src/video_core/shader/shader_interpreter.cpp b/src/video_core/shader/shader_interpreter.cpp index 79fcc56b9..295a2466b 100644 --- a/src/video_core/shader/shader_interpreter.cpp +++ b/src/video_core/shader/shader_interpreter.cpp @@ -413,9 +413,12 @@ void RunInterpreter(UnitState<Debug>& state) { bool is_inverted = (instr.opcode.Value().EffectiveOpCode() == OpCode::Id::MADI); + const int address_offset = (instr.mad.address_register_index == 0) + ? 0 : state.address_registers[instr.mad.address_register_index - 1]; + const float24* src1_ = LookupSourceRegister(instr.mad.GetSrc1(is_inverted)); - const float24* src2_ = LookupSourceRegister(instr.mad.GetSrc2(is_inverted)); - const float24* src3_ = LookupSourceRegister(instr.mad.GetSrc3(is_inverted)); + const float24* src2_ = LookupSourceRegister(instr.mad.GetSrc2(is_inverted) + (!is_inverted * address_offset)); + const float24* src3_ = LookupSourceRegister(instr.mad.GetSrc3(is_inverted) + ( is_inverted * address_offset)); const bool negate_src1 = ((bool)swizzle.negate_src1 != false); const bool negate_src2 = ((bool)swizzle.negate_src2 != false); diff --git a/src/video_core/shader/shader_jit_x64.cpp b/src/video_core/shader/shader_jit_x64.cpp index 5083d7e54..dffe051ef 100644 --- a/src/video_core/shader/shader_jit_x64.cpp +++ b/src/video_core/shader/shader_jit_x64.cpp @@ -160,40 +160,41 @@ void JitCompiler::Compile_SwizzleSrc(Instruction instr, unsigned src_num, Source ASSERT_MSG(src_offset == src_offset_disp, "Source register offset too large for int type"); unsigned operand_desc_id; + + const bool is_inverted = (0 != (instr.opcode.Value().GetInfo().subtype & OpCode::Info::SrcInversed)); + + unsigned address_register_index; + unsigned offset_src; + if (instr.opcode.Value().EffectiveOpCode() == OpCode::Id::MAD || instr.opcode.Value().EffectiveOpCode() == OpCode::Id::MADI) { - // The MAD and MADI instructions do not use the address offset registers, so loading the - // source is a bit simpler here - operand_desc_id = instr.mad.operand_desc_id; - - // Load the source - MOVAPS(dest, MDisp(src_ptr, src_offset_disp)); + offset_src = is_inverted ? 3 : 2; + address_register_index = instr.mad.address_register_index; } else { operand_desc_id = instr.common.operand_desc_id; + offset_src = is_inverted ? 2 : 1; + address_register_index = instr.common.address_register_index; + } - const bool is_inverted = (0 != (instr.opcode.Value().GetInfo().subtype & OpCode::Info::SrcInversed)); - unsigned offset_src = is_inverted ? 2 : 1; - - if (src_num == offset_src && instr.common.address_register_index != 0) { - switch (instr.common.address_register_index) { - case 1: // address offset 1 - MOVAPS(dest, MComplex(src_ptr, ADDROFFS_REG_0, SCALE_1, src_offset_disp)); - break; - case 2: // address offset 2 - MOVAPS(dest, MComplex(src_ptr, ADDROFFS_REG_1, SCALE_1, src_offset_disp)); - break; - case 3: // address offset 3 - MOVAPS(dest, MComplex(src_ptr, LOOPCOUNT_REG, SCALE_1, src_offset_disp)); - break; - default: - UNREACHABLE(); - break; - } - } else { - // Load the source - MOVAPS(dest, MDisp(src_ptr, src_offset_disp)); + if (src_num == offset_src && address_register_index != 0) { + switch (address_register_index) { + case 1: // address offset 1 + MOVAPS(dest, MComplex(src_ptr, ADDROFFS_REG_0, SCALE_1, src_offset_disp)); + break; + case 2: // address offset 2 + MOVAPS(dest, MComplex(src_ptr, ADDROFFS_REG_1, SCALE_1, src_offset_disp)); + break; + case 3: // address offset 3 + MOVAPS(dest, MComplex(src_ptr, LOOPCOUNT_REG, SCALE_1, src_offset_disp)); + break; + default: + UNREACHABLE(); + break; } + } else { + // Load the source + MOVAPS(dest, MDisp(src_ptr, src_offset_disp)); } SwizzlePattern swiz = { g_state.vs.swizzle_data[operand_desc_id] }; @@ -644,7 +645,8 @@ void JitCompiler::Compile_MAD(Instruction instr) { } void JitCompiler::Compile_IF(Instruction instr) { - ASSERT_MSG(instr.flow_control.dest_offset > *offset_ptr, "Backwards if-statements not supported"); + ASSERT_MSG(instr.flow_control.dest_offset > *offset_ptr, "Backwards if-statements (%d -> %d) not supported", + *offset_ptr, instr.flow_control.dest_offset.Value()); // Evaluate the "IF" condition if (instr.opcode.Value() == OpCode::Id::IFU) { @@ -675,7 +677,8 @@ void JitCompiler::Compile_IF(Instruction instr) { } void JitCompiler::Compile_LOOP(Instruction instr) { - ASSERT_MSG(instr.flow_control.dest_offset > *offset_ptr, "Backwards loops not supported"); + ASSERT_MSG(instr.flow_control.dest_offset > *offset_ptr, "Backwards loops (%d -> %d) not supported", + *offset_ptr, instr.flow_control.dest_offset.Value()); ASSERT_MSG(!looping, "Nested loops not supported"); looping = true; @@ -703,7 +706,8 @@ void JitCompiler::Compile_LOOP(Instruction instr) { } void JitCompiler::Compile_JMP(Instruction instr) { - ASSERT_MSG(instr.flow_control.dest_offset > *offset_ptr, "Backwards jumps not supported"); + ASSERT_MSG(instr.flow_control.dest_offset > *offset_ptr, "Backwards jumps (%d -> %d) not supported", + *offset_ptr, instr.flow_control.dest_offset.Value()); if (instr.opcode.Value() == OpCode::Id::JMPC) Compile_EvaluateCondition(instr); @@ -747,7 +751,7 @@ void JitCompiler::Compile_NextInstr(unsigned* offset) { } else { // Unhandled instruction LOG_CRITICAL(HW_GPU, "Unhandled instruction: 0x%02x (0x%08x)", - instr.opcode.Value().EffectiveOpCode(), instr.hex); + instr.opcode.Value().EffectiveOpCode(), instr.hex); } } @@ -786,7 +790,7 @@ CompiledShader* JitCompiler::Compile() { } JitCompiler::JitCompiler() { - AllocCodeSpace(1024 * 1024 * 4); + AllocCodeSpace(jit_cache_size); } void JitCompiler::Clear() { diff --git a/src/video_core/shader/shader_jit_x64.h b/src/video_core/shader/shader_jit_x64.h index 5ad2d9606..5357c964b 100644 --- a/src/video_core/shader/shader_jit_x64.h +++ b/src/video_core/shader/shader_jit_x64.h @@ -19,6 +19,11 @@ namespace Pica { namespace Shader { +/// Memory needed to be available to compile the next shader (otherwise, clear the cache) +constexpr size_t jit_shader_size = 1024 * 512; +/// Memory allocated for the JIT code space cache +constexpr size_t jit_cache_size = 1024 * 1024 * 8; + using CompiledShader = void(void* registers); /** |