Split Pipeline in Render and Compute, D3D12 part
This commit is contained in:
parent
66ff447216
commit
136cae5ee2
|
@ -215,6 +215,8 @@ if (NXT_ENABLE_D3D12)
|
||||||
${D3D12_DIR}/CommandAllocatorManager.h
|
${D3D12_DIR}/CommandAllocatorManager.h
|
||||||
${D3D12_DIR}/CommandBufferD3D12.cpp
|
${D3D12_DIR}/CommandBufferD3D12.cpp
|
||||||
${D3D12_DIR}/CommandBufferD3D12.h
|
${D3D12_DIR}/CommandBufferD3D12.h
|
||||||
|
${D3D12_DIR}/ComputePipelineD3D12.cpp
|
||||||
|
${D3D12_DIR}/ComputePipelineD3D12.h
|
||||||
${D3D12_DIR}/DescriptorHeapAllocator.cpp
|
${D3D12_DIR}/DescriptorHeapAllocator.cpp
|
||||||
${D3D12_DIR}/DescriptorHeapAllocator.h
|
${D3D12_DIR}/DescriptorHeapAllocator.h
|
||||||
${D3D12_DIR}/D3D12Backend.cpp
|
${D3D12_DIR}/D3D12Backend.cpp
|
||||||
|
@ -223,12 +225,12 @@ if (NXT_ENABLE_D3D12)
|
||||||
${D3D12_DIR}/FramebufferD3D12.h
|
${D3D12_DIR}/FramebufferD3D12.h
|
||||||
${D3D12_DIR}/InputStateD3D12.cpp
|
${D3D12_DIR}/InputStateD3D12.cpp
|
||||||
${D3D12_DIR}/InputStateD3D12.h
|
${D3D12_DIR}/InputStateD3D12.h
|
||||||
${D3D12_DIR}/PipelineD3D12.cpp
|
|
||||||
${D3D12_DIR}/PipelineD3D12.h
|
|
||||||
${D3D12_DIR}/PipelineLayoutD3D12.cpp
|
${D3D12_DIR}/PipelineLayoutD3D12.cpp
|
||||||
${D3D12_DIR}/PipelineLayoutD3D12.h
|
${D3D12_DIR}/PipelineLayoutD3D12.h
|
||||||
${D3D12_DIR}/QueueD3D12.cpp
|
${D3D12_DIR}/QueueD3D12.cpp
|
||||||
${D3D12_DIR}/QueueD3D12.h
|
${D3D12_DIR}/QueueD3D12.h
|
||||||
|
${D3D12_DIR}/RenderPipelineD3D12.cpp
|
||||||
|
${D3D12_DIR}/RenderPipelineD3D12.h
|
||||||
${D3D12_DIR}/ResourceAllocator.cpp
|
${D3D12_DIR}/ResourceAllocator.cpp
|
||||||
${D3D12_DIR}/ResourceAllocator.h
|
${D3D12_DIR}/ResourceAllocator.h
|
||||||
${D3D12_DIR}/ResourceUploader.cpp
|
${D3D12_DIR}/ResourceUploader.cpp
|
||||||
|
|
|
@ -19,11 +19,12 @@
|
||||||
#include "backend/d3d12/BindGroupD3D12.h"
|
#include "backend/d3d12/BindGroupD3D12.h"
|
||||||
#include "backend/d3d12/BindGroupLayoutD3D12.h"
|
#include "backend/d3d12/BindGroupLayoutD3D12.h"
|
||||||
#include "backend/d3d12/BufferD3D12.h"
|
#include "backend/d3d12/BufferD3D12.h"
|
||||||
|
#include "backend/d3d12/ComputePipelineD3D12.h"
|
||||||
#include "backend/d3d12/DescriptorHeapAllocator.h"
|
#include "backend/d3d12/DescriptorHeapAllocator.h"
|
||||||
#include "backend/d3d12/FramebufferD3D12.h"
|
#include "backend/d3d12/FramebufferD3D12.h"
|
||||||
#include "backend/d3d12/InputStateD3D12.h"
|
#include "backend/d3d12/InputStateD3D12.h"
|
||||||
#include "backend/d3d12/PipelineD3D12.h"
|
|
||||||
#include "backend/d3d12/PipelineLayoutD3D12.h"
|
#include "backend/d3d12/PipelineLayoutD3D12.h"
|
||||||
|
#include "backend/d3d12/RenderPipelineD3D12.h"
|
||||||
#include "backend/d3d12/ResourceAllocator.h"
|
#include "backend/d3d12/ResourceAllocator.h"
|
||||||
#include "backend/d3d12/SamplerD3D12.h"
|
#include "backend/d3d12/SamplerD3D12.h"
|
||||||
#include "backend/d3d12/TextureD3D12.h"
|
#include "backend/d3d12/TextureD3D12.h"
|
||||||
|
@ -52,12 +53,17 @@ namespace d3d12 {
|
||||||
DescriptorHeapHandle cbvSrvUavGPUDescriptorHeap = {};
|
DescriptorHeapHandle cbvSrvUavGPUDescriptorHeap = {};
|
||||||
DescriptorHeapHandle samplerGPUDescriptorHeap = {};
|
DescriptorHeapHandle samplerGPUDescriptorHeap = {};
|
||||||
std::array<BindGroup*, kMaxBindGroups> bindGroups = {};
|
std::array<BindGroup*, kMaxBindGroups> bindGroups = {};
|
||||||
|
bool inCompute = false;
|
||||||
|
|
||||||
Device* device;
|
Device* device;
|
||||||
|
|
||||||
BindGroupStateTracker(Device* device) : device(device) {
|
BindGroupStateTracker(Device* device) : device(device) {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void SetInComputePass(bool inCompute) {
|
||||||
|
this->inCompute = inCompute;
|
||||||
|
}
|
||||||
|
|
||||||
void TrackSetBindGroup(BindGroup* group, uint32_t index) {
|
void TrackSetBindGroup(BindGroup* group, uint32_t index) {
|
||||||
if (bindGroups[index] != group) {
|
if (bindGroups[index] != group) {
|
||||||
bindGroups[index] = group;
|
bindGroups[index] = group;
|
||||||
|
@ -70,25 +76,38 @@ namespace d3d12 {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void TrackSetBindInheritedGroup(uint32_t index) {
|
void TrackInheritedGroups(PipelineLayout* oldLayout, PipelineLayout* newLayout) {
|
||||||
BindGroup* group = bindGroups[index];
|
if (oldLayout == nullptr) {
|
||||||
if (group != nullptr) {
|
return;
|
||||||
TrackSetBindGroup(group, index);
|
}
|
||||||
|
|
||||||
|
auto mask = newLayout->GetBindGroupsLayoutMask();
|
||||||
|
for (uint32_t i = 0; i < kMaxBindGroups; ++i) {
|
||||||
|
// matching bind groups are inherited until they differ
|
||||||
|
if (mask[i] && oldLayout->GetBindGroupLayout(i) == newLayout->GetBindGroupLayout(i)) {
|
||||||
|
BindGroup* group = bindGroups[i];
|
||||||
|
if (group != nullptr) {
|
||||||
|
TrackSetBindGroup(group, i);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void SetBindGroup(ComPtr<ID3D12GraphicsCommandList> commandList, Pipeline* pipeline, BindGroup* group, uint32_t index, bool force = false) {
|
void SetBindGroup(ComPtr<ID3D12GraphicsCommandList> commandList, PipelineLayout* pipelineLayout, BindGroup* group,
|
||||||
|
uint32_t index, bool force = false) {
|
||||||
if (bindGroups[index] != group || force) {
|
if (bindGroups[index] != group || force) {
|
||||||
bindGroups[index] = group;
|
bindGroups[index] = group;
|
||||||
|
|
||||||
PipelineLayout* pipelineLayout = ToBackend(pipeline->GetLayout());
|
|
||||||
uint32_t cbvUavSrvCount = ToBackend(group->GetLayout())->GetCbvUavSrvDescriptorCount();
|
uint32_t cbvUavSrvCount = ToBackend(group->GetLayout())->GetCbvUavSrvDescriptorCount();
|
||||||
uint32_t samplerCount = ToBackend(group->GetLayout())->GetSamplerDescriptorCount();
|
uint32_t samplerCount = ToBackend(group->GetLayout())->GetSamplerDescriptorCount();
|
||||||
|
|
||||||
if (cbvUavSrvCount > 0) {
|
if (cbvUavSrvCount > 0) {
|
||||||
uint32_t parameterIndex = pipelineLayout->GetCbvUavSrvRootParameterIndex(index);
|
uint32_t parameterIndex = pipelineLayout->GetCbvUavSrvRootParameterIndex(index);
|
||||||
|
|
||||||
if (pipeline->IsCompute()) {
|
if (inCompute) {
|
||||||
commandList->SetComputeRootDescriptorTable(parameterIndex, cbvSrvUavGPUDescriptorHeap.GetGPUHandle(group->GetCbvUavSrvHeapOffset()));
|
commandList->SetComputeRootDescriptorTable(parameterIndex, cbvSrvUavGPUDescriptorHeap.GetGPUHandle(group->GetCbvUavSrvHeapOffset()));
|
||||||
} else {
|
} else {
|
||||||
commandList->SetGraphicsRootDescriptorTable(parameterIndex, cbvSrvUavGPUDescriptorHeap.GetGPUHandle(group->GetCbvUavSrvHeapOffset()));
|
commandList->SetGraphicsRootDescriptorTable(parameterIndex, cbvSrvUavGPUDescriptorHeap.GetGPUHandle(group->GetCbvUavSrvHeapOffset()));
|
||||||
|
@ -98,7 +117,7 @@ namespace d3d12 {
|
||||||
if (samplerCount > 0) {
|
if (samplerCount > 0) {
|
||||||
uint32_t parameterIndex = pipelineLayout->GetSamplerRootParameterIndex(index);
|
uint32_t parameterIndex = pipelineLayout->GetSamplerRootParameterIndex(index);
|
||||||
|
|
||||||
if (pipeline->IsCompute()) {
|
if (inCompute) {
|
||||||
commandList->SetComputeRootDescriptorTable(parameterIndex, samplerGPUDescriptorHeap.GetGPUHandle(group->GetSamplerHeapOffset()));
|
commandList->SetComputeRootDescriptorTable(parameterIndex, samplerGPUDescriptorHeap.GetGPUHandle(group->GetSamplerHeapOffset()));
|
||||||
} else {
|
} else {
|
||||||
commandList->SetGraphicsRootDescriptorTable(parameterIndex, samplerGPUDescriptorHeap.GetGPUHandle(group->GetSamplerHeapOffset()));
|
commandList->SetGraphicsRootDescriptorTable(parameterIndex, samplerGPUDescriptorHeap.GetGPUHandle(group->GetSamplerHeapOffset()));
|
||||||
|
@ -107,10 +126,22 @@ namespace d3d12 {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void SetInheritedBindGroup(ComPtr<ID3D12GraphicsCommandList> commandList, Pipeline* pipeline, uint32_t index) {
|
void SetInheritedBindGroups(ComPtr<ID3D12GraphicsCommandList> commandList, PipelineLayout* oldLayout, PipelineLayout* newLayout) {
|
||||||
BindGroup* group = bindGroups[index];
|
if (oldLayout == nullptr) {
|
||||||
if (group != nullptr) {
|
return;
|
||||||
SetBindGroup(commandList, pipeline, group, index, true);
|
}
|
||||||
|
auto mask = newLayout->GetBindGroupsLayoutMask();
|
||||||
|
for (uint32_t i = 0; i < kMaxBindGroups; ++i) {
|
||||||
|
// matching bind groups are inherited until they differ
|
||||||
|
if (mask[i] && oldLayout->GetBindGroupLayout(i) == oldLayout->GetBindGroupLayout(i)) {
|
||||||
|
BindGroup* group = bindGroups[i];
|
||||||
|
if (group != nullptr) {
|
||||||
|
SetBindGroup(commandList, newLayout, group, i, true);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -131,30 +162,24 @@ namespace d3d12 {
|
||||||
|
|
||||||
{
|
{
|
||||||
Command type;
|
Command type;
|
||||||
Pipeline* lastPipeline = nullptr;
|
|
||||||
PipelineLayout* lastLayout = nullptr;
|
PipelineLayout* lastLayout = nullptr;
|
||||||
|
|
||||||
while (commands->NextCommandId(&type)) {
|
while (commands->NextCommandId(&type)) {
|
||||||
switch (type) {
|
switch (type) {
|
||||||
case Command::SetPipeline:
|
case Command::SetComputePipeline:
|
||||||
{
|
{
|
||||||
SetPipelineCmd* cmd = commands->NextCommand<SetPipelineCmd>();
|
SetComputePipelineCmd* cmd = commands->NextCommand<SetComputePipelineCmd>();
|
||||||
Pipeline* pipeline = ToBackend(cmd->pipeline).Get();
|
PipelineLayout* layout = ToBackend(cmd->pipeline->GetLayout());
|
||||||
PipelineLayout* layout = ToBackend(pipeline->GetLayout());
|
bindingTracker->TrackInheritedGroups(lastLayout, layout);
|
||||||
|
lastLayout = layout;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
if (lastLayout) {
|
case Command::SetRenderPipeline:
|
||||||
auto mask = layout->GetBindGroupsLayoutMask();
|
{
|
||||||
for (uint32_t i = 0; i < kMaxBindGroups; ++i) {
|
SetRenderPipelineCmd* cmd = commands->NextCommand<SetRenderPipelineCmd>();
|
||||||
// matching bind groups are inherited until they differ
|
PipelineLayout* layout = ToBackend(cmd->pipeline->GetLayout());
|
||||||
if (mask[i] && lastLayout->GetBindGroupLayout(i) == layout->GetBindGroupLayout(i)) {
|
bindingTracker->TrackInheritedGroups(lastLayout, layout);
|
||||||
bindingTracker->TrackSetBindInheritedGroup(i);
|
|
||||||
} else {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
lastPipeline = pipeline;
|
|
||||||
lastLayout = layout;
|
lastLayout = layout;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
@ -243,7 +268,7 @@ namespace d3d12 {
|
||||||
}
|
}
|
||||||
|
|
||||||
Command type;
|
Command type;
|
||||||
Pipeline* lastPipeline = nullptr;
|
RenderPipeline* lastRenderPipeline = nullptr;
|
||||||
PipelineLayout* lastLayout = nullptr;
|
PipelineLayout* lastLayout = nullptr;
|
||||||
|
|
||||||
RenderPass* currentRenderPass = nullptr;
|
RenderPass* currentRenderPass = nullptr;
|
||||||
|
@ -255,6 +280,7 @@ namespace d3d12 {
|
||||||
case Command::BeginComputePass:
|
case Command::BeginComputePass:
|
||||||
{
|
{
|
||||||
commands.NextCommand<BeginComputePassCmd>();
|
commands.NextCommand<BeginComputePassCmd>();
|
||||||
|
bindingTracker.SetInComputePass(true);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
@ -351,8 +377,6 @@ namespace d3d12 {
|
||||||
case Command::Dispatch:
|
case Command::Dispatch:
|
||||||
{
|
{
|
||||||
DispatchCmd* dispatch = commands.NextCommand<DispatchCmd>();
|
DispatchCmd* dispatch = commands.NextCommand<DispatchCmd>();
|
||||||
|
|
||||||
ASSERT(lastPipeline->IsCompute());
|
|
||||||
commandList->Dispatch(dispatch->x, dispatch->y, dispatch->z);
|
commandList->Dispatch(dispatch->x, dispatch->y, dispatch->z);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
@ -389,6 +413,7 @@ namespace d3d12 {
|
||||||
case Command::EndComputePass:
|
case Command::EndComputePass:
|
||||||
{
|
{
|
||||||
commands.NextCommand<EndComputePassCmd>();
|
commands.NextCommand<EndComputePassCmd>();
|
||||||
|
bindingTracker.SetInComputePass(false);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
@ -405,35 +430,30 @@ namespace d3d12 {
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case Command::SetPipeline:
|
case Command::SetComputePipeline:
|
||||||
{
|
{
|
||||||
SetPipelineCmd* cmd = commands.NextCommand<SetPipelineCmd>();
|
SetComputePipelineCmd* cmd = commands.NextCommand<SetComputePipelineCmd>();
|
||||||
|
ComputePipeline* pipeline = ToBackend(cmd->pipeline).Get();
|
||||||
Pipeline* pipeline = ToBackend(cmd->pipeline).Get();
|
|
||||||
PipelineLayout* layout = ToBackend(pipeline->GetLayout());
|
PipelineLayout* layout = ToBackend(pipeline->GetLayout());
|
||||||
|
|
||||||
// TODO
|
// TODO(enga@google.com): Implement compute pipelines
|
||||||
if (pipeline->IsCompute()) {
|
bindingTracker.SetInheritedBindGroups(commandList, lastLayout, layout);
|
||||||
}
|
lastLayout = layout;
|
||||||
else {
|
}
|
||||||
commandList->SetGraphicsRootSignature(layout->GetRootSignature().Get());
|
break;
|
||||||
commandList->SetPipelineState(pipeline->GetRenderPipelineState().Get());
|
|
||||||
}
|
|
||||||
|
|
||||||
if (lastLayout) {
|
case Command::SetRenderPipeline:
|
||||||
auto mask = layout->GetBindGroupsLayoutMask();
|
{
|
||||||
for (uint32_t i = 0; i < kMaxBindGroups; ++i) {
|
SetRenderPipelineCmd* cmd = commands.NextCommand<SetRenderPipelineCmd>();
|
||||||
// matching bind groups are inherited until they differ
|
RenderPipeline* pipeline = ToBackend(cmd->pipeline).Get();
|
||||||
if (mask[i] && lastLayout->GetBindGroupLayout(i) == layout->GetBindGroupLayout(i)) {
|
PipelineLayout* layout = ToBackend(pipeline->GetLayout());
|
||||||
bindingTracker.SetInheritedBindGroup(commandList, pipeline, i);
|
|
||||||
} else {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
commandList->SetGraphicsRootSignature(layout->GetRootSignature().Get());
|
||||||
|
commandList->SetPipelineState(pipeline->GetPipelineState().Get());
|
||||||
|
|
||||||
lastPipeline = pipeline;
|
bindingTracker.SetInheritedBindGroups(commandList, lastLayout, layout);
|
||||||
|
|
||||||
|
lastRenderPipeline = pipeline;
|
||||||
lastLayout = layout;
|
lastLayout = layout;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
@ -454,7 +474,7 @@ namespace d3d12 {
|
||||||
{
|
{
|
||||||
SetBindGroupCmd* cmd = commands.NextCommand<SetBindGroupCmd>();
|
SetBindGroupCmd* cmd = commands.NextCommand<SetBindGroupCmd>();
|
||||||
BindGroup* group = ToBackend(cmd->group.Get());
|
BindGroup* group = ToBackend(cmd->group.Get());
|
||||||
bindingTracker.SetBindGroup(commandList, lastPipeline, group, cmd->index);
|
bindingTracker.SetBindGroup(commandList, lastLayout, group, cmd->index);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
@ -478,7 +498,7 @@ namespace d3d12 {
|
||||||
auto buffers = commands.NextData<Ref<BufferBase>>(cmd->count);
|
auto buffers = commands.NextData<Ref<BufferBase>>(cmd->count);
|
||||||
auto offsets = commands.NextData<uint32_t>(cmd->count);
|
auto offsets = commands.NextData<uint32_t>(cmd->count);
|
||||||
|
|
||||||
auto inputState = ToBackend(lastPipeline->GetInputState());
|
auto inputState = ToBackend(lastRenderPipeline->GetInputState());
|
||||||
|
|
||||||
std::array<D3D12_VERTEX_BUFFER_VIEW, kMaxVertexInputs> d3d12BufferViews;
|
std::array<D3D12_VERTEX_BUFFER_VIEW, kMaxVertexInputs> d3d12BufferViews;
|
||||||
for (uint32_t i = 0; i < cmd->count; ++i) {
|
for (uint32_t i = 0; i < cmd->count; ++i) {
|
||||||
|
|
|
@ -0,0 +1,75 @@
|
||||||
|
// Copyright 2017 The NXT Authors
|
||||||
|
//
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, software
|
||||||
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
// See the License for the specific language governing permissions and
|
||||||
|
// limitations under the License.
|
||||||
|
|
||||||
|
#include "backend/d3d12/ComputePipelineD3D12.h"
|
||||||
|
|
||||||
|
#include "backend/d3d12/D3D12Backend.h"
|
||||||
|
#include "backend/d3d12/ShaderModuleD3D12.h"
|
||||||
|
#include "backend/d3d12/PipelineLayoutD3D12.h"
|
||||||
|
#include "common/Assert.h"
|
||||||
|
|
||||||
|
#include <d3dcompiler.h>
|
||||||
|
|
||||||
|
namespace backend {
|
||||||
|
namespace d3d12 {
|
||||||
|
|
||||||
|
ComputePipeline::ComputePipeline(ComputePipelineBuilder* builder)
|
||||||
|
: ComputePipelineBase(builder) {
|
||||||
|
uint32_t compileFlags = 0;
|
||||||
|
#if defined(_DEBUG)
|
||||||
|
// Enable better shader debugging with the graphics debugging tools.
|
||||||
|
compileFlags |= D3DCOMPILE_DEBUG | D3DCOMPILE_SKIP_OPTIMIZATION;
|
||||||
|
#endif
|
||||||
|
// SPRIV-cross does matrix multiplication expecting row major matrices
|
||||||
|
compileFlags |= D3DCOMPILE_PACK_MATRIX_ROW_MAJOR;
|
||||||
|
|
||||||
|
const auto& module = ToBackend(builder->GetStageInfo(nxt::ShaderStage::Compute).module);
|
||||||
|
const auto& entryPoint = builder->GetStageInfo(nxt::ShaderStage::Compute).entryPoint;
|
||||||
|
const auto& hlslSource = module->GetHLSLSource();
|
||||||
|
|
||||||
|
ComPtr<ID3DBlob> compiledShader;
|
||||||
|
ComPtr<ID3DBlob> errors;
|
||||||
|
|
||||||
|
if (FAILED(D3DCompile(
|
||||||
|
hlslSource.c_str(),
|
||||||
|
hlslSource.length(),
|
||||||
|
nullptr,
|
||||||
|
{ nullptr },
|
||||||
|
nullptr,
|
||||||
|
entryPoint.c_str(),
|
||||||
|
"cs_5_0",
|
||||||
|
compileFlags,
|
||||||
|
0,
|
||||||
|
&compiledShader,
|
||||||
|
&errors
|
||||||
|
))) {
|
||||||
|
printf("%s\n", reinterpret_cast<char*>(errors->GetBufferPointer()));
|
||||||
|
ASSERT(false);
|
||||||
|
}
|
||||||
|
|
||||||
|
D3D12_COMPUTE_PIPELINE_STATE_DESC descriptor = {};
|
||||||
|
descriptor.pRootSignature = ToBackend(GetLayout())->GetRootSignature().Get();
|
||||||
|
descriptor.CS.pShaderBytecode = compiledShader->GetBufferPointer();
|
||||||
|
descriptor.CS.BytecodeLength = compiledShader->GetBufferSize();
|
||||||
|
|
||||||
|
Device* device = ToBackend(builder->GetDevice());
|
||||||
|
device->GetD3D12Device()->CreateComputePipelineState(&descriptor, IID_PPV_ARGS(&pipelineState));
|
||||||
|
}
|
||||||
|
|
||||||
|
ComPtr<ID3D12PipelineState> ComputePipeline::GetPipelineState() {
|
||||||
|
return pipelineState;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,38 @@
|
||||||
|
// Copyright 2017 The NXT Authors
|
||||||
|
//
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, software
|
||||||
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
// See the License for the specific language governing permissions and
|
||||||
|
// limitations under the License.
|
||||||
|
|
||||||
|
#ifndef BACKEND_D3D12_COMPUTEPIPELINED3D12_H_
|
||||||
|
#define BACKEND_D3D12_COMPUTEPIPELINED3D12_H_
|
||||||
|
|
||||||
|
#include "backend/ComputePipeline.h"
|
||||||
|
|
||||||
|
#include "backend/d3d12/d3d12_platform.h"
|
||||||
|
|
||||||
|
namespace backend {
|
||||||
|
namespace d3d12 {
|
||||||
|
|
||||||
|
class ComputePipeline : public ComputePipelineBase {
|
||||||
|
public:
|
||||||
|
ComputePipeline(ComputePipelineBuilder* builder);
|
||||||
|
|
||||||
|
ComPtr<ID3D12PipelineState> GetPipelineState();
|
||||||
|
|
||||||
|
private:
|
||||||
|
ComPtr<ID3D12PipelineState> pipelineState;
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif // BACKEND_D3D12_COMPUTEPIPELINED3D12_H_
|
|
@ -19,12 +19,13 @@
|
||||||
#include "backend/d3d12/BufferD3D12.h"
|
#include "backend/d3d12/BufferD3D12.h"
|
||||||
#include "backend/d3d12/CommandAllocatorManager.h"
|
#include "backend/d3d12/CommandAllocatorManager.h"
|
||||||
#include "backend/d3d12/CommandBufferD3D12.h"
|
#include "backend/d3d12/CommandBufferD3D12.h"
|
||||||
|
#include "backend/d3d12/ComputePipelineD3D12.h"
|
||||||
#include "backend/d3d12/DescriptorHeapAllocator.h"
|
#include "backend/d3d12/DescriptorHeapAllocator.h"
|
||||||
#include "backend/d3d12/FramebufferD3D12.h"
|
#include "backend/d3d12/FramebufferD3D12.h"
|
||||||
#include "backend/d3d12/InputStateD3D12.h"
|
#include "backend/d3d12/InputStateD3D12.h"
|
||||||
#include "backend/d3d12/PipelineD3D12.h"
|
|
||||||
#include "backend/d3d12/PipelineLayoutD3D12.h"
|
#include "backend/d3d12/PipelineLayoutD3D12.h"
|
||||||
#include "backend/d3d12/QueueD3D12.h"
|
#include "backend/d3d12/QueueD3D12.h"
|
||||||
|
#include "backend/d3d12/RenderPipelineD3D12.h"
|
||||||
#include "backend/d3d12/ResourceAllocator.h"
|
#include "backend/d3d12/ResourceAllocator.h"
|
||||||
#include "backend/d3d12/ResourceUploader.h"
|
#include "backend/d3d12/ResourceUploader.h"
|
||||||
#include "backend/d3d12/SamplerD3D12.h"
|
#include "backend/d3d12/SamplerD3D12.h"
|
||||||
|
@ -222,17 +223,17 @@ namespace d3d12 {
|
||||||
CommandBufferBase* Device::CreateCommandBuffer(CommandBufferBuilder* builder) {
|
CommandBufferBase* Device::CreateCommandBuffer(CommandBufferBuilder* builder) {
|
||||||
return new CommandBuffer(this, builder);
|
return new CommandBuffer(this, builder);
|
||||||
}
|
}
|
||||||
|
ComputePipelineBase* Device::CreateComputePipeline(ComputePipelineBuilder* builder) {
|
||||||
|
return new ComputePipeline(builder);
|
||||||
|
}
|
||||||
DepthStencilStateBase* Device::CreateDepthStencilState(DepthStencilStateBuilder* builder) {
|
DepthStencilStateBase* Device::CreateDepthStencilState(DepthStencilStateBuilder* builder) {
|
||||||
return new DepthStencilState(this, builder);
|
return new DepthStencilState(this, builder);
|
||||||
}
|
}
|
||||||
InputStateBase* Device::CreateInputState(InputStateBuilder* builder) {
|
|
||||||
return new InputState(this, builder);
|
|
||||||
}
|
|
||||||
FramebufferBase* Device::CreateFramebuffer(FramebufferBuilder* builder) {
|
FramebufferBase* Device::CreateFramebuffer(FramebufferBuilder* builder) {
|
||||||
return new Framebuffer(this, builder);
|
return new Framebuffer(this, builder);
|
||||||
}
|
}
|
||||||
PipelineBase* Device::CreatePipeline(PipelineBuilder* builder) {
|
InputStateBase* Device::CreateInputState(InputStateBuilder* builder) {
|
||||||
return new Pipeline(this, builder);
|
return new InputState(this, builder);
|
||||||
}
|
}
|
||||||
PipelineLayoutBase* Device::CreatePipelineLayout(PipelineLayoutBuilder* builder) {
|
PipelineLayoutBase* Device::CreatePipelineLayout(PipelineLayoutBuilder* builder) {
|
||||||
return new PipelineLayout(this, builder);
|
return new PipelineLayout(this, builder);
|
||||||
|
@ -243,6 +244,9 @@ namespace d3d12 {
|
||||||
RenderPassBase* Device::CreateRenderPass(RenderPassBuilder* builder) {
|
RenderPassBase* Device::CreateRenderPass(RenderPassBuilder* builder) {
|
||||||
return new RenderPass(this, builder);
|
return new RenderPass(this, builder);
|
||||||
}
|
}
|
||||||
|
RenderPipelineBase* Device::CreateRenderPipeline(RenderPipelineBuilder* builder) {
|
||||||
|
return new RenderPipeline(builder);
|
||||||
|
}
|
||||||
SamplerBase* Device::CreateSampler(SamplerBuilder* builder) {
|
SamplerBase* Device::CreateSampler(SamplerBuilder* builder) {
|
||||||
return new Sampler(builder);
|
return new Sampler(builder);
|
||||||
}
|
}
|
||||||
|
|
|
@ -17,18 +17,9 @@
|
||||||
|
|
||||||
#include "nxt/nxtcpp.h"
|
#include "nxt/nxtcpp.h"
|
||||||
|
|
||||||
#include "backend/Buffer.h"
|
|
||||||
#include "backend/BindGroup.h"
|
|
||||||
#include "backend/BindGroupLayout.h"
|
|
||||||
#include "backend/Device.h"
|
|
||||||
#include "backend/Framebuffer.h"
|
|
||||||
#include "backend/DepthStencilState.h"
|
#include "backend/DepthStencilState.h"
|
||||||
#include "backend/InputState.h"
|
#include "backend/Device.h"
|
||||||
#include "backend/PipelineLayout.h"
|
|
||||||
#include "backend/Queue.h"
|
|
||||||
#include "backend/RenderPass.h"
|
#include "backend/RenderPass.h"
|
||||||
#include "backend/Sampler.h"
|
|
||||||
#include "backend/Texture.h"
|
|
||||||
#include "backend/ToBackend.h"
|
#include "backend/ToBackend.h"
|
||||||
|
|
||||||
#include "backend/d3d12/d3d12_platform.h"
|
#include "backend/d3d12/d3d12_platform.h"
|
||||||
|
@ -41,18 +32,19 @@ namespace d3d12 {
|
||||||
class Buffer;
|
class Buffer;
|
||||||
class BufferView;
|
class BufferView;
|
||||||
class CommandBuffer;
|
class CommandBuffer;
|
||||||
|
class ComputePipeline;
|
||||||
class DepthStencilState;
|
class DepthStencilState;
|
||||||
class Device;
|
class Device;
|
||||||
|
class Framebuffer;
|
||||||
class InputState;
|
class InputState;
|
||||||
class Pipeline;
|
|
||||||
class PipelineLayout;
|
class PipelineLayout;
|
||||||
class Queue;
|
class Queue;
|
||||||
|
class RenderPass;
|
||||||
|
class RenderPipeline;
|
||||||
class Sampler;
|
class Sampler;
|
||||||
class ShaderModule;
|
class ShaderModule;
|
||||||
class Texture;
|
class Texture;
|
||||||
class TextureView;
|
class TextureView;
|
||||||
class Framebuffer;
|
|
||||||
class RenderPass;
|
|
||||||
|
|
||||||
class CommandAllocatorManager;
|
class CommandAllocatorManager;
|
||||||
class DescriptorHeapAllocator;
|
class DescriptorHeapAllocator;
|
||||||
|
@ -66,18 +58,19 @@ namespace d3d12 {
|
||||||
using BufferType = Buffer;
|
using BufferType = Buffer;
|
||||||
using BufferViewType = BufferView;
|
using BufferViewType = BufferView;
|
||||||
using CommandBufferType = CommandBuffer;
|
using CommandBufferType = CommandBuffer;
|
||||||
|
using ComputePipelineType = ComputePipeline;
|
||||||
using DepthStencilStateType = DepthStencilState;
|
using DepthStencilStateType = DepthStencilState;
|
||||||
using DeviceType = Device;
|
using DeviceType = Device;
|
||||||
|
using FramebufferType = Framebuffer;
|
||||||
using InputStateType = InputState;
|
using InputStateType = InputState;
|
||||||
using PipelineType = Pipeline;
|
|
||||||
using PipelineLayoutType = PipelineLayout;
|
using PipelineLayoutType = PipelineLayout;
|
||||||
using QueueType = Queue;
|
using QueueType = Queue;
|
||||||
|
using RenderPassType = RenderPass;
|
||||||
|
using RenderPipelineType = RenderPipeline;
|
||||||
using SamplerType = Sampler;
|
using SamplerType = Sampler;
|
||||||
using ShaderModuleType = ShaderModule;
|
using ShaderModuleType = ShaderModule;
|
||||||
using TextureType = Texture;
|
using TextureType = Texture;
|
||||||
using TextureViewType = TextureView;
|
using TextureViewType = TextureView;
|
||||||
using FramebufferType = Framebuffer;
|
|
||||||
using RenderPassType = RenderPass;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
template<typename T>
|
template<typename T>
|
||||||
|
@ -98,13 +91,14 @@ namespace d3d12 {
|
||||||
BufferBase* CreateBuffer(BufferBuilder* builder) override;
|
BufferBase* CreateBuffer(BufferBuilder* builder) override;
|
||||||
BufferViewBase* CreateBufferView(BufferViewBuilder* builder) override;
|
BufferViewBase* CreateBufferView(BufferViewBuilder* builder) override;
|
||||||
CommandBufferBase* CreateCommandBuffer(CommandBufferBuilder* builder) override;
|
CommandBufferBase* CreateCommandBuffer(CommandBufferBuilder* builder) override;
|
||||||
|
ComputePipelineBase* CreateComputePipeline(ComputePipelineBuilder* builder) override;
|
||||||
DepthStencilStateBase* CreateDepthStencilState(DepthStencilStateBuilder* builder) override;
|
DepthStencilStateBase* CreateDepthStencilState(DepthStencilStateBuilder* builder) override;
|
||||||
InputStateBase* CreateInputState(InputStateBuilder* builder) override;
|
|
||||||
FramebufferBase* CreateFramebuffer(FramebufferBuilder* builder) override;
|
FramebufferBase* CreateFramebuffer(FramebufferBuilder* builder) override;
|
||||||
PipelineBase* CreatePipeline(PipelineBuilder* builder) override;
|
InputStateBase* CreateInputState(InputStateBuilder* builder) override;
|
||||||
PipelineLayoutBase* CreatePipelineLayout(PipelineLayoutBuilder* builder) override;
|
PipelineLayoutBase* CreatePipelineLayout(PipelineLayoutBuilder* builder) override;
|
||||||
QueueBase* CreateQueue(QueueBuilder* builder) override;
|
QueueBase* CreateQueue(QueueBuilder* builder) override;
|
||||||
RenderPassBase* CreateRenderPass(RenderPassBuilder* builder) override;
|
RenderPassBase* CreateRenderPass(RenderPassBuilder* builder) override;
|
||||||
|
RenderPipelineBase* CreateRenderPipeline(RenderPipelineBuilder* builder) override;
|
||||||
SamplerBase* CreateSampler(SamplerBuilder* builder) override;
|
SamplerBase* CreateSampler(SamplerBuilder* builder) override;
|
||||||
ShaderModuleBase* CreateShaderModule(ShaderModuleBuilder* builder) override;
|
ShaderModuleBase* CreateShaderModule(ShaderModuleBuilder* builder) override;
|
||||||
TextureBase* CreateTexture(TextureBuilder* builder) override;
|
TextureBase* CreateTexture(TextureBuilder* builder) override;
|
||||||
|
|
|
@ -17,11 +17,12 @@
|
||||||
#include "backend/d3d12/BindGroupLayoutD3D12.h"
|
#include "backend/d3d12/BindGroupLayoutD3D12.h"
|
||||||
#include "backend/d3d12/BufferD3D12.h"
|
#include "backend/d3d12/BufferD3D12.h"
|
||||||
#include "backend/d3d12/CommandBufferD3D12.h"
|
#include "backend/d3d12/CommandBufferD3D12.h"
|
||||||
|
#include "backend/d3d12/ComputePipelineD3D12.h"
|
||||||
#include "backend/d3d12/FramebufferD3D12.h"
|
#include "backend/d3d12/FramebufferD3D12.h"
|
||||||
#include "backend/d3d12/InputStateD3D12.h"
|
#include "backend/d3d12/InputStateD3D12.h"
|
||||||
#include "backend/d3d12/PipelineD3D12.h"
|
|
||||||
#include "backend/d3d12/PipelineLayoutD3D12.h"
|
#include "backend/d3d12/PipelineLayoutD3D12.h"
|
||||||
#include "backend/d3d12/QueueD3D12.h"
|
#include "backend/d3d12/QueueD3D12.h"
|
||||||
|
#include "backend/d3d12/RenderPipelineD3D12.h"
|
||||||
#include "backend/d3d12/SamplerD3D12.h"
|
#include "backend/d3d12/SamplerD3D12.h"
|
||||||
#include "backend/d3d12/ShaderModuleD3D12.h"
|
#include "backend/d3d12/ShaderModuleD3D12.h"
|
||||||
#include "backend/d3d12/TextureD3D12.h"
|
#include "backend/d3d12/TextureD3D12.h"
|
||||||
|
|
|
@ -1,174 +0,0 @@
|
||||||
// Copyright 2017 The NXT Authors
|
|
||||||
//
|
|
||||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
// you may not use this file except in compliance with the License.
|
|
||||||
// You may obtain a copy of the License at
|
|
||||||
//
|
|
||||||
// http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
//
|
|
||||||
// Unless required by applicable law or agreed to in writing, software
|
|
||||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
// See the License for the specific language governing permissions and
|
|
||||||
// limitations under the License.
|
|
||||||
|
|
||||||
#include "backend/d3d12/PipelineD3D12.h"
|
|
||||||
|
|
||||||
#include "backend/d3d12/D3D12Backend.h"
|
|
||||||
#include "backend/d3d12/InputStateD3D12.h"
|
|
||||||
#include "backend/d3d12/ShaderModuleD3D12.h"
|
|
||||||
#include "backend/d3d12/PipelineLayoutD3D12.h"
|
|
||||||
#include "common/Assert.h"
|
|
||||||
|
|
||||||
#include <d3dcompiler.h>
|
|
||||||
|
|
||||||
using Microsoft::WRL::ComPtr;
|
|
||||||
|
|
||||||
namespace backend {
|
|
||||||
namespace d3d12 {
|
|
||||||
|
|
||||||
Pipeline::Pipeline(Device* device, PipelineBuilder* builder) : PipelineBase(builder), device(device) {
|
|
||||||
uint32_t compileFlags = 0;
|
|
||||||
#if defined(_DEBUG)
|
|
||||||
// Enable better shader debugging with the graphics debugging tools.
|
|
||||||
compileFlags |= D3DCOMPILE_DEBUG | D3DCOMPILE_SKIP_OPTIMIZATION;
|
|
||||||
#endif
|
|
||||||
// SPRIV-cross does matrix multiplication expecting row major matrices
|
|
||||||
compileFlags |= D3DCOMPILE_PACK_MATRIX_ROW_MAJOR;
|
|
||||||
|
|
||||||
if (IsCompute()) {
|
|
||||||
const auto& module = ToBackend(builder->GetStageInfo(nxt::ShaderStage::Compute).module);
|
|
||||||
const auto& entryPoint = builder->GetStageInfo(nxt::ShaderStage::Compute).entryPoint;
|
|
||||||
const auto& hlslSource = module->GetHLSLSource();
|
|
||||||
|
|
||||||
ComPtr<ID3DBlob> compiledShader;
|
|
||||||
ComPtr<ID3DBlob> errors;
|
|
||||||
|
|
||||||
if(FAILED(D3DCompile(
|
|
||||||
hlslSource.c_str(),
|
|
||||||
hlslSource.length(),
|
|
||||||
nullptr,
|
|
||||||
{ nullptr },
|
|
||||||
nullptr,
|
|
||||||
entryPoint.c_str(),
|
|
||||||
"cs_5_0",
|
|
||||||
compileFlags,
|
|
||||||
0,
|
|
||||||
&compiledShader,
|
|
||||||
&errors
|
|
||||||
))) {
|
|
||||||
printf("%s\n", reinterpret_cast<char*>(errors->GetBufferPointer()));
|
|
||||||
ASSERT(false);
|
|
||||||
}
|
|
||||||
|
|
||||||
D3D12_COMPUTE_PIPELINE_STATE_DESC descriptor = {};
|
|
||||||
descriptor.pRootSignature = ToBackend(GetLayout())->GetRootSignature().Get();
|
|
||||||
descriptor.CS.pShaderBytecode = compiledShader->GetBufferPointer();
|
|
||||||
descriptor.CS.BytecodeLength = compiledShader->GetBufferSize();
|
|
||||||
|
|
||||||
device->GetD3D12Device()->CreateComputePipelineState(&descriptor, IID_PPV_ARGS(&computePipelineState));
|
|
||||||
|
|
||||||
} else {
|
|
||||||
D3D12_GRAPHICS_PIPELINE_STATE_DESC descriptor = {};
|
|
||||||
|
|
||||||
PerStage<ComPtr<ID3DBlob>> compiledShader;
|
|
||||||
ComPtr<ID3DBlob> errors;
|
|
||||||
|
|
||||||
for (auto stage : IterateStages(GetStageMask())) {
|
|
||||||
const auto& module = ToBackend(builder->GetStageInfo(stage).module);
|
|
||||||
const auto& entryPoint = builder->GetStageInfo(stage).entryPoint;
|
|
||||||
const auto& hlslSource = module->GetHLSLSource();
|
|
||||||
|
|
||||||
const char* compileTarget = nullptr;
|
|
||||||
|
|
||||||
D3D12_SHADER_BYTECODE* shader = nullptr;
|
|
||||||
switch (stage) {
|
|
||||||
case nxt::ShaderStage::Vertex:
|
|
||||||
shader = &descriptor.VS;
|
|
||||||
compileTarget = "vs_5_1";
|
|
||||||
break;
|
|
||||||
case nxt::ShaderStage::Fragment:
|
|
||||||
shader = &descriptor.PS;
|
|
||||||
compileTarget = "ps_5_1";
|
|
||||||
break;
|
|
||||||
case nxt::ShaderStage::Compute:
|
|
||||||
UNREACHABLE();
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(FAILED(D3DCompile(
|
|
||||||
hlslSource.c_str(),
|
|
||||||
hlslSource.length(),
|
|
||||||
nullptr,
|
|
||||||
nullptr,
|
|
||||||
nullptr,
|
|
||||||
entryPoint.c_str(),
|
|
||||||
compileTarget,
|
|
||||||
compileFlags,
|
|
||||||
0,
|
|
||||||
&compiledShader[stage],
|
|
||||||
&errors
|
|
||||||
))) {
|
|
||||||
printf("%s\n", reinterpret_cast<char*>(errors->GetBufferPointer()));
|
|
||||||
ASSERT(false);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (shader != nullptr) {
|
|
||||||
shader->pShaderBytecode = compiledShader[stage]->GetBufferPointer();
|
|
||||||
shader->BytecodeLength = compiledShader[stage]->GetBufferSize();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
PipelineLayout* layout = ToBackend(GetLayout());
|
|
||||||
|
|
||||||
descriptor.pRootSignature = layout->GetRootSignature().Get();
|
|
||||||
|
|
||||||
// D3D12 logs warnings if any empty input state is used
|
|
||||||
InputState* inputState = ToBackend(GetInputState());
|
|
||||||
if (inputState->GetAttributesSetMask().any()) {
|
|
||||||
descriptor.InputLayout = inputState->GetD3D12InputLayoutDescriptor();
|
|
||||||
}
|
|
||||||
|
|
||||||
descriptor.RasterizerState.FillMode = D3D12_FILL_MODE_SOLID;
|
|
||||||
descriptor.RasterizerState.CullMode = D3D12_CULL_MODE_NONE;
|
|
||||||
descriptor.RasterizerState.FrontCounterClockwise = FALSE;
|
|
||||||
descriptor.RasterizerState.DepthBias = D3D12_DEFAULT_DEPTH_BIAS;
|
|
||||||
descriptor.RasterizerState.DepthBiasClamp = D3D12_DEFAULT_DEPTH_BIAS_CLAMP;
|
|
||||||
descriptor.RasterizerState.SlopeScaledDepthBias = D3D12_DEFAULT_SLOPE_SCALED_DEPTH_BIAS;
|
|
||||||
descriptor.RasterizerState.DepthClipEnable = TRUE;
|
|
||||||
descriptor.RasterizerState.MultisampleEnable = FALSE;
|
|
||||||
descriptor.RasterizerState.AntialiasedLineEnable = FALSE;
|
|
||||||
descriptor.RasterizerState.ForcedSampleCount = 0;
|
|
||||||
descriptor.RasterizerState.ConservativeRaster = D3D12_CONSERVATIVE_RASTERIZATION_MODE_OFF;
|
|
||||||
|
|
||||||
descriptor.BlendState.AlphaToCoverageEnable = FALSE;
|
|
||||||
descriptor.BlendState.IndependentBlendEnable = FALSE;
|
|
||||||
descriptor.BlendState.RenderTarget[0].BlendEnable = FALSE;
|
|
||||||
descriptor.BlendState.RenderTarget[0].LogicOpEnable = FALSE;
|
|
||||||
descriptor.BlendState.RenderTarget[0].SrcBlend = D3D12_BLEND_ONE;
|
|
||||||
descriptor.BlendState.RenderTarget[0].DestBlend = D3D12_BLEND_ZERO;
|
|
||||||
descriptor.BlendState.RenderTarget[0].BlendOp = D3D12_BLEND_OP_ADD;
|
|
||||||
descriptor.BlendState.RenderTarget[0].SrcBlendAlpha = D3D12_BLEND_ONE;
|
|
||||||
descriptor.BlendState.RenderTarget[0].DestBlendAlpha = D3D12_BLEND_ZERO;
|
|
||||||
descriptor.BlendState.RenderTarget[0].BlendOpAlpha = D3D12_BLEND_OP_ADD;
|
|
||||||
descriptor.BlendState.RenderTarget[0].LogicOp = D3D12_LOGIC_OP_NOOP;
|
|
||||||
descriptor.BlendState.RenderTarget[0].RenderTargetWriteMask = D3D12_COLOR_WRITE_ENABLE_ALL;
|
|
||||||
|
|
||||||
descriptor.DepthStencilState.DepthEnable = false;
|
|
||||||
descriptor.DepthStencilState.StencilEnable = false;
|
|
||||||
descriptor.SampleMask = UINT_MAX;
|
|
||||||
descriptor.PrimitiveTopologyType = D3D12_PRIMITIVE_TOPOLOGY_TYPE_TRIANGLE;
|
|
||||||
descriptor.NumRenderTargets = 1;
|
|
||||||
descriptor.RTVFormats[0] = DXGI_FORMAT_R8G8B8A8_UNORM;
|
|
||||||
descriptor.SampleDesc.Count = 1;
|
|
||||||
|
|
||||||
ASSERT_SUCCESS(device->GetD3D12Device()->CreateRenderPipelineState(&descriptor, IID_PPV_ARGS(&renderPipelineState)));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
ComPtr<ID3D12PipelineState> Pipeline::GetRenderPipelineState() {
|
|
||||||
return renderPipelineState;
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -0,0 +1,140 @@
|
||||||
|
// Copyright 2017 The NXT Authors
|
||||||
|
//
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, software
|
||||||
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
// See the License for the specific language governing permissions and
|
||||||
|
// limitations under the License.
|
||||||
|
|
||||||
|
#include "backend/d3d12/RenderPipelineD3D12.h"
|
||||||
|
|
||||||
|
#include "backend/d3d12/D3D12Backend.h"
|
||||||
|
#include "backend/d3d12/InputStateD3D12.h"
|
||||||
|
#include "backend/d3d12/ShaderModuleD3D12.h"
|
||||||
|
#include "backend/d3d12/PipelineLayoutD3D12.h"
|
||||||
|
#include "common/Assert.h"
|
||||||
|
|
||||||
|
#include <d3dcompiler.h>
|
||||||
|
|
||||||
|
namespace backend {
|
||||||
|
namespace d3d12 {
|
||||||
|
|
||||||
|
RenderPipeline::RenderPipeline(RenderPipelineBuilder* builder)
|
||||||
|
: RenderPipelineBase(builder) {
|
||||||
|
uint32_t compileFlags = 0;
|
||||||
|
#if defined(_DEBUG)
|
||||||
|
// Enable better shader debugging with the graphics debugging tools.
|
||||||
|
compileFlags |= D3DCOMPILE_DEBUG | D3DCOMPILE_SKIP_OPTIMIZATION;
|
||||||
|
#endif
|
||||||
|
// SPRIV-cross does matrix multiplication expecting row major matrices
|
||||||
|
compileFlags |= D3DCOMPILE_PACK_MATRIX_ROW_MAJOR;
|
||||||
|
|
||||||
|
D3D12_GRAPHICS_PIPELINE_STATE_DESC descriptor = {};
|
||||||
|
|
||||||
|
PerStage<ComPtr<ID3DBlob>> compiledShader;
|
||||||
|
ComPtr<ID3DBlob> errors;
|
||||||
|
|
||||||
|
for (auto stage : IterateStages(GetStageMask())) {
|
||||||
|
const auto& module = ToBackend(builder->GetStageInfo(stage).module);
|
||||||
|
const auto& entryPoint = builder->GetStageInfo(stage).entryPoint;
|
||||||
|
const auto& hlslSource = module->GetHLSLSource();
|
||||||
|
|
||||||
|
const char* compileTarget = nullptr;
|
||||||
|
|
||||||
|
D3D12_SHADER_BYTECODE* shader = nullptr;
|
||||||
|
switch (stage) {
|
||||||
|
case nxt::ShaderStage::Vertex:
|
||||||
|
shader = &descriptor.VS;
|
||||||
|
compileTarget = "vs_5_1";
|
||||||
|
break;
|
||||||
|
case nxt::ShaderStage::Fragment:
|
||||||
|
shader = &descriptor.PS;
|
||||||
|
compileTarget = "ps_5_1";
|
||||||
|
break;
|
||||||
|
case nxt::ShaderStage::Compute:
|
||||||
|
UNREACHABLE();
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
if(FAILED(D3DCompile(
|
||||||
|
hlslSource.c_str(),
|
||||||
|
hlslSource.length(),
|
||||||
|
nullptr,
|
||||||
|
nullptr,
|
||||||
|
nullptr,
|
||||||
|
entryPoint.c_str(),
|
||||||
|
compileTarget,
|
||||||
|
compileFlags,
|
||||||
|
0,
|
||||||
|
&compiledShader[stage],
|
||||||
|
&errors
|
||||||
|
))) {
|
||||||
|
printf("%s\n", reinterpret_cast<char*>(errors->GetBufferPointer()));
|
||||||
|
ASSERT(false);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (shader != nullptr) {
|
||||||
|
shader->pShaderBytecode = compiledShader[stage]->GetBufferPointer();
|
||||||
|
shader->BytecodeLength = compiledShader[stage]->GetBufferSize();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
PipelineLayout* layout = ToBackend(GetLayout());
|
||||||
|
|
||||||
|
descriptor.pRootSignature = layout->GetRootSignature().Get();
|
||||||
|
|
||||||
|
// D3D12 logs warnings if any empty input state is used
|
||||||
|
InputState* inputState = ToBackend(GetInputState());
|
||||||
|
if (inputState->GetAttributesSetMask().any()) {
|
||||||
|
descriptor.InputLayout = inputState->GetD3D12InputLayoutDescriptor();
|
||||||
|
}
|
||||||
|
|
||||||
|
descriptor.RasterizerState.FillMode = D3D12_FILL_MODE_SOLID;
|
||||||
|
descriptor.RasterizerState.CullMode = D3D12_CULL_MODE_NONE;
|
||||||
|
descriptor.RasterizerState.FrontCounterClockwise = FALSE;
|
||||||
|
descriptor.RasterizerState.DepthBias = D3D12_DEFAULT_DEPTH_BIAS;
|
||||||
|
descriptor.RasterizerState.DepthBiasClamp = D3D12_DEFAULT_DEPTH_BIAS_CLAMP;
|
||||||
|
descriptor.RasterizerState.SlopeScaledDepthBias = D3D12_DEFAULT_SLOPE_SCALED_DEPTH_BIAS;
|
||||||
|
descriptor.RasterizerState.DepthClipEnable = TRUE;
|
||||||
|
descriptor.RasterizerState.MultisampleEnable = FALSE;
|
||||||
|
descriptor.RasterizerState.AntialiasedLineEnable = FALSE;
|
||||||
|
descriptor.RasterizerState.ForcedSampleCount = 0;
|
||||||
|
descriptor.RasterizerState.ConservativeRaster = D3D12_CONSERVATIVE_RASTERIZATION_MODE_OFF;
|
||||||
|
|
||||||
|
descriptor.BlendState.AlphaToCoverageEnable = FALSE;
|
||||||
|
descriptor.BlendState.IndependentBlendEnable = FALSE;
|
||||||
|
descriptor.BlendState.RenderTarget[0].BlendEnable = FALSE;
|
||||||
|
descriptor.BlendState.RenderTarget[0].LogicOpEnable = FALSE;
|
||||||
|
descriptor.BlendState.RenderTarget[0].SrcBlend = D3D12_BLEND_ONE;
|
||||||
|
descriptor.BlendState.RenderTarget[0].DestBlend = D3D12_BLEND_ZERO;
|
||||||
|
descriptor.BlendState.RenderTarget[0].BlendOp = D3D12_BLEND_OP_ADD;
|
||||||
|
descriptor.BlendState.RenderTarget[0].SrcBlendAlpha = D3D12_BLEND_ONE;
|
||||||
|
descriptor.BlendState.RenderTarget[0].DestBlendAlpha = D3D12_BLEND_ZERO;
|
||||||
|
descriptor.BlendState.RenderTarget[0].BlendOpAlpha = D3D12_BLEND_OP_ADD;
|
||||||
|
descriptor.BlendState.RenderTarget[0].LogicOp = D3D12_LOGIC_OP_NOOP;
|
||||||
|
descriptor.BlendState.RenderTarget[0].RenderTargetWriteMask = D3D12_COLOR_WRITE_ENABLE_ALL;
|
||||||
|
|
||||||
|
descriptor.DepthStencilState.DepthEnable = false;
|
||||||
|
descriptor.DepthStencilState.StencilEnable = false;
|
||||||
|
descriptor.SampleMask = UINT_MAX;
|
||||||
|
descriptor.PrimitiveTopologyType = D3D12_PRIMITIVE_TOPOLOGY_TYPE_TRIANGLE;
|
||||||
|
descriptor.NumRenderTargets = 1;
|
||||||
|
descriptor.RTVFormats[0] = DXGI_FORMAT_R8G8B8A8_UNORM;
|
||||||
|
descriptor.SampleDesc.Count = 1;
|
||||||
|
|
||||||
|
Device* device = ToBackend(builder->GetDevice());
|
||||||
|
ASSERT_SUCCESS(device->GetD3D12Device()->CreateGraphicsPipelineState(&descriptor, IID_PPV_ARGS(&pipelineState)));
|
||||||
|
}
|
||||||
|
|
||||||
|
ComPtr<ID3D12PipelineState> RenderPipeline::GetPipelineState() {
|
||||||
|
return pipelineState;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
|
@ -12,33 +12,27 @@
|
||||||
// See the License for the specific language governing permissions and
|
// See the License for the specific language governing permissions and
|
||||||
// limitations under the License.
|
// limitations under the License.
|
||||||
|
|
||||||
#ifndef BACKEND_D3D12_PIPELINED3D12_H_
|
#ifndef BACKEND_D3D12_RENDERPIPELINED3D12_H_
|
||||||
#define BACKEND_D3D12_PIPELINED3D12_H_
|
#define BACKEND_D3D12_RENDERPIPELINED3D12_H_
|
||||||
|
|
||||||
#include "backend/Pipeline.h"
|
#include "backend/RenderPipeline.h"
|
||||||
|
|
||||||
#include "backend/d3d12/d3d12_platform.h"
|
#include "backend/d3d12/d3d12_platform.h"
|
||||||
|
|
||||||
namespace backend {
|
namespace backend {
|
||||||
namespace d3d12 {
|
namespace d3d12 {
|
||||||
|
|
||||||
class Device;
|
class RenderPipeline : public RenderPipelineBase {
|
||||||
class ShaderModule;
|
|
||||||
|
|
||||||
class Pipeline : public PipelineBase {
|
|
||||||
public:
|
public:
|
||||||
Pipeline(Device* device, PipelineBuilder* builder);
|
RenderPipeline(RenderPipelineBuilder* builder);
|
||||||
|
|
||||||
ComPtr<ID3D12PipelineState> GetRenderPipelineState();
|
ComPtr<ID3D12PipelineState> GetPipelineState();
|
||||||
|
|
||||||
private:
|
private:
|
||||||
Device* device;
|
ComPtr<ID3D12PipelineState> pipelineState;
|
||||||
|
|
||||||
ComPtr<ID3D12PipelineState> renderPipelineState;
|
|
||||||
ComPtr<ID3D12PipelineState> computePipelineState;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif // BACKEND_D3D12_PIPELINED3D12_H_
|
#endif // BACKEND_D3D12_RENDERPIPELINED3D12_H_
|
Loading…
Reference in New Issue