Skip to content

Commit

Permalink
Cheats: Prevent inlining of memory functions
Browse files Browse the repository at this point in the history
Clang is way too eager here and inlines the whole thing hundreds of
times within CheatList::Apply().
  • Loading branch information
stenzek committed Sep 9, 2024
1 parent 7bcdf11 commit e2a3fe1
Show file tree
Hide file tree
Showing 2 changed files with 13 additions and 6 deletions.
11 changes: 9 additions & 2 deletions src/common/types.h
Original file line number Diff line number Diff line change
Expand Up @@ -10,15 +10,13 @@
#include <type_traits>

// Force inline helper
#ifndef ALWAYS_INLINE
#if defined(_MSC_VER)
#define ALWAYS_INLINE __forceinline
#elif defined(__GNUC__) || defined(__clang__)
#define ALWAYS_INLINE __attribute__((always_inline)) inline
#else
#define ALWAYS_INLINE inline
#endif
#endif

// Force inline in non-debug helper
#ifdef _DEBUG
Expand All @@ -27,6 +25,15 @@
#define ALWAYS_INLINE_RELEASE ALWAYS_INLINE
#endif

// Prevent inlining
#if defined(_MSC_VER)
#define NEVER_INLINE __declspec(noinline)
#elif defined(__GNUC__) || defined(__clang__)
#define NEVER_INLINE __attribute__((noinline))
#else
#define NEVER_INLINE
#endif

// unreferenced parameter macro
#ifndef UNREFERENCED_VARIABLE
#if defined(__GNUC__) || defined(__clang__) || defined(__EMSCRIPTEN__)
Expand Down
8 changes: 4 additions & 4 deletions src/core/cheats.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,7 @@ static bool IsValidScanAddress(PhysicalMemoryAddress address)
}

template<typename T>
static T DoMemoryRead(VirtualMemoryAddress address)
NEVER_INLINE static T DoMemoryRead(VirtualMemoryAddress address)
{
using UnsignedType = typename std::make_unsigned_t<T>;
static_assert(std::is_same_v<UnsignedType, u8> || std::is_same_v<UnsignedType, u16> ||
Expand All @@ -60,7 +60,7 @@ static T DoMemoryRead(VirtualMemoryAddress address)
}

template<typename T>
static void DoMemoryWrite(PhysicalMemoryAddress address, T value)
NEVER_INLINE static void DoMemoryWrite(PhysicalMemoryAddress address, T value)
{
using UnsignedType = typename std::make_unsigned_t<T>;
static_assert(std::is_same_v<UnsignedType, u8> || std::is_same_v<UnsignedType, u16> ||
Expand All @@ -74,7 +74,7 @@ static void DoMemoryWrite(PhysicalMemoryAddress address, T value)
CPU::SafeWriteMemoryWord(address, value);
}

static u32 GetControllerButtonBits()
NEVER_INLINE static u32 GetControllerButtonBits()
{
static constexpr std::array<u16, 16> button_mapping = {{
0x0100, // Select
Expand Down Expand Up @@ -115,7 +115,7 @@ static u32 GetControllerButtonBits()
return translated_bits;
}

static u32 GetControllerAnalogBits()
NEVER_INLINE static u32 GetControllerAnalogBits()
{
// 0x010000 - Right Thumb Up
// 0x020000 - Right Thumb Right
Expand Down

0 comments on commit e2a3fe1

Please # to comment.