From d90e26ac0c585d80f7485a7ce76dd5fcdfcc7076 Mon Sep 17 00:00:00 2001 From: SimoneN64 Date: Wed, 3 Jul 2024 21:11:03 +0200 Subject: [PATCH] Various pointer changes --- external/parallel-rdp/ParallelRDPWrapper.cpp | 34 ++++++------ external/parallel-rdp/ParallelRDPWrapper.hpp | 10 ++-- src/backend/core/Interpreter.cpp | 4 ++ src/backend/core/Mem.cpp | 20 +++++++ src/backend/core/interpreter/instructions.cpp | 28 ++++++---- src/backend/core/mmio/Audio.cpp | 36 +++++++------ src/backend/core/mmio/Audio.hpp | 17 +++--- src/frontend/EmuThread.cpp | 54 +++++++++---------- src/frontend/EmuThread.hpp | 32 +++++------ src/frontend/KaizenQt.cpp | 13 +++-- src/frontend/KaizenQt.hpp | 2 +- src/frontend/MainWindow.cpp | 4 ++ src/utils/MemoryHelpers.hpp | 40 -------------- 13 files changed, 144 insertions(+), 150 deletions(-) diff --git a/external/parallel-rdp/ParallelRDPWrapper.cpp b/external/parallel-rdp/ParallelRDPWrapper.cpp index c0f94bf6..cb4e52eb 100644 --- a/external/parallel-rdp/ParallelRDPWrapper.cpp +++ b/external/parallel-rdp/ParallelRDPWrapper.cpp @@ -20,21 +20,21 @@ void ParallelRDP::SetFramerateUnlocked(bool unlocked) { Program* fullscreen_quad_program; -void ParallelRDP::LoadWSIPlatform(Vulkan::InstanceFactory* instanceFactory, std::unique_ptr&& wsi_platform, std::unique_ptr&& newWindowInfo) { - wsi = std::make_unique(); +void ParallelRDP::LoadWSIPlatform(const std::shared_ptr& instanceFactory, const std::shared_ptr& wsi_platform, const std::shared_ptr& newWindowInfo) { + wsi = std::make_shared(); wsi->set_backbuffer_srgb(false); wsi->set_platform(wsi_platform.get()); wsi->set_present_mode(PresentMode::SyncToVBlank); Context::SystemHandles handles; - if (!wsi->init_simple(instanceFactory, 1, handles)) { + if (!wsi->init_simple(instanceFactory.get(), 1, handles)) { Util::panic("Failed to initialize WSI!"); } - windowInfo = std::move(newWindowInfo); + windowInfo = newWindowInfo; } -void ParallelRDP::Init(Vulkan::InstanceFactory* factory, std::unique_ptr&& wsiPlatform, std::unique_ptr&& newWindowInfo, const u8* rdram) { - LoadWSIPlatform(factory, std::move(wsiPlatform), std::move(newWindowInfo)); +void ParallelRDP::Init(const std::shared_ptr& factory, const std::shared_ptr& wsiPlatform, const std::shared_ptr& newWindowInfo, const u8* rdram) { + LoadWSIPlatform(factory, wsiPlatform, newWindowInfo); ResourceLayout vertLayout; ResourceLayout fragLayout; @@ -63,8 +63,7 @@ void ParallelRDP::Init(Vulkan::InstanceFactory* factory, std::unique_ptr(rdram); uintptr_t offset = 0; - if (wsi->get_device().get_device_features().supports_external_memory_host) - { + if (wsi->get_device().get_device_features().supports_external_memory_host) { size_t align = wsi->get_device().get_device_features().host_memory_properties.minImportedHostPointerAlignment; offset = aligned_rdram & (align - 1); aligned_rdram -= offset; @@ -72,8 +71,8 @@ void ParallelRDP::Init(Vulkan::InstanceFactory* factory, std::unique_ptr(wsi->get_device(), reinterpret_cast(aligned_rdram), - offset, 8 * 1024 * 1024, 4 * 1024 * 1024, flags); + command_processor = std::make_shared(wsi->get_device(), reinterpret_cast(aligned_rdram), + offset, 8 * 1024 * 1024, 4 * 1024 * 1024, flags); if (!command_processor->device_is_supported()) { Util::panic("This device probably does not support 8/16-bit storage. Make sure you're using up-to-date drivers!"); @@ -101,11 +100,11 @@ void ParallelRDP::DrawFullscreenTexturedQuad(Util::IntrusivePtr image, Ut float height = (wsi->get_platform().get_surface_height() / windowSize.y) * zoom; float uniform_data[] = { - // Size - width, height, - // Offset - (1.0f - width) * 0.5f, - (1.0f - height) * 0.5f}; + // Size + width, height, + // Offset + (1.0f - width) * 0.5f, + (1.0f - height) * 0.5f}; cmd->push_constants(uniform_data, 0, sizeof(uniform_data)); @@ -122,7 +121,7 @@ void ParallelRDP::UpdateScreen(Util::IntrusivePtr image) { if (!image) { auto info = Vulkan::ImageCreateInfo::immutable_2d_image(800, 600, VK_FORMAT_R8G8B8A8_UNORM); info.usage = VK_IMAGE_USAGE_SAMPLED_BIT | VK_IMAGE_USAGE_TRANSFER_SRC_BIT | - VK_IMAGE_USAGE_TRANSFER_DST_BIT; + VK_IMAGE_USAGE_TRANSFER_DST_BIT; info.misc = IMAGE_MISC_MUTABLE_SRGB_BIT; info.initial_layout = VK_IMAGE_LAYOUT_UNDEFINED; image = wsi->get_device().create_image(info); @@ -179,8 +178,7 @@ void ParallelRDP::UpdateScreen(n64::VI& vi, bool noGame) { Util::IntrusivePtr image = command_processor->scanout(opts); UpdateScreen(image); command_processor->begin_frame_context(); - } - else { + } else { UpdateScreen(static_cast>(nullptr)); command_processor->begin_frame_context(); } diff --git a/external/parallel-rdp/ParallelRDPWrapper.hpp b/external/parallel-rdp/ParallelRDPWrapper.hpp index 04fd1924..b8a5b696 100644 --- a/external/parallel-rdp/ParallelRDPWrapper.hpp +++ b/external/parallel-rdp/ParallelRDPWrapper.hpp @@ -15,7 +15,7 @@ public: virtual ~WindowInfo() = default; }; - void Init(Vulkan::InstanceFactory*, std::unique_ptr&&, std::unique_ptr&&, const u8*); + void Init(const std::shared_ptr&, const std::shared_ptr&, const std::shared_ptr&, const u8*); ParallelRDP() = default; void UpdateScreen(n64::VI&, bool = false); @@ -24,11 +24,11 @@ public: bool IsFramerateUnlocked(); void SetFramerateUnlocked(bool); private: - void LoadWSIPlatform(Vulkan::InstanceFactory*, std::unique_ptr&&, std::unique_ptr&&); + void LoadWSIPlatform(const std::shared_ptr&, const std::shared_ptr&, const std::shared_ptr&); void DrawFullscreenTexturedQuad(Util::IntrusivePtr, Util::IntrusivePtr); void UpdateScreen(Util::IntrusivePtr); - std::unique_ptr wsi; - std::unique_ptr command_processor; - std::unique_ptr windowInfo; + std::shared_ptr wsi; + std::shared_ptr command_processor; + std::shared_ptr windowInfo; }; diff --git a/src/backend/core/Interpreter.cpp b/src/backend/core/Interpreter.cpp index 675ee6b4..728269fc 100644 --- a/src/backend/core/Interpreter.cpp +++ b/src/backend/core/Interpreter.cpp @@ -48,6 +48,10 @@ int Interpreter::Step() { return 1; } + if((u64)regs.pc == 0xFFFFFFFF8002070C) { + printf("\n"); + } + regs.oldPC = regs.pc; regs.pc = regs.nextPC; regs.nextPC += 4; diff --git a/src/backend/core/Mem.cpp b/src/backend/core/Mem.cpp index dfb65dc3..687cdc2e 100644 --- a/src/backend/core/Mem.cpp +++ b/src/backend/core/Mem.cpp @@ -337,6 +337,11 @@ template<> void Mem::Write(Registers& regs, u32 paddr, u32 val) { const auto pointer = writePages[page]; SI& si = mmio.si; + if(paddr == 0x0023e650) { + //DumpRDRAM(); + //fmt::print("PC is 0x{:016X}: Writing 0x{:02X} -> 0x{:08X}\n", (u64)regs.oldPC, (u8)val, paddr); + } + if(pointer) { ((u8*)pointer)[BYTE_ADDRESS(offset)] = val; } else { @@ -382,6 +387,11 @@ template<> void Mem::Write(Registers& regs, u32 paddr, u32 val) { const auto pointer = writePages[page]; SI& si = mmio.si; + if(paddr == 0x0023e650) { + //DumpRDRAM(); + //fmt::print("PC is 0x{:016X}: Writing 0x{:04X} -> 0x{:08X}\n", (u64) regs.oldPC, (u16) val, paddr); + } + if(pointer) { Util::WriteAccess((u8*)pointer, HALF_ADDRESS(offset), val); } else { @@ -427,6 +437,11 @@ template<> void Mem::Write(Registers& regs, u32 paddr, u32 val) { const auto pointer = writePages[page]; SI& si = mmio.si; + if(paddr == 0x0023e650) { + //DumpRDRAM(); + //fmt::print("PC is 0x{:016X}: Writing 0x{:08X} -> 0x{:08X}\n", (u64) regs.oldPC, val, paddr); + } + if(pointer) { Util::WriteAccess((u8*)pointer, offset, val); } else { @@ -466,6 +481,11 @@ void Mem::Write(Registers& regs, u32 paddr, u64 val) { const auto pointer = writePages[page]; SI& si = mmio.si; + if(paddr == 0x0023e650) { + //DumpRDRAM(); + //fmt::print("PC is 0x{:016X}: Writing 0x{:016X} -> 0x{:08X}\n", (u64) regs.oldPC, val, paddr); + } + if(pointer) { Util::WriteAccess((u8*)pointer, offset, val); } else { diff --git a/src/backend/core/interpreter/instructions.cpp b/src/backend/core/interpreter/instructions.cpp index f38b42e3..3f197c37 100644 --- a/src/backend/core/interpreter/instructions.cpp +++ b/src/backend/core/interpreter/instructions.cpp @@ -465,15 +465,19 @@ void Interpreter::sb(u32 instr) { void Interpreter::sc(u32 instr) { u64 address = regs.gpr[RS(instr)] + (s16)instr; - if (check_address_error(0b11, address)) { - regs.cop0.FireException(ExceptionCode::AddressErrorStore, 0, regs.oldPC); - return; - } - if(regs.cop0.llbit) { regs.cop0.llbit = false; + + if (check_address_error(0b11, address)) { + regs.gpr[RT(instr)] = 0; + regs.cop0.HandleTLBException(address); + regs.cop0.FireException(ExceptionCode::AddressErrorStore, 0, regs.oldPC); + return; + } + u32 paddr = 0; if(!regs.cop0.MapVAddr(Cop0::STORE, address, paddr)) { + regs.gpr[RT(instr)] = 0; regs.cop0.HandleTLBException(address); regs.cop0.FireException(regs.cop0.GetTLBExceptionCode(regs.cop0.tlbError, Cop0::STORE), 0, regs.oldPC); } else { @@ -496,16 +500,20 @@ void Interpreter::scd(u32 instr) { } s64 address = regs.gpr[RS(instr)] + (s16)instr; - if (check_address_error(0b111, address)) { - regs.cop0.HandleTLBException(address); - regs.cop0.FireException(ExceptionCode::AddressErrorStore, 0, regs.oldPC); - return; - } if(regs.cop0.llbit) { regs.cop0.llbit = false; + + if (check_address_error(0b111, address)) { + regs.gpr[RT(instr)] = 0; + regs.cop0.HandleTLBException(address); + regs.cop0.FireException(ExceptionCode::AddressErrorStore, 0, regs.oldPC); + return; + } + u32 paddr = 0; if(!regs.cop0.MapVAddr(Cop0::STORE, address, paddr)) { + regs.gpr[RT(instr)] = 0; regs.cop0.HandleTLBException(address); regs.cop0.FireException(regs.cop0.GetTLBExceptionCode(regs.cop0.tlbError, Cop0::STORE), 0, regs.oldPC); } else { diff --git a/src/backend/core/mmio/Audio.cpp b/src/backend/core/mmio/Audio.cpp index 06fff418..215ff80d 100644 --- a/src/backend/core/mmio/Audio.cpp +++ b/src/backend/core/mmio/Audio.cpp @@ -11,19 +11,13 @@ namespace n64 { void audioCallback(void* user, Uint8* stream, int length) { auto audioDevice = (AudioDevice*)user; int gotten = 0, available = 0; + if (audioDevice) { audioDevice->LockMutex(); - } - - if (audioDevice) { - available = SDL_AudioStreamAvailable(audioDevice->GetStream().get()); - } - - if (available > 0 && audioDevice) { - gotten = SDL_AudioStreamGet(audioDevice->GetStream().get(), stream, length); - } - - if (audioDevice) { + available = SDL_AudioStreamAvailable(audioDevice->GetStream()); + if (available > 0) { + gotten = SDL_AudioStreamGet(audioDevice->GetStream(), stream, length); + } audioDevice->UnlockMutex(); } @@ -37,11 +31,18 @@ void audioCallback(void* user, Uint8* stream, int length) { } } -AudioDevice::AudioDevice() : audioStream(SDL_NewAudioStream, SDL_FreeAudioStream, "audioStream", SYSTEM_SAMPLE_FORMAT, 2, AUDIO_SAMPLE_RATE, SYSTEM_SAMPLE_FORMAT, 2, AUDIO_SAMPLE_RATE), - audioStreamMutex(SDL_CreateMutex, SDL_DestroyMutex, "audioStreamMutex") { +AudioDevice::~AudioDevice() { + LockMutex(); + SDL_FreeAudioStream(GetStream()); + UnlockMutex(); + SDL_DestroyMutex(audioStreamMutex); +} + +AudioDevice::AudioDevice() : audioStream(SDL_NewAudioStream(SYSTEM_SAMPLE_FORMAT, 2, AUDIO_SAMPLE_RATE, SYSTEM_SAMPLE_FORMAT, 2, AUDIO_SAMPLE_RATE)), + audioStreamMutex(SDL_CreateMutex()) { SDL_InitSubSystem(SDL_INIT_AUDIO); - if(!audioStreamMutex.get()) { + if(!audioStreamMutex) { Util::panic("Unable to initialize audio mutex: {}", SDL_GetError()); } @@ -66,15 +67,16 @@ void AudioDevice::PushSample(float left, float volumeL, float right, float volum float adjustedR = right * volumeR; float samples[2]{ adjustedL, adjustedR }; - auto availableBytes = (float)SDL_AudioStreamAvailable(audioStream.get()); + auto availableBytes = (float)SDL_AudioStreamAvailable(audioStream); if(availableBytes <= BYTES_PER_HALF_SECOND) { - SDL_AudioStreamPut(audioStream.get(), samples, 2 * sizeof(float)); + SDL_AudioStreamPut(audioStream, samples, 2 * sizeof(float)); } } void AudioDevice::AdjustSampleRate(int sampleRate) { LockMutex(); - audioStream.Construct(SDL_NewAudioStream, SYSTEM_SAMPLE_FORMAT, 2, sampleRate, SYSTEM_SAMPLE_FORMAT, 2, AUDIO_SAMPLE_RATE); + SDL_FreeAudioStream(audioStream); + audioStream = SDL_NewAudioStream(SYSTEM_SAMPLE_FORMAT, 2, sampleRate, SYSTEM_SAMPLE_FORMAT, 2, AUDIO_SAMPLE_RATE); UnlockMutex(); } } \ No newline at end of file diff --git a/src/backend/core/mmio/Audio.hpp b/src/backend/core/mmio/Audio.hpp index 487a221c..53868557 100644 --- a/src/backend/core/mmio/Audio.hpp +++ b/src/backend/core/mmio/Audio.hpp @@ -5,24 +5,23 @@ namespace n64 { struct AudioDevice { AudioDevice(); + ~AudioDevice(); void PushSample(float, float, float, float); void AdjustSampleRate(int); void LockMutex() { - if(audioStreamMutex.get()) - SDL_LockMutex(audioStreamMutex.get()); + if(audioStreamMutex) + SDL_LockMutex(audioStreamMutex); } void UnlockMutex() { - if (audioStreamMutex.get()) - SDL_UnlockMutex(audioStreamMutex.get()); + if (audioStreamMutex) + SDL_UnlockMutex(audioStreamMutex); } - Util::AutoRelease& GetStream() { return audioStream; } + SDL_AudioStream* GetStream() { return audioStream; } private: - Util::AutoRelease audioStream; - Util::AutoRelease audioStreamMutex; + SDL_AudioStream* audioStream; + SDL_mutex* audioStreamMutex; SDL_AudioSpec audioSpec{}; SDL_AudioSpec request{}; SDL_AudioDeviceID handle{}; diff --git a/src/frontend/EmuThread.cpp b/src/frontend/EmuThread.cpp index 02c8d465..f05af38e 100644 --- a/src/frontend/EmuThread.cpp +++ b/src/frontend/EmuThread.cpp @@ -1,17 +1,13 @@ #include -#include -#include -#include "Audio.hpp" #include -EmuThread::EmuThread(std::unique_ptr&& instance_, std::unique_ptr&& wsiPlatform_, std::unique_ptr&& windowInfo_, SettingsWindow& settings) noexcept - : instance(std::move(instance_)), wsiPlatform(std::move(wsiPlatform_)), - windowInfo(std::move(windowInfo_)), - controller(SDL_GameControllerClose, "GameController"), +EmuThread::EmuThread(const std::shared_ptr& instance_, const std::shared_ptr& wsiPlatform_, const std::shared_ptr& windowInfo_, SettingsWindow& settings) noexcept + : instance(instance_), wsiPlatform(wsiPlatform_), + windowInfo(windowInfo_), core(parallel), settings(settings) {} [[noreturn]] void EmuThread::run() noexcept { - parallel.Init(instance.get(), std::move(wsiPlatform), std::move(windowInfo), core.cpu->GetMem().GetRDRAMPtr()); + parallel.Init(instance, wsiPlatform, windowInfo, core.cpu->GetMem().GetRDRAMPtr()); SDL_InitSubSystem(SDL_INIT_GAMECONTROLLER); bool controllerConnected = false; @@ -25,11 +21,11 @@ EmuThread::EmuThread(std::unique_ptr&& instance_, std::unique switch(e.type) { case SDL_CONTROLLERDEVICEADDED: { const int index = e.cdevice.which; - controller.Construct(SDL_GameControllerOpen, index); + controller = SDL_GameControllerOpen(index); Util::info("Found controller!"); - auto serial = SDL_GameControllerGetSerial(controller.get()); - auto name = SDL_GameControllerName(controller.get()); - auto path = SDL_GameControllerPath(controller.get()); + auto serial = SDL_GameControllerGetSerial(controller); + auto name = SDL_GameControllerName(controller); + auto path = SDL_GameControllerPath(controller); Util::info("\tName: {}", name ? name : "Not available"); Util::info("\tSerial: {}", serial ? serial : "Not available"); Util::info("\tPath: {}", path ? path : "Not available"); @@ -37,7 +33,7 @@ EmuThread::EmuThread(std::unique_ptr&& instance_, std::unique } break; case SDL_CONTROLLERDEVICEREMOVED: { controllerConnected = false; - controller.Destroy(); + SDL_GameControllerClose(controller); } break; } } @@ -59,22 +55,22 @@ EmuThread::EmuThread(std::unique_ptr&& instance_, std::unique if(controllerConnected) { n64::PIF& pif = core.cpu->GetMem().mmio.si.pif; - pif.UpdateButton(0, n64::Controller::Key::A, SDL_GameControllerGetButton(controller.get(), SDL_CONTROLLER_BUTTON_A)); - pif.UpdateButton(0, n64::Controller::Key::B, SDL_GameControllerGetButton(controller.get(), SDL_CONTROLLER_BUTTON_X)); - pif.UpdateButton(0, n64::Controller::Key::Z, SDL_GameControllerGetAxis(controller.get(), SDL_CONTROLLER_AXIS_TRIGGERLEFT) == SDL_JOYSTICK_AXIS_MAX); - pif.UpdateButton(0, n64::Controller::Key::Start, SDL_GameControllerGetButton(controller.get(), SDL_CONTROLLER_BUTTON_START)); - pif.UpdateButton(0, n64::Controller::Key::DUp, SDL_GameControllerGetButton(controller.get(), SDL_CONTROLLER_BUTTON_DPAD_UP)); - pif.UpdateButton(0, n64::Controller::Key::DDown, SDL_GameControllerGetButton(controller.get(), SDL_CONTROLLER_BUTTON_DPAD_DOWN)); - pif.UpdateButton(0, n64::Controller::Key::DLeft, SDL_GameControllerGetButton(controller.get(), SDL_CONTROLLER_BUTTON_DPAD_LEFT)); - pif.UpdateButton(0, n64::Controller::Key::DRight, SDL_GameControllerGetButton(controller.get(), SDL_CONTROLLER_BUTTON_DPAD_RIGHT)); - pif.UpdateButton(0, n64::Controller::Key::LT, SDL_GameControllerGetButton(controller.get(), SDL_CONTROLLER_BUTTON_LEFTSHOULDER)); - pif.UpdateButton(0, n64::Controller::Key::RT, SDL_GameControllerGetButton(controller.get(), SDL_CONTROLLER_BUTTON_RIGHTSHOULDER)); - pif.UpdateButton(0, n64::Controller::Key::CUp, SDL_GameControllerGetAxis(controller.get(), SDL_CONTROLLER_AXIS_RIGHTY) <= -127); - pif.UpdateButton(0, n64::Controller::Key::CDown, SDL_GameControllerGetAxis(controller.get(), SDL_CONTROLLER_AXIS_RIGHTY) >= 127); - pif.UpdateButton(0, n64::Controller::Key::CLeft, SDL_GameControllerGetAxis(controller.get(), SDL_CONTROLLER_AXIS_RIGHTX) <= -127); - pif.UpdateButton(0, n64::Controller::Key::CRight, SDL_GameControllerGetAxis(controller.get(), SDL_CONTROLLER_AXIS_RIGHTX) >= 127); + pif.UpdateButton(0, n64::Controller::Key::A, SDL_GameControllerGetButton(controller, SDL_CONTROLLER_BUTTON_A)); + pif.UpdateButton(0, n64::Controller::Key::B, SDL_GameControllerGetButton(controller, SDL_CONTROLLER_BUTTON_X)); + pif.UpdateButton(0, n64::Controller::Key::Z, SDL_GameControllerGetAxis(controller, SDL_CONTROLLER_AXIS_TRIGGERLEFT) == SDL_JOYSTICK_AXIS_MAX); + pif.UpdateButton(0, n64::Controller::Key::Start, SDL_GameControllerGetButton(controller, SDL_CONTROLLER_BUTTON_START)); + pif.UpdateButton(0, n64::Controller::Key::DUp, SDL_GameControllerGetButton(controller, SDL_CONTROLLER_BUTTON_DPAD_UP)); + pif.UpdateButton(0, n64::Controller::Key::DDown, SDL_GameControllerGetButton(controller, SDL_CONTROLLER_BUTTON_DPAD_DOWN)); + pif.UpdateButton(0, n64::Controller::Key::DLeft, SDL_GameControllerGetButton(controller, SDL_CONTROLLER_BUTTON_DPAD_LEFT)); + pif.UpdateButton(0, n64::Controller::Key::DRight, SDL_GameControllerGetButton(controller, SDL_CONTROLLER_BUTTON_DPAD_RIGHT)); + pif.UpdateButton(0, n64::Controller::Key::LT, SDL_GameControllerGetButton(controller, SDL_CONTROLLER_BUTTON_LEFTSHOULDER)); + pif.UpdateButton(0, n64::Controller::Key::RT, SDL_GameControllerGetButton(controller, SDL_CONTROLLER_BUTTON_RIGHTSHOULDER)); + pif.UpdateButton(0, n64::Controller::Key::CUp, SDL_GameControllerGetAxis(controller, SDL_CONTROLLER_AXIS_RIGHTY) <= -127); + pif.UpdateButton(0, n64::Controller::Key::CDown, SDL_GameControllerGetAxis(controller, SDL_CONTROLLER_AXIS_RIGHTY) >= 127); + pif.UpdateButton(0, n64::Controller::Key::CLeft, SDL_GameControllerGetAxis(controller, SDL_CONTROLLER_AXIS_RIGHTX) <= -127); + pif.UpdateButton(0, n64::Controller::Key::CRight, SDL_GameControllerGetAxis(controller, SDL_CONTROLLER_AXIS_RIGHTX) >= 127); - float xclamped = SDL_GameControllerGetAxis(controller.get(), SDL_CONTROLLER_AXIS_LEFTX); + float xclamped = SDL_GameControllerGetAxis(controller, SDL_CONTROLLER_AXIS_LEFTX); if(xclamped < 0) { xclamped /= float(std::abs(SDL_JOYSTICK_AXIS_MIN)); } else { @@ -83,7 +79,7 @@ EmuThread::EmuThread(std::unique_ptr&& instance_, std::unique xclamped *= 86; - float yclamped = SDL_GameControllerGetAxis(controller.get(), SDL_CONTROLLER_AXIS_LEFTY); + float yclamped = SDL_GameControllerGetAxis(controller, SDL_CONTROLLER_AXIS_LEFTY); if(yclamped < 0) { yclamped /= float(std::abs(SDL_JOYSTICK_AXIS_MIN)); } else { diff --git a/src/frontend/EmuThread.hpp b/src/frontend/EmuThread.hpp index 481e30b8..99c3b700 100644 --- a/src/frontend/EmuThread.hpp +++ b/src/frontend/EmuThread.hpp @@ -9,37 +9,37 @@ class EmuThread : public QThread { Q_OBJECT - std::unique_ptr instance; - std::unique_ptr wsiPlatform; - std::unique_ptr windowInfo; + std::shared_ptr instance; + std::shared_ptr wsiPlatform; + std::shared_ptr windowInfo; public: - explicit EmuThread(std::unique_ptr&& instance, std::unique_ptr&& wsiPlatform, std::unique_ptr&& windowInfo, SettingsWindow&) noexcept; + explicit EmuThread(const std::shared_ptr& instance, const std::shared_ptr& wsiPlatform, const std::shared_ptr& windowInfo, SettingsWindow&) noexcept; [[noreturn]] void run() noexcept override; - Util::AutoRelease controller; + SDL_GameController* controller = nullptr; ParallelRDP parallel; n64::Core core; SettingsWindow& settings; - bool running = false; - void TogglePause() - { - running = !running; + void TogglePause() { + core.pause = !core.pause; } - void Reset() - { - running = false; + void SetRender(bool v) { + core.render = v; + } + + void Reset() { + core.pause = true; core.Stop(); core.LoadROM(core.rom); - running = true; + core.pause = false; } - void Stop() - { + void Stop() { core.rom = {}; - running = false; + core.pause = true; core.Stop(); } }; \ No newline at end of file diff --git a/src/frontend/KaizenQt.cpp b/src/frontend/KaizenQt.cpp index e3de7e1e..32e3f066 100644 --- a/src/frontend/KaizenQt.cpp +++ b/src/frontend/KaizenQt.cpp @@ -28,14 +28,13 @@ KaizenQt::KaizenQt() noexcept : QWidget(nullptr) { grabKeyboard(); }); } + void KaizenQt::ConnectMainWindowSignalsToSlots() noexcept { connect(mainWindow.get(), &MainWindowController::OpenSettings, this, [this]() { settingsWindow->show(); }); connect(mainWindow.get(), &MainWindowController::OpenROM, this, &KaizenQt::LoadROM); - connect(mainWindow.get(), &MainWindowController::Exit, this, []() { - QApplication::quit(); - }); + connect(mainWindow.get(), &MainWindowController::Exit, this, &KaizenQt::Quit); connect(mainWindow.get(), &MainWindowController::Reset, emuThread.get(), &EmuThread::Reset); connect(mainWindow.get(), &MainWindowController::Stop, emuThread.get(), &EmuThread::Stop); connect(mainWindow.get(), &MainWindowController::Stop, this, [this]() { @@ -61,8 +60,12 @@ void KaizenQt::LoadROM(const QString& fileName) noexcept { mainWindow->setWindowTitle(emuThread->core.cpu->GetMem().rom.gameNameDB.c_str()); } -void KaizenQt::closeEvent(QCloseEvent*) { - emuThread->Stop(); +void KaizenQt::Quit() noexcept { + if(emuThread) { + emuThread->SetRender(false); + emuThread->Stop(); + } + QApplication::quit(); } void KaizenQt::LoadTAS(const QString& fileName) noexcept { diff --git a/src/frontend/KaizenQt.hpp b/src/frontend/KaizenQt.hpp index 21f1cdd7..ec7cf786 100644 --- a/src/frontend/KaizenQt.hpp +++ b/src/frontend/KaizenQt.hpp @@ -33,8 +33,8 @@ public: void dragEnterEvent(QDragEnterEvent*) override; void keyPressEvent(QKeyEvent*) override; void keyReleaseEvent(QKeyEvent*) override; - void closeEvent(QCloseEvent*) override; private: + void Quit() noexcept; void ConnectMainWindowSignalsToSlots() noexcept; std::unique_ptr mainWindow; std::unique_ptr settingsWindow; diff --git a/src/frontend/MainWindow.cpp b/src/frontend/MainWindow.cpp index 85b58fef..7470a31f 100644 --- a/src/frontend/MainWindow.cpp +++ b/src/frontend/MainWindow.cpp @@ -31,6 +31,10 @@ void MainWindowController::ConnectSignalsToSlots() noexcept { emit Exit(); }); + connect(this, &MainWindowController::destroyed, this, [this]() { + emit Exit(); + }); + connect(view.actionReset, &QAction::triggered, this, [this]() { emit Reset(); }); diff --git a/src/utils/MemoryHelpers.hpp b/src/utils/MemoryHelpers.hpp index e9f72ec5..2fae7a09 100644 --- a/src/utils/MemoryHelpers.hpp +++ b/src/utils/MemoryHelpers.hpp @@ -6,46 +6,6 @@ #include namespace Util { -template -struct AutoRelease { - AutoRelease(void (*dtor)(T*), const char* name = "") : dtor(dtor), name(name) { } - - AutoRelease(T* (*ctor)(Args...), void (*dtor)(T*), const char* name = "", Args... args) : dtor(dtor), name(name) { - thing = ctor(args...); - } - - T* get() { - if (!thing) { - Util::panic("AutoRelease::{} is null!", name); - } - return thing; - } - - void Construct(T* (*ctor)(Args...), Args... args) { - if(thing) { - dtor(thing); - } - - thing = ctor(args...); - } - - void Destroy() { - if(thing) { - dtor(thing); - } - } - - ~AutoRelease() { - if(thing) { - dtor(thing); - } - } -private: - const char* name = ""; - T* thing = nullptr; - void (*dtor)(T*) = nullptr; -}; - template static FORCE_INLINE T ReadAccess(const u8* data, u32 index) { if constexpr (sizeof(T) == 8) {