From 0904638df08fb617f6fe672587e4bd704c2d42e7 Mon Sep 17 00:00:00 2001 From: wheremyfoodat <44909372+wheremyfoodat@users.noreply.github.com> Date: Wed, 19 Jul 2023 20:51:45 +0300 Subject: [PATCH] [Cheats] Add boilerplate --- CMakeLists.txt | 4 ++-- include/cheats.hpp | 24 ++++++++++++++++++++++++ include/emulator.hpp | 5 +++++ src/core/cheats.cpp | 5 +++++ src/emulator.cpp | 6 ++++++ 5 files changed, 42 insertions(+), 2 deletions(-) create mode 100644 include/cheats.hpp create mode 100644 src/core/cheats.cpp diff --git a/CMakeLists.txt b/CMakeLists.txt index 620a1c27..867f1e81 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -96,7 +96,7 @@ endif() set(SOURCE_FILES src/main.cpp src/emulator.cpp src/io_file.cpp src/config.cpp src/core/CPU/cpu_dynarmic.cpp src/core/CPU/dynarmic_cycles.cpp src/core/memory.cpp src/renderer.cpp src/core/renderer_null/renderer_null.cpp - src/httpserver.cpp src/stb_image_write.c + src/httpserver.cpp src/stb_image_write.c src/core/cheats.cpp ) set(CRYPTO_SOURCE_FILES src/core/crypto/aes_engine.cpp) set(KERNEL_SOURCE_FILES src/core/kernel/kernel.cpp src/core/kernel/resource_limits.cpp @@ -149,7 +149,7 @@ set(HEADER_FILES include/emulator.hpp include/helpers.hpp include/termcolor.hpp include/result/result_common.hpp include/result/result_fs.hpp include/result/result_fnd.hpp include/result/result_gsp.hpp include/result/result_kernel.hpp include/result/result_os.hpp include/crypto/aes_engine.hpp include/metaprogramming.hpp include/PICA/pica_vertex.hpp - include/config.hpp include/services/ir_user.hpp include/httpserver.hpp + include/config.hpp include/services/ir_user.hpp include/httpserver.hpp include/cheats.hpp ) set(THIRD_PARTY_SOURCE_FILES third_party/imgui/imgui.cpp diff --git a/include/cheats.hpp b/include/cheats.hpp new file mode 100644 index 00000000..22843544 --- /dev/null +++ b/include/cheats.hpp @@ -0,0 +1,24 @@ +#pragma once +#include +#include + +#include "helpers.hpp" + +class ActionReplay { + using Cheat = std::vector; // A cheat is really just a bunch of u32 opcodes + std::vector cheats; + + u32 offset1, offset2; // Memory offset registers. Non-persistent. + u32 data1, data2; // Data offset registers. Non-persistent. + u32 storage1, storage2; // Storage registers. Persistent. + + // When an instruction does not specify which offset or data register to use, we use the "active" one + // Which is by default #1 and may be changed by certain AR operations + u32 *activeOffset, *activeData; + + public: + ActionReplay(); + void addCheat(const Cheat& cheat); + void runCheats(); + void reset(); +}; \ No newline at end of file diff --git a/include/emulator.hpp b/include/emulator.hpp index d99eff1d..187d6eca 100644 --- a/include/emulator.hpp +++ b/include/emulator.hpp @@ -7,6 +7,7 @@ #include #include "PICA/gpu.hpp" +#include "cheats.hpp" #include "config.hpp" #include "cpu.hpp" #include "crypto/aes_engine.hpp" @@ -31,6 +32,7 @@ class Emulator { Memory memory; Kernel kernel; Crypto::AESEngine aesEngine; + ActionReplay cheats; SDL_Window* window; @@ -41,6 +43,9 @@ class Emulator { SDL_GameController* gameController = nullptr; int gameControllerID; + // Shows whether we've loaded any action replay codes + bool haveCheats = false; + // Variables to keep track of whether the user is controlling the 3DS analog stick with their keyboard // This is done so when a gamepad is connected, we won't automatically override the 3DS analog stick settings with the gamepad's state // And so the user can still use the keyboard to control the analog diff --git a/src/core/cheats.cpp b/src/core/cheats.cpp new file mode 100644 index 00000000..a797d092 --- /dev/null +++ b/src/core/cheats.cpp @@ -0,0 +1,5 @@ +#include "cheats.hpp" + +ActionReplay::ActionReplay() { reset(); } + +void ActionReplay::reset() { cheats.clear(); } \ No newline at end of file diff --git a/src/emulator.cpp b/src/emulator.cpp index 8ab6e06e..75f8ab1c 100644 --- a/src/emulator.cpp +++ b/src/emulator.cpp @@ -76,6 +76,12 @@ void Emulator::reset(ReloadOption reload) { // Otherwise resetting the kernel or cpu might nuke them cpu.setReg(13, VirtualAddrs::StackTop); // Set initial SP + // We're resetting without reloading the ROM, so yeet cheats + if (reload == ReloadOption::NoReload) { + haveCheats = false; + cheats.reset(); + } + // If a ROM is active and we reset, with the reload option enabled then reload it. // This is necessary to set up stack, executable memory, .data/.rodata/.bss all over again if (reload == ReloadOption::Reload && romType != ROMType::None && romPath.has_value()) {