Skip to content

Commit 2b3df1e

Browse files
authored
split-combined-image-samplers: clone decorations on loads (KhronosGroup#6046)
* split-combined-image-samplers: clone decorations on loads Fixed: KhronosGroup#6045 * Add more CHECK-NOT based on type, to prove var is removed
1 parent ff4d890 commit 2b3df1e

File tree

2 files changed

+74
-2
lines changed

2 files changed

+74
-2
lines changed

source/opt/split_combined_image_sampler_pass.cpp

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -358,6 +358,13 @@ spv_result_t SplitCombinedImageSamplerPass::RemapUses(
358358
use.image_part->result_id());
359359
auto* sampler = builder.AddLoad(PointeeTypeId(use.sampler_part),
360360
use.sampler_part->result_id());
361+
362+
// Move decorations, such as RelaxedPrecision.
363+
auto* deco_mgr = context()->get_decoration_mgr();
364+
deco_mgr->CloneDecorations(load->result_id(), image->result_id());
365+
deco_mgr->CloneDecorations(load->result_id(), sampler->result_id());
366+
deco_mgr->RemoveDecorationsFrom(load->result_id());
367+
361368
// Create a sampled image from the loads of the two parts.
362369
auto* sampled_image = builder.AddSampledImage(
363370
load->type_id(), image->result_id(), sampler->result_id());

test/opt/split_combined_image_sampler_pass_test.cpp

Lines changed: 67 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -386,8 +386,8 @@ TEST_P(SplitCombinedImageSamplerPassTypeCaseTest, Combined_RemapLoad) {
386386
}
387387

388388
TEST_P(SplitCombinedImageSamplerPassTypeCaseTest,
389-
Combined_RemapLoad_RelaxedPrecisionCopied) {
390-
// All decorations are copied. In this case, RelaxedPrecision
389+
Combined_RemapLoad_RelaxedPrecisionOnVarCopied) {
390+
// All decorations on the variable are copied. In this case, RelaxedPrecision
391391
const std::string kTest = Preamble() +
392392
R"(
393393
OpName %combined "combined"
@@ -412,6 +412,7 @@ TEST_P(SplitCombinedImageSamplerPassTypeCaseTest,
412412
; The combined image variable is replaced by an image variable and a sampler variable.
413413
414414
; CHECK-NOT: %100 = OpVariable
415+
; CHECK-NOT: OpVariable _ptr_UniformConstant_11
415416
; CHECK-DAG: %[[sampler_var]] = OpVariable %[[sampler_ptr_ty]] UniformConstant
416417
; CHECK-DAG: %[[image_var]] = OpVariable %[[image_ptr_ty]] UniformConstant
417418
; CHECK: = OpFunction
@@ -445,6 +446,70 @@ TEST_P(SplitCombinedImageSamplerPassTypeCaseTest,
445446
EXPECT_EQ(status, Pass::Status::SuccessWithChange) << disasm;
446447
}
447448

449+
TEST_P(SplitCombinedImageSamplerPassTypeCaseTest,
450+
Combined_RemapLoad_RelaxedPrecisionOnLoadCopied) {
451+
// Copy decorations form an OpLoad that is replaced.
452+
const std::string kTest = Preamble() +
453+
R"(
454+
OpName %combined "combined"
455+
OpDecorate %100 DescriptorSet 0
456+
OpDecorate %100 Binding 0
457+
OpDecorate %combined RelaxedPrecision
458+
459+
; CHECK: OpName
460+
; CHECK-NOT: OpDecorate %100
461+
; CHECK: OpDecorate %[[image_var:\d+]] DescriptorSet 0
462+
; CHECK: OpDecorate %[[sampler_var:\d+]] DescriptorSet 0
463+
; CHECK: OpDecorate %[[image_var]] Binding 0
464+
; CHECK: OpDecorate %[[sampler_var]] Binding 0
465+
466+
; This is what we are checking in this test.
467+
; CHECK: OpDecorate %[[im:\d+]] RelaxedPrecision
468+
; CHECK: OpDecorate %[[s:\d+]] RelaxedPrecision
469+
470+
; CHECK: %10 = OpTypeImage %
471+
; CHECK: %[[image_ptr_ty:\w+]] = OpTypePointer UniformConstant %10
472+
; CHECK: %[[sampler_ty:\d+]] = OpTypeSampler
473+
; CHECK: %[[sampler_ptr_ty:\w+]] = OpTypePointer UniformConstant %[[sampler_ty]]
474+
475+
; The combined image variable is replaced by an image variable and a sampler variable.
476+
477+
; CHECK-NOT: %100 = OpVariable
478+
; CHECK-NOT: OpVariable _ptr_UniformConstant_11
479+
; CHECK-DAG: %[[sampler_var]] = OpVariable %[[sampler_ptr_ty]] UniformConstant
480+
; CHECK-DAG: %[[image_var]] = OpVariable %[[image_ptr_ty]] UniformConstant
481+
; CHECK: = OpFunction
482+
483+
; The load of the combined image+sampler is replaced by a two loads, then
484+
; a combination operation. The new loads get the same decorations that the
485+
; original load had.
486+
; CHECK: %[[im]] = OpLoad %10 %[[image_var]]
487+
; CHECK: %[[s]] = OpLoad %[[sampler_ty]] %[[sampler_var]]
488+
; CHECK: %combined = OpSampledImage %11 %[[im]] %[[s]]
489+
490+
%bool = OpTypeBool ; location marker
491+
)" + BasicTypes() +
492+
" %10 = " + GetParam().image_type_decl + R"(
493+
%11 = OpTypeSampledImage %10
494+
%_ptr_UniformConstant_11 = OpTypePointer UniformConstant %11
495+
496+
%100 = OpVariable %_ptr_UniformConstant_11 UniformConstant
497+
%main = OpFunction %void None %voidfn
498+
%main_0 = OpLabel
499+
%combined = OpLoad %11 %100
500+
501+
; Uses of the combined image sampler are preserved.
502+
; CHECK: OpCopyObject %11 %combined
503+
504+
%7 = OpCopyObject %11 %combined
505+
OpReturn
506+
OpFunctionEnd
507+
)";
508+
auto [disasm, status] = SinglePassRunAndMatch<SplitCombinedImageSamplerPass>(
509+
kTest, /* do_validation= */ true);
510+
EXPECT_EQ(status, Pass::Status::SuccessWithChange) << disasm;
511+
}
512+
448513
TEST_P(SplitCombinedImageSamplerPassTypeCaseTest,
449514
Combined_DeletesCopyObjectOfPtr) {
450515
// OpCopyObject is deleted, and its uses updated.

0 commit comments

Comments
 (0)