diff --git a/Source/Core/Core/CheatSearch.cpp b/Source/Core/Core/CheatSearch.cpp index 1b85cd9d14..9710f31624 100644 --- a/Source/Core/Core/CheatSearch.cpp +++ b/Source/Core/Core/CheatSearch.cpp @@ -101,87 +101,87 @@ std::vector Cheats::GetValueAsByteVector(const Cheats::SearchValue& value) namespace { template -static PowerPC::TryReadResult +static std::optional> TryReadValueFromEmulatedMemory(u32 addr, PowerPC::RequestedAddressSpace space); template <> -PowerPC::TryReadResult TryReadValueFromEmulatedMemory(u32 addr, - PowerPC::RequestedAddressSpace space) +std::optional> +TryReadValueFromEmulatedMemory(u32 addr, PowerPC::RequestedAddressSpace space) { return PowerPC::HostTryReadU8(addr, space); } template <> -PowerPC::TryReadResult TryReadValueFromEmulatedMemory(u32 addr, - PowerPC::RequestedAddressSpace space) +std::optional> +TryReadValueFromEmulatedMemory(u32 addr, PowerPC::RequestedAddressSpace space) { return PowerPC::HostTryReadU16(addr, space); } template <> -PowerPC::TryReadResult TryReadValueFromEmulatedMemory(u32 addr, - PowerPC::RequestedAddressSpace space) +std::optional> +TryReadValueFromEmulatedMemory(u32 addr, PowerPC::RequestedAddressSpace space) { return PowerPC::HostTryReadU32(addr, space); } template <> -PowerPC::TryReadResult TryReadValueFromEmulatedMemory(u32 addr, - PowerPC::RequestedAddressSpace space) +std::optional> +TryReadValueFromEmulatedMemory(u32 addr, PowerPC::RequestedAddressSpace space) { return PowerPC::HostTryReadU64(addr, space); } template <> -PowerPC::TryReadResult TryReadValueFromEmulatedMemory(u32 addr, - PowerPC::RequestedAddressSpace space) +std::optional> +TryReadValueFromEmulatedMemory(u32 addr, PowerPC::RequestedAddressSpace space) { auto tmp = PowerPC::HostTryReadU8(addr, space); if (!tmp) - return PowerPC::TryReadResult(); - return PowerPC::TryReadResult(tmp.translated, Common::BitCast(tmp.value)); + return std::nullopt; + return PowerPC::ReadResult(tmp->translated, Common::BitCast(tmp->value)); } template <> -PowerPC::TryReadResult TryReadValueFromEmulatedMemory(u32 addr, - PowerPC::RequestedAddressSpace space) +std::optional> +TryReadValueFromEmulatedMemory(u32 addr, PowerPC::RequestedAddressSpace space) { auto tmp = PowerPC::HostTryReadU16(addr, space); if (!tmp) - return PowerPC::TryReadResult(); - return PowerPC::TryReadResult(tmp.translated, Common::BitCast(tmp.value)); + return std::nullopt; + return PowerPC::ReadResult(tmp->translated, Common::BitCast(tmp->value)); } template <> -PowerPC::TryReadResult TryReadValueFromEmulatedMemory(u32 addr, - PowerPC::RequestedAddressSpace space) +std::optional> +TryReadValueFromEmulatedMemory(u32 addr, PowerPC::RequestedAddressSpace space) { auto tmp = PowerPC::HostTryReadU32(addr, space); if (!tmp) - return PowerPC::TryReadResult(); - return PowerPC::TryReadResult(tmp.translated, Common::BitCast(tmp.value)); + return std::nullopt; + return PowerPC::ReadResult(tmp->translated, Common::BitCast(tmp->value)); } template <> -PowerPC::TryReadResult TryReadValueFromEmulatedMemory(u32 addr, - PowerPC::RequestedAddressSpace space) +std::optional> +TryReadValueFromEmulatedMemory(u32 addr, PowerPC::RequestedAddressSpace space) { auto tmp = PowerPC::HostTryReadU64(addr, space); if (!tmp) - return PowerPC::TryReadResult(); - return PowerPC::TryReadResult(tmp.translated, Common::BitCast(tmp.value)); + return std::nullopt; + return PowerPC::ReadResult(tmp->translated, Common::BitCast(tmp->value)); } template <> -PowerPC::TryReadResult TryReadValueFromEmulatedMemory(u32 addr, - PowerPC::RequestedAddressSpace space) +std::optional> +TryReadValueFromEmulatedMemory(u32 addr, PowerPC::RequestedAddressSpace space) { return PowerPC::HostTryReadF32(addr, space); } template <> -PowerPC::TryReadResult TryReadValueFromEmulatedMemory(u32 addr, - PowerPC::RequestedAddressSpace space) +std::optional> +TryReadValueFromEmulatedMemory(u32 addr, PowerPC::RequestedAddressSpace space) { return PowerPC::HostTryReadF64(addr, space); } @@ -230,11 +230,11 @@ Cheats::NewSearch(const std::vector& memory_ranges, if (!current_value) continue; - if (validator(current_value.value)) + if (validator(current_value->value)) { auto& r = results.emplace_back(); - r.m_value = current_value.value; - r.m_value_state = current_value.translated ? + r.m_value = current_value->value; + r.m_value_state = current_value->translated ? Cheats::SearchResultValueState::ValueFromVirtualMemory : Cheats::SearchResultValueState::ValueFromPhysicalMemory; r.m_address = addr; @@ -284,11 +284,11 @@ Cheats::NextSearch(const std::vector>& previous_results, // if the previous state was invalid we always update the value to avoid getting stuck in an // invalid state if (!previous_result.IsValueValid() || - validator(current_value.value, previous_result.m_value)) + validator(current_value->value, previous_result.m_value)) { auto& r = results.emplace_back(); - r.m_value = current_value.value; - r.m_value_state = current_value.translated ? + r.m_value = current_value->value; + r.m_value_state = current_value->translated ? Cheats::SearchResultValueState::ValueFromVirtualMemory : Cheats::SearchResultValueState::ValueFromPhysicalMemory; r.m_address = addr; diff --git a/Source/Core/Core/PowerPC/MMU.cpp b/Source/Core/Core/PowerPC/MMU.cpp index f97f916f2f..6f1ef604f9 100644 --- a/Source/Core/Core/PowerPC/MMU.cpp +++ b/Source/Core/Core/PowerPC/MMU.cpp @@ -468,34 +468,35 @@ u32 HostRead_Instruction(const u32 address) return ReadFromHardware(address); } -TryReadResult HostTryReadInstruction(const u32 address, RequestedAddressSpace space) +std::optional> HostTryReadInstruction(const u32 address, + RequestedAddressSpace space) { if (!HostIsInstructionRAMAddress(address, space)) - return TryReadResult(); + return std::nullopt; switch (space) { case RequestedAddressSpace::Effective: { const u32 value = ReadFromHardware(address); - return TryReadResult(!!MSR.DR, value); + return ReadResult(!!MSR.DR, value); } case RequestedAddressSpace::Physical: { const u32 value = ReadFromHardware(address); - return TryReadResult(false, value); + return ReadResult(false, value); } case RequestedAddressSpace::Virtual: { if (!MSR.DR) - return TryReadResult(); + return std::nullopt; const u32 value = ReadFromHardware(address); - return TryReadResult(true, value); + return ReadResult(true, value); } } ASSERT(0); - return TryReadResult(); + return std::nullopt; } static void Memcheck(u32 address, u64 var, bool write, size_t size) @@ -574,70 +575,70 @@ float Read_F32(const u32 address) } template -static TryReadResult HostTryReadUX(const u32 address, RequestedAddressSpace space) +static std::optional> HostTryReadUX(const u32 address, RequestedAddressSpace space) { if (!HostIsRAMAddress(address, space)) - return TryReadResult(); + return std::nullopt; switch (space) { case RequestedAddressSpace::Effective: { T value = ReadFromHardware(address); - return TryReadResult(!!MSR.DR, std::move(value)); + return ReadResult(!!MSR.DR, std::move(value)); } case RequestedAddressSpace::Physical: { T value = ReadFromHardware(address); - return TryReadResult(false, std::move(value)); + return ReadResult(false, std::move(value)); } case RequestedAddressSpace::Virtual: { if (!MSR.DR) - return TryReadResult(); + return std::nullopt; T value = ReadFromHardware(address); - return TryReadResult(true, std::move(value)); + return ReadResult(true, std::move(value)); } } ASSERT(0); - return TryReadResult(); + return std::nullopt; } -TryReadResult HostTryReadU8(u32 address, RequestedAddressSpace space) +std::optional> HostTryReadU8(u32 address, RequestedAddressSpace space) { return HostTryReadUX(address, space); } -TryReadResult HostTryReadU16(u32 address, RequestedAddressSpace space) +std::optional> HostTryReadU16(u32 address, RequestedAddressSpace space) { return HostTryReadUX(address, space); } -TryReadResult HostTryReadU32(u32 address, RequestedAddressSpace space) +std::optional> HostTryReadU32(u32 address, RequestedAddressSpace space) { return HostTryReadUX(address, space); } -TryReadResult HostTryReadU64(u32 address, RequestedAddressSpace space) +std::optional> HostTryReadU64(u32 address, RequestedAddressSpace space) { return HostTryReadUX(address, space); } -TryReadResult HostTryReadF32(u32 address, RequestedAddressSpace space) +std::optional> HostTryReadF32(u32 address, RequestedAddressSpace space) { const auto result = HostTryReadUX(address, space); if (!result) - return TryReadResult(); - return TryReadResult(result.translated, Common::BitCast(result.value)); + return std::nullopt; + return ReadResult(result->translated, Common::BitCast(result->value)); } -TryReadResult HostTryReadF64(u32 address, RequestedAddressSpace space) +std::optional> HostTryReadF64(u32 address, RequestedAddressSpace space) { const auto result = HostTryReadUX(address, space); if (!result) - return TryReadResult(); - return TryReadResult(result.translated, Common::BitCast(result.value)); + return std::nullopt; + return ReadResult(result->translated, Common::BitCast(result->value)); } u32 Read_U8_ZX(const u32 address) @@ -763,62 +764,68 @@ void HostWrite_F64(const double var, const u32 address) HostWrite_U64(integral, address); } -static TryWriteResult HostTryWriteUX(const u32 var, const u32 address, const u32 size, - RequestedAddressSpace space) +static std::optional HostTryWriteUX(const u32 var, const u32 address, const u32 size, + RequestedAddressSpace space) { if (!HostIsRAMAddress(address, space)) - return TryWriteResult(); + return std::nullopt; switch (space) { case RequestedAddressSpace::Effective: WriteToHardware(address, var, size); - return TryWriteResult(!!MSR.DR); + return WriteResult(!!MSR.DR); case RequestedAddressSpace::Physical: WriteToHardware(address, var, size); - return TryWriteResult(false); + return WriteResult(false); case RequestedAddressSpace::Virtual: if (!MSR.DR) - return TryWriteResult(); + return std::nullopt; WriteToHardware(address, var, size); - return TryWriteResult(true); + return WriteResult(true); } ASSERT(0); - return TryWriteResult(); + return std::nullopt; } -TryWriteResult HostTryWriteU8(const u32 var, const u32 address, RequestedAddressSpace space) +std::optional HostTryWriteU8(const u32 var, const u32 address, + RequestedAddressSpace space) { return HostTryWriteUX(var, address, 1, space); } -TryWriteResult HostTryWriteU16(const u32 var, const u32 address, RequestedAddressSpace space) +std::optional HostTryWriteU16(const u32 var, const u32 address, + RequestedAddressSpace space) { return HostTryWriteUX(var, address, 2, space); } -TryWriteResult HostTryWriteU32(const u32 var, const u32 address, RequestedAddressSpace space) +std::optional HostTryWriteU32(const u32 var, const u32 address, + RequestedAddressSpace space) { return HostTryWriteUX(var, address, 4, space); } -TryWriteResult HostTryWriteU64(const u64 var, const u32 address, RequestedAddressSpace space) +std::optional HostTryWriteU64(const u64 var, const u32 address, + RequestedAddressSpace space) { - const TryWriteResult result = HostTryWriteUX(static_cast(var >> 32), address, 4, space); + const auto result = HostTryWriteUX(static_cast(var >> 32), address, 4, space); if (!result) return result; return HostTryWriteUX(static_cast(var), address + 4, 4, space); } -TryWriteResult HostTryWriteF32(const float var, const u32 address, RequestedAddressSpace space) +std::optional HostTryWriteF32(const float var, const u32 address, + RequestedAddressSpace space) { const u32 integral = Common::BitCast(var); return HostTryWriteU32(integral, address, space); } -TryWriteResult HostTryWriteF64(const double var, const u32 address, RequestedAddressSpace space) +std::optional HostTryWriteF64(const double var, const u32 address, + RequestedAddressSpace space) { const u64 integral = Common::BitCast(var); return HostTryWriteU64(integral, address, space); @@ -840,25 +847,26 @@ std::string HostGetString(u32 address, size_t size) return s; } -TryReadResult HostTryReadString(u32 address, size_t size, RequestedAddressSpace space) +std::optional> HostTryReadString(u32 address, size_t size, + RequestedAddressSpace space) { auto c = HostTryReadU8(address, space); if (!c) - return TryReadResult(); - if (c.value == 0) - return TryReadResult(c.translated, ""); + return std::nullopt; + if (c->value == 0) + return ReadResult(c->translated, ""); std::string s; - s += static_cast(c.value); + s += static_cast(c->value); while (size == 0 || s.length() < size) { ++address; const auto res = HostTryReadU8(address, space); - if (!res || res.value == 0) + if (!res || res->value == 0) break; - s += static_cast(res.value); + s += static_cast(res->value); } - return TryReadResult(c.translated, std::move(s)); + return ReadResult(c->translated, std::move(s)); } bool IsOptimizableRAMAddress(const u32 address) diff --git a/Source/Core/Core/PowerPC/MMU.h b/Source/Core/Core/PowerPC/MMU.h index 47786078cb..afe36a9875 100644 --- a/Source/Core/Core/PowerPC/MMU.h +++ b/Source/Core/Core/PowerPC/MMU.h @@ -37,11 +37,8 @@ u32 HostRead_Instruction(u32 address); std::string HostGetString(u32 address, size_t size = 0); template -struct TryReadResult +struct ReadResult { - // whether the read succeeded; if false, the other fields should not be touched - bool success; - // whether the address had to be translated (given address was treated as virtual) or not (given // address was treated as physical) bool translated; @@ -49,37 +46,31 @@ struct TryReadResult // the actual value that was read T value; - TryReadResult() : success(false) {} - TryReadResult(bool translated_, T&& value_) - : success(true), translated(translated_), value(std::move(value_)) + ReadResult(bool translated_, T&& value_) : translated(translated_), value(std::forward(value_)) { } - TryReadResult(bool translated_, const T& value_) - : success(true), translated(translated_), value(value_) - { - } - explicit operator bool() const { return success; } + ReadResult(bool translated_, const T& value_) : translated(translated_), value(value_) {} }; // Try to read a value from emulated memory at the given address in the given memory space. -// If the read succeeds, the returned TryReadResult contains the read value and information on -// whether the given address had to be translated or not. Unlike the HostRead functions, this does -// not raise a user-visible alert on failure. -TryReadResult HostTryReadU8(u32 address, - RequestedAddressSpace space = RequestedAddressSpace::Effective); -TryReadResult HostTryReadU16(u32 address, - RequestedAddressSpace space = RequestedAddressSpace::Effective); -TryReadResult HostTryReadU32(u32 address, - RequestedAddressSpace space = RequestedAddressSpace::Effective); -TryReadResult HostTryReadU64(u32 address, - RequestedAddressSpace space = RequestedAddressSpace::Effective); -TryReadResult HostTryReadF32(u32 address, - RequestedAddressSpace space = RequestedAddressSpace::Effective); -TryReadResult +// If the read succeeds, the returned value will be present and the ReadResult contains the read +// value and information on whether the given address had to be translated or not. Unlike the +// HostRead functions, this does not raise a user-visible alert on failure. +std::optional> +HostTryReadU8(u32 address, RequestedAddressSpace space = RequestedAddressSpace::Effective); +std::optional> +HostTryReadU16(u32 address, RequestedAddressSpace space = RequestedAddressSpace::Effective); +std::optional> +HostTryReadU32(u32 address, RequestedAddressSpace space = RequestedAddressSpace::Effective); +std::optional> +HostTryReadU64(u32 address, RequestedAddressSpace space = RequestedAddressSpace::Effective); +std::optional> +HostTryReadF32(u32 address, RequestedAddressSpace space = RequestedAddressSpace::Effective); +std::optional> HostTryReadF64(u32 address, RequestedAddressSpace space = RequestedAddressSpace::Effective); -TryReadResult +std::optional> HostTryReadInstruction(u32 address, RequestedAddressSpace space = RequestedAddressSpace::Effective); -TryReadResult +std::optional> HostTryReadString(u32 address, size_t size = 0, RequestedAddressSpace space = RequestedAddressSpace::Effective); @@ -93,36 +84,37 @@ void HostWrite_U64(u64 var, u32 address); void HostWrite_F32(float var, u32 address); void HostWrite_F64(double var, u32 address); -struct TryWriteResult +struct WriteResult { - // whether the write succeeded; if false, the other fields should not be touched - bool success; - // whether the address had to be translated (given address was treated as virtual) or not (given // address was treated as physical) bool translated; - TryWriteResult() : success(false) {} - TryWriteResult(bool translated_) : success(true), translated(translated_) {} - explicit operator bool() const { return success; } + explicit WriteResult(bool translated_) : translated(translated_) {} }; // Try to a write a value to memory at the given address in the given memory space. // If the write succeeds, the returned TryWriteResult contains information on whether the given // address had to be translated or not. Unlike the HostWrite functions, this does not raise a // user-visible alert on failure. -TryWriteResult HostTryWriteU8(u32 var, const u32 address, - RequestedAddressSpace space = RequestedAddressSpace::Effective); -TryWriteResult HostTryWriteU16(u32 var, const u32 address, - RequestedAddressSpace space = RequestedAddressSpace::Effective); -TryWriteResult HostTryWriteU32(u32 var, const u32 address, - RequestedAddressSpace space = RequestedAddressSpace::Effective); -TryWriteResult HostTryWriteU64(u64 var, const u32 address, - RequestedAddressSpace space = RequestedAddressSpace::Effective); -TryWriteResult HostTryWriteF32(float var, const u32 address, - RequestedAddressSpace space = RequestedAddressSpace::Effective); -TryWriteResult HostTryWriteF64(double var, const u32 address, - RequestedAddressSpace space = RequestedAddressSpace::Effective); +std::optional +HostTryWriteU8(u32 var, const u32 address, + RequestedAddressSpace space = RequestedAddressSpace::Effective); +std::optional +HostTryWriteU16(u32 var, const u32 address, + RequestedAddressSpace space = RequestedAddressSpace::Effective); +std::optional +HostTryWriteU32(u32 var, const u32 address, + RequestedAddressSpace space = RequestedAddressSpace::Effective); +std::optional +HostTryWriteU64(u64 var, const u32 address, + RequestedAddressSpace space = RequestedAddressSpace::Effective); +std::optional +HostTryWriteF32(float var, const u32 address, + RequestedAddressSpace space = RequestedAddressSpace::Effective); +std::optional +HostTryWriteF64(double var, const u32 address, + RequestedAddressSpace space = RequestedAddressSpace::Effective); // Returns whether a read or write to the given address will resolve to a RAM access in the given // address space.