diff --git a/include/DLL_VERSION.H b/include/DLL_VERSION.H
index cbb0afd..b867f19 100644
--- a/include/DLL_VERSION.H
+++ b/include/DLL_VERSION.H
@@ -2,8 +2,8 @@
#define TBF_MAJOR 0
-#define TBF_MINOR 1
-#define TBF_BUILD 7
+#define TBF_MINOR 2
+#define TBF_BUILD 0
#define TBF_REV 0
diff --git a/include/config.h b/include/config.h
index 9543582..02ba9f4 100644
--- a/include/config.h
+++ b/include/config.h
@@ -31,41 +31,26 @@ extern std::wstring DEFAULT_BK2;
struct tbf_config_t
{
struct {
- uint32_t sample_hz = 48000;
- uint32_t channels = 6; // OBSOLETE
- bool compatibility = false;
- bool enable_fix = true;
+ uint32_t sample_hz = -1;
+ uint32_t channels = 6;
+ bool compatibility = false;
+ bool enable_fix = true;
} audio;
struct {
- bool yield_processor = true;
- bool allow_fake_sleep = false;
- bool minimize_latency = false;
- DWORD speedresetcode_addr = 0x0046C0F9; //0x0046C529;
- DWORD speedresetcode2_addr = 0x0056EB41; //0x0056E441; 0x217B464
- DWORD speedresetcode3_addr = 0x0056E03F; //0x0056D93F;
- DWORD limiter_branch_addr = 0x00990F53; //0x00990873;
- bool disable_limiter = true;
- bool auto_adjust = false;
- int target = 60;
- int battle_target = 60;
- bool battle_adaptive = false;
- int cutscene_target = 30;
- bool reshade_fix = false;
+ bool replace_limiter = true;
+ int target = 60;
+ bool reshade_fix = false;
} framerate;
struct {
- bool capture = false;
+ bool capture = false;
} file_io;
struct {
- bool allow_broadcasts = false;
+ bool allow_broadcasts = false;
} steam;
- struct {
- bool fix_priest = true;
- } lua;
-
struct {
float fovy = 0.785398f;
float aspect_ratio = 1.777778f;
@@ -81,11 +66,13 @@ struct tbf_config_t
} render;
struct {
- bool dump = false;
- bool remaster = true;
- bool cache = true;
- int32_t max_cache_in_mib = 2048L;
- int32_t worker_threads = 6;
+ bool dump = false;
+ bool remaster = true;
+ bool cache = true;
+ bool uncompressed = false;
+ float lod_bias = -0.2666f;
+ int32_t max_cache_in_mib = 2048L;
+ int32_t worker_threads = 6;
} textures;
struct {
diff --git a/include/framerate.h b/include/framerate.h
index 46d29db..80864a4 100644
--- a/include/framerate.h
+++ b/include/framerate.h
@@ -1,12 +1,12 @@
/**
- * This file is part of Tales of Zestiria "Fix".
+ * This file is part of Tales of Berseria "Fix".
*
- * Tales of Zestiria "Fix" is free software : you can redistribute it
+ * Tales of Berseria "Fix" is free software : you can redistribute it
* and/or modify it under the terms of the GNU General Public License
* as published by The Free Software Foundation, either version 3 of
* the License, or (at your option) any later version.
*
- * Tales of Zestiria "Fix" is distributed in the hope that it will be
+ * Tales of Berseria "Fix" is distributed in the hope that it will be
* useful,
*
* But WITHOUT ANY WARRANTY; without even the implied warranty of
@@ -14,20 +14,20 @@
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
- * along with Tales of Zestiria "Fix".
+ * along with Tales of Berseria "Fix".
*
* If not, see .
*
**/
-#ifndef __TZF__FRAMERATE_H__
-#define __TZF__FRAMERATE_H__
+#ifndef __TBF__FRAMERATE_H__
+#define __TBF__FRAMERATE_H__
#include
#include
#include "command.h"
-namespace tzf
+namespace tbf
{
namespace FrameRateFix
{
@@ -39,10 +39,7 @@ namespace tzf
void RenderTick (void);
- // Determine the appropriate value for TickScale
- long CalcTickScale (double elapsed_ms);
-
-
+#if 0
//
// At key points during the game, we need to disable the code that
// cuts timing in half. These places will be wrapped by calls to
@@ -52,6 +49,7 @@ namespace tzf
void End30FPSEvent (void);
void SetFPS (int fps);
+#endif
class CommandProcessor : public SK_IVariableListener {
public:
@@ -74,23 +72,12 @@ namespace tzf
static CommandProcessor* pCommProc;
};
-
- // True if the game is running in fullscreen
- extern bool fullscreen;
-
- // True if the game is being framerate limited by the DRIVER
- extern bool driver_limit_setup;
-
// True if the executable has been modified (at run-time) to allow 60 FPS
extern bool variable_speed_installed;
// This is actually setup in the SK DLL that loads this one
extern uint32_t target_fps;
- // Store the original unmodifed game instructions
- extern uint8_t old_speed_reset_code2 [7];
- extern uint8_t old_limiter_instruction [6];
-
// Cache the game's tick scale for timing -- this can be changed without
// our knowledge, so this is more or less a hint rather than a rule
extern int32_t tick_scale;
@@ -104,4 +91,4 @@ namespace tzf
}
}
-#endif /* __TZF__FRAMERATE_H__ */
\ No newline at end of file
+#endif /* __TBF__FRAMERATE_H__ */
\ No newline at end of file
diff --git a/include/parameter.h b/include/parameter.h
index 889ef51..7d9e99e 100644
--- a/include/parameter.h
+++ b/include/parameter.h
@@ -163,8 +163,16 @@ class ParameterBool : public Parameter
bool load (bool& ref);
+ enum boolean_term_t {
+ TrueFalse = 0,
+ OnOff = 1,
+ YesNo = 2,
+ ZeroNonZero = 3
+ };
+
protected:
- bool value;
+ bool value;
+ boolean_term_t type = TrueFalse;
};
class ParameterFloat : public Parameter
diff --git a/include/scanner.h b/include/scanner.h
index 1db517b..9ae4d93 100644
--- a/include/scanner.h
+++ b/include/scanner.h
@@ -20,11 +20,12 @@
*
**/
-#ifndef __TZF__SCANNER_H__
-#define __TZF__SCANNER_H__
+#ifndef __TBF__SCANNER_H__
+#define __TBF__SCANNER_H__
#include
-void* TBF_Scan (uint8_t* pattern, size_t len, uint8_t* mask = nullptr);
+void* TBF_Scan (uint8_t* pattern, size_t len, uint8_t* mask = nullptr);
+uintptr_t TBF_GetBaseAddr (void);
-#endif /* __TZF__SCANNER_H__ */
\ No newline at end of file
+#endif /* __TBF__SCANNER_H__ */
\ No newline at end of file
diff --git a/src/config.cpp b/src/config.cpp
index 4987ad7..faca1bd 100644
--- a/src/config.cpp
+++ b/src/config.cpp
@@ -51,19 +51,7 @@ struct {
} audio;
struct {
- tbf::ParameterBool* allow_fake_sleep;
- tbf::ParameterBool* yield_processor;
- tbf::ParameterBool* minimize_latency;
- tbf::ParameterInt* speedresetcode_addr;
- tbf::ParameterInt* speedresetcode2_addr;
- tbf::ParameterInt* speedresetcode3_addr;
- tbf::ParameterInt* limiter_branch_addr;
- tbf::ParameterBool* disable_limiter;
- tbf::ParameterBool* auto_adjust;
- tbf::ParameterInt* target;
- tbf::ParameterInt* battle_target;
- tbf::ParameterBool* battle_adaptive;
- tbf::ParameterInt* cutscene_target;
+ tbf::ParameterBool* replace_limiter;
} framerate;
struct {
@@ -84,6 +72,8 @@ struct {
struct {
tbf::ParameterBool* remaster;
+ tbf::ParameterBool* uncompressed;
+ tbf::ParameterFloat* lod_bias;
tbf::ParameterBool* cache;
tbf::ParameterBool* dump;
tbf::ParameterInt* cache_size;
@@ -101,10 +91,6 @@ struct {
} keyboard;
-struct {
- tbf::ParameterBool* fix_priest;
-} lua;
-
struct {
struct {
tbf::ParameterStringW* texture_set;
@@ -225,6 +211,26 @@ TBF_LoadConfig (std::wstring name)
L"Texture.System",
L"Remaster" );
+ textures.uncompressed =
+ static_cast
+ (g_ParameterFactory.create_parameter (
+ L"Do Not Re-Compress Remastered Textures")
+ );
+ textures.uncompressed->register_to_ini (
+ render_ini,
+ L"Texture.System",
+ L"UncompressedRemasters" );
+
+ textures.lod_bias =
+ static_cast
+ (g_ParameterFactory.create_parameter (
+ L"Texture LOD Bias")
+ );
+ textures.lod_bias->register_to_ini (
+ render_ini,
+ L"Texture.System",
+ L"LODBias" );
+
textures.cache_size =
static_cast
(g_ParameterFactory.create_parameter (
@@ -277,6 +283,16 @@ TBF_LoadConfig (std::wstring name)
L"Shadow.Quality",
L"RescaleEnvShadows" );
+ framerate.replace_limiter =
+ static_cast
+ (g_ParameterFactory.create_parameter (
+ L"Replace Namco's Framerate Limiter")
+ );
+ framerate.replace_limiter->register_to_ini (
+ render_ini,
+ L"Framerate.Fix",
+ L"ReplaceLimiter" );
+
input.gamepad.texture_set =
static_cast
@@ -345,7 +361,11 @@ TBF_LoadConfig (std::wstring name)
render.dump_shaders->load (config.render.dump_shaders);
+ framerate.replace_limiter->load (config.framerate.replace_limiter);
+
textures.remaster->load (config.textures.remaster);
+ textures.uncompressed->load (config.textures.uncompressed);
+ textures.lod_bias->load (config.textures.lod_bias);
textures.cache->load (config.textures.cache);
textures.dump->load (config.textures.dump);
textures.cache_size->load (config.textures.max_cache_in_mib);
@@ -365,12 +385,16 @@ TBF_SaveConfig (std::wstring name, bool close_config)
audio.compatibility->store (config.audio.compatibility);
audio.enable_fix->store (config.audio.enable_fix);
+ framerate.replace_limiter->store (config.framerate.replace_limiter);
+
render.dump_shaders->store (config.render.dump_shaders);
render.rescale_shadows->store (config.render.shadow_rescale);
render.rescale_env_shadows->store (config.render.env_shadow_rescale);
textures.remaster->store (config.textures.remaster);
+ textures.uncompressed->store (config.textures.uncompressed);
+ textures.lod_bias->store (config.textures.lod_bias);
textures.cache->store (config.textures.cache);
textures.dump->store (config.textures.dump);
textures.cache_size->store (config.textures.max_cache_in_mib);
diff --git a/src/dllmain.cpp b/src/dllmain.cpp
index 9787096..9f0e7fd 100644
--- a/src/dllmain.cpp
+++ b/src/dllmain.cpp
@@ -35,6 +35,8 @@
#include "command.h"
#include "hook.h"
+#include "scanner.h"
+
#pragma comment (lib, "kernel32.lib")
typedef HRESULT (__stdcall *SK_UpdateSoftware_pfn) (const wchar_t* wszProduct);
@@ -74,15 +76,17 @@ SKPlugIn_Init (HMODULE hModSpecialK)
TBF_VER_STR.c_str () );
if (! TBF_LoadConfig ()) {
- config.audio.channels = 6;
- config.audio.sample_hz = 48000;
+ config.audio.channels = 6;
+ config.audio.sample_hz = -1;
config.audio.compatibility = false;
config.audio.enable_fix = true;
config.file_io.capture = false;
config.steam.allow_broadcasts = false;
- config.lua.fix_priest = true;
+
+ config.framerate.replace_limiter = true;
+ config.framerate.target = 20;
config.render.aspect_ratio = 1.777778f;
config.render.fovy = 0.785398f;
@@ -123,7 +127,7 @@ SKPlugIn_Init (HMODULE hModSpecialK)
//tbf::FileIO::Init ();
//tbf::SteamFix::Init ();
tbf::RenderFix::Init ();
- //tbf::FrameRateFix::Init ();
+ tbf::FrameRateFix::Init ();
//tbf::KeyboardFix::Init ();
// Uncomment this when spawning a thread
@@ -176,7 +180,7 @@ DllMain (HMODULE hModule,
//tbf::FileIO::Shutdown ();
//tbf::SteamFix::Shutdown ();
tbf::RenderFix::Shutdown ();
- //tbf::FrameRateFix::Shutdown ();
+ tbf::FrameRateFix::Shutdown ();
//tbf::KeyboardFix::Shutdown ();
TBF_UnInit_MinHook ();
diff --git a/src/framerate.cpp b/src/framerate.cpp
index 89245b2..4a47e72 100644
--- a/src/framerate.cpp
+++ b/src/framerate.cpp
@@ -28,270 +28,25 @@
#include "hook.h"
#include "scanner.h"
-#include "priest.lua.h"
-
#include "render.h"
#include "textures.h"
#include
-uint32_t TICK_ADDR_BASE = 0x217B464;
-// 0x0217B3D4 1.3
-
-uint8_t tzf::FrameRateFix::old_speed_reset_code2 [7];
-uint8_t tzf::FrameRateFix::old_limiter_instruction [6];
-int32_t tzf::FrameRateFix::tick_scale = 2; // 30 FPS
-
-CRITICAL_SECTION tzf::FrameRateFix::alter_speed_cs = { 0 };
-
-bool tzf::FrameRateFix::variable_speed_installed = false;
-bool tzf::FrameRateFix::fullscreen = false;
-
-uint32_t tzf::FrameRateFix::target_fps = 30;
-
-HMODULE tzf::FrameRateFix::bink_dll = 0;
-HMODULE tzf::FrameRateFix::kernel32_dll = 0;
-
-float limiter_tolerance = 0.40f;
-int max_latency = 2;
-bool wait_for_vblank = true;
-
-typedef void (WINAPI *Sleep_pfn)(DWORD dwMilliseconds);
-Sleep_pfn Sleep_Original = nullptr;
-
-typedef BOOL(WINAPI *QueryPerformanceCounter_pfn)(_Out_ LARGE_INTEGER *lpPerformanceCount);
-QueryPerformanceCounter_pfn QueryPerformanceCounter_Original = nullptr;
-
-class FramerateLimiter
-{
-public:
- FramerateLimiter (double target = 60.0) {
- init (target);
- }
- ~FramerateLimiter (void) {
- }
-
- void init (double target) {
- ms = 1000.0 / target;
- fps = target;
-
- frames = 0;
-
- IDirect3DDevice9Ex* d3d9ex = nullptr;
- if (tzf::RenderFix::pDevice != nullptr) {
- tzf::RenderFix::pDevice->QueryInterface (
- __uuidof (IDirect3DDevice9Ex),
- (void **)&d3d9ex );
- }
-
- QueryPerformanceFrequency (&freq);
-
- // Align the start to VBlank for minimum input latency
- if (d3d9ex != nullptr) {
- d3d9ex->SetMaximumFrameLatency (1);
- d3d9ex->WaitForVBlank (0);
- d3d9ex->SetMaximumFrameLatency (max_latency);
- d3d9ex->Release ();
- }
-
- QueryPerformanceCounter_Original (&start);
-
- next.QuadPart = 0ULL;
- time.QuadPart = 0ULL;
- last.QuadPart = 0ULL;
-
- last.QuadPart = start.QuadPart - (ms / 1000.0) * freq.QuadPart;
- next.QuadPart = start.QuadPart + (ms / 1000.0) * freq.QuadPart;
- }
-
- void wait (void) {
- static bool restart = false;
-
- frames++;
-
- QueryPerformanceCounter_Original (&time);
-
- if ((double)(time.QuadPart - next.QuadPart) / (double)freq.QuadPart / (ms / 1000.0) > (limiter_tolerance * fps)) {
- //dll_log->Log ( L" * Frame ran long (%3.01fx expected) - restarting"
- //L" limiter...",
- //(double)(time.QuadPart - next.QuadPart) / (double)freq.QuadPart / (ms / 1000.0) / fps );
- restart = true;
- }
-
- if (restart) {
- frames = 0;
- start.QuadPart = time.QuadPart + (ms / 1000.0) * (double)freq.QuadPart;
- restart = false;
- }
-
- next.QuadPart = (start.QuadPart + (double)frames * (ms / 1000.0) * (double)freq.QuadPart);
-
- if (next.QuadPart > 0ULL) {
- // If available (Windows 7+), wait on the swapchain
- IDirect3DDevice9Ex* d3d9ex = nullptr;
- if (tzf::RenderFix::pDevice != nullptr) {
- tzf::RenderFix::pDevice->QueryInterface (
- __uuidof (IDirect3DDevice9Ex),
- (void **)&d3d9ex );
- }
-
- while (time.QuadPart < next.QuadPart) {
- if (wait_for_vblank && (double)(next.QuadPart - time.QuadPart) > (0.0166667 * (double)freq.QuadPart)) {
- if (d3d9ex != nullptr) {
- d3d9ex->WaitForVBlank (0);
- }
- }
-
- if (GetForegroundWindow () != tzf::RenderFix::hWndDevice &&
- tzf::FrameRateFix::fullscreen) {
- //dll_log->Log (L"[FrameLimit] # Restarting framerate limiter; fullscreen Alt+Tab...");
- restart = true;
- break;
- }
-
- QueryPerformanceCounter_Original (&time);
- }
-
- if (d3d9ex != nullptr)
- d3d9ex->Release ();
- }
-
- else {
- dll_log->Log (L"[FrameLimit] Lost time");
- start.QuadPart += -next.QuadPart;
- }
-
- last.QuadPart = time.QuadPart;
- }
-
- void change_limit (double target) {
- init (target);
- }
-
-private:
- double ms, fps;
-
- LARGE_INTEGER start, last, next, time, freq;
-
- uint32_t frames;
-} *limiter = nullptr;
-
-
-typedef D3DPRESENT_PARAMETERS* (__stdcall *SK_SetPresentParamsD3D9_pfn)
- (IDirect3DDevice9* device,
- D3DPRESENT_PARAMETERS* pparams);
-SK_SetPresentParamsD3D9_pfn SK_SetPresentParamsD3D9_Original = nullptr;
-
-COM_DECLSPEC_NOTHROW
-D3DPRESENT_PARAMETERS*
-__stdcall
-SK_SetPresentParamsD3D9_Detour (IDirect3DDevice9* device,
- D3DPRESENT_PARAMETERS* pparams)
-{
- D3DPRESENT_PARAMETERS present_params;
-
- //
- // TODO: Figure out what the hell is doing this when RTSS is allowed to use
- // custom D3D libs. 1x1@0Hz is obviously NOT for rendering!
- //
- if ( pparams->BackBufferWidth == 1 &&
- pparams->BackBufferHeight == 1 &&
- pparams->FullScreen_RefreshRateInHz == 0 ) {
- dll_log->Log (L"[ D3D9 ] * Fake D3D9Ex Device Detected... Ignoring!");
- return SK_SetPresentParamsD3D9_Original (device, pparams);
- }
-
- tzf::RenderFix::pDevice = device;
- tzf::RenderFix::pPostProcessSurface = nullptr;
-
- if (pparams != nullptr) {
- memcpy (&present_params, pparams, sizeof D3DPRESENT_PARAMETERS);
-
- if (device != nullptr) {
- dll_log->Log ( L"[ D3D9 ] %% Caught D3D9 Swapchain :: Fullscreen=%s "
- L" (%lux%lu@%lu Hz) "
- L" [Device Window: 0x%04X]",
- pparams->Windowed ? L"False" :
- L"True",
- pparams->BackBufferWidth,
- pparams->BackBufferHeight,
- pparams->FullScreen_RefreshRateInHz,
- pparams->hDeviceWindow );
- }
-
- tzf::RenderFix::hWndDevice = pparams->hDeviceWindow;
-
- tzf::RenderFix::width = present_params.BackBufferWidth;
- tzf::RenderFix::height = present_params.BackBufferHeight;
- tzf::FrameRateFix::fullscreen = (! pparams->Windowed);
-
- // Change the Aspect Ratio
- char szAspectCommand [64];
- sprintf (szAspectCommand, "AspectRatio %f", (float)tzf::RenderFix::width / (float)tzf::RenderFix::height);
-
- SK_GetCommandProcessor ()->ProcessCommandLine (szAspectCommand);
- }
-
- return SK_SetPresentParamsD3D9_Original (device, pparams);
-}
-
-bool render_sleep0 = false;
-LARGE_INTEGER last_perfCount = { 0 };
-
-void
-WINAPI
-Sleep_Detour (DWORD dwMilliseconds)
-{
- if ((! config.framerate.disable_limiter) && GetCurrentThreadId () == tzf::RenderFix::dwRenderThreadID) {
- if (dwMilliseconds == 0)
- render_sleep0 = true;
- else {
- render_sleep0 = false;
- }
- }
-
- if (config.framerate.yield_processor && dwMilliseconds == 0)
- YieldProcessor ();
-
- if (dwMilliseconds != 0 || config.framerate.allow_fake_sleep) {
- Sleep_Original (dwMilliseconds);
- }
-}
-
-BOOL
-WINAPI
-QueryPerformanceCounter_Detour (_Out_ LARGE_INTEGER *lpPerformanceCount)
-{
- BOOL ret = QueryPerformanceCounter_Original (lpPerformanceCount);
-
- DWORD dwThreadId = GetCurrentThreadId ();
-
- //
- // Handle threads that aren't render-related NORMALLY as well as the render
- // thread when it DID NOT just voluntarily relinquish its scheduling
- // timeslice
- //
- if (dwThreadId != tzf::RenderFix::dwRenderThreadID || (! render_sleep0) || tzf::RenderFix::bink) {
- if (dwThreadId == tzf::RenderFix::dwRenderThreadID)
- memcpy (&last_perfCount, lpPerformanceCount, sizeof (LARGE_INTEGER));
-
- return ret;
- }
-
- //
- // At this point, we're fixing up the thread that throttles the swapchain.
- //
- render_sleep0 = false;
+//
+// @TODO: Develop a heuristic to scan for this memory address;
+// hardcoding it is going to break stuff :)
+//
+uintptr_t TICK_ADDR_BASE = 0xB1B074;
- LARGE_INTEGER freq;
- QueryPerformanceFrequency (&freq);
+int32_t tbf::FrameRateFix::tick_scale = INT32_MAX; // 0 FPS
- // Mess with the numbers slightly to prevent scheduling from wreaking havoc
- lpPerformanceCount->QuadPart += (double)freq.QuadPart * ((double)tzf::FrameRateFix::target_fps / 1000.0);
+CRITICAL_SECTION tbf::FrameRateFix::alter_speed_cs = { 0 };
- memcpy (&last_perfCount, lpPerformanceCount, sizeof (LARGE_INTEGER));
+bool tbf::FrameRateFix::variable_speed_installed = false;
+uint32_t tbf::FrameRateFix::target_fps = 0;
- return ret;
-}
+HMODULE tbf::FrameRateFix::bink_dll = 0;
+HMODULE tbf::FrameRateFix::kernel32_dll = 0;
typedef void* (__stdcall *BinkOpen_pfn)(const char* filename, DWORD unknown0);
BinkOpen_pfn BinkOpen_Original = nullptr;
@@ -325,8 +80,8 @@ BinkOpen_Detour ( const char* filename,
if (bink_ret != nullptr) {
dll_log->Log (L"[FrameLimit] * Disabling TargetFPS -- Bink Video Opened");
- tzf::RenderFix::bink = true;
- tzf::FrameRateFix::Begin30FPSEvent ();
+ tbf::RenderFix::bink = true;
+ //tbf::FrameRateFix::Begin30FPSEvent ();
}
return bink_ret;
@@ -343,22 +98,18 @@ BinkClose_Detour (DWORD unknown)
dll_log->Log (L"[FrameLimit] * Restoring TargetFPS -- Bink Video Closed");
- tzf::RenderFix::bink = false;
- tzf::FrameRateFix::End30FPSEvent ();
+ tbf::RenderFix::bink = false;
+ //tbf::FrameRateFix::End30FPSEvent ();
}
-LPVOID pfnQueryPerformanceCounter = nullptr;
-LPVOID pfnSleep = nullptr;
-LPVOID pfnSK_SetPresentParamsD3D9 = nullptr;
-
// Hook these to properly synch audio subtitles during FMVs
LPVOID pfnBinkOpen = nullptr;
LPVOID pfnBinkClose = nullptr;
void
-TZF_FlushInstructionCache ( LPCVOID base_addr,
+TBF_FlushInstructionCache ( LPCVOID base_addr,
size_t code_size )
{
FlushInstructionCache ( GetCurrentProcess (),
@@ -367,11 +118,11 @@ TZF_FlushInstructionCache ( LPCVOID base_addr,
}
void
-TZF_InjectByteCode ( LPVOID base_addr,
- uint8_t* new_code,
- size_t code_size,
- DWORD permissions,
- uint8_t* old_code = nullptr )
+TBF_InjectMachineCode ( LPVOID base_addr,
+ uint8_t* new_code,
+ size_t code_size,
+ DWORD permissions,
+ uint8_t* old_code = nullptr )
{
DWORD dwOld;
@@ -384,67 +135,7 @@ TZF_InjectByteCode ( LPVOID base_addr,
}
VirtualProtect (base_addr, code_size, dwOld, &dwOld);
- TZF_FlushInstructionCache (base_addr, code_size);
-}
-
-LPVOID pLuaReturn = nullptr;
-
-void
-__declspec(naked)
-TZF_LuaHook (void)
-{
- char *name;
- size_t *pSz;
- char **pBuffer;
-
- __asm
- {
- pushad
- pushfd
-
- // save luaL_loadbuffer's stack frame because we need some stuff on it
- mov ebx, ebp
-
- push ebp
- mov ebp, esp
- sub esp, __LOCAL_SIZE
-
- // compiler must've optimised away the calling convention here
- mov name, eax
-
- mov eax, ebx
- add eax, 0xC
- mov pSz, eax
- mov eax, ebx
- add eax, 0x8
- mov pBuffer, eax
- }
-
-#if 0
- dll_log->Log (L"[ 60 FPS ]Lua script loaded: \"%S\"", name);
-#endif
-
- if (! strcmp (name, "MEP_100_130_010_PF_Script")) {
- dll_log->Log (L"[ 60 FPS ] * Replacing priest script...");
-
- *pSz = lua_bytecode_priest_size;
- *pBuffer = lua_bytecode_priest;
- }
-
- __asm
- {
- mov esp, ebp
- pop ebp
-
- popfd
- popad
-
- // overwritten instructions from original function
- mov ecx, [ebp + 0x8]
- mov [esp + 0x4], ecx
-
- jmp pLuaReturn
- }
+ TBF_FlushInstructionCache (base_addr, code_size);
}
typedef BOOL (WINAPI *CreateTimerQueueTimer_pfn)
@@ -482,521 +173,113 @@ CreateTimerQueueTimer_Override (
}
void
-tzf::FrameRateFix::Init (void)
+tbf::FrameRateFix::Init (void)
{
- CommandProcessor* comm_proc = CommandProcessor::getInstance ();
+ //CommandProcessor* comm_proc = CommandProcessor::getInstance ();
InitializeCriticalSectionAndSpinCount (&alter_speed_cs, 1000UL);
- target_fps = config.framerate.target;
+ target_fps = 0;
+ bink_dll = LoadLibrary (L"bink2w64.dll");
- TZF_CreateDLLHook2 ( config.system.injector.c_str (), "SK_SetPresentParamsD3D9",
- SK_SetPresentParamsD3D9_Detour,
- (LPVOID *)&SK_SetPresentParamsD3D9_Original,
- &pfnSK_SetPresentParamsD3D9 );
-
- bink_dll = LoadLibrary (L"bink2w32.dll");
-
- TZF_CreateDLLHook2 ( L"bink2w32.dll", "_BinkOpen@8",
+#if 0
+ TBF_CreateDLLHook2 ( L"bink2w64.dll", "_BinkOpen@8",
BinkOpen_Detour,
(LPVOID *)&BinkOpen_Original,
&pfnBinkOpen );
- TZF_CreateDLLHook2 ( L"bink2w32.dll", "_BinkClose@4",
+ TBF_CreateDLLHook2 ( L"bink2w64.dll", "_BinkClose@4",
BinkClose_Detour,
(LPVOID *)&BinkClose_Original,
&pfnBinkClose );
+#endif
- TZF_CreateDLLHook2 ( config.system.injector.c_str (), "QueryPerformanceCounter_Detour",
- QueryPerformanceCounter_Detour,
- (LPVOID *)&QueryPerformanceCounter_Original,
- (LPVOID *)&pfnQueryPerformanceCounter );
-
- TZF_CreateDLLHook2 ( L"kernel32.dll", "CreateTimerQueueTimer",
+ TBF_CreateDLLHook2 ( L"kernel32.dll", "CreateTimerQueueTimer",
CreateTimerQueueTimer_Override,
(LPVOID *)&CreateTimerQueueTimer_Original );
- TZF_ApplyQueuedHooks ();
-
- if (true) {
- if (*((DWORD *)config.framerate.speedresetcode_addr) != 0x428CB08D) {
- uint8_t sig [] = { 0x8D, 0xB0, 0x8C, 0x42,
- 0x00, 0x00, 0x8D, 0xBB,
- 0x8C, 0x42, 0x00, 0x00,
- 0xB9, 0x0B, 0x00, 0x00 };
- uintptr_t addr = (uintptr_t)TZF_Scan (sig, 16);
-
- if (addr != NULL) {
- dll_log->Log (L"[FrameLimit] Scanned SpeedResetCode Address: %06Xh", addr);
- config.framerate.speedresetcode_addr = addr;
- }
- else {
- dll_log->Log (L"[FrameLimit] >> ERROR: Unable to find SpeedResetCode memory!");
- }
- }
-
- if (*((DWORD *)config.framerate.speedresetcode3_addr) != 0x02) {
- uint8_t sig [] = { 0x0F, 0x95, 0xC0, 0x3A,
- 0xC3, 0x74, 0x17, 0xB8,
- 0x02, 0x00, 0x00, 0x00 };
- uintptr_t addr = (uintptr_t)TZF_Scan (sig, 12);
-
- if (addr != NULL && *((DWORD *)((uint8_t *)addr + 8)) == 0x2) {
- dll_log->Log (L"[FrameLimit] Scanned SpeedResetCode3 Address: %06Xh", addr + 8);
- config.framerate.speedresetcode3_addr = addr + 8;
- }
- else {
- dll_log->Log (L"[FrameLimit] >> ERROR: Unable to find SpeedResetCode3 memory!");
- }
- }
-
- dll_log->LogEx (true, L"[FrameLimit] * Installing variable rate simulation... ");
-
- DWORD dwOld;
-
- //
- // original code:
- //
- // >> lea esi, [eax+0000428C]
- // >> lea edi, [ebx+0000428C]
- // >> mov ecx, 11
- // rep movsd
- //
- // we want to skip the first two dwords
- //
- VirtualProtect((LPVOID)config.framerate.speedresetcode_addr, 17, PAGE_EXECUTE_READWRITE, &dwOld);
- *((DWORD *)(config.framerate.speedresetcode_addr + 2)) += 8;
- *((DWORD *)(config.framerate.speedresetcode_addr + 8)) += 8;
- *((DWORD *)(config.framerate.speedresetcode_addr + 13)) -= 2;
- VirtualProtect((LPVOID)config.framerate.speedresetcode_addr, 17, dwOld, &dwOld);
-
- TZF_FlushInstructionCache ((LPCVOID)config.framerate.speedresetcode_addr, 17);
-
- uint8_t mask [] = { 0xff, 0xff, 0xff, // cmp [ebx+28h], eax
- 0, 0, // jz short <...>
- 0xff, 0xff, 0xff, // cmp eax, 2
- 0, 0, // jl short <...>
- 0xff, 0, 0, 0, 0, // mov , eax
- 0xff, 0, 0, 0, 0, // mov , eax
- 0xff, 0xff, 0xff // mov [ebx+28h], eax
- };
-
- uint8_t sig [] = { 0x39, 0x43, 0x28, // cmp [ebx+28h], eax
- 0x74, 0x12, // jz short <...>
- 0x83, 0xF8, 0x02, // cmp eax, 2
- 0x7C, 0x0D, // jl short <...>
- 0xA3, 0x64, 0xB4, 0x17, 0x02, // mov , eax
- 0xA3, 0x68, 0xB4, 0x17, 0x02, // mov , eax
- 0x89, 0x43, 0x28 // mov [ebx+28h], eax
- };
-
- if (*((DWORD *)config.framerate.speedresetcode2_addr) != 0x0F8831274) {
- uintptr_t addr = (uintptr_t)TZF_Scan (sig, 23, mask);
-
- if (addr != NULL) {
- config.framerate.speedresetcode2_addr = addr + 3;
-
- dll_log->Log (L"[FrameLimit] Scanned SpeedResetCode2 Address: %06Xh", addr + 3);
-
- TICK_ADDR_BASE = *(DWORD *)((uint8_t *)(addr + 11));
-
- dll_log->Log (L"[FrameLimit] >> TICK_ADDR_BASE: %06Xh", TICK_ADDR_BASE);
- }
- else {
- dll_log->Log (L"[FrameLimit] >> ERROR: Unable to find SpeedResetCode2 memory!");
- }
- }
+ TBF_ApplyQueuedHooks ();
- //
- // original code:
- //
- // ...
- // cmp [ebx+28], eax
- // >> jz after_set
- // >> cmp eax, 2
- // >> jl after_set
- // mov 0217B3D4, eax
- // mov 0217B3D8, eax
- // mov [ebx+28], eax
- // after_set:
- // ...
- //
- // we just want this to be 1 always
- //
- // new code:
- // mov eax, 01
- // nop
- // nop
- //
- uint8_t new_code [7] = { 0xB8, 0x01, 0x00, 0x00, 0x00, 0x90, 0x90 };
-
- TZF_InjectByteCode ( (LPVOID)config.framerate.speedresetcode2_addr,
- new_code,
- 7,
- PAGE_EXECUTE_READWRITE,
- old_speed_reset_code2 );
-
- variable_speed_installed = true;
-
- // mov eax, 02 to mov eax, 01
- char scale [32];
- sprintf ( scale,
- "TickScale %li",
- CalcTickScale (1000.0f * (1.0f / target_fps)) );
- SK_GetCommandProcessor ()->ProcessCommandLine (scale);
-
- dll_log->LogEx ( false, L"Field=%lu FPS, Battle=%lu FPS (%s), Cutscene=%lu FPS\n",
- target_fps,
- config.framerate.battle_target,
- config.framerate.battle_adaptive ? L"Adaptive" : L"Fixed",
- config.framerate.cutscene_target );
- }
+ if (config.framerate.replace_limiter) {
+ /*
+ 6D3610 0x48 0x83 0xec 0x38 ; Namco Limiter
+ 6D3610 0xc3 0x90 0x90 0x90 ; No Limiter
- variable_speed_installed = true;
+ Tales of Berseria.exe+6D3610 - 48 83 EC 38 - sub rsp,38 { 56 }
- if (config.framerate.disable_limiter) {
- // Replace the original jump (jb) with an unconditional jump (jmp)
- uint8_t new_code [6] = { 0xE9, 0x8B, 0x00, 0x00, 0x00, 0x90 };
+ 0x48 0x83 0xec 0x38 0x8b 0x0d -------- 0x85 0xc9
+ */
- if (*(DWORD *)config.framerate.limiter_branch_addr != 0x8A820F) {
- uint8_t sig [] = { 0x53, // push ebx
- 0x56, // push esi
- 0x57, // push edi
- 0x0F, 0x82, 0x8A, 0x0, 0x0, 0x0 // jb
- };
- uintptr_t addr = (uintptr_t)TZF_Scan (sig, 9);
+ uint8_t sig [] = { 0x48, 0x83, 0xec, 0x38,
+ 0x8b, 0x0d, 0xff, 0xff, 0xff, 0xff,
+ 0x85, 0xc9 };
+ uint8_t mask [] = { 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0x00, 0x00, 0x00, 0x00,
+ 0xff, 0xff };
- if (addr != NULL) {
- config.framerate.limiter_branch_addr = addr + 3;
+ void* limiter_addr =
+ TBF_Scan (sig, sizeof (sig), mask);
- dll_log->Log (L"[FrameLimit] Scanned Limiter Branch Address: %06Xh", addr + 3);
- }
- else {
- dll_log->Log (L"[FrameLimit] >> ERROR: Unable to find LimiterBranchAddr memory!");
- }
+ if (limiter_addr != nullptr) {
+ dll_log->Log ( L"[FrameLimit] Scanned Namco's Framerate Limit Bug Address: %ph",
+ limiter_addr );
+ } else {
+ dll_log->Log (L"[FrameLimit] >> ERROR: Unable to find Framerate Limiter code!");
}
- TZF_InjectByteCode ( (LPVOID)config.framerate.limiter_branch_addr,
- new_code,
- 6,
- PAGE_EXECUTE_READWRITE );
- }
-
- if (config.lua.fix_priest) {
- uint8_t sig[14] = { 0x8B, 0x4D, 0x08, // mov ecx, [ebp+08]
- 0x89, 0x4C, 0x24, 0x04, // mov [esp+04], ecx
- 0x8B, 0x4D, 0x0C, // mov ecx, [ebp+0C]
- 0x89, 0x4C, 0x24, 0x08 // mov [esp+08], ecx
- };
- uint8_t new_code[7] = { 0xE9, 0x00, 0x00, 0x00, 0x00, 0x90, 0x90 };
+ if (limiter_addr != nullptr) {
+ //dll_log->LogEx (true, L"[FrameLimit] * Installing variable rate simulation... ");
- void *addr = TZF_Scan (sig, 14);
+ uint8_t disable_inst [] = { 0xc3, 0x90, 0x90, 0x90 };
- if (addr != NULL) {
- dll_log->Log (L"[ 60 FPS ] Scanned Lua Loader Address: %06Xh", addr);
+ TBF_InjectMachineCode ( limiter_addr,
+ disable_inst,
+ sizeof (disable_inst),
+ PAGE_EXECUTE_READWRITE );
- DWORD hookOffset = (PtrToUlong (&TZF_LuaHook) - (uintptr_t)addr - 5);
- memcpy (new_code + 1, &hookOffset, 4);
- TZF_InjectByteCode (addr, new_code, 7, PAGE_EXECUTE_READWRITE);
- pLuaReturn = (LPVOID)((uintptr_t)addr + 7);
- }
- else {
- dll_log->Log (L"[ 60 FPS ] >> ERROR: Unable to find Lua loader address! Priest bug will occur.");
+ variable_speed_installed = true;
}
}
-
- SK_ICommandProcessor* pCmdProc =
- SK_GetCommandProcessor ();
-
- // Special K already has something named this ... get it out of there!
- pCmdProc->RemoveVariable ("TargetFPS");
-
- pCmdProc->AddVariable ("TargetFPS", TZF_CreateVar (SK_IVariable::Int, (int *)&config.framerate.target));
- pCmdProc->AddVariable ("BattleFPS", TZF_CreateVar (SK_IVariable::Int, (int *)&config.framerate.battle_target));
- pCmdProc->AddVariable ("BattleAdaptive", TZF_CreateVar (SK_IVariable::Boolean, (bool *)&config.framerate.battle_adaptive));
- pCmdProc->AddVariable ("CutsceneFPS", TZF_CreateVar (SK_IVariable::Int, (int *)&config.framerate.cutscene_target));
-
- // No matter which technique we use, these things need to be options
- pCmdProc->AddVariable ("MinimizeLatency", TZF_CreateVar (SK_IVariable::Boolean, &config.framerate.minimize_latency));
-
- // Hook this no matter what, because it lowers the _REPORTED_ CPU usage,
- // and some people would object if we suddenly changed this behavior :P
- TZF_CreateDLLHook ( config.system.injector.c_str (), "Sleep_Detour",
- Sleep_Detour,
- (LPVOID *)&Sleep_Original,
- (LPVOID *)&pfnSleep );
- TZF_EnableHook (pfnSleep);
-
- pCmdProc->AddVariable ("AllowFakeSleep", TZF_CreateVar (SK_IVariable::Boolean, &config.framerate.allow_fake_sleep));
- pCmdProc->AddVariable ("YieldProcessor", TZF_CreateVar (SK_IVariable::Boolean, &config.framerate.yield_processor));
-
- pCmdProc->AddVariable ("AutoAdjust", TZF_CreateVar (SK_IVariable::Boolean, &config.framerate.auto_adjust));
}
void
-tzf::FrameRateFix::Shutdown (void)
+tbf::FrameRateFix::Shutdown (void)
{
+ DeleteCriticalSection (&alter_speed_cs);
+
FreeLibrary (kernel32_dll);
FreeLibrary (bink_dll);
- ////TZF_DisableHook (pfnSK_SetPresentParamsD3D9);
+ ////TBF_DisableHook (pfnSK_SetPresentParamsD3D9);
if (variable_speed_installed) {
- DWORD dwOld;
-
- VirtualProtect ((LPVOID)config.framerate.speedresetcode_addr, 17, PAGE_EXECUTE_READWRITE, &dwOld);
- *((DWORD *)(config.framerate.speedresetcode_addr + 2)) -= 8;
- *((DWORD *)(config.framerate.speedresetcode_addr + 8)) -= 8;
- *((DWORD *)(config.framerate.speedresetcode_addr + 13)) += 2;
- VirtualProtect ((LPVOID)config.framerate.speedresetcode_addr, 17, dwOld, &dwOld);
-
- TZF_FlushInstructionCache ((LPCVOID)config.framerate.speedresetcode_addr, 17);
-
- TZF_InjectByteCode ( (LPVOID)config.framerate.speedresetcode2_addr,
- old_speed_reset_code2,
- 7,
- PAGE_EXECUTE_READWRITE );
-
- SK_GetCommandProcessor ()->ProcessCommandLine ("TickScale 2");
-
- variable_speed_installed = false;
- }
-
- ////TZF_DisableHook (pfnSleep);
-}
-
-static int fps_before = 60;
-bool forced_30 = false;
-
-void
-tzf::FrameRateFix::Begin30FPSEvent (void)
-{
- //EnterCriticalSection (&alter_speed_cs);
-
- if (variable_speed_installed && (! forced_30)) {
- forced_30 = true;
- fps_before = target_fps;
- SetFPS (30);
- }
-
- //LeaveCriticalSection (&alter_speed_cs);
-}
-
-void
-tzf::FrameRateFix::End30FPSEvent (void)
-{
- //EnterCriticalSection (&alter_speed_cs);
-
- if (variable_speed_installed && (forced_30)) {
- forced_30 = false;
- SetFPS (fps_before);
- }
-
- //LeaveCriticalSection (&alter_speed_cs);
-}
-
-void
-tzf::FrameRateFix::SetFPS (int fps)
-{
- //EnterCriticalSection (&alter_speed_cs);
-
- if (variable_speed_installed && (target_fps != fps)) {
- target_fps = fps;
- char szRescale [32];
- sprintf (szRescale, "TickScale %li", CalcTickScale (1000.0f * (1.0f / fps)));
- SK_GetCommandProcessor ()->ProcessCommandLine (szRescale);
- }
-
- //LeaveCriticalSection (&alter_speed_cs);
-}
-
-
-
-
-bool use_accumulator = false;
-
-tzf::FrameRateFix::CommandProcessor* tzf::FrameRateFix::CommandProcessor::pCommProc;
-
-tzf::FrameRateFix::CommandProcessor::CommandProcessor (void)
-{
- tick_scale_ = TZF_CreateVar (SK_IVariable::Int, &tick_scale, this);
-
- SK_ICommandProcessor* pCmdProc =
- SK_GetCommandProcessor ();
-
- pCmdProc->AddVariable ("TickScale", tick_scale_);
-
- pCmdProc->AddVariable ("UseAccumulator", TZF_CreateVar (SK_IVariable::Boolean, &use_accumulator));
- pCmdProc->AddVariable ("MaxFrameLatency", TZF_CreateVar (SK_IVariable::Int, &max_latency));
- pCmdProc->AddVariable ("WaitForVBLANK", TZF_CreateVar (SK_IVariable::Boolean, &wait_for_vblank));
- pCmdProc->AddVariable ("LimiterTolerance", TZF_CreateVar (SK_IVariable::Float, &limiter_tolerance));
-}
-
-bool
-tzf::FrameRateFix::CommandProcessor::OnVarChange (SK_IVariable* var, void* val)
-{
- DWORD dwOld;
-
- if (var == tick_scale_) {
- DWORD original0 = *((DWORD *)(TICK_ADDR_BASE ));
- DWORD original1 = *((DWORD *)(TICK_ADDR_BASE + 4));
-
- if (val != nullptr) {
- VirtualProtect ((LPVOID)TICK_ADDR_BASE, 8, PAGE_READWRITE, &dwOld);
-
- if (variable_speed_installed) {
- // Battle Tickrate
- *(DWORD *)(TICK_ADDR_BASE) = *(DWORD *)val;
- }
-
- if (variable_speed_installed) {
- // World Tickrate
- *(DWORD *)(TICK_ADDR_BASE + 4) = *(DWORD *)val;
- }
- *(DWORD *)val = *(DWORD *)(TICK_ADDR_BASE + 4);
-
- VirtualProtect ((LPVOID)TICK_ADDR_BASE, 8, dwOld, &dwOld);
-
- if (variable_speed_installed) {
- // mov eax, 02 to mov eax,
- VirtualProtect ((LPVOID)config.framerate.speedresetcode3_addr, 4, PAGE_EXECUTE_READWRITE, &dwOld);
- *(DWORD *)config.framerate.speedresetcode3_addr = *(DWORD *)val;
- VirtualProtect ((LPVOID)config.framerate.speedresetcode3_addr, 4, dwOld, &dwOld);
-
- uint8_t new_code [7] = { 0xB8, (uint8_t)*(DWORD *)val, 0x00, 0x00, 0x00, 0x90, 0x90 };
-
- TZF_InjectByteCode ( (LPVOID)config.framerate.speedresetcode2_addr,
- new_code,
- 7,
- PAGE_EXECUTE_READWRITE,
- old_speed_reset_code2 );
- }
- //InterlockedExchange ((DWORD *)val, *(DWORD *)config.framerate.speedresetcode3_addr);
-
- tick_scale = *(int32_t *)val;
- }
}
- return true;
-}
-
-
-
-long
-tzf::FrameRateFix::CalcTickScale (double elapsed_ms)
-{
- const double tick_ms = (1.0 / 60.0) * 1000.0;
- const double inv_rate = 1.0 / target_fps;
-
- long scale = min (max (elapsed_ms / tick_ms, 1), 7);
-
- if (scale > 6)
- scale = max (inv_rate / (1.0 / 60.0), 1);
-
- return scale;
+ ////TBF_DisableHook (pfnSleep);
}
-
+//
+// Called at the end of every frame to make sure the mod's replacement framerate limiter
+// is following user preferences.
+//
void
-tzf::FrameRateFix::RenderTick (void)
+tbf::FrameRateFix::RenderTick (void)
{
- if (! forced_30) {
- //if (config.framerate.cutscene_target != config.framerate.target)
- if (game_state.inCutscene ())
- SetFPS (config.framerate.cutscene_target);
-
- //if (config.framerate.battle_target != config.framerate.target)
- else if (game_state.inBattle ())
- SetFPS (config.framerate.battle_target);
-
- else //if (! (game_state.inBattle () || game_state.inCutscene ()))
- SetFPS (config.framerate.target);
- }
-
- static LARGE_INTEGER last_time = { 0 };
- static LARGE_INTEGER freq = { 0 };
-
- LARGE_INTEGER time;
-
- QueryPerformanceFrequency (&freq);
-
- static uint32_t last_limit = target_fps;
-
- if (limiter == nullptr) {
- limiter = new FramerateLimiter ();
- last_limit = 0;
- }
-
- if (last_limit != target_fps) {
- limiter->change_limit (target_fps);
-
- last_limit = target_fps;
- }
-
- // Skip the limiter while loading, it needlessly
- // prolongs loading screens otherwise.
- if (! game_state.isLoading ())
- limiter->wait ();
-
- QueryPerformanceCounter_Original (&time);
-
-
- if (forced_30) {
- last_time.QuadPart = time.QuadPart;
- return;
- }
-
-
- double dt = ((double)(time.QuadPart - last_time.QuadPart) / (double)freq.QuadPart) / (1.0 / 60.0);
-
-
-#ifdef ACCUMULATOR
- static double accum = 0.0;
-
- if (use_accumulator) {
- accum += dt - floor (dt);
-
- time.QuadPart +=
- (dt - floor (dt)) * (1.0 / 60.0) * freq.QuadPart;
-
- dt -= (dt - floor (dt));
-
- if (accum >= 1.0) {
- time.QuadPart -=
- (accum - (accum - floor (accum))) * (1.0 / 60.0) * freq.QuadPart;
- dt += accum - (accum - floor (accum));
- accum -= accum - (accum - floor (accum));
- }
- } else {
- accum = 0.0;
+ uint32_t* pTickScale =
+ (uint32_t *)(TBF_GetBaseAddr () + TICK_ADDR_BASE);
+
+ if (*pTickScale != tick_scale) {
+ dll_log->Log ( L"[FrameLimit] [@] Framerate limit changed from "
+ L"%04.1f FPS to %04.1f FPS...",
+ 60.0f / (float)tick_scale,
+ 60.0f / (float)*pTickScale );
+
+ tick_scale = *pTickScale;
+ target_fps = 60 / max (0, tick_scale);
+
+ SK_GetCommandProcessor ()->ProcessCommandFormatted (
+ "TargetFPS %f",
+ 60.0f / (float)tick_scale
+ );
}
-#endif
-
- long scale = CalcTickScale (dt * (1.0 / 60.0) * 1000.0);
-
- static bool last_frame_battle = false;
-
- if (scale != tick_scale) {
- if (config.framerate.auto_adjust || (config.framerate.battle_adaptive && game_state.inBattle ())) {
- if (config.framerate.battle_adaptive && game_state.inBattle ()) {
- last_frame_battle = true;
-
-#if 0
- dll_log->Log ( L"[FrameLimit] ** Adjusting TickScale because of battle framerate change "
- L"(Expected: ~%4.2f ms, Got: %4.2f ms)",
- last_scale * 16.666667f, dt * (1.0 / 60.0) * 1000.0 );
-#endif
- }
-
- SK_GetCommandProcessor ()->ProcessCommandFormatted ("TickScale %li", scale);
- }
- }
-
- if (last_frame_battle && (! game_state.inBattle ()))
- target_fps = 1; // Reset FPS and TickScale on the next frame.
-
- if (! game_state.inBattle ())
- last_frame_battle = false;
-
- last_time.QuadPart = time.QuadPart;
-}
+}
\ No newline at end of file
diff --git a/src/log.cpp b/src/log.cpp
index ef270ad..721ec8a 100644
--- a/src/log.cpp
+++ b/src/log.cpp
@@ -24,7 +24,7 @@
#include
#include "log.h"
-iSK_Logger* dll_log;
+iSK_Logger* dll_log = nullptr;
iSK_Logger*
TBF_CreateLog (const wchar_t* const wszName)
diff --git a/src/parameter.cpp b/src/parameter.cpp
index 5a66e3b..c578f61 100644
--- a/src/parameter.cpp
+++ b/src/parameter.cpp
@@ -142,10 +142,17 @@ tbf::ParameterInt64::load (int64_t& ref)
std::wstring
tbf::ParameterBool::get_value_str (void)
{
- if (value == true)
- return L"true";
-
- return L"false";
+ switch (type) {
+ case ZeroNonZero:
+ return value ? L"1" : L"0";
+ case YesNo:
+ return value ? L"Yes" : L"No";
+ case OnOff:
+ return value ? L"On" : L"Off";
+ case TrueFalse:
+ default:
+ return value ? L"True" : L"False";
+ }
}
bool
@@ -164,19 +171,57 @@ tbf::ParameterBool::set_value (bool val)
void
tbf::ParameterBool::set_value_str (std::wstring str)
{
- if (str.length () == 1 &&
- str [0] == L'1')
- value = true;
+ size_t len = str.length ();
+
+ type = TrueFalse;
+
+ switch (len)
+ {
+ case 1:
+ type = ZeroNonZero;
- else if (str.length () == 4 &&
- towlower (str [0]) == L't' &&
- towlower (str [1]) == L'r' &&
- towlower (str [2]) == L'u' &&
- towlower (str [3]) == L'e')
- value = true;
+ if (str [0] == L'1')
+ value = true;
+ break;
+
+ case 2:
+ if ( towlower (str [0]) == L'o' &&
+ towlower (str [1]) == L'n' ) {
+ type = OnOff;
+ value = true;
+ } else if ( towlower (str [0]) == L'n' &&
+ towlower (str [1]) == L'o' ) {
+ type = YesNo;
+ value = false;
+ }
+ break;
- else
- value = false;
+ case 3:
+ if ( towlower (str [0]) == L'y' &&
+ towlower (str [1]) == L'e' &&
+ towlower (str [2]) == L's' ) {
+ type = YesNo;
+ value = true;
+ } else if ( towlower (str [0]) == L'o' &&
+ towlower (str [1]) == L'f' &&
+ towlower (str [2]) == L'f' ) {
+ type = OnOff;
+ value = false;
+ }
+ break;
+
+ case 4:
+ if ( towlower (str [0]) == L't' &&
+ towlower (str [1]) == L'r' &&
+ towlower (str [2]) == L'u' &&
+ towlower (str [3]) == L'e' )
+ value = true;
+ break;
+
+ default:
+ value = false;
+ break;
+ }
}
diff --git a/src/render.cpp b/src/render.cpp
index 28dae20..4d17c69 100644
--- a/src/render.cpp
+++ b/src/render.cpp
@@ -138,7 +138,7 @@ D3D9SetSamplerState_Detour (IDirect3DDevice9* This,
Type == D3DSAMP_MIPMAPLODBIAS) {
//dll_log->Log (L" [!] IDirect3DDevice9::SetSamplerState (...)");
- if (Type < 8) {
+ if (Type <= 8) {
//dll_log->Log (L" %s Filter: %x", Type == D3DSAMP_MIPFILTER ? L"Mip" : Type == D3DSAMP_MINFILTER ? L"Min" : L"Mag", Value);
if (Type == D3DSAMP_MIPFILTER && Value != D3DTEXF_NONE) {
Value = D3DTEXF_LINEAR;
@@ -151,11 +151,11 @@ D3D9SetSamplerState_Detour (IDirect3DDevice9* This,
// Clamp [0, oo)
if (Type == D3DSAMP_MIPMAPLODBIAS) {
- float fMax =
- max (0.0f, *(float *)&Value);
+ float fMax = config.textures.lod_bias;
+ //float fMax =
+ //max (0.0f, *reinterpret_cast (&Value));
- *(DWORD *)&Value =
- *(DWORD *)&fMax;
+ Value = *reinterpret_cast (&fMax);
}
}
}
@@ -659,6 +659,11 @@ D3D9EndFrame_Post (HRESULT hr, IUnknown* device)
hr = SK_EndBufferSwap (hr, device);
+ if ( config.framerate.replace_limiter &&
+ tbf::FrameRateFix::variable_speed_installed ) {
+ tbf::FrameRateFix::RenderTick ();
+ }
+
//if (config.framerate.minimize_latency)
//tbf::FrameRateFix::RenderTick ();
@@ -1780,22 +1785,30 @@ tbf::RenderFix::CommandProcessor::CommandProcessor (void)
SK_IVariable* aspect_correct_vids = TBF_CreateVar (SK_IVariable::Boolean, &config.render.blackbar_videos);
SK_IVariable* aspect_correction = TBF_CreateVar (SK_IVariable::Boolean, &config.render.aspect_correction);
+ SK_IVariable* postproc_ratio = TBF_CreateVar (SK_IVariable::Float, &config.render.postproc_ratio);
+ SK_IVariable* clear_blackbars = TBF_CreateVar (SK_IVariable::Boolean, &config.render.clear_blackbars);
+
SK_IVariable* remaster_textures = TBF_CreateVar (SK_IVariable::Boolean, &config.textures.remaster);
+ SK_IVariable* lod_bias = TBF_CreateVar (SK_IVariable::Float, &config.textures.lod_bias);
+ SK_IVariable* uncompressed = TBF_CreateVar (SK_IVariable::Boolean, &config.textures.uncompressed);
+
SK_IVariable* rescale_shadows = TBF_CreateVar (SK_IVariable::Int, &config.render.shadow_rescale);
SK_IVariable* rescale_env_shadows = TBF_CreateVar (SK_IVariable::Int, &config.render.env_shadow_rescale);
- SK_IVariable* postproc_ratio = TBF_CreateVar (SK_IVariable::Float, &config.render.postproc_ratio);
- SK_IVariable* clear_blackbars = TBF_CreateVar (SK_IVariable::Boolean, &config.render.clear_blackbars);
//command.AddVariable ("AspectRatio", aspect_ratio_);
//command.AddVariable ("FOVY", fovy_);
- command.AddVariable ("AspectCorrectVideos", aspect_correct_vids);
- command.AddVariable ("AspectCorrection", aspect_correction);
- command.AddVariable ("RemasterTextures", remaster_textures);
- command.AddVariable ("RescaleShadows", rescale_shadows);
- command.AddVariable ("RescaleEnvShadows", rescale_env_shadows);
- command.AddVariable ("PostProcessRatio", postproc_ratio);
- command.AddVariable ("ClearBlackbars", clear_blackbars);
+ command.AddVariable ("Textures.Remaster", remaster_textures);
+ command.AddVariable ("Textures.LODBias", lod_bias);
+ command.AddVariable ("Textures.Uncompressed", uncompressed);
+
+ command.AddVariable ("Shadows.Rescale", rescale_shadows);
+ command.AddVariable ("Shadows.RescaleEnv", rescale_env_shadows);
+
+ command.AddVariable ("AspectCorrectVideos", aspect_correct_vids);
+ command.AddVariable ("AspectCorrection", aspect_correction);
+ command.AddVariable ("PostProcessRatio", postproc_ratio);
+ command.AddVariable ("ClearBlackbars", clear_blackbars);
command.AddVariable ("TestVS", TBF_CreateVar (SK_IVariable::Int, &TEST_VS));
diff --git a/src/scanner.cpp b/src/scanner.cpp
index a2511cd..1df5679 100644
--- a/src/scanner.cpp
+++ b/src/scanner.cpp
@@ -24,6 +24,12 @@
#include
+uintptr_t
+TBF_GetBaseAddr (void)
+{
+ return (uintptr_t)GetModuleHandle (nullptr);
+}
+
void*
TBF_Scan (uint8_t* pattern, size_t len, uint8_t* mask)
{
diff --git a/src/textures.cpp b/src/textures.cpp
index efdf6f1..c399c6f 100644
--- a/src/textures.cpp
+++ b/src/textures.cpp
@@ -59,31 +59,28 @@ typedef HRESULT (STDMETHODCALLTYPE *SetRenderState_pfn)
static D3DXSaveTextureToFile_pfn D3DXSaveTextureToFile = nullptr;
-static D3DXCreateTextureFromFileInMemoryEx_pfn D3DXCreateTextureFromFileInMemoryEx_Original = nullptr;
+static D3DXCreateTextureFromFileInMemoryEx_pfn D3DXCreateTextureFromFileInMemoryEx = nullptr;
-static BeginScene_pfn D3D9BeginScene_Original = nullptr;
-static EndScene_pfn D3D9EndScene_Original = nullptr;
- SetRenderState_pfn D3D9SetRenderState_Original = nullptr;
+static BeginScene_pfn D3D9BeginScene = nullptr;
+static EndScene_pfn D3D9EndScene = nullptr;
+ SetRenderState_pfn D3D9SetRenderState = nullptr;
-static StretchRect_pfn D3D9StretchRect_Original = nullptr;
-static CreateTexture_pfn D3D9CreateTexture_Original = nullptr;
-static CreateRenderTarget_pfn D3D9CreateRenderTarget_Original = nullptr;
-static CreateDepthStencilSurface_pfn D3D9CreateDepthStencilSurface_Original = nullptr;
+static StretchRect_pfn D3D9StretchRect = nullptr;
+static CreateTexture_pfn D3D9CreateTexture = nullptr;
+static CreateRenderTarget_pfn D3D9CreateRenderTarget = nullptr;
+static CreateDepthStencilSurface_pfn D3D9CreateDepthStencilSurface = nullptr;
-static SetTexture_pfn D3D9SetTexture_Original = nullptr;
-static SetRenderTarget_pfn D3D9SetRenderTarget_Original = nullptr;
-static SetDepthStencilSurface_pfn D3D9SetDepthStencilSurface_Original = nullptr;
+static SetTexture_pfn D3D9SetTexture = nullptr;
+static SetRenderTarget_pfn D3D9SetRenderTarget = nullptr;
+static SetDepthStencilSurface_pfn D3D9SetDepthStencilSurface = nullptr;
extern uint32_t
TBF_MakeShadowBitShift (uint32_t dim);
-typedef BOOL(WINAPI *QueryPerformanceCounter_t)(_Out_ LARGE_INTEGER *lpPerformanceCount);
-extern QueryPerformanceCounter_t QueryPerformanceCounter_Original;
-
tbf::RenderFix::TextureManager
tbf::RenderFix::tex_mgr;
-iSK_Logger* tex_log;
+iSK_Logger* tex_log = nullptr;
#include
@@ -453,7 +450,7 @@ D3D9StretchRect_Detour ( IDirect3DDevice9 *This,
dumping = false;
- return D3D9StretchRect_Original (This, pSourceSurface, pSourceRect,
+ return D3D9StretchRect (This, pSourceSurface, pSourceRect,
pDestSurface, pDestRect,
Filter);
}
@@ -470,7 +467,7 @@ D3D9SetRenderState_Detour (IDirect3DDevice9* This,
if (This != tbf::RenderFix::pDevice) {
dll_log->Log (L"[Render Fix] >> WARNING: SetRenderState came from unknown IDirect3DDevice9! << ");
- return D3D9SetRenderState_Original (This, State, Value);
+ return D3D9SetRenderState (This, State, Value);
}
#if 0
@@ -481,7 +478,7 @@ D3D9SetRenderState_Detour (IDirect3DDevice9* This,
}
#endif
- return D3D9SetRenderState_Original (This, State, Value);
+ return D3D9SetRenderState (This, State, Value);
}
COM_DECLSPEC_NOTHROW
@@ -502,7 +499,7 @@ D3D9CreateRenderTarget_Detour (IDirect3DDevice9 *This,
Width, Height, Format, MultiSample, MultisampleQuality,
Lockable, ppSurface, pSharedHandle);
- return D3D9CreateRenderTarget_Original (This, Width, Height, Format,
+ return D3D9CreateRenderTarget (This, Width, Height, Format,
MultiSample, MultisampleQuality,
Lockable, ppSurface, pSharedHandle);
}
@@ -525,7 +522,7 @@ D3D9CreateDepthStencilSurface_Detour (IDirect3DDevice9 *This,
Width, Height, Format, MultiSample, MultisampleQuality,
Discard, ppSurface, pSharedHandle);
- return D3D9CreateDepthStencilSurface_Original (This, Width, Height, Format,
+ return D3D9CreateDepthStencilSurface (This, Width, Height, Format,
MultiSample, MultisampleQuality,
Discard, ppSurface, pSharedHandle);
}
@@ -569,7 +566,7 @@ D3D9StretchRect_Detour ( IDirect3DDevice9 *This,
{
dumping = false;
- return D3D9StretchRect_Original (This, pSourceSurface, pSourceRect,
+ return D3D9StretchRect (This, pSourceSurface, pSourceRect,
pDestSurface, pDestRect,
Filter);
}
@@ -588,10 +585,10 @@ D3D9SetDepthStencilSurface_Detour (
{
// Ignore anything that's not the primary render device.
if (This != tbf::RenderFix::pDevice) {
- return D3D9SetDepthStencilSurface_Original (This, pNewZStencil);
+ return D3D9SetDepthStencilSurface (This, pNewZStencil);
}
- return D3D9SetDepthStencilSurface_Original (This, pNewZStencil);
+ return D3D9SetDepthStencilSurface (This, pNewZStencil);
}
@@ -609,7 +606,7 @@ D3D9SetTexture_Detour (
{
// Ignore anything that's not the primary render device.
if (This != tbf::RenderFix::pDevice) {
- return D3D9SetTexture_Original (This, Sampler, pTexture);
+ return D3D9SetTexture (This, Sampler, pTexture);
}
//if (tbf::RenderFix::tracer.log) {
@@ -627,7 +624,7 @@ D3D9SetTexture_Detour (
textures_used.insert (pSKTex->tex_crc32);
- QueryPerformanceCounter/*_Original*/ (&pSKTex->last_used);
+ QueryPerformanceCounter (&pSKTex->last_used);
//
// This is how blocking is implemented -- only do it when a texture that needs
@@ -656,7 +653,7 @@ D3D9SetTexture_Detour (
else tsf::RenderFix::active_samplers.erase (Sampler);
#endif
- return D3D9SetTexture_Original (This, Sampler, pTexture);
+ return D3D9SetTexture (This, Sampler, pTexture);
}
D3DXSaveSurfaceToFile_pfn D3DXSaveSurfaceToFileW = nullptr;
@@ -678,7 +675,7 @@ D3D9CreateTexture_Detour (IDirect3DDevice9 *This,
{
// Ignore anything that's not the primary render device.
if (This != tbf::RenderFix::pDevice) {
- return D3D9CreateTexture_Original ( This, Width, Height,
+ return D3D9CreateTexture ( This, Width, Height,
Levels, Usage, Format,
Pool, ppTexture, pSharedHandle );
}
@@ -755,7 +752,7 @@ D3D9CreateTexture_Detour (IDirect3DDevice9 *This,
int levels = Levels;
HRESULT result =
- D3D9CreateTexture_Original (This, Width, Height, levels, Usage,
+ D3D9CreateTexture (This, Width, Height, levels, Usage,
Format, Pool, ppTexture, pSharedHandle);
return result;
@@ -770,7 +767,7 @@ D3D9BeginScene_Detour (IDirect3DDevice9* This)
if (This != tbf::RenderFix::pDevice) {
dll_log->Log (L"[Render Fix] >> WARNING: D3D9 BeginScene came from unknown IDirect3DDevice9! << ");
- return D3D9BeginScene_Original (This);
+ return D3D9BeginScene (This);
}
tbf::RenderFix::draw_state.draws = 0;
@@ -781,7 +778,7 @@ D3D9BeginScene_Detour (IDirect3DDevice9* This)
D3D9_VIRTUAL_OVERRIDE ( &This, 16,
L"IDirect3DDevice9::Reset",
D3D9Reset_Detour,
- D3D9Reset_Original,
+ D3D9Reset,
Reset_pfn );
D3DXCreateFontW ( This,
@@ -795,7 +792,7 @@ sss L"Arial",
}
#endif
- HRESULT result = D3D9BeginScene_Original (This);
+ HRESULT result = D3D9BeginScene (This);
return result;
}
@@ -808,9 +805,9 @@ D3D9EndScene_Detour (IDirect3DDevice9* This)
{
// Ignore anything that's not the primary render device.
if (This != tbf::RenderFix::pDevice) {
- return D3D9EndScene_Original (This);
+ return D3D9EndScene (This);
}
- return D3D9EndScene_Original (This);
+ return D3D9EndScene (This);
}
#endif
@@ -938,14 +935,11 @@ static D3DXCreateTextureFromFile_pfn
#define D3DX_SKIP_DDS_MIP_LEVELS(l, f) ((((l) & D3DX_SKIP_DDS_MIP_LEVELS_MASK) \
<< D3DX_SKIP_DDS_MIP_LEVELS_SHIFT) | ((f) == D3DX_DEFAULT ? D3DX_FILTER_BOX : (f)))
-typedef BOOL(WINAPI *QueryPerformanceCounter_t)(_Out_ LARGE_INTEGER *lpPerformanceCount);
-extern QueryPerformanceCounter_t QueryPerformanceCounter_Original;
-
#define __PTR_SIZE sizeof LPCVOID
#define __PAGE_PRIVS PAGE_EXECUTE_READWRITE
-#define D3D9_VIRTUAL_OVERRIDE(_Base,_Index,_Name,_Override,_Original,_Type) { \
+#define D3D9_VIRTUAL_OVERRIDE(_Base,_Index,_Name,_Override,_Type) { \
void** vftable = *(void***)*_Base; \
\
if (vftable [_Index] != _Override) { \
@@ -957,10 +951,10 @@ extern QueryPerformanceCounter_t QueryPerformanceCounter_Original;
/*L##_Name, vftable [_Index], */\
/*SK_DescribeVirtualProtectFlags (dwProtect)); */\
\
- if (_Original == NULL) \
- _Original = (##_Type)vftable [_Index]; \
+ if ( == NULL) \
+ = (##_Type)vftable [_Index]; \
\
- /*dll_log->Log (L" + %s: %08Xh", L#_Original, _Original);*/ \
+ /*dll_log->Log (L" + %s: %08Xh", L#, );*/ \
\
vftable [_Index] = _Override; \
\
@@ -1489,7 +1483,7 @@ InjectTexture (tbf_tex_load_s* load)
load->SrcDataSize,
&img_info );
- hr = D3DXCreateTextureFromFileInMemoryEx_Original (
+ hr = D3DXCreateTextureFromFileInMemoryEx (
load->pDevice,
load->pSrcData, load->SrcDataSize,
D3DX_DEFAULT, D3DX_DEFAULT, img_info.MipLevels,
@@ -1591,7 +1585,7 @@ TBFix_LoadQueuedTextures (void)
tbf_tex_load_s* load =
*it;
- QueryPerformanceCounter/*_Original*/ (&load->end);
+ QueryPerformanceCounter (&load->end);
if (true) {
tex_log->Log ( L"[%s] Finished %s texture %08x (%5.2f MiB in %9.4f ms)",
@@ -1623,7 +1617,7 @@ TBFix_LoadQueuedTextures (void)
tex_log->Log (L"[ Tex. Mgr ] >> Original texture no longer referenced, discarding new one!");
load->pSrc->Release ();
} else {
- QueryPerformanceCounter/*_Original*/ (&pSKTex->last_used);
+ QueryPerformanceCounter (&pSKTex->last_used);
pSKTex->pTexOverride = load->pSrc;
pSKTex->override_size = load->SrcDataSize;
@@ -1706,7 +1700,7 @@ D3DXCreateTextureFromFileInMemoryEx_Detour (
// Injection would recurse slightly and cause impossible to diagnose reference counting problems
// with texture caching if we did not check for this!
if (inject_thread) {
- return D3DXCreateTextureFromFileInMemoryEx_Original (
+ return D3DXCreateTextureFromFileInMemoryEx (
pDevice,
pSrcData, SrcDataSize,
Width, Height, MipLevels,
@@ -1734,7 +1728,7 @@ D3DXCreateTextureFromFileInMemoryEx_Detour (
if (freq.QuadPart == 0LL)
QueryPerformanceFrequency (&freq);
- QueryPerformanceCounter/*_Original*/ (&start);
+ QueryPerformanceCounter (&start);
uint32_t checksum =
crc32 (0, pSrcData, SrcDataSize);
@@ -1760,7 +1754,7 @@ D3DXCreateTextureFromFileInMemoryEx_Detour (
// Necessary to make D3DX texture write functions work
if ( Pool == D3DPOOL_DEFAULT && config.textures.dump &&
- (! dumped_textures.count (checksum)) &&
+ (! dumped_textures.count (checksum)) &&
(! injectable_textures.count (checksum)) )
Usage = D3DUSAGE_DYNAMIC;
@@ -1775,7 +1769,7 @@ D3DXCreateTextureFromFileInMemoryEx_Detour (
if (true) {//fmt_real == D3DFMT_DXT1 ||
//fmt_real == D3DFMT_DXT3 ||
//fmt_real == D3DFMT_DXT5) {
- if (/*info.Width >= 128 && info.Height >= 128 && */info.MipLevels == 3) {
+ if (/*info.Width >= 128 && info.Height >= 128 && */ info.MipLevels > 1 || config.textures.uncompressed) {
// Don't resample faces
if ( resample_blacklist.count (checksum) == 0 )
resample = true;
@@ -1844,9 +1838,9 @@ D3DXCreateTextureFromFileInMemoryEx_Detour (
//tex_log->Log (L"D3DXCreateTextureFromFileInMemoryEx (... MipLevels=%lu ...)", MipLevels);
hr =
- D3DXCreateTextureFromFileInMemoryEx_Original ( pDevice,
+ D3DXCreateTextureFromFileInMemoryEx ( pDevice,
pSrcData, SrcDataSize,
- Width, Height, will_replace ? 1 : MipLevels,
+ Width, Height, MipLevels,
Usage, Format, Pool,
Filter, MipFilter, ColorKey,
pSrcInfo, pPalette,
@@ -1968,7 +1962,7 @@ D3DXCreateTextureFromFileInMemoryEx_Detour (
//
else if (load_op != nullptr && load_op->type == tsf_tex_load_s::Immediate) {
QueryPerformanceFrequency (&load_op->freq);
- QueryPerformanceCounter/*_Original*/ (&load_op->start);
+ QueryPerformanceCounter (&load_op->start);
EnterCriticalSection (&cs_tex_inject);
inject_tids.insert (GetCurrentThreadId ());
@@ -1982,7 +1976,7 @@ D3DXCreateTextureFromFileInMemoryEx_Detour (
inject_tids.erase (GetCurrentThreadId ());
LeaveCriticalSection (&cs_tex_inject);
- QueryPerformanceCounter/*_Original*/ (&load_op->end);
+ QueryPerformanceCounter (&load_op->end);
if (SUCCEEDED (hr)) {
tex_log->Log ( L"[Inject Tex] Finished synchronous texture %08x (%5.2f MiB in %9.4f ms)",
@@ -2036,7 +2030,7 @@ D3DXCreateTextureFromFileInMemoryEx_Detour (
load_op = nullptr;
}
- QueryPerformanceCounter/*_Original*/ (&end);
+ QueryPerformanceCounter (&end);
if (SUCCEEDED (hr)) {
if (config.textures.cache && checksum != 0x00) {
@@ -2206,7 +2200,7 @@ D3D9SetRenderTarget_Detour (
// Ignore anything that's not the primary render device.
if (This != tbf::RenderFix::pDevice) {
- return D3D9SetRenderTarget_Original (This, RenderTargetIndex, pRenderTarget);
+ return D3D9SetRenderTarget (This, RenderTargetIndex, pRenderTarget);
}
//if (tsf::RenderFix::tracer.log) {
@@ -2249,7 +2243,7 @@ D3D9SetRenderTarget_Detour (
#endif
//}
- return D3D9SetRenderTarget_Original (This, RenderTargetIndex, pRenderTarget);
+ return D3D9SetRenderTarget (This, RenderTargetIndex, pRenderTarget);
}
void
@@ -2548,47 +2542,47 @@ tbf::RenderFix::TextureManager::Init (void)
TBF_CreateDLLHook ( config.system.injector.c_str (),
"D3D9SetRenderState_Override",
D3D9SetRenderState_Detour,
- (LPVOID*)&D3D9SetRenderState_Original );
+ (LPVOID*)&D3D9SetRenderState );
TBF_CreateDLLHook ( config.system.injector.c_str (),
"D3D9BeginScene_Override",
D3D9BeginScene_Detour,
- (LPVOID*)&D3D9BeginScene_Original );
+ (LPVOID*)&D3D9BeginScene );
TBF_CreateDLLHook ( config.system.injector.c_str (),
"D3D9StretchRect_Override",
D3D9StretchRect_Detour,
- (LPVOID*)&D3D9StretchRect_Original );
+ (LPVOID*)&D3D9StretchRect );
TBF_CreateDLLHook ( config.system.injector.c_str (),
"D3D9CreateDepthStencilSurface_Override",
D3D9CreateDepthStencilSurface_Detour,
- (LPVOID*)&D3D9CreateDepthStencilSurface_Original );
+ (LPVOID*)&D3D9CreateDepthStencilSurface );
TBF_CreateDLLHook ( config.system.injector.c_str (),
"D3D9CreateTexture_Override",
D3D9CreateTexture_Detour,
- (LPVOID*)&D3D9CreateTexture_Original );
+ (LPVOID*)&D3D9CreateTexture );
TBF_CreateDLLHook ( config.system.injector.c_str (),
"D3D9SetTexture_Override",
D3D9SetTexture_Detour,
- (LPVOID*)&D3D9SetTexture_Original );
+ (LPVOID*)&D3D9SetTexture );
TBF_CreateDLLHook ( config.system.injector.c_str (),
"D3D9SetRenderTarget_Override",
D3D9SetRenderTarget_Detour,
- (LPVOID*)&D3D9SetRenderTarget_Original );
+ (LPVOID*)&D3D9SetRenderTarget );
TBF_CreateDLLHook ( config.system.injector.c_str (),
"D3D9SetDepthStencilSurface_Override",
D3D9SetDepthStencilSurface_Detour,
- (LPVOID*)&D3D9SetDepthStencilSurface_Original );
+ (LPVOID*)&D3D9SetDepthStencilSurface );
TBF_CreateDLLHook ( L"D3DX9_43.DLL",
"D3DXCreateTextureFromFileInMemoryEx",
D3DXCreateTextureFromFileInMemoryEx_Detour,
- (LPVOID *)&D3DXCreateTextureFromFileInMemoryEx_Original );
+ (LPVOID *)&D3DXCreateTextureFromFileInMemoryEx );
D3DXSaveTextureToFile =
(D3DXSaveTextureToFile_pfn)
@@ -2616,19 +2610,19 @@ tbf::RenderFix::TextureManager::Init (void)
"D3DXGetImageInfoFromFileW" );
// We don't hook this, but we still use it...
- if (D3D9CreateRenderTarget_Original == nullptr) {
+ if (D3D9CreateRenderTarget == nullptr) {
static HMODULE hModD3D9 =
GetModuleHandle (config.system.injector.c_str ());
- D3D9CreateRenderTarget_Original =
+ D3D9CreateRenderTarget =
(CreateRenderTarget_pfn)
GetProcAddress (hModD3D9, "D3D9CreateRenderTarget_Override");
}
// We don't hook this, but we still use it...
- if (D3D9CreateDepthStencilSurface_Original == nullptr) {
+ if (D3D9CreateDepthStencilSurface == nullptr) {
static HMODULE hModD3D9 =
GetModuleHandle (config.system.injector.c_str ());
- D3D9CreateDepthStencilSurface_Original =
+ D3D9CreateDepthStencilSurface =
(CreateDepthStencilSurface_pfn)
GetProcAddress (hModD3D9, "D3D9CreateDepthStencilSurface_Override");
}
@@ -2677,6 +2671,12 @@ bool shutting_down = false;
void
tbf::RenderFix::TextureManager::Shutdown (void)
{
+ // It is possible for the DLL to be unloaded before the texture manager is
+ // initialized, in which case a nullptr value for tex_log is the easiest
+ // way to detect this.
+ if (tex_log == nullptr)
+ return;
+
// 16.6 ms per-frame (60 FPS)
const float frame_time = 16.6f;
@@ -3033,8 +3033,8 @@ HRESULT
WINAPI
ResampleTexture (tbf_tex_load_s* load)
{
- QueryPerformanceFrequency (&load->freq);
- QueryPerformanceCounter/*_Original*/ (&load->start);
+ QueryPerformanceFrequency (&load->freq);
+ QueryPerformanceCounter (&load->start);
D3DXIMAGE_INFO img_info;
@@ -3047,13 +3047,14 @@ ResampleTexture (tbf_tex_load_s* load)
if (img_info.Depth == 1) {
hr =
- D3DXCreateTextureFromFileInMemoryEx_Original (
+ D3DXCreateTextureFromFileInMemoryEx (
load->pDevice,
load->pSrcData, load->SrcDataSize,
- img_info.Width, img_info.Height, 0,//D3DX_DEFAULT,
- 0, img_info.Format,
+ img_info.Width, img_info.Height, 0,
+ 0, config.textures.uncompressed ? D3DFMT_A8R8G8B8 : img_info.Format,
D3DPOOL_DEFAULT,
- D3DX_FILTER_POINT, D3DX_FILTER_TRIANGLE | D3DX_FILTER_DITHER,
+ D3DX_FILTER_TRIANGLE | D3DX_FILTER_DITHER,
+ D3DX_FILTER_BOX | D3DX_FILTER_DITHER,
0,
nullptr, nullptr,
&load->pSrc );
@@ -3135,13 +3136,13 @@ SK_TextureWorkerThread::ThreadProc (LPVOID user)
if (pStream->type == tbf_tex_load_s::Resample) {
InterlockedIncrement (&resampling);
- QueryPerformanceFrequency (&pStream->freq);
- QueryPerformanceCounter/*_Original*/ (&pStream->start);
+ QueryPerformanceFrequency (&pStream->freq);
+ QueryPerformanceCounter (&pStream->start);
HRESULT hr =
ResampleTexture (pStream);//InjectTexture (pStream);
- QueryPerformanceCounter/*_Original*/ (&pStream->end);
+ QueryPerformanceCounter (&pStream->end);
InterlockedDecrement (&resampling);
@@ -3153,13 +3154,13 @@ SK_TextureWorkerThread::ThreadProc (LPVOID user)
InterlockedIncrement (&streaming);
InterlockedExchangeAdd (&streaming_bytes, pStream->SrcDataSize);
- QueryPerformanceFrequency (&pStream->freq);
- QueryPerformanceCounter/*_Original*/ (&pStream->start);
+ QueryPerformanceFrequency (&pStream->freq);
+ QueryPerformanceCounter (&pStream->start);
HRESULT hr =
InjectTexture (pStream);
- QueryPerformanceCounter/*_Original*/ (&pStream->end);
+ QueryPerformanceCounter (&pStream->end);
InterlockedExchangeSubtract (&streaming_bytes, pStream->SrcDataSize);
InterlockedDecrement (&streaming);
diff --git a/tbf.VC.db b/tbf.VC.db
index f6d3ecf..d6d9c9d 100644
Binary files a/tbf.VC.db and b/tbf.VC.db differ
diff --git a/tbf.vcxproj b/tbf.vcxproj
index 6e72c93..39f24d5 100644
--- a/tbf.vcxproj
+++ b/tbf.vcxproj
@@ -229,6 +229,7 @@
+
diff --git a/tbf.vcxproj.filters b/tbf.vcxproj.filters
index 0dac966..c74d31a 100644
--- a/tbf.vcxproj.filters
+++ b/tbf.vcxproj.filters
@@ -40,6 +40,9 @@
Source Files
+
+ Source Files
+
diff --git a/version.ini b/version.ini
index 85a0419..fc40ce9 100644
Binary files a/version.ini and b/version.ini differ