Warning, /include/llvm/Target/TargetMacroFusion.td is written in an unsupported language. File is not indexed.
0001 //===-- TargetMacroFusion.td - Target Macro Fusion ---------*- tablegen -*-===//
0002 //
0003 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
0004 // See https://llvm.org/LICENSE.txt for license information.
0005 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
0006 //
0007 //===----------------------------------------------------------------------===//
0008 //
0009 // This file defines the TableGen-based macro fusion classes.
0010
0011 // The target instruction that FusionPredicate will be evaluated on.
0012 class FusionTarget;
0013 def first_fusion_target : FusionTarget;
0014 def second_fusion_target : FusionTarget;
0015 def both_fusion_target : FusionTarget;
0016
0017 // Base class of FusionPredicate, etc. The available variables are:
0018 // * const TargetInstrInfo &TII
0019 // * const TargetSubtargetInfo &STI
0020 // * const MachineRegisterInfo &MRI
0021 // * const MachineInstr *FirstMI
0022 // * const MachineInstr &SecondMI
0023 class FusionPredicate<FusionTarget target> {
0024 FusionTarget Target = target;
0025 }
0026 class FirstFusionPredicate: FusionPredicate<first_fusion_target>;
0027 class SecondFusionPredicate: FusionPredicate<second_fusion_target>;
0028 class BothFusionPredicate: FusionPredicate<both_fusion_target>;
0029
0030 // FusionPredicate with raw code predicate.
0031 class FusionPredicateWithCode<code pred> : FusionPredicate<both_fusion_target> {
0032 code Predicate = pred;
0033 }
0034
0035 // FusionPredicate with MCInstPredicate.
0036 class FusionPredicateWithMCInstPredicate<FusionTarget target, MCInstPredicate pred>
0037 : FusionPredicate<target> {
0038 MCInstPredicate Predicate = pred;
0039 }
0040 class FirstFusionPredicateWithMCInstPredicate<MCInstPredicate pred>
0041 : FusionPredicateWithMCInstPredicate<first_fusion_target, pred>;
0042 class SecondFusionPredicateWithMCInstPredicate<MCInstPredicate pred>
0043 : FusionPredicateWithMCInstPredicate<second_fusion_target, pred>;
0044 // The pred will be applied on both firstMI and secondMI.
0045 class BothFusionPredicateWithMCInstPredicate<MCInstPredicate pred>
0046 : FusionPredicateWithMCInstPredicate<both_fusion_target, pred>;
0047
0048 // Tie firstOpIdx and secondOpIdx. The operand of `FirstMI` at position
0049 // `firstOpIdx` should be the same as the operand of `SecondMI` at position
0050 // `secondOpIdx`.
0051 // If the fusion has `IsCommutable` being true and the operand at `secondOpIdx`
0052 // has commutable operand, then the commutable operand will be checked too.
0053 class TieReg<int firstOpIdx, int secondOpIdx> : BothFusionPredicate {
0054 int FirstOpIdx = firstOpIdx;
0055 int SecondOpIdx = secondOpIdx;
0056 }
0057
0058 // The operand of `SecondMI` at position `firstOpIdx` should be the same as the
0059 // operand at position `secondOpIdx`.
0060 // If the fusion has `IsCommutable` being true and the operand at `secondOpIdx`
0061 // has commutable operand, then the commutable operand will be checked too.
0062 class SameReg<int firstOpIdx, int secondOpIdx> : SecondFusionPredicate {
0063 int FirstOpIdx = firstOpIdx;
0064 int SecondOpIdx = secondOpIdx;
0065 }
0066
0067 // A predicate for wildcard. The generated code will be like:
0068 // ```
0069 // if (!FirstMI)
0070 // return ReturnValue;
0071 // ```
0072 class WildcardPred<bit ret> : FirstFusionPredicate {
0073 bit ReturnValue = ret;
0074 }
0075 def WildcardFalse : WildcardPred<0>;
0076 def WildcardTrue : WildcardPred<1>;
0077
0078 // Indicates that the destination register of `FirstMI` should have one use if
0079 // it is a virtual register.
0080 class OneUsePred : FirstFusionPredicate;
0081 def OneUse : OneUsePred;
0082
0083 // Handled by MacroFusionPredicatorEmitter backend.
0084 // The generated predicator will be like:
0085 // ```
0086 // bool isNAME(const TargetInstrInfo &TII,
0087 // const TargetSubtargetInfo &STI,
0088 // const MachineInstr *FirstMI,
0089 // const MachineInstr &SecondMI) {
0090 // auto &MRI = SecondMI.getMF()->getRegInfo();
0091 // /* Predicates */
0092 // return true;
0093 // }
0094 // ```
0095 //
0096 // `IsCommutable` means whether we should handle commutable operands.
0097 class Fusion<string name, string fieldName, string desc, list<FusionPredicate> predicates>
0098 : SubtargetFeature<name, fieldName, "true", desc> {
0099 list<FusionPredicate> Predicates = predicates;
0100 bit IsCommutable = 0;
0101 }
0102
0103 // The generated predicator will be like:
0104 // ```
0105 // bool isNAME(const TargetInstrInfo &TII,
0106 // const TargetSubtargetInfo &STI,
0107 // const MachineInstr *FirstMI,
0108 // const MachineInstr &SecondMI) {
0109 // auto &MRI = SecondMI.getMF()->getRegInfo();
0110 // /* Prolog */
0111 // /* Predicate for `SecondMI` */
0112 // /* Wildcard */
0113 // /* Predicate for `FirstMI` */
0114 // /* Check same registers */
0115 // /* Check One Use */
0116 // /* Tie registers */
0117 // /* Epilog */
0118 // return true;
0119 // }
0120 // ```
0121 class SimpleFusion<string name, string fieldName, string desc,
0122 MCInstPredicate firstPred, MCInstPredicate secondPred,
0123 list<FusionPredicate> prolog = [],
0124 list<FusionPredicate> epilog = []>
0125 : Fusion<name, fieldName, desc,
0126 !listconcat(
0127 prolog,
0128 [
0129 SecondFusionPredicateWithMCInstPredicate<secondPred>,
0130 WildcardTrue,
0131 FirstFusionPredicateWithMCInstPredicate<firstPred>,
0132 SameReg<0, 1>,
0133 OneUse,
0134 TieReg<0, 1>,
0135 ],
0136 epilog)>;
0137
0138 class SingleFusion<string name, string fieldName, string desc,
0139 Instruction firstInst, Instruction secondInst,
0140 MCInstPredicate firstInstPred = TruePred,
0141 MCInstPredicate secondInstPred = TruePred,
0142 list<FusionPredicate> prolog = [],
0143 list<FusionPredicate> epilog = []>
0144 : SimpleFusion<name, fieldName, desc,
0145 CheckAll<!listconcat(
0146 [CheckOpcode<[firstInst]>],
0147 [firstInstPred])>,
0148 CheckAll<!listconcat(
0149 [CheckOpcode<[secondInst]>],
0150 [secondInstPred])>,
0151 prolog, epilog> {
0152 let IsCommutable = secondInst.isCommutable;
0153 }