Skip to content

Commit 1350f1d

Browse files
spirv-val: Only validate local size with non-spec const
1 parent 9544818 commit 1350f1d

File tree

3 files changed

+51
-27
lines changed

3 files changed

+51
-27
lines changed

source/val/validate_builtins.cpp

Lines changed: 10 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -3170,19 +3170,24 @@ spv_result_t BuiltInsValidator::ValidateWorkgroupSizeAtDefinition(
31703170
"constant. "
31713171
<< GetIdDesc(inst) << " is not a constant.";
31723172
}
3173-
} else {
3174-
// can only validate product if static
3173+
} else if (inst.opcode() == spv::Op::OpConstantComposite) {
3174+
// can only validate product if static and not spec constant
3175+
if (_.FindDef(inst.word(3))->opcode() == spv::Op::OpConstant &&
3176+
_.FindDef(inst.word(4))->opcode() == spv::Op::OpConstant &&
3177+
_.FindDef(inst.word(5))->opcode() == spv::Op::OpConstant) {
31753178
uint64_t x_size, y_size, z_size;
31763179
// ValidateI32Vec above confirms there will be 3 words to read
31773180
bool static_x = _.GetConstantValUint64(inst.word(3), &x_size);
31783181
bool static_y = _.GetConstantValUint64(inst.word(4), &y_size);
31793182
bool static_z = _.GetConstantValUint64(inst.word(5), &z_size);
31803183
if (static_x && static_y && static_z &&
31813184
((x_size * y_size * z_size) == 0)) {
3182-
return _.diag(SPV_ERROR_INVALID_DATA, &inst)
3183-
<< "WorkgroupSize decorations must not have a static "
3184-
"product of zero (X = " << x_size << ", Y = " << y_size << ", Z = " << z_size << ").";
3185+
return _.diag(SPV_ERROR_INVALID_DATA, &inst)
3186+
<< "WorkgroupSize decorations must not have a static "
3187+
"product of zero (X = "
3188+
<< x_size << ", Y = " << y_size << ", Z = " << z_size << ").";
31853189
}
3190+
}
31863191
}
31873192

31883193
// Seed at reference checks with this built-in.

source/val/validate_mode_setting.cpp

Lines changed: 22 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -340,18 +340,28 @@ spv_result_t ValidateEntryPoint(ValidationState_t& _, const Instruction* inst) {
340340
const Instruction* local_size_id_inst =
341341
_.GetLocalSizeIdInstruction(entry_point_id);
342342
if (local_size_id_inst) {
343-
uint64_t x_size, y_size, z_size;
344-
bool static_x =
345-
_.GetConstantValUint64(local_size_id_inst->word(3), &x_size);
346-
bool static_y =
347-
_.GetConstantValUint64(local_size_id_inst->word(4), &y_size);
348-
bool static_z =
349-
_.GetConstantValUint64(local_size_id_inst->word(5), &z_size);
350-
if (static_x && static_y && static_z && ((x_size * y_size * z_size) == 0)) {
351-
return _.diag(SPV_ERROR_INVALID_DATA, local_size_inst)
352-
<< "Local Size Id execution mode must not have a product of zero "
353-
"(X = "
354-
<< x_size << ", Y = " << y_size << ", Z = " << z_size << ").";
343+
// can only validate product if static and not spec constant
344+
if (_.FindDef(local_size_id_inst->word(3))->opcode() ==
345+
spv::Op::OpConstant &&
346+
_.FindDef(local_size_id_inst->word(4))->opcode() ==
347+
spv::Op::OpConstant &&
348+
_.FindDef(local_size_id_inst->word(5))->opcode() ==
349+
spv::Op::OpConstant) {
350+
uint64_t x_size, y_size, z_size;
351+
bool static_x =
352+
_.GetConstantValUint64(local_size_id_inst->word(3), &x_size);
353+
bool static_y =
354+
_.GetConstantValUint64(local_size_id_inst->word(4), &y_size);
355+
bool static_z =
356+
_.GetConstantValUint64(local_size_id_inst->word(5), &z_size);
357+
if (static_x && static_y && static_z &&
358+
((x_size * y_size * z_size) == 0)) {
359+
return _.diag(SPV_ERROR_INVALID_DATA, local_size_inst)
360+
<< "Local Size Id execution mode must not have a product of "
361+
"zero "
362+
"(X = "
363+
<< x_size << ", Y = " << y_size << ", Z = " << z_size << ").";
364+
}
355365
}
356366
}
357367

test/val/val_modes_test.cpp

Lines changed: 19 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -123,11 +123,24 @@ OpDecorate %int3_1 BuiltIn WorkgroupSize
123123
)" + kVoidFunction;
124124

125125
CompileSuccessfully(spirv);
126-
EXPECT_THAT(SPV_ERROR_INVALID_DATA, ValidateInstructions());
127-
EXPECT_THAT(
128-
getDiagnosticString(),
129-
HasSubstr(
130-
"WorkgroupSize decorations must not have a static product of zero"));
126+
EXPECT_EQ(SPV_SUCCESS, ValidateInstructions());
127+
}
128+
129+
TEST_F(ValidateMode, GLComputeZeroSpecCompositeWorkgroupSize) {
130+
const std::string spirv = R"(
131+
OpCapability Shader
132+
OpMemoryModel Logical GLSL450
133+
OpEntryPoint GLCompute %main "main"
134+
OpDecorate %int3_1 BuiltIn WorkgroupSize
135+
%int = OpTypeInt 32 0
136+
%int3 = OpTypeVector %int 3
137+
%int_0 = OpSpecConstant %int 0
138+
%int_1 = OpSpecConstant %int 1
139+
%int3_1 = OpSpecConstantComposite %int3 %int_1 %int_0 %int_0
140+
)" + kVoidFunction;
141+
142+
CompileSuccessfully(spirv);
143+
EXPECT_EQ(SPV_SUCCESS, ValidateInstructions());
131144
}
132145

133146
TEST_F(ValidateMode, KernelZeroWorkgroupSizeConstant) {
@@ -280,11 +293,7 @@ OpExecutionModeId %main LocalSizeId %int_1 %int_0 %int_1
280293

281294
spv_target_env env = SPV_ENV_UNIVERSAL_1_3;
282295
CompileSuccessfully(spirv, env);
283-
EXPECT_THAT(SPV_ERROR_INVALID_DATA, ValidateInstructions(env));
284-
EXPECT_THAT(
285-
getDiagnosticString(),
286-
HasSubstr(
287-
"Local Size Id execution mode must not have a product of zero"));
296+
EXPECT_EQ(SPV_SUCCESS, ValidateInstructions(env));
288297
}
289298

290299
TEST_F(ValidateMode, KernelZeroLocalSizeId) {

0 commit comments

Comments
 (0)