spirv-reader: Add interpolate(flat) to integral pipeline IO

This is now required in WGSL, and will soon become an error in Tint.

Bug: tint:1224
Change-Id: Ide98c4c0b7aac86a2b43f7e02abde3d8a297dce4
Reviewed-on: https://dawn-review.googlesource.com/c/tint/+/68920
Kokoro: Kokoro <noreply+kokoro@google.com>
Reviewed-by: David Neto <dneto@google.com>
Commit-Queue: James Price <jrprice@google.com>
This commit is contained in:
James Price 2021-11-09 17:35:34 +00:00 committed by Tint LUCI CQ
parent 72b6bb94c2
commit ae4b3ffe6b
2 changed files with 18 additions and 40 deletions

View File

@ -1777,9 +1777,9 @@ const ast::Decoration* ParserImpl::SetLocation(
bool ParserImpl::ConvertPipelineDecorations(const Type* store_type,
const DecorationList& decorations,
ast::DecorationList* ast_decos) {
bool has_interpolate_no_perspective = false;
bool has_interpolate_sampling_centroid = false;
bool has_interpolate_sampling_sample = false;
// Vulkan defaults to perspective-correct interpolation.
ast::InterpolationType type = ast::InterpolationType::kPerspective;
ast::InterpolationSampling sampling = ast::InterpolationSampling::kNone;
for (const auto& deco : decorations) {
TINT_ASSERT(Reader, deco.size() > 0);
@ -1793,22 +1793,14 @@ bool ParserImpl::ConvertPipelineDecorations(const Type* store_type,
create<ast::LocationDecoration>(Source{}, deco[1]));
break;
case SpvDecorationFlat:
// In WGSL, integral types are always flat, and so the decoration
// is never specified.
if (!store_type->IsIntegerScalarOrVector()) {
ast_decos->emplace_back(create<ast::InterpolateDecoration>(
Source{}, ast::InterpolationType::kFlat,
ast::InterpolationSampling::kNone));
// Only one interpolate attribute is allowed.
return true;
}
type = ast::InterpolationType::kFlat;
break;
case SpvDecorationNoPerspective:
if (store_type->IsIntegerScalarOrVector()) {
// This doesn't capture the array or struct case.
return Fail() << "NoPerspective is invalid on integral IO";
}
has_interpolate_no_perspective = true;
type = ast::InterpolationType::kLinear;
break;
case SpvDecorationCentroid:
if (store_type->IsIntegerScalarOrVector()) {
@ -1816,7 +1808,7 @@ bool ParserImpl::ConvertPipelineDecorations(const Type* store_type,
return Fail()
<< "Centroid interpolation sampling is invalid on integral IO";
}
has_interpolate_sampling_centroid = true;
sampling = ast::InterpolationSampling::kCentroid;
break;
case SpvDecorationSample:
if (store_type->IsIntegerScalarOrVector()) {
@ -1824,33 +1816,19 @@ bool ParserImpl::ConvertPipelineDecorations(const Type* store_type,
return Fail()
<< "Sample interpolation sampling is invalid on integral IO";
}
has_interpolate_sampling_sample = true;
sampling = ast::InterpolationSampling::kSample;
break;
default:
break;
}
}
// Apply non-integral interpolation.
if (has_interpolate_no_perspective || has_interpolate_sampling_centroid ||
has_interpolate_sampling_sample) {
const ast::InterpolationType type =
has_interpolate_no_perspective ? ast::InterpolationType::kLinear
: ast::InterpolationType::kPerspective;
const ast::InterpolationSampling sampling =
has_interpolate_sampling_centroid
? ast::InterpolationSampling::kCentroid
: (has_interpolate_sampling_sample
? ast::InterpolationSampling::kSample
: ast::InterpolationSampling::
kNone /* Center is the default */);
if (type == ast::InterpolationType::kPerspective &&
sampling == ast::InterpolationSampling::kNone) {
// This is the default. Don't add a decoration.
} else {
ast_decos->emplace_back(
create<ast::InterpolateDecoration>(type, sampling));
}
// Apply interpolation.
if (type == ast::InterpolationType::kPerspective &&
sampling == ast::InterpolationSampling::kNone) {
// This is the default. Don't add a decoration.
} else {
ast_decos->emplace_back(create<ast::InterpolateDecoration>(type, sampling));
}
return success();

View File

@ -4813,7 +4813,7 @@ struct main_out {
};
[[stage(vertex)]]
fn main([[location(1)]] x_1_param : u32, [[location(2)]] x_2_param : vec2<u32>, [[location(3)]] x_3_param : i32, [[location(4)]] x_4_param : vec2<i32>, [[location(5), interpolate(flat)]] x_5_param : f32, [[location(6), interpolate(flat)]] x_6_param : vec2<f32>) -> main_out {
fn main([[location(1), interpolate(flat)]] x_1_param : u32, [[location(2), interpolate(flat)]] x_2_param : vec2<u32>, [[location(3), interpolate(flat)]] x_3_param : i32, [[location(4), interpolate(flat)]] x_4_param : vec2<i32>, [[location(5), interpolate(flat)]] x_5_param : f32, [[location(6), interpolate(flat)]] x_6_param : vec2<f32>) -> main_out {
x_1 = x_1_param;
x_2 = x_2_param;
x_3 = x_3_param;
@ -4893,13 +4893,13 @@ fn main_1() {
}
struct main_out {
[[location(1)]]
[[location(1), interpolate(flat)]]
x_1_1 : u32;
[[location(2)]]
[[location(2), interpolate(flat)]]
x_2_1 : vec2<u32>;
[[location(3)]]
[[location(3), interpolate(flat)]]
x_3_1 : i32;
[[location(4)]]
[[location(4), interpolate(flat)]]
x_4_1 : vec2<i32>;
[[location(5), interpolate(flat)]]
x_5_1 : f32;