blob: 361d3cacb45d9cda15aad76e203ad5bb8aa1fcb9 [file] [log] [blame]
Yi Kong4e9417d2022-10-12 11:48:30 +09001// Copyright (c) 2016 Google Inc.
2//
3// Licensed under the Apache License, Version 2.0 (the "License");
4// you may not use this file except in compliance with the License.
5// You may obtain a copy of the License at
6//
7// http://www.apache.org/licenses/LICENSE-2.0
8//
9// Unless required by applicable law or agreed to in writing, software
10// distributed under the License is distributed on an "AS IS" BASIS,
11// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12// See the License for the specific language governing permissions and
13// limitations under the License.
14
15#ifndef SOURCE_OPT_FOLD_SPEC_CONSTANT_OP_AND_COMPOSITE_PASS_H_
16#define SOURCE_OPT_FOLD_SPEC_CONSTANT_OP_AND_COMPOSITE_PASS_H_
17
18#include <memory>
19#include <unordered_map>
20#include <vector>
21
22#include "source/opt/constants.h"
23#include "source/opt/def_use_manager.h"
24#include "source/opt/ir_context.h"
25#include "source/opt/module.h"
26#include "source/opt/pass.h"
27#include "source/opt/type_manager.h"
28
29namespace spvtools {
30namespace opt {
31
32// See optimizer.hpp for documentation.
33class FoldSpecConstantOpAndCompositePass : public Pass {
34 public:
35 FoldSpecConstantOpAndCompositePass() = default;
36
37 const char* name() const override { return "fold-spec-const-op-composite"; }
38
39 // Iterates through the types-constants-globals section of the given module,
40 // finds the Spec Constants defined with OpSpecConstantOp and
41 // OpSpecConstantComposite instructions. If the result value of those spec
42 // constants can be folded, fold them to their corresponding normal constants.
43 Status Process() override;
44
45 private:
46 // Processes the OpSpecConstantOp instruction pointed by the given
47 // instruction iterator, folds it to normal constants if possible. Returns
48 // true if the spec constant is folded to normal constants. New instructions
49 // will be inserted before the OpSpecConstantOp instruction pointed by the
50 // instruction iterator. The instruction iterator, which is passed by
51 // pointer, will still point to the original OpSpecConstantOp instruction. If
52 // folding is done successfully, the original OpSpecConstantOp instruction
53 // will be changed to Nop and new folded instruction will be inserted before
54 // it.
55 bool ProcessOpSpecConstantOp(Module::inst_iterator* pos);
56
57 // Returns the result of folding the OpSpecConstantOp instruction
58 // |inst_iter_ptr| using the instruction folder.
59 Instruction* FoldWithInstructionFolder(Module::inst_iterator* inst_iter_ptr);
60
61 // Try to fold the OpSpecConstantOp VectorShuffle instruction pointed by the
62 // given instruction iterator to a normal constant defining instruction.
63 // Returns the pointer to the new constant defining instruction if succeeded.
64 // Otherwise return nullptr.
65 Instruction* DoVectorShuffle(Module::inst_iterator* inst_iter_ptr);
66
67 // Try to fold the OpSpecConstantOp <component wise operations> instruction
68 // pointed by the given instruction iterator to a normal constant defining
69 // instruction. Returns the pointer to the new constant defining instruction
70 // if succeeded, otherwise return nullptr.
71 Instruction* DoComponentWiseOperation(Module::inst_iterator* inst_iter_ptr);
72
73 // Returns the |element|'th subtype of |type|.
74 //
75 // |type| must be a composite type.
76 uint32_t GetTypeComponent(uint32_t type, uint32_t element) const;
77};
78
79} // namespace opt
80} // namespace spvtools
81
82#endif // SOURCE_OPT_FOLD_SPEC_CONSTANT_OP_AND_COMPOSITE_PASS_H_