summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--build/visual-studio/slang-unit-test-tool/slang-unit-test-tool.vcxproj1
-rw-r--r--build/visual-studio/slang-unit-test-tool/slang-unit-test-tool.vcxproj.filters3
-rw-r--r--examples/gpu-printing/main.cpp4
-rw-r--r--examples/model-viewer/main.cpp2
-rw-r--r--examples/ray-tracing-pipeline/main.cpp4
-rw-r--r--examples/ray-tracing/main.cpp4
-rw-r--r--examples/shader-object/main.cpp5
-rw-r--r--examples/shader-toy/main.cpp2
-rw-r--r--examples/triangle/main.cpp2
-rw-r--r--slang-gfx.h51
-rw-r--r--slang.h8
-rw-r--r--slang.sln30
-rw-r--r--source/core/slang-chunked-list.h1
-rw-r--r--source/slang/slang-parameter-binding.cpp10
-rw-r--r--source/slang/slang-reflection-api.cpp15
-rw-r--r--source/slang/slang-type-layout.h3
-rw-r--r--tools/gfx-unit-test/buffer-barrier-test.cpp3
-rw-r--r--tools/gfx-unit-test/compute-smoke.cpp3
-rw-r--r--tools/gfx-unit-test/create-buffer-from-handle.cpp3
-rw-r--r--tools/gfx-unit-test/existing-device-handle-test.cpp3
-rw-r--r--tools/gfx-unit-test/format-unit-tests.cpp3
-rw-r--r--tools/gfx-unit-test/gfx-test-util.cpp4
-rw-r--r--tools/gfx-unit-test/mutable-shader-object.cpp3
-rw-r--r--tools/gfx-unit-test/nested-parameter-block.cpp4
-rw-r--r--tools/gfx-unit-test/root-mutable-shader-object.cpp3
-rw-r--r--tools/gfx-unit-test/shared-buffers-tests.cpp3
-rw-r--r--tools/gfx-unit-test/shared-textures-tests.cpp3
-rw-r--r--tools/gfx/cpu/render-cpu.cpp19
-rw-r--r--tools/gfx/cuda/render-cuda.cpp23
-rw-r--r--tools/gfx/d3d11/render-d3d11.cpp23
-rw-r--r--tools/gfx/d3d12/descriptor-heap-d3d12.h154
-rw-r--r--tools/gfx/d3d12/render-d3d12.cpp341
-rw-r--r--tools/gfx/debug-layer.cpp4
-rw-r--r--tools/gfx/debug-layer.h1
-rw-r--r--tools/gfx/mutable-shader-object.h2
-rw-r--r--tools/gfx/open-gl/render-gl.cpp22
-rw-r--r--tools/gfx/renderer-shared.cpp98
-rw-r--r--tools/gfx/renderer-shared.h32
-rw-r--r--tools/gfx/vulkan/render-vk.cpp51
-rw-r--r--tools/platform/gui.cpp2
-rw-r--r--tools/render-test/render-test-main.cpp4
-rw-r--r--tools/render-test/slang-support.cpp6
-rw-r--r--tools/slang-unit-test/unit-test-chunked-list.cpp41
43 files changed, 776 insertions, 227 deletions
diff --git a/build/visual-studio/slang-unit-test-tool/slang-unit-test-tool.vcxproj b/build/visual-studio/slang-unit-test-tool/slang-unit-test-tool.vcxproj
index 74126e92c..fd24865a4 100644
--- a/build/visual-studio/slang-unit-test-tool/slang-unit-test-tool.vcxproj
+++ b/build/visual-studio/slang-unit-test-tool/slang-unit-test-tool.vcxproj
@@ -273,6 +273,7 @@
<ItemGroup>
<ClCompile Include="..\..\..\tools\slang-unit-test\unit-offset-container.cpp" />
<ClCompile Include="..\..\..\tools\slang-unit-test\unit-test-byte-encode.cpp" />
+ <ClCompile Include="..\..\..\tools\slang-unit-test\unit-test-chunked-list.cpp" />
<ClCompile Include="..\..\..\tools\slang-unit-test\unit-test-command-line-args.cpp" />
<ClCompile Include="..\..\..\tools\slang-unit-test\unit-test-compression.cpp" />
<ClCompile Include="..\..\..\tools\slang-unit-test\unit-test-find-type-by-name.cpp" />
diff --git a/build/visual-studio/slang-unit-test-tool/slang-unit-test-tool.vcxproj.filters b/build/visual-studio/slang-unit-test-tool/slang-unit-test-tool.vcxproj.filters
index 9db9bee4c..7e06cf50c 100644
--- a/build/visual-studio/slang-unit-test-tool/slang-unit-test-tool.vcxproj.filters
+++ b/build/visual-studio/slang-unit-test-tool/slang-unit-test-tool.vcxproj.filters
@@ -20,6 +20,9 @@
<ClCompile Include="..\..\..\tools\slang-unit-test\unit-test-byte-encode.cpp">
<Filter>Source Files</Filter>
</ClCompile>
+ <ClCompile Include="..\..\..\tools\slang-unit-test\unit-test-chunked-list.cpp">
+ <Filter>Source Files</Filter>
+ </ClCompile>
<ClCompile Include="..\..\..\tools\slang-unit-test\unit-test-command-line-args.cpp">
<Filter>Source Files</Filter>
</ClCompile>
diff --git a/examples/gpu-printing/main.cpp b/examples/gpu-printing/main.cpp
index 31313830f..d8f680376 100644
--- a/examples/gpu-printing/main.cpp
+++ b/examples/gpu-printing/main.cpp
@@ -73,7 +73,7 @@ ComPtr<gfx::IShaderProgram> loadComputeProgram(slang::IModule* slangModule, char
gGPUPrinting.loadStrings(linkedProgram->getLayout());
gfx::IShaderProgram::Desc programDesc = {};
- programDesc.slangProgram = linkedProgram;
+ programDesc.slangGlobalScope = linkedProgram;
auto shaderProgram = gDevice->createProgram(programDesc);
@@ -113,7 +113,7 @@ Result execute()
IResourceView::Desc printBufferViewDesc;
printBufferViewDesc.type = IResourceView::Type::UnorderedAccess;
- auto printBufferView = gDevice->createBufferView(printBuffer, printBufferViewDesc);
+ auto printBufferView = gDevice->createBufferView(printBuffer, nullptr, printBufferViewDesc);
ITransientResourceHeap::Desc transientResourceHeapDesc = {};
transientResourceHeapDesc.constantBufferSize = 256;
diff --git a/examples/model-viewer/main.cpp b/examples/model-viewer/main.cpp
index dcc1a975f..3b278fede 100644
--- a/examples/model-viewer/main.cpp
+++ b/examples/model-viewer/main.cpp
@@ -108,7 +108,7 @@ struct RendererContext
// We can create a `gfx::IShaderProgram` object from `composedProgram`
// so it may be used by the graphics layer.
gfx::IShaderProgram::Desc programDesc = {};
- programDesc.slangProgram = composedProgram.get();
+ programDesc.slangGlobalScope = composedProgram.get();
shaderProgram = device->createProgram(programDesc);
diff --git a/examples/ray-tracing-pipeline/main.cpp b/examples/ray-tracing-pipeline/main.cpp
index 9b01d251c..9e00ccf67 100644
--- a/examples/ray-tracing-pipeline/main.cpp
+++ b/examples/ray-tracing-pipeline/main.cpp
@@ -201,7 +201,7 @@ gfx::Result loadShaderProgram(
SLANG_RETURN_ON_FAIL(result);
gfx::IShaderProgram::Desc programDesc = {};
- programDesc.slangProgram = linkedProgram;
+ programDesc.slangGlobalScope = linkedProgram;
SLANG_RETURN_ON_FAIL(device->createProgram(programDesc, outProgram));
return SLANG_OK;
@@ -327,7 +327,7 @@ Slang::Result initialize()
primitiveSRVDesc.format = Format::Unknown;
primitiveSRVDesc.type = IResourceView::Type::ShaderResource;
primitiveSRVDesc.bufferElementSize = sizeof(Primitive);
- gPrimitiveBufferSRV = gDevice->createBufferView(gPrimitiveBuffer, primitiveSRVDesc);
+ gPrimitiveBufferSRV = gDevice->createBufferView(gPrimitiveBuffer, nullptr, primitiveSRVDesc);
IBufferResource::Desc transformBufferDesc;
transformBufferDesc.type = IResource::Type::Buffer;
diff --git a/examples/ray-tracing/main.cpp b/examples/ray-tracing/main.cpp
index 9d6a638d4..82ad01c95 100644
--- a/examples/ray-tracing/main.cpp
+++ b/examples/ray-tracing/main.cpp
@@ -193,7 +193,7 @@ gfx::Result loadShaderProgram(
SLANG_RETURN_ON_FAIL(result);
gfx::IShaderProgram::Desc programDesc = {};
- programDesc.slangProgram = linkedProgram;
+ programDesc.slangGlobalScope = linkedProgram;
SLANG_RETURN_ON_FAIL(device->createProgram(programDesc, outProgram));
return SLANG_OK;
@@ -318,7 +318,7 @@ Slang::Result initialize()
primitiveSRVDesc.format = Format::Unknown;
primitiveSRVDesc.type = IResourceView::Type::ShaderResource;
primitiveSRVDesc.bufferElementSize = sizeof(Primitive);
- gPrimitiveBufferSRV = gDevice->createBufferView(gPrimitiveBuffer, primitiveSRVDesc);
+ gPrimitiveBufferSRV = gDevice->createBufferView(gPrimitiveBuffer, nullptr, primitiveSRVDesc);
IBufferResource::Desc transformBufferDesc;
transformBufferDesc.type = IResource::Type::Buffer;
diff --git a/examples/shader-object/main.cpp b/examples/shader-object/main.cpp
index 58c6abbfd..7c72194d3 100644
--- a/examples/shader-object/main.cpp
+++ b/examples/shader-object/main.cpp
@@ -120,7 +120,7 @@ Result loadShaderProgram(
// We can create a `gfx::IShaderProgram` object from `composedProgram`
// so it may be used by the graphics layer.
gfx::IShaderProgram::Desc programDesc = {};
- programDesc.slangProgram = composedProgram.get();
+ programDesc.slangGlobalScope = composedProgram.get();
auto shaderProgram = device->createProgram(programDesc);
@@ -183,7 +183,8 @@ int main()
gfx::IResourceView::Desc viewDesc = {};
viewDesc.type = gfx::IResourceView::Type::UnorderedAccess;
viewDesc.format = gfx::Format::Unknown;
- SLANG_RETURN_ON_FAIL(device->createBufferView(numbersBuffer, viewDesc, bufferView.writeRef()));
+ SLANG_RETURN_ON_FAIL(
+ device->createBufferView(numbersBuffer, nullptr, viewDesc, bufferView.writeRef()));
// We have done all the set up work, now it is time to start recording a command buffer for
// GPU execution.
diff --git a/examples/shader-toy/main.cpp b/examples/shader-toy/main.cpp
index 879330aca..ec161aee8 100644
--- a/examples/shader-toy/main.cpp
+++ b/examples/shader-toy/main.cpp
@@ -263,7 +263,7 @@ Result loadShaderProgram(gfx::IDevice* device, ComPtr<gfx::IShaderProgram>& outS
SLANG_RETURN_ON_FAIL(result);
gfx::IShaderProgram::Desc programDesc = {};
- programDesc.slangProgram = linkedProgram.get();
+ programDesc.slangGlobalScope = linkedProgram.get();
auto shaderProgram = device->createProgram(programDesc);
outShaderProgram = shaderProgram;
return SLANG_OK;
diff --git a/examples/triangle/main.cpp b/examples/triangle/main.cpp
index a81a105ab..bd6542b38 100644
--- a/examples/triangle/main.cpp
+++ b/examples/triangle/main.cpp
@@ -181,7 +181,7 @@ gfx::Result loadShaderProgram(
// program representation.
//
gfx::IShaderProgram::Desc programDesc = {};
- programDesc.slangProgram = linkedProgram;
+ programDesc.slangGlobalScope = linkedProgram;
SLANG_RETURN_ON_FAIL(device->createProgram(programDesc, outProgram));
return SLANG_OK;
diff --git a/slang-gfx.h b/slang-gfx.h
index 37eb64935..d0e80d923 100644
--- a/slang-gfx.h
+++ b/slang-gfx.h
@@ -110,9 +110,33 @@ class ITransientResourceHeap;
class IShaderProgram: public ISlangUnknown
{
public:
+ // Defines how linking should be performed for a shader program.
+ enum class LinkingStyle
+ {
+ // Compose all entry-points in a single program, then compile all entry-points together with the same
+ // set of root shader arguments.
+ SingleProgram,
+
+ // Link and compile each entry-point individually, potentially with different specializations.
+ SeparateEntryPointCompilation
+ };
+
struct Desc
{
- slang::IComponentType* slangProgram;
+ // The linking style of this program.
+ LinkingStyle linkingStyle = LinkingStyle::SingleProgram;
+
+ // The global scope or a Slang composite component that represents the entire program.
+ slang::IComponentType* slangGlobalScope;
+
+ // Number of separate entry point components in the `slangEntryPoints` array to link in.
+ // If set to 0, then `slangGlobalScope` must contain Slang EntryPoint components.
+ // If not 0, then `slangGlobalScope` must not contain any EntryPoint components.
+ uint32_t entryPointCount = 0;
+
+ // An array of Slang entry points. The size of the array must be `entryPointCount`.
+ // Each element must define only 1 Slang EntryPoint.
+ slang::IComponentType** slangEntryPoints = nullptr;
};
};
#define SLANG_UUID_IShaderProgram \
@@ -558,8 +582,8 @@ struct ClearValue
struct BufferRange
{
- uint32_t firstElement;
- uint32_t elementCount;
+ uint64_t firstElement;
+ uint64_t elementCount;
};
enum class TextureAspect : uint32_t
@@ -1278,11 +1302,12 @@ struct HitGroupDesc
struct RayTracingPipelineStateDesc
{
IShaderProgram* program = nullptr;
- int32_t hitGroupCount;
- const HitGroupDesc* hitGroups;
- int maxRecursion;
- int maxRayPayloadSize;
- RayTracingPipelineFlags::Enum flags;
+ int32_t hitGroupCount = 0;
+ const HitGroupDesc* hitGroups = nullptr;
+ int maxRecursion = 0;
+ int maxRayPayloadSize = 0;
+ int maxAttributeSizeInBytes = 8;
+ RayTracingPipelineFlags::Enum flags = RayTracingPipelineFlags::None;
};
class IShaderTable : public ISlangUnknown
@@ -2104,12 +2129,16 @@ public:
}
virtual SLANG_NO_THROW Result SLANG_MCALL createBufferView(
- IBufferResource* buffer, IResourceView::Desc const& desc, IResourceView** outView) = 0;
+ IBufferResource* buffer,
+ IBufferResource* counterBuffer,
+ IResourceView::Desc const& desc,
+ IResourceView** outView) = 0;
- inline ComPtr<IResourceView> createBufferView(IBufferResource* buffer, IResourceView::Desc const& desc)
+ inline ComPtr<IResourceView> createBufferView(
+ IBufferResource* buffer, IBufferResource* counterBuffer, IResourceView::Desc const& desc)
{
ComPtr<IResourceView> view;
- SLANG_RETURN_NULL_ON_FAIL(createBufferView(buffer, desc, view.writeRef()));
+ SLANG_RETURN_NULL_ON_FAIL(createBufferView(buffer, counterBuffer, desc, view.writeRef()));
return view;
}
diff --git a/slang.h b/slang.h
index 4d9effad3..cdc0daeab 100644
--- a/slang.h
+++ b/slang.h
@@ -2114,6 +2114,9 @@ extern "C"
SLANG_API char const* spReflectionEntryPoint_getName(
SlangReflectionEntryPoint* entryPoint);
+ SLANG_API char const* spReflectionEntryPoint_getNameOverride(
+ SlangReflectionEntryPoint* entryPoint);
+
SLANG_API unsigned spReflectionEntryPoint_getParameterCount(
SlangReflectionEntryPoint* entryPoint);
@@ -2880,6 +2883,11 @@ namespace slang
return spReflectionEntryPoint_getName((SlangReflectionEntryPoint*) this);
}
+ char const* getNameOverride()
+ {
+ return spReflectionEntryPoint_getNameOverride((SlangReflectionEntryPoint*)this);
+ }
+
unsigned getParameterCount()
{
return spReflectionEntryPoint_getParameterCount((SlangReflectionEntryPoint*) this);
diff --git a/slang.sln b/slang.sln
index 8b7bf1cf5..b4b30eeee 100644
--- a/slang.sln
+++ b/slang.sln
@@ -35,10 +35,6 @@ Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "gpu-printing", "build\visua
EndProject
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "hello-world", "build\visual-studio\hello-world\hello-world.vcxproj", "{010BE414-ED5B-CF56-16C0-BD18027062C0}"
EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "heterogeneous-first-gen", "build\visual-studio\heterogeneous-hello-world\heterogeneous-first-gen.vcxproj", "{3E8C6F8B-AAC3-B722-B3CD-1B461F84DE1B}"
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "heterogeneous-hello-world", "build\visual-studio\heterogeneous-hello-world\heterogeneous-hello-world.vcxproj", "{150CAA5A-0177-6A66-AA92-CFCB96DC2D49}"
-EndProject
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "model-viewer", "build\visual-studio\model-viewer\model-viewer.vcxproj", "{2F8724C6-1BC3-2730-84D5-3F277030D04A}"
EndProject
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "ray-tracing", "build\visual-studio\ray-tracing\ray-tracing.vcxproj", "{71AC0F50-5DFD-FA91-8661-E95372118EFB}"
@@ -271,30 +267,6 @@ Global
{010BE414-ED5B-CF56-16C0-BD18027062C0}.Release|Win32.Build.0 = Release|Win32
{010BE414-ED5B-CF56-16C0-BD18027062C0}.Release|x64.ActiveCfg = Release|x64
{010BE414-ED5B-CF56-16C0-BD18027062C0}.Release|x64.Build.0 = Release|x64
- {3E8C6F8B-AAC3-B722-B3CD-1B461F84DE1B}.Debug|aarch64.ActiveCfg = Debug aarch64|ARM
- {3E8C6F8B-AAC3-B722-B3CD-1B461F84DE1B}.Debug|aarch64.Build.0 = Debug aarch64|ARM
- {3E8C6F8B-AAC3-B722-B3CD-1B461F84DE1B}.Debug|Win32.ActiveCfg = Debug|Win32
- {3E8C6F8B-AAC3-B722-B3CD-1B461F84DE1B}.Debug|Win32.Build.0 = Debug|Win32
- {3E8C6F8B-AAC3-B722-B3CD-1B461F84DE1B}.Debug|x64.ActiveCfg = Debug|x64
- {3E8C6F8B-AAC3-B722-B3CD-1B461F84DE1B}.Debug|x64.Build.0 = Debug|x64
- {3E8C6F8B-AAC3-B722-B3CD-1B461F84DE1B}.Release|aarch64.ActiveCfg = Release aarch64|ARM
- {3E8C6F8B-AAC3-B722-B3CD-1B461F84DE1B}.Release|aarch64.Build.0 = Release aarch64|ARM
- {3E8C6F8B-AAC3-B722-B3CD-1B461F84DE1B}.Release|Win32.ActiveCfg = Release|Win32
- {3E8C6F8B-AAC3-B722-B3CD-1B461F84DE1B}.Release|Win32.Build.0 = Release|Win32
- {3E8C6F8B-AAC3-B722-B3CD-1B461F84DE1B}.Release|x64.ActiveCfg = Release|x64
- {3E8C6F8B-AAC3-B722-B3CD-1B461F84DE1B}.Release|x64.Build.0 = Release|x64
- {150CAA5A-0177-6A66-AA92-CFCB96DC2D49}.Debug|aarch64.ActiveCfg = Debug aarch64|ARM
- {150CAA5A-0177-6A66-AA92-CFCB96DC2D49}.Debug|aarch64.Build.0 = Debug aarch64|ARM
- {150CAA5A-0177-6A66-AA92-CFCB96DC2D49}.Debug|Win32.ActiveCfg = Debug|Win32
- {150CAA5A-0177-6A66-AA92-CFCB96DC2D49}.Debug|Win32.Build.0 = Debug|Win32
- {150CAA5A-0177-6A66-AA92-CFCB96DC2D49}.Debug|x64.ActiveCfg = Debug|x64
- {150CAA5A-0177-6A66-AA92-CFCB96DC2D49}.Debug|x64.Build.0 = Debug|x64
- {150CAA5A-0177-6A66-AA92-CFCB96DC2D49}.Release|aarch64.ActiveCfg = Release aarch64|ARM
- {150CAA5A-0177-6A66-AA92-CFCB96DC2D49}.Release|aarch64.Build.0 = Release aarch64|ARM
- {150CAA5A-0177-6A66-AA92-CFCB96DC2D49}.Release|Win32.ActiveCfg = Release|Win32
- {150CAA5A-0177-6A66-AA92-CFCB96DC2D49}.Release|Win32.Build.0 = Release|Win32
- {150CAA5A-0177-6A66-AA92-CFCB96DC2D49}.Release|x64.ActiveCfg = Release|x64
- {150CAA5A-0177-6A66-AA92-CFCB96DC2D49}.Release|x64.Build.0 = Release|x64
{2F8724C6-1BC3-2730-84D5-3F277030D04A}.Debug|aarch64.ActiveCfg = Debug aarch64|ARM
{2F8724C6-1BC3-2730-84D5-3F277030D04A}.Debug|aarch64.Build.0 = Debug aarch64|ARM
{2F8724C6-1BC3-2730-84D5-3F277030D04A}.Debug|Win32.ActiveCfg = Debug|Win32
@@ -493,8 +465,6 @@ Global
{37BED5B5-23FA-D81F-8C0C-F1167867813A} = {EB5FC2C6-D72D-B6CC-C0C1-26F3AC2E9231}
{57C81DD3-4304-213D-AC16-39349871C957} = {EB5FC2C6-D72D-B6CC-C0C1-26F3AC2E9231}
{010BE414-ED5B-CF56-16C0-BD18027062C0} = {EB5FC2C6-D72D-B6CC-C0C1-26F3AC2E9231}
- {3E8C6F8B-AAC3-B722-B3CD-1B461F84DE1B} = {EB5FC2C6-D72D-B6CC-C0C1-26F3AC2E9231}
- {150CAA5A-0177-6A66-AA92-CFCB96DC2D49} = {EB5FC2C6-D72D-B6CC-C0C1-26F3AC2E9231}
{2F8724C6-1BC3-2730-84D5-3F277030D04A} = {EB5FC2C6-D72D-B6CC-C0C1-26F3AC2E9231}
{71AC0F50-5DFD-FA91-8661-E95372118EFB} = {EB5FC2C6-D72D-B6CC-C0C1-26F3AC2E9231}
{17BA8E32-034E-84DA-6C12-DE8E58C5BECC} = {EB5FC2C6-D72D-B6CC-C0C1-26F3AC2E9231}
diff --git a/source/core/slang-chunked-list.h b/source/core/slang-chunked-list.h
index fced9834a..36f97cedd 100644
--- a/source/core/slang-chunked-list.h
+++ b/source/core/slang-chunked-list.h
@@ -243,6 +243,7 @@ private:
{
auto nextChunk = chunk->next;
freeChunk(chunk);
+ chunk = nextChunk;
}
m_firstChunk.next = 0;
m_firstChunk.size = 0;
diff --git a/source/slang/slang-parameter-binding.cpp b/source/slang/slang-parameter-binding.cpp
index 48e637047..abbc010f8 100644
--- a/source/slang/slang-parameter-binding.cpp
+++ b/source/slang/slang-parameter-binding.cpp
@@ -2477,6 +2477,7 @@ static void removePerEntryPointParameterKinds(
static RefPtr<EntryPointLayout> collectEntryPointParameters(
ParameterBindingContext* context,
EntryPoint* entryPoint,
+ String entryPointNameOverride,
EntryPoint::EntryPointSpecializationInfo* specializationInfo)
{
auto astBuilder = context->getASTBuilder();
@@ -2487,6 +2488,7 @@ static RefPtr<EntryPointLayout> collectEntryPointParameters(
RefPtr<EntryPointLayout> entryPointLayout = new EntryPointLayout();
entryPointLayout->profile = entryPoint->getProfile();
entryPointLayout->name = entryPoint->getName();
+ entryPointLayout->nameOverride = entryPointNameOverride;
// The entry point layout must be added to the output
// program layout so that it can be accessed by reflection.
@@ -2836,6 +2838,7 @@ struct CollectParametersVisitor : ComponentTypeVisitor
{}
ParameterBindingContext* m_context;
+ String m_currentEntryPointNameOverride;
void visitComposite(CompositeComponentType* composite, CompositeComponentType::CompositeSpecializationInfo* specializationInfo) SLANG_OVERRIDE
{
@@ -2892,15 +2895,18 @@ struct CollectParametersVisitor : ComponentTypeVisitor
ParameterBindingContext contextData = *m_context;
auto context = &contextData;
context->stage = entryPoint->getStage();
-
- collectEntryPointParameters(context, entryPoint, specializationInfo);
+ collectEntryPointParameters(
+ context, entryPoint, m_currentEntryPointNameOverride, specializationInfo);
}
void visitRenamedEntryPoint(
RenamedEntryPointComponentType* renamedEntryPoint,
EntryPoint::EntryPointSpecializationInfo* specializationInfo) SLANG_OVERRIDE
{
+ auto lastNameOverride = m_currentEntryPointNameOverride;
+ m_currentEntryPointNameOverride = renamedEntryPoint->getEntryPointNameOverride(0);
renamedEntryPoint->getBase()->acceptVisitor(this, specializationInfo);
+ m_currentEntryPointNameOverride = lastNameOverride;
}
void visitModule(Module* module, Module::ModuleSpecializationInfo* specializationInfo) SLANG_OVERRIDE
diff --git a/source/slang/slang-reflection-api.cpp b/source/slang/slang-reflection-api.cpp
index 17ceb6842..714dc292f 100644
--- a/source/slang/slang-reflection-api.cpp
+++ b/source/slang/slang-reflection-api.cpp
@@ -728,6 +728,8 @@ SLANG_API SlangReflectionType * spReflection_FindTypeByName(SlangReflection * re
try
{
Type* result = program->getTypeFromString(name, &sink);
+ if (as<ErrorType>(result))
+ return nullptr;
return (SlangReflectionType*)result;
}
catch( ... )
@@ -2567,6 +2569,19 @@ SLANG_API char const* spReflectionEntryPoint_getName(
return entryPointLayout ? getCstr(entryPointLayout->name) : nullptr;
}
+SLANG_API char const* spReflectionEntryPoint_getNameOverride(SlangReflectionEntryPoint* inEntryPoint)
+{
+ auto entryPointLayout = convert(inEntryPoint);
+ if (entryPointLayout)
+ {
+ if (entryPointLayout->nameOverride.getLength())
+ return entryPointLayout->nameOverride.getBuffer();
+ else
+ return getCstr(entryPointLayout->name);
+ }
+ return nullptr;
+}
+
SLANG_API unsigned spReflectionEntryPoint_getParameterCount(
SlangReflectionEntryPoint* inEntryPoint)
{
diff --git a/source/slang/slang-type-layout.h b/source/slang/slang-type-layout.h
index 8c50b4eb3..82d333fa9 100644
--- a/source/slang/slang-type-layout.h
+++ b/source/slang/slang-type-layout.h
@@ -761,6 +761,9 @@ public:
// The name of the entry point. Always available even if entryPoint is nullptr (for example when it came from a library)
Name* name = nullptr;
+ // The overrided name of the entry point.
+ String nameOverride;
+
// Layout for any results of the entry point
RefPtr<VarLayout> resultLayout;
diff --git a/tools/gfx-unit-test/buffer-barrier-test.cpp b/tools/gfx-unit-test/buffer-barrier-test.cpp
index fb3d62f8c..b2692f6fd 100644
--- a/tools/gfx-unit-test/buffer-barrier-test.cpp
+++ b/tools/gfx-unit-test/buffer-barrier-test.cpp
@@ -48,7 +48,8 @@ namespace gfx_test
viewDesc.type = unorderedAccess ? IResourceView::Type::UnorderedAccess : IResourceView::Type::ShaderResource;
viewDesc.format = Format::Unknown;
viewDesc.bufferElementSize = sizeof(float);
- GFX_CHECK_CALL_ABORT(device->createBufferView(outBuffer.buffer, viewDesc, outBuffer.view.writeRef()));
+ GFX_CHECK_CALL_ABORT(device->createBufferView(
+ outBuffer.buffer, nullptr, viewDesc, outBuffer.view.writeRef()));
}
void barrierTestImpl(IDevice* device, UnitTestContext* context)
diff --git a/tools/gfx-unit-test/compute-smoke.cpp b/tools/gfx-unit-test/compute-smoke.cpp
index 185e8aa99..68925f1e0 100644
--- a/tools/gfx-unit-test/compute-smoke.cpp
+++ b/tools/gfx-unit-test/compute-smoke.cpp
@@ -51,7 +51,8 @@ namespace gfx_test
IResourceView::Desc viewDesc = {};
viewDesc.type = IResourceView::Type::UnorderedAccess;
viewDesc.format = Format::Unknown;
- GFX_CHECK_CALL_ABORT(device->createBufferView(numbersBuffer, viewDesc, bufferView.writeRef()));
+ GFX_CHECK_CALL_ABORT(
+ device->createBufferView(numbersBuffer, nullptr, viewDesc, bufferView.writeRef()));
// We have done all the set up work, now it is time to start recording a command buffer for
// GPU execution.
diff --git a/tools/gfx-unit-test/create-buffer-from-handle.cpp b/tools/gfx-unit-test/create-buffer-from-handle.cpp
index 22612dbf0..4e2261465 100644
--- a/tools/gfx-unit-test/create-buffer-from-handle.cpp
+++ b/tools/gfx-unit-test/create-buffer-from-handle.cpp
@@ -57,7 +57,8 @@ namespace gfx_test
IResourceView::Desc viewDesc = {};
viewDesc.type = IResourceView::Type::UnorderedAccess;
viewDesc.format = Format::Unknown;
- GFX_CHECK_CALL_ABORT(device->createBufferView(numbersBuffer, viewDesc, bufferView.writeRef()));
+ GFX_CHECK_CALL_ABORT(
+ device->createBufferView(numbersBuffer, nullptr, viewDesc, bufferView.writeRef()));
// We have done all the set up work, now it is time to start recording a command buffer for
// GPU execution.
diff --git a/tools/gfx-unit-test/existing-device-handle-test.cpp b/tools/gfx-unit-test/existing-device-handle-test.cpp
index cf13fe090..d6f66af84 100644
--- a/tools/gfx-unit-test/existing-device-handle-test.cpp
+++ b/tools/gfx-unit-test/existing-device-handle-test.cpp
@@ -51,7 +51,8 @@ namespace gfx_test
IResourceView::Desc viewDesc = {};
viewDesc.type = IResourceView::Type::UnorderedAccess;
viewDesc.format = Format::Unknown;
- GFX_CHECK_CALL_ABORT(device->createBufferView(numbersBuffer, viewDesc, bufferView.writeRef()));
+ GFX_CHECK_CALL_ABORT(
+ device->createBufferView(numbersBuffer, nullptr, viewDesc, bufferView.writeRef()));
// We have done all the set up work, now it is time to start recording a command buffer for
// GPU execution.
diff --git a/tools/gfx-unit-test/format-unit-tests.cpp b/tools/gfx-unit-test/format-unit-tests.cpp
index 55aa2768b..1a885174f 100644
--- a/tools/gfx-unit-test/format-unit-tests.cpp
+++ b/tools/gfx-unit-test/format-unit-tests.cpp
@@ -153,7 +153,8 @@ namespace gfx_test
IResourceView::Desc viewDesc = {};
viewDesc.type = IResourceView::Type::UnorderedAccess;
viewDesc.format = Format::Unknown;
- GFX_CHECK_CALL_ABORT(device->createBufferView(outBuffer, viewDesc, bufferView.writeRef()));
+ GFX_CHECK_CALL_ABORT(
+ device->createBufferView(outBuffer, nullptr, viewDesc, bufferView.writeRef()));
return bufferView;
}
diff --git a/tools/gfx-unit-test/gfx-test-util.cpp b/tools/gfx-unit-test/gfx-test-util.cpp
index c95c3d0e5..1133e3842 100644
--- a/tools/gfx-unit-test/gfx-test-util.cpp
+++ b/tools/gfx-unit-test/gfx-test-util.cpp
@@ -57,7 +57,7 @@ namespace gfx_test
slangReflection = composedProgram->getLayout();
gfx::IShaderProgram::Desc programDesc = {};
- programDesc.slangProgram = composedProgram.get();
+ programDesc.slangGlobalScope = composedProgram.get();
auto shaderProgram = device->createProgram(programDesc);
@@ -105,7 +105,7 @@ namespace gfx_test
slangReflection = composedProgram->getLayout();
gfx::IShaderProgram::Desc programDesc = {};
- programDesc.slangProgram = composedProgram.get();
+ programDesc.slangGlobalScope = composedProgram.get();
auto shaderProgram = device->createProgram(programDesc);
diff --git a/tools/gfx-unit-test/mutable-shader-object.cpp b/tools/gfx-unit-test/mutable-shader-object.cpp
index 28ec8fb45..cc9707643 100644
--- a/tools/gfx-unit-test/mutable-shader-object.cpp
+++ b/tools/gfx-unit-test/mutable-shader-object.cpp
@@ -51,7 +51,8 @@ namespace gfx_test
IResourceView::Desc viewDesc = {};
viewDesc.type = IResourceView::Type::UnorderedAccess;
viewDesc.format = Format::Unknown;
- GFX_CHECK_CALL_ABORT(device->createBufferView(numbersBuffer, viewDesc, bufferView.writeRef()));
+ GFX_CHECK_CALL_ABORT(
+ device->createBufferView(numbersBuffer, nullptr, viewDesc, bufferView.writeRef()));
{
slang::TypeReflection* addTransformerType =
diff --git a/tools/gfx-unit-test/nested-parameter-block.cpp b/tools/gfx-unit-test/nested-parameter-block.cpp
index 2917218f1..b21b0bcf2 100644
--- a/tools/gfx-unit-test/nested-parameter-block.cpp
+++ b/tools/gfx-unit-test/nested-parameter-block.cpp
@@ -70,7 +70,7 @@ namespace gfx_test
srvDesc.bufferElementSize = sizeof(uint32_t) * 4;
srvDesc.bufferRange.elementCount = 4;
srvDesc.bufferRange.firstElement = 0;
- srvs.add(device->createBufferView(srvBuffers[i], srvDesc));
+ srvs.add(device->createBufferView(srvBuffers[i], nullptr, srvDesc));
}
Slang::ComPtr<IBufferResource> resultBuffer =
createBuffer(device, 0, gfx::ResourceState::UnorderedAccess);
@@ -82,7 +82,7 @@ namespace gfx_test
resultBufferViewDesc.bufferRange.firstElement = 0;
Slang::ComPtr<IResourceView> resultBufferView;
SLANG_CHECK(SLANG_SUCCEEDED(device->createBufferView(
- resultBuffer, resultBufferViewDesc, resultBufferView.writeRef())));
+ resultBuffer, nullptr, resultBufferViewDesc, resultBufferView.writeRef())));
Slang::ComPtr<IShaderObject> materialObject;
SLANG_CHECK(SLANG_SUCCEEDED(device->createMutableShaderObject(
diff --git a/tools/gfx-unit-test/root-mutable-shader-object.cpp b/tools/gfx-unit-test/root-mutable-shader-object.cpp
index 43c5fbd1f..10079b62a 100644
--- a/tools/gfx-unit-test/root-mutable-shader-object.cpp
+++ b/tools/gfx-unit-test/root-mutable-shader-object.cpp
@@ -51,7 +51,8 @@ namespace gfx_test
IResourceView::Desc viewDesc = {};
viewDesc.type = IResourceView::Type::UnorderedAccess;
viewDesc.format = Format::Unknown;
- GFX_CHECK_CALL_ABORT(device->createBufferView(numbersBuffer, viewDesc, bufferView.writeRef()));
+ GFX_CHECK_CALL_ABORT(
+ device->createBufferView(numbersBuffer, nullptr, viewDesc, bufferView.writeRef()));
ComPtr<IShaderObject> rootObject;
device->createMutableRootShaderObject(shaderProgram, rootObject.writeRef());
diff --git a/tools/gfx-unit-test/shared-buffers-tests.cpp b/tools/gfx-unit-test/shared-buffers-tests.cpp
index 915da798b..ccd223fc0 100644
--- a/tools/gfx-unit-test/shared-buffers-tests.cpp
+++ b/tools/gfx-unit-test/shared-buffers-tests.cpp
@@ -70,7 +70,8 @@ namespace gfx_test
IResourceView::Desc viewDesc = {};
viewDesc.type = IResourceView::Type::UnorderedAccess;
viewDesc.format = Format::Unknown;
- GFX_CHECK_CALL_ABORT(dstDevice->createBufferView(dstBuffer, viewDesc, bufferView.writeRef()));
+ GFX_CHECK_CALL_ABORT(
+ dstDevice->createBufferView(dstBuffer, nullptr, viewDesc, bufferView.writeRef()));
{
ICommandQueue::Desc queueDesc = { ICommandQueue::QueueType::Graphics };
diff --git a/tools/gfx-unit-test/shared-textures-tests.cpp b/tools/gfx-unit-test/shared-textures-tests.cpp
index b83f58a78..831296c72 100644
--- a/tools/gfx-unit-test/shared-textures-tests.cpp
+++ b/tools/gfx-unit-test/shared-textures-tests.cpp
@@ -130,7 +130,8 @@ namespace gfx_test
IResourceView::Desc viewDesc = {};
viewDesc.type = IResourceView::Type::UnorderedAccess;
viewDesc.format = Format::Unknown;
- GFX_CHECK_CALL_ABORT(device->createBufferView(outBuffer, viewDesc, bufferView.writeRef()));
+ GFX_CHECK_CALL_ABORT(
+ device->createBufferView(outBuffer, nullptr, viewDesc, bufferView.writeRef()));
return bufferView;
}
diff --git a/tools/gfx/cpu/render-cpu.cpp b/tools/gfx/cpu/render-cpu.cpp
index 38b72e28b..a20ed3ebe 100644
--- a/tools/gfx/cpu/render-cpu.cpp
+++ b/tools/gfx/cpu/render-cpu.cpp
@@ -1091,7 +1091,7 @@ private:
ComPtr<ISlangSharedLibrary> sharedLibrary;
ComPtr<ISlangBlob> diagnostics;
- auto compileResult = program->slangProgram->getEntryPointHostCallable(
+ auto compileResult = program->slangGlobalScope->getEntryPointHostCallable(
entryPointIndex, targetIndex, sharedLibrary.writeRef(), diagnostics.writeRef());
if (diagnostics)
{
@@ -1205,7 +1205,10 @@ public:
}
virtual SLANG_NO_THROW Result SLANG_MCALL createBufferView(
- IBufferResource* inBuffer, IResourceView::Desc const& desc, IResourceView** outView) override
+ IBufferResource* inBuffer,
+ IBufferResource* counterBuffer,
+ IResourceView::Desc const& desc,
+ IResourceView** outView) override
{
auto buffer = static_cast<CPUBufferResource*>(inBuffer);
RefPtr<CPUBufferView> view = new CPUBufferView(desc, buffer);
@@ -1266,15 +1269,11 @@ public:
ISlangBlob** outDiagnosticBlob) override
{
RefPtr<CPUShaderProgram> cpuProgram = new CPUShaderProgram();
-
- // TODO: stuff?
-
- auto slangProgram = desc.slangProgram;
- if( slangProgram )
+ cpuProgram->init(desc);
+ auto slangGlobalScope = cpuProgram->linkedProgram;
+ if( slangGlobalScope )
{
- cpuProgram->slangProgram = slangProgram;
-
- auto slangProgramLayout = slangProgram->getLayout();
+ auto slangProgramLayout = slangGlobalScope->getLayout();
if(!slangProgramLayout)
return SLANG_FAIL;
diff --git a/tools/gfx/cuda/render-cuda.cpp b/tools/gfx/cuda/render-cuda.cpp
index cb8f779f4..bacaa42ee 100644
--- a/tools/gfx/cuda/render-cuda.cpp
+++ b/tools/gfx/cuda/render-cuda.cpp
@@ -2112,7 +2112,10 @@ public:
}
virtual SLANG_NO_THROW Result SLANG_MCALL createBufferView(
- IBufferResource* buffer, IResourceView::Desc const& desc, IResourceView** outView) override
+ IBufferResource* buffer,
+ IBufferResource* counterBuffer,
+ IResourceView::Desc const& desc,
+ IResourceView** outView) override
{
RefPtr<CUDAResourceView> view = new CUDAResourceView();
view->m_desc = desc;
@@ -2181,18 +2184,18 @@ public:
// don't actually create any kernels. This program will be specialized later when we know
// the shader object bindings.
RefPtr<CUDAShaderProgram> cudaProgram = new CUDAShaderProgram();
- cudaProgram->slangProgram = desc.slangProgram;
+ cudaProgram->init(desc);
cudaProgram->cudaContext = m_context;
- if (desc.slangProgram->getSpecializationParamCount() != 0)
+ if (desc.slangGlobalScope->getSpecializationParamCount() != 0)
{
- cudaProgram->layout = new CUDAProgramLayout(this, desc.slangProgram->getLayout());
+ cudaProgram->layout = new CUDAProgramLayout(this, desc.slangGlobalScope->getLayout());
returnComPtr(outProgram, cudaProgram);
return SLANG_OK;
}
ComPtr<ISlangBlob> kernelCode;
ComPtr<ISlangBlob> diagnostics;
- auto compileResult = desc.slangProgram->getEntryPointCode(
+ auto compileResult = desc.slangGlobalScope->getEntryPointCode(
(SlangInt)0, 0, kernelCode.writeRef(), diagnostics.writeRef());
if (diagnostics)
{
@@ -2206,16 +2209,16 @@ public:
SLANG_RETURN_ON_FAIL(compileResult);
SLANG_CUDA_RETURN_ON_FAIL(cuModuleLoadData(&cudaProgram->cudaModule, kernelCode->getBufferPointer()));
- cudaProgram->kernelName = desc.slangProgram->getLayout()->getEntryPointByIndex(0)->getName();
+ cudaProgram->kernelName = desc.slangGlobalScope->getLayout()->getEntryPointByIndex(0)->getName();
SLANG_CUDA_RETURN_ON_FAIL(cuModuleGetFunction(
&cudaProgram->cudaKernel, cudaProgram->cudaModule, cudaProgram->kernelName.getBuffer()));
- auto slangProgram = desc.slangProgram;
- if( slangProgram )
+ auto slangGlobalScope = desc.slangGlobalScope;
+ if( slangGlobalScope )
{
- cudaProgram->slangProgram = slangProgram;
+ cudaProgram->slangGlobalScope = slangGlobalScope;
- auto slangProgramLayout = slangProgram->getLayout();
+ auto slangProgramLayout = slangGlobalScope->getLayout();
if(!slangProgramLayout)
return SLANG_FAIL;
diff --git a/tools/gfx/d3d11/render-d3d11.cpp b/tools/gfx/d3d11/render-d3d11.cpp
index 2e3963c30..04399700e 100644
--- a/tools/gfx/d3d11/render-d3d11.cpp
+++ b/tools/gfx/d3d11/render-d3d11.cpp
@@ -93,6 +93,7 @@ public:
virtual SLANG_NO_THROW Result SLANG_MCALL createBufferView(
IBufferResource* buffer,
+ IBufferResource* counterBuffer,
IResourceView::Desc const& desc,
IResourceView** outView) override;
@@ -3008,7 +3009,11 @@ Result D3D11Device::createTextureView(ITextureResource* texture, IResourceView::
}
}
-Result D3D11Device::createBufferView(IBufferResource* buffer, IResourceView::Desc const& desc, IResourceView** outView)
+Result D3D11Device::createBufferView(
+ IBufferResource* buffer,
+ IBufferResource* counterBuffer,
+ IResourceView::Desc const& desc,
+ IResourceView** outView)
{
auto resourceImpl = (BufferResourceImpl*) buffer;
auto resourceDesc = *resourceImpl->getDesc();
@@ -3483,21 +3488,21 @@ void D3D11Device::drawIndexedInstanced(
Result D3D11Device::createProgram(
const IShaderProgram::Desc& desc, IShaderProgram** outProgram, ISlangBlob** outDiagnosticBlob)
{
- SLANG_ASSERT(desc.slangProgram);
+ SLANG_ASSERT(desc.slangGlobalScope);
- if (desc.slangProgram->getSpecializationParamCount() != 0)
+ if (desc.slangGlobalScope->getSpecializationParamCount() != 0)
{
// For a specializable program, we don't invoke any actual slang compilation yet.
RefPtr<ShaderProgramImpl> shaderProgram = new ShaderProgramImpl();
- shaderProgram->slangProgram = desc.slangProgram;
+ shaderProgram->init(desc);
returnComPtr(outProgram, shaderProgram);
return SLANG_OK;
}
// If the program is already specialized, compile and create shader kernels now.
SlangInt targetIndex = 0;
- auto slangProgram = desc.slangProgram;
- auto programLayout = slangProgram->getLayout(targetIndex);
+ auto slangGlobalScope = desc.slangGlobalScope;
+ auto programLayout = slangGlobalScope->getLayout(targetIndex);
if (!programLayout)
return SLANG_FAIL;
SlangUInt entryPointCount = programLayout->getEntryPointCount();
@@ -3505,7 +3510,7 @@ Result D3D11Device::createProgram(
return SLANG_FAIL;
RefPtr<ShaderProgramImpl> shaderProgram = new ShaderProgramImpl();
- shaderProgram->slangProgram = desc.slangProgram;
+ shaderProgram->slangGlobalScope = desc.slangGlobalScope;
ScopeNVAPI scopeNVAPI;
SLANG_RETURN_ON_FAIL(scopeNVAPI.init(this, 0));
@@ -3514,7 +3519,7 @@ Result D3D11Device::createProgram(
ComPtr<ISlangBlob> kernelCode;
ComPtr<ISlangBlob> diagnostics;
- auto compileResult = slangProgram->getEntryPointCode(
+ auto compileResult = slangGlobalScope->getEntryPointCode(
(SlangInt)i, 0, kernelCode.writeRef(), diagnostics.writeRef());
if (diagnostics)
@@ -3728,7 +3733,7 @@ Result D3D11Device::createRootShaderObject(IShaderProgram* program, ShaderObject
RefPtr<RootShaderObjectImpl> shaderObject;
RefPtr<RootShaderObjectLayoutImpl> rootLayout;
SLANG_RETURN_ON_FAIL(RootShaderObjectLayoutImpl::create(
- this, programImpl->slangProgram, programImpl->slangProgram->getLayout(), rootLayout.writeRef()));
+ this, programImpl->slangGlobalScope, programImpl->slangGlobalScope->getLayout(), rootLayout.writeRef()));
SLANG_RETURN_ON_FAIL(RootShaderObjectImpl::create(
this, rootLayout.Ptr(), shaderObject.writeRef()));
returnRefPtrMove(outObject, shaderObject);
diff --git a/tools/gfx/d3d12/descriptor-heap-d3d12.h b/tools/gfx/d3d12/descriptor-heap-d3d12.h
index 26b9c6a16..2718f09e1 100644
--- a/tools/gfx/d3d12/descriptor-heap-d3d12.h
+++ b/tools/gfx/d3d12/descriptor-heap-d3d12.h
@@ -91,8 +91,7 @@ class D3D12GeneralDescriptorHeap : public Slang::RefObject
Slang::VirtualObjectPool m_allocator;
public:
- D3D12GeneralDescriptorHeap()
- {}
+ int getSize() { return m_chunkSize; }
Slang::Result init(ID3D12Device* device, int chunkSize, D3D12_DESCRIPTOR_HEAP_TYPE type, D3D12_DESCRIPTOR_HEAP_FLAGS flag)
{
@@ -151,16 +150,140 @@ public:
}
};
+class D3D12GeneralExpandingDescriptorHeap : public Slang::RefObject
+{
+ ID3D12Device* m_device;
+ D3D12_DESCRIPTOR_HEAP_TYPE m_type;
+ D3D12_DESCRIPTOR_HEAP_FLAGS m_flag;
+ int m_chunkSize;
+ Slang::List<Slang::RefPtr<D3D12GeneralDescriptorHeap>> m_subHeaps;
+ Slang::List<int> m_subHeapStartingIndex;
+
+public:
+ Slang::Result newSubHeap()
+ {
+ Slang::RefPtr<D3D12GeneralDescriptorHeap> subHeap = new D3D12GeneralDescriptorHeap();
+ SLANG_RETURN_ON_FAIL(subHeap->init(m_device, m_chunkSize, m_type, m_flag));
+ m_subHeaps.add(subHeap);
+ if (m_subHeapStartingIndex.getCount())
+ {
+ m_subHeapStartingIndex.add(m_subHeapStartingIndex.getLast() + m_subHeaps.getLast()->getSize());
+ }
+ else
+ {
+ m_subHeapStartingIndex.add(0);
+ }
+ return SLANG_OK;
+ }
+
+ int getSubHeapIndex(int descriptorIndex) const
+ {
+ Slang::Index l = 0;
+ Slang::Index r = m_subHeapStartingIndex.getCount();
+ while (l < r - 1)
+ {
+ Slang::Index m = l + (r - l) / 2;
+ if (m_subHeapStartingIndex[m] < descriptorIndex)
+ l = m;
+ else if (m_subHeapStartingIndex[m] > descriptorIndex)
+ r = m;
+ else
+ return (int)m;
+ }
+ assert(
+ m_subHeapStartingIndex[l] <= descriptorIndex &&
+ m_subHeapStartingIndex[l] + m_subHeaps[l]->getSize() > descriptorIndex);
+ return (int)l;
+ }
+
+ Slang::Result init(
+ ID3D12Device* device,
+ int chunkSize,
+ D3D12_DESCRIPTOR_HEAP_TYPE type,
+ D3D12_DESCRIPTOR_HEAP_FLAGS flag)
+ {
+ m_device = device;
+ m_chunkSize = chunkSize;
+ m_type = type;
+ m_flag = flag;
+
+ return newSubHeap();
+ }
+
+ SLANG_FORCE_INLINE D3D12_CPU_DESCRIPTOR_HANDLE getCpuHandle(int index) const
+ {
+ auto subHeapIndex = getSubHeapIndex(index);
+ return m_subHeaps[subHeapIndex]->getCpuHandle(index - m_subHeapStartingIndex[subHeapIndex]);
+ }
+
+ SLANG_FORCE_INLINE D3D12_GPU_DESCRIPTOR_HANDLE getGpuHandle(int index) const
+ {
+ auto subHeapIndex = getSubHeapIndex(index);
+ return m_subHeaps[subHeapIndex]->getGpuHandle(index - m_subHeapStartingIndex[subHeapIndex]);
+ }
+
+ int allocate(int count)
+ {
+ auto result = m_subHeaps.getLast()->allocate(count);
+ if (result == -1)
+ {
+ newSubHeap();
+ return allocate(count);
+ }
+ return result + m_subHeapStartingIndex.getLast();
+ }
+
+ Slang::Result allocate(D3D12Descriptor* outDescriptor)
+ {
+ int index = allocate(1);
+ if (index < 0)
+ {
+ assert(!"descriptor allocation failed");
+ return SLANG_FAIL;
+ }
+
+ D3D12Descriptor descriptor;
+ descriptor.cpuHandle = getCpuHandle(index);
+
+ *outDescriptor = descriptor;
+ return SLANG_OK;
+ }
+
+ void free(int index, int count)
+ {
+ auto subHeapIndex = getSubHeapIndex(index);
+ m_subHeaps[subHeapIndex]->free(index - m_subHeapStartingIndex[subHeapIndex], count);
+ }
+
+ void free(D3D12Descriptor descriptor)
+ {
+ for (auto& subHeap : m_subHeaps)
+ {
+ if (descriptor.cpuHandle.ptr >= subHeap->getCpuHandle(0).ptr)
+ {
+ auto subIndex = descriptor.cpuHandle.ptr - subHeap->getCpuHandle(0).ptr;
+ if (subIndex < subHeap->getSize())
+ {
+ subHeap->free(descriptor);
+ break;
+ }
+ }
+
+ }
+ }
+};
+
struct DescriptorHeapReference
{
enum class Type
{
- Linear, General
+ Linear, General, ExpandingGeneral
};
union Ptr
{
D3D12DescriptorHeap* linearHeap;
D3D12GeneralDescriptorHeap* generalHeap;
+ D3D12GeneralExpandingDescriptorHeap* generalExpandingHeap;
};
Type type;
Ptr ptr;
@@ -175,14 +298,21 @@ struct DescriptorHeapReference
type = Type::General;
ptr.generalHeap = heap;
}
+ DescriptorHeapReference(D3D12GeneralExpandingDescriptorHeap* heap)
+ {
+ type = Type::ExpandingGeneral;
+ ptr.generalExpandingHeap = heap;
+ }
D3D12_CPU_DESCRIPTOR_HANDLE getCpuHandle(int index) const
{
switch (type)
{
case Type::Linear:
return ptr.linearHeap->getCpuHandle(index);
- default:
+ case Type::General:
return ptr.generalHeap->getCpuHandle(index);
+ default:
+ return ptr.generalExpandingHeap->getCpuHandle(index);
}
}
D3D12_GPU_DESCRIPTOR_HANDLE getGpuHandle(int index) const
@@ -191,8 +321,10 @@ struct DescriptorHeapReference
{
case Type::Linear:
return ptr.linearHeap->getGpuHandle(index);
- default:
+ case Type::General:
return ptr.generalHeap->getGpuHandle(index);
+ default:
+ return ptr.generalExpandingHeap->getGpuHandle(index);
}
}
int allocate(int numDescriptors)
@@ -201,8 +333,10 @@ struct DescriptorHeapReference
{
case Type::Linear:
return ptr.linearHeap->allocate(numDescriptors);
- default:
+ case Type::General:
return ptr.generalHeap->allocate(numDescriptors);
+ default:
+ return ptr.generalExpandingHeap->allocate(numDescriptors);
}
}
void free(int index, int count)
@@ -212,8 +346,10 @@ struct DescriptorHeapReference
case Type::Linear:
SLANG_ASSERT(!"Linear heap does not support free().");
break;
- default:
+ case Type::General:
return ptr.generalHeap->free(index, count);
+ default:
+ return ptr.generalExpandingHeap->free(index, count);
}
}
void freeIfSupported(int index, int count)
@@ -222,8 +358,10 @@ struct DescriptorHeapReference
{
case Type::Linear:
return;
- default:
+ case Type::General:
return ptr.generalHeap->free(index, count);
+ default:
+ return ptr.generalExpandingHeap->free(index, count);
}
}
};
diff --git a/tools/gfx/d3d12/render-d3d12.cpp b/tools/gfx/d3d12/render-d3d12.cpp
index a6d02cdc3..e5a1d1876 100644
--- a/tools/gfx/d3d12/render-d3d12.cpp
+++ b/tools/gfx/d3d12/render-d3d12.cpp
@@ -110,7 +110,10 @@ public:
IResourceView::Desc const& desc,
IResourceView** outView) override;
virtual SLANG_NO_THROW Result SLANG_MCALL createBufferView(
- IBufferResource* buffer, IResourceView::Desc const& desc, IResourceView** outView) override;
+ IBufferResource* buffer,
+ IBufferResource* counterBuffer,
+ IResourceView::Desc const& desc,
+ IResourceView** outView) override;
virtual SLANG_NO_THROW Result SLANG_MCALL
createFramebuffer(IFramebuffer::Desc const& desc, IFramebuffer** outFrameBuffer) override;
@@ -377,7 +380,7 @@ public:
{
public:
D3D12Descriptor m_descriptor;
- Slang::RefPtr<D3D12GeneralDescriptorHeap> m_allocator;
+ Slang::RefPtr<D3D12GeneralExpandingDescriptorHeap> m_allocator;
~SamplerStateImpl()
{
m_allocator->free(m_descriptor);
@@ -394,7 +397,7 @@ public:
{
public:
D3D12Descriptor m_descriptor;
- RefPtr<D3D12GeneralDescriptorHeap> m_allocator;
+ RefPtr<D3D12GeneralExpandingDescriptorHeap> m_allocator;
~ResourceViewInternalImpl() { m_allocator->free(m_descriptor); }
};
@@ -2279,6 +2282,7 @@ public:
struct ShaderBinary
{
SlangStage stage;
+ slang::EntryPointReflection* entryPointInfo;
List<uint8_t> code;
};
@@ -3934,7 +3938,24 @@ public:
virtual SLANG_NO_THROW void SLANG_MCALL
dispatchComputeIndirect(IBufferResource* argBuffer, uint64_t offset) override
{
- SLANG_UNIMPLEMENTED_X("dispatchComputeIndirect");
+ // Submit binding for compute
+ {
+ ComputeSubmitter submitter(m_d3dCmdList);
+ RefPtr<PipelineStateBase> newPipeline;
+ if (SLANG_FAILED(_bindRenderState(&submitter, newPipeline)))
+ {
+ assert(!"Failed to bind render state");
+ }
+ }
+ auto argBufferImpl = static_cast<BufferResourceImpl*>(argBuffer);
+
+ m_d3dCmdList->ExecuteIndirect(
+ m_renderer->dispatchIndirectCmdSignature,
+ 1,
+ argBufferImpl->m_resource,
+ offset,
+ nullptr,
+ 0);
}
};
@@ -4233,11 +4254,13 @@ public:
}
auto rowSize = (footprint.Footprint.Width + formatInfo.blockWidth - 1) /
formatInfo.blockWidth * formatInfo.blockSizeInBytes;
+ auto rowCount = (footprint.Footprint.Height + formatInfo.blockHeight - 1) /
+ formatInfo.blockHeight;
footprint.Footprint.RowPitch = (UINT)D3DUtil::calcAligned(
rowSize, (uint32_t)D3D12_TEXTURE_DATA_PITCH_ALIGNMENT);
- auto bufferSize = footprint.Footprint.RowPitch * footprint.Footprint.Height *
- footprint.Footprint.Depth;
+ auto bufferSize =
+ footprint.Footprint.RowPitch * rowCount * footprint.Footprint.Depth;
IBufferResource* stagingBuffer;
m_commandBuffer->m_transientHeap->allocateStagingBuffer(
@@ -4249,11 +4272,10 @@ public:
bufferImpl->m_resource.getResource()->Map(0, &mapRange, (void**)&bufferData);
for (uint32_t z = 0; z < footprint.Footprint.Depth; z++)
{
- auto imageStart = bufferData + footprint.Footprint.RowPitch *
- footprint.Footprint.Height * (size_t)z;
+ auto imageStart = bufferData + footprint.Footprint.RowPitch * rowCount * (size_t)z;
auto srcData =
(uint8_t*)subResourceData->data + subResourceData->strideZ * z;
- for (uint32_t row = 0; row < footprint.Footprint.Height; row++)
+ for (uint32_t row = 0; row < rowCount; row++)
{
memcpy(
imageStart + row * (size_t)footprint.Footprint.RowPitch,
@@ -4979,14 +5001,14 @@ public:
RefPtr<CommandQueueImpl> m_resourceCommandQueue;
RefPtr<TransientResourceHeapImpl> m_resourceCommandTransientHeap;
- RefPtr<D3D12GeneralDescriptorHeap> m_rtvAllocator;
- RefPtr<D3D12GeneralDescriptorHeap> m_dsvAllocator;
+ RefPtr<D3D12GeneralExpandingDescriptorHeap> m_rtvAllocator;
+ RefPtr<D3D12GeneralExpandingDescriptorHeap> m_dsvAllocator;
// Space in the GPU-visible heaps is precious, so we will also keep
// around CPU-visible heaps for storing descriptors in a format
// that is ready for copying into the GPU-visible heaps as needed.
//
- RefPtr<D3D12GeneralDescriptorHeap> m_cpuViewHeap; ///< Cbv, Srv, Uav
- RefPtr<D3D12GeneralDescriptorHeap> m_cpuSamplerHeap; ///< Heap for samplers
+ RefPtr<D3D12GeneralExpandingDescriptorHeap> m_cpuViewHeap; ///< Cbv, Srv, Uav
+ RefPtr<D3D12GeneralExpandingDescriptorHeap> m_cpuSamplerHeap; ///< Heap for samplers
// Dll entry points
PFN_D3D12_GET_DEBUG_INTERFACE m_D3D12GetDebugInterface = nullptr;
@@ -4999,6 +5021,7 @@ public:
// as well as the command type to be used (DrawInstanced and DrawIndexedInstanced, in this case).
ComPtr<ID3D12CommandSignature> drawIndirectCmdSignature;
ComPtr<ID3D12CommandSignature> drawIndexedIndirectCmdSignature;
+ ComPtr<ID3D12CommandSignature> dispatchIndirectCmdSignature;
};
SLANG_NO_THROW Result SLANG_MCALL D3D12Device::TransientResourceHeapImpl::synchronizeAndReset()
@@ -5189,18 +5212,34 @@ static void _initSrvDesc(
{
switch (desc.Dimension)
{
- case D3D12_RESOURCE_DIMENSION_TEXTURE1D: descOut.ViewDimension = D3D12_SRV_DIMENSION_TEXTURE1D; break;
- case D3D12_RESOURCE_DIMENSION_TEXTURE2D: descOut.ViewDimension = D3D12_SRV_DIMENSION_TEXTURE2D; break;
- case D3D12_RESOURCE_DIMENSION_TEXTURE3D: descOut.ViewDimension = D3D12_SRV_DIMENSION_TEXTURE3D; break;
- default: assert(!"Unknown dimension");
+ case D3D12_RESOURCE_DIMENSION_TEXTURE1D:
+ descOut.ViewDimension = D3D12_SRV_DIMENSION_TEXTURE1D;
+ descOut.Texture1D.MipLevels = subresourceRange.mipLevelCount == 0
+ ? desc.MipLevels - subresourceRange.mipLevel
+ : subresourceRange.mipLevelCount;
+ descOut.Texture1D.MostDetailedMip = subresourceRange.mipLevel;
+ break;
+ case D3D12_RESOURCE_DIMENSION_TEXTURE2D:
+ descOut.ViewDimension = D3D12_SRV_DIMENSION_TEXTURE2D;
+ descOut.Texture2D.PlaneSlice =
+ D3DUtil::getPlaneSlice(descOut.Format, subresourceRange.aspectMask);
+ descOut.Texture2D.ResourceMinLODClamp = 0.0f;
+ descOut.Texture2D.MipLevels = subresourceRange.mipLevelCount == 0
+ ? desc.MipLevels - subresourceRange.mipLevel
+ : subresourceRange.mipLevelCount;
+ descOut.Texture2D.MostDetailedMip = subresourceRange.mipLevel;
+ break;
+ case D3D12_RESOURCE_DIMENSION_TEXTURE3D:
+ descOut.ViewDimension = D3D12_SRV_DIMENSION_TEXTURE3D;
+ descOut.Texture3D.MipLevels = subresourceRange.mipLevelCount == 0
+ ? desc.MipLevels - subresourceRange.mipLevel
+ : subresourceRange.mipLevelCount;
+ descOut.Texture3D.MostDetailedMip = subresourceRange.mipLevel;
+ break;
+ default:
+ assert(!"Unknown dimension");
}
- descOut.Texture2D.MipLevels =
- subresourceRange.mipLevelCount == 0 ? desc.MipLevels : subresourceRange.mipLevelCount;
- descOut.Texture2D.MostDetailedMip = subresourceRange.mipLevel;
- descOut.Texture2D.PlaneSlice =
- D3DUtil::getPlaneSlice(descOut.Format, subresourceRange.aspectMask);
- descOut.Texture2D.ResourceMinLODClamp = 0.0f;
}
else if (resourceType == IResource::Type::TextureCube)
{
@@ -5213,7 +5252,7 @@ static void _initSrvDesc(
: subresourceRange.layerCount / 6;
descOut.TextureCubeArray.First2DArrayFace = subresourceRange.baseArrayLayer;
descOut.TextureCubeArray.MipLevels = subresourceRange.mipLevelCount == 0
- ? desc.MipLevels
+ ? desc.MipLevels - subresourceRange.mipLevel
: subresourceRange.mipLevelCount;
descOut.TextureCubeArray.MostDetailedMip = subresourceRange.mipLevel;
descOut.TextureCubeArray.ResourceMinLODClamp = 0;
@@ -5223,7 +5262,7 @@ static void _initSrvDesc(
descOut.ViewDimension = D3D12_SRV_DIMENSION_TEXTURECUBE;
descOut.TextureCube.MipLevels = subresourceRange.mipLevelCount == 0
- ? desc.MipLevels
+ ? desc.MipLevels - subresourceRange.mipLevel
: subresourceRange.mipLevelCount;
descOut.TextureCube.MostDetailedMip = subresourceRange.mipLevel;
descOut.TextureCube.ResourceMinLODClamp = 0;
@@ -5235,22 +5274,46 @@ static void _initSrvDesc(
switch (desc.Dimension)
{
- case D3D12_RESOURCE_DIMENSION_TEXTURE1D: descOut.ViewDimension = D3D12_SRV_DIMENSION_TEXTURE1DARRAY; break;
- case D3D12_RESOURCE_DIMENSION_TEXTURE2D: descOut.ViewDimension = D3D12_SRV_DIMENSION_TEXTURE2DARRAY; break;
- case D3D12_RESOURCE_DIMENSION_TEXTURE3D: descOut.ViewDimension = D3D12_SRV_DIMENSION_TEXTURE3D; break;
+ case D3D12_RESOURCE_DIMENSION_TEXTURE1D:
+ descOut.ViewDimension = D3D12_SRV_DIMENSION_TEXTURE1DARRAY;
+ descOut.Texture1D.MostDetailedMip = subresourceRange.mipLevel;
+ descOut.Texture1D.MipLevels = subresourceRange.mipLevelCount == 0
+ ? desc.MipLevels
+ : subresourceRange.mipLevelCount;
+ descOut.Texture1DArray.ArraySize = subresourceRange.layerCount == 0
+ ? desc.DepthOrArraySize
+ : subresourceRange.layerCount;
+ descOut.Texture1DArray.FirstArraySlice = subresourceRange.baseArrayLayer;
+ descOut.Texture1DArray.ResourceMinLODClamp = 0;
+ descOut.Texture1DArray.MostDetailedMip = subresourceRange.mipLevel;
+ descOut.Texture1DArray.MipLevels = subresourceRange.mipLevelCount == 0
+ ? desc.MipLevels - subresourceRange.mipLevel
+ : subresourceRange.mipLevelCount;
+ break;
+ case D3D12_RESOURCE_DIMENSION_TEXTURE2D:
+ descOut.ViewDimension = D3D12_SRV_DIMENSION_TEXTURE2DARRAY;
+ descOut.Texture2DArray.ArraySize =
+ subresourceRange.layerCount == 0 ? desc.DepthOrArraySize : subresourceRange.layerCount;
+ descOut.Texture2DArray.FirstArraySlice = subresourceRange.baseArrayLayer;
+ descOut.Texture2DArray.PlaneSlice =
+ D3DUtil::getPlaneSlice(descOut.Format, subresourceRange.aspectMask);
+ descOut.Texture2DArray.ResourceMinLODClamp = 0;
+ descOut.Texture2DArray.MostDetailedMip = subresourceRange.mipLevel;
+ descOut.Texture2DArray.MipLevels = subresourceRange.mipLevelCount == 0
+ ? desc.MipLevels - subresourceRange.mipLevel
+ : subresourceRange.mipLevelCount;
+ break;
+ case D3D12_RESOURCE_DIMENSION_TEXTURE3D:
+ descOut.ViewDimension = D3D12_SRV_DIMENSION_TEXTURE3D;
+ descOut.Texture3D.MostDetailedMip = subresourceRange.mipLevel;
+ descOut.Texture3D.MipLevels = subresourceRange.mipLevelCount == 0
+ ? desc.MipLevels
+ : subresourceRange.mipLevelCount;
+ break;
- default: assert(!"Unknown dimension");
+ default:
+ assert(!"Unknown dimension");
}
-
- descOut.Texture2DArray.ArraySize =
- subresourceRange.layerCount == 0 ? desc.DepthOrArraySize : subresourceRange.layerCount;
- descOut.Texture2DArray.MostDetailedMip = subresourceRange.mipLevel;
- descOut.Texture2DArray.MipLevels =
- subresourceRange.mipLevelCount == 0 ? desc.MipLevels : subresourceRange.mipLevelCount;
- descOut.Texture2DArray.FirstArraySlice = subresourceRange.baseArrayLayer;
- descOut.Texture2DArray.PlaneSlice =
- D3DUtil::getPlaneSlice(descOut.Format, subresourceRange.aspectMask);
- descOut.Texture2DArray.ResourceMinLODClamp = 0;
}
}
@@ -5822,20 +5885,20 @@ Result D3D12Device::initialize(const Desc& desc)
// since this object is already owned by `D3D12Device`.
m_resourceCommandTransientHeap->breakStrongReferenceToDevice();
- m_cpuViewHeap = new D3D12GeneralDescriptorHeap();
+ m_cpuViewHeap = new D3D12GeneralExpandingDescriptorHeap();
SLANG_RETURN_ON_FAIL(m_cpuViewHeap->init(
m_device,
1024 * 1024,
D3D12_DESCRIPTOR_HEAP_TYPE_CBV_SRV_UAV,
D3D12_DESCRIPTOR_HEAP_FLAG_NONE));
- m_cpuSamplerHeap = new D3D12GeneralDescriptorHeap();
+ m_cpuSamplerHeap = new D3D12GeneralExpandingDescriptorHeap();
SLANG_RETURN_ON_FAIL(m_cpuSamplerHeap->init(
m_device, 2048, D3D12_DESCRIPTOR_HEAP_TYPE_SAMPLER, D3D12_DESCRIPTOR_HEAP_FLAG_NONE));
- m_rtvAllocator = new D3D12GeneralDescriptorHeap();
+ m_rtvAllocator = new D3D12GeneralExpandingDescriptorHeap();
SLANG_RETURN_ON_FAIL(m_rtvAllocator->init(
m_device, 16 * 1024, D3D12_DESCRIPTOR_HEAP_TYPE_RTV, D3D12_DESCRIPTOR_HEAP_FLAG_NONE));
- m_dsvAllocator = new D3D12GeneralDescriptorHeap();
+ m_dsvAllocator = new D3D12GeneralExpandingDescriptorHeap();
SLANG_RETURN_ON_FAIL(m_dsvAllocator->init(
m_device, 1024, D3D12_DESCRIPTOR_HEAP_TYPE_DSV, D3D12_DESCRIPTOR_HEAP_FLAG_NONE));
@@ -5936,6 +5999,21 @@ Result D3D12Device::initialize(const Desc& desc)
SLANG_RETURN_ON_FAIL(m_device->CreateCommandSignature(&desc, nullptr, IID_PPV_ARGS(drawIndexedIndirectCmdSignature.writeRef())));
}
+ // Allocate a D3D12 "command signature" object that matches the behavior
+ // of a D3D11-style `Dispatch` operation.
+ {
+ D3D12_INDIRECT_ARGUMENT_DESC args;
+ args.Type = D3D12_INDIRECT_ARGUMENT_TYPE_DISPATCH;
+
+ D3D12_COMMAND_SIGNATURE_DESC desc;
+ desc.ByteStride = sizeof(D3D12_DISPATCH_ARGUMENTS);
+ desc.NumArgumentDescs = 1;
+ desc.pArgumentDescs = &args;
+ desc.NodeMask = 0;
+
+ SLANG_RETURN_ON_FAIL(m_device->CreateCommandSignature(
+ &desc, nullptr, IID_PPV_ARGS(dispatchIndirectCmdSignature.writeRef())));
+ }
m_isInitialized = true;
return SLANG_OK;
}
@@ -6046,6 +6124,31 @@ static D3D12_RESOURCE_DIMENSION _calcResourceDimension(IResource::Type type)
}
}
+DXGI_FORMAT getTypelessFormatFromDepthFormat(Format format)
+{
+ switch (format)
+ {
+ case Format::D16_UNORM:
+ return DXGI_FORMAT_R16_TYPELESS;
+ case Format::D32_FLOAT:
+ return DXGI_FORMAT_R32_TYPELESS;
+ default:
+ return D3DUtil::getMapFormat(format);
+ }
+}
+
+BOOL isTypelessDepthFormat(DXGI_FORMAT format)
+{
+ switch (format)
+ {
+ case DXGI_FORMAT_R16_TYPELESS:
+ case DXGI_FORMAT_R32_TYPELESS:
+ return true;
+ default:
+ return false;
+ }
+}
+
Result setupResourceDesc(D3D12_RESOURCE_DESC& resourceDesc, const ITextureResource::Desc& srcDesc)
{
const DXGI_FORMAT pixelFormat = D3DUtil::getMapFormat(srcDesc.format);
@@ -6080,6 +6183,13 @@ Result setupResourceDesc(D3D12_RESOURCE_DESC& resourceDesc, const ITextureResour
resourceDesc.Alignment = 0;
+ if (isDepthFormat(srcDesc.format) &&
+ (srcDesc.allowedStates.contains(ResourceState::ShaderResource) ||
+ srcDesc.allowedStates.contains(ResourceState::UnorderedAccess)))
+ {
+ resourceDesc.Format = getTypelessFormatFromDepthFormat(srcDesc.format);
+ }
+
return SLANG_OK;
}
@@ -6129,6 +6239,10 @@ Result D3D12Device::createTextureResource(const ITextureResource::Desc& descIn,
{
clearValuePtr = nullptr;
}
+ if (isTypelessDepthFormat(resourceDesc.Format))
+ {
+ clearValuePtr = nullptr;
+ }
clearValue.Format = resourceDesc.Format;
memcpy(clearValue.Color, &descIn.optimalClearValue.color, sizeof(clearValue.Color));
clearValue.DepthStencil.Depth = descIn.optimalClearValue.depthStencil.depth;
@@ -6632,9 +6746,7 @@ Result D3D12Device::createTextureView(ITextureResource* texture, IResourceView::
d3d12desc.ViewDimension = D3D12_UAV_DIMENSION_TEXTURE3D;
d3d12desc.Texture3D.MipSlice = desc.subresourceRange.mipLevel;
d3d12desc.Texture3D.FirstWSlice = desc.subresourceRange.baseArrayLayer;
- d3d12desc.Texture3D.WSize = desc.subresourceRange.layerCount == 0
- ? resourceDesc.size.depth
- : desc.subresourceRange.layerCount;
+ d3d12desc.Texture3D.WSize = resourceDesc.size.depth;
break;
default:
return SLANG_FAIL;
@@ -6719,7 +6831,11 @@ Result D3D12Device::getFormatSupportedResourceStates(Format format, ResourceStat
return SLANG_OK;
}
-Result D3D12Device::createBufferView(IBufferResource* buffer, IResourceView::Desc const& desc, IResourceView** outView)
+Result D3D12Device::createBufferView(
+ IBufferResource* buffer,
+ IBufferResource* counterBuffer,
+ IResourceView::Desc const& desc,
+ IResourceView** outView)
{
auto resourceImpl = (BufferResourceImpl*) buffer;
auto resourceDesc = *resourceImpl->getDesc();
@@ -6745,14 +6861,14 @@ Result D3D12Device::createBufferView(IBufferResource* buffer, IResourceView::Des
uavDesc.Buffer.NumElements =
desc.bufferRange.elementCount == 0
? UINT(resourceDesc.sizeInBytes / desc.bufferElementSize)
- : desc.bufferRange.elementCount;
+ : (UINT)desc.bufferRange.elementCount;
}
else if(desc.format == Format::Unknown)
{
uavDesc.Format = DXGI_FORMAT_R32_TYPELESS;
uavDesc.Buffer.NumElements = desc.bufferRange.elementCount == 0
? UINT(resourceDesc.sizeInBytes / 4)
- : desc.bufferRange.elementCount / 4;
+ : UINT(desc.bufferRange.elementCount / 4);
uavDesc.Buffer.Flags |= D3D12_BUFFER_UAV_FLAG_RAW;
}
else
@@ -6763,16 +6879,16 @@ Result D3D12Device::createBufferView(IBufferResource* buffer, IResourceView::Des
uavDesc.Buffer.NumElements =
desc.bufferRange.elementCount == 0
? UINT(resourceDesc.sizeInBytes / sizeInfo.blockSizeInBytes)
- : desc.bufferRange.elementCount;
+ : (UINT)desc.bufferRange.elementCount;
}
-
-
- // TODO: need to support the separate "counter resource" for the case
- // of append/consume buffers with attached counters.
-
+ auto counterResourceImpl = static_cast<BufferResourceImpl*>(counterBuffer);
SLANG_RETURN_ON_FAIL(m_cpuViewHeap->allocate(&viewImpl->m_descriptor));
viewImpl->m_allocator = m_cpuViewHeap;
- m_device->CreateUnorderedAccessView(resourceImpl->m_resource, nullptr, &uavDesc, viewImpl->m_descriptor.cpuHandle);
+ m_device->CreateUnorderedAccessView(
+ resourceImpl->m_resource,
+ counterResourceImpl ? counterResourceImpl->m_resource.getResource() : nullptr,
+ &uavDesc,
+ viewImpl->m_descriptor.cpuHandle);
}
break;
@@ -6790,14 +6906,14 @@ Result D3D12Device::createBufferView(IBufferResource* buffer, IResourceView::Des
srvDesc.Buffer.NumElements =
desc.bufferRange.elementCount == 0
? UINT(resourceDesc.sizeInBytes / desc.bufferElementSize)
- : desc.bufferRange.elementCount;
+ : (UINT)desc.bufferRange.elementCount;
}
else if (desc.format == Format::Unknown)
{
srvDesc.Format = DXGI_FORMAT_R32_TYPELESS;
srvDesc.Buffer.NumElements = desc.bufferRange.elementCount == 0
? UINT(resourceDesc.sizeInBytes / 4)
- : desc.bufferRange.elementCount / 4;
+ : UINT(desc.bufferRange.elementCount / 4);
srvDesc.Buffer.Flags |= D3D12_BUFFER_SRV_FLAG_RAW;
}
else
@@ -6808,7 +6924,7 @@ Result D3D12Device::createBufferView(IBufferResource* buffer, IResourceView::Des
srvDesc.Buffer.NumElements =
desc.bufferRange.elementCount == 0
? UINT(resourceDesc.sizeInBytes / sizeInfo.blockSizeInBytes)
- : desc.bufferRange.elementCount;
+ : (UINT)desc.bufferRange.elementCount;
}
SLANG_RETURN_ON_FAIL(m_cpuViewHeap->allocate(&viewImpl->m_descriptor));
@@ -7021,12 +7137,12 @@ Result D3D12Device::readBufferResource(
Result D3D12Device::createProgram(const IShaderProgram::Desc& desc, IShaderProgram** outProgram, ISlangBlob** outDiagnosticBlob)
{
RefPtr<ShaderProgramImpl> shaderProgram = new ShaderProgramImpl();
- shaderProgram->slangProgram = desc.slangProgram;
+ shaderProgram->init(desc);
ComPtr<ID3DBlob> d3dDiagnosticBlob;
auto rootShaderLayoutResult = RootShaderObjectLayoutImpl::create(
this,
- desc.slangProgram,
- desc.slangProgram->getLayout(),
+ shaderProgram->linkedProgram,
+ shaderProgram->linkedProgram->getLayout(),
shaderProgram->m_rootObjectLayout.writeRef(),
d3dDiagnosticBlob.writeRef());
if (!SLANG_SUCCEEDED(rootShaderLayoutResult))
@@ -7039,22 +7155,22 @@ Result D3D12Device::createProgram(const IShaderProgram::Desc& desc, IShaderProgr
}
return rootShaderLayoutResult;
}
- if (desc.slangProgram->getSpecializationParamCount() != 0)
+ if (shaderProgram->isSpecializable())
{
// For a specializable program, we don't invoke any actual slang compilation yet.
returnComPtr(outProgram, shaderProgram);
return SLANG_OK;
}
// For a fully specialized program, read and store its kernel code in `shaderProgram`.
- auto programReflection = desc.slangProgram->getLayout();
- for (SlangUInt i = 0; i < programReflection->getEntryPointCount(); i++)
+ auto compileShader = [&](slang::EntryPointReflection* entryPointInfo,
+ slang::IComponentType* entryPointComponent,
+ SlangInt entryPointIndex)
{
- auto entryPointInfo = programReflection->getEntryPointByIndex(i);
auto stage = entryPointInfo->getStage();
ComPtr<ISlangBlob> kernelCode;
ComPtr<ISlangBlob> diagnostics;
- auto compileResult = desc.slangProgram->getEntryPointCode(
- (SlangInt)i, 0, kernelCode.writeRef(), diagnostics.writeRef());
+ auto compileResult = entryPointComponent->getEntryPointCode(
+ entryPointIndex, 0, kernelCode.writeRef(), diagnostics.writeRef());
if (diagnostics)
{
getDebugCallback()->handleMessage(
@@ -7067,10 +7183,35 @@ Result D3D12Device::createProgram(const IShaderProgram::Desc& desc, IShaderProgr
SLANG_RETURN_ON_FAIL(compileResult);
ShaderBinary shaderBin;
shaderBin.stage = stage;
+ shaderBin.entryPointInfo = entryPointInfo;
shaderBin.code.addRange(
reinterpret_cast<const uint8_t*>(kernelCode->getBufferPointer()),
(Index)kernelCode->getBufferSize());
shaderProgram->m_shaders.add(_Move(shaderBin));
+ return SLANG_OK;
+ };
+
+ if (shaderProgram->linkedEntryPoints.getCount() == 0)
+ {
+ // If the user does not explicitly specify entry point components, find them from `linkedEntryPoints`.
+ auto programReflection = shaderProgram->linkedProgram->getLayout();
+ for (SlangUInt i = 0; i < programReflection->getEntryPointCount(); i++)
+ {
+ SLANG_RETURN_ON_FAIL(compileShader(
+ programReflection->getEntryPointByIndex(i),
+ shaderProgram->linkedProgram,
+ (SlangInt)i));
+ }
+ }
+ else
+ {
+ // If the user specifies entry point components via the separated entry point array, compile code
+ // from there.
+ for (auto& entryPoint : shaderProgram->linkedEntryPoints)
+ {
+ SLANG_RETURN_ON_FAIL(
+ compileShader(entryPoint->getLayout()->getEntryPointByIndex(0), entryPoint, 0));
+ }
}
returnComPtr(outProgram, shaderProgram);
return SLANG_OK;
@@ -7150,6 +7291,7 @@ Result D3D12Device::createGraphicsPipelineState(const GraphicsPipelineStateDesc&
D3D12_GRAPHICS_PIPELINE_STATE_DESC psoDesc = {};
psoDesc.pRootSignature = programImpl->m_rootObjectLayout->m_rootSignature;
+
for (auto& shaderBin : programImpl->m_shaders)
{
switch (shaderBin.stage)
@@ -7283,7 +7425,7 @@ Result D3D12Device::createGraphicsPipelineState(const GraphicsPipelineStateDesc&
if (m_pipelineCreationAPIDispatcher)
{
SLANG_RETURN_ON_FAIL(m_pipelineCreationAPIDispatcher->createGraphicsPipelineState(
- this, programImpl->slangProgram.get(), &psoDesc, (void**)pipelineState.writeRef()));
+ this, programImpl->linkedProgram.get(), &psoDesc, (void**)pipelineState.writeRef()));
}
else
{
@@ -7312,7 +7454,7 @@ Result D3D12Device::createComputePipelineState(const ComputePipelineStateDesc& i
// Only actually create a D3D12 pipeline state if the pipeline is fully specialized.
ComPtr<ID3D12PipelineState> pipelineState;
- if (!programImpl->slangProgram || programImpl->slangProgram->getSpecializationParamCount() == 0)
+ if (!programImpl->isSpecializable())
{
// Describe and create the compute pipeline state object
D3D12_COMPUTE_PIPELINE_STATE_DESC computeDesc = {};
@@ -7361,7 +7503,7 @@ Result D3D12Device::createComputePipelineState(const ComputePipelineStateDesc& i
{
SLANG_RETURN_ON_FAIL(m_pipelineCreationAPIDispatcher->createComputePipelineState(
this,
- programImpl->slangProgram.get(),
+ programImpl->linkedProgram.get(),
&computeDesc,
(void**)pipelineState.writeRef()));
}
@@ -7835,8 +7977,8 @@ Result D3D12Device::createRayTracingPipelineState(const RayTracingPipelineStateD
pipelineStateImpl->init(inDesc);
auto program = static_cast<ShaderProgramImpl*>(inDesc.program);
- auto slangProgram = program->slangProgram;
- auto programLayout = slangProgram->getLayout();
+ auto slangGlobalScope = program->linkedProgram;
+ auto programLayout = slangGlobalScope->getLayout();
if (!program->m_rootObjectLayout->m_rootSignature)
{
@@ -7847,13 +7989,24 @@ Result D3D12Device::createRayTracingPipelineState(const RayTracingPipelineStateD
ChunkedList<D3D12_DXIL_LIBRARY_DESC> dxilLibraries;
ChunkedList<D3D12_HIT_GROUP_DESC> hitGroups;
ChunkedList<ComPtr<ISlangBlob>> codeBlobs;
+ ChunkedList<D3D12_EXPORT_DESC> exports;
+ ChunkedList<const wchar_t*> strPtrs;
+
ComPtr<ISlangBlob> diagnostics;
ChunkedList<OSString> stringPool;
- for (SlangUInt i = 0; i < programLayout->getEntryPointCount(); i++)
+ auto getWStr = [&](const char* name)
+ {
+ String str = String(name);
+ auto wstr = str.toWString();
+ return stringPool.add(wstr)->begin();
+ };
+ auto compileShader = [&](slang::EntryPointLayout* entryPointInfo,
+ slang::IComponentType* component,
+ SlangInt entryPointIndex)
{
ComPtr<ISlangBlob> codeBlob;
- auto compileResult =
- slangProgram->getEntryPointCode(i, 0, codeBlob.writeRef(), diagnostics.writeRef());
+ auto compileResult = component->getEntryPointCode(
+ entryPointIndex, 0, codeBlob.writeRef(), diagnostics.writeRef());
if (diagnostics.get())
{
getDebugCallback()->handleMessage(
@@ -7864,20 +8017,38 @@ Result D3D12Device::createRayTracingPipelineState(const RayTracingPipelineStateD
SLANG_RETURN_ON_FAIL(compileResult);
codeBlobs.add(codeBlob);
D3D12_DXIL_LIBRARY_DESC library = {};
- library.DXILLibrary.BytecodeLength = codeBlob->getBufferSize();;
+ library.DXILLibrary.BytecodeLength = codeBlob->getBufferSize();
library.DXILLibrary.pShaderBytecode = codeBlob->getBufferPointer();
+ library.NumExports = 1;
+ D3D12_EXPORT_DESC exportDesc = {};
+ exportDesc.Name = getWStr(entryPointInfo->getNameOverride());
+ exportDesc.ExportToRename = getWStr(entryPointInfo->getNameOverride());
+ exportDesc.Flags = D3D12_EXPORT_FLAG_NONE;
+ library.pExports = exports.add(exportDesc);
D3D12_STATE_SUBOBJECT dxilSubObject = {};
dxilSubObject.Type = D3D12_STATE_SUBOBJECT_TYPE_DXIL_LIBRARY;
dxilSubObject.pDesc = dxilLibraries.add(library);
subObjects.add(dxilSubObject);
+ return SLANG_OK;
+ };
+ if (program->linkedEntryPoints.getCount() == 0)
+ {
+ for (SlangUInt i = 0; i < programLayout->getEntryPointCount(); i++)
+ {
+ SLANG_RETURN_ON_FAIL(compileShader(
+ programLayout->getEntryPointByIndex(i), program->linkedProgram, (SlangInt)i));
+ }
}
- auto getWStr = [&](const char* name)
+ else
{
- String str = String(name);
- auto wstr = str.toWString();
- return stringPool.add(wstr)->begin();
- };
+ for (auto& entryPoint : program->linkedEntryPoints)
+ {
+ SLANG_RETURN_ON_FAIL(
+ compileShader(entryPoint->getLayout()->getEntryPointByIndex(0), entryPoint, 0));
+ }
+ }
+
for (int i = 0; i < inDesc.hitGroupCount; i++)
{
auto hitGroup = inDesc.hitGroups[i];
@@ -7909,7 +8080,7 @@ Result D3D12Device::createRayTracingPipelineState(const RayTracingPipelineStateD
D3D12_RAYTRACING_SHADER_CONFIG shaderConfig = {};
// According to DXR spec, fixed function triangle intersections must use float2 as ray attributes
// that defines the barycentric coordinates at intersection.
- shaderConfig.MaxAttributeSizeInBytes = sizeof(float) * 2;
+ shaderConfig.MaxAttributeSizeInBytes = inDesc.maxAttributeSizeInBytes;
shaderConfig.MaxPayloadSizeInBytes = inDesc.maxRayPayloadSize;
D3D12_STATE_SUBOBJECT shaderConfigSubObject = {};
shaderConfigSubObject.Type = D3D12_STATE_SUBOBJECT_TYPE_RAYTRACING_SHADER_CONFIG;
@@ -7932,7 +8103,7 @@ Result D3D12Device::createRayTracingPipelineState(const RayTracingPipelineStateD
if (m_pipelineCreationAPIDispatcher)
{
- m_pipelineCreationAPIDispatcher->beforeCreateRayTracingState(this, slangProgram);
+ m_pipelineCreationAPIDispatcher->beforeCreateRayTracingState(this, slangGlobalScope);
}
D3D12_STATE_OBJECT_DESC rtpsoDesc = {};
@@ -7943,7 +8114,7 @@ Result D3D12Device::createRayTracingPipelineState(const RayTracingPipelineStateD
if (m_pipelineCreationAPIDispatcher)
{
- m_pipelineCreationAPIDispatcher->afterCreateRayTracingState(this, slangProgram);
+ m_pipelineCreationAPIDispatcher->afterCreateRayTracingState(this, slangGlobalScope);
}
returnComPtr(outState, pipelineStateImpl);
diff --git a/tools/gfx/debug-layer.cpp b/tools/gfx/debug-layer.cpp
index 484729068..eed6afdb0 100644
--- a/tools/gfx/debug-layer.cpp
+++ b/tools/gfx/debug-layer.cpp
@@ -464,6 +464,7 @@ Result DebugDevice::createTextureView(
Result DebugDevice::createBufferView(
IBufferResource* buffer,
+ IBufferResource* counterBuffer,
IResourceView::Desc const& desc,
IResourceView** outView)
{
@@ -472,6 +473,7 @@ Result DebugDevice::createBufferView(
RefPtr<DebugResourceView> outObject = new DebugResourceView();
auto result = baseObject->createBufferView(
static_cast<DebugBufferResource*>(buffer)->baseObject,
+ counterBuffer ? static_cast<DebugBufferResource*>(counterBuffer)->baseObject : nullptr,
desc,
outObject->baseObject.writeRef());
if (SLANG_FAILED(result))
@@ -1909,7 +1911,7 @@ Result DebugFence::setCurrentValue(uint64_t value)
DebugShaderProgram::DebugShaderProgram(const IShaderProgram::Desc& desc)
{
- m_slangProgram = desc.slangProgram;
+ m_slangProgram = desc.slangGlobalScope;
}
Result DebugPipelineState::getNativeHandle(InteropHandle* outHandle)
diff --git a/tools/gfx/debug-layer.h b/tools/gfx/debug-layer.h
index 069895f9b..cb894dfd4 100644
--- a/tools/gfx/debug-layer.h
+++ b/tools/gfx/debug-layer.h
@@ -85,6 +85,7 @@ public:
IResourceView** outView) override;
virtual SLANG_NO_THROW Result SLANG_MCALL createBufferView(
IBufferResource* buffer,
+ IBufferResource* counterBuffer,
IResourceView::Desc const& desc,
IResourceView** outView) override;
virtual SLANG_NO_THROW Result SLANG_MCALL getAccelerationStructurePrebuildInfo(
diff --git a/tools/gfx/mutable-shader-object.h b/tools/gfx/mutable-shader-object.h
index 54fdf87c2..a9562f200 100644
--- a/tools/gfx/mutable-shader-object.h
+++ b/tools/gfx/mutable-shader-object.h
@@ -249,7 +249,7 @@ namespace gfx
MutableRootShaderObject(RendererBase* device, Slang::RefPtr<ShaderProgramBase> program)
{
this->m_device = device;
- auto programLayout = program->slangProgram->getLayout();
+ auto programLayout = program->slangGlobalScope->getLayout();
SlangInt entryPointCount = programLayout->getEntryPointCount();
for (SlangInt e = 0; e < entryPointCount; ++e)
{
diff --git a/tools/gfx/open-gl/render-gl.cpp b/tools/gfx/open-gl/render-gl.cpp
index 63c20fbea..b407fa000 100644
--- a/tools/gfx/open-gl/render-gl.cpp
+++ b/tools/gfx/open-gl/render-gl.cpp
@@ -130,7 +130,10 @@ public:
virtual SLANG_NO_THROW Result SLANG_MCALL createTextureView(
ITextureResource* texture, IResourceView::Desc const& desc, IResourceView** outView) override;
virtual SLANG_NO_THROW Result SLANG_MCALL createBufferView(
- IBufferResource* buffer, IResourceView::Desc const& desc, IResourceView** outView) override;
+ IBufferResource* buffer,
+ IBufferResource* counterBuffer,
+ IResourceView::Desc const& desc,
+ IResourceView** outView) override;
virtual SLANG_NO_THROW Result SLANG_MCALL createInputLayout(
IInputLayout::Desc const& desc,
@@ -2546,7 +2549,10 @@ SLANG_NO_THROW Result SLANG_MCALL GLDevice::createTextureView(
}
SLANG_NO_THROW Result SLANG_MCALL GLDevice::createBufferView(
- IBufferResource* buffer, IResourceView::Desc const& desc, IResourceView** outView)
+ IBufferResource* buffer,
+ IBufferResource* counterBuffer,
+ IResourceView::Desc const& desc,
+ IResourceView** outView)
{
auto resourceImpl = (BufferResourceImpl*) buffer;
@@ -2759,23 +2765,23 @@ void GLDevice::dispatchCompute(int x, int y, int z)
Result GLDevice::createProgram(
const IShaderProgram::Desc& desc, IShaderProgram** outProgram, ISlangBlob** outDiagnosticBlob)
{
- if (desc.slangProgram->getSpecializationParamCount() != 0)
+ if (desc.slangGlobalScope->getSpecializationParamCount() != 0)
{
// For a specializable program, we don't invoke any actual slang compilation yet.
RefPtr<ShaderProgramImpl> shaderProgram = new ShaderProgramImpl(m_weakRenderer, 0);
- shaderProgram->slangProgram = desc.slangProgram;
+ shaderProgram->init(desc);
returnComPtr(outProgram, shaderProgram);
return SLANG_OK;
}
auto programID = glCreateProgram();
- auto programLayout = desc.slangProgram->getLayout();
+ auto programLayout = desc.slangGlobalScope->getLayout();
ShortList<GLuint> shaderIDs;
for (SlangUInt i = 0; i < programLayout->getEntryPointCount(); i++)
{
ComPtr<ISlangBlob> kernelCode;
ComPtr<ISlangBlob> diagnostics;
- auto compileResult = desc.slangProgram->getEntryPointCode(
+ auto compileResult = desc.slangGlobalScope->getEntryPointCode(
i, 0, kernelCode.writeRef(), diagnostics.writeRef());
if (diagnostics)
{
@@ -2844,7 +2850,7 @@ Result GLDevice::createProgram(
}
RefPtr<ShaderProgramImpl> program = new ShaderProgramImpl(m_weakRenderer, programID);
- program->slangProgram = desc.slangProgram;
+ program->slangGlobalScope = desc.slangGlobalScope;
returnComPtr(outProgram, program);
return SLANG_OK;
}
@@ -2913,7 +2919,7 @@ Result GLDevice::createRootShaderObject(IShaderProgram* program, ShaderObjectBas
RefPtr<RootShaderObjectImpl> shaderObject;
RefPtr<RootShaderObjectLayoutImpl> rootLayout;
SLANG_RETURN_ON_FAIL(RootShaderObjectLayoutImpl::create(
- this, programImpl->slangProgram, programImpl->slangProgram->getLayout(), rootLayout.writeRef()));
+ this, programImpl->slangGlobalScope, programImpl->slangGlobalScope->getLayout(), rootLayout.writeRef()));
SLANG_RETURN_ON_FAIL(RootShaderObjectImpl::create(
this, rootLayout.Ptr(), shaderObject.writeRef()));
returnRefPtrMove(outObject, shaderObject);
diff --git a/tools/gfx/renderer-shared.cpp b/tools/gfx/renderer-shared.cpp
index d1cedaa61..f9ffe8dfd 100644
--- a/tools/gfx/renderer-shared.cpp
+++ b/tools/gfx/renderer-shared.cpp
@@ -298,8 +298,17 @@ void PipelineStateBase::initializeBase(const PipelineStateDesc& inDesc)
auto program = desc.getProgram();
m_program = program;
- isSpecializable = (program->slangProgram && program->slangProgram->getSpecializationParamCount() != 0);
-
+ isSpecializable = false;
+ if (program->slangGlobalScope && program->slangGlobalScope->getSpecializationParamCount() != 0)
+ isSpecializable = true;
+ for (auto& entryPoint : program->slangEntryPoints)
+ {
+ if (entryPoint->getSpecializationParamCount() != 0)
+ {
+ isSpecializable = true;
+ break;
+ }
+ }
// Hold a strong reference to inputLayout and framebufferLayout objects to prevent it from
// destruction.
if (inDesc.type == PipelineType::Graphics)
@@ -716,12 +725,12 @@ ResourceViewBase* SimpleShaderObjectData::getResourceView(
viewDesc.format = Format::Unknown;
viewDesc.type = IResourceView::Type::ShaderResource;
SLANG_RETURN_NULL_ON_FAIL(device->createBufferView(
- bufferResource.get(), viewDesc, resourceView.writeRef()));
+ bufferResource.get(), nullptr, viewDesc, resourceView.writeRef()));
m_structuredBufferView = static_cast<ResourceViewBase*>(resourceView.get());
viewDesc.type = IResourceView::Type::UnorderedAccess;
SLANG_RETURN_NULL_ON_FAIL(
device->createBufferView(
- bufferResource.get(), viewDesc, resourceView.writeRef()));
+ bufferResource.get(), nullptr, viewDesc, resourceView.writeRef()));
m_rwStructuredBufferView = static_cast<ResourceViewBase*>(resourceView.get());
}
@@ -737,6 +746,57 @@ ResourceViewBase* SimpleShaderObjectData::getResourceView(
}
}
+void ShaderProgramBase::init(const IShaderProgram::Desc& inDesc)
+{
+ desc = inDesc;
+
+ slangGlobalScope = desc.slangGlobalScope;
+ for (uint32_t i = 0; i < desc.entryPointCount; i++)
+ {
+ slangEntryPoints.add(ComPtr<slang::IComponentType>(desc.slangEntryPoints[i]));
+ }
+
+ auto session = desc.slangGlobalScope ? desc.slangGlobalScope->getSession() : nullptr;
+ if (desc.linkingStyle == IShaderProgram::LinkingStyle::SingleProgram)
+ {
+ List<slang::IComponentType*> components;
+ if (desc.slangGlobalScope)
+ {
+ components.add(desc.slangGlobalScope);
+ }
+ for (uint32_t i = 0; i < desc.entryPointCount; i++)
+ {
+ if (!session)
+ {
+ session = desc.slangEntryPoints[i]->getSession();
+ }
+ components.add(desc.slangEntryPoints[i]);
+ }
+ session->createCompositeComponentType(
+ components.getBuffer(), components.getCount(), linkedProgram.writeRef());
+ }
+ else
+ {
+ for (uint32_t i = 0; i < desc.entryPointCount; i++)
+ {
+ if (desc.slangGlobalScope)
+ {
+ slang::IComponentType* entryPointComponents[2] = {
+ desc.slangGlobalScope, desc.slangEntryPoints[i]};
+ ComPtr<slang::IComponentType> linkedEntryPoint;
+ session->createCompositeComponentType(
+ entryPointComponents, 2, linkedEntryPoint.writeRef());
+ linkedEntryPoints.add(linkedEntryPoint);
+ }
+ else
+ {
+ linkedEntryPoints.add(ComPtr<slang::IComponentType>(desc.slangEntryPoints[i]));
+ }
+ }
+ linkedProgram = desc.slangGlobalScope;
+ }
+}
+
Result RendererBase::maybeSpecializePipeline(
PipelineStateBase* currentPipeline,
ShaderObjectBase* rootObject,
@@ -766,11 +826,11 @@ Result RendererBase::maybeSpecializePipeline(
auto unspecializedProgram = static_cast<ShaderProgramBase*>(pipelineType == PipelineType::Compute
? currentPipeline->desc.compute.program
: currentPipeline->desc.graphics.program);
- auto unspecializedProgramLayout = unspecializedProgram->slangProgram->getLayout();
+ auto unspecializedProgramLayout = unspecializedProgram->linkedProgram->getLayout();
ComPtr<slang::IComponentType> specializedComponentType;
ComPtr<slang::IBlob> diagnosticBlob;
- auto compileRs = unspecializedProgram->slangProgram->specialize(
+ auto compileRs = unspecializedProgram->linkedProgram->specialize(
specializationArgs.components.getArrayView().getBuffer(),
specializationArgs.getCount(),
specializedComponentType.writeRef(),
@@ -784,10 +844,18 @@ Result RendererBase::maybeSpecializePipeline(
}
SLANG_RETURN_ON_FAIL(compileRs);
- // Now create specialized shader program using compiled binaries.
+ // Now create the specialized shader program using compiled binaries.
ComPtr<IShaderProgram> specializedProgram;
- IShaderProgram::Desc specializedProgramDesc = {};
- specializedProgramDesc.slangProgram = specializedComponentType;
+ IShaderProgram::Desc specializedProgramDesc = unspecializedProgram->desc;
+ specializedProgramDesc.slangGlobalScope = specializedComponentType;
+
+ if (specializedProgramDesc.linkingStyle == IShaderProgram::LinkingStyle::SingleProgram)
+ {
+ // When linking style is GraphicsCompute, the specialized global scope already contains
+ // entry-points, so we do not need to supply them again when creating the specialized
+ // pipeline.
+ specializedProgramDesc.entryPointCount = 0;
+ }
SLANG_RETURN_ON_FAIL(createProgram(specializedProgramDesc, specializedProgram.writeRef()));
// Create specialized pipeline state.
@@ -904,5 +972,17 @@ Result ShaderTableBase::init(const IShaderTable::Desc& desc)
return SLANG_OK;
}
+bool isDepthFormat(Format format)
+{
+ switch (format)
+ {
+ case Format::D16_UNORM:
+ case Format::D32_FLOAT:
+ return true;
+ default:
+ return false;
+ }
+}
+
} // namespace gfx
diff --git a/tools/gfx/renderer-shared.h b/tools/gfx/renderer-shared.h
index a23cf9dfe..e6f54ae10 100644
--- a/tools/gfx/renderer-shared.h
+++ b/tools/gfx/renderer-shared.h
@@ -973,7 +973,35 @@ public:
SLANG_COM_OBJECT_IUNKNOWN_ALL
IShaderProgram* getInterface(const Slang::Guid& guid);
- ComPtr<slang::IComponentType> slangProgram;
+ Desc desc;
+
+ Slang::ComPtr<slang::IComponentType> slangGlobalScope;
+ Slang::List<ComPtr<slang::IComponentType>> slangEntryPoints;
+
+ // Linked program when linkingStyle is GraphicsCompute, or the original global scope
+ // when linking style is RayTracing.
+ Slang::ComPtr<slang::IComponentType> linkedProgram;
+
+ // Linked program for each entry point when linkingStyle is RayTracing.
+ Slang::List<Slang::ComPtr<slang::IComponentType>> linkedEntryPoints;
+
+ void init(const IShaderProgram::Desc& desc);
+
+ bool isSpecializable()
+ {
+ if (slangGlobalScope->getSpecializationParamCount() != 0)
+ {
+ return true;
+ }
+ for (auto& entryPoint : slangEntryPoints)
+ {
+ if (entryPoint->getSpecializationParamCount() != 0)
+ {
+ return true;
+ }
+ }
+ return false;
+ }
};
class InputLayoutBase
@@ -1369,6 +1397,8 @@ public:
Slang::Dictionary<slang::TypeReflection*, Slang::RefPtr<ShaderObjectLayoutBase>> m_shaderObjectLayoutCache;
};
+bool isDepthFormat(Format format);
+
IDebugCallback*& _getDebugCallback();
IDebugCallback* _getNullDebugCallback();
inline IDebugCallback* getDebugCallback()
diff --git a/tools/gfx/vulkan/render-vk.cpp b/tools/gfx/vulkan/render-vk.cpp
index 7b6b31366..80084ae7b 100644
--- a/tools/gfx/vulkan/render-vk.cpp
+++ b/tools/gfx/vulkan/render-vk.cpp
@@ -94,7 +94,10 @@ public:
virtual SLANG_NO_THROW Result SLANG_MCALL createTextureView(
ITextureResource* texture, IResourceView::Desc const& desc, IResourceView** outView) override;
virtual SLANG_NO_THROW Result SLANG_MCALL createBufferView(
- IBufferResource* buffer, IResourceView::Desc const& desc, IResourceView** outView) override;
+ IBufferResource* buffer,
+ IBufferResource* counterBuffer,
+ IResourceView::Desc const& desc,
+ IResourceView** outView) override;
virtual SLANG_NO_THROW Result SLANG_MCALL createInputLayout(
IInputLayout::Desc const& desc,
@@ -8075,7 +8078,11 @@ Result VKDevice::getFormatSupportedResourceStates(Format format, ResourceStateSe
return SLANG_OK;
}
-Result VKDevice::createBufferView(IBufferResource* buffer, IResourceView::Desc const& desc, IResourceView** outView)
+Result VKDevice::createBufferView(
+ IBufferResource* buffer,
+ IBufferResource* counterBuffer,
+ IResourceView::Desc const& desc,
+ IResourceView** outView)
{
auto resourceImpl = (BufferResourceImpl*) buffer;
@@ -8244,15 +8251,16 @@ Result VKDevice::createProgram(
const IShaderProgram::Desc& desc, IShaderProgram** outProgram, ISlangBlob** outDiagnosticBlob)
{
RefPtr<ShaderProgramImpl> shaderProgram = new ShaderProgramImpl(this);
- shaderProgram->slangProgram = desc.slangProgram;
+ shaderProgram->init(desc);
+
m_deviceObjectsWithPotentialBackReferences.add(shaderProgram);
RootShaderObjectLayout::create(
this,
- desc.slangProgram,
- desc.slangProgram->getLayout(),
+ shaderProgram->linkedProgram,
+ shaderProgram->linkedProgram->getLayout(),
shaderProgram->m_rootObjectLayout.writeRef());
- if (desc.slangProgram->getSpecializationParamCount() != 0)
+ if (shaderProgram->isSpecializable())
{
// For a specializable program, we don't invoke any actual slang compilation yet.
returnComPtr(outProgram, shaderProgram);
@@ -8260,15 +8268,15 @@ Result VKDevice::createProgram(
}
// For a fully specialized program, create `VkShaderModule`s for each shader stage.
- auto programReflection = desc.slangProgram->getLayout();
- for (SlangUInt i = 0; i < programReflection->getEntryPointCount(); i++)
+ auto compileShader = [&](slang::EntryPointReflection* entryPointInfo,
+ slang::IComponentType* component,
+ SlangInt entryPointIndex)
{
- auto entryPointInfo = programReflection->getEntryPointByIndex(i);
auto stage = entryPointInfo->getStage();
ComPtr<ISlangBlob> kernelCode;
ComPtr<ISlangBlob> diagnostics;
- auto compileResult = desc.slangProgram->getEntryPointCode(
- (SlangInt)i, 0, kernelCode.writeRef(), diagnostics.writeRef());
+ auto compileResult = component->getEntryPointCode(
+ entryPointIndex, 0, kernelCode.writeRef(), diagnostics.writeRef());
if (diagnostics)
{
getDebugCallback()->handleMessage(
@@ -8295,6 +8303,27 @@ Result VKDevice::createProgram(
(VkShaderStageFlagBits)VulkanUtil::getShaderStage(stage),
shaderModule));
shaderProgram->m_modules.add(shaderModule);
+ return SLANG_OK;
+ };
+ if (shaderProgram->linkedEntryPoints.getCount() == 0)
+ {
+ // If the user does not explicitly specify entry point components, find them from
+ // `linkedEntryPoints`.
+ auto programReflection = shaderProgram->linkedProgram->getLayout();
+ for (SlangUInt i = 0; i < programReflection->getEntryPointCount(); i++)
+ {
+ auto entryPointInfo = programReflection->getEntryPointByIndex(i);
+ SLANG_RETURN_ON_FAIL(compileShader(entryPointInfo, shaderProgram->linkedProgram, (SlangInt)i));
+ }
+ }
+ else
+ {
+ // If the user specifies entry point components via the separated entry point array, compile
+ // code from there.
+ for (auto& entryPoint : shaderProgram->linkedEntryPoints)
+ {
+ SLANG_RETURN_ON_FAIL(compileShader(entryPoint->getLayout()->getEntryPointByIndex(0), entryPoint, 0));
+ }
}
returnComPtr(outProgram, shaderProgram);
return SLANG_OK;
diff --git a/tools/platform/gui.cpp b/tools/platform/gui.cpp
index 37e69114a..84d458e71 100644
--- a/tools/platform/gui.cpp
+++ b/tools/platform/gui.cpp
@@ -98,7 +98,7 @@ GUI::GUI(
#if 0
gfx::IShaderProgram::Desc programDesc = {};
programDesc.pipelineType = gfx::PipelineType::Graphics;
- programDesc.slangProgram = slangProgram;
+ programDesc.slangGlobalScope = slangGlobalScope;
program = device->createProgram(programDesc);
#endif
InputElementDesc inputElements[] = {
diff --git a/tools/render-test/render-test-main.cpp b/tools/render-test/render-test-main.cpp
index d36ee8a86..4b46f8115 100644
--- a/tools/render-test/render-test-main.cpp
+++ b/tools/render-test/render-test-main.cpp
@@ -213,9 +213,7 @@ struct AssignValsFromLayoutContext
viewDesc.type = IResourceView::Type::UnorderedAccess;
viewDesc.format = srcBuffer.format;
viewDesc.bufferElementSize = srcVal->bufferDesc.stride;
- auto bufferView = device->createBufferView(
- bufferResource,
- viewDesc);
+ auto bufferView = device->createBufferView(bufferResource, nullptr, viewDesc);
dstCursor.setResource(bufferView);
maybeAddOutput(dstCursor, srcVal, bufferResource);
diff --git a/tools/render-test/slang-support.cpp b/tools/render-test/slang-support.cpp
index 8240212ec..ed7bb752e 100644
--- a/tools/render-test/slang-support.cpp
+++ b/tools/render-test/slang-support.cpp
@@ -54,13 +54,13 @@ void ShaderCompilerUtil::Output::set(
slang::IComponentType* inSlangProgram)
{
slangProgram = inSlangProgram;
- desc.slangProgram = inSlangProgram;
+ desc.slangGlobalScope = inSlangProgram;
}
void ShaderCompilerUtil::Output::reset()
{
{
- desc.slangProgram = nullptr;
+ desc.slangGlobalScope = nullptr;
}
session = nullptr;
@@ -313,7 +313,7 @@ void ShaderCompilerUtil::Output::reset()
SLANG_RETURN_ON_FAIL(_compileProgramImpl(session, options, input, request, out));
out.m_extraRequestForReflection = slangOutput.getRequestForReflection();
- out.desc.slangProgram = slangOutput.desc.slangProgram;
+ out.desc.slangGlobalScope = slangOutput.desc.slangGlobalScope;
slangOutput.m_requestForKernels = nullptr;
return SLANG_OK;
diff --git a/tools/slang-unit-test/unit-test-chunked-list.cpp b/tools/slang-unit-test/unit-test-chunked-list.cpp
new file mode 100644
index 000000000..af4f597b2
--- /dev/null
+++ b/tools/slang-unit-test/unit-test-chunked-list.cpp
@@ -0,0 +1,41 @@
+// unit-test-path.cpp
+
+#include "source/core/slang-basic.h"
+#include "source/core/slang-chunked-list.h"
+#include "tools/unit-test/slang-unit-test.h"
+
+using namespace Slang;
+
+template<typename T>
+static bool _checkArrayView(ArrayView<T> v0, ArrayView<T> v1)
+{
+ if (v0.getCount() != v1.getCount())
+ return false;
+ for (Index i = 0; i < v0.getCount(); i++)
+ if (v0[i] != v1[i])
+ return false;
+ return true;
+}
+
+SLANG_UNIT_TEST(chunkedList)
+{
+ {
+ ChunkedList<String> stringList;
+ List<String*> ptrs;
+ for (int i = 0; i < 256; i++)
+ {
+ ptrs.add(stringList.add(String(i)));
+ }
+ SLANG_CHECK(stringList.getCount() == 256);
+ SLANG_CHECK(*(ptrs[128]) == "128");
+
+ stringList.clearAndDeallocate();
+ ptrs.clear();
+ for (int i = 0; i < 64; i++)
+ {
+ ptrs.add(stringList.add(String(i)));
+ }
+ SLANG_CHECK(stringList.getCount() == 64);
+ SLANG_CHECK(*(ptrs[32]) == "32");
+ }
+}