mirror of
https://github.com/doitsujin/dxvk.git
synced 2024-12-13 07:08:50 +01:00
[dxvk] Use precompiled compute pipelines whenever possible
This commit is contained in:
parent
6265b5b809
commit
cb56e16a4b
@ -14,11 +14,14 @@ namespace dxvk {
|
||||
DxvkDevice* device,
|
||||
DxvkPipelineManager* pipeMgr,
|
||||
DxvkComputePipelineShaders shaders,
|
||||
DxvkBindingLayoutObjects* layout)
|
||||
DxvkBindingLayoutObjects* layout,
|
||||
DxvkShaderPipelineLibrary* library)
|
||||
: m_device (device),
|
||||
m_cache (&pipeMgr->m_cache),
|
||||
m_stateCache (&pipeMgr->m_stateCache),
|
||||
m_stats (&pipeMgr->m_stats),
|
||||
m_library (library),
|
||||
m_libraryHandle (VK_NULL_HANDLE),
|
||||
m_shaders (std::move(shaders)),
|
||||
m_bindings (layout) {
|
||||
|
||||
@ -33,6 +36,18 @@ namespace dxvk {
|
||||
|
||||
VkPipeline DxvkComputePipeline::getPipelineHandle(
|
||||
const DxvkComputePipelineStateInfo& state) {
|
||||
if (m_library) {
|
||||
// For compute pipelines that can be precompiled, we can use that
|
||||
// pipeline variant unconditionally since there is no state for us
|
||||
// to worry about other than specialization constants
|
||||
if (unlikely(!m_libraryHandle)) {
|
||||
m_libraryHandle = m_library->getPipelineHandle(m_cache->handle(),
|
||||
DxvkShaderPipelineLibraryCompileArgs());
|
||||
m_stats->numComputePipelines += 1;
|
||||
}
|
||||
|
||||
return m_libraryHandle;
|
||||
} else {
|
||||
DxvkComputePipelineInstance* instance = this->findInstance(state);
|
||||
|
||||
if (unlikely(!instance)) {
|
||||
@ -47,15 +62,18 @@ namespace dxvk {
|
||||
|
||||
return instance->pipeline();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void DxvkComputePipeline::compilePipeline(
|
||||
const DxvkComputePipelineStateInfo& state) {
|
||||
if (!m_library) {
|
||||
std::lock_guard<dxvk::mutex> lock(m_mutex);
|
||||
|
||||
if (!this->findInstance(state))
|
||||
this->createInstance(state);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
DxvkComputePipelineInstance* DxvkComputePipeline::createInstance(
|
||||
|
@ -96,7 +96,8 @@ namespace dxvk {
|
||||
DxvkDevice* device,
|
||||
DxvkPipelineManager* pipeMgr,
|
||||
DxvkComputePipelineShaders shaders,
|
||||
DxvkBindingLayoutObjects* layout);
|
||||
DxvkBindingLayoutObjects* layout,
|
||||
DxvkShaderPipelineLibrary* library);
|
||||
|
||||
~DxvkComputePipeline();
|
||||
|
||||
@ -146,6 +147,9 @@ namespace dxvk {
|
||||
DxvkStateCache* m_stateCache;
|
||||
DxvkPipelineStats* m_stats;
|
||||
|
||||
DxvkShaderPipelineLibrary* m_library;
|
||||
VkPipeline m_libraryHandle;
|
||||
|
||||
DxvkComputePipelineShaders m_shaders;
|
||||
DxvkBindingLayoutObjects* m_bindings;
|
||||
|
||||
|
@ -189,11 +189,12 @@ namespace dxvk {
|
||||
return &pair->second;
|
||||
|
||||
auto layout = createPipelineLayout(shaders.cs->getBindings());
|
||||
auto library = findPipelineLibrary(shaders.cs);
|
||||
|
||||
auto iter = m_computePipelines.emplace(
|
||||
std::piecewise_construct,
|
||||
std::tuple(shaders),
|
||||
std::tuple(m_device, this, shaders, layout));
|
||||
std::tuple(m_device, this, shaders, layout, library));
|
||||
return &iter.first->second;
|
||||
}
|
||||
|
||||
@ -342,4 +343,17 @@ namespace dxvk {
|
||||
return &iter.first->second;
|
||||
}
|
||||
|
||||
|
||||
DxvkShaderPipelineLibrary* DxvkPipelineManager::findPipelineLibrary(
|
||||
const Rc<DxvkShader>& shader) {
|
||||
DxvkShaderPipelineLibraryKey key;
|
||||
key.shader = shader;
|
||||
|
||||
auto pair = m_shaderLibraries.find(key);
|
||||
if (pair == m_shaderLibraries.end())
|
||||
return nullptr;
|
||||
|
||||
return &pair->second;
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -271,6 +271,9 @@ namespace dxvk {
|
||||
DxvkShaderPipelineLibrary* createPipelineLibrary(
|
||||
const Rc<DxvkShader>& shader);
|
||||
|
||||
DxvkShaderPipelineLibrary* findPipelineLibrary(
|
||||
const Rc<DxvkShader>& shader);
|
||||
|
||||
};
|
||||
|
||||
}
|
Loading…
Reference in New Issue
Block a user