mirror of
https://github.com/KhronosGroup/SPIRV-Tools
synced 2025-01-12 09:20:15 +00:00
Remove struct member offset monotonicity check
Fixes #1822 * Remove check that struct member offsets must be monotonic * All environments match Vulkan behaviour now * updated offending tests
This commit is contained in:
parent
482b1744ca
commit
cb0f1f565b
@ -350,8 +350,6 @@ spv_result_t checkLayout(uint32_t struct_id, const char* storage_class_str,
|
||||
|
||||
// To check for member overlaps, we want to traverse the members in
|
||||
// offset order.
|
||||
const bool permit_non_monotonic_member_offsets =
|
||||
vstate.features().non_monotonic_struct_member_offsets;
|
||||
struct MemberOffsetPair {
|
||||
uint32_t member;
|
||||
uint32_t offset;
|
||||
@ -381,7 +379,6 @@ spv_result_t checkLayout(uint32_t struct_id, const char* storage_class_str,
|
||||
});
|
||||
|
||||
// Now scan from lowest offest to highest offset.
|
||||
uint32_t prevOffset = 0;
|
||||
uint32_t nextValidOffset = 0;
|
||||
for (size_t ordered_member_idx = 0;
|
||||
ordered_member_idx < member_offsets.size(); ordered_member_idx++) {
|
||||
@ -418,19 +415,6 @@ spv_result_t checkLayout(uint32_t struct_id, const char* storage_class_str,
|
||||
<< "at offset " << offset << " is not aligned to " << alignment;
|
||||
}
|
||||
}
|
||||
// SPIR-V requires struct members to be specified in memory address order,
|
||||
// and they should not overlap. Vulkan relaxes that rule.
|
||||
if (!permit_non_monotonic_member_offsets) {
|
||||
const auto out_of_order =
|
||||
ordered_member_idx > 0 &&
|
||||
(memberIdx < member_offsets[ordered_member_idx - 1].member);
|
||||
if (out_of_order) {
|
||||
return fail(memberIdx)
|
||||
<< "at offset " << offset << " has a higher offset than member "
|
||||
<< member_offsets[ordered_member_idx - 1].member << " at offset "
|
||||
<< prevOffset;
|
||||
}
|
||||
}
|
||||
if (offset < nextValidOffset)
|
||||
return fail(memberIdx) << "at offset " << offset
|
||||
<< " overlaps previous member ending at offset "
|
||||
@ -483,7 +467,6 @@ spv_result_t checkLayout(uint32_t struct_id, const char* storage_class_str,
|
||||
// or array.
|
||||
nextValidOffset = align(nextValidOffset, alignment);
|
||||
}
|
||||
prevOffset = offset;
|
||||
}
|
||||
return SPV_SUCCESS;
|
||||
}
|
||||
|
@ -176,8 +176,6 @@ ValidationState_t::ValidationState_t(const spv_const_context ctx,
|
||||
const auto env = context_->target_env;
|
||||
|
||||
if (spvIsVulkanEnv(env)) {
|
||||
features_.non_monotonic_struct_member_offsets = true;
|
||||
|
||||
// Vulkan 1.1 includes VK_KHR_relaxed_block_layout in core.
|
||||
if (env != SPV_ENV_VULKAN_1_0) {
|
||||
features_.env_relaxed_block_layout = true;
|
||||
|
@ -83,10 +83,6 @@ class ValidationState_t {
|
||||
// Allow OpTypeInt with 8 bit width?
|
||||
bool declare_int8_type = false;
|
||||
|
||||
// Allow non-monotonic offsets for struct members?
|
||||
// Vulkan permits this.
|
||||
bool non_monotonic_struct_member_offsets = false;
|
||||
|
||||
// Target environment uses relaxed block layout.
|
||||
// This is true for Vulkan 1.1 or later.
|
||||
bool env_relaxed_block_layout = false;
|
||||
|
@ -2522,7 +2522,7 @@ TEST_F(ValidateDecorations,
|
||||
"offset 4 overlaps previous member ending at offset 15"));
|
||||
}
|
||||
|
||||
TEST_F(ValidateDecorations, BlockLayoutOffsetOutOfOrderBadUniversal1_0) {
|
||||
TEST_F(ValidateDecorations, BlockLayoutOffsetOutOfOrderGoodUniversal1_0) {
|
||||
std::string spirv = R"(
|
||||
OpCapability Shader
|
||||
%1 = OpExtInstImport "GLSL.std.450"
|
||||
@ -2547,17 +2547,11 @@ TEST_F(ValidateDecorations, BlockLayoutOffsetOutOfOrderBadUniversal1_0) {
|
||||
)";
|
||||
|
||||
CompileSuccessfully(spirv);
|
||||
EXPECT_EQ(SPV_ERROR_INVALID_ID,
|
||||
EXPECT_EQ(SPV_SUCCESS,
|
||||
ValidateAndRetrieveValidationState(SPV_ENV_UNIVERSAL_1_0));
|
||||
EXPECT_THAT(
|
||||
getDiagnosticString(),
|
||||
HasSubstr(
|
||||
"Structure id 3 decorated as Block for variable in Uniform storage "
|
||||
"class must follow standard uniform buffer layout rules: member 0 at "
|
||||
"offset 4 has a higher offset than member 1 at offset 0"));
|
||||
}
|
||||
|
||||
TEST_F(ValidateDecorations, BlockLayoutOffsetOutOfOrderBadOpenGL4_5) {
|
||||
TEST_F(ValidateDecorations, BlockLayoutOffsetOutOfOrderGoodOpenGL4_5) {
|
||||
std::string spirv = R"(
|
||||
OpCapability Shader
|
||||
%1 = OpExtInstImport "GLSL.std.450"
|
||||
@ -2582,14 +2576,8 @@ TEST_F(ValidateDecorations, BlockLayoutOffsetOutOfOrderBadOpenGL4_5) {
|
||||
)";
|
||||
|
||||
CompileSuccessfully(spirv);
|
||||
EXPECT_EQ(SPV_ERROR_INVALID_ID,
|
||||
EXPECT_EQ(SPV_SUCCESS,
|
||||
ValidateAndRetrieveValidationState(SPV_ENV_OPENGL_4_5));
|
||||
EXPECT_THAT(
|
||||
getDiagnosticString(),
|
||||
HasSubstr(
|
||||
"Structure id 3 decorated as Block for variable in Uniform storage "
|
||||
"class must follow standard uniform buffer layout rules: member 0 at "
|
||||
"offset 4 has a higher offset than member 1 at offset 0"));
|
||||
}
|
||||
|
||||
TEST_F(ValidateDecorations, BlockLayoutOffsetOutOfOrderGoodVulkan1_1) {
|
||||
|
Loading…
Reference in New Issue
Block a user