Skip to content

Commit

Permalink
Optimized memory scanner
Browse files Browse the repository at this point in the history
  • Loading branch information
andon authored and andon committed Mar 1, 2017
1 parent e3c9918 commit 6063951
Show file tree
Hide file tree
Showing 6 changed files with 94 additions and 61 deletions.
2 changes: 1 addition & 1 deletion include/DLL_VERSION.H
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
#define TBF_MAJOR 0
#define TBF_MINOR 10
#define TBF_BUILD 1
#define TBF_REV 1
#define TBF_REV 2



Expand Down
4 changes: 2 additions & 2 deletions include/scanner.h
Original file line number Diff line number Diff line change
Expand Up @@ -25,8 +25,8 @@

#include <stdint.h>

void* TBF_Scan (uint8_t* pattern, size_t len, uint8_t* mask = nullptr);
void* TBF_ScanEx (uint8_t* pattern, size_t len, uint8_t* mask, void* after);
void* TBF_Scan (uint8_t* pattern, size_t len, uint8_t* mask = nullptr, int align=1);
void* TBF_ScanEx (uint8_t* pattern, size_t len, uint8_t* mask, void* after, int align=1);
uintptr_t TBF_GetBaseAddr (void);

#endif /* __TBF__SCANNER_H__ */
3 changes: 2 additions & 1 deletion src/framerate.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -330,7 +330,8 @@ tbf::FrameRateFix::Init (void)
uint8_t mask [] = { 0xff, 0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff };

void* limiter_addr =
TBF_Scan (sig, sizeof (sig), mask);
TBF_Scan (sig, sizeof (sig), mask, 16);
// x64 functions are 16-byte aligned in Microsoft's ABI, use this to speed the search up

uintptr_t rip = (uintptr_t)limiter_addr + 18;

Expand Down
42 changes: 26 additions & 16 deletions src/render.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1234,9 +1234,6 @@ class TBF_AutoViewport
void
TBF_Viewport_HUD (IDirect3DDevice9* This, uint32_t vs_checksum, uint32_t ps_checksum)
{
D3DVIEWPORT9 vp;
This->GetViewport (&vp);

//if (vp.Height != tbf::RenderFix::height || vp.Width != tbf::RenderFix::width || vp.MaxZ != 1.0f || vp.MinZ != 0.0f || vp.X != 0 || vp.Y != 0)
//return;

Expand All @@ -1259,8 +1256,8 @@ TBF_Viewport_HUD (IDirect3DDevice9* This, uint32_t vs_checksum, uint32_t ps_chec
if (tbf::RenderFix::width > tbf::RenderFix::height * (16.0f / 9.0f))
{
D3DVIEWPORT9 new_vp;
new_vp.MinZ = vp.MinZ;
new_vp.MaxZ = vp.MaxZ;
new_vp.MinZ = last_viewport.MinZ;
new_vp.MaxZ = last_viewport.MaxZ;
new_vp.Width = tbf::RenderFix::height * (16.0f / 9.0f);
new_vp.Height = tbf::RenderFix::height;
new_vp.X = (tbf::RenderFix::width - tbf::RenderFix::height * (16.0f / 9.0f)) / 2;
Expand All @@ -1271,8 +1268,8 @@ TBF_Viewport_HUD (IDirect3DDevice9* This, uint32_t vs_checksum, uint32_t ps_chec
else
{
D3DVIEWPORT9 new_vp;
new_vp.MinZ = vp.MinZ;
new_vp.MaxZ = vp.MaxZ;
new_vp.MinZ = last_viewport.MinZ;
new_vp.MaxZ = last_viewport.MaxZ;
new_vp.Width = tbf::RenderFix::width;
new_vp.Height = tbf::RenderFix::width * (9.0f / 16.0f);
new_vp.X = 0;
Expand Down Expand Up @@ -2147,6 +2144,8 @@ tbf::RenderFix::Init (void)
aspect_ratio_data.blacklist.textures.emplace (0x5f245e67); // Star's Shadow (Also used on one menu screen)
aspect_ratio_data.blacklist.textures.emplace (0x7ca202a3); // Pulsing ring around Star

aspect_ratio_data.blacklist.textures.emplace (0xc070b309); // Border around location names [Stretch Horiz]

aspect_ratio_data.blacklist.textures.emplace (0x952b0ff8); // NPC Dialog Background

////aspect_ratio_data.blacklist.pixel_shaders.emplace (0x872e7c85); // Pixel Shader for Skits (in general)
Expand Down Expand Up @@ -2322,24 +2321,35 @@ tbf::RenderFix::CommandProcessor::CommandProcessor (void)

uint8_t signature [] = { 0x39, 0x8E, 0xE3, 0x3F };

if (*(float *)(uintptr_t)config.render.aspect_addr != 16.0f / 9.0f)
if ( config.render.aspect_ratio > (16.0f / 9.0f) + 0.001f ||
config.render.aspect_ratio < (16.0f / 9.0f) - 0.001f )
{
void* addr = TBF_Scan(signature, sizeof(float), nullptr);
void* addr =
TBF_Scan (signature, sizeof (float), nullptr, 4);

do {
if (addr == nullptr)
break;

dll_log->Log (L"[Asp. Ratio] Scanned Aspect Ratio Address: %06Xh", addr);
HMODULE hMod;

DWORD dwOld;
if (GetModuleHandleExW ( GET_MODULE_HANDLE_EX_FLAG_UNCHANGED_REFCOUNT |
GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS, (LPCWSTR)addr, &hMod ))
{
if (hMod != GetModuleHandle (nullptr))
continue;

dll_log->Log (L"[Asp. Ratio] Scanned Aspect Ratio Address: %06Xh", addr);

VirtualProtect (addr, sizeof (float), PAGE_READWRITE, &dwOld);
*(float *)addr = config.render.aspect_ratio;
VirtualProtect (addr, sizeof (float), dwOld, &dwOld);
DWORD dwOld;

aspect_ratio.addrs [aspect_ratio.count++] = (float *)addr;
VirtualProtect (addr, sizeof (float), PAGE_READWRITE, &dwOld);
*(float *)addr = config.render.aspect_ratio;
VirtualProtect (addr, sizeof (float), dwOld, &dwOld);

} while (addr != nullptr && (addr = TBF_ScanEx (signature, sizeof (float), nullptr, addr)));
aspect_ratio.addrs [aspect_ratio.count++] = (float *)addr;
}
} while (addr != nullptr && (addr = TBF_ScanEx (signature, sizeof (float), nullptr, addr, 4)));
}

#if 0
Expand Down
104 changes: 63 additions & 41 deletions src/scanner.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ TBF_GetBaseAddr (void)
}

void*
TBF_Scan (uint8_t* pattern, size_t len, uint8_t* mask)
TBF_Scan (uint8_t* pattern, size_t len, uint8_t* mask, int align)
{
uint8_t* base_addr = (uint8_t *)GetModuleHandle (nullptr);

Expand All @@ -57,8 +57,12 @@ TBF_Scan (uint8_t* pattern, size_t len, uint8_t* mask)
uint8_t* end_addr = (uint8_t *)mem_info.BaseAddress + mem_info.RegionSize;

if (base_addr != (uint8_t *)0x400000) {
dll_log->Log ( L"[ Sig Scan ] Expected module base addr. 40000h, but got: %ph",
base_addr );
static bool warned = false;
if (! warned) {
dll_log->Log ( L"[ Sig Scan ] Expected module base addr. 40000h, but got: %ph",
base_addr );
warned = true;
}
}

size_t pages = 0;
Expand Down Expand Up @@ -87,17 +91,25 @@ uint8_t* const PAGE_WALK_LIMIT = (base_addr + (uintptr_t)(1ULL << 36));
}

if (end_addr > PAGE_WALK_LIMIT) {
dll_log->Log ( L"[ Sig Scan ] Module page walk resulted in end addr. out-of-range: %ph",
end_addr );
dll_log->Log ( L"[ Sig Scan ] >> Restricting to %ph",
PAGE_WALK_LIMIT );
static bool warned = false;

if (! warned) {
dll_log->Log ( L"[ Sig Scan ] Module page walk resulted in end addr. out-of-range: %ph",
end_addr );
dll_log->Log ( L"[ Sig Scan ] >> Restricting to %ph",
PAGE_WALK_LIMIT );
warned = true;
}

end_addr = (uint8_t *)PAGE_WALK_LIMIT;
}

#if 0
dll_log->Log ( L"[ Sig Scan ] Module image consists of %zu pages, from %ph to %ph",
pages,
base_addr,
end_addr );
#endif
#endif

__SK_base_img_addr = base_addr;
Expand Down Expand Up @@ -142,19 +154,35 @@ uint8_t* const PAGE_WALK_LIMIT = (base_addr + (uintptr_t)(1ULL << 36));
if (mask != nullptr && (! mask [idx]))
match = true;

if (match) {
if (match)
{
if (++idx == len)
return (void *)begin;
{
if (((uintptr_t)begin % align) == 0)
return (void *)begin;
else
{
begin += (idx + 1);
begin += align - ((uintptr_t)begin % align);

++it;
it = begin;
idx = 0;
}
}

else
++it;
}

else {
// No match?!
if (it > end_addr - len)
break;

it = ++begin;
begin += (idx + 1);
begin += align - ((uintptr_t)begin % align);

it = begin;
idx = 0;
}
}
Expand Down Expand Up @@ -189,7 +217,7 @@ SK_InjectMemory ( LPVOID base_addr,
}

void*
TBF_ScanEx (uint8_t* pattern, size_t len, uint8_t* mask, void* after)
TBF_ScanEx (uint8_t* pattern, size_t len, uint8_t* mask, void* after, int align)
{
uint8_t* base_addr = (uint8_t *)GetModuleHandle (nullptr);

Expand All @@ -210,11 +238,6 @@ TBF_ScanEx (uint8_t* pattern, size_t len, uint8_t* mask, void* after)
base_addr = (uint8_t *)mem_info.BaseAddress;//AllocationBase;
uint8_t* end_addr = (uint8_t *)mem_info.BaseAddress + mem_info.RegionSize;

if (base_addr != (uint8_t *)0x400000) {
dll_log->Log ( L"[ Sig Scan ] Expected module base addr. 40000h, but got: %ph",
base_addr );
}

size_t pages = 0;

// Scan up to 256 MiB worth of data
Expand All @@ -241,23 +264,11 @@ uint8_t* const PAGE_WALK_LIMIT = (base_addr + (uintptr_t)(1ULL << 36));
}

if (end_addr > PAGE_WALK_LIMIT) {
dll_log->Log ( L"[ Sig Scan ] Module page walk resulted in end addr. out-of-range: %ph",
end_addr );
dll_log->Log ( L"[ Sig Scan ] >> Restricting to %ph",
PAGE_WALK_LIMIT );
end_addr = (uint8_t *)PAGE_WALK_LIMIT;
}

dll_log->Log ( L"[ Sig Scan ] Module image consists of %zu pages, from %ph to %ph",
pages,
base_addr,
end_addr );
#endif

__SK_base_img_addr = base_addr;
__SK_end_img_addr = end_addr;

uint8_t* begin = (uint8_t *)base_addr;
uint8_t* begin = (uint8_t *)after + align;
uint8_t* it = begin;
int idx = 0;

Expand Down Expand Up @@ -286,7 +297,8 @@ uint8_t* const PAGE_WALK_LIMIT = (base_addr + (uintptr_t)(1ULL << 36));
if (next_rgn >= end_addr)
break;

while (it < next_rgn) {
while (it < next_rgn)
{
uint8_t* scan_addr = it;

bool match = (*scan_addr == pattern [idx]);
Expand All @@ -296,26 +308,36 @@ uint8_t* const PAGE_WALK_LIMIT = (base_addr + (uintptr_t)(1ULL << 36));
if (mask != nullptr && (! mask [idx]))
match = true;

if (match) {
if (++idx == len) {
if ((void *)begin > after)
if (match)
{
if (++idx == len)
{
if (((uintptr_t)begin % align) == 0)
return (void *)begin;
else {
it = ++begin;
idx = 0;
continue;
else
{
begin += (idx + 1);
begin += align - ((uintptr_t)begin % align);

it = begin;
idx = 0;
}
}

++it;
else
++it;
}

else {
else
{
// No match?!
if (it > end_addr - len)
break;

it = ++begin;
begin += (idx+1);
begin += align - ((uintptr_t)begin % align);

it = begin;
idx = 0;
}
}
Expand Down
Binary file modified version.ini
Binary file not shown.

0 comments on commit 6063951

Please sign in to comment.