[GPU] Async shader compilation for D3D12 and Vulkan
Adds async_shader_compilation cvar (default true) that forces new pipelines to be created async from the main thread, skips draws entirely on D3D12 and on vulkan replaces pixel shader with placeholder until the real one is ready. Causes some visual artifacts on first load but greatly reduces load times and stutter.
This commit is contained in:
@@ -520,6 +520,65 @@ std::unique_ptr<ImmediateDrawer> D3D12Provider::CreateImmediateDrawer() {
|
||||
return D3D12ImmediateDrawer::Create(*this);
|
||||
}
|
||||
|
||||
void D3D12Provider::LogD3D12DebugMessages() const {
|
||||
if (!device_) {
|
||||
return;
|
||||
}
|
||||
|
||||
ID3D12InfoQueue* info_queue = nullptr;
|
||||
if (FAILED(device_->QueryInterface(IID_PPV_ARGS(&info_queue)))) {
|
||||
return;
|
||||
}
|
||||
|
||||
UINT64 message_count = info_queue->GetNumStoredMessages();
|
||||
for (UINT64 i = 0; i < message_count; ++i) {
|
||||
SIZE_T message_size = 0;
|
||||
if (FAILED(info_queue->GetMessage(i, nullptr, &message_size))) {
|
||||
continue;
|
||||
}
|
||||
|
||||
D3D12_MESSAGE* message =
|
||||
reinterpret_cast<D3D12_MESSAGE*>(alloca(message_size));
|
||||
if (FAILED(info_queue->GetMessage(i, message, &message_size))) {
|
||||
continue;
|
||||
}
|
||||
|
||||
const char* severity_str = "INFO";
|
||||
switch (message->Severity) {
|
||||
case D3D12_MESSAGE_SEVERITY_CORRUPTION:
|
||||
severity_str = "CORRUPTION";
|
||||
break;
|
||||
case D3D12_MESSAGE_SEVERITY_ERROR:
|
||||
severity_str = "ERROR";
|
||||
break;
|
||||
case D3D12_MESSAGE_SEVERITY_WARNING:
|
||||
severity_str = "WARNING";
|
||||
break;
|
||||
case D3D12_MESSAGE_SEVERITY_INFO:
|
||||
severity_str = "INFO";
|
||||
break;
|
||||
case D3D12_MESSAGE_SEVERITY_MESSAGE:
|
||||
severity_str = "MESSAGE";
|
||||
break;
|
||||
}
|
||||
|
||||
if (message->Severity == D3D12_MESSAGE_SEVERITY_ERROR ||
|
||||
message->Severity == D3D12_MESSAGE_SEVERITY_CORRUPTION) {
|
||||
XELOGE("D3D12 {}: [ID {}] {}", severity_str,
|
||||
static_cast<int>(message->ID), message->pDescription);
|
||||
} else if (message->Severity == D3D12_MESSAGE_SEVERITY_WARNING) {
|
||||
XELOGW("D3D12 {}: [ID {}] {}", severity_str,
|
||||
static_cast<int>(message->ID), message->pDescription);
|
||||
} else {
|
||||
XELOGI("D3D12 {}: [ID {}] {}", severity_str,
|
||||
static_cast<int>(message->ID), message->pDescription);
|
||||
}
|
||||
}
|
||||
|
||||
info_queue->ClearStoredMessages();
|
||||
info_queue->Release();
|
||||
}
|
||||
|
||||
} // namespace d3d12
|
||||
} // namespace ui
|
||||
} // namespace xe
|
||||
|
||||
@@ -158,6 +158,10 @@ class D3D12Provider : public GraphicsProvider {
|
||||
return pfn_dxcompiler_dxc_create_instance_(rclsid, riid, ppv);
|
||||
}
|
||||
|
||||
// Logs all pending D3D12 debug messages to xenia's log.
|
||||
// Call this after operations that fail to get detailed error info.
|
||||
void LogD3D12DebugMessages() const;
|
||||
|
||||
private:
|
||||
D3D12Provider() = default;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user