131d157ae1ac2cd9c787dc3c1d28e64c682803844Jia Liu//===-- ARMBaseInstrInfo.h - ARM Base Instruction Information ---*- C++ -*-===//
2334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin//
3334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin//                     The LLVM Compiler Infrastructure
4334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin//
5334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin// This file is distributed under the University of Illinois Open Source
6334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin// License. See LICENSE.TXT for details.
7334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin//
8334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin//===----------------------------------------------------------------------===//
9334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin//
10334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin// This file contains the Base ARM implementation of the TargetInstrInfo class.
11334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin//
12334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin//===----------------------------------------------------------------------===//
13334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin
1437ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines#ifndef LLVM_LIB_TARGET_ARM_ARMBASEINSTRINFO_H
1537ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines#define LLVM_LIB_TARGET_ARM_ARMBASEINSTRINFO_H
16334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin
1736b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines#include "MCTargetDesc/ARMBaseInfo.h"
1848575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng#include "llvm/ADT/DenseMap.h"
1948575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng#include "llvm/ADT/SmallSet.h"
20a1514e24cc24b050f53a12650e047799358833a1Chandler Carruth#include "llvm/CodeGen/MachineInstrBuilder.h"
2137ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines#include "llvm/Support/CodeGen.h"
22a1514e24cc24b050f53a12650e047799358833a1Chandler Carruth#include "llvm/Target/TargetInstrInfo.h"
23334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin
244db3cffe94a5285239cc0056f939c6b74a5ca0b6Evan Cheng#define GET_INSTRINFO_HEADER
254db3cffe94a5285239cc0056f939c6b74a5ca0b6Evan Cheng#include "ARMGenInstrInfo.inc"
264db3cffe94a5285239cc0056f939c6b74a5ca0b6Evan Cheng
27334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwinnamespace llvm {
284dbbe3433f7339ed277af55037ff6847f484e5abChris Lattner  class ARMSubtarget;
294dbbe3433f7339ed277af55037ff6847f484e5abChris Lattner  class ARMBaseRegisterInfo;
30334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin
314db3cffe94a5285239cc0056f939c6b74a5ca0b6Evan Chengclass ARMBaseInstrInfo : public ARMGenInstrInfo {
324dbbe3433f7339ed277af55037ff6847f484e5abChris Lattner  const ARMSubtarget &Subtarget;
3348575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng
34334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwinprotected:
35334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin  // Can be only subclassed.
36f95215f551949d5e5adfbf4753aa833b9009b77aAnton Korobeynikov  explicit ARMBaseInstrInfo(const ARMSubtarget &STI);
3748575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng
3837ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  void expandLoadStackGuardBase(MachineBasicBlock::iterator MI,
39de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                                unsigned LoadImmOpc, unsigned LoadOpc) const;
4037ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines
4137ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// Build the equivalent inputs of a REG_SEQUENCE for the given \p MI
4237ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// and \p DefIdx.
4337ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// \p [out] InputRegs of the equivalent REG_SEQUENCE. Each element of
4437ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// the list is modeled as <Reg:SubReg, SubIdx>.
4537ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// E.g., REG_SEQUENCE vreg1:sub1, sub0, vreg2, sub1 would produce
4637ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// two elements:
4737ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// - vreg1:sub1, sub0
4837ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// - vreg2<:0>, sub1
4937ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  ///
5037ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// \returns true if it is possible to build such an input sequence
5137ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// with the pair \p MI, \p DefIdx. False otherwise.
5237ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  ///
5337ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// \pre MI.isRegSequenceLike().
5437ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  bool getRegSequenceLikeInputs(
5537ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines      const MachineInstr &MI, unsigned DefIdx,
5637ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines      SmallVectorImpl<RegSubRegPairAndIdx> &InputRegs) const override;
5737ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines
5837ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// Build the equivalent inputs of a EXTRACT_SUBREG for the given \p MI
5937ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// and \p DefIdx.
6037ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// \p [out] InputReg of the equivalent EXTRACT_SUBREG.
6137ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// E.g., EXTRACT_SUBREG vreg1:sub1, sub0, sub1 would produce:
6237ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// - vreg1:sub1, sub0
6337ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  ///
6437ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// \returns true if it is possible to build such an input sequence
6537ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// with the pair \p MI, \p DefIdx. False otherwise.
6637ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  ///
6737ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// \pre MI.isExtractSubregLike().
6837ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  bool getExtractSubregLikeInputs(const MachineInstr &MI, unsigned DefIdx,
6937ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines                                  RegSubRegPairAndIdx &InputReg) const override;
7037ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines
7137ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// Build the equivalent inputs of a INSERT_SUBREG for the given \p MI
7237ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// and \p DefIdx.
7337ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// \p [out] BaseReg and \p [out] InsertedReg contain
7437ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// the equivalent inputs of INSERT_SUBREG.
7537ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// E.g., INSERT_SUBREG vreg0:sub0, vreg1:sub1, sub3 would produce:
7637ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// - BaseReg: vreg0:sub0
7737ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// - InsertedReg: vreg1:sub1, sub3
7837ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  ///
7937ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// \returns true if it is possible to build such an input sequence
8037ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// with the pair \p MI, \p DefIdx. False otherwise.
8137ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  ///
8237ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  /// \pre MI.isInsertSubregLike().
8337ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  bool
8437ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  getInsertSubregLikeInputs(const MachineInstr &MI, unsigned DefIdx,
8537ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines                            RegSubRegPair &BaseReg,
8637ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines                            RegSubRegPairAndIdx &InsertedReg) const override;
8737ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines
88f3ef5332fa3f4d5ec72c178a2b19dac363a19383Pirama Arumuga Nainar  /// Commutes the operands in the given instruction.
89f3ef5332fa3f4d5ec72c178a2b19dac363a19383Pirama Arumuga Nainar  /// The commutable operands are specified by their indices OpIdx1 and OpIdx2.
90f3ef5332fa3f4d5ec72c178a2b19dac363a19383Pirama Arumuga Nainar  ///
91f3ef5332fa3f4d5ec72c178a2b19dac363a19383Pirama Arumuga Nainar  /// Do not call this method for a non-commutable instruction or for
92f3ef5332fa3f4d5ec72c178a2b19dac363a19383Pirama Arumuga Nainar  /// non-commutable pair of operand indices OpIdx1 and OpIdx2.
93f3ef5332fa3f4d5ec72c178a2b19dac363a19383Pirama Arumuga Nainar  /// Even though the instruction is commutable, the method may still
94f3ef5332fa3f4d5ec72c178a2b19dac363a19383Pirama Arumuga Nainar  /// fail to commute the operands, null pointer is returned in such cases.
95de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  MachineInstr *commuteInstructionImpl(MachineInstr &MI, bool NewMI,
96f3ef5332fa3f4d5ec72c178a2b19dac363a19383Pirama Arumuga Nainar                                       unsigned OpIdx1,
97f3ef5332fa3f4d5ec72c178a2b19dac363a19383Pirama Arumuga Nainar                                       unsigned OpIdx2) const override;
98f3ef5332fa3f4d5ec72c178a2b19dac363a19383Pirama Arumuga Nainar
99334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwinpublic:
100c01810eeb7227010f73cb39e3c4fa0197a3c4ef0Jim Grosbach  // Return whether the target has an explicit NOP encoding.
101c01810eeb7227010f73cb39e3c4fa0197a3c4ef0Jim Grosbach  bool hasNOP() const;
102c01810eeb7227010f73cb39e3c4fa0197a3c4ef0Jim Grosbach
103334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin  // Return the non-pre/post incrementing version of 'Opc'. Return 0
104334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin  // if there is not such an opcode.
105334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin  virtual unsigned getUnindexedOpcode(unsigned Opc) const =0;
106334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin
10736b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines  MachineInstr *convertToThreeAddress(MachineFunction::iterator &MFI,
108de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                                      MachineInstr &MI,
10936b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                                      LiveVariables *LV) const override;
110334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin
11157148c166ab232191098492633c924fad9c44ef3Bill Wendling  virtual const ARMBaseRegisterInfo &getRegisterInfo() const = 0;
112f95215f551949d5e5adfbf4753aa833b9009b77aAnton Korobeynikov  const ARMSubtarget &getSubtarget() const { return Subtarget; }
113334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin
11448575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng  ScheduleHazardRecognizer *
115c6a4f5e819217e1e12c458aed8e7b122e23a3a58Stephen Hines  CreateTargetHazardRecognizer(const TargetSubtargetInfo *STI,
11636b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                               const ScheduleDAG *DAG) const override;
1172da8bc8a5f7705ac131184cd247f48500da0d74eAndrew Trick
1182da8bc8a5f7705ac131184cd247f48500da0d74eAndrew Trick  ScheduleHazardRecognizer *
1192da8bc8a5f7705ac131184cd247f48500da0d74eAndrew Trick  CreateTargetPostRAHazardRecognizer(const InstrItineraryData *II,
12036b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                                     const ScheduleDAG *DAG) const override;
12148575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng
122334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin  // Branch analysis.
123de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  bool analyzeBranch(MachineBasicBlock &MBB, MachineBasicBlock *&TBB,
12436b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                     MachineBasicBlock *&FBB,
12536b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                     SmallVectorImpl<MachineOperand> &Cond,
12636b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                     bool AllowModify = false) const override;
12736b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines  unsigned RemoveBranch(MachineBasicBlock &MBB) const override;
12836b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines  unsigned InsertBranch(MachineBasicBlock &MBB, MachineBasicBlock *TBB,
1296948897e478cbd66626159776a8017b3c18579b9Pirama Arumuga Nainar                        MachineBasicBlock *FBB, ArrayRef<MachineOperand> Cond,
130de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                        const DebugLoc &DL) const override;
13136b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines
13236b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines  bool
13336b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines  ReverseBranchCondition(SmallVectorImpl<MachineOperand> &Cond) const override;
134334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin
135334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin  // Predication support.
136de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  bool isPredicated(const MachineInstr &MI) const override;
137334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin
138de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  ARMCC::CondCodes getPredicate(const MachineInstr &MI) const {
139de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar    int PIdx = MI.findFirstPredOperandIdx();
140de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar    return PIdx != -1 ? (ARMCC::CondCodes)MI.getOperand(PIdx).getImm()
141334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin                      : ARMCC::AL;
142334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin  }
143334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin
144de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  bool PredicateInstruction(MachineInstr &MI,
145de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                            ArrayRef<MachineOperand> Pred) const override;
146334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin
1476948897e478cbd66626159776a8017b3c18579b9Pirama Arumuga Nainar  bool SubsumesPredicate(ArrayRef<MachineOperand> Pred1,
1486948897e478cbd66626159776a8017b3c18579b9Pirama Arumuga Nainar                         ArrayRef<MachineOperand> Pred2) const override;
149334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin
150de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  bool DefinesPredicate(MachineInstr &MI,
15136b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                        std::vector<MachineOperand> &Pred) const override;
152334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin
153de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  bool isPredicable(MachineInstr &MI) const override;
154ac0869dc8a7986855c5557cc67d4709600158ef5Evan Cheng
155334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin  /// GetInstSize - Returns the size of the specified MachineInstr.
156334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin  ///
157de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  virtual unsigned GetInstSizeInBytes(const MachineInstr &MI) const;
158334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin
159de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  unsigned isLoadFromStackSlot(const MachineInstr &MI,
16036b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                               int &FrameIndex) const override;
161de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  unsigned isStoreToStackSlot(const MachineInstr &MI,
16236b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                              int &FrameIndex) const override;
163de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  unsigned isLoadFromStackSlotPostFE(const MachineInstr &MI,
16436b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                                     int &FrameIndex) const override;
165de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  unsigned isStoreToStackSlotPostFE(const MachineInstr &MI,
16636b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                                    int &FrameIndex) const override;
167334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin
16837ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  void copyToCPSR(MachineBasicBlock &MBB, MachineBasicBlock::iterator I,
16937ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines                  unsigned SrcReg, bool KillSrc,
17037ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines                  const ARMSubtarget &Subtarget) const;
17137ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines  void copyFromCPSR(MachineBasicBlock &MBB, MachineBasicBlock::iterator I,
17237ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines                    unsigned DestReg, bool KillSrc,
17337ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines                    const ARMSubtarget &Subtarget) const;
17437ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines
17536b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines  void copyPhysReg(MachineBasicBlock &MBB, MachineBasicBlock::iterator I,
176de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                   const DebugLoc &DL, unsigned DestReg, unsigned SrcReg,
17736b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                   bool KillSrc) const override;
1785732ca084aaa0cd26149e50dd4b487efff37fe41Evan Cheng
17936b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines  void storeRegToStackSlot(MachineBasicBlock &MBB,
18036b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                           MachineBasicBlock::iterator MBBI,
18136b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                           unsigned SrcReg, bool isKill, int FrameIndex,
18236b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                           const TargetRegisterClass *RC,
18336b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                           const TargetRegisterInfo *TRI) const override;
184334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin
18536b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines  void loadRegFromStackSlot(MachineBasicBlock &MBB,
18636b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                            MachineBasicBlock::iterator MBBI,
18736b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                            unsigned DestReg, int FrameIndex,
18836b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                            const TargetRegisterClass *RC,
18936b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                            const TargetRegisterInfo *TRI) const override;
190334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin
191de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  bool expandPostRAPseudo(MachineInstr &MI) const override;
192142bd1a54e93f3f66d420717ecba53539a556035Jakob Stoklund Olesen
19336b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines  void reMaterialize(MachineBasicBlock &MBB, MachineBasicBlock::iterator MI,
19436b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                     unsigned DestReg, unsigned SubIdx,
195de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                     const MachineInstr &Orig,
19636b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                     const TargetRegisterInfo &TRI) const override;
197fdc834046efd427d474e3b899ec69354c05071e0Evan Cheng
198de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  MachineInstr *duplicate(MachineInstr &Orig,
19936b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                          MachineFunction &MF) const override;
20030ac0467ced4627a9b84d8a1d3ca5e8706ddad63Jakob Stoklund Olesen
2014cc1407b84dc6dbbc0d62b1d1b8db7c0ddec86ccTim Northover  const MachineInstrBuilder &AddDReg(MachineInstrBuilder &MIB, unsigned Reg,
2024cc1407b84dc6dbbc0d62b1d1b8db7c0ddec86ccTim Northover                                     unsigned SubIdx, unsigned State,
2034cc1407b84dc6dbbc0d62b1d1b8db7c0ddec86ccTim Northover                                     const TargetRegisterInfo *TRI) const;
2044cc1407b84dc6dbbc0d62b1d1b8db7c0ddec86ccTim Northover
205de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  bool produceSameValue(const MachineInstr &MI0, const MachineInstr &MI1,
20636b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                        const MachineRegisterInfo *MRI) const override;
20786050dc8cc0aaea8c9dfeb89de02cafbd7f48d92Evan Cheng
2084b722108e2cf8e77157e0879a23789cd44829933Bill Wendling  /// areLoadsFromSameBasePtr - This is used by the pre-regalloc scheduler to
2094b722108e2cf8e77157e0879a23789cd44829933Bill Wendling  /// determine if two loads are loading from the same base address. It should
2104b722108e2cf8e77157e0879a23789cd44829933Bill Wendling  /// only return true if the base pointers are the same and the only
2114b722108e2cf8e77157e0879a23789cd44829933Bill Wendling  /// differences between the two addresses is the offset. It also returns the
2124b722108e2cf8e77157e0879a23789cd44829933Bill Wendling  /// offsets by reference.
21336b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines  bool areLoadsFromSameBasePtr(SDNode *Load1, SDNode *Load2, int64_t &Offset1,
21436b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                               int64_t &Offset2) const override;
2154b722108e2cf8e77157e0879a23789cd44829933Bill Wendling
2164b722108e2cf8e77157e0879a23789cd44829933Bill Wendling  /// shouldScheduleLoadsNear - This is a used by the pre-regalloc scheduler to
217f921c0fe3418f96bd1e37beb582a368d3ac24295Jim Grosbach  /// determine (in conjunction with areLoadsFromSameBasePtr) if two loads
218f921c0fe3418f96bd1e37beb582a368d3ac24295Jim Grosbach  /// should be scheduled togther. On some targets if two loads are loading from
2194b722108e2cf8e77157e0879a23789cd44829933Bill Wendling  /// addresses in the same cache line, it's better if they are scheduled
2204b722108e2cf8e77157e0879a23789cd44829933Bill Wendling  /// together. This function takes two integers that represent the load offsets
2214b722108e2cf8e77157e0879a23789cd44829933Bill Wendling  /// from the common base address. It returns true if it decides it's desirable
2224b722108e2cf8e77157e0879a23789cd44829933Bill Wendling  /// to schedule the two loads together. "NumLoads" is the number of loads that
2234b722108e2cf8e77157e0879a23789cd44829933Bill Wendling  /// have already been scheduled after Load1.
22436b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines  bool shouldScheduleLoadsNear(SDNode *Load1, SDNode *Load2,
22536b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                               int64_t Offset1, int64_t Offset2,
22636b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                               unsigned NumLoads) const override;
22736b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines
228de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  bool isSchedulingBoundary(const MachineInstr &MI,
22936b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                            const MachineBasicBlock *MBB,
23036b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                            const MachineFunction &MF) const override;
23136b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines
23236b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines  bool isProfitableToIfCvt(MachineBasicBlock &MBB,
23336b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                           unsigned NumCycles, unsigned ExtraPredCycles,
234f3ef5332fa3f4d5ec72c178a2b19dac363a19383Pirama Arumuga Nainar                           BranchProbability Probability) const override;
23536b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines
23636b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines  bool isProfitableToIfCvt(MachineBasicBlock &TMBB, unsigned NumT,
23736b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                           unsigned ExtraT, MachineBasicBlock &FMBB,
23836b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                           unsigned NumF, unsigned ExtraF,
239f3ef5332fa3f4d5ec72c178a2b19dac363a19383Pirama Arumuga Nainar                           BranchProbability Probability) const override;
24036b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines
24136b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines  bool isProfitableToDupForIfCvt(MachineBasicBlock &MBB, unsigned NumCycles,
242f3ef5332fa3f4d5ec72c178a2b19dac363a19383Pirama Arumuga Nainar                                 BranchProbability Probability) const override {
2435876db7a66fcc4ec4444a9f3e387c1cdc8baf9e5Cameron Zwarich    return NumCycles == 1;
24413151432edace19ee867a93b5c14573df4f75d24Evan Cheng  }
245e4ddbdfd3cf031034020671d03626f0373fbd5caBill Wendling
24636b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines  bool isProfitableToUnpredicate(MachineBasicBlock &TMBB,
24736b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                                 MachineBasicBlock &FMBB) const override;
248eb1641d54a7eda7717304bc4d55d059208d8ebedBob Wilson
249de7266c611b37ec050efb53b73166081a98cea13Manman Ren  /// analyzeCompare - For a comparison instruction, return the source registers
250de7266c611b37ec050efb53b73166081a98cea13Manman Ren  /// in SrcReg and SrcReg2 if having two register operands, and the value it
251de7266c611b37ec050efb53b73166081a98cea13Manman Ren  /// compares against in CmpValue. Return true if the comparison instruction
252de7266c611b37ec050efb53b73166081a98cea13Manman Ren  /// can be analyzed.
253de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  bool analyzeCompare(const MachineInstr &MI, unsigned &SrcReg,
25436b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                      unsigned &SrcReg2, int &CmpMask,
25536b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                      int &CmpValue) const override;
256de7266c611b37ec050efb53b73166081a98cea13Manman Ren
257de7266c611b37ec050efb53b73166081a98cea13Manman Ren  /// optimizeCompareInstr - Convert the instruction to set the zero flag so
258de7266c611b37ec050efb53b73166081a98cea13Manman Ren  /// that we can remove a "comparison with zero"; Remove a redundant CMP
259de7266c611b37ec050efb53b73166081a98cea13Manman Ren  /// instruction if the flags can be updated in the same way by an earlier
260de7266c611b37ec050efb53b73166081a98cea13Manman Ren  /// instruction such as SUB.
261de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  bool optimizeCompareInstr(MachineInstr &CmpInstr, unsigned SrcReg,
26236b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                            unsigned SrcReg2, int CmpMask, int CmpValue,
26336b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                            const MachineRegisterInfo *MRI) const override;
2645f54ce347368105260be2cec497b6a4199dc5789Evan Cheng
265de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  bool analyzeSelect(const MachineInstr &MI,
266de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                     SmallVectorImpl<MachineOperand> &Cond, unsigned &TrueOp,
267de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                     unsigned &FalseOp, bool &Optimizable) const override;
268053b5b0b3c34d4763511b6dcd8e0150f8e9dd083Jakob Stoklund Olesen
269de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  MachineInstr *optimizeSelect(MachineInstr &MI,
270ebe69fe11e48d322045d5949c83283927a0d790bStephen Hines                               SmallPtrSetImpl<MachineInstr *> &SeenMIs,
271ebe69fe11e48d322045d5949c83283927a0d790bStephen Hines                               bool) const override;
272053b5b0b3c34d4763511b6dcd8e0150f8e9dd083Jakob Stoklund Olesen
273c4af4638dfdab0dc3b6257276cfad2ee45053060Evan Cheng  /// FoldImmediate - 'Reg' is known to be defined by a move immediate
274c4af4638dfdab0dc3b6257276cfad2ee45053060Evan Cheng  /// instruction, try to fold the immediate into the use instruction.
275de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  bool FoldImmediate(MachineInstr &UseMI, MachineInstr &DefMI, unsigned Reg,
276de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                     MachineRegisterInfo *MRI) const override;
277c4af4638dfdab0dc3b6257276cfad2ee45053060Evan Cheng
27836b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines  unsigned getNumMicroOps(const InstrItineraryData *ItinData,
279de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                          const MachineInstr &MI) const override;
280a0792de66c8364d47b0a688c7f408efb7b10f31bEvan Cheng
281a0792de66c8364d47b0a688c7f408efb7b10f31bEvan Cheng  int getOperandLatency(const InstrItineraryData *ItinData,
282de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                        const MachineInstr &DefMI, unsigned DefIdx,
283de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                        const MachineInstr &UseMI,
28436b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                        unsigned UseIdx) const override;
285a0792de66c8364d47b0a688c7f408efb7b10f31bEvan Cheng  int getOperandLatency(const InstrItineraryData *ItinData,
286a0792de66c8364d47b0a688c7f408efb7b10f31bEvan Cheng                        SDNode *DefNode, unsigned DefIdx,
28736b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                        SDNode *UseNode, unsigned UseIdx) const override;
28813fd601e0f1c6d8558c4c2b027dacd148f19e6afJakob Stoklund Olesen
28913fd601e0f1c6d8558c4c2b027dacd148f19e6afJakob Stoklund Olesen  /// VFP/NEON execution domains.
29013fd601e0f1c6d8558c4c2b027dacd148f19e6afJakob Stoklund Olesen  std::pair<uint16_t, uint16_t>
291de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  getExecutionDomain(const MachineInstr &MI) const override;
292de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  void setExecutionDomain(MachineInstr &MI, unsigned Domain) const override;
29313fd601e0f1c6d8558c4c2b027dacd148f19e6afJakob Stoklund Olesen
294de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  unsigned
295de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  getPartialRegUpdateClearance(const MachineInstr &, unsigned,
296de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                               const TargetRegisterInfo *) const override;
297de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  void breakPartialRegDependency(MachineInstr &, unsigned,
29836b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                                 const TargetRegisterInfo *TRI) const override;
299c6a4f5e819217e1e12c458aed8e7b122e23a3a58Stephen Hines
3009eed53379f19f836769a0c4a14042eeb1b587769Andrew Trick  /// Get the number of addresses by LDM or VLDM or zero for unknown.
301de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  unsigned getNumLDMAddresses(const MachineInstr &MI) const;
3029eed53379f19f836769a0c4a14042eeb1b587769Andrew Trick
303a0792de66c8364d47b0a688c7f408efb7b10f31bEvan Chengprivate:
304de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  unsigned getInstBundleLength(const MachineInstr &MI) const;
305ddfd1377d2e4154d44dc3ad217735adc15af2e3fEvan Cheng
306344d9db97062736cd66da6c07baa9108b6cfa419Evan Cheng  int getVLDMDefCycle(const InstrItineraryData *ItinData,
307e837dead3c8dc3445ef6a0e2322179c57e264a13Evan Cheng                      const MCInstrDesc &DefMCID,
308344d9db97062736cd66da6c07baa9108b6cfa419Evan Cheng                      unsigned DefClass,
309344d9db97062736cd66da6c07baa9108b6cfa419Evan Cheng                      unsigned DefIdx, unsigned DefAlign) const;
310344d9db97062736cd66da6c07baa9108b6cfa419Evan Cheng  int getLDMDefCycle(const InstrItineraryData *ItinData,
311e837dead3c8dc3445ef6a0e2322179c57e264a13Evan Cheng                     const MCInstrDesc &DefMCID,
312344d9db97062736cd66da6c07baa9108b6cfa419Evan Cheng                     unsigned DefClass,
313344d9db97062736cd66da6c07baa9108b6cfa419Evan Cheng                     unsigned DefIdx, unsigned DefAlign) const;
314344d9db97062736cd66da6c07baa9108b6cfa419Evan Cheng  int getVSTMUseCycle(const InstrItineraryData *ItinData,
315e837dead3c8dc3445ef6a0e2322179c57e264a13Evan Cheng                      const MCInstrDesc &UseMCID,
316344d9db97062736cd66da6c07baa9108b6cfa419Evan Cheng                      unsigned UseClass,
317344d9db97062736cd66da6c07baa9108b6cfa419Evan Cheng                      unsigned UseIdx, unsigned UseAlign) const;
318344d9db97062736cd66da6c07baa9108b6cfa419Evan Cheng  int getSTMUseCycle(const InstrItineraryData *ItinData,
319e837dead3c8dc3445ef6a0e2322179c57e264a13Evan Cheng                     const MCInstrDesc &UseMCID,
320344d9db97062736cd66da6c07baa9108b6cfa419Evan Cheng                     unsigned UseClass,
321344d9db97062736cd66da6c07baa9108b6cfa419Evan Cheng                     unsigned UseIdx, unsigned UseAlign) const;
322a0792de66c8364d47b0a688c7f408efb7b10f31bEvan Cheng  int getOperandLatency(const InstrItineraryData *ItinData,
323e837dead3c8dc3445ef6a0e2322179c57e264a13Evan Cheng                        const MCInstrDesc &DefMCID,
324a0792de66c8364d47b0a688c7f408efb7b10f31bEvan Cheng                        unsigned DefIdx, unsigned DefAlign,
325e837dead3c8dc3445ef6a0e2322179c57e264a13Evan Cheng                        const MCInstrDesc &UseMCID,
326a0792de66c8364d47b0a688c7f408efb7b10f31bEvan Cheng                        unsigned UseIdx, unsigned UseAlign) const;
3272312842de0c641107dd04d7e056d02491cc781caEvan Cheng
328de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  int getOperandLatencyImpl(const InstrItineraryData *ItinData,
329de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                            const MachineInstr &DefMI, unsigned DefIdx,
330de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                            const MCInstrDesc &DefMCID, unsigned DefAdj,
331de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                            const MachineOperand &DefMO, unsigned Reg,
332de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                            const MachineInstr &UseMI, unsigned UseIdx,
333de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                            const MCInstrDesc &UseMCID, unsigned UseAdj) const;
334de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar
335de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  unsigned getPredicationCost(const MachineInstr &MI) const override;
336d42730dc712026cbfb1322a979e0ac72cd31a19eArnold Schwaighofer
337b7e0289fb320c8440ba5eed121a8b932dbd806a2Andrew Trick  unsigned getInstrLatency(const InstrItineraryData *ItinData,
338de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                           const MachineInstr &MI,
339dce4a407a24b04eebc6a376f8e62b41aaa7b071fStephen Hines                           unsigned *PredCost = nullptr) const override;
3408239daf7c83a65a189c352cce3191cdc3bbfe151Evan Cheng
3418239daf7c83a65a189c352cce3191cdc3bbfe151Evan Cheng  int getInstrLatency(const InstrItineraryData *ItinData,
34236b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                      SDNode *Node) const override;
3438239daf7c83a65a189c352cce3191cdc3bbfe151Evan Cheng
3446948897e478cbd66626159776a8017b3c18579b9Pirama Arumuga Nainar  bool hasHighOperandLatency(const TargetSchedModel &SchedModel,
3452312842de0c641107dd04d7e056d02491cc781caEvan Cheng                             const MachineRegisterInfo *MRI,
346de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                             const MachineInstr &DefMI, unsigned DefIdx,
347de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                             const MachineInstr &UseMI,
34836b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                             unsigned UseIdx) const override;
3496948897e478cbd66626159776a8017b3c18579b9Pirama Arumuga Nainar  bool hasLowDefLatency(const TargetSchedModel &SchedModel,
350de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                        const MachineInstr &DefMI,
35136b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                        unsigned DefIdx) const override;
35248575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng
3533be654f8082dcbdff011a6716a7c90486e28fc9eAndrew Trick  /// verifyInstruction - Perform target specific instruction verification.
354de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  bool verifyInstruction(const MachineInstr &MI,
35536b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                         StringRef &ErrInfo) const override;
3563be654f8082dcbdff011a6716a7c90486e28fc9eAndrew Trick
357de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar  virtual void expandLoadStackGuard(MachineBasicBlock::iterator MI) const = 0;
35837ed9c199ca639565f6ce88105f9e39e898d82d0Stephen Hines
359f3ef5332fa3f4d5ec72c178a2b19dac363a19383Pirama Arumuga Nainar  void expandMEMCPY(MachineBasicBlock::iterator) const;
360f3ef5332fa3f4d5ec72c178a2b19dac363a19383Pirama Arumuga Nainar
36148575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Chengprivate:
36248575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng  /// Modeling special VFP / NEON fp MLA / MLS hazards.
36348575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng
36448575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng  /// MLxEntryMap - Map fp MLA / MLS to the corresponding entry in the internal
36548575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng  /// MLx table.
36648575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng  DenseMap<unsigned, unsigned> MLxEntryMap;
36748575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng
36848575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng  /// MLxHazardOpcodes - Set of add / sub and multiply opcodes that would cause
36948575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng  /// stalls when scheduled together with fp MLA / MLS opcodes.
37048575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng  SmallSet<unsigned, 16> MLxHazardOpcodes;
37148575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng
37248575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Chengpublic:
37348575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng  /// isFpMLxInstruction - Return true if the specified opcode is a fp MLA / MLS
37448575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng  /// instruction.
37548575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng  bool isFpMLxInstruction(unsigned Opcode) const {
37648575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng    return MLxEntryMap.count(Opcode);
37748575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng  }
37848575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng
37948575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng  /// isFpMLxInstruction - This version also returns the multiply opcode and the
38048575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng  /// addition / subtraction opcode to expand to. Return true for 'HasLane' for
38148575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng  /// the MLX instructions with an extra lane operand.
38248575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng  bool isFpMLxInstruction(unsigned Opcode, unsigned &MulOpc,
38348575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng                          unsigned &AddSubOpc, bool &NegAcc,
38448575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng                          bool &HasLane) const;
38548575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng
38648575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng  /// canCauseFpMLxStall - Return true if an instruction of the specified opcode
38748575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng  /// will cause stalls when scheduled after (within 4-cycle window) a fp
38848575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng  /// MLA / MLS instruction.
38948575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng  bool canCauseFpMLxStall(unsigned Opcode) const {
39048575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng    return MLxHazardOpcodes.count(Opcode);
39148575f6ea7d5cd21ab29ca370f58fcf9ca31400bEvan Cheng  }
39208da4865576056f997a9c8013240d716018f7edfArnold Schwaighofer
39308da4865576056f997a9c8013240d716018f7edfArnold Schwaighofer  /// Returns true if the instruction has a shift by immediate that can be
39408da4865576056f997a9c8013240d716018f7edfArnold Schwaighofer  /// executed in one cycle less.
39508da4865576056f997a9c8013240d716018f7edfArnold Schwaighofer  bool isSwiftFastImmShift(const MachineInstr *MI) const;
3966495f63945e8dbde81f03a1dc2ab421993b9a495Evan Cheng};
3975ca53a7ad821613d324e4189ddbb0d468a326146Evan Cheng
3986495f63945e8dbde81f03a1dc2ab421993b9a495Evan Chengstatic inline
3996495f63945e8dbde81f03a1dc2ab421993b9a495Evan Chengconst MachineInstrBuilder &AddDefaultPred(const MachineInstrBuilder &MIB) {
4006495f63945e8dbde81f03a1dc2ab421993b9a495Evan Cheng  return MIB.addImm((int64_t)ARMCC::AL).addReg(0);
4016495f63945e8dbde81f03a1dc2ab421993b9a495Evan Cheng}
4025ca53a7ad821613d324e4189ddbb0d468a326146Evan Cheng
4036495f63945e8dbde81f03a1dc2ab421993b9a495Evan Chengstatic inline
4046495f63945e8dbde81f03a1dc2ab421993b9a495Evan Chengconst MachineInstrBuilder &AddDefaultCC(const MachineInstrBuilder &MIB) {
4056495f63945e8dbde81f03a1dc2ab421993b9a495Evan Cheng  return MIB.addReg(0);
4066495f63945e8dbde81f03a1dc2ab421993b9a495Evan Cheng}
40783e0e36be8390fee1235783731f6c64aa604b7eeEvan Cheng
4086495f63945e8dbde81f03a1dc2ab421993b9a495Evan Chengstatic inline
409e8af1f9afe5e70e1d4ec4d00a6870428dba88692Evan Chengconst MachineInstrBuilder &AddDefaultT1CC(const MachineInstrBuilder &MIB,
410e8af1f9afe5e70e1d4ec4d00a6870428dba88692Evan Cheng                                          bool isDead = false) {
411e8af1f9afe5e70e1d4ec4d00a6870428dba88692Evan Cheng  return MIB.addReg(ARM::CPSR, getDefRegState(true) | getDeadRegState(isDead));
4126495f63945e8dbde81f03a1dc2ab421993b9a495Evan Cheng}
4136495f63945e8dbde81f03a1dc2ab421993b9a495Evan Cheng
4146495f63945e8dbde81f03a1dc2ab421993b9a495Evan Chengstatic inline
415bc9b754091ea281e769e487f396b40f6675b9edbEvan Chengconst MachineInstrBuilder &AddNoT1CC(const MachineInstrBuilder &MIB) {
416bc9b754091ea281e769e487f396b40f6675b9edbEvan Cheng  return MIB.addReg(0);
417bc9b754091ea281e769e487f396b40f6675b9edbEvan Cheng}
418bc9b754091ea281e769e487f396b40f6675b9edbEvan Cheng
419bc9b754091ea281e769e487f396b40f6675b9edbEvan Chengstatic inline
4206495f63945e8dbde81f03a1dc2ab421993b9a495Evan Chengbool isUncondBranchOpcode(int Opc) {
4216495f63945e8dbde81f03a1dc2ab421993b9a495Evan Cheng  return Opc == ARM::B || Opc == ARM::tB || Opc == ARM::t2B;
422334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin}
423334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin
4246495f63945e8dbde81f03a1dc2ab421993b9a495Evan Chengstatic inline
4256495f63945e8dbde81f03a1dc2ab421993b9a495Evan Chengbool isCondBranchOpcode(int Opc) {
4266495f63945e8dbde81f03a1dc2ab421993b9a495Evan Cheng  return Opc == ARM::Bcc || Opc == ARM::tBcc || Opc == ARM::t2Bcc;
4276495f63945e8dbde81f03a1dc2ab421993b9a495Evan Cheng}
4286495f63945e8dbde81f03a1dc2ab421993b9a495Evan Cheng
4296495f63945e8dbde81f03a1dc2ab421993b9a495Evan Chengstatic inline
4306495f63945e8dbde81f03a1dc2ab421993b9a495Evan Chengbool isJumpTableBranchOpcode(int Opc) {
4316495f63945e8dbde81f03a1dc2ab421993b9a495Evan Cheng  return Opc == ARM::BR_JTr || Opc == ARM::BR_JTm || Opc == ARM::BR_JTadd ||
4326495f63945e8dbde81f03a1dc2ab421993b9a495Evan Cheng    Opc == ARM::tBR_JTr || Opc == ARM::t2BR_JT;
4336495f63945e8dbde81f03a1dc2ab421993b9a495Evan Cheng}
4346495f63945e8dbde81f03a1dc2ab421993b9a495Evan Cheng
4358d4de5abfa1bcd974554ea14904ebf7af289e84dBob Wilsonstatic inline
4368d4de5abfa1bcd974554ea14904ebf7af289e84dBob Wilsonbool isIndirectBranchOpcode(int Opc) {
4376e46d84eea97792a66c0bb64f26aad3976a23365Bill Wendling  return Opc == ARM::BX || Opc == ARM::MOVPCRX || Opc == ARM::tBRIND;
4388d4de5abfa1bcd974554ea14904ebf7af289e84dBob Wilson}
4398d4de5abfa1bcd974554ea14904ebf7af289e84dBob Wilson
440323ac85d6ad7ba5d9593d8e151d879bd91d82e08Tim Northoverstatic inline bool isPopOpcode(int Opc) {
441323ac85d6ad7ba5d9593d8e151d879bd91d82e08Tim Northover  return Opc == ARM::tPOP_RET || Opc == ARM::LDMIA_RET ||
442323ac85d6ad7ba5d9593d8e151d879bd91d82e08Tim Northover         Opc == ARM::t2LDMIA_RET || Opc == ARM::tPOP || Opc == ARM::LDMIA_UPD ||
443323ac85d6ad7ba5d9593d8e151d879bd91d82e08Tim Northover         Opc == ARM::t2LDMIA_UPD || Opc == ARM::VLDMDIA_UPD;
444323ac85d6ad7ba5d9593d8e151d879bd91d82e08Tim Northover}
445323ac85d6ad7ba5d9593d8e151d879bd91d82e08Tim Northover
446323ac85d6ad7ba5d9593d8e151d879bd91d82e08Tim Northoverstatic inline bool isPushOpcode(int Opc) {
447323ac85d6ad7ba5d9593d8e151d879bd91d82e08Tim Northover  return Opc == ARM::tPUSH || Opc == ARM::t2STMDB_UPD ||
448323ac85d6ad7ba5d9593d8e151d879bd91d82e08Tim Northover         Opc == ARM::STMDB_UPD || Opc == ARM::VSTMDDB_UPD;
449323ac85d6ad7ba5d9593d8e151d879bd91d82e08Tim Northover}
450323ac85d6ad7ba5d9593d8e151d879bd91d82e08Tim Northover
4518fb903604e83dfd63659c919042bf2bfed3c940fEvan Cheng/// getInstrPredicate - If instruction is predicated, returns its predicate
4528fb903604e83dfd63659c919042bf2bfed3c940fEvan Cheng/// condition, otherwise returns AL. It also returns the condition code
4538fb903604e83dfd63659c919042bf2bfed3c940fEvan Cheng/// register by reference.
454de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga NainarARMCC::CondCodes getInstrPredicate(const MachineInstr &MI, unsigned &PredReg);
4558fb903604e83dfd63659c919042bf2bfed3c940fEvan Cheng
4566948897e478cbd66626159776a8017b3c18579b9Pirama Arumuga Nainarunsigned getMatchingCondBranchOpcode(unsigned Opc);
4576495f63945e8dbde81f03a1dc2ab421993b9a495Evan Cheng
4582860b7ea3a1d60213ee7228bd274bc4f8b170772Jakob Stoklund Olesen/// Determine if MI can be folded into an ARM MOVCC instruction, and return the
4592860b7ea3a1d60213ee7228bd274bc4f8b170772Jakob Stoklund Olesen/// opcode of the SSA instruction representing the conditional MI.
4602860b7ea3a1d60213ee7228bd274bc4f8b170772Jakob Stoklund Olesenunsigned canFoldARMInstrIntoMOVCC(unsigned Reg,
4612860b7ea3a1d60213ee7228bd274bc4f8b170772Jakob Stoklund Olesen                                  MachineInstr *&MI,
4622860b7ea3a1d60213ee7228bd274bc4f8b170772Jakob Stoklund Olesen                                  const MachineRegisterInfo &MRI);
4633be654f8082dcbdff011a6716a7c90486e28fc9eAndrew Trick
4643be654f8082dcbdff011a6716a7c90486e28fc9eAndrew Trick/// Map pseudo instructions that imply an 'S' bit onto real opcodes. Whether
4653be654f8082dcbdff011a6716a7c90486e28fc9eAndrew Trick/// the instruction is encoded with an 'S' bit is determined by the optional
4663be654f8082dcbdff011a6716a7c90486e28fc9eAndrew Trick/// CPSR def operand.
4673be654f8082dcbdff011a6716a7c90486e28fc9eAndrew Trickunsigned convertAddSubFlagsOpcode(unsigned OldOpc);
4683be654f8082dcbdff011a6716a7c90486e28fc9eAndrew Trick
4696495f63945e8dbde81f03a1dc2ab421993b9a495Evan Cheng/// emitARMRegPlusImmediate / emitT2RegPlusImmediate - Emits a series of
4706495f63945e8dbde81f03a1dc2ab421993b9a495Evan Cheng/// instructions to materializea destreg = basereg + immediate in ARM / Thumb2
4716495f63945e8dbde81f03a1dc2ab421993b9a495Evan Cheng/// code.
4726495f63945e8dbde81f03a1dc2ab421993b9a495Evan Chengvoid emitARMRegPlusImmediate(MachineBasicBlock &MBB,
473de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                             MachineBasicBlock::iterator &MBBI,
474de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                             const DebugLoc &dl, unsigned DestReg,
475de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                             unsigned BaseReg, int NumBytes,
4766495f63945e8dbde81f03a1dc2ab421993b9a495Evan Cheng                             ARMCC::CondCodes Pred, unsigned PredReg,
47757caad7a33ff145b71545f10dcfbbf2fd0f595d3Anton Korobeynikov                             const ARMBaseInstrInfo &TII, unsigned MIFlags = 0);
4786495f63945e8dbde81f03a1dc2ab421993b9a495Evan Cheng
4796495f63945e8dbde81f03a1dc2ab421993b9a495Evan Chengvoid emitT2RegPlusImmediate(MachineBasicBlock &MBB,
480de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                            MachineBasicBlock::iterator &MBBI,
481de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                            const DebugLoc &dl, unsigned DestReg,
482de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                            unsigned BaseReg, int NumBytes,
4836495f63945e8dbde81f03a1dc2ab421993b9a495Evan Cheng                            ARMCC::CondCodes Pred, unsigned PredReg,
48457caad7a33ff145b71545f10dcfbbf2fd0f595d3Anton Korobeynikov                            const ARMBaseInstrInfo &TII, unsigned MIFlags = 0);
485e4ad387a5a88dae20f0f7578e55170bbc8eee2a9Jim Grosbachvoid emitThumbRegPlusImmediate(MachineBasicBlock &MBB,
486de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                               MachineBasicBlock::iterator &MBBI,
487de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                               const DebugLoc &dl, unsigned DestReg,
488de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                               unsigned BaseReg, int NumBytes,
489de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                               const TargetInstrInfo &TII,
490de2d8694e25a814696358e95141f4b1aa4d8847ePirama Arumuga Nainar                               const ARMBaseRegisterInfo &MRI,
49157caad7a33ff145b71545f10dcfbbf2fd0f595d3Anton Korobeynikov                               unsigned MIFlags = 0);
4926495f63945e8dbde81f03a1dc2ab421993b9a495Evan Cheng
493323ac85d6ad7ba5d9593d8e151d879bd91d82e08Tim Northover/// Tries to add registers to the reglist of a given base-updating
494323ac85d6ad7ba5d9593d8e151d879bd91d82e08Tim Northover/// push/pop instruction to adjust the stack by an additional
495323ac85d6ad7ba5d9593d8e151d879bd91d82e08Tim Northover/// NumBytes. This can save a few bytes per function in code-size, but
496323ac85d6ad7ba5d9593d8e151d879bd91d82e08Tim Northover/// obviously generates more memory traffic. As such, it only takes
497323ac85d6ad7ba5d9593d8e151d879bd91d82e08Tim Northover/// effect in functions being optimised for size.
49836b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hinesbool tryFoldSPUpdateIntoPushPop(const ARMSubtarget &Subtarget,
49936b56886974eae4f9c5ebc96befd3e7bfe5de338Stephen Hines                                MachineFunction &MF, MachineInstr *MI,
500323ac85d6ad7ba5d9593d8e151d879bd91d82e08Tim Northover                                unsigned NumBytes);
5016495f63945e8dbde81f03a1dc2ab421993b9a495Evan Cheng
502764ab52dd80310a205c9888bf166d09dab858f90Jim Grosbach/// rewriteARMFrameIndex / rewriteT2FrameIndex -
503cdbb3f5d3311e0f46d22bc8daa211b2fab3541cbEvan Cheng/// Rewrite MI to access 'Offset' bytes from the FP. Return false if the
504cdbb3f5d3311e0f46d22bc8daa211b2fab3541cbEvan Cheng/// offset could not be handled directly in MI, and return the left-over
505cdbb3f5d3311e0f46d22bc8daa211b2fab3541cbEvan Cheng/// portion by reference.
506cdbb3f5d3311e0f46d22bc8daa211b2fab3541cbEvan Chengbool rewriteARMFrameIndex(MachineInstr &MI, unsigned FrameRegIdx,
507cdbb3f5d3311e0f46d22bc8daa211b2fab3541cbEvan Cheng                          unsigned FrameReg, int &Offset,
508cdbb3f5d3311e0f46d22bc8daa211b2fab3541cbEvan Cheng                          const ARMBaseInstrInfo &TII);
509cdbb3f5d3311e0f46d22bc8daa211b2fab3541cbEvan Cheng
510cdbb3f5d3311e0f46d22bc8daa211b2fab3541cbEvan Chengbool rewriteT2FrameIndex(MachineInstr &MI, unsigned FrameRegIdx,
511cdbb3f5d3311e0f46d22bc8daa211b2fab3541cbEvan Cheng                         unsigned FrameReg, int &Offset,
512cdbb3f5d3311e0f46d22bc8daa211b2fab3541cbEvan Cheng                         const ARMBaseInstrInfo &TII);
5136495f63945e8dbde81f03a1dc2ab421993b9a495Evan Cheng
5146495f63945e8dbde81f03a1dc2ab421993b9a495Evan Cheng} // End llvm namespace
5156495f63945e8dbde81f03a1dc2ab421993b9a495Evan Cheng
516334c26473bba3ad8b88341bb0d25d0ac2008bb8dDavid Goodwin#endif
517