1
0
mirror of https://github.com/doitsujin/dxvk.git synced 2024-12-11 10:24:10 +01:00

[dxgi] Use global user config for DXGI options

This commit is contained in:
Philip Rebohle 2018-08-07 14:47:06 +02:00
parent c0398caa2b
commit 524ff9e233
No known key found for this signature in database
GPG Key ID: C8CC613427A31C99
10 changed files with 46 additions and 42 deletions

View File

@ -64,8 +64,7 @@ namespace dxvk {
|| InterfaceName == __uuidof(ID3D10Device1)) { || InterfaceName == __uuidof(ID3D10Device1)) {
Logger::warn("DXGI: CheckInterfaceSupport: No D3D10 support"); Logger::warn("DXGI: CheckInterfaceSupport: No D3D10 support");
DxgiOptions dxgiOptions = getDxgiAppOptions(env::getExeName()); return m_factory->GetOptions()->fakeDx10Support
return dxgiOptions.test(DxgiOption::FakeDx10Support)
? S_OK : DXGI_ERROR_UNSUPPORTED; ? S_OK : DXGI_ERROR_UNSUPPORTED;
} }
@ -215,7 +214,8 @@ namespace dxvk {
InitReturnPtr(ppDevice); InitReturnPtr(ppDevice);
try { try {
*ppDevice = new dxvk::DxgiDevice(pContainer, this, pFeatures); *ppDevice = new dxvk::DxgiDevice(pContainer,
this, m_factory->GetOptions(), pFeatures);
return S_OK; return S_OK;
} catch (const dxvk::DxvkError& e) { } catch (const dxvk::DxvkError& e) {
dxvk::Logger::err(e.message()); dxvk::Logger::err(e.message());

View File

@ -8,9 +8,11 @@ namespace dxvk {
DxgiDevice::DxgiDevice( DxgiDevice::DxgiDevice(
IDXGIObject* pContainer, IDXGIObject* pContainer,
IDXGIVkAdapter* pAdapter, IDXGIVkAdapter* pAdapter,
const DxgiOptions* pOptions,
const DxvkDeviceFeatures* pFeatures) const DxvkDeviceFeatures* pFeatures)
: m_container (pContainer), : m_container (pContainer),
m_adapter (pAdapter) { m_adapter (pAdapter),
m_frameLatencyCap (pOptions->maxFrameLatency) {
m_device = m_adapter->GetDXVKAdapter()->createDevice(*pFeatures); m_device = m_adapter->GetDXVKAdapter()->createDevice(*pFeatures);
for (uint32_t i = 0; i < m_frameEvents.size(); i++) for (uint32_t i = 0; i < m_frameEvents.size(); i++)
@ -161,7 +163,13 @@ namespace dxvk {
Rc<DxvkEvent> STDMETHODCALLTYPE DxgiDevice::GetFrameSyncEvent() { Rc<DxvkEvent> STDMETHODCALLTYPE DxgiDevice::GetFrameSyncEvent() {
uint32_t frameId = m_frameId++ % m_frameLatency; uint32_t frameLatency = m_frameLatency;
if (m_frameLatencyCap != 0
&& m_frameLatencyCap <= frameLatency)
frameLatency = m_frameLatencyCap;
uint32_t frameId = m_frameId++ % frameLatency;
return m_frameEvents[frameId]; return m_frameEvents[frameId];
} }

View File

@ -4,6 +4,7 @@
#include "dxgi_adapter.h" #include "dxgi_adapter.h"
#include "dxgi_interfaces.h" #include "dxgi_interfaces.h"
#include "dxgi_options.h"
namespace dxvk { namespace dxvk {
@ -16,6 +17,7 @@ namespace dxvk {
DxgiDevice( DxgiDevice(
IDXGIObject* pContainer, IDXGIObject* pContainer,
IDXGIVkAdapter* pAdapter, IDXGIVkAdapter* pAdapter,
const DxgiOptions* pOptions,
const DxvkDeviceFeatures* pFeatures); const DxvkDeviceFeatures* pFeatures);
~DxgiDevice(); ~DxgiDevice();
@ -96,8 +98,9 @@ namespace dxvk {
Com<IDXGIVkAdapter> m_adapter; Com<IDXGIVkAdapter> m_adapter;
Rc<DxvkDevice> m_device; Rc<DxvkDevice> m_device;
uint32_t m_frameLatency = DefaultFrameLatency; uint32_t m_frameLatencyCap = 0;
uint32_t m_frameId = 0; uint32_t m_frameLatency = DefaultFrameLatency;
uint32_t m_frameId = 0;
std::array<Rc<DxvkEvent>, 16> m_frameEvents; std::array<Rc<DxvkEvent>, 16> m_frameEvents;

View File

@ -4,7 +4,8 @@
namespace dxvk { namespace dxvk {
DxgiFactory::DxgiFactory() DxgiFactory::DxgiFactory()
: m_instance(new DxvkInstance()) { : m_instance(new DxvkInstance()),
m_options (m_instance->config()) {
for (uint32_t i = 0; m_instance->enumAdapters(i) != nullptr; i++) for (uint32_t i = 0; m_instance->enumAdapters(i) != nullptr; i++)
m_instance->enumAdapters(i)->logAdapterInfo(); m_instance->enumAdapters(i)->logAdapterInfo();
} }

View File

@ -5,6 +5,7 @@
#include <dxvk_instance.h> #include <dxvk_instance.h>
#include "dxgi_adapter.h" #include "dxgi_adapter.h"
#include "dxgi_options.h"
namespace dxvk { namespace dxvk {
@ -100,9 +101,14 @@ namespace dxvk {
void STDMETHODCALLTYPE UnregisterOcclusionStatus( void STDMETHODCALLTYPE UnregisterOcclusionStatus(
DWORD dwCookie) final; DWORD dwCookie) final;
const DxgiOptions* GetOptions() const {
return &m_options;
}
private: private:
Rc<DxvkInstance> m_instance; Rc<DxvkInstance> m_instance;
DxgiOptions m_options;
HWND m_associatedWindow = nullptr; HWND m_associatedWindow = nullptr;

View File

@ -4,23 +4,10 @@
namespace dxvk { namespace dxvk {
const static std::unordered_map<std::string, DxgiOptions> g_dxgiAppOptions = {{ DxgiOptions::DxgiOptions(const Config& config) {
{ "Frostpunk.exe", DxgiOptions(DxgiOption::DeferSurfaceCreation) }, this->deferSurfaceCreation = config.getOption<bool> ("dxgi.deferSurfaceCreation", false);
{ "Wow.exe", DxgiOptions(DxgiOption::FakeDx10Support) }, this->fakeDx10Support = config.getOption<bool> ("dxgi.fakeDx10Support", false);
}}; this->maxFrameLatency = config.getOption<int32_t> ("dxgi.maxFrameLatency", 0);
DxgiOptions getDxgiAppOptions(const std::string& appName) {
DxgiOptions options;
auto appOptions = g_dxgiAppOptions.find(appName);
if (appOptions != g_dxgiAppOptions.end())
options = appOptions->second;
if (env::getEnvVar(L"DXVK_FAKE_DX10_SUPPORT") == "1")
options.set(DxgiOption::FakeDx10Support);
return options;
} }
} }

View File

@ -1,5 +1,7 @@
#pragma once #pragma once
#include "../util/config/config.h"
#include "dxgi_include.h" #include "dxgi_include.h"
namespace dxvk { namespace dxvk {
@ -10,26 +12,22 @@ namespace dxvk {
* Per-app options that control the * Per-app options that control the
* behaviour of some DXGI classes. * behaviour of some DXGI classes.
*/ */
enum class DxgiOption : uint64_t { struct DxgiOptions {
DxgiOptions(const Config& config);
/// Defer surface creation until first present call. This /// Defer surface creation until first present call. This
/// fixes issues with games that create multiple swap chains /// fixes issues with games that create multiple swap chains
/// for a single window that may interfere with each other. /// for a single window that may interfere with each other.
DeferSurfaceCreation, bool deferSurfaceCreation;
/// Report to the app that Dx10 interfaces are supported, /// Report to the app that Dx10 interfaces are supported,
/// even if they are not actually supported. Some apps /// even if they are not actually supported. Some apps
/// refuse to start without it, some don't work with it. /// refuse to start without it, some don't work with it.
FakeDx10Support, bool fakeDx10Support;
/// Override maximum frame latency if the app specifies
/// a higher value. May help with frame timing issues.
int32_t maxFrameLatency;
}; };
using DxgiOptions = Flags<DxgiOption>;
/**
* \brief Gets app-specific DXGI options
*
* \param [in] appName Application name
* \returns DXGI options for this application
*/
DxgiOptions getDxgiAppOptions(const std::string& appName);
} }

View File

@ -8,6 +8,7 @@
namespace dxvk { namespace dxvk {
DxgiVkPresenter::DxgiVkPresenter( DxgiVkPresenter::DxgiVkPresenter(
const DxgiOptions* pOptions,
const Rc<DxvkDevice>& device, const Rc<DxvkDevice>& device,
HWND window) HWND window)
: m_window (window), : m_window (window),
@ -16,9 +17,7 @@ namespace dxvk {
// Some games don't work with deferred surface creation, // Some games don't work with deferred surface creation,
// so we should default to initializing it immediately. // so we should default to initializing it immediately.
DxgiOptions dxgiOptions = getDxgiAppOptions(env::getExeName()); if (!pOptions->deferSurfaceCreation)
if (!dxgiOptions.test(DxgiOption::DeferSurfaceCreation))
m_surface = CreateSurface(); m_surface = CreateSurface();
// Reset options for the swap chain itself. We will // Reset options for the swap chain itself. We will

View File

@ -69,6 +69,7 @@ namespace dxvk {
public: public:
DxgiVkPresenter( DxgiVkPresenter(
const DxgiOptions* pOptions,
const Rc<DxvkDevice>& device, const Rc<DxvkDevice>& device,
HWND window); HWND window);

View File

@ -469,6 +469,7 @@ namespace dxvk {
HRESULT DxgiSwapChain::CreatePresenter() { HRESULT DxgiSwapChain::CreatePresenter() {
try { try {
m_presenter = new DxgiVkPresenter( m_presenter = new DxgiVkPresenter(
m_factory->GetOptions(),
m_device->GetDXVKDevice(), m_device->GetDXVKDevice(),
m_window); m_window);
return S_OK; return S_OK;