hlsl/writer: Fix output for texture intrinsics and types

Fixed: tint:146
Change-Id: Icf356faf7bee364a0783c717ee76ea98056b4401
Reviewed-on: https://dawn-review.googlesource.com/c/tint/+/42022
Commit-Queue: Ben Clayton <bclayton@google.com>
Reviewed-by: dan sinclair <dsinclair@chromium.org>
This commit is contained in:
Ben Clayton 2021-02-18 16:49:48 +00:00 committed by Commit Bot service account
parent 1d5a7eb82f
commit 15daded41b
3 changed files with 195 additions and 82 deletions

View File

@ -58,7 +58,9 @@
#include "src/type/f32_type.h" #include "src/type/f32_type.h"
#include "src/type/i32_type.h" #include "src/type/i32_type.h"
#include "src/type/matrix_type.h" #include "src/type/matrix_type.h"
#include "src/type/multisampled_texture_type.h"
#include "src/type/pointer_type.h" #include "src/type/pointer_type.h"
#include "src/type/sampled_texture_type.h"
#include "src/type/sampler_type.h" #include "src/type/sampler_type.h"
#include "src/type/storage_texture_type.h" #include "src/type/storage_texture_type.h"
#include "src/type/struct_type.h" #include "src/type/struct_type.h"
@ -161,7 +163,10 @@ bool GeneratorImpl::Generate(std::ostream& out) {
} }
} }
// emitted_globals is a set used to ensure that globals are emitted once even
// if they are used by multiple entry points.
std::unordered_set<Symbol> emitted_globals; std::unordered_set<Symbol> emitted_globals;
// Make sure all entry point data is emitted before the entry point functions // Make sure all entry point data is emitted before the entry point functions
for (auto* func : builder_.AST().Functions()) { for (auto* func : builder_.AST().Functions()) {
if (!func->IsEntryPoint()) { if (!func->IsEntryPoint()) {
@ -791,9 +796,9 @@ bool GeneratorImpl::EmitTextureCall(std::ostream& pre,
case semantic::IntrinsicType::kTextureNumLevels: case semantic::IntrinsicType::kTextureNumLevels:
case semantic::IntrinsicType::kTextureNumSamples: { case semantic::IntrinsicType::kTextureNumSamples: {
// All of these intrinsics use the GetDimensions() method on the texture // All of these intrinsics use the GetDimensions() method on the texture
bool is_ms = texture_type->Is<type::MultisampledTexture>();
int num_dimensions = 0; int num_dimensions = 0;
const char* swizzle = ""; std::string swizzle;
bool add_mip_level_in = false;
switch (intrinsic->Type()) { switch (intrinsic->Type()) {
case semantic::IntrinsicType::kTextureDimensions: case semantic::IntrinsicType::kTextureDimensions:
@ -809,10 +814,11 @@ bool GeneratorImpl::EmitTextureCall(std::ostream& pre,
swizzle = ".x"; swizzle = ".x";
break; break;
case type::TextureDimension::k2d: case type::TextureDimension::k2d:
num_dimensions = 2; num_dimensions = is_ms ? 3 : 2;
swizzle = is_ms ? ".xy" : "";
break; break;
case type::TextureDimension::k2dArray: case type::TextureDimension::k2dArray:
num_dimensions = 3; num_dimensions = is_ms ? 4 : 3;
swizzle = ".xy"; swizzle = ".xy";
break; break;
case type::TextureDimension::k3d: case type::TextureDimension::k3d:
@ -838,10 +844,13 @@ bool GeneratorImpl::EmitTextureCall(std::ostream& pre,
TINT_ICE(diagnostics_) << "texture dimension is not arrayed"; TINT_ICE(diagnostics_) << "texture dimension is not arrayed";
return false; return false;
case type::TextureDimension::k1dArray: case type::TextureDimension::k1dArray:
num_dimensions = 2; num_dimensions = is_ms ? 3 : 2;
swizzle = ".y"; swizzle = ".y";
break; break;
case type::TextureDimension::k2dArray: case type::TextureDimension::k2dArray:
num_dimensions = is_ms ? 4 : 3;
swizzle = ".z";
break;
case type::TextureDimension::kCubeArray: case type::TextureDimension::kCubeArray:
num_dimensions = 3; num_dimensions = 3;
swizzle = ".z"; swizzle = ".z";
@ -849,7 +858,6 @@ bool GeneratorImpl::EmitTextureCall(std::ostream& pre,
} }
break; break;
case semantic::IntrinsicType::kTextureNumLevels: case semantic::IntrinsicType::kTextureNumLevels:
add_mip_level_in = true;
switch (texture_type->dim()) { switch (texture_type->dim()) {
default: default:
TINT_ICE(diagnostics_) TINT_ICE(diagnostics_)
@ -889,34 +897,63 @@ bool GeneratorImpl::EmitTextureCall(std::ostream& pre,
return false; return false;
} }
auto* level_arg = arg(Usage::kLevel);
if (level_arg) {
// `NumberOfLevels` is a non-optional argument if `MipLevel` was passed.
// Increment the number of dimensions for the temporary vector to
// accommodate this.
num_dimensions++;
// If the swizzle was empty, the expression will evaluate to the whole
// vector. As we've grown the vector by one element, we now need to
// swizzle to keep the result expression equivalent.
if (swizzle.empty()) {
static constexpr const char* swizzles[] = {"", ".x", ".xy", ".xyz"};
swizzle = swizzles[num_dimensions - 1];
}
}
if (num_dimensions > 4) {
TINT_ICE(diagnostics_)
<< "Texture query intrinsic temporary vector has " << num_dimensions
<< " dimensions";
return false;
}
// Declare a variable to hold the queried texture info // Declare a variable to hold the queried texture info
auto dims = generate_name(kTempNamePrefix); auto dims = generate_name(kTempNamePrefix);
if (num_dimensions == 1) { if (num_dimensions == 1) {
pre << "int " << dims << ";\n"; pre << "int " << dims << ";";
} else { } else {
pre << "int" << num_dimensions << " " << dims << ";\n"; pre << "int" << num_dimensions << " " << dims << ";";
} }
pre << std::endl;
make_indent(pre);
if (!EmitExpression(pre, pre, texture)) { if (!EmitExpression(pre, pre, texture)) {
return false; return false;
} }
pre << ".GetDimensions("; pre << ".GetDimensions(";
if (auto* level = arg(Usage::kLevel)) {
if (!EmitExpression(pre, pre, level)) { if (level_arg) {
if (!EmitExpression(pre, pre, level_arg)) {
return false; return false;
} }
pre << ", "; pre << ", ";
} else if (add_mip_level_in) { } else if (intrinsic->Type() ==
semantic::IntrinsicType::kTextureNumLevels) {
pre << "0, "; pre << "0, ";
} }
if (num_dimensions == 1) { if (num_dimensions == 1) {
pre << dims; pre << dims;
} else { } else {
static constexpr char xyzw[] = {'x', 'y', 'z', 'w'};
assert(num_dimensions > 0); assert(num_dimensions > 0);
assert(num_dimensions <= 4); assert(num_dimensions <= 4);
static constexpr char xyzw[] = {'x', 'y', 'z', 'w'};
for (int i = 0; i < num_dimensions; i++) { for (int i = 0; i < num_dimensions; i++) {
if (i > 0) { if (i > 0) {
pre << ", "; pre << ", ";
@ -924,7 +961,9 @@ bool GeneratorImpl::EmitTextureCall(std::ostream& pre,
pre << dims << "." << xyzw[i]; pre << dims << "." << xyzw[i];
} }
} }
pre << ");";
pre << ");" << std::endl;
make_indent(pre);
// The out parameters of the GetDimensions() call is now in temporary // The out parameters of the GetDimensions() call is now in temporary
// `dims` variable. This may be packed with other data, so the final // `dims` variable. This may be packed with other data, so the final
@ -1578,6 +1617,11 @@ bool GeneratorImpl::EmitEntryPointData(
for (auto data : func_sem->ReferencedUniformVariables()) { for (auto data : func_sem->ReferencedUniformVariables()) {
auto* var = data.first; auto* var = data.first;
auto* decl = var->Declaration(); auto* decl = var->Declaration();
if (!emitted_globals.emplace(decl->symbol()).second) {
continue; // Global already emitted
}
// TODO(dsinclair): We're using the binding to make up the buffer number but // TODO(dsinclair): We're using the binding to make up the buffer number but
// we should instead be using a provided mapping that uses both buffer and // we should instead be using a provided mapping that uses both buffer and
// set. https://bugs.chromium.org/p/tint/issues/detail?id=104 // set. https://bugs.chromium.org/p/tint/issues/detail?id=104
@ -1590,13 +1634,6 @@ bool GeneratorImpl::EmitEntryPointData(
} }
// auto* set = data.second.set; // auto* set = data.second.set;
// If the global has already been emitted we skip it, it's been emitted by
// a previous entry point.
if (emitted_globals.count(decl->symbol()) != 0) {
continue;
}
emitted_globals.insert(decl->symbol());
auto* type = decl->type()->UnwrapIfNeeded(); auto* type = decl->type()->UnwrapIfNeeded();
if (auto* strct = type->As<type::Struct>()) { if (auto* strct = type->As<type::Struct>()) {
out << "ConstantBuffer<" << builder_.Symbols().NameFor(strct->symbol()) out << "ConstantBuffer<" << builder_.Symbols().NameFor(strct->symbol())
@ -1634,15 +1671,12 @@ bool GeneratorImpl::EmitEntryPointData(
for (auto data : func_sem->ReferencedStorageBufferVariables()) { for (auto data : func_sem->ReferencedStorageBufferVariables()) {
auto* var = data.first; auto* var = data.first;
auto* decl = var->Declaration(); auto* decl = var->Declaration();
auto* binding = data.second.binding;
// If the global has already been emitted we skip it, it's been emitted by if (!emitted_globals.emplace(decl->symbol()).second) {
// a previous entry point. continue; // Global already emitted
if (emitted_globals.count(decl->symbol()) != 0) {
continue;
} }
emitted_globals.insert(decl->symbol());
auto* binding = data.second.binding;
auto* ac = decl->type()->As<type::AccessControl>(); auto* ac = decl->type()->As<type::AccessControl>();
if (ac == nullptr) { if (ac == nullptr) {
diagnostics_.add_error("access control type required for storage buffer"); diagnostics_.add_error("access control type required for storage buffer");
@ -1762,6 +1796,34 @@ bool GeneratorImpl::EmitEntryPointData(
out << "};" << std::endl << std::endl; out << "};" << std::endl << std::endl;
} }
{
bool add_newline = false;
for (auto* var : func_sem->ReferencedModuleVariables()) {
auto* decl = var->Declaration();
auto* unwrapped_type = decl->type()->UnwrapAll();
if (!unwrapped_type->Is<type::Texture>() &&
!unwrapped_type->Is<type::Sampler>()) {
continue; // Not interested in this type
}
if (!emitted_globals.emplace(decl->symbol()).second) {
continue; // Global already emitted
}
if (!EmitType(out, decl->type(), "")) {
return false;
}
out << " " << namer_.NameFor(builder_.Symbols().NameFor(decl->symbol()))
<< ";" << std::endl;
add_newline = true;
}
if (add_newline) {
out << std::endl;
}
}
return true; return true;
} }
@ -2314,6 +2376,9 @@ bool GeneratorImpl::EmitStatement(std::ostream& out, ast::Statement* stmt) {
return false; return false;
} }
out << pre.str(); out << pre.str();
if (!TypeOf(c->expr())->Is<type::Void>()) {
out << "(void) ";
}
out << call_out.str() << ";" << std::endl; out << call_out.str() << ";" << std::endl;
return true; return true;
} }
@ -2439,6 +2504,8 @@ bool GeneratorImpl::EmitType(std::ostream& out,
} }
out << "Texture"; out << "Texture";
auto* ms = tex->As<type::MultisampledTexture>();
switch (tex->dim()) { switch (tex->dim()) {
case type::TextureDimension::k1d: case type::TextureDimension::k1d:
out << "1D"; out << "1D";
@ -2447,10 +2514,10 @@ bool GeneratorImpl::EmitType(std::ostream& out,
out << "1DArray"; out << "1DArray";
break; break;
case type::TextureDimension::k2d: case type::TextureDimension::k2d:
out << "2D"; out << (ms ? "2DMS" : "2D");
break; break;
case type::TextureDimension::k2dArray: case type::TextureDimension::k2dArray:
out << "2DArray"; out << (ms ? "2DMSArray" : "2DArray");
break; break;
case type::TextureDimension::k3d: case type::TextureDimension::k3d:
out << "3D"; out << "3D";
@ -2462,11 +2529,31 @@ bool GeneratorImpl::EmitType(std::ostream& out,
out << "CubeArray"; out << "CubeArray";
break; break;
default: default:
diagnostics_.add_error("Invalid texture dimensions"); TINT_UNREACHABLE(diagnostics_)
<< "unexpected TextureDimension " << tex->dim();
return false; return false;
} }
if (auto* st = tex->As<type::StorageTexture>()) { if (ms) {
out << "<";
if (ms->type()->Is<type::F32>()) {
out << "float4";
} else if (ms->type()->Is<type::I32>()) {
out << "int4";
} else if (ms->type()->Is<type::U32>()) {
out << "uint4";
} else {
TINT_ICE(diagnostics_) << "Unsupported multisampled texture type";
return false;
}
// TODO(ben-clayton): The HLSL docs claim that the MS texture type should
// also contain the number of samples, which is not part of the WGSL type.
// However, DXC seems to consider this optional.
// See: https://github.com/gpuweb/gpuweb/issues/1445
out << ">";
} else if (auto* st = tex->As<type::StorageTexture>()) {
auto* component = image_format_to_rwtexture_type(st->image_format()); auto* component = image_format_to_rwtexture_type(st->image_format());
if (component == nullptr) { if (component == nullptr) {
TINT_ICE(diagnostics_) << "Unsupported StorageTexture ImageFormat: " TINT_ICE(diagnostics_) << "Unsupported StorageTexture ImageFormat: "

View File

@ -44,127 +44,153 @@ ExpectedResult expected_texture_overload(
case ValidTextureOverload::kDimensionsStorageRO1d: case ValidTextureOverload::kDimensionsStorageRO1d:
case ValidTextureOverload::kDimensionsStorageWO1d: case ValidTextureOverload::kDimensionsStorageWO1d:
return { return {
"int _tint_tmp;\n" R"(int _tint_tmp;
"texture_tint_0.GetDimensions(_tint_tmp);", texture_tint_0.GetDimensions(_tint_tmp);
)",
"_tint_tmp", "_tint_tmp",
}; };
case ValidTextureOverload::kDimensions1dArray: case ValidTextureOverload::kDimensions1dArray:
case ValidTextureOverload::kDimensionsStorageRO1dArray: case ValidTextureOverload::kDimensionsStorageRO1dArray:
case ValidTextureOverload::kDimensionsStorageWO1dArray: case ValidTextureOverload::kDimensionsStorageWO1dArray:
return { return {
"int2 _tint_tmp;\n" R"(int2 _tint_tmp;
"texture_tint_0.GetDimensions(_tint_tmp.x, _tint_tmp.y);", texture_tint_0.GetDimensions(_tint_tmp.x, _tint_tmp.y);
)",
"_tint_tmp.x", "_tint_tmp.x",
}; };
case ValidTextureOverload::kDimensions2d: case ValidTextureOverload::kDimensions2d:
case ValidTextureOverload::kDimensionsMultisampled2d:
case ValidTextureOverload::kDimensionsDepth2d: case ValidTextureOverload::kDimensionsDepth2d:
case ValidTextureOverload::kDimensionsStorageRO2d: case ValidTextureOverload::kDimensionsStorageRO2d:
case ValidTextureOverload::kDimensionsStorageWO2d: case ValidTextureOverload::kDimensionsStorageWO2d:
return { return {
"int2 _tint_tmp;\n" R"(int2 _tint_tmp;
"texture_tint_0.GetDimensions(_tint_tmp.x, _tint_tmp.y);", texture_tint_0.GetDimensions(_tint_tmp.x, _tint_tmp.y);
)",
"_tint_tmp", "_tint_tmp",
}; };
case ValidTextureOverload::kDimensionsMultisampled2d:
return {
R"(int3 _tint_tmp;
texture_tint_0.GetDimensions(_tint_tmp.x, _tint_tmp.y, _tint_tmp.z);
)",
"_tint_tmp.xy",
};
case ValidTextureOverload::kDimensions2dArray: case ValidTextureOverload::kDimensions2dArray:
case ValidTextureOverload::kDimensionsMultisampled2dArray:
case ValidTextureOverload::kDimensionsDepth2dArray: case ValidTextureOverload::kDimensionsDepth2dArray:
case ValidTextureOverload::kDimensionsStorageRO2dArray: case ValidTextureOverload::kDimensionsStorageRO2dArray:
case ValidTextureOverload::kDimensionsStorageWO2dArray: case ValidTextureOverload::kDimensionsStorageWO2dArray:
return { return {
"int3 _tint_tmp;\n" R"(int3 _tint_tmp;
"texture_tint_0." texture_tint_0.GetDimensions(_tint_tmp.x, _tint_tmp.y, _tint_tmp.z);
"GetDimensions(_tint_tmp.x, _tint_tmp.y, _tint_tmp.z);", )",
"_tint_tmp.xy",
};
case ValidTextureOverload::kDimensionsMultisampled2dArray:
return {
R"(int4 _tint_tmp;
texture_tint_0.GetDimensions(_tint_tmp.x, _tint_tmp.y, _tint_tmp.z, _tint_tmp.w);
)",
"_tint_tmp.xy", "_tint_tmp.xy",
}; };
case ValidTextureOverload::kDimensions3d: case ValidTextureOverload::kDimensions3d:
case ValidTextureOverload::kDimensionsStorageRO3d: case ValidTextureOverload::kDimensionsStorageRO3d:
case ValidTextureOverload::kDimensionsStorageWO3d: case ValidTextureOverload::kDimensionsStorageWO3d:
return { return {
"int3 _tint_tmp;\n" R"(int3 _tint_tmp;
"texture_tint_0." texture_tint_0.GetDimensions(_tint_tmp.x, _tint_tmp.y, _tint_tmp.z);
"GetDimensions(_tint_tmp.x, _tint_tmp.y, _tint_tmp.z);", )",
"_tint_tmp", "_tint_tmp",
}; };
case ValidTextureOverload::kDimensionsCube: case ValidTextureOverload::kDimensionsCube:
case ValidTextureOverload::kDimensionsDepthCube: case ValidTextureOverload::kDimensionsDepthCube:
return { return {
"int2 _tint_tmp;\n" "int2 _tint_tmp;\n"
"texture_tint_0.GetDimensions(_tint_tmp.x, _tint_tmp.y);", "texture_tint_0.GetDimensions(_tint_tmp.x, _tint_tmp.y);\n",
"_tint_tmp.xyy", "_tint_tmp.xyy",
}; };
case ValidTextureOverload::kDimensionsCubeArray: case ValidTextureOverload::kDimensionsCubeArray:
case ValidTextureOverload::kDimensionsDepthCubeArray: case ValidTextureOverload::kDimensionsDepthCubeArray:
return { return {
"int3 _tint_tmp;\n" R"(int3 _tint_tmp;
"texture_tint_0." texture_tint_0.GetDimensions(_tint_tmp.x, _tint_tmp.y, _tint_tmp.z);
"GetDimensions(_tint_tmp.x, _tint_tmp.y, _tint_tmp.z);", )",
"_tint_tmp.xyy", "_tint_tmp.xyy",
}; };
case ValidTextureOverload::kDimensions2dLevel: case ValidTextureOverload::kDimensions2dLevel:
case ValidTextureOverload::kDimensionsDepth2dLevel: case ValidTextureOverload::kDimensionsDepth2dLevel:
return { return {
"int2 _tint_tmp;\n" R"(int3 _tint_tmp;
"texture_tint_0.GetDimensions(1, _tint_tmp.x, _tint_tmp.y);", texture_tint_0.GetDimensions(1, _tint_tmp.x, _tint_tmp.y, _tint_tmp.z);
"_tint_tmp", )",
"_tint_tmp.xy",
}; };
case ValidTextureOverload::kDimensions2dArrayLevel: case ValidTextureOverload::kDimensions2dArrayLevel:
case ValidTextureOverload::kDimensionsDepth2dArrayLevel: case ValidTextureOverload::kDimensionsDepth2dArrayLevel:
return { return {
"int3 _tint_tmp;\n" R"(int4 _tint_tmp;
"texture_tint_0." texture_tint_0.GetDimensions(1, _tint_tmp.x, _tint_tmp.y, _tint_tmp.z, _tint_tmp.w);
"GetDimensions(1, _tint_tmp.x, _tint_tmp.y, _tint_tmp.z);", )",
"_tint_tmp.xy", "_tint_tmp.xy",
}; };
case ValidTextureOverload::kDimensions3dLevel: case ValidTextureOverload::kDimensions3dLevel:
return { return {
"int3 _tint_tmp;\n" R"(int4 _tint_tmp;
"texture_tint_0." texture_tint_0.GetDimensions(1, _tint_tmp.x, _tint_tmp.y, _tint_tmp.z, _tint_tmp.w);
"GetDimensions(1, _tint_tmp.x, _tint_tmp.y, _tint_tmp.z);", )",
"_tint_tmp", "_tint_tmp.xyz",
}; };
case ValidTextureOverload::kDimensionsCubeLevel: case ValidTextureOverload::kDimensionsCubeLevel:
case ValidTextureOverload::kDimensionsDepthCubeLevel: case ValidTextureOverload::kDimensionsDepthCubeLevel:
return { return {
"int2 _tint_tmp;\n" R"(int3 _tint_tmp;
"texture_tint_0.GetDimensions(1, _tint_tmp.x, _tint_tmp.y);", texture_tint_0.GetDimensions(1, _tint_tmp.x, _tint_tmp.y, _tint_tmp.z);
)",
"_tint_tmp.xyy", "_tint_tmp.xyy",
}; };
case ValidTextureOverload::kDimensionsCubeArrayLevel: case ValidTextureOverload::kDimensionsCubeArrayLevel:
case ValidTextureOverload::kDimensionsDepthCubeArrayLevel: case ValidTextureOverload::kDimensionsDepthCubeArrayLevel:
return { return {
"int3 _tint_tmp;\n" R"(int4 _tint_tmp;
"texture_tint_0." texture_tint_0.GetDimensions(1, _tint_tmp.x, _tint_tmp.y, _tint_tmp.z, _tint_tmp.w);
"GetDimensions(1, _tint_tmp.x, _tint_tmp.y, _tint_tmp.z);", )",
"_tint_tmp.xyy", "_tint_tmp.xyy",
}; };
case ValidTextureOverload::kNumLayers1dArray: case ValidTextureOverload::kNumLayers1dArray:
case ValidTextureOverload::kNumLayersStorageWO1dArray: case ValidTextureOverload::kNumLayersStorageWO1dArray:
return { return {
"int2 _tint_tmp;\n" R"(int2 _tint_tmp;
"texture_tint_0.GetDimensions(_tint_tmp.x, _tint_tmp.y);", texture_tint_0.GetDimensions(_tint_tmp.x, _tint_tmp.y);
)",
"_tint_tmp.y", "_tint_tmp.y",
}; };
case ValidTextureOverload::kNumLayers2dArray: case ValidTextureOverload::kNumLayers2dArray:
case ValidTextureOverload::kNumLayersMultisampled2dArray:
case ValidTextureOverload::kNumLayersDepth2dArray: case ValidTextureOverload::kNumLayersDepth2dArray:
case ValidTextureOverload::kNumLayersCubeArray: case ValidTextureOverload::kNumLayersCubeArray:
case ValidTextureOverload::kNumLayersDepthCubeArray: case ValidTextureOverload::kNumLayersDepthCubeArray:
case ValidTextureOverload::kNumLayersStorageWO2dArray: case ValidTextureOverload::kNumLayersStorageWO2dArray:
return { return {
"int3 _tint_tmp;\n" R"(int3 _tint_tmp;
"texture_tint_0." texture_tint_0.GetDimensions(_tint_tmp.x, _tint_tmp.y, _tint_tmp.z);
"GetDimensions(_tint_tmp.x, _tint_tmp.y, _tint_tmp.z);", )",
"_tint_tmp.z", "_tint_tmp.z",
}; };
case ValidTextureOverload::kNumLayersMultisampled2dArray:
return {
R"(int4 _tint_tmp;
texture_tint_0.GetDimensions(_tint_tmp.x, _tint_tmp.y, _tint_tmp.z, _tint_tmp.w);
)",
"_tint_tmp.z",
};
case ValidTextureOverload::kNumLevels2d: case ValidTextureOverload::kNumLevels2d:
case ValidTextureOverload::kNumLevelsCube: case ValidTextureOverload::kNumLevelsCube:
case ValidTextureOverload::kNumLevelsDepth2d: case ValidTextureOverload::kNumLevelsDepth2d:
case ValidTextureOverload::kNumLevelsDepthCube: case ValidTextureOverload::kNumLevelsDepthCube:
return { return {
"int3 _tint_tmp;\n" R"(int3 _tint_tmp;
"texture_tint_0." texture_tint_0.GetDimensions(0, _tint_tmp.x, _tint_tmp.y, _tint_tmp.z);
"GetDimensions(0, _tint_tmp.x, _tint_tmp.y, _tint_tmp.z);", )",
"_tint_tmp.z", "_tint_tmp.z",
}; };
case ValidTextureOverload::kNumLevels2dArray: case ValidTextureOverload::kNumLevels2dArray:
@ -173,23 +199,23 @@ ExpectedResult expected_texture_overload(
case ValidTextureOverload::kNumLevelsDepth2dArray: case ValidTextureOverload::kNumLevelsDepth2dArray:
case ValidTextureOverload::kNumLevelsDepthCubeArray: case ValidTextureOverload::kNumLevelsDepthCubeArray:
return { return {
"int4 _tint_tmp;\n" R"(int4 _tint_tmp;
"texture_tint_0.GetDimensions(0, " texture_tint_0.GetDimensions(0, _tint_tmp.x, _tint_tmp.y, _tint_tmp.z, _tint_tmp.w);
"_tint_tmp.x, _tint_tmp.y, _tint_tmp.z, _tint_tmp.w);", )",
"_tint_tmp.w", "_tint_tmp.w",
}; };
case ValidTextureOverload::kNumSamplesMultisampled2d: case ValidTextureOverload::kNumSamplesMultisampled2d:
return { return {
"int3 _tint_tmp;\n" R"(int3 _tint_tmp;
"texture_tint_0." texture_tint_0.GetDimensions(_tint_tmp.x, _tint_tmp.y, _tint_tmp.z);
"GetDimensions(_tint_tmp.x, _tint_tmp.y, _tint_tmp.z);", )",
"_tint_tmp.z", "_tint_tmp.z",
}; };
case ValidTextureOverload::kNumSamplesMultisampled2dArray: case ValidTextureOverload::kNumSamplesMultisampled2dArray:
return { return {
"int4 _tint_tmp;\n" R"(int4 _tint_tmp;
"texture_tint_0." texture_tint_0.GetDimensions(_tint_tmp.x, _tint_tmp.y, _tint_tmp.z, _tint_tmp.w);
"GetDimensions(_tint_tmp.x, _tint_tmp.y, _tint_tmp.z, _tint_tmp.w);", )",
"_tint_tmp.w", "_tint_tmp.w",
}; };
case ValidTextureOverload::kSample1dF32: case ValidTextureOverload::kSample1dF32:

View File

@ -389,7 +389,7 @@ TEST_F(HlslGeneratorImplTest_Type, EmitMultisampledTexture) {
GeneratorImpl& gen = Build(); GeneratorImpl& gen = Build();
ASSERT_TRUE(gen.EmitType(out, &s, "")) << gen.error(); ASSERT_TRUE(gen.EmitType(out, &s, "")) << gen.error();
EXPECT_EQ(result(), "Texture2D"); EXPECT_EQ(result(), "Texture2DMS<float4>");
} }
struct HlslStorageTextureData { struct HlslStorageTextureData {