Skip to content

Commit

Permalink
spirv-val: Separate Location check for tess patch
Browse files Browse the repository at this point in the history
  • Loading branch information
spencer-lunarg committed Apr 24, 2024
1 parent dd4b663 commit e552b5a
Show file tree
Hide file tree
Showing 2 changed files with 78 additions and 0 deletions.
12 changes: 12 additions & 0 deletions source/val/validate_interfaces.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -519,6 +519,8 @@ spv_result_t ValidateLocations(ValidationState_t& _,
std::unordered_set<uint32_t> input_locations;
std::unordered_set<uint32_t> output_locations_index0;
std::unordered_set<uint32_t> output_locations_index1;
std::unordered_set<uint32_t> patch_locations_index0;
std::unordered_set<uint32_t> patch_locations_index1;
std::unordered_set<uint32_t> seen;
for (uint32_t i = 3; i < entry_point->operands().size(); ++i) {
auto interface_id = entry_point->GetOperandAs<uint32_t>(i);
Expand All @@ -534,6 +536,16 @@ spv_result_t ValidateLocations(ValidationState_t& _,
continue;
}

for (auto& dec : _.id_decorations(interface_var->id())) {
if (dec.dec_type() == spv::Decoration::Patch) {
if (auto error = GetLocationsForVariable(_, entry_point, interface_var,
&patch_locations_index0,
&patch_locations_index1))
return error;
break;
}
}

auto locations = (storage_class == spv::StorageClass::Input)
? &input_locations
: &output_locations_index0;
Expand Down
66 changes: 66 additions & 0 deletions test/val/val_interfaces_test.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -623,6 +623,72 @@ OpFunctionEnd
"at location 1"));
}

TEST_F(ValidateInterfacesTest, VulkanPatchAndNonPatchOverlap) {
const std::string text = R"(
OpCapability Tessellation
OpMemoryModel Logical GLSL450
OpEntryPoint TessellationControl %main "main" %a %b
OpExecutionMode %main OutputVertices 4
OpDecorate %a Location 0
OpDecorate %b Patch
OpDecorate %b Location 0
%void = OpTypeVoid
%3 = OpTypeFunction %void
%float = OpTypeFloat 32
%uint = OpTypeInt 32 0
%uint_4 = OpConstant %uint 4
%_arr_float_uint_4 = OpTypeArray %float %uint_4
%_ptr_Output__arr_float_uint_4 = OpTypePointer Output %_arr_float_uint_4
%a = OpVariable %_ptr_Output__arr_float_uint_4 Output
%_ptr_Output_float = OpTypePointer Output %float
%b = OpVariable %_ptr_Output_float Output
%main = OpFunction %void None %3
%5 = OpLabel
OpReturn
OpFunctionEnd
)";

CompileSuccessfully(text, SPV_ENV_VULKAN_1_2);
EXPECT_EQ(SPV_SUCCESS, ValidateInstructions(SPV_ENV_VULKAN_1_2));
}

TEST_F(ValidateInterfacesTest, VulkanPatchOverlap) {
const std::string text = R"(
OpCapability Tessellation
OpMemoryModel Logical GLSL450
OpEntryPoint TessellationControl %main "main" %a %b %c
OpExecutionMode %main OutputVertices 4
OpDecorate %a Location 0
OpDecorate %b Patch
OpDecorate %b Location 6
OpDecorate %c Patch
OpDecorate %c Location 6
%void = OpTypeVoid
%3 = OpTypeFunction %void
%float = OpTypeFloat 32
%uint = OpTypeInt 32 0
%uint_4 = OpConstant %uint 4
%_arr_float_uint_4 = OpTypeArray %float %uint_4
%_ptr_Output__arr_float_uint_4 = OpTypePointer Output %_arr_float_uint_4
%a = OpVariable %_ptr_Output__arr_float_uint_4 Output
%_ptr_Output_float = OpTypePointer Output %float
%b = OpVariable %_ptr_Output_float Output
%c = OpVariable %_ptr_Output_float Output
%main = OpFunction %void None %3
%5 = OpLabel
OpReturn
OpFunctionEnd
)";

CompileSuccessfully(text, SPV_ENV_VULKAN_1_2);
EXPECT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions(SPV_ENV_VULKAN_1_2));
EXPECT_THAT(getDiagnosticString(),
AnyVUID("VUID-StandaloneSpirv-OpEntryPoint-08722"));
EXPECT_THAT(getDiagnosticString(),
HasSubstr("Entry-point has conflicting output location "
"assignment at location 6, component 0"));
}

TEST_F(ValidateInterfacesTest,
VulkanLocationsSameLocationInputAndOutputNoConflict) {
const std::string text = R"(
Expand Down

0 comments on commit e552b5a

Please sign in to comment.