[D3D12] Constant buffer binding

This commit is contained in:
Triang3l
2018-07-30 15:59:43 +03:00
parent 84e7ae16e7
commit e0eede73b9
9 changed files with 857 additions and 350 deletions

View File

@@ -11,6 +11,7 @@
#define XENIA_GPU_D3D12_D3D12_COMMAND_PROCESSOR_H_
#include <memory>
#include <unordered_map>
#include "xenia/gpu/command_processor.h"
#include "xenia/gpu/d3d12/d3d12_graphics_system.h"
@@ -20,6 +21,7 @@
#include "xenia/kernel/kernel_state.h"
#include "xenia/ui/d3d12/command_list.h"
#include "xenia/ui/d3d12/d3d12_context.h"
#include "xenia/ui/d3d12/pools.h"
namespace xe {
namespace gpu {
@@ -38,10 +40,29 @@ class D3D12CommandProcessor : public CommandProcessor {
return static_cast<xe::ui::d3d12::D3D12Context*>(context_.get());
}
// Finds or creates root signature for a pipeline.
ID3D12RootSignature* GetRootSignature(const D3D12Shader* vertex_shader,
const D3D12Shader* pixel_shader);
// Request and automatically rebind descriptors on the draw command list.
// Refer to DescriptorHeapPool::Request for partial/full update explanation.
uint64_t RequestViewDescriptors(uint64_t previous_full_update,
uint32_t count_for_partial_update,
uint32_t count_for_full_update,
D3D12_CPU_DESCRIPTOR_HANDLE& cpu_handle_out,
D3D12_GPU_DESCRIPTOR_HANDLE& gpu_handle_out);
uint64_t RequestSamplerDescriptors(
uint64_t previous_full_update, uint32_t count_for_partial_update,
uint32_t count_for_full_update,
D3D12_CPU_DESCRIPTOR_HANDLE& cpu_handle_out,
D3D12_GPU_DESCRIPTOR_HANDLE& gpu_handle_out);
protected:
bool SetupContext() override;
void ShutdownContext() override;
void WriteRegister(uint32_t index, uint32_t value) override;
void PerformSwap(uint32_t frontbuffer_ptr, uint32_t frontbuffer_width,
uint32_t frontbuffer_height) override;
@@ -54,11 +75,61 @@ class D3D12CommandProcessor : public CommandProcessor {
bool IssueCopy() override;
private:
enum RootParameter : UINT {
// These are always present.
// Very frequently changed, especially for UI draws, and for models drawn in
// multiple parts - contains fetch constants with vertex addresses (b10).
kRootParameter_FetchConstants,
// Quite frequently changed (for one object drawn multiple times, for
// instance - may contain projection matrices) - 8 pages of float constants
// (b2-b9).
kRootParameter_VertexFloatConstants,
// Less frequently changed (per-material) - 8 pages of float constants
// (b2-b9).
kRootParameter_PixelFloatConstants,
// Rarely changed - system constants like viewport and alpha testing (b0)
// and loop and bool constants (b1).
kRootParameter_CommonConstants,
// Never changed - shared memory byte address buffer (t0, space1).
kRootParameter_SharedMemory,
kRootParameter_Count_NoTextures,
// These are there only if textures are fetched (they are changed pretty
// frequently, but for the ease of maintenance they're in the end).
// If the pixel shader samples textures, these are for pixel textures
// (changed more frequently), otherwise, if the vertex shader samples
// textures, these are for vertex textures.
// Used textures of all types (t0+, space0).
kRootParameter_PixelOrVertexTextures = kRootParameter_Count_NoTextures,
// Used samplers (s0+).
kRootParameter_PixelOrVertexSamplers,
kRootParameter_Count_OneStageTextures,
// These are only present if both pixel and vertex shaders sample textures
// for vertex textures.
// Used textures of all types (t0+, space0).
kRootParameter_VertexTextures = kRootParameter_Count_OneStageTextures,
// Used samplers (s0+).
kRootParameter_VertexSamplers,
kRootParameter_Count_TwoStageTextures,
};
// Returns true if a new frame was started.
bool BeginFrame();
// Returns true if an open frame was ended.
bool EndFrame();
bool UpdateBindings(ID3D12GraphicsCommandList* command_list,
const D3D12Shader* vertex_shader,
const D3D12Shader* pixel_shader,
ID3D12RootSignature* root_signature);
bool cache_clear_requested_ = false;
std::unique_ptr<ui::d3d12::CommandList>
@@ -67,9 +138,58 @@ class D3D12CommandProcessor : public CommandProcessor {
command_lists_[ui::d3d12::D3D12Context::kQueuedFrames] = {};
std::unique_ptr<SharedMemory> shared_memory_ = nullptr;
// Root signatures for different descriptor counts.
std::unordered_map<uint32_t, ID3D12RootSignature*> root_signatures_;
std::unique_ptr<PipelineCache> pipeline_cache_ = nullptr;
std::unique_ptr<ui::d3d12::UploadBufferPool> constant_buffer_pool_ = nullptr;
std::unique_ptr<ui::d3d12::DescriptorHeapPool> view_heap_pool_ = nullptr;
std::unique_ptr<ui::d3d12::DescriptorHeapPool> sampler_heap_pool_ = nullptr;
uint32_t current_queue_frame_ = UINT32_MAX;
// Currently bound graphics or compute pipeline.
ID3D12PipelineState* current_pipeline_;
// Currently bound graphics root signature.
ID3D12RootSignature* current_graphics_root_signature_;
// Whether root parameters are up to date - reset if a new signature is bound.
uint32_t current_graphics_root_up_to_date_;
// Currently bound descriptor heaps - update by RequestViewDescriptors and
// RequestSamplerDescriptors.
ID3D12DescriptorHeap* current_view_heap_;
ID3D12DescriptorHeap* current_sampler_heap_;
// System shader constants.
struct SystemConstants {
float viewport_inv_scale_x;
float viewport_inv_scale_y;
uint32_t vertex_index_endian;
uint32_t textures_are_3d;
} cbuffer_system_;
// Constant buffer bindings.
struct ConstantBufferBinding {
D3D12_GPU_VIRTUAL_ADDRESS buffer_address;
bool up_to_date;
};
ConstantBufferBinding cbuffer_bindings_system_;
ConstantBufferBinding cbuffer_bindings_float_[16];
ConstantBufferBinding cbuffer_bindings_bool_loop_;
ConstantBufferBinding cbuffer_bindings_fetch_;
// Pages with the descriptors currently used for handling Xenos draw calls.
uint64_t draw_view_full_update_;
uint64_t draw_sampler_full_update_;
// Latest descriptor handles used for handling Xenos draw calls.
D3D12_GPU_DESCRIPTOR_HANDLE gpu_handle_common_constants_;
D3D12_GPU_DESCRIPTOR_HANDLE gpu_handle_vertex_float_constants_;
D3D12_GPU_DESCRIPTOR_HANDLE gpu_handle_pixel_float_constants_;
D3D12_GPU_DESCRIPTOR_HANDLE gpu_handle_fetch_constants_;
D3D12_GPU_DESCRIPTOR_HANDLE gpu_handle_shared_memory_;
};
} // namespace d3d12