parent
c27e4d04de
commit
25a6b128eb
@ -212,6 +212,26 @@ namespace
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void trigger_high_performance_gpu_switch()
|
||||||
|
{
|
||||||
|
// Make sure to link D3D11, as this might trigger high performance GPU
|
||||||
|
static volatile auto _ = &D3D11CreateDevice;
|
||||||
|
|
||||||
|
const auto key = utils::nt::open_or_create_registry_key(
|
||||||
|
HKEY_CURRENT_USER, R"(Software\Microsoft\DirectX\UserGpuPreferences)");
|
||||||
|
if (!key)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const auto self = utils::nt::library::get_by_address(&trigger_high_performance_gpu_switch);
|
||||||
|
|
||||||
|
const std::wstring data = L"GpuPreference=2;";
|
||||||
|
RegSetValueExW(key, self.get_path().make_preferred().wstring().data(), 0, REG_SZ,
|
||||||
|
reinterpret_cast<const BYTE*>(data.data()),
|
||||||
|
static_cast<DWORD>((data.size() + 1u) * 2));
|
||||||
|
}
|
||||||
|
|
||||||
int main()
|
int main()
|
||||||
{
|
{
|
||||||
if (handle_process_runner())
|
if (handle_process_runner())
|
||||||
@ -246,9 +266,14 @@ namespace
|
|||||||
|
|
||||||
const auto is_server = utils::flags::has_flag("dedicated") || (!has_client && has_server);
|
const auto is_server = utils::flags::has_flag("dedicated") || (!has_client && has_server);
|
||||||
|
|
||||||
if (!is_server && !launcher::run())
|
if (!is_server)
|
||||||
{
|
{
|
||||||
return 0;
|
trigger_high_performance_gpu_switch();
|
||||||
|
|
||||||
|
if (!launcher::run())
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!component_loader::activate(is_server))
|
if (!component_loader::activate(is_server))
|
||||||
|
@ -24,3 +24,9 @@ extern "C"
|
|||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
extern "C"
|
||||||
|
{
|
||||||
|
__declspec(dllexport) DWORD NvOptimusEnablement = 1;
|
||||||
|
__declspec(dllexport) DWORD AmdPowerXpressRequestHighPerformance = 1;
|
||||||
|
}
|
||||||
|
@ -51,6 +51,7 @@
|
|||||||
#include <iphlpapi.h>
|
#include <iphlpapi.h>
|
||||||
#include <wincrypt.h>
|
#include <wincrypt.h>
|
||||||
#include <shellscalingapi.h>
|
#include <shellscalingapi.h>
|
||||||
|
#include <d3d11.h>
|
||||||
|
|
||||||
// min and max is required by gdi, therefore NOMINMAX won't work
|
// min and max is required by gdi, therefore NOMINMAX won't work
|
||||||
#ifdef max
|
#ifdef max
|
||||||
@ -101,5 +102,6 @@
|
|||||||
#pragma comment(lib, "urlmon.lib" )
|
#pragma comment(lib, "urlmon.lib" )
|
||||||
#pragma comment(lib, "iphlpapi.lib")
|
#pragma comment(lib, "iphlpapi.lib")
|
||||||
#pragma comment(lib, "Crypt32.lib")
|
#pragma comment(lib, "Crypt32.lib")
|
||||||
|
#pragma comment(lib, "d3d11.lib")
|
||||||
|
|
||||||
using namespace std::literals;
|
using namespace std::literals;
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
#include "nt.hpp"
|
#include "nt.hpp"
|
||||||
|
#include "string.hpp"
|
||||||
|
|
||||||
namespace utils::nt
|
namespace utils::nt
|
||||||
{
|
{
|
||||||
@ -223,6 +224,34 @@ namespace utils::nt
|
|||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
registry_key open_or_create_registry_key(const HKEY base, const std::string& input)
|
||||||
|
{
|
||||||
|
const auto parts = string::split(input, '\\');
|
||||||
|
|
||||||
|
registry_key current_key = base;
|
||||||
|
|
||||||
|
for (const auto& part : parts)
|
||||||
|
{
|
||||||
|
registry_key new_key{};
|
||||||
|
if (RegOpenKeyExA(current_key, part.data(), 0,
|
||||||
|
KEY_ALL_ACCESS, &new_key) == ERROR_SUCCESS)
|
||||||
|
{
|
||||||
|
current_key = std::move(new_key);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (RegCreateKeyExA(current_key, part.data(), 0, nullptr, REG_OPTION_NON_VOLATILE, KEY_ALL_ACCESS,
|
||||||
|
nullptr, &new_key, nullptr) != ERROR_SUCCESS)
|
||||||
|
{
|
||||||
|
return {};
|
||||||
|
}
|
||||||
|
|
||||||
|
current_key = std::move(new_key);
|
||||||
|
}
|
||||||
|
|
||||||
|
return current_key;
|
||||||
|
}
|
||||||
|
|
||||||
bool is_wine()
|
bool is_wine()
|
||||||
{
|
{
|
||||||
static const auto has_wine_export = []() -> bool
|
static const auto has_wine_export = []() -> bool
|
||||||
|
@ -173,6 +173,77 @@ namespace utils::nt
|
|||||||
HANDLE handle_{InvalidHandle};
|
HANDLE handle_{InvalidHandle};
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
class registry_key
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
registry_key() = default;
|
||||||
|
|
||||||
|
registry_key(HKEY key)
|
||||||
|
: key_(key)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
registry_key(const registry_key&) = delete;
|
||||||
|
registry_key& operator=(const registry_key&) = delete;
|
||||||
|
|
||||||
|
registry_key(registry_key&& obj) noexcept
|
||||||
|
: registry_key()
|
||||||
|
{
|
||||||
|
this->operator=(std::move(obj));
|
||||||
|
}
|
||||||
|
|
||||||
|
registry_key& operator=(registry_key&& obj) noexcept
|
||||||
|
{
|
||||||
|
if (this != obj.GetRef())
|
||||||
|
{
|
||||||
|
this->~registry_key();
|
||||||
|
this->key_ = obj.key_;
|
||||||
|
obj.key_ = nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
|
||||||
|
~registry_key()
|
||||||
|
{
|
||||||
|
if (this->key_)
|
||||||
|
{
|
||||||
|
RegCloseKey(this->key_);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
operator HKEY() const
|
||||||
|
{
|
||||||
|
return this->key_;
|
||||||
|
}
|
||||||
|
|
||||||
|
operator bool() const
|
||||||
|
{
|
||||||
|
return this->key_ != nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
HKEY* operator&()
|
||||||
|
{
|
||||||
|
return &this->key_;
|
||||||
|
}
|
||||||
|
|
||||||
|
registry_key* GetRef()
|
||||||
|
{
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
const registry_key* GetRef() const
|
||||||
|
{
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
HKEY key_{};
|
||||||
|
};
|
||||||
|
|
||||||
|
registry_key open_or_create_registry_key(const HKEY base, const std::string& input);
|
||||||
|
|
||||||
bool is_wine();
|
bool is_wine();
|
||||||
bool is_shutdown_in_progress();
|
bool is_shutdown_in_progress();
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user