mirror of
https://github.com/KhronosGroup/SPIRV-Tools
synced 2024-10-18 19:20:05 +00:00
Extend reducer to remove relaxed precision decorations (#2797)
Adds a reduction pass that removes OpDecorate and OpMemberDecorate instructions that annotate instructions and members with RelaxedPrecision. As well as being useful in its own right, removing such references allows other passes to remove further instructions.
This commit is contained in:
parent
b00ef0d26e
commit
8336d1925f
@ -30,6 +30,7 @@ set(SPIRV_TOOLS_REDUCE_SOURCES
|
|||||||
remove_function_reduction_opportunity.h
|
remove_function_reduction_opportunity.h
|
||||||
remove_function_reduction_opportunity_finder.h
|
remove_function_reduction_opportunity_finder.h
|
||||||
remove_opname_instruction_reduction_opportunity_finder.h
|
remove_opname_instruction_reduction_opportunity_finder.h
|
||||||
|
remove_relaxed_precision_decoration_opportunity_finder.h
|
||||||
remove_selection_reduction_opportunity.h
|
remove_selection_reduction_opportunity.h
|
||||||
remove_selection_reduction_opportunity_finder.h
|
remove_selection_reduction_opportunity_finder.h
|
||||||
remove_unreferenced_instruction_reduction_opportunity_finder.h
|
remove_unreferenced_instruction_reduction_opportunity_finder.h
|
||||||
@ -56,6 +57,7 @@ set(SPIRV_TOOLS_REDUCE_SOURCES
|
|||||||
remove_function_reduction_opportunity.cpp
|
remove_function_reduction_opportunity.cpp
|
||||||
remove_function_reduction_opportunity_finder.cpp
|
remove_function_reduction_opportunity_finder.cpp
|
||||||
remove_instruction_reduction_opportunity.cpp
|
remove_instruction_reduction_opportunity.cpp
|
||||||
|
remove_relaxed_precision_decoration_opportunity_finder.cpp
|
||||||
remove_selection_reduction_opportunity.cpp
|
remove_selection_reduction_opportunity.cpp
|
||||||
remove_selection_reduction_opportunity_finder.cpp
|
remove_selection_reduction_opportunity_finder.cpp
|
||||||
remove_unreferenced_instruction_reduction_opportunity_finder.cpp
|
remove_unreferenced_instruction_reduction_opportunity_finder.cpp
|
||||||
|
@ -25,6 +25,7 @@
|
|||||||
#include "source/reduce/remove_block_reduction_opportunity_finder.h"
|
#include "source/reduce/remove_block_reduction_opportunity_finder.h"
|
||||||
#include "source/reduce/remove_function_reduction_opportunity_finder.h"
|
#include "source/reduce/remove_function_reduction_opportunity_finder.h"
|
||||||
#include "source/reduce/remove_opname_instruction_reduction_opportunity_finder.h"
|
#include "source/reduce/remove_opname_instruction_reduction_opportunity_finder.h"
|
||||||
|
#include "source/reduce/remove_relaxed_precision_decoration_opportunity_finder.h"
|
||||||
#include "source/reduce/remove_selection_reduction_opportunity_finder.h"
|
#include "source/reduce/remove_selection_reduction_opportunity_finder.h"
|
||||||
#include "source/reduce/remove_unreferenced_instruction_reduction_opportunity_finder.h"
|
#include "source/reduce/remove_unreferenced_instruction_reduction_opportunity_finder.h"
|
||||||
#include "source/reduce/simple_conditional_branch_to_branch_opportunity_finder.h"
|
#include "source/reduce/simple_conditional_branch_to_branch_opportunity_finder.h"
|
||||||
@ -175,6 +176,8 @@ Reducer::ReductionResultStatus Reducer::Run(
|
|||||||
void Reducer::AddDefaultReductionPasses() {
|
void Reducer::AddDefaultReductionPasses() {
|
||||||
AddReductionPass(spvtools::MakeUnique<
|
AddReductionPass(spvtools::MakeUnique<
|
||||||
RemoveOpNameInstructionReductionOpportunityFinder>());
|
RemoveOpNameInstructionReductionOpportunityFinder>());
|
||||||
|
AddReductionPass(spvtools::MakeUnique<
|
||||||
|
RemoveRelaxedPrecisionDecorationOpportunityFinder>());
|
||||||
AddReductionPass(
|
AddReductionPass(
|
||||||
spvtools::MakeUnique<OperandToUndefReductionOpportunityFinder>());
|
spvtools::MakeUnique<OperandToUndefReductionOpportunityFinder>());
|
||||||
AddReductionPass(
|
AddReductionPass(
|
||||||
|
@ -0,0 +1,49 @@
|
|||||||
|
// Copyright (c) 2018 Google Inc.
|
||||||
|
//
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, software
|
||||||
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
// See the License for the specific language governing permissions and
|
||||||
|
// limitations under the License.
|
||||||
|
|
||||||
|
#include "source/reduce/remove_relaxed_precision_decoration_opportunity_finder.h"
|
||||||
|
|
||||||
|
#include "source/reduce/remove_instruction_reduction_opportunity.h"
|
||||||
|
|
||||||
|
namespace spvtools {
|
||||||
|
namespace reduce {
|
||||||
|
|
||||||
|
std::vector<std::unique_ptr<ReductionOpportunity>>
|
||||||
|
RemoveRelaxedPrecisionDecorationOpportunityFinder::GetAvailableOpportunities(
|
||||||
|
opt::IRContext* context) const {
|
||||||
|
std::vector<std::unique_ptr<ReductionOpportunity>> result;
|
||||||
|
|
||||||
|
// Consider all annotation instructions
|
||||||
|
for (auto& inst : context->module()->annotations()) {
|
||||||
|
// We are interested in removing instructions of the form:
|
||||||
|
// SpvOpDecorate %id RelaxedPrecision
|
||||||
|
// and
|
||||||
|
// SpvOpMemberDecorate %id member RelaxedPrecision
|
||||||
|
if ((inst.opcode() == SpvOpDecorate &&
|
||||||
|
inst.GetSingleWordInOperand(1) == SpvDecorationRelaxedPrecision) ||
|
||||||
|
(inst.opcode() == SpvOpMemberDecorate &&
|
||||||
|
inst.GetSingleWordInOperand(2) == SpvDecorationRelaxedPrecision)) {
|
||||||
|
result.push_back(
|
||||||
|
MakeUnique<RemoveInstructionReductionOpportunity>(&inst));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::string RemoveRelaxedPrecisionDecorationOpportunityFinder::GetName() const {
|
||||||
|
return "RemoveRelaxedPrecisionDecorationOpportunityFinder";
|
||||||
|
}
|
||||||
|
|
||||||
|
} // namespace reduce
|
||||||
|
} // namespace spvtools
|
@ -0,0 +1,36 @@
|
|||||||
|
// Copyright (c) 2019 Google LLC
|
||||||
|
//
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, software
|
||||||
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
// See the License for the specific language governing permissions and
|
||||||
|
// limitations under the License.
|
||||||
|
|
||||||
|
#ifndef SOURCE_REDUCE_REMOVE_RELAXED_PRECISION_OPPORTUNITY_FINDER_H_
|
||||||
|
#define SOURCE_REDUCE_REMOVE_RELAXED_PRECISION_OPPORTUNITY_FINDER_H_
|
||||||
|
|
||||||
|
#include "source/reduce/reduction_opportunity_finder.h"
|
||||||
|
|
||||||
|
namespace spvtools {
|
||||||
|
namespace reduce {
|
||||||
|
|
||||||
|
// A finder for opportunities to remove relaxed precision decorations.
|
||||||
|
class RemoveRelaxedPrecisionDecorationOpportunityFinder
|
||||||
|
: public ReductionOpportunityFinder {
|
||||||
|
public:
|
||||||
|
std::vector<std::unique_ptr<ReductionOpportunity>> GetAvailableOpportunities(
|
||||||
|
opt::IRContext* context) const override;
|
||||||
|
|
||||||
|
std::string GetName() const override;
|
||||||
|
};
|
||||||
|
|
||||||
|
} // namespace reduce
|
||||||
|
} // namespace spvtools
|
||||||
|
|
||||||
|
#endif // SOURCE_REDUCE_REMOVE_RELAXED_PRECISION_OPPORTUNITY_FINDER_H_
|
@ -21,11 +21,9 @@
|
|||||||
namespace spvtools {
|
namespace spvtools {
|
||||||
namespace reduce {
|
namespace reduce {
|
||||||
|
|
||||||
using opt::IRContext;
|
|
||||||
|
|
||||||
std::vector<std::unique_ptr<ReductionOpportunity>>
|
std::vector<std::unique_ptr<ReductionOpportunity>>
|
||||||
RemoveUnreferencedInstructionReductionOpportunityFinder::
|
RemoveUnreferencedInstructionReductionOpportunityFinder::
|
||||||
GetAvailableOpportunities(IRContext* context) const {
|
GetAvailableOpportunities(opt::IRContext* context) const {
|
||||||
std::vector<std::unique_ptr<ReductionOpportunity>> result;
|
std::vector<std::unique_ptr<ReductionOpportunity>> result;
|
||||||
|
|
||||||
for (auto& function : *context->module()) {
|
for (auto& function : *context->module()) {
|
||||||
|
@ -24,6 +24,7 @@ add_spvtools_unittest(TARGET reduce
|
|||||||
remove_block_test.cpp
|
remove_block_test.cpp
|
||||||
remove_function_test.cpp
|
remove_function_test.cpp
|
||||||
remove_opname_instruction_test.cpp
|
remove_opname_instruction_test.cpp
|
||||||
|
remove_relaxed_precision_decoration_test.cpp
|
||||||
remove_selection_test.cpp
|
remove_selection_test.cpp
|
||||||
remove_unreferenced_instruction_test.cpp
|
remove_unreferenced_instruction_test.cpp
|
||||||
structured_loop_to_selection_test.cpp
|
structured_loop_to_selection_test.cpp
|
||||||
|
177
test/reduce/remove_relaxed_precision_decoration_test.cpp
Normal file
177
test/reduce/remove_relaxed_precision_decoration_test.cpp
Normal file
@ -0,0 +1,177 @@
|
|||||||
|
// Copyright (c) 2019 Google LLC
|
||||||
|
//
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, software
|
||||||
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
// See the License for the specific language governing permissions and
|
||||||
|
// limitations under the License.
|
||||||
|
|
||||||
|
#include "source/reduce/remove_relaxed_precision_decoration_opportunity_finder.h"
|
||||||
|
|
||||||
|
#include "source/opt/build_module.h"
|
||||||
|
#include "source/reduce/reduction_opportunity.h"
|
||||||
|
#include "source/reduce/reduction_pass.h"
|
||||||
|
#include "test/reduce/reduce_test_util.h"
|
||||||
|
|
||||||
|
namespace spvtools {
|
||||||
|
namespace reduce {
|
||||||
|
namespace {
|
||||||
|
|
||||||
|
TEST(RemoveRelaxedPrecisionDecorationTest, NothingToRemove) {
|
||||||
|
const std::string source = R"(
|
||||||
|
OpCapability Shader
|
||||||
|
%1 = OpExtInstImport "GLSL.std.450"
|
||||||
|
OpMemoryModel Logical GLSL450
|
||||||
|
OpEntryPoint Fragment %4 "main"
|
||||||
|
OpExecutionMode %4 OriginUpperLeft
|
||||||
|
OpSource ESSL 310
|
||||||
|
%2 = OpTypeVoid
|
||||||
|
%3 = OpTypeFunction %2
|
||||||
|
%4 = OpFunction %2 None %3
|
||||||
|
%5 = OpLabel
|
||||||
|
OpReturn
|
||||||
|
OpFunctionEnd
|
||||||
|
)";
|
||||||
|
|
||||||
|
const auto env = SPV_ENV_UNIVERSAL_1_3;
|
||||||
|
const auto consumer = nullptr;
|
||||||
|
const auto context =
|
||||||
|
BuildModule(env, consumer, source, kReduceAssembleOption);
|
||||||
|
const auto ops = RemoveRelaxedPrecisionDecorationOpportunityFinder()
|
||||||
|
.GetAvailableOpportunities(context.get());
|
||||||
|
ASSERT_EQ(0, ops.size());
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST(RemoveRelaxedPrecisionDecorationTest, RemoveDecorations) {
|
||||||
|
const std::string source = R"(
|
||||||
|
OpCapability Shader
|
||||||
|
%1 = OpExtInstImport "GLSL.std.450"
|
||||||
|
OpMemoryModel Logical GLSL450
|
||||||
|
OpEntryPoint Fragment %4 "main"
|
||||||
|
OpExecutionMode %4 OriginUpperLeft
|
||||||
|
OpSource ESSL 310
|
||||||
|
OpName %4 "main"
|
||||||
|
OpName %8 "f"
|
||||||
|
OpName %12 "i"
|
||||||
|
OpName %16 "v"
|
||||||
|
OpName %19 "S"
|
||||||
|
OpMemberName %19 0 "a"
|
||||||
|
OpMemberName %19 1 "b"
|
||||||
|
OpMemberName %19 2 "c"
|
||||||
|
OpName %21 "s"
|
||||||
|
OpDecorate %8 RelaxedPrecision
|
||||||
|
OpDecorate %12 RelaxedPrecision
|
||||||
|
OpDecorate %16 RelaxedPrecision
|
||||||
|
OpDecorate %17 RelaxedPrecision
|
||||||
|
OpDecorate %18 RelaxedPrecision
|
||||||
|
OpMemberDecorate %19 0 RelaxedPrecision
|
||||||
|
OpMemberDecorate %19 1 RelaxedPrecision
|
||||||
|
OpMemberDecorate %19 2 RelaxedPrecision
|
||||||
|
OpDecorate %22 RelaxedPrecision
|
||||||
|
OpDecorate %23 RelaxedPrecision
|
||||||
|
OpDecorate %24 RelaxedPrecision
|
||||||
|
%2 = OpTypeVoid
|
||||||
|
%3 = OpTypeFunction %2
|
||||||
|
%6 = OpTypeFloat 32
|
||||||
|
%7 = OpTypePointer Function %6
|
||||||
|
%9 = OpConstant %6 2
|
||||||
|
%10 = OpTypeInt 32 1
|
||||||
|
%11 = OpTypePointer Function %10
|
||||||
|
%13 = OpConstant %10 22
|
||||||
|
%14 = OpTypeVector %6 2
|
||||||
|
%15 = OpTypePointer Function %14
|
||||||
|
%19 = OpTypeStruct %10 %6 %14
|
||||||
|
%20 = OpTypePointer Function %19
|
||||||
|
%4 = OpFunction %2 None %3
|
||||||
|
%5 = OpLabel
|
||||||
|
%8 = OpVariable %7 Function
|
||||||
|
%12 = OpVariable %11 Function
|
||||||
|
%16 = OpVariable %15 Function
|
||||||
|
%21 = OpVariable %20 Function
|
||||||
|
OpStore %8 %9
|
||||||
|
OpStore %12 %13
|
||||||
|
%17 = OpLoad %6 %8
|
||||||
|
%18 = OpCompositeConstruct %14 %17 %17
|
||||||
|
OpStore %16 %18
|
||||||
|
%22 = OpLoad %10 %12
|
||||||
|
%23 = OpLoad %6 %8
|
||||||
|
%24 = OpLoad %14 %16
|
||||||
|
%25 = OpCompositeConstruct %19 %22 %23 %24
|
||||||
|
OpStore %21 %25
|
||||||
|
OpReturn
|
||||||
|
OpFunctionEnd
|
||||||
|
)";
|
||||||
|
|
||||||
|
const auto env = SPV_ENV_UNIVERSAL_1_3;
|
||||||
|
const auto consumer = nullptr;
|
||||||
|
const auto context =
|
||||||
|
BuildModule(env, consumer, source, kReduceAssembleOption);
|
||||||
|
const auto ops = RemoveRelaxedPrecisionDecorationOpportunityFinder()
|
||||||
|
.GetAvailableOpportunities(context.get());
|
||||||
|
ASSERT_EQ(11, ops.size());
|
||||||
|
|
||||||
|
for (auto& op : ops) {
|
||||||
|
ASSERT_TRUE(op->PreconditionHolds());
|
||||||
|
op->TryToApply();
|
||||||
|
}
|
||||||
|
|
||||||
|
const std::string expected = R"(
|
||||||
|
OpCapability Shader
|
||||||
|
%1 = OpExtInstImport "GLSL.std.450"
|
||||||
|
OpMemoryModel Logical GLSL450
|
||||||
|
OpEntryPoint Fragment %4 "main"
|
||||||
|
OpExecutionMode %4 OriginUpperLeft
|
||||||
|
OpSource ESSL 310
|
||||||
|
OpName %4 "main"
|
||||||
|
OpName %8 "f"
|
||||||
|
OpName %12 "i"
|
||||||
|
OpName %16 "v"
|
||||||
|
OpName %19 "S"
|
||||||
|
OpMemberName %19 0 "a"
|
||||||
|
OpMemberName %19 1 "b"
|
||||||
|
OpMemberName %19 2 "c"
|
||||||
|
OpName %21 "s"
|
||||||
|
%2 = OpTypeVoid
|
||||||
|
%3 = OpTypeFunction %2
|
||||||
|
%6 = OpTypeFloat 32
|
||||||
|
%7 = OpTypePointer Function %6
|
||||||
|
%9 = OpConstant %6 2
|
||||||
|
%10 = OpTypeInt 32 1
|
||||||
|
%11 = OpTypePointer Function %10
|
||||||
|
%13 = OpConstant %10 22
|
||||||
|
%14 = OpTypeVector %6 2
|
||||||
|
%15 = OpTypePointer Function %14
|
||||||
|
%19 = OpTypeStruct %10 %6 %14
|
||||||
|
%20 = OpTypePointer Function %19
|
||||||
|
%4 = OpFunction %2 None %3
|
||||||
|
%5 = OpLabel
|
||||||
|
%8 = OpVariable %7 Function
|
||||||
|
%12 = OpVariable %11 Function
|
||||||
|
%16 = OpVariable %15 Function
|
||||||
|
%21 = OpVariable %20 Function
|
||||||
|
OpStore %8 %9
|
||||||
|
OpStore %12 %13
|
||||||
|
%17 = OpLoad %6 %8
|
||||||
|
%18 = OpCompositeConstruct %14 %17 %17
|
||||||
|
OpStore %16 %18
|
||||||
|
%22 = OpLoad %10 %12
|
||||||
|
%23 = OpLoad %6 %8
|
||||||
|
%24 = OpLoad %14 %16
|
||||||
|
%25 = OpCompositeConstruct %19 %22 %23 %24
|
||||||
|
OpStore %21 %25
|
||||||
|
OpReturn
|
||||||
|
OpFunctionEnd
|
||||||
|
)";
|
||||||
|
|
||||||
|
CheckEqual(env, expected, context.get());
|
||||||
|
}
|
||||||
|
|
||||||
|
} // namespace
|
||||||
|
} // namespace reduce
|
||||||
|
} // namespace spvtools
|
Loading…
Reference in New Issue
Block a user