summaryrefslogtreecommitdiffstats
path: root/source/slang
diff options
context:
space:
mode:
authorJay Kwak <82421531+jkwak-work@users.noreply.github.com>2024-05-14 20:28:28 -0700
committerGitHub <noreply@github.com>2024-05-14 20:28:28 -0700
commitcc88530a722cc2ce7a09f2a39dadeeb504e2f221 (patch)
tree2b2c3e56a4f4e13044a370f792e3d386b3d3f2ac /source/slang
parent4edc72e4dea47cf549b4e28940e3509a5ab61439 (diff)
Support combined textures for Metal target (#4169)
Diffstat (limited to 'source/slang')
-rw-r--r--source/slang/hlsl.meta.slang106
-rw-r--r--source/slang/slang-emit.cpp11
2 files changed, 92 insertions, 25 deletions
diff --git a/source/slang/hlsl.meta.slang b/source/slang/hlsl.meta.slang
index f318eb79e..176c7c0e4 100644
--- a/source/slang/hlsl.meta.slang
+++ b/source/slang/hlsl.meta.slang
@@ -529,13 +529,14 @@ extension __TextureImpl<T,Shape,isArray,isMS,sampleCount,0,isShadow,1,format>
[__readNone]
[ForceInline]
- [require(glsl_hlsl_spirv, texture_querylod)]
+ [require(glsl_hlsl_metal_spirv, texture_querylod)]
float CalculateLevelOfDetail(TextureCoord location)
{
__requireComputeDerivative();
__target_switch
{
case hlsl:
+ case metal:
{
return __getTexture().CalculateLevelOfDetail(__getSampler(), location);
}
@@ -551,13 +552,14 @@ extension __TextureImpl<T,Shape,isArray,isMS,sampleCount,0,isShadow,1,format>
[__readNone]
[ForceInline]
- [require(glsl_hlsl_spirv, texture_querylod)]
+ [require(glsl_hlsl_metal_spirv, texture_querylod)]
float CalculateLevelOfDetailUnclamped(TextureCoord location)
{
__requireComputeDerivative();
__target_switch
{
case hlsl:
+ case metal:
{
return __getTexture().CalculateLevelOfDetailUnclamped(__getSampler(), location);
}
@@ -573,7 +575,7 @@ extension __TextureImpl<T,Shape,isArray,isMS,sampleCount,0,isShadow,1,format>
[__readNone]
[ForceInline]
- [require(cpp_cuda_glsl_hlsl_spirv, texture_sm_4_1_fragment)]
+ [require(cpp_cuda_glsl_hlsl_metal_spirv, texture_sm_4_1_fragment)]
T Sample(vector<float, Shape.dimensions+isArray> location)
{
__requireComputeDerivative();
@@ -581,6 +583,7 @@ extension __TextureImpl<T,Shape,isArray,isMS,sampleCount,0,isShadow,1,format>
{
case cpp:
case hlsl:
+ case metal:
return __getTexture().Sample(__getSampler(), location);
case glsl:
__intrinsic_asm "$ctexture($0, $1)$z";
@@ -624,8 +627,32 @@ extension __TextureImpl<T,Shape,isArray,isMS,sampleCount,0,isShadow,1,format>
[__readNone]
[ForceInline]
+ [require(cpp_glsl_hlsl_metal_spirv, texture_sm_4_1_fragment)]
+ T Sample(vector<float, Shape.dimensions+isArray> location, constexpr vector<int, Shape.planeDimensions> offset)
+ {
+ __requireComputeDerivative();
+ __target_switch
+ {
+ case cpp:
+ case hlsl:
+ case metal:
+ return __getTexture().Sample(__getSampler(), location, offset);
+ case glsl:
+ __intrinsic_asm "$ctextureOffsetClampARB($0, $1, $2)$z";
+ case spirv:
+ return spirv_asm
+ {
+ OpCapability MinLod;
+ %sampled : __sampledType(T) = OpImageSampleImplicitLod $this $location None|ConstOffset $offset;
+ __truncate $$T result __sampledType(T) %sampled;
+ };
+ }
+ }
+
+ [__readNone]
+ [ForceInline]
__glsl_extension(GL_ARB_sparse_texture_clamp)
- [require(cpp_glsl_hlsl_spirv, texture_sm_4_1_fragment)]
+ [require(cpp_glsl_hlsl_metal_spirv, texture_sm_4_1_fragment)]
T Sample(vector<float, Shape.dimensions+isArray> location, vector<int, Shape.planeDimensions> offset, float clamp)
{
__requireComputeDerivative();
@@ -633,6 +660,7 @@ extension __TextureImpl<T,Shape,isArray,isMS,sampleCount,0,isShadow,1,format>
{
case cpp:
case hlsl:
+ case metal:
return __getTexture().Sample(__getSampler(), location, offset, clamp);
case glsl:
__intrinsic_asm "$ctextureOffsetClampARB($0, $1, $2, $3)$z";
@@ -648,7 +676,7 @@ extension __TextureImpl<T,Shape,isArray,isMS,sampleCount,0,isShadow,1,format>
[__readNone]
[ForceInline]
- [require(cpp_glsl_hlsl_spirv, texture_sm_4_1_fragment)]
+ [require(cpp_glsl_hlsl_metal_spirv, texture_sm_4_1_fragment)]
T Sample(vector<float, Shape.dimensions+isArray> location, vector<int, Shape.planeDimensions> offset, float clamp, out uint status)
{
__target_switch
@@ -662,7 +690,7 @@ extension __TextureImpl<T,Shape,isArray,isMS,sampleCount,0,isShadow,1,format>
[__readNone]
[ForceInline]
- [require(cpp_glsl_hlsl_spirv, texture_sm_4_1_fragment)]
+ [require(cpp_glsl_hlsl_metal_spirv, texture_sm_4_1_fragment)]
T SampleBias(vector<float, Shape.dimensions+isArray> location, float bias)
{
__requireComputeDerivative();
@@ -670,6 +698,7 @@ extension __TextureImpl<T,Shape,isArray,isMS,sampleCount,0,isShadow,1,format>
{
case cpp:
case hlsl:
+ case metal:
return __getTexture().SampleBias(__getSampler(), location, bias);
case glsl:
__intrinsic_asm "$ctexture($0, $1, $2)$z";
@@ -685,7 +714,7 @@ extension __TextureImpl<T,Shape,isArray,isMS,sampleCount,0,isShadow,1,format>
[__readNone]
[ForceInline]
- [require(cpp_glsl_hlsl_spirv, texture_sm_4_1_fragment)]
+ [require(cpp_glsl_hlsl_metal_spirv, texture_sm_4_1_fragment)]
T SampleBias(vector<float, Shape.dimensions+isArray> location, float bias, constexpr vector<int, Shape.planeDimensions> offset)
{
__requireComputeDerivative();
@@ -693,6 +722,7 @@ extension __TextureImpl<T,Shape,isArray,isMS,sampleCount,0,isShadow,1,format>
{
case cpp:
case hlsl:
+ case metal:
return __getTexture().SampleBias(__getSampler(), location, bias, offset);
case glsl:
__intrinsic_asm "$ctextureOffset($0, $1, $3, $2)$z";
@@ -707,7 +737,7 @@ extension __TextureImpl<T,Shape,isArray,isMS,sampleCount,0,isShadow,1,format>
[__readNone]
[ForceInline]
- [require(glsl_hlsl_spirv, texture_shadowlod)]
+ [require(glsl_hlsl_metal_spirv, texture_shadowlod)]
float SampleCmp(vector<float, Shape.dimensions+isArray> location, float compareValue)
{
__target_switch
@@ -726,6 +756,7 @@ extension __TextureImpl<T,Shape,isArray,isMS,sampleCount,0,isShadow,1,format>
return __glsl_texture(this, __makeVector(location, compareValue));
}
case hlsl:
+ case metal:
return __getTexture().SampleCmp(__getComparisonSampler(), location, compareValue);
case spirv:
return spirv_asm
@@ -737,7 +768,7 @@ extension __TextureImpl<T,Shape,isArray,isMS,sampleCount,0,isShadow,1,format>
[__readNone]
[ForceInline]
- [require(glsl_hlsl_spirv, texture_shadowlod)]
+ [require(glsl_hlsl_metal_spirv, texture_shadowlod)]
float SampleCmpLevelZero(vector<float, Shape.dimensions+isArray> location, float compareValue)
{
__target_switch
@@ -752,6 +783,7 @@ extension __TextureImpl<T,Shape,isArray,isMS,sampleCount,0,isShadow,1,format>
return __glsl_texture_level_zero(this, __makeVector(location, compareValue));
}
case hlsl:
+ case metal:
return __getTexture().SampleCmpLevelZero(__getComparisonSampler(), location, compareValue);
case spirv:
const float zeroFloat = 0.0f;
@@ -764,7 +796,7 @@ extension __TextureImpl<T,Shape,isArray,isMS,sampleCount,0,isShadow,1,format>
[__readNone]
[ForceInline]
- [require(glsl_hlsl_spirv, texture_shadowlod)]
+ [require(glsl_hlsl_metal_spirv, texture_shadowlod)]
float SampleCmp(vector<float, Shape.dimensions+isArray> location, float compareValue, constexpr vector<int, Shape.planeDimensions> offset)
{
__target_switch
@@ -779,6 +811,7 @@ extension __TextureImpl<T,Shape,isArray,isMS,sampleCount,0,isShadow,1,format>
return __glsl_texture_offset(this, __makeVector(location, compareValue), offset);
}
case hlsl:
+ case metal:
return __getTexture().SampleCmp(__getComparisonSampler(), location, compareValue, offset);
case spirv:
return spirv_asm
@@ -790,7 +823,7 @@ extension __TextureImpl<T,Shape,isArray,isMS,sampleCount,0,isShadow,1,format>
[__readNone]
[ForceInline]
- [require(glsl_hlsl_spirv, texture_shadowlod)]
+ [require(glsl_hlsl_metal_spirv, texture_shadowlod)]
float SampleCmpLevelZero(vector<float, Shape.dimensions+isArray> location, float compareValue, constexpr vector<int, Shape.planeDimensions> offset)
{
__target_switch
@@ -805,6 +838,7 @@ extension __TextureImpl<T,Shape,isArray,isMS,sampleCount,0,isShadow,1,format>
return __glsl_texture_offset_level_zero(this, __makeVector(location, compareValue), offset);
}
case hlsl:
+ case metal:
return __getTexture().SampleCmpLevelZero(__getComparisonSampler(), location, compareValue, offset);
case spirv:
const float zeroFloat = 0.0f;
@@ -817,13 +851,14 @@ extension __TextureImpl<T,Shape,isArray,isMS,sampleCount,0,isShadow,1,format>
[__readNone]
[ForceInline]
- [require(cpp_glsl_hlsl_spirv, texture_sm_4_1)]
+ [require(cpp_glsl_hlsl_metal_spirv, texture_sm_4_1)]
T SampleGrad(vector<float, Shape.dimensions+isArray> location, vector<float, Shape.dimensions> gradX, vector<float, Shape.dimensions> gradY)
{
__target_switch
{
case cpp:
case hlsl:
+ case metal:
return __getTexture().SampleGrad(__getSampler(), location, gradX, gradY);
case glsl:
@@ -839,13 +874,14 @@ extension __TextureImpl<T,Shape,isArray,isMS,sampleCount,0,isShadow,1,format>
[__readNone]
[ForceInline]
- [require(cpp_glsl_hlsl_spirv, texture_sm_4_1)]
+ [require(cpp_glsl_hlsl_metal_spirv, texture_sm_4_1)]
T SampleGrad(vector<float, Shape.dimensions+isArray> location, vector<float, Shape.dimensions> gradX, vector<float, Shape.dimensions> gradY, constexpr vector<int, Shape.dimensions> offset)
{
__target_switch
{
case cpp:
case hlsl:
+ case metal:
return __getTexture().SampleGrad(__getSampler(), location, gradX, gradY, offset);
case glsl:
__intrinsic_asm "$ctextureGradOffset($0, $1, $2, $3, $4)$z";
@@ -861,13 +897,14 @@ extension __TextureImpl<T,Shape,isArray,isMS,sampleCount,0,isShadow,1,format>
[__readNone]
[ForceInline]
__glsl_extension(GL_ARB_sparse_texture_clamp)
- [require(cpp_glsl_hlsl_spirv, texture_sm_4_1)]
+ [require(cpp_glsl_hlsl_metal_spirv, texture_sm_4_1)]
T SampleGrad(vector<float, Shape.dimensions+isArray> location, vector<float, Shape.dimensions> gradX, vector<float, Shape.dimensions> gradY, constexpr vector<int, Shape.dimensions> offset, float lodClamp)
{
__target_switch
{
case cpp:
case hlsl:
+ case metal:
return __getTexture().SampleGrad(__getSampler(), location, gradX, gradY, offset, lodClamp);
case glsl:
__intrinsic_asm "$ctextureGradOffsetClampARB($0, $1, $2, $3, $4, $5)$z";
@@ -883,13 +920,14 @@ extension __TextureImpl<T,Shape,isArray,isMS,sampleCount,0,isShadow,1,format>
[__readNone]
[ForceInline]
- [require(cpp_cuda_glsl_hlsl_spirv, texture_sm_4_1)]
+ [require(cpp_cuda_glsl_hlsl_metal_spirv, texture_sm_4_1)]
T SampleLevel(vector<float, Shape.dimensions+isArray> location, float level)
{
__target_switch
{
case cpp:
case hlsl:
+ case metal:
return __getTexture().SampleLevel(__getSampler(), location, level);
case glsl:
__intrinsic_asm "$ctextureLod($0, $1, $2)$z";
@@ -935,13 +973,14 @@ extension __TextureImpl<T,Shape,isArray,isMS,sampleCount,0,isShadow,1,format>
[__readNone]
[ForceInline]
- [require(cpp_glsl_hlsl_spirv, texture_sm_4_1)]
+ [require(cpp_glsl_hlsl_metal_spirv, texture_sm_4_1)]
T SampleLevel(vector<float, Shape.dimensions+isArray> location, float level, constexpr vector<int, Shape.planeDimensions> offset)
{
__target_switch
{
case cpp:
case hlsl:
+ case metal:
return __getTexture().SampleLevel(__getSampler(), location, level, offset);
case glsl:
@@ -2109,15 +2148,29 @@ for (int isScalarTexture = 0; isScalarTexture <= 1; isScalarTexture++) {
}}}}
{ // begin extension for gather
${{{{
+ if (isCombined)
+ {
+}}}}
+ __intrinsic_op($(kIROp_CombinedTextureSamplerGetTexture))
+ __TextureImpl<T, Shape, isArray, isMS, sampleCount, 0, isShadow, 0, format> __getTexture();
+
+ __intrinsic_op($(kIROp_CombinedTextureSamplerGetSampler))
+ SamplerState __getSampler();
+
+ __intrinsic_op($(kIROp_CombinedTextureSamplerGetSampler))
+ SamplerComparisonState __getComparisonSampler();
+${{{{
+ }
+
// Gather component
const char* samplerStateParam = isCombined ? "" : " s,";
- const char* metalSupport = isCombined ? "" : "metal_";
- const char* caseMetal = isCombined ? "" : "case metal:";
+ const char* getTexture = isCombined ? "__getTexture()" : "this";
for (int isCmp = 0; isCmp < 2; ++isCmp) {
const char* cmp = isCmp ? "Cmp" : "";
const char* cmpParam = isCmp ? ", T compareValue" : "";
const char* compareArg = isCmp ? ", compareValue" : "";
const char* samplerStateType = isCombined ? "" : (isCmp ? "SamplerComparisonState" : "SamplerState");
+ const char* getSampler = isCombined ? (isCmp ? " __getComparisonSampler()," : " __getSampler(),") : samplerStateParam;
const char* componentNames[] = { "", "Red", "Green", "Blue", "Alpha"};
const char* glslComponentNames[] = { ", 0", ", 1", ", 2", ", 3" };
@@ -2126,26 +2179,28 @@ ${{{{
auto glslComponent = (isCmp ? "" :glslComponentNames[componentId == 0 ? 0 : componentId - 1]);
}}}}
[ForceInline]
- [require(glsl_hlsl_$(metalSupport)spirv, texture_gather)]
+ [require(glsl_hlsl_metal_spirv, texture_gather)]
vector<T,4> Gather$(cmp)$(componentName)($(samplerStateType)$(samplerStateParam) vector<float, Shape.dimensions+isArray> location $(cmpParam))
{
__target_switch
{
case hlsl: __intrinsic_asm ".Gather$(cmp)$(componentName)";
- $(caseMetal)
+ case metal:
+ return __texture_gather$(cmp)<T>($(getTexture),$(getSampler) location $(compareArg) $(glslComponent));
case glsl:
case spirv:
return __texture_gather$(cmp)<T>(this,$(samplerStateParam) location $(compareArg) $(glslComponent));
}
}
[ForceInline]
- [require(glsl_hlsl_$(metalSupport)spirv, texture_gather)]
+ [require(glsl_hlsl_metal_spirv, texture_gather)]
vector<T,4> Gather$(cmp)$(componentName)($(samplerStateType)$(samplerStateParam) vector<float, Shape.dimensions+isArray> location $(cmpParam), constexpr vector<int, Shape.planeDimensions> offset)
{
__target_switch
{
case hlsl: __intrinsic_asm ".Gather$(cmp)$(componentName)";
- $(caseMetal)
+ case metal:
+ return __texture_gather$(cmp)_offset<T>($(getTexture),$(getSampler) location $(compareArg), offset $(glslComponent));
case glsl:
case spirv:
return __texture_gather$(cmp)_offset<T>(this,$(samplerStateParam) location $(compareArg), offset $(glslComponent));
@@ -2347,7 +2402,7 @@ extension __TextureImpl<T,Shape,isArray,0,sampleCount,0,isShadow,isCombined,form
__glsl_extension(GL_EXT_samplerless_texture_functions)
[__readNone]
[ForceInline]
- [require(cpp_glsl_hlsl_spirv, texture_sm_4_1_samplerless)]
+ [require(cpp_glsl_hlsl_metal_spirv, texture_sm_4_1_samplerless)]
get
{
__target_switch
@@ -2355,6 +2410,8 @@ extension __TextureImpl<T,Shape,isArray,0,sampleCount,0,isShadow,isCombined,form
case cpp:
case hlsl:
__intrinsic_asm ".operator[]";
+ case metal:
+ return Load(__makeVector(location, 0));
case glsl:
return __glsl_load(location);
case spirv:
@@ -2511,7 +2568,7 @@ extension __TextureImpl<T,Shape,isArray,1,sampleCount,0,isShadow,isCombined,form
__glsl_extension(GL_EXT_samplerless_texture_functions)
[__readNone]
[ForceInline]
- [require(cpp_glsl_hlsl_spirv, texture_sm_4_1_samplerless)]
+ [require(cpp_glsl_hlsl_metal_spirv, texture_sm_4_1_samplerless)]
get
{
__target_switch
@@ -2519,6 +2576,7 @@ extension __TextureImpl<T,Shape,isArray,1,sampleCount,0,isShadow,isCombined,form
case cpp:
case hlsl:
__intrinsic_asm "($0).sample[$2][$1]";
+ case metal:
case glsl:
case spirv:
return Load(location, sampleIndex);
diff --git a/source/slang/slang-emit.cpp b/source/slang/slang-emit.cpp
index ab22e1f90..7cc056009 100644
--- a/source/slang/slang-emit.cpp
+++ b/source/slang/slang-emit.cpp
@@ -550,9 +550,18 @@ Result linkAndOptimizeIR(
lowerAppendConsumeStructuredBuffers(targetProgram, irModule, sink);
}
- if (target == CodeGenTarget::HLSL || ArtifactDescUtil::isCpuLikeTarget(artifactDesc))
+ switch (target)
{
+ default:
+ if (!ArtifactDescUtil::isCpuLikeTarget(artifactDesc))
+ break;
+ [[fallthrough]];
+ case CodeGenTarget::HLSL:
+ case CodeGenTarget::Metal:
+ case CodeGenTarget::MetalLib:
+ case CodeGenTarget::MetalLibAssembly:
lowerCombinedTextureSamplers(irModule, sink);
+ break;
}
addUserTypeHintDecorations(irModule);