1*9880d681SAndroid Build Coastguard Worker //===- AArch64InstrInfo.h - AArch64 Instruction Information -----*- C++ -*-===//
2*9880d681SAndroid Build Coastguard Worker //
3*9880d681SAndroid Build Coastguard Worker // The LLVM Compiler Infrastructure
4*9880d681SAndroid Build Coastguard Worker //
5*9880d681SAndroid Build Coastguard Worker // This file is distributed under the University of Illinois Open Source
6*9880d681SAndroid Build Coastguard Worker // License. See LICENSE.TXT for details.
7*9880d681SAndroid Build Coastguard Worker //
8*9880d681SAndroid Build Coastguard Worker //===----------------------------------------------------------------------===//
9*9880d681SAndroid Build Coastguard Worker //
10*9880d681SAndroid Build Coastguard Worker // This file contains the AArch64 implementation of the TargetInstrInfo class.
11*9880d681SAndroid Build Coastguard Worker //
12*9880d681SAndroid Build Coastguard Worker //===----------------------------------------------------------------------===//
13*9880d681SAndroid Build Coastguard Worker
14*9880d681SAndroid Build Coastguard Worker #ifndef LLVM_LIB_TARGET_AARCH64_AARCH64INSTRINFO_H
15*9880d681SAndroid Build Coastguard Worker #define LLVM_LIB_TARGET_AARCH64_AARCH64INSTRINFO_H
16*9880d681SAndroid Build Coastguard Worker
17*9880d681SAndroid Build Coastguard Worker #include "AArch64.h"
18*9880d681SAndroid Build Coastguard Worker #include "AArch64RegisterInfo.h"
19*9880d681SAndroid Build Coastguard Worker #include "llvm/CodeGen/MachineCombinerPattern.h"
20*9880d681SAndroid Build Coastguard Worker #include "llvm/Target/TargetInstrInfo.h"
21*9880d681SAndroid Build Coastguard Worker
22*9880d681SAndroid Build Coastguard Worker #define GET_INSTRINFO_HEADER
23*9880d681SAndroid Build Coastguard Worker #include "AArch64GenInstrInfo.inc"
24*9880d681SAndroid Build Coastguard Worker
25*9880d681SAndroid Build Coastguard Worker namespace llvm {
26*9880d681SAndroid Build Coastguard Worker
27*9880d681SAndroid Build Coastguard Worker class AArch64Subtarget;
28*9880d681SAndroid Build Coastguard Worker class AArch64TargetMachine;
29*9880d681SAndroid Build Coastguard Worker
30*9880d681SAndroid Build Coastguard Worker class AArch64InstrInfo : public AArch64GenInstrInfo {
31*9880d681SAndroid Build Coastguard Worker const AArch64RegisterInfo RI;
32*9880d681SAndroid Build Coastguard Worker const AArch64Subtarget &Subtarget;
33*9880d681SAndroid Build Coastguard Worker
34*9880d681SAndroid Build Coastguard Worker public:
35*9880d681SAndroid Build Coastguard Worker explicit AArch64InstrInfo(const AArch64Subtarget &STI);
36*9880d681SAndroid Build Coastguard Worker
37*9880d681SAndroid Build Coastguard Worker /// getRegisterInfo - TargetInstrInfo is a superset of MRegister info. As
38*9880d681SAndroid Build Coastguard Worker /// such, whenever a client has an instance of instruction info, it should
39*9880d681SAndroid Build Coastguard Worker /// always be able to get register info as well (through this method).
getRegisterInfo()40*9880d681SAndroid Build Coastguard Worker const AArch64RegisterInfo &getRegisterInfo() const { return RI; }
41*9880d681SAndroid Build Coastguard Worker
42*9880d681SAndroid Build Coastguard Worker unsigned GetInstSizeInBytes(const MachineInstr &MI) const;
43*9880d681SAndroid Build Coastguard Worker
44*9880d681SAndroid Build Coastguard Worker bool isAsCheapAsAMove(const MachineInstr &MI) const override;
45*9880d681SAndroid Build Coastguard Worker
46*9880d681SAndroid Build Coastguard Worker bool isCoalescableExtInstr(const MachineInstr &MI, unsigned &SrcReg,
47*9880d681SAndroid Build Coastguard Worker unsigned &DstReg, unsigned &SubIdx) const override;
48*9880d681SAndroid Build Coastguard Worker
49*9880d681SAndroid Build Coastguard Worker bool
50*9880d681SAndroid Build Coastguard Worker areMemAccessesTriviallyDisjoint(MachineInstr &MIa, MachineInstr &MIb,
51*9880d681SAndroid Build Coastguard Worker AliasAnalysis *AA = nullptr) const override;
52*9880d681SAndroid Build Coastguard Worker
53*9880d681SAndroid Build Coastguard Worker unsigned isLoadFromStackSlot(const MachineInstr &MI,
54*9880d681SAndroid Build Coastguard Worker int &FrameIndex) const override;
55*9880d681SAndroid Build Coastguard Worker unsigned isStoreToStackSlot(const MachineInstr &MI,
56*9880d681SAndroid Build Coastguard Worker int &FrameIndex) const override;
57*9880d681SAndroid Build Coastguard Worker
58*9880d681SAndroid Build Coastguard Worker /// Returns true if there is a shiftable register and that the shift value
59*9880d681SAndroid Build Coastguard Worker /// is non-zero.
60*9880d681SAndroid Build Coastguard Worker bool hasShiftedReg(const MachineInstr &MI) const;
61*9880d681SAndroid Build Coastguard Worker
62*9880d681SAndroid Build Coastguard Worker /// Returns true if there is an extendable register and that the extending
63*9880d681SAndroid Build Coastguard Worker /// value is non-zero.
64*9880d681SAndroid Build Coastguard Worker bool hasExtendedReg(const MachineInstr &MI) const;
65*9880d681SAndroid Build Coastguard Worker
66*9880d681SAndroid Build Coastguard Worker /// \brief Does this instruction set its full destination register to zero?
67*9880d681SAndroid Build Coastguard Worker bool isGPRZero(const MachineInstr &MI) const;
68*9880d681SAndroid Build Coastguard Worker
69*9880d681SAndroid Build Coastguard Worker /// \brief Does this instruction rename a GPR without modifying bits?
70*9880d681SAndroid Build Coastguard Worker bool isGPRCopy(const MachineInstr &MI) const;
71*9880d681SAndroid Build Coastguard Worker
72*9880d681SAndroid Build Coastguard Worker /// \brief Does this instruction rename an FPR without modifying bits?
73*9880d681SAndroid Build Coastguard Worker bool isFPRCopy(const MachineInstr &MI) const;
74*9880d681SAndroid Build Coastguard Worker
75*9880d681SAndroid Build Coastguard Worker /// Return true if this is load/store scales or extends its register offset.
76*9880d681SAndroid Build Coastguard Worker /// This refers to scaling a dynamic index as opposed to scaled immediates.
77*9880d681SAndroid Build Coastguard Worker /// MI should be a memory op that allows scaled addressing.
78*9880d681SAndroid Build Coastguard Worker bool isScaledAddr(const MachineInstr &MI) const;
79*9880d681SAndroid Build Coastguard Worker
80*9880d681SAndroid Build Coastguard Worker /// Return true if pairing the given load or store is hinted to be
81*9880d681SAndroid Build Coastguard Worker /// unprofitable.
82*9880d681SAndroid Build Coastguard Worker bool isLdStPairSuppressed(const MachineInstr &MI) const;
83*9880d681SAndroid Build Coastguard Worker
84*9880d681SAndroid Build Coastguard Worker /// Return true if this is an unscaled load/store.
85*9880d681SAndroid Build Coastguard Worker bool isUnscaledLdSt(unsigned Opc) const;
86*9880d681SAndroid Build Coastguard Worker
87*9880d681SAndroid Build Coastguard Worker /// Return true if this is an unscaled load/store.
88*9880d681SAndroid Build Coastguard Worker bool isUnscaledLdSt(MachineInstr &MI) const;
89*9880d681SAndroid Build Coastguard Worker
90*9880d681SAndroid Build Coastguard Worker /// Return true if this is a load/store that can be potentially paired/merged.
91*9880d681SAndroid Build Coastguard Worker bool isCandidateToMergeOrPair(MachineInstr &MI) const;
92*9880d681SAndroid Build Coastguard Worker
93*9880d681SAndroid Build Coastguard Worker /// Hint that pairing the given load or store is unprofitable.
94*9880d681SAndroid Build Coastguard Worker void suppressLdStPair(MachineInstr &MI) const;
95*9880d681SAndroid Build Coastguard Worker
96*9880d681SAndroid Build Coastguard Worker bool getMemOpBaseRegImmOfs(MachineInstr &LdSt, unsigned &BaseReg,
97*9880d681SAndroid Build Coastguard Worker int64_t &Offset,
98*9880d681SAndroid Build Coastguard Worker const TargetRegisterInfo *TRI) const override;
99*9880d681SAndroid Build Coastguard Worker
100*9880d681SAndroid Build Coastguard Worker bool getMemOpBaseRegImmOfsWidth(MachineInstr &LdSt, unsigned &BaseReg,
101*9880d681SAndroid Build Coastguard Worker int64_t &Offset, unsigned &Width,
102*9880d681SAndroid Build Coastguard Worker const TargetRegisterInfo *TRI) const;
103*9880d681SAndroid Build Coastguard Worker
enableClusterLoads()104*9880d681SAndroid Build Coastguard Worker bool enableClusterLoads() const override { return true; }
105*9880d681SAndroid Build Coastguard Worker
enableClusterStores()106*9880d681SAndroid Build Coastguard Worker bool enableClusterStores() const override { return true; }
107*9880d681SAndroid Build Coastguard Worker
108*9880d681SAndroid Build Coastguard Worker bool shouldClusterMemOps(MachineInstr &FirstLdSt, MachineInstr &SecondLdSt,
109*9880d681SAndroid Build Coastguard Worker unsigned NumLoads) const override;
110*9880d681SAndroid Build Coastguard Worker
111*9880d681SAndroid Build Coastguard Worker bool shouldScheduleAdjacent(MachineInstr &First,
112*9880d681SAndroid Build Coastguard Worker MachineInstr &Second) const override;
113*9880d681SAndroid Build Coastguard Worker
114*9880d681SAndroid Build Coastguard Worker MachineInstr *emitFrameIndexDebugValue(MachineFunction &MF, int FrameIx,
115*9880d681SAndroid Build Coastguard Worker uint64_t Offset, const MDNode *Var,
116*9880d681SAndroid Build Coastguard Worker const MDNode *Expr,
117*9880d681SAndroid Build Coastguard Worker const DebugLoc &DL) const;
118*9880d681SAndroid Build Coastguard Worker void copyPhysRegTuple(MachineBasicBlock &MBB, MachineBasicBlock::iterator I,
119*9880d681SAndroid Build Coastguard Worker const DebugLoc &DL, unsigned DestReg, unsigned SrcReg,
120*9880d681SAndroid Build Coastguard Worker bool KillSrc, unsigned Opcode,
121*9880d681SAndroid Build Coastguard Worker llvm::ArrayRef<unsigned> Indices) const;
122*9880d681SAndroid Build Coastguard Worker void copyPhysReg(MachineBasicBlock &MBB, MachineBasicBlock::iterator I,
123*9880d681SAndroid Build Coastguard Worker const DebugLoc &DL, unsigned DestReg, unsigned SrcReg,
124*9880d681SAndroid Build Coastguard Worker bool KillSrc) const override;
125*9880d681SAndroid Build Coastguard Worker
126*9880d681SAndroid Build Coastguard Worker void storeRegToStackSlot(MachineBasicBlock &MBB,
127*9880d681SAndroid Build Coastguard Worker MachineBasicBlock::iterator MBBI, unsigned SrcReg,
128*9880d681SAndroid Build Coastguard Worker bool isKill, int FrameIndex,
129*9880d681SAndroid Build Coastguard Worker const TargetRegisterClass *RC,
130*9880d681SAndroid Build Coastguard Worker const TargetRegisterInfo *TRI) const override;
131*9880d681SAndroid Build Coastguard Worker
132*9880d681SAndroid Build Coastguard Worker void loadRegFromStackSlot(MachineBasicBlock &MBB,
133*9880d681SAndroid Build Coastguard Worker MachineBasicBlock::iterator MBBI, unsigned DestReg,
134*9880d681SAndroid Build Coastguard Worker int FrameIndex, const TargetRegisterClass *RC,
135*9880d681SAndroid Build Coastguard Worker const TargetRegisterInfo *TRI) const override;
136*9880d681SAndroid Build Coastguard Worker
137*9880d681SAndroid Build Coastguard Worker using TargetInstrInfo::foldMemoryOperandImpl;
138*9880d681SAndroid Build Coastguard Worker MachineInstr *
139*9880d681SAndroid Build Coastguard Worker foldMemoryOperandImpl(MachineFunction &MF, MachineInstr &MI,
140*9880d681SAndroid Build Coastguard Worker ArrayRef<unsigned> Ops,
141*9880d681SAndroid Build Coastguard Worker MachineBasicBlock::iterator InsertPt, int FrameIndex,
142*9880d681SAndroid Build Coastguard Worker LiveIntervals *LIS = nullptr) const override;
143*9880d681SAndroid Build Coastguard Worker
144*9880d681SAndroid Build Coastguard Worker bool analyzeBranch(MachineBasicBlock &MBB, MachineBasicBlock *&TBB,
145*9880d681SAndroid Build Coastguard Worker MachineBasicBlock *&FBB,
146*9880d681SAndroid Build Coastguard Worker SmallVectorImpl<MachineOperand> &Cond,
147*9880d681SAndroid Build Coastguard Worker bool AllowModify = false) const override;
148*9880d681SAndroid Build Coastguard Worker unsigned RemoveBranch(MachineBasicBlock &MBB) const override;
149*9880d681SAndroid Build Coastguard Worker unsigned InsertBranch(MachineBasicBlock &MBB, MachineBasicBlock *TBB,
150*9880d681SAndroid Build Coastguard Worker MachineBasicBlock *FBB, ArrayRef<MachineOperand> Cond,
151*9880d681SAndroid Build Coastguard Worker const DebugLoc &DL) const override;
152*9880d681SAndroid Build Coastguard Worker bool
153*9880d681SAndroid Build Coastguard Worker ReverseBranchCondition(SmallVectorImpl<MachineOperand> &Cond) const override;
154*9880d681SAndroid Build Coastguard Worker bool canInsertSelect(const MachineBasicBlock &, ArrayRef<MachineOperand> Cond,
155*9880d681SAndroid Build Coastguard Worker unsigned, unsigned, int &, int &, int &) const override;
156*9880d681SAndroid Build Coastguard Worker void insertSelect(MachineBasicBlock &MBB, MachineBasicBlock::iterator MI,
157*9880d681SAndroid Build Coastguard Worker const DebugLoc &DL, unsigned DstReg,
158*9880d681SAndroid Build Coastguard Worker ArrayRef<MachineOperand> Cond, unsigned TrueReg,
159*9880d681SAndroid Build Coastguard Worker unsigned FalseReg) const override;
160*9880d681SAndroid Build Coastguard Worker void getNoopForMachoTarget(MCInst &NopInst) const override;
161*9880d681SAndroid Build Coastguard Worker
162*9880d681SAndroid Build Coastguard Worker /// analyzeCompare - For a comparison instruction, return the source registers
163*9880d681SAndroid Build Coastguard Worker /// in SrcReg and SrcReg2, and the value it compares against in CmpValue.
164*9880d681SAndroid Build Coastguard Worker /// Return true if the comparison instruction can be analyzed.
165*9880d681SAndroid Build Coastguard Worker bool analyzeCompare(const MachineInstr &MI, unsigned &SrcReg,
166*9880d681SAndroid Build Coastguard Worker unsigned &SrcReg2, int &CmpMask,
167*9880d681SAndroid Build Coastguard Worker int &CmpValue) const override;
168*9880d681SAndroid Build Coastguard Worker /// optimizeCompareInstr - Convert the instruction supplying the argument to
169*9880d681SAndroid Build Coastguard Worker /// the comparison into one that sets the zero bit in the flags register.
170*9880d681SAndroid Build Coastguard Worker bool optimizeCompareInstr(MachineInstr &CmpInstr, unsigned SrcReg,
171*9880d681SAndroid Build Coastguard Worker unsigned SrcReg2, int CmpMask, int CmpValue,
172*9880d681SAndroid Build Coastguard Worker const MachineRegisterInfo *MRI) const override;
173*9880d681SAndroid Build Coastguard Worker bool optimizeCondBranch(MachineInstr &MI) const override;
174*9880d681SAndroid Build Coastguard Worker
175*9880d681SAndroid Build Coastguard Worker /// Return true when a code sequence can improve throughput. It
176*9880d681SAndroid Build Coastguard Worker /// should be called only for instructions in loops.
177*9880d681SAndroid Build Coastguard Worker /// \param Pattern - combiner pattern
178*9880d681SAndroid Build Coastguard Worker bool isThroughputPattern(MachineCombinerPattern Pattern) const override;
179*9880d681SAndroid Build Coastguard Worker /// Return true when there is potentially a faster code sequence
180*9880d681SAndroid Build Coastguard Worker /// for an instruction chain ending in <Root>. All potential patterns are
181*9880d681SAndroid Build Coastguard Worker /// listed in the <Patterns> array.
182*9880d681SAndroid Build Coastguard Worker bool getMachineCombinerPatterns(MachineInstr &Root,
183*9880d681SAndroid Build Coastguard Worker SmallVectorImpl<MachineCombinerPattern> &Patterns)
184*9880d681SAndroid Build Coastguard Worker const override;
185*9880d681SAndroid Build Coastguard Worker /// Return true when Inst is associative and commutative so that it can be
186*9880d681SAndroid Build Coastguard Worker /// reassociated.
187*9880d681SAndroid Build Coastguard Worker bool isAssociativeAndCommutative(const MachineInstr &Inst) const override;
188*9880d681SAndroid Build Coastguard Worker /// When getMachineCombinerPatterns() finds patterns, this function generates
189*9880d681SAndroid Build Coastguard Worker /// the instructions that could replace the original code sequence
190*9880d681SAndroid Build Coastguard Worker void genAlternativeCodeSequence(
191*9880d681SAndroid Build Coastguard Worker MachineInstr &Root, MachineCombinerPattern Pattern,
192*9880d681SAndroid Build Coastguard Worker SmallVectorImpl<MachineInstr *> &InsInstrs,
193*9880d681SAndroid Build Coastguard Worker SmallVectorImpl<MachineInstr *> &DelInstrs,
194*9880d681SAndroid Build Coastguard Worker DenseMap<unsigned, unsigned> &InstrIdxForVirtReg) const override;
195*9880d681SAndroid Build Coastguard Worker /// AArch64 supports MachineCombiner.
196*9880d681SAndroid Build Coastguard Worker bool useMachineCombiner() const override;
197*9880d681SAndroid Build Coastguard Worker
198*9880d681SAndroid Build Coastguard Worker bool expandPostRAPseudo(MachineInstr &MI) const override;
199*9880d681SAndroid Build Coastguard Worker
200*9880d681SAndroid Build Coastguard Worker std::pair<unsigned, unsigned>
201*9880d681SAndroid Build Coastguard Worker decomposeMachineOperandsTargetFlags(unsigned TF) const override;
202*9880d681SAndroid Build Coastguard Worker ArrayRef<std::pair<unsigned, const char *>>
203*9880d681SAndroid Build Coastguard Worker getSerializableDirectMachineOperandTargetFlags() const override;
204*9880d681SAndroid Build Coastguard Worker ArrayRef<std::pair<unsigned, const char *>>
205*9880d681SAndroid Build Coastguard Worker getSerializableBitmaskMachineOperandTargetFlags() const override;
206*9880d681SAndroid Build Coastguard Worker
207*9880d681SAndroid Build Coastguard Worker private:
208*9880d681SAndroid Build Coastguard Worker void instantiateCondBranch(MachineBasicBlock &MBB, const DebugLoc &DL,
209*9880d681SAndroid Build Coastguard Worker MachineBasicBlock *TBB,
210*9880d681SAndroid Build Coastguard Worker ArrayRef<MachineOperand> Cond) const;
211*9880d681SAndroid Build Coastguard Worker bool substituteCmpToZero(MachineInstr &CmpInstr, unsigned SrcReg,
212*9880d681SAndroid Build Coastguard Worker const MachineRegisterInfo *MRI) const;
213*9880d681SAndroid Build Coastguard Worker };
214*9880d681SAndroid Build Coastguard Worker
215*9880d681SAndroid Build Coastguard Worker /// emitFrameOffset - Emit instructions as needed to set DestReg to SrcReg
216*9880d681SAndroid Build Coastguard Worker /// plus Offset. This is intended to be used from within the prolog/epilog
217*9880d681SAndroid Build Coastguard Worker /// insertion (PEI) pass, where a virtual scratch register may be allocated
218*9880d681SAndroid Build Coastguard Worker /// if necessary, to be replaced by the scavenger at the end of PEI.
219*9880d681SAndroid Build Coastguard Worker void emitFrameOffset(MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI,
220*9880d681SAndroid Build Coastguard Worker const DebugLoc &DL, unsigned DestReg, unsigned SrcReg,
221*9880d681SAndroid Build Coastguard Worker int Offset, const TargetInstrInfo *TII,
222*9880d681SAndroid Build Coastguard Worker MachineInstr::MIFlag = MachineInstr::NoFlags,
223*9880d681SAndroid Build Coastguard Worker bool SetNZCV = false);
224*9880d681SAndroid Build Coastguard Worker
225*9880d681SAndroid Build Coastguard Worker /// rewriteAArch64FrameIndex - Rewrite MI to access 'Offset' bytes from the
226*9880d681SAndroid Build Coastguard Worker /// FP. Return false if the offset could not be handled directly in MI, and
227*9880d681SAndroid Build Coastguard Worker /// return the left-over portion by reference.
228*9880d681SAndroid Build Coastguard Worker bool rewriteAArch64FrameIndex(MachineInstr &MI, unsigned FrameRegIdx,
229*9880d681SAndroid Build Coastguard Worker unsigned FrameReg, int &Offset,
230*9880d681SAndroid Build Coastguard Worker const AArch64InstrInfo *TII);
231*9880d681SAndroid Build Coastguard Worker
232*9880d681SAndroid Build Coastguard Worker /// \brief Use to report the frame offset status in isAArch64FrameOffsetLegal.
233*9880d681SAndroid Build Coastguard Worker enum AArch64FrameOffsetStatus {
234*9880d681SAndroid Build Coastguard Worker AArch64FrameOffsetCannotUpdate = 0x0, ///< Offset cannot apply.
235*9880d681SAndroid Build Coastguard Worker AArch64FrameOffsetIsLegal = 0x1, ///< Offset is legal.
236*9880d681SAndroid Build Coastguard Worker AArch64FrameOffsetCanUpdate = 0x2 ///< Offset can apply, at least partly.
237*9880d681SAndroid Build Coastguard Worker };
238*9880d681SAndroid Build Coastguard Worker
239*9880d681SAndroid Build Coastguard Worker /// \brief Check if the @p Offset is a valid frame offset for @p MI.
240*9880d681SAndroid Build Coastguard Worker /// The returned value reports the validity of the frame offset for @p MI.
241*9880d681SAndroid Build Coastguard Worker /// It uses the values defined by AArch64FrameOffsetStatus for that.
242*9880d681SAndroid Build Coastguard Worker /// If result == AArch64FrameOffsetCannotUpdate, @p MI cannot be updated to
243*9880d681SAndroid Build Coastguard Worker /// use an offset.eq
244*9880d681SAndroid Build Coastguard Worker /// If result & AArch64FrameOffsetIsLegal, @p Offset can completely be
245*9880d681SAndroid Build Coastguard Worker /// rewriten in @p MI.
246*9880d681SAndroid Build Coastguard Worker /// If result & AArch64FrameOffsetCanUpdate, @p Offset contains the
247*9880d681SAndroid Build Coastguard Worker /// amount that is off the limit of the legal offset.
248*9880d681SAndroid Build Coastguard Worker /// If set, @p OutUseUnscaledOp will contain the whether @p MI should be
249*9880d681SAndroid Build Coastguard Worker /// turned into an unscaled operator, which opcode is in @p OutUnscaledOp.
250*9880d681SAndroid Build Coastguard Worker /// If set, @p EmittableOffset contains the amount that can be set in @p MI
251*9880d681SAndroid Build Coastguard Worker /// (possibly with @p OutUnscaledOp if OutUseUnscaledOp is true) and that
252*9880d681SAndroid Build Coastguard Worker /// is a legal offset.
253*9880d681SAndroid Build Coastguard Worker int isAArch64FrameOffsetLegal(const MachineInstr &MI, int &Offset,
254*9880d681SAndroid Build Coastguard Worker bool *OutUseUnscaledOp = nullptr,
255*9880d681SAndroid Build Coastguard Worker unsigned *OutUnscaledOp = nullptr,
256*9880d681SAndroid Build Coastguard Worker int *EmittableOffset = nullptr);
257*9880d681SAndroid Build Coastguard Worker
isUncondBranchOpcode(int Opc)258*9880d681SAndroid Build Coastguard Worker static inline bool isUncondBranchOpcode(int Opc) { return Opc == AArch64::B; }
259*9880d681SAndroid Build Coastguard Worker
isCondBranchOpcode(int Opc)260*9880d681SAndroid Build Coastguard Worker static inline bool isCondBranchOpcode(int Opc) {
261*9880d681SAndroid Build Coastguard Worker switch (Opc) {
262*9880d681SAndroid Build Coastguard Worker case AArch64::Bcc:
263*9880d681SAndroid Build Coastguard Worker case AArch64::CBZW:
264*9880d681SAndroid Build Coastguard Worker case AArch64::CBZX:
265*9880d681SAndroid Build Coastguard Worker case AArch64::CBNZW:
266*9880d681SAndroid Build Coastguard Worker case AArch64::CBNZX:
267*9880d681SAndroid Build Coastguard Worker case AArch64::TBZW:
268*9880d681SAndroid Build Coastguard Worker case AArch64::TBZX:
269*9880d681SAndroid Build Coastguard Worker case AArch64::TBNZW:
270*9880d681SAndroid Build Coastguard Worker case AArch64::TBNZX:
271*9880d681SAndroid Build Coastguard Worker return true;
272*9880d681SAndroid Build Coastguard Worker default:
273*9880d681SAndroid Build Coastguard Worker return false;
274*9880d681SAndroid Build Coastguard Worker }
275*9880d681SAndroid Build Coastguard Worker }
276*9880d681SAndroid Build Coastguard Worker
isIndirectBranchOpcode(int Opc)277*9880d681SAndroid Build Coastguard Worker static inline bool isIndirectBranchOpcode(int Opc) { return Opc == AArch64::BR; }
278*9880d681SAndroid Build Coastguard Worker
279*9880d681SAndroid Build Coastguard Worker } // end namespace llvm
280*9880d681SAndroid Build Coastguard Worker
281*9880d681SAndroid Build Coastguard Worker #endif
282