HexagonVLIWPacketizer.cpp revision 249423
1239310Sdim//===----- HexagonPacketizer.cpp - vliw packetizer ---------------------===//
2239310Sdim//
3239310Sdim//                     The LLVM Compiler Infrastructure
4239310Sdim//
5239310Sdim// This file is distributed under the University of Illinois Open Source
6239310Sdim// License. See LICENSE.TXT for details.
7239310Sdim//
8239310Sdim//===----------------------------------------------------------------------===//
9239310Sdim//
10239310Sdim// This implements a simple VLIW packetizer using DFA. The packetizer works on
11239310Sdim// machine basic blocks. For each instruction I in BB, the packetizer consults
12239310Sdim// the DFA to see if machine resources are available to execute I. If so, the
13239310Sdim// packetizer checks if I depends on any instruction J in the current packet.
14239310Sdim// If no dependency is found, I is added to current packet and machine resource
15239310Sdim// is marked as taken. If any dependency is found, a target API call is made to
16239310Sdim// prune the dependence.
17239310Sdim//
18239310Sdim//===----------------------------------------------------------------------===//
19239310Sdim#define DEBUG_TYPE "packets"
20239310Sdim#include "llvm/CodeGen/DFAPacketizer.h"
21239310Sdim#include "llvm/CodeGen/Passes.h"
22239310Sdim#include "llvm/CodeGen/MachineDominators.h"
23239310Sdim#include "llvm/CodeGen/MachineFunctionPass.h"
24239310Sdim#include "llvm/CodeGen/MachineLoopInfo.h"
25239310Sdim#include "llvm/CodeGen/ScheduleDAG.h"
26239310Sdim#include "llvm/CodeGen/ScheduleDAGInstrs.h"
27239310Sdim#include "llvm/CodeGen/LatencyPriorityQueue.h"
28239310Sdim#include "llvm/CodeGen/SchedulerRegistry.h"
29239310Sdim#include "llvm/CodeGen/MachineFrameInfo.h"
30239310Sdim#include "llvm/CodeGen/MachineInstrBuilder.h"
31239310Sdim#include "llvm/CodeGen/MachineRegisterInfo.h"
32239310Sdim#include "llvm/CodeGen/MachineFunctionAnalysis.h"
33239310Sdim#include "llvm/CodeGen/ScheduleHazardRecognizer.h"
34239310Sdim#include "llvm/Target/TargetMachine.h"
35239310Sdim#include "llvm/Target/TargetInstrInfo.h"
36239310Sdim#include "llvm/Target/TargetRegisterInfo.h"
37239310Sdim#include "llvm/ADT/DenseMap.h"
38239310Sdim#include "llvm/ADT/Statistic.h"
39239310Sdim#include "llvm/Support/MathExtras.h"
40239310Sdim#include "llvm/MC/MCInstrItineraries.h"
41239310Sdim#include "llvm/Support/Compiler.h"
42239310Sdim#include "llvm/Support/CommandLine.h"
43239310Sdim#include "llvm/Support/Debug.h"
44239310Sdim#include "Hexagon.h"
45239310Sdim#include "HexagonTargetMachine.h"
46239310Sdim#include "HexagonRegisterInfo.h"
47239310Sdim#include "HexagonSubtarget.h"
48239310Sdim#include "HexagonMachineFunctionInfo.h"
49239310Sdim
50239310Sdim#include <map>
51239310Sdim
52239310Sdimusing namespace llvm;
53239310Sdim
54239310Sdimnamespace {
55239310Sdim  class HexagonPacketizer : public MachineFunctionPass {
56239310Sdim
57239310Sdim  public:
58239310Sdim    static char ID;
59239310Sdim    HexagonPacketizer() : MachineFunctionPass(ID) {}
60239310Sdim
61239310Sdim    void getAnalysisUsage(AnalysisUsage &AU) const {
62239310Sdim      AU.setPreservesCFG();
63239310Sdim      AU.addRequired<MachineDominatorTree>();
64239310Sdim      AU.addPreserved<MachineDominatorTree>();
65239310Sdim      AU.addRequired<MachineLoopInfo>();
66239310Sdim      AU.addPreserved<MachineLoopInfo>();
67239310Sdim      MachineFunctionPass::getAnalysisUsage(AU);
68239310Sdim    }
69239310Sdim
70239310Sdim    const char *getPassName() const {
71239310Sdim      return "Hexagon Packetizer";
72239310Sdim    }
73239310Sdim
74239310Sdim    bool runOnMachineFunction(MachineFunction &Fn);
75239310Sdim  };
76239310Sdim  char HexagonPacketizer::ID = 0;
77239310Sdim
78239310Sdim  class HexagonPacketizerList : public VLIWPacketizerList {
79239310Sdim
80239310Sdim  private:
81239310Sdim
82239310Sdim    // Has the instruction been promoted to a dot-new instruction.
83239310Sdim    bool PromotedToDotNew;
84239310Sdim
85239310Sdim    // Has the instruction been glued to allocframe.
86239310Sdim    bool GlueAllocframeStore;
87239310Sdim
88239310Sdim    // Has the feeder instruction been glued to new value jump.
89239310Sdim    bool GlueToNewValueJump;
90239310Sdim
91239310Sdim    // Check if there is a dependence between some instruction already in this
92239310Sdim    // packet and this instruction.
93239310Sdim    bool Dependence;
94239310Sdim
95239310Sdim    // Only check for dependence if there are resources available to
96239310Sdim    // schedule this instruction.
97239310Sdim    bool FoundSequentialDependence;
98239310Sdim
99239310Sdim  public:
100239310Sdim    // Ctor.
101239310Sdim    HexagonPacketizerList(MachineFunction &MF, MachineLoopInfo &MLI,
102239310Sdim                          MachineDominatorTree &MDT);
103239310Sdim
104239310Sdim    // initPacketizerState - initialize some internal flags.
105239310Sdim    void initPacketizerState();
106239310Sdim
107239310Sdim    // ignorePseudoInstruction - Ignore bundling of pseudo instructions.
108239310Sdim    bool ignorePseudoInstruction(MachineInstr *MI, MachineBasicBlock *MBB);
109239310Sdim
110239310Sdim    // isSoloInstruction - return true if instruction MI can not be packetized
111239310Sdim    // with any other instruction, which means that MI itself is a packet.
112239310Sdim    bool isSoloInstruction(MachineInstr *MI);
113239310Sdim
114239310Sdim    // isLegalToPacketizeTogether - Is it legal to packetize SUI and SUJ
115239310Sdim    // together.
116239310Sdim    bool isLegalToPacketizeTogether(SUnit *SUI, SUnit *SUJ);
117239310Sdim
118239310Sdim    // isLegalToPruneDependencies - Is it legal to prune dependece between SUI
119239310Sdim    // and SUJ.
120239310Sdim    bool isLegalToPruneDependencies(SUnit *SUI, SUnit *SUJ);
121239310Sdim
122239310Sdim    MachineBasicBlock::iterator addToPacket(MachineInstr *MI);
123239310Sdim  private:
124239310Sdim    bool IsCallDependent(MachineInstr* MI, SDep::Kind DepType, unsigned DepReg);
125239310Sdim    bool PromoteToDotNew(MachineInstr* MI, SDep::Kind DepType,
126239310Sdim                    MachineBasicBlock::iterator &MII,
127239310Sdim                    const TargetRegisterClass* RC);
128239310Sdim    bool CanPromoteToDotNew(MachineInstr* MI, SUnit* PacketSU,
129239310Sdim                    unsigned DepReg,
130239310Sdim                    std::map <MachineInstr*, SUnit*> MIToSUnit,
131239310Sdim                    MachineBasicBlock::iterator &MII,
132239310Sdim                    const TargetRegisterClass* RC);
133239310Sdim    bool CanPromoteToNewValue(MachineInstr* MI, SUnit* PacketSU,
134239310Sdim                    unsigned DepReg,
135239310Sdim                    std::map <MachineInstr*, SUnit*> MIToSUnit,
136239310Sdim                    MachineBasicBlock::iterator &MII);
137239310Sdim    bool CanPromoteToNewValueStore(MachineInstr* MI, MachineInstr* PacketMI,
138239310Sdim                    unsigned DepReg,
139239310Sdim                    std::map <MachineInstr*, SUnit*> MIToSUnit);
140239310Sdim    bool DemoteToDotOld(MachineInstr* MI);
141239310Sdim    bool ArePredicatesComplements(MachineInstr* MI1, MachineInstr* MI2,
142239310Sdim                    std::map <MachineInstr*, SUnit*> MIToSUnit);
143239310Sdim    bool RestrictingDepExistInPacket(MachineInstr*,
144239310Sdim                    unsigned, std::map <MachineInstr*, SUnit*>);
145239310Sdim    bool isNewifiable(MachineInstr* MI);
146239310Sdim    bool isCondInst(MachineInstr* MI);
147239310Sdim    bool IsNewifyStore (MachineInstr* MI);
148239310Sdim    bool tryAllocateResourcesForConstExt(MachineInstr* MI);
149239310Sdim    bool canReserveResourcesForConstExt(MachineInstr *MI);
150239310Sdim    void reserveResourcesForConstExt(MachineInstr* MI);
151239310Sdim    bool isNewValueInst(MachineInstr* MI);
152239310Sdim  };
153239310Sdim}
154239310Sdim
155239310Sdim// HexagonPacketizerList Ctor.
156239310SdimHexagonPacketizerList::HexagonPacketizerList(
157239310Sdim  MachineFunction &MF, MachineLoopInfo &MLI,MachineDominatorTree &MDT)
158239310Sdim  : VLIWPacketizerList(MF, MLI, MDT, true){
159239310Sdim}
160239310Sdim
161239310Sdimbool HexagonPacketizer::runOnMachineFunction(MachineFunction &Fn) {
162239310Sdim  const TargetInstrInfo *TII = Fn.getTarget().getInstrInfo();
163239310Sdim  MachineLoopInfo &MLI = getAnalysis<MachineLoopInfo>();
164239310Sdim  MachineDominatorTree &MDT = getAnalysis<MachineDominatorTree>();
165239310Sdim
166239310Sdim  // Instantiate the packetizer.
167239310Sdim  HexagonPacketizerList Packetizer(Fn, MLI, MDT);
168239310Sdim
169239310Sdim  // DFA state table should not be empty.
170239310Sdim  assert(Packetizer.getResourceTracker() && "Empty DFA table!");
171239310Sdim
172239310Sdim  //
173239310Sdim  // Loop over all basic blocks and remove KILL pseudo-instructions
174239310Sdim  // These instructions confuse the dependence analysis. Consider:
175239310Sdim  // D0 = ...   (Insn 0)
176239310Sdim  // R0 = KILL R0, D0 (Insn 1)
177239310Sdim  // R0 = ... (Insn 2)
178239310Sdim  // Here, Insn 1 will result in the dependence graph not emitting an output
179239310Sdim  // dependence between Insn 0 and Insn 2. This can lead to incorrect
180239310Sdim  // packetization
181239310Sdim  //
182239310Sdim  for (MachineFunction::iterator MBB = Fn.begin(), MBBe = Fn.end();
183239310Sdim       MBB != MBBe; ++MBB) {
184239310Sdim    MachineBasicBlock::iterator End = MBB->end();
185239310Sdim    MachineBasicBlock::iterator MI = MBB->begin();
186239310Sdim    while (MI != End) {
187239310Sdim      if (MI->isKill()) {
188239310Sdim        MachineBasicBlock::iterator DeleteMI = MI;
189239310Sdim        ++MI;
190239310Sdim        MBB->erase(DeleteMI);
191239310Sdim        End = MBB->end();
192239310Sdim        continue;
193239310Sdim      }
194239310Sdim      ++MI;
195239310Sdim    }
196239310Sdim  }
197239310Sdim
198239310Sdim  // Loop over all of the basic blocks.
199239310Sdim  for (MachineFunction::iterator MBB = Fn.begin(), MBBe = Fn.end();
200239310Sdim       MBB != MBBe; ++MBB) {
201239310Sdim    // Find scheduling regions and schedule / packetize each region.
202239310Sdim    unsigned RemainingCount = MBB->size();
203239310Sdim    for(MachineBasicBlock::iterator RegionEnd = MBB->end();
204239310Sdim        RegionEnd != MBB->begin();) {
205239310Sdim      // The next region starts above the previous region. Look backward in the
206239310Sdim      // instruction stream until we find the nearest boundary.
207239310Sdim      MachineBasicBlock::iterator I = RegionEnd;
208239310Sdim      for(;I != MBB->begin(); --I, --RemainingCount) {
209239310Sdim        if (TII->isSchedulingBoundary(llvm::prior(I), MBB, Fn))
210239310Sdim          break;
211239310Sdim      }
212239310Sdim      I = MBB->begin();
213239310Sdim
214239310Sdim      // Skip empty scheduling regions.
215239310Sdim      if (I == RegionEnd) {
216239310Sdim        RegionEnd = llvm::prior(RegionEnd);
217239310Sdim        --RemainingCount;
218239310Sdim        continue;
219239310Sdim      }
220239310Sdim      // Skip regions with one instruction.
221239310Sdim      if (I == llvm::prior(RegionEnd)) {
222239310Sdim        RegionEnd = llvm::prior(RegionEnd);
223239310Sdim        continue;
224239310Sdim      }
225239310Sdim
226239310Sdim      Packetizer.PacketizeMIs(MBB, I, RegionEnd);
227239310Sdim      RegionEnd = I;
228239310Sdim    }
229239310Sdim  }
230239310Sdim
231239310Sdim  return true;
232239310Sdim}
233239310Sdim
234239310Sdim
235239310Sdimstatic bool IsIndirectCall(MachineInstr* MI) {
236239310Sdim  return ((MI->getOpcode() == Hexagon::CALLR) ||
237239310Sdim          (MI->getOpcode() == Hexagon::CALLRv3));
238239310Sdim}
239239310Sdim
240239310Sdim// Reserve resources for constant extender. Trigure an assertion if
241239310Sdim// reservation fail.
242239310Sdimvoid HexagonPacketizerList::reserveResourcesForConstExt(MachineInstr* MI) {
243239310Sdim  const HexagonInstrInfo *QII = (const HexagonInstrInfo *) TII;
244249423Sdim  MachineFunction *MF = MI->getParent()->getParent();
245249423Sdim  MachineInstr *PseudoMI = MF->CreateMachineInstr(QII->get(Hexagon::IMMEXT_i),
246249423Sdim                                                  MI->getDebugLoc());
247239310Sdim
248239310Sdim  if (ResourceTracker->canReserveResources(PseudoMI)) {
249239310Sdim    ResourceTracker->reserveResources(PseudoMI);
250239310Sdim    MI->getParent()->getParent()->DeleteMachineInstr(PseudoMI);
251239310Sdim  } else {
252239310Sdim    MI->getParent()->getParent()->DeleteMachineInstr(PseudoMI);
253239310Sdim    llvm_unreachable("can not reserve resources for constant extender.");
254239310Sdim  }
255239310Sdim  return;
256239310Sdim}
257239310Sdim
258239310Sdimbool HexagonPacketizerList::canReserveResourcesForConstExt(MachineInstr *MI) {
259239310Sdim  const HexagonInstrInfo *QII = (const HexagonInstrInfo *) TII;
260249423Sdim  assert((QII->isExtended(MI) || QII->isConstExtended(MI)) &&
261239310Sdim         "Should only be called for constant extended instructions");
262239310Sdim  MachineFunction *MF = MI->getParent()->getParent();
263249423Sdim  MachineInstr *PseudoMI = MF->CreateMachineInstr(QII->get(Hexagon::IMMEXT_i),
264239310Sdim                                                  MI->getDebugLoc());
265239310Sdim  bool CanReserve = ResourceTracker->canReserveResources(PseudoMI);
266239310Sdim  MF->DeleteMachineInstr(PseudoMI);
267239310Sdim  return CanReserve;
268239310Sdim}
269239310Sdim
270239310Sdim// Allocate resources (i.e. 4 bytes) for constant extender. If succeed, return
271239310Sdim// true, otherwise, return false.
272239310Sdimbool HexagonPacketizerList::tryAllocateResourcesForConstExt(MachineInstr* MI) {
273239310Sdim  const HexagonInstrInfo *QII = (const HexagonInstrInfo *) TII;
274249423Sdim  MachineFunction *MF = MI->getParent()->getParent();
275249423Sdim  MachineInstr *PseudoMI = MF->CreateMachineInstr(QII->get(Hexagon::IMMEXT_i),
276249423Sdim                                                  MI->getDebugLoc());
277239310Sdim
278239310Sdim  if (ResourceTracker->canReserveResources(PseudoMI)) {
279239310Sdim    ResourceTracker->reserveResources(PseudoMI);
280239310Sdim    MI->getParent()->getParent()->DeleteMachineInstr(PseudoMI);
281239310Sdim    return true;
282239310Sdim  } else {
283239310Sdim    MI->getParent()->getParent()->DeleteMachineInstr(PseudoMI);
284239310Sdim    return false;
285239310Sdim  }
286239310Sdim}
287239310Sdim
288239310Sdim
289239310Sdimbool HexagonPacketizerList::IsCallDependent(MachineInstr* MI,
290239310Sdim                                          SDep::Kind DepType,
291239310Sdim                                          unsigned DepReg) {
292239310Sdim
293239310Sdim  const HexagonInstrInfo *QII = (const HexagonInstrInfo *) TII;
294239310Sdim  const HexagonRegisterInfo* QRI =
295239310Sdim              (const HexagonRegisterInfo *) TM.getRegisterInfo();
296239310Sdim
297239310Sdim  // Check for lr dependence
298239310Sdim  if (DepReg == QRI->getRARegister()) {
299239310Sdim    return true;
300239310Sdim  }
301239310Sdim
302239310Sdim  if (QII->isDeallocRet(MI)) {
303239310Sdim    if (DepReg == QRI->getFrameRegister() ||
304239310Sdim        DepReg == QRI->getStackRegister())
305239310Sdim      return true;
306239310Sdim  }
307239310Sdim
308239310Sdim  // Check if this is a predicate dependence
309239310Sdim  const TargetRegisterClass* RC = QRI->getMinimalPhysRegClass(DepReg);
310239310Sdim  if (RC == &Hexagon::PredRegsRegClass) {
311239310Sdim    return true;
312239310Sdim  }
313239310Sdim
314239310Sdim  //
315239310Sdim  // Lastly check for an operand used in an indirect call
316239310Sdim  // If we had an attribute for checking if an instruction is an indirect call,
317239310Sdim  // then we could have avoided this relatively brittle implementation of
318239310Sdim  // IsIndirectCall()
319239310Sdim  //
320239310Sdim  // Assumes that the first operand of the CALLr is the function address
321239310Sdim  //
322239310Sdim  if (IsIndirectCall(MI) && (DepType == SDep::Data)) {
323239310Sdim    MachineOperand MO = MI->getOperand(0);
324239310Sdim    if (MO.isReg() && MO.isUse() && (MO.getReg() == DepReg)) {
325239310Sdim      return true;
326239310Sdim    }
327239310Sdim  }
328239310Sdim
329239310Sdim  return false;
330239310Sdim}
331239310Sdim
332239310Sdimstatic bool IsRegDependence(const SDep::Kind DepType) {
333239310Sdim  return (DepType == SDep::Data || DepType == SDep::Anti ||
334239310Sdim          DepType == SDep::Output);
335239310Sdim}
336239310Sdim
337239310Sdimstatic bool IsDirectJump(MachineInstr* MI) {
338239310Sdim  return (MI->getOpcode() == Hexagon::JMP);
339239310Sdim}
340239310Sdim
341239310Sdimstatic bool IsSchedBarrier(MachineInstr* MI) {
342239310Sdim  switch (MI->getOpcode()) {
343239310Sdim  case Hexagon::BARRIER:
344239310Sdim    return true;
345239310Sdim  }
346239310Sdim  return false;
347239310Sdim}
348239310Sdim
349239310Sdimstatic bool IsControlFlow(MachineInstr* MI) {
350239310Sdim  return (MI->getDesc().isTerminator() || MI->getDesc().isCall());
351239310Sdim}
352239310Sdim
353239310Sdim// Function returns true if an instruction can be promoted to the new-value
354239310Sdim// store. It will always return false for v2 and v3.
355239310Sdim// It lists all the conditional and unconditional stores that can be promoted
356239310Sdim// to the new-value stores.
357239310Sdim
358239310Sdimbool HexagonPacketizerList::IsNewifyStore (MachineInstr* MI) {
359239310Sdim  const HexagonRegisterInfo* QRI =
360239310Sdim                          (const HexagonRegisterInfo *) TM.getRegisterInfo();
361239310Sdim  switch (MI->getOpcode())
362239310Sdim  {
363239310Sdim    // store byte
364239310Sdim    case Hexagon::STrib:
365239310Sdim    case Hexagon::STrib_indexed:
366239310Sdim    case Hexagon::STrib_indexed_shl_V4:
367239310Sdim    case Hexagon::STrib_shl_V4:
368239310Sdim    case Hexagon::STb_GP_V4:
369239310Sdim    case Hexagon::POST_STbri:
370239310Sdim    case Hexagon::STrib_cPt:
371239310Sdim    case Hexagon::STrib_cdnPt_V4:
372239310Sdim    case Hexagon::STrib_cNotPt:
373239310Sdim    case Hexagon::STrib_cdnNotPt_V4:
374239310Sdim    case Hexagon::STrib_indexed_cPt:
375239310Sdim    case Hexagon::STrib_indexed_cdnPt_V4:
376239310Sdim    case Hexagon::STrib_indexed_cNotPt:
377239310Sdim    case Hexagon::STrib_indexed_cdnNotPt_V4:
378239310Sdim    case Hexagon::STrib_indexed_shl_cPt_V4:
379239310Sdim    case Hexagon::STrib_indexed_shl_cdnPt_V4:
380239310Sdim    case Hexagon::STrib_indexed_shl_cNotPt_V4:
381239310Sdim    case Hexagon::STrib_indexed_shl_cdnNotPt_V4:
382239310Sdim    case Hexagon::POST_STbri_cPt:
383239310Sdim    case Hexagon::POST_STbri_cdnPt_V4:
384239310Sdim    case Hexagon::POST_STbri_cNotPt:
385239310Sdim    case Hexagon::POST_STbri_cdnNotPt_V4:
386239310Sdim    case Hexagon::STb_GP_cPt_V4:
387239310Sdim    case Hexagon::STb_GP_cNotPt_V4:
388239310Sdim    case Hexagon::STb_GP_cdnPt_V4:
389239310Sdim    case Hexagon::STb_GP_cdnNotPt_V4:
390239310Sdim
391239310Sdim    // store halfword
392239310Sdim    case Hexagon::STrih:
393239310Sdim    case Hexagon::STrih_indexed:
394239310Sdim    case Hexagon::STrih_indexed_shl_V4:
395239310Sdim    case Hexagon::STrih_shl_V4:
396239310Sdim    case Hexagon::STh_GP_V4:
397239310Sdim    case Hexagon::POST_SThri:
398239310Sdim    case Hexagon::STrih_cPt:
399239310Sdim    case Hexagon::STrih_cdnPt_V4:
400239310Sdim    case Hexagon::STrih_cNotPt:
401239310Sdim    case Hexagon::STrih_cdnNotPt_V4:
402239310Sdim    case Hexagon::STrih_indexed_cPt:
403239310Sdim    case Hexagon::STrih_indexed_cdnPt_V4:
404239310Sdim    case Hexagon::STrih_indexed_cNotPt:
405239310Sdim    case Hexagon::STrih_indexed_cdnNotPt_V4:
406239310Sdim    case Hexagon::STrih_indexed_shl_cPt_V4:
407239310Sdim    case Hexagon::STrih_indexed_shl_cdnPt_V4:
408239310Sdim    case Hexagon::STrih_indexed_shl_cNotPt_V4:
409239310Sdim    case Hexagon::STrih_indexed_shl_cdnNotPt_V4:
410239310Sdim    case Hexagon::POST_SThri_cPt:
411239310Sdim    case Hexagon::POST_SThri_cdnPt_V4:
412239310Sdim    case Hexagon::POST_SThri_cNotPt:
413239310Sdim    case Hexagon::POST_SThri_cdnNotPt_V4:
414239310Sdim    case Hexagon::STh_GP_cPt_V4:
415239310Sdim    case Hexagon::STh_GP_cNotPt_V4:
416239310Sdim    case Hexagon::STh_GP_cdnPt_V4:
417239310Sdim    case Hexagon::STh_GP_cdnNotPt_V4:
418239310Sdim
419239310Sdim    // store word
420239310Sdim    case Hexagon::STriw:
421239310Sdim    case Hexagon::STriw_indexed:
422239310Sdim    case Hexagon::STriw_indexed_shl_V4:
423239310Sdim    case Hexagon::STriw_shl_V4:
424239310Sdim    case Hexagon::STw_GP_V4:
425239310Sdim    case Hexagon::POST_STwri:
426239310Sdim    case Hexagon::STriw_cPt:
427239310Sdim    case Hexagon::STriw_cdnPt_V4:
428239310Sdim    case Hexagon::STriw_cNotPt:
429239310Sdim    case Hexagon::STriw_cdnNotPt_V4:
430239310Sdim    case Hexagon::STriw_indexed_cPt:
431239310Sdim    case Hexagon::STriw_indexed_cdnPt_V4:
432239310Sdim    case Hexagon::STriw_indexed_cNotPt:
433239310Sdim    case Hexagon::STriw_indexed_cdnNotPt_V4:
434239310Sdim    case Hexagon::STriw_indexed_shl_cPt_V4:
435239310Sdim    case Hexagon::STriw_indexed_shl_cdnPt_V4:
436239310Sdim    case Hexagon::STriw_indexed_shl_cNotPt_V4:
437239310Sdim    case Hexagon::STriw_indexed_shl_cdnNotPt_V4:
438239310Sdim    case Hexagon::POST_STwri_cPt:
439239310Sdim    case Hexagon::POST_STwri_cdnPt_V4:
440239310Sdim    case Hexagon::POST_STwri_cNotPt:
441239310Sdim    case Hexagon::POST_STwri_cdnNotPt_V4:
442239310Sdim    case Hexagon::STw_GP_cPt_V4:
443239310Sdim    case Hexagon::STw_GP_cNotPt_V4:
444239310Sdim    case Hexagon::STw_GP_cdnPt_V4:
445239310Sdim    case Hexagon::STw_GP_cdnNotPt_V4:
446239310Sdim        return QRI->Subtarget.hasV4TOps();
447239310Sdim  }
448239310Sdim  return false;
449239310Sdim}
450239310Sdim
451239310Sdimstatic bool IsLoopN(MachineInstr *MI) {
452239310Sdim  return (MI->getOpcode() == Hexagon::LOOP0_i ||
453239310Sdim          MI->getOpcode() == Hexagon::LOOP0_r);
454239310Sdim}
455239310Sdim
456239310Sdim/// DoesModifyCalleeSavedReg - Returns true if the instruction modifies a
457239310Sdim/// callee-saved register.
458239310Sdimstatic bool DoesModifyCalleeSavedReg(MachineInstr *MI,
459239310Sdim                                     const TargetRegisterInfo *TRI) {
460239310Sdim  for (const uint16_t *CSR = TRI->getCalleeSavedRegs(); *CSR; ++CSR) {
461239310Sdim    unsigned CalleeSavedReg = *CSR;
462239310Sdim    if (MI->modifiesRegister(CalleeSavedReg, TRI))
463239310Sdim      return true;
464239310Sdim  }
465239310Sdim  return false;
466239310Sdim}
467239310Sdim
468239310Sdim// Return the new value instruction for a given store.
469239310Sdimstatic int GetDotNewOp(const int opc) {
470239310Sdim  switch (opc) {
471239310Sdim  default: llvm_unreachable("Unknown .new type");
472239310Sdim  // store new value byte
473239310Sdim  case Hexagon::STrib:
474239310Sdim    return Hexagon::STrib_nv_V4;
475239310Sdim
476239310Sdim  case Hexagon::STrib_indexed:
477239310Sdim    return Hexagon::STrib_indexed_nv_V4;
478239310Sdim
479239310Sdim  case Hexagon::STrib_indexed_shl_V4:
480239310Sdim    return Hexagon::STrib_indexed_shl_nv_V4;
481239310Sdim
482239310Sdim  case Hexagon::STrib_shl_V4:
483239310Sdim    return Hexagon::STrib_shl_nv_V4;
484239310Sdim
485239310Sdim  case Hexagon::STb_GP_V4:
486239310Sdim    return Hexagon::STb_GP_nv_V4;
487239310Sdim
488239310Sdim  case Hexagon::POST_STbri:
489239310Sdim    return Hexagon::POST_STbri_nv_V4;
490239310Sdim
491239310Sdim  case Hexagon::STrib_cPt:
492239310Sdim    return Hexagon::STrib_cPt_nv_V4;
493239310Sdim
494239310Sdim  case Hexagon::STrib_cdnPt_V4:
495239310Sdim    return Hexagon::STrib_cdnPt_nv_V4;
496239310Sdim
497239310Sdim  case Hexagon::STrib_cNotPt:
498239310Sdim    return Hexagon::STrib_cNotPt_nv_V4;
499239310Sdim
500239310Sdim  case Hexagon::STrib_cdnNotPt_V4:
501239310Sdim    return Hexagon::STrib_cdnNotPt_nv_V4;
502239310Sdim
503239310Sdim  case Hexagon::STrib_indexed_cPt:
504239310Sdim    return Hexagon::STrib_indexed_cPt_nv_V4;
505239310Sdim
506239310Sdim  case Hexagon::STrib_indexed_cdnPt_V4:
507239310Sdim    return Hexagon::STrib_indexed_cdnPt_nv_V4;
508239310Sdim
509239310Sdim  case Hexagon::STrib_indexed_cNotPt:
510239310Sdim    return Hexagon::STrib_indexed_cNotPt_nv_V4;
511239310Sdim
512239310Sdim  case Hexagon::STrib_indexed_cdnNotPt_V4:
513239310Sdim    return Hexagon::STrib_indexed_cdnNotPt_nv_V4;
514239310Sdim
515239310Sdim  case Hexagon::STrib_indexed_shl_cPt_V4:
516239310Sdim    return Hexagon::STrib_indexed_shl_cPt_nv_V4;
517239310Sdim
518239310Sdim  case Hexagon::STrib_indexed_shl_cdnPt_V4:
519239310Sdim    return Hexagon::STrib_indexed_shl_cdnPt_nv_V4;
520239310Sdim
521239310Sdim  case Hexagon::STrib_indexed_shl_cNotPt_V4:
522239310Sdim    return Hexagon::STrib_indexed_shl_cNotPt_nv_V4;
523239310Sdim
524239310Sdim  case Hexagon::STrib_indexed_shl_cdnNotPt_V4:
525239310Sdim    return Hexagon::STrib_indexed_shl_cdnNotPt_nv_V4;
526239310Sdim
527239310Sdim  case Hexagon::POST_STbri_cPt:
528239310Sdim    return Hexagon::POST_STbri_cPt_nv_V4;
529239310Sdim
530239310Sdim  case Hexagon::POST_STbri_cdnPt_V4:
531239310Sdim    return Hexagon::POST_STbri_cdnPt_nv_V4;
532239310Sdim
533239310Sdim  case Hexagon::POST_STbri_cNotPt:
534239310Sdim    return Hexagon::POST_STbri_cNotPt_nv_V4;
535239310Sdim
536239310Sdim  case Hexagon::POST_STbri_cdnNotPt_V4:
537239310Sdim    return Hexagon::POST_STbri_cdnNotPt_nv_V4;
538239310Sdim
539239310Sdim  case Hexagon::STb_GP_cPt_V4:
540239310Sdim    return Hexagon::STb_GP_cPt_nv_V4;
541239310Sdim
542239310Sdim  case Hexagon::STb_GP_cNotPt_V4:
543239310Sdim    return Hexagon::STb_GP_cNotPt_nv_V4;
544239310Sdim
545239310Sdim  case Hexagon::STb_GP_cdnPt_V4:
546239310Sdim    return Hexagon::STb_GP_cdnPt_nv_V4;
547239310Sdim
548239310Sdim  case Hexagon::STb_GP_cdnNotPt_V4:
549239310Sdim    return Hexagon::STb_GP_cdnNotPt_nv_V4;
550239310Sdim
551239310Sdim  // store new value halfword
552239310Sdim  case Hexagon::STrih:
553239310Sdim    return Hexagon::STrih_nv_V4;
554239310Sdim
555239310Sdim  case Hexagon::STrih_indexed:
556239310Sdim    return Hexagon::STrih_indexed_nv_V4;
557239310Sdim
558239310Sdim  case Hexagon::STrih_indexed_shl_V4:
559239310Sdim    return Hexagon::STrih_indexed_shl_nv_V4;
560239310Sdim
561239310Sdim  case Hexagon::STrih_shl_V4:
562239310Sdim    return Hexagon::STrih_shl_nv_V4;
563239310Sdim
564239310Sdim  case Hexagon::STh_GP_V4:
565239310Sdim    return Hexagon::STh_GP_nv_V4;
566239310Sdim
567239310Sdim  case Hexagon::POST_SThri:
568239310Sdim    return Hexagon::POST_SThri_nv_V4;
569239310Sdim
570239310Sdim  case Hexagon::STrih_cPt:
571239310Sdim    return Hexagon::STrih_cPt_nv_V4;
572239310Sdim
573239310Sdim  case Hexagon::STrih_cdnPt_V4:
574239310Sdim    return Hexagon::STrih_cdnPt_nv_V4;
575239310Sdim
576239310Sdim  case Hexagon::STrih_cNotPt:
577239310Sdim    return Hexagon::STrih_cNotPt_nv_V4;
578239310Sdim
579239310Sdim  case Hexagon::STrih_cdnNotPt_V4:
580239310Sdim    return Hexagon::STrih_cdnNotPt_nv_V4;
581239310Sdim
582239310Sdim  case Hexagon::STrih_indexed_cPt:
583239310Sdim    return Hexagon::STrih_indexed_cPt_nv_V4;
584239310Sdim
585239310Sdim  case Hexagon::STrih_indexed_cdnPt_V4:
586239310Sdim    return Hexagon::STrih_indexed_cdnPt_nv_V4;
587239310Sdim
588239310Sdim  case Hexagon::STrih_indexed_cNotPt:
589239310Sdim    return Hexagon::STrih_indexed_cNotPt_nv_V4;
590239310Sdim
591239310Sdim  case Hexagon::STrih_indexed_cdnNotPt_V4:
592239310Sdim    return Hexagon::STrih_indexed_cdnNotPt_nv_V4;
593239310Sdim
594239310Sdim  case Hexagon::STrih_indexed_shl_cPt_V4:
595239310Sdim    return Hexagon::STrih_indexed_shl_cPt_nv_V4;
596239310Sdim
597239310Sdim  case Hexagon::STrih_indexed_shl_cdnPt_V4:
598239310Sdim    return Hexagon::STrih_indexed_shl_cdnPt_nv_V4;
599239310Sdim
600239310Sdim  case Hexagon::STrih_indexed_shl_cNotPt_V4:
601239310Sdim    return Hexagon::STrih_indexed_shl_cNotPt_nv_V4;
602239310Sdim
603239310Sdim  case Hexagon::STrih_indexed_shl_cdnNotPt_V4:
604239310Sdim    return Hexagon::STrih_indexed_shl_cdnNotPt_nv_V4;
605239310Sdim
606239310Sdim  case Hexagon::POST_SThri_cPt:
607239310Sdim    return Hexagon::POST_SThri_cPt_nv_V4;
608239310Sdim
609239310Sdim  case Hexagon::POST_SThri_cdnPt_V4:
610239310Sdim    return Hexagon::POST_SThri_cdnPt_nv_V4;
611239310Sdim
612239310Sdim  case Hexagon::POST_SThri_cNotPt:
613239310Sdim    return Hexagon::POST_SThri_cNotPt_nv_V4;
614239310Sdim
615239310Sdim  case Hexagon::POST_SThri_cdnNotPt_V4:
616239310Sdim    return Hexagon::POST_SThri_cdnNotPt_nv_V4;
617239310Sdim
618239310Sdim  case Hexagon::STh_GP_cPt_V4:
619239310Sdim    return Hexagon::STh_GP_cPt_nv_V4;
620239310Sdim
621239310Sdim  case Hexagon::STh_GP_cNotPt_V4:
622239310Sdim    return Hexagon::STh_GP_cNotPt_nv_V4;
623239310Sdim
624239310Sdim  case Hexagon::STh_GP_cdnPt_V4:
625239310Sdim    return Hexagon::STh_GP_cdnPt_nv_V4;
626239310Sdim
627239310Sdim  case Hexagon::STh_GP_cdnNotPt_V4:
628239310Sdim    return Hexagon::STh_GP_cdnNotPt_nv_V4;
629239310Sdim
630239310Sdim  // store new value word
631239310Sdim  case Hexagon::STriw:
632239310Sdim    return Hexagon::STriw_nv_V4;
633239310Sdim
634239310Sdim  case Hexagon::STriw_indexed:
635239310Sdim    return Hexagon::STriw_indexed_nv_V4;
636239310Sdim
637239310Sdim  case Hexagon::STriw_indexed_shl_V4:
638239310Sdim    return Hexagon::STriw_indexed_shl_nv_V4;
639239310Sdim
640239310Sdim  case Hexagon::STriw_shl_V4:
641239310Sdim    return Hexagon::STriw_shl_nv_V4;
642239310Sdim
643239310Sdim  case Hexagon::STw_GP_V4:
644239310Sdim    return Hexagon::STw_GP_nv_V4;
645239310Sdim
646239310Sdim  case Hexagon::POST_STwri:
647239310Sdim    return Hexagon::POST_STwri_nv_V4;
648239310Sdim
649239310Sdim  case Hexagon::STriw_cPt:
650239310Sdim    return Hexagon::STriw_cPt_nv_V4;
651239310Sdim
652239310Sdim  case Hexagon::STriw_cdnPt_V4:
653239310Sdim    return Hexagon::STriw_cdnPt_nv_V4;
654239310Sdim
655239310Sdim  case Hexagon::STriw_cNotPt:
656239310Sdim    return Hexagon::STriw_cNotPt_nv_V4;
657239310Sdim
658239310Sdim  case Hexagon::STriw_cdnNotPt_V4:
659239310Sdim    return Hexagon::STriw_cdnNotPt_nv_V4;
660239310Sdim
661239310Sdim  case Hexagon::STriw_indexed_cPt:
662239310Sdim    return Hexagon::STriw_indexed_cPt_nv_V4;
663239310Sdim
664239310Sdim  case Hexagon::STriw_indexed_cdnPt_V4:
665239310Sdim    return Hexagon::STriw_indexed_cdnPt_nv_V4;
666239310Sdim
667239310Sdim  case Hexagon::STriw_indexed_cNotPt:
668239310Sdim    return Hexagon::STriw_indexed_cNotPt_nv_V4;
669239310Sdim
670239310Sdim  case Hexagon::STriw_indexed_cdnNotPt_V4:
671239310Sdim    return Hexagon::STriw_indexed_cdnNotPt_nv_V4;
672239310Sdim
673239310Sdim  case Hexagon::STriw_indexed_shl_cPt_V4:
674239310Sdim    return Hexagon::STriw_indexed_shl_cPt_nv_V4;
675239310Sdim
676239310Sdim  case Hexagon::STriw_indexed_shl_cdnPt_V4:
677239310Sdim    return Hexagon::STriw_indexed_shl_cdnPt_nv_V4;
678239310Sdim
679239310Sdim  case Hexagon::STriw_indexed_shl_cNotPt_V4:
680239310Sdim    return Hexagon::STriw_indexed_shl_cNotPt_nv_V4;
681239310Sdim
682239310Sdim  case Hexagon::STriw_indexed_shl_cdnNotPt_V4:
683239310Sdim    return Hexagon::STriw_indexed_shl_cdnNotPt_nv_V4;
684239310Sdim
685239310Sdim  case Hexagon::POST_STwri_cPt:
686239310Sdim    return Hexagon::POST_STwri_cPt_nv_V4;
687239310Sdim
688239310Sdim  case Hexagon::POST_STwri_cdnPt_V4:
689239310Sdim    return Hexagon::POST_STwri_cdnPt_nv_V4;
690239310Sdim
691239310Sdim  case Hexagon::POST_STwri_cNotPt:
692239310Sdim    return Hexagon::POST_STwri_cNotPt_nv_V4;
693239310Sdim
694239310Sdim  case Hexagon::POST_STwri_cdnNotPt_V4:
695239310Sdim    return Hexagon::POST_STwri_cdnNotPt_nv_V4;
696239310Sdim
697239310Sdim  case Hexagon::STw_GP_cPt_V4:
698239310Sdim    return Hexagon::STw_GP_cPt_nv_V4;
699239310Sdim
700239310Sdim  case Hexagon::STw_GP_cNotPt_V4:
701239310Sdim    return Hexagon::STw_GP_cNotPt_nv_V4;
702239310Sdim
703239310Sdim  case Hexagon::STw_GP_cdnPt_V4:
704239310Sdim    return Hexagon::STw_GP_cdnPt_nv_V4;
705239310Sdim
706239310Sdim  case Hexagon::STw_GP_cdnNotPt_V4:
707239310Sdim    return Hexagon::STw_GP_cdnNotPt_nv_V4;
708239310Sdim
709239310Sdim  }
710239310Sdim}
711239310Sdim
712239310Sdim// Return .new predicate version for an instruction
713239310Sdimstatic int GetDotNewPredOp(const int opc) {
714239310Sdim  switch (opc) {
715239310Sdim  default: llvm_unreachable("Unknown .new type");
716239310Sdim  // Conditional stores
717239310Sdim  // Store byte conditionally
718239310Sdim  case Hexagon::STrib_cPt :
719239310Sdim    return Hexagon::STrib_cdnPt_V4;
720239310Sdim
721239310Sdim  case Hexagon::STrib_cNotPt :
722239310Sdim    return Hexagon::STrib_cdnNotPt_V4;
723239310Sdim
724239310Sdim  case Hexagon::STrib_indexed_cPt :
725239310Sdim    return Hexagon::STrib_indexed_cdnPt_V4;
726239310Sdim
727239310Sdim  case Hexagon::STrib_indexed_cNotPt :
728239310Sdim    return Hexagon::STrib_indexed_cdnNotPt_V4;
729239310Sdim
730239310Sdim  case Hexagon::STrib_imm_cPt_V4 :
731239310Sdim    return Hexagon::STrib_imm_cdnPt_V4;
732239310Sdim
733239310Sdim  case Hexagon::STrib_imm_cNotPt_V4 :
734239310Sdim    return Hexagon::STrib_imm_cdnNotPt_V4;
735239310Sdim
736239310Sdim  case Hexagon::POST_STbri_cPt :
737239310Sdim    return Hexagon::POST_STbri_cdnPt_V4;
738239310Sdim
739239310Sdim  case Hexagon::POST_STbri_cNotPt :
740239310Sdim    return Hexagon::POST_STbri_cdnNotPt_V4;
741239310Sdim
742239310Sdim  case Hexagon::STrib_indexed_shl_cPt_V4 :
743239310Sdim    return Hexagon::STrib_indexed_shl_cdnPt_V4;
744239310Sdim
745239310Sdim  case Hexagon::STrib_indexed_shl_cNotPt_V4 :
746239310Sdim    return Hexagon::STrib_indexed_shl_cdnNotPt_V4;
747239310Sdim
748239310Sdim  case Hexagon::STb_GP_cPt_V4 :
749239310Sdim    return Hexagon::STb_GP_cdnPt_V4;
750239310Sdim
751239310Sdim  case Hexagon::STb_GP_cNotPt_V4 :
752239310Sdim    return Hexagon::STb_GP_cdnNotPt_V4;
753239310Sdim
754239310Sdim  // Store doubleword conditionally
755239310Sdim  case Hexagon::STrid_cPt :
756239310Sdim    return Hexagon::STrid_cdnPt_V4;
757239310Sdim
758239310Sdim  case Hexagon::STrid_cNotPt :
759239310Sdim    return Hexagon::STrid_cdnNotPt_V4;
760239310Sdim
761239310Sdim  case Hexagon::STrid_indexed_cPt :
762239310Sdim    return Hexagon::STrid_indexed_cdnPt_V4;
763239310Sdim
764239310Sdim  case Hexagon::STrid_indexed_cNotPt :
765239310Sdim    return Hexagon::STrid_indexed_cdnNotPt_V4;
766239310Sdim
767239310Sdim  case Hexagon::STrid_indexed_shl_cPt_V4 :
768239310Sdim    return Hexagon::STrid_indexed_shl_cdnPt_V4;
769239310Sdim
770239310Sdim  case Hexagon::STrid_indexed_shl_cNotPt_V4 :
771239310Sdim    return Hexagon::STrid_indexed_shl_cdnNotPt_V4;
772239310Sdim
773239310Sdim  case Hexagon::POST_STdri_cPt :
774239310Sdim    return Hexagon::POST_STdri_cdnPt_V4;
775239310Sdim
776239310Sdim  case Hexagon::POST_STdri_cNotPt :
777239310Sdim    return Hexagon::POST_STdri_cdnNotPt_V4;
778239310Sdim
779239310Sdim  case Hexagon::STd_GP_cPt_V4 :
780239310Sdim    return Hexagon::STd_GP_cdnPt_V4;
781239310Sdim
782239310Sdim  case Hexagon::STd_GP_cNotPt_V4 :
783239310Sdim    return Hexagon::STd_GP_cdnNotPt_V4;
784239310Sdim
785239310Sdim  // Store halfword conditionally
786239310Sdim  case Hexagon::STrih_cPt :
787239310Sdim    return Hexagon::STrih_cdnPt_V4;
788239310Sdim
789239310Sdim  case Hexagon::STrih_cNotPt :
790239310Sdim    return Hexagon::STrih_cdnNotPt_V4;
791239310Sdim
792239310Sdim  case Hexagon::STrih_indexed_cPt :
793239310Sdim    return Hexagon::STrih_indexed_cdnPt_V4;
794239310Sdim
795239310Sdim  case Hexagon::STrih_indexed_cNotPt :
796239310Sdim    return Hexagon::STrih_indexed_cdnNotPt_V4;
797239310Sdim
798239310Sdim  case Hexagon::STrih_imm_cPt_V4 :
799239310Sdim    return Hexagon::STrih_imm_cdnPt_V4;
800239310Sdim
801239310Sdim  case Hexagon::STrih_imm_cNotPt_V4 :
802239310Sdim    return Hexagon::STrih_imm_cdnNotPt_V4;
803239310Sdim
804239310Sdim  case Hexagon::STrih_indexed_shl_cPt_V4 :
805239310Sdim    return Hexagon::STrih_indexed_shl_cdnPt_V4;
806239310Sdim
807239310Sdim  case Hexagon::STrih_indexed_shl_cNotPt_V4 :
808239310Sdim    return Hexagon::STrih_indexed_shl_cdnNotPt_V4;
809239310Sdim
810239310Sdim  case Hexagon::POST_SThri_cPt :
811239310Sdim    return Hexagon::POST_SThri_cdnPt_V4;
812239310Sdim
813239310Sdim  case Hexagon::POST_SThri_cNotPt :
814239310Sdim    return Hexagon::POST_SThri_cdnNotPt_V4;
815239310Sdim
816239310Sdim  case Hexagon::STh_GP_cPt_V4 :
817239310Sdim    return Hexagon::STh_GP_cdnPt_V4;
818239310Sdim
819239310Sdim  case Hexagon::STh_GP_cNotPt_V4 :
820239310Sdim    return Hexagon::STh_GP_cdnNotPt_V4;
821239310Sdim
822239310Sdim  // Store word conditionally
823239310Sdim  case Hexagon::STriw_cPt :
824239310Sdim    return Hexagon::STriw_cdnPt_V4;
825239310Sdim
826239310Sdim  case Hexagon::STriw_cNotPt :
827239310Sdim    return Hexagon::STriw_cdnNotPt_V4;
828239310Sdim
829239310Sdim  case Hexagon::STriw_indexed_cPt :
830239310Sdim    return Hexagon::STriw_indexed_cdnPt_V4;
831239310Sdim
832239310Sdim  case Hexagon::STriw_indexed_cNotPt :
833239310Sdim    return Hexagon::STriw_indexed_cdnNotPt_V4;
834239310Sdim
835239310Sdim  case Hexagon::STriw_imm_cPt_V4 :
836239310Sdim    return Hexagon::STriw_imm_cdnPt_V4;
837239310Sdim
838239310Sdim  case Hexagon::STriw_imm_cNotPt_V4 :
839239310Sdim    return Hexagon::STriw_imm_cdnNotPt_V4;
840239310Sdim
841239310Sdim  case Hexagon::STriw_indexed_shl_cPt_V4 :
842239310Sdim    return Hexagon::STriw_indexed_shl_cdnPt_V4;
843239310Sdim
844239310Sdim  case Hexagon::STriw_indexed_shl_cNotPt_V4 :
845239310Sdim    return Hexagon::STriw_indexed_shl_cdnNotPt_V4;
846239310Sdim
847239310Sdim  case Hexagon::POST_STwri_cPt :
848239310Sdim    return Hexagon::POST_STwri_cdnPt_V4;
849239310Sdim
850239310Sdim  case Hexagon::POST_STwri_cNotPt :
851239310Sdim    return Hexagon::POST_STwri_cdnNotPt_V4;
852239310Sdim
853239310Sdim  case Hexagon::STw_GP_cPt_V4 :
854239310Sdim    return Hexagon::STw_GP_cdnPt_V4;
855239310Sdim
856239310Sdim  case Hexagon::STw_GP_cNotPt_V4 :
857239310Sdim    return Hexagon::STw_GP_cdnNotPt_V4;
858239310Sdim
859239310Sdim  // Condtional Jumps
860239310Sdim  case Hexagon::JMP_c:
861239310Sdim    return Hexagon::JMP_cdnPt;
862239310Sdim
863239310Sdim  case Hexagon::JMP_cNot:
864239310Sdim    return Hexagon::JMP_cdnNotPt;
865239310Sdim
866239310Sdim  case Hexagon::JMPR_cPt:
867239310Sdim    return Hexagon::JMPR_cdnPt_V3;
868239310Sdim
869239310Sdim  case Hexagon::JMPR_cNotPt:
870239310Sdim    return Hexagon::JMPR_cdnNotPt_V3;
871239310Sdim
872239310Sdim  // Conditional Transfers
873239310Sdim  case Hexagon::TFR_cPt:
874239310Sdim    return Hexagon::TFR_cdnPt;
875239310Sdim
876239310Sdim  case Hexagon::TFR_cNotPt:
877239310Sdim    return Hexagon::TFR_cdnNotPt;
878239310Sdim
879239310Sdim  case Hexagon::TFRI_cPt:
880239310Sdim    return Hexagon::TFRI_cdnPt;
881239310Sdim
882239310Sdim  case Hexagon::TFRI_cNotPt:
883239310Sdim    return Hexagon::TFRI_cdnNotPt;
884239310Sdim
885239310Sdim  // Load double word
886239310Sdim  case Hexagon::LDrid_cPt :
887239310Sdim    return Hexagon::LDrid_cdnPt;
888239310Sdim
889239310Sdim  case Hexagon::LDrid_cNotPt :
890239310Sdim    return Hexagon::LDrid_cdnNotPt;
891239310Sdim
892239310Sdim  case Hexagon::LDrid_indexed_cPt :
893239310Sdim    return Hexagon::LDrid_indexed_cdnPt;
894239310Sdim
895239310Sdim  case Hexagon::LDrid_indexed_cNotPt :
896239310Sdim    return Hexagon::LDrid_indexed_cdnNotPt;
897239310Sdim
898239310Sdim  case Hexagon::POST_LDrid_cPt :
899239310Sdim    return Hexagon::POST_LDrid_cdnPt_V4;
900239310Sdim
901239310Sdim  case Hexagon::POST_LDrid_cNotPt :
902239310Sdim    return Hexagon::POST_LDrid_cdnNotPt_V4;
903239310Sdim
904239310Sdim  // Load word
905239310Sdim  case Hexagon::LDriw_cPt :
906239310Sdim    return Hexagon::LDriw_cdnPt;
907239310Sdim
908239310Sdim  case Hexagon::LDriw_cNotPt :
909239310Sdim    return Hexagon::LDriw_cdnNotPt;
910239310Sdim
911239310Sdim  case Hexagon::LDriw_indexed_cPt :
912239310Sdim    return Hexagon::LDriw_indexed_cdnPt;
913239310Sdim
914239310Sdim  case Hexagon::LDriw_indexed_cNotPt :
915239310Sdim    return Hexagon::LDriw_indexed_cdnNotPt;
916239310Sdim
917239310Sdim  case Hexagon::POST_LDriw_cPt :
918239310Sdim    return Hexagon::POST_LDriw_cdnPt_V4;
919239310Sdim
920239310Sdim  case Hexagon::POST_LDriw_cNotPt :
921239310Sdim    return Hexagon::POST_LDriw_cdnNotPt_V4;
922239310Sdim
923239310Sdim  // Load halfword
924239310Sdim  case Hexagon::LDrih_cPt :
925239310Sdim    return Hexagon::LDrih_cdnPt;
926239310Sdim
927239310Sdim  case Hexagon::LDrih_cNotPt :
928239310Sdim    return Hexagon::LDrih_cdnNotPt;
929239310Sdim
930239310Sdim  case Hexagon::LDrih_indexed_cPt :
931239310Sdim    return Hexagon::LDrih_indexed_cdnPt;
932239310Sdim
933239310Sdim  case Hexagon::LDrih_indexed_cNotPt :
934239310Sdim    return Hexagon::LDrih_indexed_cdnNotPt;
935239310Sdim
936239310Sdim  case Hexagon::POST_LDrih_cPt :
937239310Sdim    return Hexagon::POST_LDrih_cdnPt_V4;
938239310Sdim
939239310Sdim  case Hexagon::POST_LDrih_cNotPt :
940239310Sdim    return Hexagon::POST_LDrih_cdnNotPt_V4;
941239310Sdim
942239310Sdim  // Load byte
943239310Sdim  case Hexagon::LDrib_cPt :
944239310Sdim    return Hexagon::LDrib_cdnPt;
945239310Sdim
946239310Sdim  case Hexagon::LDrib_cNotPt :
947239310Sdim    return Hexagon::LDrib_cdnNotPt;
948239310Sdim
949239310Sdim  case Hexagon::LDrib_indexed_cPt :
950239310Sdim    return Hexagon::LDrib_indexed_cdnPt;
951239310Sdim
952239310Sdim  case Hexagon::LDrib_indexed_cNotPt :
953239310Sdim    return Hexagon::LDrib_indexed_cdnNotPt;
954239310Sdim
955239310Sdim  case Hexagon::POST_LDrib_cPt :
956239310Sdim    return Hexagon::POST_LDrib_cdnPt_V4;
957239310Sdim
958239310Sdim  case Hexagon::POST_LDrib_cNotPt :
959239310Sdim    return Hexagon::POST_LDrib_cdnNotPt_V4;
960239310Sdim
961239310Sdim  // Load unsigned halfword
962239310Sdim  case Hexagon::LDriuh_cPt :
963239310Sdim    return Hexagon::LDriuh_cdnPt;
964239310Sdim
965239310Sdim  case Hexagon::LDriuh_cNotPt :
966239310Sdim    return Hexagon::LDriuh_cdnNotPt;
967239310Sdim
968239310Sdim  case Hexagon::LDriuh_indexed_cPt :
969239310Sdim    return Hexagon::LDriuh_indexed_cdnPt;
970239310Sdim
971239310Sdim  case Hexagon::LDriuh_indexed_cNotPt :
972239310Sdim    return Hexagon::LDriuh_indexed_cdnNotPt;
973239310Sdim
974239310Sdim  case Hexagon::POST_LDriuh_cPt :
975239310Sdim    return Hexagon::POST_LDriuh_cdnPt_V4;
976239310Sdim
977239310Sdim  case Hexagon::POST_LDriuh_cNotPt :
978239310Sdim    return Hexagon::POST_LDriuh_cdnNotPt_V4;
979239310Sdim
980239310Sdim  // Load unsigned byte
981239310Sdim  case Hexagon::LDriub_cPt :
982239310Sdim    return Hexagon::LDriub_cdnPt;
983239310Sdim
984239310Sdim  case Hexagon::LDriub_cNotPt :
985239310Sdim    return Hexagon::LDriub_cdnNotPt;
986239310Sdim
987239310Sdim  case Hexagon::LDriub_indexed_cPt :
988239310Sdim    return Hexagon::LDriub_indexed_cdnPt;
989239310Sdim
990239310Sdim  case Hexagon::LDriub_indexed_cNotPt :
991239310Sdim    return Hexagon::LDriub_indexed_cdnNotPt;
992239310Sdim
993239310Sdim  case Hexagon::POST_LDriub_cPt :
994239310Sdim    return Hexagon::POST_LDriub_cdnPt_V4;
995239310Sdim
996239310Sdim  case Hexagon::POST_LDriub_cNotPt :
997239310Sdim    return Hexagon::POST_LDriub_cdnNotPt_V4;
998239310Sdim
999239310Sdim  // V4 indexed+scaled load
1000239310Sdim
1001239310Sdim  case Hexagon::LDrid_indexed_shl_cPt_V4 :
1002239310Sdim    return Hexagon::LDrid_indexed_shl_cdnPt_V4;
1003239310Sdim
1004239310Sdim  case Hexagon::LDrid_indexed_shl_cNotPt_V4 :
1005239310Sdim    return Hexagon::LDrid_indexed_shl_cdnNotPt_V4;
1006239310Sdim
1007239310Sdim  case Hexagon::LDrib_indexed_shl_cPt_V4 :
1008239310Sdim    return Hexagon::LDrib_indexed_shl_cdnPt_V4;
1009239310Sdim
1010239310Sdim  case Hexagon::LDrib_indexed_shl_cNotPt_V4 :
1011239310Sdim    return Hexagon::LDrib_indexed_shl_cdnNotPt_V4;
1012239310Sdim
1013239310Sdim  case Hexagon::LDriub_indexed_shl_cPt_V4 :
1014239310Sdim    return Hexagon::LDriub_indexed_shl_cdnPt_V4;
1015239310Sdim
1016239310Sdim  case Hexagon::LDriub_indexed_shl_cNotPt_V4 :
1017239310Sdim    return Hexagon::LDriub_indexed_shl_cdnNotPt_V4;
1018239310Sdim
1019239310Sdim  case Hexagon::LDrih_indexed_shl_cPt_V4 :
1020239310Sdim    return Hexagon::LDrih_indexed_shl_cdnPt_V4;
1021239310Sdim
1022239310Sdim  case Hexagon::LDrih_indexed_shl_cNotPt_V4 :
1023239310Sdim    return Hexagon::LDrih_indexed_shl_cdnNotPt_V4;
1024239310Sdim
1025239310Sdim  case Hexagon::LDriuh_indexed_shl_cPt_V4 :
1026239310Sdim    return Hexagon::LDriuh_indexed_shl_cdnPt_V4;
1027239310Sdim
1028239310Sdim  case Hexagon::LDriuh_indexed_shl_cNotPt_V4 :
1029239310Sdim    return Hexagon::LDriuh_indexed_shl_cdnNotPt_V4;
1030239310Sdim
1031239310Sdim  case Hexagon::LDriw_indexed_shl_cPt_V4 :
1032239310Sdim    return Hexagon::LDriw_indexed_shl_cdnPt_V4;
1033239310Sdim
1034239310Sdim  case Hexagon::LDriw_indexed_shl_cNotPt_V4 :
1035239310Sdim    return Hexagon::LDriw_indexed_shl_cdnNotPt_V4;
1036239310Sdim
1037239310Sdim  // V4 global address load
1038239310Sdim
1039239310Sdim  case Hexagon::LDd_GP_cPt_V4:
1040239310Sdim    return Hexagon::LDd_GP_cdnPt_V4;
1041239310Sdim
1042239310Sdim  case Hexagon::LDd_GP_cNotPt_V4:
1043239310Sdim    return Hexagon::LDd_GP_cdnNotPt_V4;
1044239310Sdim
1045239310Sdim  case Hexagon::LDb_GP_cPt_V4:
1046239310Sdim    return Hexagon::LDb_GP_cdnPt_V4;
1047239310Sdim
1048239310Sdim  case Hexagon::LDb_GP_cNotPt_V4:
1049239310Sdim    return Hexagon::LDb_GP_cdnNotPt_V4;
1050239310Sdim
1051239310Sdim  case Hexagon::LDub_GP_cPt_V4:
1052239310Sdim    return Hexagon::LDub_GP_cdnPt_V4;
1053239310Sdim
1054239310Sdim  case Hexagon::LDub_GP_cNotPt_V4:
1055239310Sdim    return Hexagon::LDub_GP_cdnNotPt_V4;
1056239310Sdim
1057239310Sdim  case Hexagon::LDh_GP_cPt_V4:
1058239310Sdim    return Hexagon::LDh_GP_cdnPt_V4;
1059239310Sdim
1060239310Sdim  case Hexagon::LDh_GP_cNotPt_V4:
1061239310Sdim    return Hexagon::LDh_GP_cdnNotPt_V4;
1062239310Sdim
1063239310Sdim  case Hexagon::LDuh_GP_cPt_V4:
1064239310Sdim    return Hexagon::LDuh_GP_cdnPt_V4;
1065239310Sdim
1066239310Sdim  case Hexagon::LDuh_GP_cNotPt_V4:
1067239310Sdim    return Hexagon::LDuh_GP_cdnNotPt_V4;
1068239310Sdim
1069239310Sdim  case Hexagon::LDw_GP_cPt_V4:
1070239310Sdim    return Hexagon::LDw_GP_cdnPt_V4;
1071239310Sdim
1072239310Sdim  case Hexagon::LDw_GP_cNotPt_V4:
1073239310Sdim    return Hexagon::LDw_GP_cdnNotPt_V4;
1074239310Sdim
1075239310Sdim  // Conditional store new-value byte
1076239310Sdim  case Hexagon::STrib_cPt_nv_V4 :
1077239310Sdim    return Hexagon::STrib_cdnPt_nv_V4;
1078239310Sdim  case Hexagon::STrib_cNotPt_nv_V4 :
1079239310Sdim    return Hexagon::STrib_cdnNotPt_nv_V4;
1080239310Sdim
1081239310Sdim  case Hexagon::STrib_indexed_cPt_nv_V4 :
1082239310Sdim    return Hexagon::STrib_indexed_cdnPt_nv_V4;
1083239310Sdim  case Hexagon::STrib_indexed_cNotPt_nv_V4 :
1084239310Sdim    return Hexagon::STrib_indexed_cdnNotPt_nv_V4;
1085239310Sdim
1086239310Sdim  case Hexagon::STrib_indexed_shl_cPt_nv_V4 :
1087239310Sdim    return Hexagon::STrib_indexed_shl_cdnPt_nv_V4;
1088239310Sdim  case Hexagon::STrib_indexed_shl_cNotPt_nv_V4 :
1089239310Sdim    return Hexagon::STrib_indexed_shl_cdnNotPt_nv_V4;
1090239310Sdim
1091239310Sdim  case Hexagon::POST_STbri_cPt_nv_V4 :
1092239310Sdim    return Hexagon::POST_STbri_cdnPt_nv_V4;
1093239310Sdim  case Hexagon::POST_STbri_cNotPt_nv_V4 :
1094239310Sdim    return Hexagon::POST_STbri_cdnNotPt_nv_V4;
1095239310Sdim
1096239310Sdim  case Hexagon::STb_GP_cPt_nv_V4 :
1097239310Sdim    return Hexagon::STb_GP_cdnPt_nv_V4;
1098239310Sdim
1099239310Sdim  case Hexagon::STb_GP_cNotPt_nv_V4 :
1100239310Sdim    return Hexagon::STb_GP_cdnNotPt_nv_V4;
1101239310Sdim
1102239310Sdim  // Conditional store new-value halfword
1103239310Sdim  case Hexagon::STrih_cPt_nv_V4 :
1104239310Sdim    return Hexagon::STrih_cdnPt_nv_V4;
1105239310Sdim  case Hexagon::STrih_cNotPt_nv_V4 :
1106239310Sdim    return Hexagon::STrih_cdnNotPt_nv_V4;
1107239310Sdim
1108239310Sdim  case Hexagon::STrih_indexed_cPt_nv_V4 :
1109239310Sdim    return Hexagon::STrih_indexed_cdnPt_nv_V4;
1110239310Sdim  case Hexagon::STrih_indexed_cNotPt_nv_V4 :
1111239310Sdim    return Hexagon::STrih_indexed_cdnNotPt_nv_V4;
1112239310Sdim
1113239310Sdim  case Hexagon::STrih_indexed_shl_cPt_nv_V4 :
1114239310Sdim    return Hexagon::STrih_indexed_shl_cdnPt_nv_V4;
1115239310Sdim  case Hexagon::STrih_indexed_shl_cNotPt_nv_V4 :
1116239310Sdim    return Hexagon::STrih_indexed_shl_cdnNotPt_nv_V4;
1117239310Sdim
1118239310Sdim  case Hexagon::POST_SThri_cPt_nv_V4 :
1119239310Sdim    return Hexagon::POST_SThri_cdnPt_nv_V4;
1120239310Sdim  case Hexagon::POST_SThri_cNotPt_nv_V4 :
1121239310Sdim    return Hexagon::POST_SThri_cdnNotPt_nv_V4;
1122239310Sdim
1123239310Sdim  case Hexagon::STh_GP_cPt_nv_V4 :
1124239310Sdim    return Hexagon::STh_GP_cdnPt_nv_V4;
1125239310Sdim
1126239310Sdim  case Hexagon::STh_GP_cNotPt_nv_V4 :
1127239310Sdim    return Hexagon::STh_GP_cdnNotPt_nv_V4;
1128239310Sdim
1129239310Sdim  // Conditional store new-value word
1130239310Sdim  case Hexagon::STriw_cPt_nv_V4 :
1131239310Sdim    return  Hexagon::STriw_cdnPt_nv_V4;
1132239310Sdim  case Hexagon::STriw_cNotPt_nv_V4 :
1133239310Sdim    return Hexagon::STriw_cdnNotPt_nv_V4;
1134239310Sdim
1135239310Sdim  case Hexagon::STriw_indexed_cPt_nv_V4 :
1136239310Sdim    return Hexagon::STriw_indexed_cdnPt_nv_V4;
1137239310Sdim  case Hexagon::STriw_indexed_cNotPt_nv_V4 :
1138239310Sdim    return Hexagon::STriw_indexed_cdnNotPt_nv_V4;
1139239310Sdim
1140239310Sdim  case Hexagon::STriw_indexed_shl_cPt_nv_V4 :
1141239310Sdim    return Hexagon::STriw_indexed_shl_cdnPt_nv_V4;
1142239310Sdim  case Hexagon::STriw_indexed_shl_cNotPt_nv_V4 :
1143239310Sdim    return Hexagon::STriw_indexed_shl_cdnNotPt_nv_V4;
1144239310Sdim
1145239310Sdim  case Hexagon::POST_STwri_cPt_nv_V4 :
1146239310Sdim    return Hexagon::POST_STwri_cdnPt_nv_V4;
1147239310Sdim  case Hexagon::POST_STwri_cNotPt_nv_V4:
1148239310Sdim    return Hexagon::POST_STwri_cdnNotPt_nv_V4;
1149239310Sdim
1150239310Sdim  case Hexagon::STw_GP_cPt_nv_V4 :
1151239310Sdim    return Hexagon::STw_GP_cdnPt_nv_V4;
1152239310Sdim
1153239310Sdim  case Hexagon::STw_GP_cNotPt_nv_V4 :
1154239310Sdim    return Hexagon::STw_GP_cdnNotPt_nv_V4;
1155239310Sdim
1156239310Sdim  // Conditional add
1157239310Sdim  case Hexagon::ADD_ri_cPt :
1158239310Sdim    return Hexagon::ADD_ri_cdnPt;
1159239310Sdim  case Hexagon::ADD_ri_cNotPt :
1160239310Sdim    return Hexagon::ADD_ri_cdnNotPt;
1161239310Sdim
1162239310Sdim  case Hexagon::ADD_rr_cPt :
1163239310Sdim    return Hexagon::ADD_rr_cdnPt;
1164239310Sdim  case Hexagon::ADD_rr_cNotPt :
1165239310Sdim    return Hexagon::ADD_rr_cdnNotPt;
1166239310Sdim
1167239310Sdim  // Conditional logical Operations
1168239310Sdim  case Hexagon::XOR_rr_cPt :
1169239310Sdim    return Hexagon::XOR_rr_cdnPt;
1170239310Sdim  case Hexagon::XOR_rr_cNotPt :
1171239310Sdim    return Hexagon::XOR_rr_cdnNotPt;
1172239310Sdim
1173239310Sdim  case Hexagon::AND_rr_cPt :
1174239310Sdim    return Hexagon::AND_rr_cdnPt;
1175239310Sdim  case Hexagon::AND_rr_cNotPt :
1176239310Sdim    return Hexagon::AND_rr_cdnNotPt;
1177239310Sdim
1178239310Sdim  case Hexagon::OR_rr_cPt :
1179239310Sdim    return Hexagon::OR_rr_cdnPt;
1180239310Sdim  case Hexagon::OR_rr_cNotPt :
1181239310Sdim    return Hexagon::OR_rr_cdnNotPt;
1182239310Sdim
1183239310Sdim  // Conditional Subtract
1184239310Sdim  case Hexagon::SUB_rr_cPt :
1185239310Sdim    return Hexagon::SUB_rr_cdnPt;
1186239310Sdim  case Hexagon::SUB_rr_cNotPt :
1187239310Sdim    return Hexagon::SUB_rr_cdnNotPt;
1188239310Sdim
1189239310Sdim  // Conditional combine
1190239310Sdim  case Hexagon::COMBINE_rr_cPt :
1191239310Sdim    return Hexagon::COMBINE_rr_cdnPt;
1192239310Sdim  case Hexagon::COMBINE_rr_cNotPt :
1193239310Sdim    return Hexagon::COMBINE_rr_cdnNotPt;
1194239310Sdim
1195239310Sdim  case Hexagon::ASLH_cPt_V4 :
1196239310Sdim    return Hexagon::ASLH_cdnPt_V4;
1197239310Sdim  case Hexagon::ASLH_cNotPt_V4 :
1198239310Sdim    return Hexagon::ASLH_cdnNotPt_V4;
1199239310Sdim
1200239310Sdim  case Hexagon::ASRH_cPt_V4 :
1201239310Sdim    return Hexagon::ASRH_cdnPt_V4;
1202239310Sdim  case Hexagon::ASRH_cNotPt_V4 :
1203239310Sdim    return Hexagon::ASRH_cdnNotPt_V4;
1204239310Sdim
1205239310Sdim  case Hexagon::SXTB_cPt_V4 :
1206239310Sdim    return Hexagon::SXTB_cdnPt_V4;
1207239310Sdim  case Hexagon::SXTB_cNotPt_V4 :
1208239310Sdim    return Hexagon::SXTB_cdnNotPt_V4;
1209239310Sdim
1210239310Sdim  case Hexagon::SXTH_cPt_V4 :
1211239310Sdim    return Hexagon::SXTH_cdnPt_V4;
1212239310Sdim  case Hexagon::SXTH_cNotPt_V4 :
1213239310Sdim    return Hexagon::SXTH_cdnNotPt_V4;
1214239310Sdim
1215239310Sdim  case Hexagon::ZXTB_cPt_V4 :
1216239310Sdim    return Hexagon::ZXTB_cdnPt_V4;
1217239310Sdim  case Hexagon::ZXTB_cNotPt_V4 :
1218239310Sdim    return Hexagon::ZXTB_cdnNotPt_V4;
1219239310Sdim
1220239310Sdim  case Hexagon::ZXTH_cPt_V4 :
1221239310Sdim    return Hexagon::ZXTH_cdnPt_V4;
1222239310Sdim  case Hexagon::ZXTH_cNotPt_V4 :
1223239310Sdim    return Hexagon::ZXTH_cdnNotPt_V4;
1224239310Sdim  }
1225239310Sdim}
1226239310Sdim
1227239310Sdim// Returns true if an instruction can be promoted to .new predicate
1228239310Sdim// or new-value store.
1229239310Sdimbool HexagonPacketizerList::isNewifiable(MachineInstr* MI) {
1230239310Sdim  if ( isCondInst(MI) || IsNewifyStore(MI))
1231239310Sdim    return true;
1232239310Sdim  else
1233239310Sdim    return false;
1234239310Sdim}
1235239310Sdim
1236239310Sdimbool HexagonPacketizerList::isCondInst (MachineInstr* MI) {
1237239310Sdim  const HexagonInstrInfo *QII = (const HexagonInstrInfo *) TII;
1238239310Sdim  const MCInstrDesc& TID = MI->getDesc();
1239239310Sdim                                    // bug 5670: until that is fixed,
1240239310Sdim                                    // this portion is disabled.
1241239310Sdim  if (   TID.isConditionalBranch()  // && !IsRegisterJump(MI)) ||
1242239310Sdim      || QII->isConditionalTransfer(MI)
1243239310Sdim      || QII->isConditionalALU32(MI)
1244239310Sdim      || QII->isConditionalLoad(MI)
1245239310Sdim      || QII->isConditionalStore(MI)) {
1246239310Sdim    return true;
1247239310Sdim  }
1248239310Sdim  return false;
1249239310Sdim}
1250239310Sdim
1251239310Sdim
1252239310Sdim// Promote an instructiont to its .new form.
1253239310Sdim// At this time, we have already made a call to CanPromoteToDotNew
1254239310Sdim// and made sure that it can *indeed* be promoted.
1255239310Sdimbool HexagonPacketizerList::PromoteToDotNew(MachineInstr* MI,
1256239310Sdim                        SDep::Kind DepType, MachineBasicBlock::iterator &MII,
1257239310Sdim                        const TargetRegisterClass* RC) {
1258239310Sdim
1259239310Sdim  assert (DepType == SDep::Data);
1260239310Sdim  const HexagonInstrInfo *QII = (const HexagonInstrInfo *) TII;
1261239310Sdim
1262239310Sdim  int NewOpcode;
1263239310Sdim  if (RC == &Hexagon::PredRegsRegClass)
1264239310Sdim    NewOpcode = GetDotNewPredOp(MI->getOpcode());
1265239310Sdim  else
1266239310Sdim    NewOpcode = GetDotNewOp(MI->getOpcode());
1267239310Sdim  MI->setDesc(QII->get(NewOpcode));
1268239310Sdim
1269239310Sdim  return true;
1270239310Sdim}
1271239310Sdim
1272239310Sdim// Returns the most basic instruction for the .new predicated instructions and
1273239310Sdim// new-value stores.
1274239310Sdim// For example, all of the following instructions will be converted back to the
1275239310Sdim// same instruction:
1276239310Sdim// 1) if (p0.new) memw(R0+#0) = R1.new  --->
1277239310Sdim// 2) if (p0) memw(R0+#0)= R1.new      -------> if (p0) memw(R0+#0) = R1
1278239310Sdim// 3) if (p0.new) memw(R0+#0) = R1      --->
1279239310Sdim//
1280239310Sdim// To understand the translation of instruction 1 to its original form, consider
1281239310Sdim// a packet with 3 instructions.
1282239310Sdim// { p0 = cmp.eq(R0,R1)
1283239310Sdim//   if (p0.new) R2 = add(R3, R4)
1284239310Sdim//   R5 = add (R3, R1)
1285239310Sdim//   }
1286239310Sdim// if (p0) memw(R5+#0) = R2 <--- trying to include it in the previous packet
1287239310Sdim//
1288239310Sdim// This instruction can be part of the previous packet only if both p0 and R2
1289239310Sdim// are promoted to .new values. This promotion happens in steps, first
1290239310Sdim// predicate register is promoted to .new and in the next iteration R2 is
1291239310Sdim// promoted. Therefore, in case of dependence check failure (due to R5) during
1292239310Sdim// next iteration, it should be converted back to its most basic form.
1293239310Sdim
1294239310Sdimstatic int GetDotOldOp(const int opc) {
1295239310Sdim  switch (opc) {
1296239310Sdim  default: llvm_unreachable("Unknown .old type");
1297239310Sdim  case Hexagon::TFR_cdnPt:
1298239310Sdim    return Hexagon::TFR_cPt;
1299239310Sdim
1300239310Sdim  case Hexagon::TFR_cdnNotPt:
1301239310Sdim    return Hexagon::TFR_cNotPt;
1302239310Sdim
1303239310Sdim  case Hexagon::TFRI_cdnPt:
1304239310Sdim    return Hexagon::TFRI_cPt;
1305239310Sdim
1306239310Sdim  case Hexagon::TFRI_cdnNotPt:
1307239310Sdim    return Hexagon::TFRI_cNotPt;
1308239310Sdim
1309239310Sdim  case Hexagon::JMP_cdnPt:
1310239310Sdim    return Hexagon::JMP_c;
1311239310Sdim
1312239310Sdim  case Hexagon::JMP_cdnNotPt:
1313239310Sdim    return Hexagon::JMP_cNot;
1314239310Sdim
1315239310Sdim  case Hexagon::JMPR_cdnPt_V3:
1316239310Sdim    return Hexagon::JMPR_cPt;
1317239310Sdim
1318239310Sdim  case Hexagon::JMPR_cdnNotPt_V3:
1319239310Sdim    return Hexagon::JMPR_cNotPt;
1320239310Sdim
1321239310Sdim  // Load double word
1322239310Sdim
1323239310Sdim  case Hexagon::LDrid_cdnPt :
1324239310Sdim    return Hexagon::LDrid_cPt;
1325239310Sdim
1326239310Sdim  case Hexagon::LDrid_cdnNotPt :
1327239310Sdim    return Hexagon::LDrid_cNotPt;
1328239310Sdim
1329239310Sdim  case Hexagon::LDrid_indexed_cdnPt :
1330239310Sdim    return Hexagon::LDrid_indexed_cPt;
1331239310Sdim
1332239310Sdim  case Hexagon::LDrid_indexed_cdnNotPt :
1333239310Sdim    return Hexagon::LDrid_indexed_cNotPt;
1334239310Sdim
1335239310Sdim  case Hexagon::POST_LDrid_cdnPt_V4 :
1336239310Sdim    return Hexagon::POST_LDrid_cPt;
1337239310Sdim
1338239310Sdim  case Hexagon::POST_LDrid_cdnNotPt_V4 :
1339239310Sdim    return Hexagon::POST_LDrid_cNotPt;
1340239310Sdim
1341239310Sdim  // Load word
1342239310Sdim
1343239310Sdim  case Hexagon::LDriw_cdnPt :
1344239310Sdim    return Hexagon::LDriw_cPt;
1345239310Sdim
1346239310Sdim  case Hexagon::LDriw_cdnNotPt :
1347239310Sdim    return Hexagon::LDriw_cNotPt;
1348239310Sdim
1349239310Sdim  case Hexagon::LDriw_indexed_cdnPt :
1350239310Sdim    return Hexagon::LDriw_indexed_cPt;
1351239310Sdim
1352239310Sdim  case Hexagon::LDriw_indexed_cdnNotPt :
1353239310Sdim    return Hexagon::LDriw_indexed_cNotPt;
1354239310Sdim
1355239310Sdim  case Hexagon::POST_LDriw_cdnPt_V4 :
1356239310Sdim    return Hexagon::POST_LDriw_cPt;
1357239310Sdim
1358239310Sdim  case Hexagon::POST_LDriw_cdnNotPt_V4 :
1359239310Sdim    return Hexagon::POST_LDriw_cNotPt;
1360239310Sdim
1361239310Sdim  // Load half
1362239310Sdim
1363239310Sdim  case Hexagon::LDrih_cdnPt :
1364239310Sdim    return Hexagon::LDrih_cPt;
1365239310Sdim
1366239310Sdim  case Hexagon::LDrih_cdnNotPt :
1367239310Sdim    return Hexagon::LDrih_cNotPt;
1368239310Sdim
1369239310Sdim  case Hexagon::LDrih_indexed_cdnPt :
1370239310Sdim    return Hexagon::LDrih_indexed_cPt;
1371239310Sdim
1372239310Sdim  case Hexagon::LDrih_indexed_cdnNotPt :
1373239310Sdim    return Hexagon::LDrih_indexed_cNotPt;
1374239310Sdim
1375239310Sdim  case Hexagon::POST_LDrih_cdnPt_V4 :
1376239310Sdim    return Hexagon::POST_LDrih_cPt;
1377239310Sdim
1378239310Sdim  case Hexagon::POST_LDrih_cdnNotPt_V4 :
1379239310Sdim    return Hexagon::POST_LDrih_cNotPt;
1380239310Sdim
1381239310Sdim  // Load byte
1382239310Sdim
1383239310Sdim  case Hexagon::LDrib_cdnPt :
1384239310Sdim    return Hexagon::LDrib_cPt;
1385239310Sdim
1386239310Sdim  case Hexagon::LDrib_cdnNotPt :
1387239310Sdim    return Hexagon::LDrib_cNotPt;
1388239310Sdim
1389239310Sdim  case Hexagon::LDrib_indexed_cdnPt :
1390239310Sdim    return Hexagon::LDrib_indexed_cPt;
1391239310Sdim
1392239310Sdim  case Hexagon::LDrib_indexed_cdnNotPt :
1393239310Sdim    return Hexagon::LDrib_indexed_cNotPt;
1394239310Sdim
1395239310Sdim  case Hexagon::POST_LDrib_cdnPt_V4 :
1396239310Sdim    return Hexagon::POST_LDrib_cPt;
1397239310Sdim
1398239310Sdim  case Hexagon::POST_LDrib_cdnNotPt_V4 :
1399239310Sdim    return Hexagon::POST_LDrib_cNotPt;
1400239310Sdim
1401239310Sdim  // Load unsigned half
1402239310Sdim
1403239310Sdim  case Hexagon::LDriuh_cdnPt :
1404239310Sdim    return Hexagon::LDriuh_cPt;
1405239310Sdim
1406239310Sdim  case Hexagon::LDriuh_cdnNotPt :
1407239310Sdim    return Hexagon::LDriuh_cNotPt;
1408239310Sdim
1409239310Sdim  case Hexagon::LDriuh_indexed_cdnPt :
1410239310Sdim    return Hexagon::LDriuh_indexed_cPt;
1411239310Sdim
1412239310Sdim  case Hexagon::LDriuh_indexed_cdnNotPt :
1413239310Sdim    return Hexagon::LDriuh_indexed_cNotPt;
1414239310Sdim
1415239310Sdim  case Hexagon::POST_LDriuh_cdnPt_V4 :
1416239310Sdim    return Hexagon::POST_LDriuh_cPt;
1417239310Sdim
1418239310Sdim  case Hexagon::POST_LDriuh_cdnNotPt_V4 :
1419239310Sdim    return Hexagon::POST_LDriuh_cNotPt;
1420239310Sdim
1421239310Sdim  // Load unsigned byte
1422239310Sdim  case Hexagon::LDriub_cdnPt :
1423239310Sdim    return Hexagon::LDriub_cPt;
1424239310Sdim
1425239310Sdim  case Hexagon::LDriub_cdnNotPt :
1426239310Sdim    return Hexagon::LDriub_cNotPt;
1427239310Sdim
1428239310Sdim  case Hexagon::LDriub_indexed_cdnPt :
1429239310Sdim    return Hexagon::LDriub_indexed_cPt;
1430239310Sdim
1431239310Sdim  case Hexagon::LDriub_indexed_cdnNotPt :
1432239310Sdim    return Hexagon::LDriub_indexed_cNotPt;
1433239310Sdim
1434239310Sdim  case Hexagon::POST_LDriub_cdnPt_V4 :
1435239310Sdim    return Hexagon::POST_LDriub_cPt;
1436239310Sdim
1437239310Sdim  case Hexagon::POST_LDriub_cdnNotPt_V4 :
1438239310Sdim    return Hexagon::POST_LDriub_cNotPt;
1439239310Sdim
1440239310Sdim  // V4 indexed+scaled Load
1441239310Sdim
1442239310Sdim  case Hexagon::LDrid_indexed_shl_cdnPt_V4 :
1443239310Sdim    return Hexagon::LDrid_indexed_shl_cPt_V4;
1444239310Sdim
1445239310Sdim  case Hexagon::LDrid_indexed_shl_cdnNotPt_V4 :
1446239310Sdim    return Hexagon::LDrid_indexed_shl_cNotPt_V4;
1447239310Sdim
1448239310Sdim  case Hexagon::LDrib_indexed_shl_cdnPt_V4 :
1449239310Sdim    return Hexagon::LDrib_indexed_shl_cPt_V4;
1450239310Sdim
1451239310Sdim  case Hexagon::LDrib_indexed_shl_cdnNotPt_V4 :
1452239310Sdim    return Hexagon::LDrib_indexed_shl_cNotPt_V4;
1453239310Sdim
1454239310Sdim  case Hexagon::LDriub_indexed_shl_cdnPt_V4 :
1455239310Sdim    return Hexagon::LDriub_indexed_shl_cPt_V4;
1456239310Sdim
1457239310Sdim  case Hexagon::LDriub_indexed_shl_cdnNotPt_V4 :
1458239310Sdim    return Hexagon::LDriub_indexed_shl_cNotPt_V4;
1459239310Sdim
1460239310Sdim  case Hexagon::LDrih_indexed_shl_cdnPt_V4 :
1461239310Sdim    return Hexagon::LDrih_indexed_shl_cPt_V4;
1462239310Sdim
1463239310Sdim  case Hexagon::LDrih_indexed_shl_cdnNotPt_V4 :
1464239310Sdim    return Hexagon::LDrih_indexed_shl_cNotPt_V4;
1465239310Sdim
1466239310Sdim  case Hexagon::LDriuh_indexed_shl_cdnPt_V4 :
1467239310Sdim    return Hexagon::LDriuh_indexed_shl_cPt_V4;
1468239310Sdim
1469239310Sdim  case Hexagon::LDriuh_indexed_shl_cdnNotPt_V4 :
1470239310Sdim    return Hexagon::LDriuh_indexed_shl_cNotPt_V4;
1471239310Sdim
1472239310Sdim  case Hexagon::LDriw_indexed_shl_cdnPt_V4 :
1473239310Sdim    return Hexagon::LDriw_indexed_shl_cPt_V4;
1474239310Sdim
1475239310Sdim  case Hexagon::LDriw_indexed_shl_cdnNotPt_V4 :
1476239310Sdim    return Hexagon::LDriw_indexed_shl_cNotPt_V4;
1477239310Sdim
1478239310Sdim  // V4 global address load
1479239310Sdim
1480239310Sdim  case Hexagon::LDd_GP_cdnPt_V4:
1481239310Sdim    return Hexagon::LDd_GP_cPt_V4;
1482239310Sdim
1483239310Sdim  case Hexagon::LDd_GP_cdnNotPt_V4:
1484239310Sdim    return Hexagon::LDd_GP_cNotPt_V4;
1485239310Sdim
1486239310Sdim  case Hexagon::LDb_GP_cdnPt_V4:
1487239310Sdim    return Hexagon::LDb_GP_cPt_V4;
1488239310Sdim
1489239310Sdim  case Hexagon::LDb_GP_cdnNotPt_V4:
1490239310Sdim    return Hexagon::LDb_GP_cNotPt_V4;
1491239310Sdim
1492239310Sdim  case Hexagon::LDub_GP_cdnPt_V4:
1493239310Sdim    return Hexagon::LDub_GP_cPt_V4;
1494239310Sdim
1495239310Sdim  case Hexagon::LDub_GP_cdnNotPt_V4:
1496239310Sdim    return Hexagon::LDub_GP_cNotPt_V4;
1497239310Sdim
1498239310Sdim  case Hexagon::LDh_GP_cdnPt_V4:
1499239310Sdim    return Hexagon::LDh_GP_cPt_V4;
1500239310Sdim
1501239310Sdim  case Hexagon::LDh_GP_cdnNotPt_V4:
1502239310Sdim    return Hexagon::LDh_GP_cNotPt_V4;
1503239310Sdim
1504239310Sdim  case Hexagon::LDuh_GP_cdnPt_V4:
1505239310Sdim    return Hexagon::LDuh_GP_cPt_V4;
1506239310Sdim
1507239310Sdim  case Hexagon::LDuh_GP_cdnNotPt_V4:
1508239310Sdim    return Hexagon::LDuh_GP_cNotPt_V4;
1509239310Sdim
1510239310Sdim  case Hexagon::LDw_GP_cdnPt_V4:
1511239310Sdim    return Hexagon::LDw_GP_cPt_V4;
1512239310Sdim
1513239310Sdim  case Hexagon::LDw_GP_cdnNotPt_V4:
1514239310Sdim    return Hexagon::LDw_GP_cNotPt_V4;
1515239310Sdim
1516239310Sdim  // Conditional add
1517239310Sdim
1518239310Sdim  case Hexagon::ADD_ri_cdnPt :
1519239310Sdim    return Hexagon::ADD_ri_cPt;
1520239310Sdim  case Hexagon::ADD_ri_cdnNotPt :
1521239310Sdim    return Hexagon::ADD_ri_cNotPt;
1522239310Sdim
1523239310Sdim  case Hexagon::ADD_rr_cdnPt :
1524239310Sdim    return Hexagon::ADD_rr_cPt;
1525239310Sdim  case Hexagon::ADD_rr_cdnNotPt:
1526239310Sdim    return Hexagon::ADD_rr_cNotPt;
1527239310Sdim
1528239310Sdim  // Conditional logical Operations
1529239310Sdim
1530239310Sdim  case Hexagon::XOR_rr_cdnPt :
1531239310Sdim    return Hexagon::XOR_rr_cPt;
1532239310Sdim  case Hexagon::XOR_rr_cdnNotPt :
1533239310Sdim    return Hexagon::XOR_rr_cNotPt;
1534239310Sdim
1535239310Sdim  case Hexagon::AND_rr_cdnPt :
1536239310Sdim    return Hexagon::AND_rr_cPt;
1537239310Sdim  case Hexagon::AND_rr_cdnNotPt :
1538239310Sdim    return Hexagon::AND_rr_cNotPt;
1539239310Sdim
1540239310Sdim  case Hexagon::OR_rr_cdnPt :
1541239310Sdim    return Hexagon::OR_rr_cPt;
1542239310Sdim  case Hexagon::OR_rr_cdnNotPt :
1543239310Sdim    return Hexagon::OR_rr_cNotPt;
1544239310Sdim
1545239310Sdim  // Conditional Subtract
1546239310Sdim
1547239310Sdim  case Hexagon::SUB_rr_cdnPt :
1548239310Sdim    return Hexagon::SUB_rr_cPt;
1549239310Sdim  case Hexagon::SUB_rr_cdnNotPt :
1550239310Sdim    return Hexagon::SUB_rr_cNotPt;
1551239310Sdim
1552239310Sdim  // Conditional combine
1553239310Sdim
1554239310Sdim  case Hexagon::COMBINE_rr_cdnPt :
1555239310Sdim    return Hexagon::COMBINE_rr_cPt;
1556239310Sdim  case Hexagon::COMBINE_rr_cdnNotPt :
1557239310Sdim    return Hexagon::COMBINE_rr_cNotPt;
1558239310Sdim
1559239310Sdim// Conditional shift operations
1560239310Sdim
1561239310Sdim  case Hexagon::ASLH_cdnPt_V4 :
1562239310Sdim    return Hexagon::ASLH_cPt_V4;
1563239310Sdim  case Hexagon::ASLH_cdnNotPt_V4 :
1564239310Sdim    return Hexagon::ASLH_cNotPt_V4;
1565239310Sdim
1566239310Sdim  case Hexagon::ASRH_cdnPt_V4 :
1567239310Sdim    return Hexagon::ASRH_cPt_V4;
1568239310Sdim  case Hexagon::ASRH_cdnNotPt_V4 :
1569239310Sdim    return Hexagon::ASRH_cNotPt_V4;
1570239310Sdim
1571239310Sdim  case Hexagon::SXTB_cdnPt_V4 :
1572239310Sdim    return Hexagon::SXTB_cPt_V4;
1573239310Sdim  case Hexagon::SXTB_cdnNotPt_V4 :
1574239310Sdim    return Hexagon::SXTB_cNotPt_V4;
1575239310Sdim
1576239310Sdim  case Hexagon::SXTH_cdnPt_V4 :
1577239310Sdim    return Hexagon::SXTH_cPt_V4;
1578239310Sdim  case Hexagon::SXTH_cdnNotPt_V4 :
1579239310Sdim    return Hexagon::SXTH_cNotPt_V4;
1580239310Sdim
1581239310Sdim  case Hexagon::ZXTB_cdnPt_V4 :
1582239310Sdim    return Hexagon::ZXTB_cPt_V4;
1583239310Sdim  case Hexagon::ZXTB_cdnNotPt_V4 :
1584239310Sdim    return Hexagon::ZXTB_cNotPt_V4;
1585239310Sdim
1586239310Sdim  case Hexagon::ZXTH_cdnPt_V4 :
1587239310Sdim    return Hexagon::ZXTH_cPt_V4;
1588239310Sdim  case Hexagon::ZXTH_cdnNotPt_V4 :
1589239310Sdim    return Hexagon::ZXTH_cNotPt_V4;
1590239310Sdim
1591239310Sdim  // Store byte
1592239310Sdim
1593239310Sdim  case Hexagon::STrib_imm_cdnPt_V4 :
1594239310Sdim    return Hexagon::STrib_imm_cPt_V4;
1595239310Sdim
1596239310Sdim  case Hexagon::STrib_imm_cdnNotPt_V4 :
1597239310Sdim    return Hexagon::STrib_imm_cNotPt_V4;
1598239310Sdim
1599239310Sdim  case Hexagon::STrib_cdnPt_nv_V4 :
1600239310Sdim  case Hexagon::STrib_cPt_nv_V4 :
1601239310Sdim  case Hexagon::STrib_cdnPt_V4 :
1602239310Sdim    return Hexagon::STrib_cPt;
1603239310Sdim
1604239310Sdim  case Hexagon::STrib_cdnNotPt_nv_V4 :
1605239310Sdim  case Hexagon::STrib_cNotPt_nv_V4 :
1606239310Sdim  case Hexagon::STrib_cdnNotPt_V4 :
1607239310Sdim    return Hexagon::STrib_cNotPt;
1608239310Sdim
1609239310Sdim  case Hexagon::STrib_indexed_cdnPt_V4 :
1610239310Sdim  case Hexagon::STrib_indexed_cPt_nv_V4 :
1611239310Sdim  case Hexagon::STrib_indexed_cdnPt_nv_V4 :
1612239310Sdim    return Hexagon::STrib_indexed_cPt;
1613239310Sdim
1614239310Sdim  case Hexagon::STrib_indexed_cdnNotPt_V4 :
1615239310Sdim  case Hexagon::STrib_indexed_cNotPt_nv_V4 :
1616239310Sdim  case Hexagon::STrib_indexed_cdnNotPt_nv_V4 :
1617239310Sdim    return Hexagon::STrib_indexed_cNotPt;
1618239310Sdim
1619239310Sdim  case Hexagon::STrib_indexed_shl_cdnPt_nv_V4:
1620239310Sdim  case Hexagon::STrib_indexed_shl_cPt_nv_V4 :
1621239310Sdim  case Hexagon::STrib_indexed_shl_cdnPt_V4 :
1622239310Sdim    return Hexagon::STrib_indexed_shl_cPt_V4;
1623239310Sdim
1624239310Sdim  case Hexagon::STrib_indexed_shl_cdnNotPt_nv_V4:
1625239310Sdim  case Hexagon::STrib_indexed_shl_cNotPt_nv_V4 :
1626239310Sdim  case Hexagon::STrib_indexed_shl_cdnNotPt_V4 :
1627239310Sdim    return Hexagon::STrib_indexed_shl_cNotPt_V4;
1628239310Sdim
1629239310Sdim  case Hexagon::POST_STbri_cdnPt_nv_V4 :
1630239310Sdim  case Hexagon::POST_STbri_cPt_nv_V4 :
1631239310Sdim  case Hexagon::POST_STbri_cdnPt_V4 :
1632239310Sdim    return Hexagon::POST_STbri_cPt;
1633239310Sdim
1634239310Sdim  case Hexagon::POST_STbri_cdnNotPt_nv_V4 :
1635239310Sdim  case Hexagon::POST_STbri_cNotPt_nv_V4:
1636239310Sdim  case Hexagon::POST_STbri_cdnNotPt_V4 :
1637239310Sdim    return Hexagon::POST_STbri_cNotPt;
1638239310Sdim
1639239310Sdim  case Hexagon::STb_GP_cdnPt_nv_V4:
1640239310Sdim  case Hexagon::STb_GP_cdnPt_V4:
1641239310Sdim  case Hexagon::STb_GP_cPt_nv_V4:
1642239310Sdim    return Hexagon::STb_GP_cPt_V4;
1643239310Sdim
1644239310Sdim  case Hexagon::STb_GP_cdnNotPt_nv_V4:
1645239310Sdim  case Hexagon::STb_GP_cdnNotPt_V4:
1646239310Sdim  case Hexagon::STb_GP_cNotPt_nv_V4:
1647239310Sdim    return Hexagon::STb_GP_cNotPt_V4;
1648239310Sdim
1649239310Sdim  // Store new-value byte - unconditional
1650239310Sdim  case Hexagon::STrib_nv_V4:
1651239310Sdim    return Hexagon::STrib;
1652239310Sdim
1653239310Sdim  case Hexagon::STrib_indexed_nv_V4:
1654239310Sdim    return Hexagon::STrib_indexed;
1655239310Sdim
1656239310Sdim  case Hexagon::STrib_indexed_shl_nv_V4:
1657239310Sdim    return Hexagon::STrib_indexed_shl_V4;
1658239310Sdim
1659239310Sdim  case Hexagon::STrib_shl_nv_V4:
1660239310Sdim    return Hexagon::STrib_shl_V4;
1661239310Sdim
1662239310Sdim  case Hexagon::STb_GP_nv_V4:
1663239310Sdim    return Hexagon::STb_GP_V4;
1664239310Sdim
1665239310Sdim  case Hexagon::POST_STbri_nv_V4:
1666239310Sdim    return Hexagon::POST_STbri;
1667239310Sdim
1668239310Sdim  // Store halfword
1669239310Sdim  case Hexagon::STrih_imm_cdnPt_V4 :
1670239310Sdim    return Hexagon::STrih_imm_cPt_V4;
1671239310Sdim
1672239310Sdim  case Hexagon::STrih_imm_cdnNotPt_V4 :
1673239310Sdim    return Hexagon::STrih_imm_cNotPt_V4;
1674239310Sdim
1675239310Sdim  case Hexagon::STrih_cdnPt_nv_V4 :
1676239310Sdim  case Hexagon::STrih_cPt_nv_V4 :
1677239310Sdim  case Hexagon::STrih_cdnPt_V4 :
1678239310Sdim    return Hexagon::STrih_cPt;
1679239310Sdim
1680239310Sdim  case Hexagon::STrih_cdnNotPt_nv_V4 :
1681239310Sdim  case Hexagon::STrih_cNotPt_nv_V4 :
1682239310Sdim  case Hexagon::STrih_cdnNotPt_V4 :
1683239310Sdim    return Hexagon::STrih_cNotPt;
1684239310Sdim
1685239310Sdim  case Hexagon::STrih_indexed_cdnPt_nv_V4:
1686239310Sdim  case Hexagon::STrih_indexed_cPt_nv_V4 :
1687239310Sdim  case Hexagon::STrih_indexed_cdnPt_V4 :
1688239310Sdim    return Hexagon::STrih_indexed_cPt;
1689239310Sdim
1690239310Sdim  case Hexagon::STrih_indexed_cdnNotPt_nv_V4:
1691239310Sdim  case Hexagon::STrih_indexed_cNotPt_nv_V4 :
1692239310Sdim  case Hexagon::STrih_indexed_cdnNotPt_V4 :
1693239310Sdim    return Hexagon::STrih_indexed_cNotPt;
1694239310Sdim
1695239310Sdim  case Hexagon::STrih_indexed_shl_cdnPt_nv_V4 :
1696239310Sdim  case Hexagon::STrih_indexed_shl_cPt_nv_V4 :
1697239310Sdim  case Hexagon::STrih_indexed_shl_cdnPt_V4 :
1698239310Sdim    return Hexagon::STrih_indexed_shl_cPt_V4;
1699239310Sdim
1700239310Sdim  case Hexagon::STrih_indexed_shl_cdnNotPt_nv_V4 :
1701239310Sdim  case Hexagon::STrih_indexed_shl_cNotPt_nv_V4 :
1702239310Sdim  case Hexagon::STrih_indexed_shl_cdnNotPt_V4 :
1703239310Sdim    return Hexagon::STrih_indexed_shl_cNotPt_V4;
1704239310Sdim
1705239310Sdim  case Hexagon::POST_SThri_cdnPt_nv_V4 :
1706239310Sdim  case Hexagon::POST_SThri_cPt_nv_V4 :
1707239310Sdim  case Hexagon::POST_SThri_cdnPt_V4 :
1708239310Sdim    return Hexagon::POST_SThri_cPt;
1709239310Sdim
1710239310Sdim  case Hexagon::POST_SThri_cdnNotPt_nv_V4 :
1711239310Sdim  case Hexagon::POST_SThri_cNotPt_nv_V4 :
1712239310Sdim  case Hexagon::POST_SThri_cdnNotPt_V4 :
1713239310Sdim    return Hexagon::POST_SThri_cNotPt;
1714239310Sdim
1715239310Sdim  case Hexagon::STh_GP_cdnPt_nv_V4:
1716239310Sdim  case Hexagon::STh_GP_cdnPt_V4:
1717239310Sdim  case Hexagon::STh_GP_cPt_nv_V4:
1718239310Sdim    return Hexagon::STh_GP_cPt_V4;
1719239310Sdim
1720239310Sdim  case Hexagon::STh_GP_cdnNotPt_nv_V4:
1721239310Sdim  case Hexagon::STh_GP_cdnNotPt_V4:
1722239310Sdim  case Hexagon::STh_GP_cNotPt_nv_V4:
1723239310Sdim    return Hexagon::STh_GP_cNotPt_V4;
1724239310Sdim
1725239310Sdim  // Store new-value halfword - unconditional
1726239310Sdim
1727239310Sdim  case Hexagon::STrih_nv_V4:
1728239310Sdim    return Hexagon::STrih;
1729239310Sdim
1730239310Sdim  case Hexagon::STrih_indexed_nv_V4:
1731239310Sdim    return Hexagon::STrih_indexed;
1732239310Sdim
1733239310Sdim  case Hexagon::STrih_indexed_shl_nv_V4:
1734239310Sdim    return Hexagon::STrih_indexed_shl_V4;
1735239310Sdim
1736239310Sdim  case Hexagon::STrih_shl_nv_V4:
1737239310Sdim    return Hexagon::STrih_shl_V4;
1738239310Sdim
1739239310Sdim  case Hexagon::STh_GP_nv_V4:
1740239310Sdim    return Hexagon::STh_GP_V4;
1741239310Sdim
1742239310Sdim  case Hexagon::POST_SThri_nv_V4:
1743239310Sdim    return Hexagon::POST_SThri;
1744239310Sdim
1745239310Sdim   // Store word
1746239310Sdim
1747239310Sdim   case Hexagon::STriw_imm_cdnPt_V4 :
1748239310Sdim    return Hexagon::STriw_imm_cPt_V4;
1749239310Sdim
1750239310Sdim  case Hexagon::STriw_imm_cdnNotPt_V4 :
1751239310Sdim    return Hexagon::STriw_imm_cNotPt_V4;
1752239310Sdim
1753239310Sdim  case Hexagon::STriw_cdnPt_nv_V4 :
1754239310Sdim  case Hexagon::STriw_cPt_nv_V4 :
1755239310Sdim  case Hexagon::STriw_cdnPt_V4 :
1756239310Sdim    return Hexagon::STriw_cPt;
1757239310Sdim
1758239310Sdim  case Hexagon::STriw_cdnNotPt_nv_V4 :
1759239310Sdim  case Hexagon::STriw_cNotPt_nv_V4 :
1760239310Sdim  case Hexagon::STriw_cdnNotPt_V4 :
1761239310Sdim    return Hexagon::STriw_cNotPt;
1762239310Sdim
1763239310Sdim  case Hexagon::STriw_indexed_cdnPt_nv_V4 :
1764239310Sdim  case Hexagon::STriw_indexed_cPt_nv_V4 :
1765239310Sdim  case Hexagon::STriw_indexed_cdnPt_V4 :
1766239310Sdim    return Hexagon::STriw_indexed_cPt;
1767239310Sdim
1768239310Sdim  case Hexagon::STriw_indexed_cdnNotPt_nv_V4 :
1769239310Sdim  case Hexagon::STriw_indexed_cNotPt_nv_V4 :
1770239310Sdim  case Hexagon::STriw_indexed_cdnNotPt_V4 :
1771239310Sdim    return Hexagon::STriw_indexed_cNotPt;
1772239310Sdim
1773239310Sdim  case Hexagon::STriw_indexed_shl_cdnPt_nv_V4 :
1774239310Sdim  case Hexagon::STriw_indexed_shl_cPt_nv_V4 :
1775239310Sdim  case Hexagon::STriw_indexed_shl_cdnPt_V4 :
1776239310Sdim    return Hexagon::STriw_indexed_shl_cPt_V4;
1777239310Sdim
1778239310Sdim  case Hexagon::STriw_indexed_shl_cdnNotPt_nv_V4 :
1779239310Sdim  case Hexagon::STriw_indexed_shl_cNotPt_nv_V4 :
1780239310Sdim  case Hexagon::STriw_indexed_shl_cdnNotPt_V4 :
1781239310Sdim    return Hexagon::STriw_indexed_shl_cNotPt_V4;
1782239310Sdim
1783239310Sdim  case Hexagon::POST_STwri_cdnPt_nv_V4 :
1784239310Sdim  case Hexagon::POST_STwri_cPt_nv_V4 :
1785239310Sdim  case Hexagon::POST_STwri_cdnPt_V4 :
1786239310Sdim    return Hexagon::POST_STwri_cPt;
1787239310Sdim
1788239310Sdim  case Hexagon::POST_STwri_cdnNotPt_nv_V4 :
1789239310Sdim  case Hexagon::POST_STwri_cNotPt_nv_V4 :
1790239310Sdim  case Hexagon::POST_STwri_cdnNotPt_V4 :
1791239310Sdim    return Hexagon::POST_STwri_cNotPt;
1792239310Sdim
1793239310Sdim  case Hexagon::STw_GP_cdnPt_nv_V4:
1794239310Sdim  case Hexagon::STw_GP_cdnPt_V4:
1795239310Sdim  case Hexagon::STw_GP_cPt_nv_V4:
1796239310Sdim    return Hexagon::STw_GP_cPt_V4;
1797239310Sdim
1798239310Sdim  case Hexagon::STw_GP_cdnNotPt_nv_V4:
1799239310Sdim  case Hexagon::STw_GP_cdnNotPt_V4:
1800239310Sdim  case Hexagon::STw_GP_cNotPt_nv_V4:
1801239310Sdim    return Hexagon::STw_GP_cNotPt_V4;
1802239310Sdim
1803239310Sdim  // Store new-value word - unconditional
1804239310Sdim
1805239310Sdim  case Hexagon::STriw_nv_V4:
1806239310Sdim    return Hexagon::STriw;
1807239310Sdim
1808239310Sdim  case Hexagon::STriw_indexed_nv_V4:
1809239310Sdim    return Hexagon::STriw_indexed;
1810239310Sdim
1811239310Sdim  case Hexagon::STriw_indexed_shl_nv_V4:
1812239310Sdim    return Hexagon::STriw_indexed_shl_V4;
1813239310Sdim
1814239310Sdim  case Hexagon::STriw_shl_nv_V4:
1815239310Sdim    return Hexagon::STriw_shl_V4;
1816239310Sdim
1817239310Sdim  case Hexagon::STw_GP_nv_V4:
1818239310Sdim    return Hexagon::STw_GP_V4;
1819239310Sdim
1820239310Sdim  case Hexagon::POST_STwri_nv_V4:
1821239310Sdim    return Hexagon::POST_STwri;
1822239310Sdim
1823239310Sdim // Store doubleword
1824239310Sdim
1825239310Sdim  case Hexagon::STrid_cdnPt_V4 :
1826239310Sdim    return Hexagon::STrid_cPt;
1827239310Sdim
1828239310Sdim  case Hexagon::STrid_cdnNotPt_V4 :
1829239310Sdim    return Hexagon::STrid_cNotPt;
1830239310Sdim
1831239310Sdim  case Hexagon::STrid_indexed_cdnPt_V4 :
1832239310Sdim    return Hexagon::STrid_indexed_cPt;
1833239310Sdim
1834239310Sdim  case Hexagon::STrid_indexed_cdnNotPt_V4 :
1835239310Sdim    return Hexagon::STrid_indexed_cNotPt;
1836239310Sdim
1837239310Sdim  case Hexagon::STrid_indexed_shl_cdnPt_V4 :
1838239310Sdim    return Hexagon::STrid_indexed_shl_cPt_V4;
1839239310Sdim
1840239310Sdim  case Hexagon::STrid_indexed_shl_cdnNotPt_V4 :
1841239310Sdim    return Hexagon::STrid_indexed_shl_cNotPt_V4;
1842239310Sdim
1843239310Sdim  case Hexagon::POST_STdri_cdnPt_V4 :
1844239310Sdim    return Hexagon::POST_STdri_cPt;
1845239310Sdim
1846239310Sdim  case Hexagon::POST_STdri_cdnNotPt_V4 :
1847239310Sdim    return Hexagon::POST_STdri_cNotPt;
1848239310Sdim
1849239310Sdim  case Hexagon::STd_GP_cdnPt_V4 :
1850239310Sdim    return Hexagon::STd_GP_cPt_V4;
1851239310Sdim
1852239310Sdim  case Hexagon::STd_GP_cdnNotPt_V4 :
1853239310Sdim    return Hexagon::STd_GP_cNotPt_V4;
1854239310Sdim
1855239310Sdim  }
1856239310Sdim}
1857239310Sdim
1858239310Sdimbool HexagonPacketizerList::DemoteToDotOld(MachineInstr* MI) {
1859239310Sdim  const HexagonInstrInfo *QII = (const HexagonInstrInfo *) TII;
1860239310Sdim  int NewOpcode = GetDotOldOp(MI->getOpcode());
1861239310Sdim  MI->setDesc(QII->get(NewOpcode));
1862239310Sdim  return true;
1863239310Sdim}
1864239310Sdim
1865239310Sdim// Returns true if an instruction is predicated on p0 and false if it's
1866239310Sdim// predicated on !p0.
1867239310Sdim
1868239310Sdimstatic bool GetPredicateSense(MachineInstr* MI,
1869239310Sdim                              const HexagonInstrInfo *QII) {
1870239310Sdim
1871239310Sdim  switch (MI->getOpcode()) {
1872239310Sdim  default: llvm_unreachable("Unknown predicate sense of the instruction");
1873239310Sdim  case Hexagon::TFR_cPt:
1874239310Sdim  case Hexagon::TFR_cdnPt:
1875239310Sdim  case Hexagon::TFRI_cPt:
1876239310Sdim  case Hexagon::TFRI_cdnPt:
1877239310Sdim  case Hexagon::STrib_cPt :
1878239310Sdim  case Hexagon::STrib_cdnPt_V4 :
1879239310Sdim  case Hexagon::STrib_indexed_cPt :
1880239310Sdim  case Hexagon::STrib_indexed_cdnPt_V4 :
1881239310Sdim  case Hexagon::STrib_indexed_shl_cPt_V4 :
1882239310Sdim  case Hexagon::STrib_indexed_shl_cdnPt_V4 :
1883239310Sdim  case Hexagon::POST_STbri_cPt :
1884239310Sdim  case Hexagon::POST_STbri_cdnPt_V4 :
1885239310Sdim  case Hexagon::STrih_cPt :
1886239310Sdim  case Hexagon::STrih_cdnPt_V4 :
1887239310Sdim  case Hexagon::STrih_indexed_cPt :
1888239310Sdim  case Hexagon::STrih_indexed_cdnPt_V4 :
1889239310Sdim  case Hexagon::STrih_indexed_shl_cPt_V4 :
1890239310Sdim  case Hexagon::STrih_indexed_shl_cdnPt_V4 :
1891239310Sdim  case Hexagon::POST_SThri_cPt :
1892239310Sdim  case Hexagon::POST_SThri_cdnPt_V4 :
1893239310Sdim  case Hexagon::STriw_cPt :
1894239310Sdim  case Hexagon::STriw_cdnPt_V4 :
1895239310Sdim  case Hexagon::STriw_indexed_cPt :
1896239310Sdim  case Hexagon::STriw_indexed_cdnPt_V4 :
1897239310Sdim  case Hexagon::STriw_indexed_shl_cPt_V4 :
1898239310Sdim  case Hexagon::STriw_indexed_shl_cdnPt_V4 :
1899239310Sdim  case Hexagon::POST_STwri_cPt :
1900239310Sdim  case Hexagon::POST_STwri_cdnPt_V4 :
1901239310Sdim  case Hexagon::STrib_imm_cPt_V4 :
1902239310Sdim  case Hexagon::STrib_imm_cdnPt_V4 :
1903239310Sdim  case Hexagon::STrid_cPt :
1904239310Sdim  case Hexagon::STrid_cdnPt_V4 :
1905239310Sdim  case Hexagon::STrid_indexed_cPt :
1906239310Sdim  case Hexagon::STrid_indexed_cdnPt_V4 :
1907239310Sdim  case Hexagon::STrid_indexed_shl_cPt_V4 :
1908239310Sdim  case Hexagon::STrid_indexed_shl_cdnPt_V4 :
1909239310Sdim  case Hexagon::POST_STdri_cPt :
1910239310Sdim  case Hexagon::POST_STdri_cdnPt_V4 :
1911239310Sdim  case Hexagon::STrih_imm_cPt_V4 :
1912239310Sdim  case Hexagon::STrih_imm_cdnPt_V4 :
1913239310Sdim  case Hexagon::STriw_imm_cPt_V4 :
1914239310Sdim  case Hexagon::STriw_imm_cdnPt_V4 :
1915239310Sdim  case Hexagon::JMP_cdnPt :
1916239310Sdim  case Hexagon::LDrid_cPt :
1917239310Sdim  case Hexagon::LDrid_cdnPt :
1918239310Sdim  case Hexagon::LDrid_indexed_cPt :
1919239310Sdim  case Hexagon::LDrid_indexed_cdnPt :
1920239310Sdim  case Hexagon::POST_LDrid_cPt :
1921239310Sdim  case Hexagon::POST_LDrid_cdnPt_V4 :
1922239310Sdim  case Hexagon::LDriw_cPt :
1923239310Sdim  case Hexagon::LDriw_cdnPt :
1924239310Sdim  case Hexagon::LDriw_indexed_cPt :
1925239310Sdim  case Hexagon::LDriw_indexed_cdnPt :
1926239310Sdim  case Hexagon::POST_LDriw_cPt :
1927239310Sdim  case Hexagon::POST_LDriw_cdnPt_V4 :
1928239310Sdim  case Hexagon::LDrih_cPt :
1929239310Sdim  case Hexagon::LDrih_cdnPt :
1930239310Sdim  case Hexagon::LDrih_indexed_cPt :
1931239310Sdim  case Hexagon::LDrih_indexed_cdnPt :
1932239310Sdim  case Hexagon::POST_LDrih_cPt :
1933239310Sdim  case Hexagon::POST_LDrih_cdnPt_V4 :
1934239310Sdim  case Hexagon::LDrib_cPt :
1935239310Sdim  case Hexagon::LDrib_cdnPt :
1936239310Sdim  case Hexagon::LDrib_indexed_cPt :
1937239310Sdim  case Hexagon::LDrib_indexed_cdnPt :
1938239310Sdim  case Hexagon::POST_LDrib_cPt :
1939239310Sdim  case Hexagon::POST_LDrib_cdnPt_V4 :
1940239310Sdim  case Hexagon::LDriuh_cPt :
1941239310Sdim  case Hexagon::LDriuh_cdnPt :
1942239310Sdim  case Hexagon::LDriuh_indexed_cPt :
1943239310Sdim  case Hexagon::LDriuh_indexed_cdnPt :
1944239310Sdim  case Hexagon::POST_LDriuh_cPt :
1945239310Sdim  case Hexagon::POST_LDriuh_cdnPt_V4 :
1946239310Sdim  case Hexagon::LDriub_cPt :
1947239310Sdim  case Hexagon::LDriub_cdnPt :
1948239310Sdim  case Hexagon::LDriub_indexed_cPt :
1949239310Sdim  case Hexagon::LDriub_indexed_cdnPt :
1950239310Sdim  case Hexagon::POST_LDriub_cPt :
1951239310Sdim  case Hexagon::POST_LDriub_cdnPt_V4 :
1952239310Sdim  case Hexagon::LDrid_indexed_shl_cPt_V4 :
1953239310Sdim  case Hexagon::LDrid_indexed_shl_cdnPt_V4 :
1954239310Sdim  case Hexagon::LDrib_indexed_shl_cPt_V4 :
1955239310Sdim  case Hexagon::LDrib_indexed_shl_cdnPt_V4 :
1956239310Sdim  case Hexagon::LDriub_indexed_shl_cPt_V4 :
1957239310Sdim  case Hexagon::LDriub_indexed_shl_cdnPt_V4 :
1958239310Sdim  case Hexagon::LDrih_indexed_shl_cPt_V4 :
1959239310Sdim  case Hexagon::LDrih_indexed_shl_cdnPt_V4 :
1960239310Sdim  case Hexagon::LDriuh_indexed_shl_cPt_V4 :
1961239310Sdim  case Hexagon::LDriuh_indexed_shl_cdnPt_V4 :
1962239310Sdim  case Hexagon::LDriw_indexed_shl_cPt_V4 :
1963239310Sdim  case Hexagon::LDriw_indexed_shl_cdnPt_V4 :
1964239310Sdim  case Hexagon::ADD_ri_cPt :
1965239310Sdim  case Hexagon::ADD_ri_cdnPt :
1966239310Sdim  case Hexagon::ADD_rr_cPt :
1967239310Sdim  case Hexagon::ADD_rr_cdnPt :
1968239310Sdim  case Hexagon::XOR_rr_cPt :
1969239310Sdim  case Hexagon::XOR_rr_cdnPt :
1970239310Sdim  case Hexagon::AND_rr_cPt :
1971239310Sdim  case Hexagon::AND_rr_cdnPt :
1972239310Sdim  case Hexagon::OR_rr_cPt :
1973239310Sdim  case Hexagon::OR_rr_cdnPt :
1974239310Sdim  case Hexagon::SUB_rr_cPt :
1975239310Sdim  case Hexagon::SUB_rr_cdnPt :
1976239310Sdim  case Hexagon::COMBINE_rr_cPt :
1977239310Sdim  case Hexagon::COMBINE_rr_cdnPt :
1978239310Sdim  case Hexagon::ASLH_cPt_V4 :
1979239310Sdim  case Hexagon::ASLH_cdnPt_V4 :
1980239310Sdim  case Hexagon::ASRH_cPt_V4 :
1981239310Sdim  case Hexagon::ASRH_cdnPt_V4 :
1982239310Sdim  case Hexagon::SXTB_cPt_V4 :
1983239310Sdim  case Hexagon::SXTB_cdnPt_V4 :
1984239310Sdim  case Hexagon::SXTH_cPt_V4 :
1985239310Sdim  case Hexagon::SXTH_cdnPt_V4 :
1986239310Sdim  case Hexagon::ZXTB_cPt_V4 :
1987239310Sdim  case Hexagon::ZXTB_cdnPt_V4 :
1988239310Sdim  case Hexagon::ZXTH_cPt_V4 :
1989239310Sdim  case Hexagon::ZXTH_cdnPt_V4 :
1990239310Sdim  case Hexagon::LDd_GP_cPt_V4 :
1991239310Sdim  case Hexagon::LDb_GP_cPt_V4 :
1992239310Sdim  case Hexagon::LDub_GP_cPt_V4 :
1993239310Sdim  case Hexagon::LDh_GP_cPt_V4 :
1994239310Sdim  case Hexagon::LDuh_GP_cPt_V4 :
1995239310Sdim  case Hexagon::LDw_GP_cPt_V4 :
1996239310Sdim  case Hexagon::STd_GP_cPt_V4 :
1997239310Sdim  case Hexagon::STb_GP_cPt_V4 :
1998239310Sdim  case Hexagon::STh_GP_cPt_V4 :
1999239310Sdim  case Hexagon::STw_GP_cPt_V4 :
2000239310Sdim  case Hexagon::LDd_GP_cdnPt_V4 :
2001239310Sdim  case Hexagon::LDb_GP_cdnPt_V4 :
2002239310Sdim  case Hexagon::LDub_GP_cdnPt_V4 :
2003239310Sdim  case Hexagon::LDh_GP_cdnPt_V4 :
2004239310Sdim  case Hexagon::LDuh_GP_cdnPt_V4 :
2005239310Sdim  case Hexagon::LDw_GP_cdnPt_V4 :
2006239310Sdim  case Hexagon::STd_GP_cdnPt_V4 :
2007239310Sdim  case Hexagon::STb_GP_cdnPt_V4 :
2008239310Sdim  case Hexagon::STh_GP_cdnPt_V4 :
2009239310Sdim  case Hexagon::STw_GP_cdnPt_V4 :
2010239310Sdim    return true;
2011239310Sdim
2012239310Sdim  case Hexagon::TFR_cNotPt:
2013239310Sdim  case Hexagon::TFR_cdnNotPt:
2014239310Sdim  case Hexagon::TFRI_cNotPt:
2015239310Sdim  case Hexagon::TFRI_cdnNotPt:
2016239310Sdim  case Hexagon::STrib_cNotPt :
2017239310Sdim  case Hexagon::STrib_cdnNotPt_V4 :
2018239310Sdim  case Hexagon::STrib_indexed_cNotPt :
2019239310Sdim  case Hexagon::STrib_indexed_cdnNotPt_V4 :
2020239310Sdim  case Hexagon::STrib_indexed_shl_cNotPt_V4 :
2021239310Sdim  case Hexagon::STrib_indexed_shl_cdnNotPt_V4 :
2022239310Sdim  case Hexagon::POST_STbri_cNotPt :
2023239310Sdim  case Hexagon::POST_STbri_cdnNotPt_V4 :
2024239310Sdim  case Hexagon::STrih_cNotPt :
2025239310Sdim  case Hexagon::STrih_cdnNotPt_V4 :
2026239310Sdim  case Hexagon::STrih_indexed_cNotPt :
2027239310Sdim  case Hexagon::STrih_indexed_cdnNotPt_V4 :
2028239310Sdim  case Hexagon::STrih_indexed_shl_cNotPt_V4 :
2029239310Sdim  case Hexagon::STrih_indexed_shl_cdnNotPt_V4 :
2030239310Sdim  case Hexagon::POST_SThri_cNotPt :
2031239310Sdim  case Hexagon::POST_SThri_cdnNotPt_V4 :
2032239310Sdim  case Hexagon::STriw_cNotPt :
2033239310Sdim  case Hexagon::STriw_cdnNotPt_V4 :
2034239310Sdim  case Hexagon::STriw_indexed_cNotPt :
2035239310Sdim  case Hexagon::STriw_indexed_cdnNotPt_V4 :
2036239310Sdim  case Hexagon::STriw_indexed_shl_cNotPt_V4 :
2037239310Sdim  case Hexagon::STriw_indexed_shl_cdnNotPt_V4 :
2038239310Sdim  case Hexagon::POST_STwri_cNotPt :
2039239310Sdim  case Hexagon::POST_STwri_cdnNotPt_V4 :
2040239310Sdim  case Hexagon::STrib_imm_cNotPt_V4 :
2041239310Sdim  case Hexagon::STrib_imm_cdnNotPt_V4 :
2042239310Sdim  case Hexagon::STrid_cNotPt :
2043239310Sdim  case Hexagon::STrid_cdnNotPt_V4 :
2044239310Sdim  case Hexagon::STrid_indexed_cdnNotPt_V4 :
2045239310Sdim  case Hexagon::STrid_indexed_cNotPt :
2046239310Sdim  case Hexagon::STrid_indexed_shl_cNotPt_V4 :
2047239310Sdim  case Hexagon::STrid_indexed_shl_cdnNotPt_V4 :
2048239310Sdim  case Hexagon::POST_STdri_cNotPt :
2049239310Sdim  case Hexagon::POST_STdri_cdnNotPt_V4 :
2050239310Sdim  case Hexagon::STrih_imm_cNotPt_V4 :
2051239310Sdim  case Hexagon::STrih_imm_cdnNotPt_V4 :
2052239310Sdim  case Hexagon::STriw_imm_cNotPt_V4 :
2053239310Sdim  case Hexagon::STriw_imm_cdnNotPt_V4 :
2054239310Sdim  case Hexagon::JMP_cdnNotPt :
2055239310Sdim  case Hexagon::LDrid_cNotPt :
2056239310Sdim  case Hexagon::LDrid_cdnNotPt :
2057239310Sdim  case Hexagon::LDrid_indexed_cNotPt :
2058239310Sdim  case Hexagon::LDrid_indexed_cdnNotPt :
2059239310Sdim  case Hexagon::POST_LDrid_cNotPt :
2060239310Sdim  case Hexagon::POST_LDrid_cdnNotPt_V4 :
2061239310Sdim  case Hexagon::LDriw_cNotPt :
2062239310Sdim  case Hexagon::LDriw_cdnNotPt :
2063239310Sdim  case Hexagon::LDriw_indexed_cNotPt :
2064239310Sdim  case Hexagon::LDriw_indexed_cdnNotPt :
2065239310Sdim  case Hexagon::POST_LDriw_cNotPt :
2066239310Sdim  case Hexagon::POST_LDriw_cdnNotPt_V4 :
2067239310Sdim  case Hexagon::LDrih_cNotPt :
2068239310Sdim  case Hexagon::LDrih_cdnNotPt :
2069239310Sdim  case Hexagon::LDrih_indexed_cNotPt :
2070239310Sdim  case Hexagon::LDrih_indexed_cdnNotPt :
2071239310Sdim  case Hexagon::POST_LDrih_cNotPt :
2072239310Sdim  case Hexagon::POST_LDrih_cdnNotPt_V4 :
2073239310Sdim  case Hexagon::LDrib_cNotPt :
2074239310Sdim  case Hexagon::LDrib_cdnNotPt :
2075239310Sdim  case Hexagon::LDrib_indexed_cNotPt :
2076239310Sdim  case Hexagon::LDrib_indexed_cdnNotPt :
2077239310Sdim  case Hexagon::POST_LDrib_cNotPt :
2078239310Sdim  case Hexagon::POST_LDrib_cdnNotPt_V4 :
2079239310Sdim  case Hexagon::LDriuh_cNotPt :
2080239310Sdim  case Hexagon::LDriuh_cdnNotPt :
2081239310Sdim  case Hexagon::LDriuh_indexed_cNotPt :
2082239310Sdim  case Hexagon::LDriuh_indexed_cdnNotPt :
2083239310Sdim  case Hexagon::POST_LDriuh_cNotPt :
2084239310Sdim  case Hexagon::POST_LDriuh_cdnNotPt_V4 :
2085239310Sdim  case Hexagon::LDriub_cNotPt :
2086239310Sdim  case Hexagon::LDriub_cdnNotPt :
2087239310Sdim  case Hexagon::LDriub_indexed_cNotPt :
2088239310Sdim  case Hexagon::LDriub_indexed_cdnNotPt :
2089239310Sdim  case Hexagon::POST_LDriub_cNotPt :
2090239310Sdim  case Hexagon::POST_LDriub_cdnNotPt_V4 :
2091239310Sdim  case Hexagon::LDrid_indexed_shl_cNotPt_V4 :
2092239310Sdim  case Hexagon::LDrid_indexed_shl_cdnNotPt_V4 :
2093239310Sdim  case Hexagon::LDrib_indexed_shl_cNotPt_V4 :
2094239310Sdim  case Hexagon::LDrib_indexed_shl_cdnNotPt_V4 :
2095239310Sdim  case Hexagon::LDriub_indexed_shl_cNotPt_V4 :
2096239310Sdim  case Hexagon::LDriub_indexed_shl_cdnNotPt_V4 :
2097239310Sdim  case Hexagon::LDrih_indexed_shl_cNotPt_V4 :
2098239310Sdim  case Hexagon::LDrih_indexed_shl_cdnNotPt_V4 :
2099239310Sdim  case Hexagon::LDriuh_indexed_shl_cNotPt_V4 :
2100239310Sdim  case Hexagon::LDriuh_indexed_shl_cdnNotPt_V4 :
2101239310Sdim  case Hexagon::LDriw_indexed_shl_cNotPt_V4 :
2102239310Sdim  case Hexagon::LDriw_indexed_shl_cdnNotPt_V4 :
2103239310Sdim  case Hexagon::ADD_ri_cNotPt :
2104239310Sdim  case Hexagon::ADD_ri_cdnNotPt :
2105239310Sdim  case Hexagon::ADD_rr_cNotPt :
2106239310Sdim  case Hexagon::ADD_rr_cdnNotPt :
2107239310Sdim  case Hexagon::XOR_rr_cNotPt :
2108239310Sdim  case Hexagon::XOR_rr_cdnNotPt :
2109239310Sdim  case Hexagon::AND_rr_cNotPt :
2110239310Sdim  case Hexagon::AND_rr_cdnNotPt :
2111239310Sdim  case Hexagon::OR_rr_cNotPt :
2112239310Sdim  case Hexagon::OR_rr_cdnNotPt :
2113239310Sdim  case Hexagon::SUB_rr_cNotPt :
2114239310Sdim  case Hexagon::SUB_rr_cdnNotPt :
2115239310Sdim  case Hexagon::COMBINE_rr_cNotPt :
2116239310Sdim  case Hexagon::COMBINE_rr_cdnNotPt :
2117239310Sdim  case Hexagon::ASLH_cNotPt_V4 :
2118239310Sdim  case Hexagon::ASLH_cdnNotPt_V4 :
2119239310Sdim  case Hexagon::ASRH_cNotPt_V4 :
2120239310Sdim  case Hexagon::ASRH_cdnNotPt_V4 :
2121239310Sdim  case Hexagon::SXTB_cNotPt_V4 :
2122239310Sdim  case Hexagon::SXTB_cdnNotPt_V4 :
2123239310Sdim  case Hexagon::SXTH_cNotPt_V4 :
2124239310Sdim  case Hexagon::SXTH_cdnNotPt_V4 :
2125239310Sdim  case Hexagon::ZXTB_cNotPt_V4 :
2126239310Sdim  case Hexagon::ZXTB_cdnNotPt_V4 :
2127239310Sdim  case Hexagon::ZXTH_cNotPt_V4 :
2128239310Sdim  case Hexagon::ZXTH_cdnNotPt_V4 :
2129239310Sdim
2130239310Sdim  case Hexagon::LDd_GP_cNotPt_V4 :
2131239310Sdim  case Hexagon::LDb_GP_cNotPt_V4 :
2132239310Sdim  case Hexagon::LDub_GP_cNotPt_V4 :
2133239310Sdim  case Hexagon::LDh_GP_cNotPt_V4 :
2134239310Sdim  case Hexagon::LDuh_GP_cNotPt_V4 :
2135239310Sdim  case Hexagon::LDw_GP_cNotPt_V4 :
2136239310Sdim  case Hexagon::STd_GP_cNotPt_V4 :
2137239310Sdim  case Hexagon::STb_GP_cNotPt_V4 :
2138239310Sdim  case Hexagon::STh_GP_cNotPt_V4 :
2139239310Sdim  case Hexagon::STw_GP_cNotPt_V4 :
2140239310Sdim  case Hexagon::LDd_GP_cdnNotPt_V4 :
2141239310Sdim  case Hexagon::LDb_GP_cdnNotPt_V4 :
2142239310Sdim  case Hexagon::LDub_GP_cdnNotPt_V4 :
2143239310Sdim  case Hexagon::LDh_GP_cdnNotPt_V4 :
2144239310Sdim  case Hexagon::LDuh_GP_cdnNotPt_V4 :
2145239310Sdim  case Hexagon::LDw_GP_cdnNotPt_V4 :
2146239310Sdim  case Hexagon::STd_GP_cdnNotPt_V4 :
2147239310Sdim  case Hexagon::STb_GP_cdnNotPt_V4 :
2148239310Sdim  case Hexagon::STh_GP_cdnNotPt_V4 :
2149239310Sdim  case Hexagon::STw_GP_cdnNotPt_V4 :
2150239310Sdim    return false;
2151239310Sdim  }
2152239310Sdim  // return *some value* to avoid compiler warning
2153239310Sdim  return false;
2154239310Sdim}
2155239310Sdim
2156239310Sdimstatic MachineOperand& GetPostIncrementOperand(MachineInstr *MI,
2157239310Sdim                                               const HexagonInstrInfo *QII) {
2158239310Sdim  assert(QII->isPostIncrement(MI) && "Not a post increment operation.");
2159239310Sdim#ifndef NDEBUG
2160239310Sdim  // Post Increment means duplicates. Use dense map to find duplicates in the
2161239310Sdim  // list. Caution: Densemap initializes with the minimum of 64 buckets,
2162239310Sdim  // whereas there are at most 5 operands in the post increment.
2163239310Sdim  DenseMap<unsigned,  unsigned> DefRegsSet;
2164239310Sdim  for(unsigned opNum = 0; opNum < MI->getNumOperands(); opNum++)
2165239310Sdim    if (MI->getOperand(opNum).isReg() &&
2166239310Sdim        MI->getOperand(opNum).isDef()) {
2167239310Sdim      DefRegsSet[MI->getOperand(opNum).getReg()] = 1;
2168239310Sdim    }
2169239310Sdim
2170239310Sdim  for(unsigned opNum = 0; opNum < MI->getNumOperands(); opNum++)
2171239310Sdim    if (MI->getOperand(opNum).isReg() &&
2172239310Sdim        MI->getOperand(opNum).isUse()) {
2173239310Sdim      if (DefRegsSet[MI->getOperand(opNum).getReg()]) {
2174239310Sdim        return MI->getOperand(opNum);
2175239310Sdim      }
2176239310Sdim    }
2177239310Sdim#else
2178239310Sdim  if (MI->getDesc().mayLoad()) {
2179239310Sdim    // The 2nd operand is always the post increment operand in load.
2180239310Sdim    assert(MI->getOperand(1).isReg() &&
2181239310Sdim                "Post increment operand has be to a register.");
2182239310Sdim    return (MI->getOperand(1));
2183239310Sdim  }
2184239310Sdim  if (MI->getDesc().mayStore()) {
2185239310Sdim    // The 1st operand is always the post increment operand in store.
2186239310Sdim    assert(MI->getOperand(0).isReg() &&
2187239310Sdim                "Post increment operand has be to a register.");
2188239310Sdim    return (MI->getOperand(0));
2189239310Sdim  }
2190239310Sdim#endif
2191239310Sdim  // we should never come here.
2192239310Sdim  llvm_unreachable("mayLoad or mayStore not set for Post Increment operation");
2193239310Sdim}
2194239310Sdim
2195239310Sdim// get the value being stored
2196239310Sdimstatic MachineOperand& GetStoreValueOperand(MachineInstr *MI) {
2197239310Sdim  // value being stored is always the last operand.
2198239310Sdim  return (MI->getOperand(MI->getNumOperands()-1));
2199239310Sdim}
2200239310Sdim
2201239310Sdim// can be new value store?
2202239310Sdim// Following restrictions are to be respected in convert a store into
2203239310Sdim// a new value store.
2204239310Sdim// 1. If an instruction uses auto-increment, its address register cannot
2205239310Sdim//    be a new-value register. Arch Spec 5.4.2.1
2206239310Sdim// 2. If an instruction uses absolute-set addressing mode,
2207239310Sdim//    its address register cannot be a new-value register.
2208239310Sdim//    Arch Spec 5.4.2.1.TODO: This is not enabled as
2209239310Sdim//    as absolute-set address mode patters are not implemented.
2210239310Sdim// 3. If an instruction produces a 64-bit result, its registers cannot be used
2211239310Sdim//    as new-value registers. Arch Spec 5.4.2.2.
2212239310Sdim// 4. If the instruction that sets a new-value register is conditional, then
2213239310Sdim//    the instruction that uses the new-value register must also be conditional,
2214239310Sdim//    and both must always have their predicates evaluate identically.
2215239310Sdim//    Arch Spec 5.4.2.3.
2216239310Sdim// 5. There is an implied restriction of a packet can not have another store,
2217239310Sdim//    if there is a  new value store in the packet. Corollary, if there is
2218239310Sdim//    already a store in a packet, there can not be a new value store.
2219239310Sdim//    Arch Spec: 3.4.4.2
2220239310Sdimbool HexagonPacketizerList::CanPromoteToNewValueStore( MachineInstr *MI,
2221239310Sdim                MachineInstr *PacketMI, unsigned DepReg,
2222239310Sdim                std::map <MachineInstr*, SUnit*> MIToSUnit)
2223239310Sdim{
2224239310Sdim  // Make sure we are looking at the store
2225239310Sdim  if (!IsNewifyStore(MI))
2226239310Sdim    return false;
2227239310Sdim
2228239310Sdim  // Make sure there is dependency and can be new value'ed
2229239310Sdim  if (GetStoreValueOperand(MI).isReg() &&
2230239310Sdim      GetStoreValueOperand(MI).getReg() != DepReg)
2231239310Sdim    return false;
2232239310Sdim
2233239310Sdim  const HexagonRegisterInfo* QRI =
2234239310Sdim                            (const HexagonRegisterInfo *) TM.getRegisterInfo();
2235239310Sdim  const MCInstrDesc& MCID = PacketMI->getDesc();
2236239310Sdim  // first operand is always the result
2237239310Sdim
2238239310Sdim  const HexagonInstrInfo *QII = (const HexagonInstrInfo *) TII;
2239239310Sdim  const TargetRegisterClass* PacketRC = QII->getRegClass(MCID, 0, QRI, MF);
2240239310Sdim
2241239310Sdim  // if there is already an store in the packet, no can do new value store
2242239310Sdim  // Arch Spec 3.4.4.2.
2243239310Sdim  for (std::vector<MachineInstr*>::iterator VI = CurrentPacketMIs.begin(),
2244239310Sdim         VE = CurrentPacketMIs.end();
2245239310Sdim       (VI != VE); ++VI) {
2246239310Sdim    SUnit* PacketSU = MIToSUnit[*VI];
2247239310Sdim    if (PacketSU->getInstr()->getDesc().mayStore() ||
2248239310Sdim        // if we have mayStore = 1 set on ALLOCFRAME and DEALLOCFRAME,
2249239310Sdim        // then we don't need this
2250239310Sdim        PacketSU->getInstr()->getOpcode() == Hexagon::ALLOCFRAME ||
2251239310Sdim        PacketSU->getInstr()->getOpcode() == Hexagon::DEALLOCFRAME)
2252239310Sdim      return false;
2253239310Sdim  }
2254239310Sdim
2255239310Sdim  if (PacketRC == &Hexagon::DoubleRegsRegClass) {
2256239310Sdim    // new value store constraint: double regs can not feed into new value store
2257239310Sdim    // arch spec section: 5.4.2.2
2258239310Sdim    return false;
2259239310Sdim  }
2260239310Sdim
2261239310Sdim  // Make sure it's NOT the post increment register that we are going to
2262239310Sdim  // new value.
2263239310Sdim  if (QII->isPostIncrement(MI) &&
2264239310Sdim      MI->getDesc().mayStore() &&
2265239310Sdim      GetPostIncrementOperand(MI, QII).getReg() == DepReg) {
2266239310Sdim    return false;
2267239310Sdim  }
2268239310Sdim
2269239310Sdim  if (QII->isPostIncrement(PacketMI) &&
2270239310Sdim      PacketMI->getDesc().mayLoad() &&
2271239310Sdim      GetPostIncrementOperand(PacketMI, QII).getReg() == DepReg) {
2272239310Sdim    // if source is post_inc, or absolute-set addressing,
2273239310Sdim    // it can not feed into new value store
2274239310Sdim    //  r3 = memw(r2++#4)
2275239310Sdim    //  memw(r30 + #-1404) = r2.new -> can not be new value store
2276239310Sdim    // arch spec section: 5.4.2.1
2277239310Sdim    return false;
2278239310Sdim  }
2279239310Sdim
2280239310Sdim  // If the source that feeds the store is predicated, new value store must
2281239310Sdim  // also be also predicated.
2282239310Sdim  if (QII->isPredicated(PacketMI)) {
2283239310Sdim    if (!QII->isPredicated(MI))
2284239310Sdim      return false;
2285239310Sdim
2286239310Sdim    // Check to make sure that they both will have their predicates
2287239310Sdim    // evaluate identically
2288239310Sdim    unsigned predRegNumSrc = 0;
2289239310Sdim    unsigned predRegNumDst = 0;
2290239310Sdim    const TargetRegisterClass* predRegClass = NULL;
2291239310Sdim
2292239310Sdim    // Get predicate register used in the source instruction
2293239310Sdim    for(unsigned opNum = 0; opNum < PacketMI->getNumOperands(); opNum++) {
2294239310Sdim      if ( PacketMI->getOperand(opNum).isReg())
2295239310Sdim      predRegNumSrc = PacketMI->getOperand(opNum).getReg();
2296239310Sdim      predRegClass = QRI->getMinimalPhysRegClass(predRegNumSrc);
2297239310Sdim      if (predRegClass == &Hexagon::PredRegsRegClass) {
2298239310Sdim        break;
2299239310Sdim      }
2300239310Sdim    }
2301239310Sdim    assert ((predRegClass == &Hexagon::PredRegsRegClass ) &&
2302239310Sdim        ("predicate register not found in a predicated PacketMI instruction"));
2303239310Sdim
2304239310Sdim    // Get predicate register used in new-value store instruction
2305239310Sdim    for(unsigned opNum = 0; opNum < MI->getNumOperands(); opNum++) {
2306239310Sdim      if ( MI->getOperand(opNum).isReg())
2307239310Sdim      predRegNumDst = MI->getOperand(opNum).getReg();
2308239310Sdim      predRegClass = QRI->getMinimalPhysRegClass(predRegNumDst);
2309239310Sdim      if (predRegClass == &Hexagon::PredRegsRegClass) {
2310239310Sdim        break;
2311239310Sdim      }
2312239310Sdim    }
2313239310Sdim    assert ((predRegClass == &Hexagon::PredRegsRegClass ) &&
2314239310Sdim            ("predicate register not found in a predicated MI instruction"));
2315239310Sdim
2316239310Sdim    // New-value register producer and user (store) need to satisfy these
2317239310Sdim    // constraints:
2318239310Sdim    // 1) Both instructions should be predicated on the same register.
2319239310Sdim    // 2) If producer of the new-value register is .new predicated then store
2320239310Sdim    // should also be .new predicated and if producer is not .new predicated
2321239310Sdim    // then store should not be .new predicated.
2322239310Sdim    // 3) Both new-value register producer and user should have same predicate
2323239310Sdim    // sense, i.e, either both should be negated or both should be none negated.
2324239310Sdim
2325239310Sdim    if (( predRegNumDst != predRegNumSrc) ||
2326249423Sdim          QII->isDotNewInst(PacketMI) != QII->isDotNewInst(MI)  ||
2327239310Sdim          GetPredicateSense(MI, QII) != GetPredicateSense(PacketMI, QII)) {
2328239310Sdim      return false;
2329239310Sdim    }
2330239310Sdim  }
2331239310Sdim
2332239310Sdim  // Make sure that other than the new-value register no other store instruction
2333239310Sdim  // register has been modified in the same packet. Predicate registers can be
2334239310Sdim  // modified by they should not be modified between the producer and the store
2335239310Sdim  // instruction as it will make them both conditional on different values.
2336239310Sdim  // We already know this to be true for all the instructions before and
2337239310Sdim  // including PacketMI. Howerver, we need to perform the check for the
2338239310Sdim  // remaining instructions in the packet.
2339239310Sdim
2340239310Sdim  std::vector<MachineInstr*>::iterator VI;
2341239310Sdim  std::vector<MachineInstr*>::iterator VE;
2342239310Sdim  unsigned StartCheck = 0;
2343239310Sdim
2344239310Sdim  for (VI=CurrentPacketMIs.begin(), VE = CurrentPacketMIs.end();
2345239310Sdim      (VI != VE); ++VI) {
2346239310Sdim    SUnit* TempSU = MIToSUnit[*VI];
2347239310Sdim    MachineInstr* TempMI = TempSU->getInstr();
2348239310Sdim
2349239310Sdim    // Following condition is true for all the instructions until PacketMI is
2350239310Sdim    // reached (StartCheck is set to 0 before the for loop).
2351239310Sdim    // StartCheck flag is 1 for all the instructions after PacketMI.
2352239310Sdim    if (TempMI != PacketMI && !StartCheck) // start processing only after
2353239310Sdim      continue;                            // encountering PacketMI
2354239310Sdim
2355239310Sdim    StartCheck = 1;
2356239310Sdim    if (TempMI == PacketMI) // We don't want to check PacketMI for dependence
2357239310Sdim      continue;
2358239310Sdim
2359239310Sdim    for(unsigned opNum = 0; opNum < MI->getNumOperands(); opNum++) {
2360239310Sdim      if (MI->getOperand(opNum).isReg() &&
2361239310Sdim          TempSU->getInstr()->modifiesRegister(MI->getOperand(opNum).getReg(),
2362239310Sdim                                               QRI))
2363239310Sdim        return false;
2364239310Sdim    }
2365239310Sdim  }
2366239310Sdim
2367239310Sdim  // Make sure that for non POST_INC stores:
2368239310Sdim  // 1. The only use of reg is DepReg and no other registers.
2369239310Sdim  //    This handles V4 base+index registers.
2370239310Sdim  //    The following store can not be dot new.
2371239310Sdim  //    Eg.   r0 = add(r0, #3)a
2372239310Sdim  //          memw(r1+r0<<#2) = r0
2373239310Sdim  if (!QII->isPostIncrement(MI) &&
2374239310Sdim      GetStoreValueOperand(MI).isReg() &&
2375239310Sdim      GetStoreValueOperand(MI).getReg() == DepReg) {
2376239310Sdim    for(unsigned opNum = 0; opNum < MI->getNumOperands()-1; opNum++) {
2377239310Sdim      if (MI->getOperand(opNum).isReg() &&
2378239310Sdim          MI->getOperand(opNum).getReg() == DepReg) {
2379239310Sdim        return false;
2380239310Sdim      }
2381239310Sdim    }
2382239310Sdim    // 2. If data definition is because of implicit definition of the register,
2383239310Sdim    //    do not newify the store. Eg.
2384239310Sdim    //    %R9<def> = ZXTH %R12, %D6<imp-use>, %R12<imp-def>
2385239310Sdim    //    STrih_indexed %R8, 2, %R12<kill>; mem:ST2[%scevgep343]
2386239310Sdim    for(unsigned opNum = 0; opNum < PacketMI->getNumOperands(); opNum++) {
2387239310Sdim      if (PacketMI->getOperand(opNum).isReg() &&
2388239310Sdim          PacketMI->getOperand(opNum).getReg() == DepReg &&
2389239310Sdim          PacketMI->getOperand(opNum).isDef() &&
2390239310Sdim          PacketMI->getOperand(opNum).isImplicit()) {
2391239310Sdim        return false;
2392239310Sdim      }
2393239310Sdim    }
2394239310Sdim  }
2395239310Sdim
2396239310Sdim  // Can be dot new store.
2397239310Sdim  return true;
2398239310Sdim}
2399239310Sdim
2400239310Sdim// can this MI to promoted to either
2401239310Sdim// new value store or new value jump
2402239310Sdimbool HexagonPacketizerList::CanPromoteToNewValue( MachineInstr *MI,
2403239310Sdim                SUnit *PacketSU, unsigned DepReg,
2404239310Sdim                std::map <MachineInstr*, SUnit*> MIToSUnit,
2405239310Sdim                MachineBasicBlock::iterator &MII)
2406239310Sdim{
2407239310Sdim
2408239310Sdim  const HexagonRegisterInfo* QRI =
2409239310Sdim                            (const HexagonRegisterInfo *) TM.getRegisterInfo();
2410239310Sdim  if (!QRI->Subtarget.hasV4TOps() ||
2411239310Sdim      !IsNewifyStore(MI))
2412239310Sdim    return false;
2413239310Sdim
2414239310Sdim  MachineInstr *PacketMI = PacketSU->getInstr();
2415239310Sdim
2416239310Sdim  // Check to see the store can be new value'ed.
2417239310Sdim  if (CanPromoteToNewValueStore(MI, PacketMI, DepReg, MIToSUnit))
2418239310Sdim    return true;
2419239310Sdim
2420239310Sdim  // Check to see the compare/jump can be new value'ed.
2421239310Sdim  // This is done as a pass on its own. Don't need to check it here.
2422239310Sdim  return false;
2423239310Sdim}
2424239310Sdim
2425239310Sdim// Check to see if an instruction can be dot new
2426239310Sdim// There are three kinds.
2427239310Sdim// 1. dot new on predicate - V2/V3/V4
2428239310Sdim// 2. dot new on stores NV/ST - V4
2429239310Sdim// 3. dot new on jump NV/J - V4 -- This is generated in a pass.
2430239310Sdimbool HexagonPacketizerList::CanPromoteToDotNew( MachineInstr *MI,
2431239310Sdim                              SUnit *PacketSU, unsigned DepReg,
2432239310Sdim                              std::map <MachineInstr*, SUnit*> MIToSUnit,
2433239310Sdim                              MachineBasicBlock::iterator &MII,
2434239310Sdim                              const TargetRegisterClass* RC )
2435239310Sdim{
2436249423Sdim  const HexagonInstrInfo *QII = (const HexagonInstrInfo *) TII;
2437249423Sdim  // Already a dot new instruction.
2438249423Sdim  if (QII->isDotNewInst(MI) && !IsNewifyStore(MI))
2439239310Sdim    return false;
2440239310Sdim
2441239310Sdim  if (!isNewifiable(MI))
2442239310Sdim    return false;
2443239310Sdim
2444239310Sdim  // predicate .new
2445239310Sdim  if (RC == &Hexagon::PredRegsRegClass && isCondInst(MI))
2446239310Sdim      return true;
2447239310Sdim  else if (RC != &Hexagon::PredRegsRegClass &&
2448239310Sdim      !IsNewifyStore(MI)) // MI is not a new-value store
2449239310Sdim    return false;
2450239310Sdim  else {
2451239310Sdim    // Create a dot new machine instruction to see if resources can be
2452239310Sdim    // allocated. If not, bail out now.
2453239310Sdim    int NewOpcode = GetDotNewOp(MI->getOpcode());
2454239310Sdim    const MCInstrDesc &desc = QII->get(NewOpcode);
2455239310Sdim    DebugLoc dl;
2456239310Sdim    MachineInstr *NewMI =
2457239310Sdim                    MI->getParent()->getParent()->CreateMachineInstr(desc, dl);
2458239310Sdim    bool ResourcesAvailable = ResourceTracker->canReserveResources(NewMI);
2459239310Sdim    MI->getParent()->getParent()->DeleteMachineInstr(NewMI);
2460239310Sdim
2461239310Sdim    if (!ResourcesAvailable)
2462239310Sdim      return false;
2463239310Sdim
2464239310Sdim    // new value store only
2465239310Sdim    // new new value jump generated as a passes
2466239310Sdim    if (!CanPromoteToNewValue(MI, PacketSU, DepReg, MIToSUnit, MII)) {
2467239310Sdim      return false;
2468239310Sdim    }
2469239310Sdim  }
2470239310Sdim  return true;
2471239310Sdim}
2472239310Sdim
2473239310Sdim// Go through the packet instructions and search for anti dependency
2474239310Sdim// between them and DepReg from MI
2475239310Sdim// Consider this case:
2476239310Sdim// Trying to add
2477239310Sdim// a) %R1<def> = TFRI_cdNotPt %P3, 2
2478239310Sdim// to this packet:
2479239310Sdim// {
2480239310Sdim//   b) %P0<def> = OR_pp %P3<kill>, %P0<kill>
2481239310Sdim//   c) %P3<def> = TFR_PdRs %R23
2482239310Sdim//   d) %R1<def> = TFRI_cdnPt %P3, 4
2483239310Sdim//  }
2484239310Sdim// The P3 from a) and d) will be complements after
2485239310Sdim// a)'s P3 is converted to .new form
2486239310Sdim// Anti Dep between c) and b) is irrelevant for this case
2487239310Sdimbool HexagonPacketizerList::RestrictingDepExistInPacket (MachineInstr* MI,
2488239310Sdim      unsigned DepReg,
2489239310Sdim      std::map <MachineInstr*, SUnit*> MIToSUnit) {
2490239310Sdim
2491239310Sdim  const HexagonInstrInfo *QII = (const HexagonInstrInfo *) TII;
2492239310Sdim  SUnit* PacketSUDep = MIToSUnit[MI];
2493239310Sdim
2494239310Sdim  for (std::vector<MachineInstr*>::iterator VIN = CurrentPacketMIs.begin(),
2495239310Sdim       VEN = CurrentPacketMIs.end(); (VIN != VEN); ++VIN) {
2496239310Sdim
2497239310Sdim    // We only care for dependencies to predicated instructions
2498239310Sdim    if(!QII->isPredicated(*VIN)) continue;
2499239310Sdim
2500239310Sdim    // Scheduling Unit for current insn in the packet
2501239310Sdim    SUnit* PacketSU = MIToSUnit[*VIN];
2502239310Sdim
2503239310Sdim    // Look at dependencies between current members of the packet
2504239310Sdim    // and predicate defining instruction MI.
2505239310Sdim    // Make sure that dependency is on the exact register
2506239310Sdim    // we care about.
2507239310Sdim    if (PacketSU->isSucc(PacketSUDep)) {
2508239310Sdim      for (unsigned i = 0; i < PacketSU->Succs.size(); ++i) {
2509239310Sdim        if ((PacketSU->Succs[i].getSUnit() == PacketSUDep) &&
2510239310Sdim            (PacketSU->Succs[i].getKind() == SDep::Anti) &&
2511239310Sdim            (PacketSU->Succs[i].getReg() == DepReg)) {
2512239310Sdim          return true;
2513239310Sdim        }
2514239310Sdim      }
2515239310Sdim    }
2516239310Sdim  }
2517239310Sdim
2518239310Sdim  return false;
2519239310Sdim}
2520239310Sdim
2521239310Sdim
2522239310Sdim// Given two predicated instructions, this function detects whether
2523239310Sdim// the predicates are complements
2524239310Sdimbool HexagonPacketizerList::ArePredicatesComplements (MachineInstr* MI1,
2525239310Sdim     MachineInstr* MI2, std::map <MachineInstr*, SUnit*> MIToSUnit) {
2526239310Sdim
2527239310Sdim  const HexagonInstrInfo *QII = (const HexagonInstrInfo *) TII;
2528239310Sdim  // Currently can only reason about conditional transfers
2529239310Sdim  if (!QII->isConditionalTransfer(MI1) || !QII->isConditionalTransfer(MI2)) {
2530239310Sdim    return false;
2531239310Sdim  }
2532239310Sdim
2533239310Sdim  // Scheduling unit for candidate
2534239310Sdim  SUnit* SU = MIToSUnit[MI1];
2535239310Sdim
2536239310Sdim  // One corner case deals with the following scenario:
2537239310Sdim  // Trying to add
2538239310Sdim  // a) %R24<def> = TFR_cPt %P0, %R25
2539239310Sdim  // to this packet:
2540239310Sdim  //
2541239310Sdim  // {
2542239310Sdim  //   b) %R25<def> = TFR_cNotPt %P0, %R24
2543239310Sdim  //   c) %P0<def> = CMPEQri %R26, 1
2544239310Sdim  // }
2545239310Sdim  //
2546239310Sdim  // On general check a) and b) are complements, but
2547239310Sdim  // presence of c) will convert a) to .new form, and
2548239310Sdim  // then it is not a complement
2549239310Sdim  // We attempt to detect it by analyzing  existing
2550239310Sdim  // dependencies in the packet
2551239310Sdim
2552239310Sdim  // Analyze relationships between all existing members of the packet.
2553239310Sdim  // Look for Anti dependecy on the same predicate reg
2554239310Sdim  // as used in the candidate
2555239310Sdim  for (std::vector<MachineInstr*>::iterator VIN = CurrentPacketMIs.begin(),
2556239310Sdim       VEN = CurrentPacketMIs.end(); (VIN != VEN); ++VIN) {
2557239310Sdim
2558239310Sdim    // Scheduling Unit for current insn in the packet
2559239310Sdim    SUnit* PacketSU = MIToSUnit[*VIN];
2560239310Sdim
2561239310Sdim    // If this instruction in the packet is succeeded by the candidate...
2562239310Sdim    if (PacketSU->isSucc(SU)) {
2563239310Sdim      for (unsigned i = 0; i < PacketSU->Succs.size(); ++i) {
2564239310Sdim        // The corner case exist when there is true data
2565239310Sdim        // dependency between candidate and one of current
2566239310Sdim        // packet members, this dep is on predicate reg, and
2567239310Sdim        // there already exist anti dep on the same pred in
2568239310Sdim        // the packet.
2569239310Sdim        if (PacketSU->Succs[i].getSUnit() == SU &&
2570239310Sdim            Hexagon::PredRegsRegClass.contains(
2571239310Sdim              PacketSU->Succs[i].getReg()) &&
2572239310Sdim            PacketSU->Succs[i].getKind() == SDep::Data &&
2573239310Sdim            // Here I know that *VIN is predicate setting instruction
2574239310Sdim            // with true data dep to candidate on the register
2575239310Sdim            // we care about - c) in the above example.
2576239310Sdim            // Now I need to see if there is an anti dependency
2577239310Sdim            // from c) to any other instruction in the
2578239310Sdim            // same packet on the pred reg of interest
2579239310Sdim            RestrictingDepExistInPacket(*VIN,PacketSU->Succs[i].getReg(),
2580239310Sdim                                        MIToSUnit)) {
2581239310Sdim           return false;
2582239310Sdim        }
2583239310Sdim      }
2584239310Sdim    }
2585239310Sdim  }
2586239310Sdim
2587239310Sdim  // If the above case does not apply, check regular
2588239310Sdim  // complement condition.
2589239310Sdim  // Check that the predicate register is the same and
2590239310Sdim  // that the predicate sense is different
2591239310Sdim  // We also need to differentiate .old vs. .new:
2592239310Sdim  // !p0 is not complimentary to p0.new
2593239310Sdim  return ((MI1->getOperand(1).getReg() == MI2->getOperand(1).getReg()) &&
2594239310Sdim          (GetPredicateSense(MI1, QII) != GetPredicateSense(MI2, QII)) &&
2595249423Sdim          (QII->isDotNewInst(MI1) == QII->isDotNewInst(MI2)));
2596239310Sdim}
2597239310Sdim
2598239310Sdim// initPacketizerState - Initialize packetizer flags
2599239310Sdimvoid HexagonPacketizerList::initPacketizerState() {
2600239310Sdim
2601239310Sdim  Dependence = false;
2602239310Sdim  PromotedToDotNew = false;
2603239310Sdim  GlueToNewValueJump = false;
2604239310Sdim  GlueAllocframeStore = false;
2605239310Sdim  FoundSequentialDependence = false;
2606239310Sdim
2607239310Sdim  return;
2608239310Sdim}
2609239310Sdim
2610239310Sdim// ignorePseudoInstruction - Ignore bundling of pseudo instructions.
2611239310Sdimbool HexagonPacketizerList::ignorePseudoInstruction(MachineInstr *MI,
2612239310Sdim                                                    MachineBasicBlock *MBB) {
2613239310Sdim  if (MI->isDebugValue())
2614239310Sdim    return true;
2615239310Sdim
2616239310Sdim  // We must print out inline assembly
2617239310Sdim  if (MI->isInlineAsm())
2618239310Sdim    return false;
2619239310Sdim
2620239310Sdim  // We check if MI has any functional units mapped to it.
2621239310Sdim  // If it doesn't, we ignore the instruction.
2622239310Sdim  const MCInstrDesc& TID = MI->getDesc();
2623239310Sdim  unsigned SchedClass = TID.getSchedClass();
2624239310Sdim  const InstrStage* IS =
2625239310Sdim                    ResourceTracker->getInstrItins()->beginStage(SchedClass);
2626239310Sdim  unsigned FuncUnits = IS->getUnits();
2627239310Sdim  return !FuncUnits;
2628239310Sdim}
2629239310Sdim
2630239310Sdim// isSoloInstruction: - Returns true for instructions that must be
2631239310Sdim// scheduled in their own packet.
2632239310Sdimbool HexagonPacketizerList::isSoloInstruction(MachineInstr *MI) {
2633239310Sdim
2634239310Sdim  if (MI->isInlineAsm())
2635239310Sdim    return true;
2636239310Sdim
2637239310Sdim  if (MI->isEHLabel())
2638239310Sdim    return true;
2639239310Sdim
2640239310Sdim  // From Hexagon V4 Programmer's Reference Manual 3.4.4 Grouping constraints:
2641239310Sdim  // trap, pause, barrier, icinva, isync, and syncht are solo instructions.
2642239310Sdim  // They must not be grouped with other instructions in a packet.
2643239310Sdim  if (IsSchedBarrier(MI))
2644239310Sdim    return true;
2645239310Sdim
2646239310Sdim  return false;
2647239310Sdim}
2648239310Sdim
2649239310Sdim// isLegalToPacketizeTogether:
2650239310Sdim// SUI is the current instruction that is out side of the current packet.
2651239310Sdim// SUJ is the current instruction inside the current packet against which that
2652239310Sdim// SUI will be packetized.
2653239310Sdimbool HexagonPacketizerList::isLegalToPacketizeTogether(SUnit *SUI, SUnit *SUJ) {
2654239310Sdim  MachineInstr *I = SUI->getInstr();
2655239310Sdim  MachineInstr *J = SUJ->getInstr();
2656239310Sdim  assert(I && J && "Unable to packetize null instruction!");
2657239310Sdim
2658239310Sdim  const MCInstrDesc &MCIDI = I->getDesc();
2659239310Sdim  const MCInstrDesc &MCIDJ = J->getDesc();
2660239310Sdim
2661239310Sdim  MachineBasicBlock::iterator II = I;
2662239310Sdim
2663239310Sdim  const unsigned FrameSize = MF.getFrameInfo()->getStackSize();
2664239310Sdim  const HexagonRegisterInfo* QRI =
2665239310Sdim                      (const HexagonRegisterInfo *) TM.getRegisterInfo();
2666239310Sdim  const HexagonInstrInfo *QII = (const HexagonInstrInfo *) TII;
2667239310Sdim
2668239310Sdim  // Inline asm cannot go in the packet.
2669239310Sdim  if (I->getOpcode() == Hexagon::INLINEASM)
2670239310Sdim    llvm_unreachable("Should not meet inline asm here!");
2671239310Sdim
2672239310Sdim  if (isSoloInstruction(I))
2673239310Sdim    llvm_unreachable("Should not meet solo instr here!");
2674239310Sdim
2675239310Sdim  // A save callee-save register function call can only be in a packet
2676239310Sdim  // with instructions that don't write to the callee-save registers.
2677239310Sdim  if ((QII->isSaveCalleeSavedRegsCall(I) &&
2678239310Sdim       DoesModifyCalleeSavedReg(J, QRI)) ||
2679239310Sdim      (QII->isSaveCalleeSavedRegsCall(J) &&
2680239310Sdim       DoesModifyCalleeSavedReg(I, QRI))) {
2681239310Sdim    Dependence = true;
2682239310Sdim    return false;
2683239310Sdim  }
2684239310Sdim
2685239310Sdim  // Two control flow instructions cannot go in the same packet.
2686239310Sdim  if (IsControlFlow(I) && IsControlFlow(J)) {
2687239310Sdim    Dependence = true;
2688239310Sdim    return false;
2689239310Sdim  }
2690239310Sdim
2691239310Sdim  // A LoopN instruction cannot appear in the same packet as a jump or call.
2692239310Sdim  if (IsLoopN(I) && (   IsDirectJump(J)
2693239310Sdim                     || MCIDJ.isCall()
2694239310Sdim                     || QII->isDeallocRet(J))) {
2695239310Sdim    Dependence = true;
2696239310Sdim    return false;
2697239310Sdim  }
2698239310Sdim  if (IsLoopN(J) && (   IsDirectJump(I)
2699239310Sdim                     || MCIDI.isCall()
2700239310Sdim                     || QII->isDeallocRet(I))) {
2701239310Sdim    Dependence = true;
2702239310Sdim    return false;
2703239310Sdim  }
2704239310Sdim
2705239310Sdim  // dealloc_return cannot appear in the same packet as a conditional or
2706239310Sdim  // unconditional jump.
2707239310Sdim  if (QII->isDeallocRet(I) && (   MCIDJ.isBranch()
2708239310Sdim                               || MCIDJ.isCall()
2709239310Sdim                               || MCIDJ.isBarrier())) {
2710239310Sdim    Dependence = true;
2711239310Sdim    return false;
2712239310Sdim  }
2713239310Sdim
2714239310Sdim
2715239310Sdim  // V4 allows dual store. But does not allow second store, if the
2716239310Sdim  // first store is not in SLOT0. New value store, new value jump,
2717239310Sdim  // dealloc_return and memop always take SLOT0.
2718239310Sdim  // Arch spec 3.4.4.2
2719239310Sdim  if (QRI->Subtarget.hasV4TOps()) {
2720249423Sdim    if (MCIDI.mayStore() && MCIDJ.mayStore() &&
2721249423Sdim       (QII->isNewValueInst(J) || QII->isMemOp(J) || QII->isMemOp(I))) {
2722239310Sdim      Dependence = true;
2723239310Sdim      return false;
2724239310Sdim    }
2725239310Sdim
2726249423Sdim    if ((QII->isMemOp(J) && MCIDI.mayStore())
2727239310Sdim        || (MCIDJ.mayStore() && QII->isMemOp(I))
2728239310Sdim        || (QII->isMemOp(J) && QII->isMemOp(I))) {
2729239310Sdim      Dependence = true;
2730239310Sdim      return false;
2731239310Sdim    }
2732239310Sdim
2733239310Sdim    //if dealloc_return
2734239310Sdim    if (MCIDJ.mayStore() && QII->isDeallocRet(I)){
2735239310Sdim      Dependence = true;
2736239310Sdim      return false;
2737239310Sdim    }
2738239310Sdim
2739239310Sdim    // If an instruction feeds new value jump, glue it.
2740239310Sdim    MachineBasicBlock::iterator NextMII = I;
2741239310Sdim    ++NextMII;
2742239310Sdim    MachineInstr *NextMI = NextMII;
2743239310Sdim
2744239310Sdim    if (QII->isNewValueJump(NextMI)) {
2745239310Sdim
2746239310Sdim      bool secondRegMatch = false;
2747239310Sdim      bool maintainNewValueJump = false;
2748239310Sdim
2749239310Sdim      if (NextMI->getOperand(1).isReg() &&
2750239310Sdim          I->getOperand(0).getReg() == NextMI->getOperand(1).getReg()) {
2751239310Sdim        secondRegMatch = true;
2752239310Sdim        maintainNewValueJump = true;
2753239310Sdim      }
2754239310Sdim
2755239310Sdim      if (!secondRegMatch &&
2756239310Sdim           I->getOperand(0).getReg() == NextMI->getOperand(0).getReg()) {
2757239310Sdim        maintainNewValueJump = true;
2758239310Sdim      }
2759239310Sdim
2760239310Sdim      for (std::vector<MachineInstr*>::iterator
2761239310Sdim            VI = CurrentPacketMIs.begin(),
2762239310Sdim             VE = CurrentPacketMIs.end();
2763239310Sdim           (VI != VE && maintainNewValueJump); ++VI) {
2764239310Sdim        SUnit* PacketSU = MIToSUnit[*VI];
2765239310Sdim
2766239310Sdim        // NVJ can not be part of the dual jump - Arch Spec: section 7.8
2767239310Sdim        if (PacketSU->getInstr()->getDesc().isCall()) {
2768239310Sdim          Dependence = true;
2769239310Sdim          break;
2770239310Sdim        }
2771239310Sdim        // Validate
2772239310Sdim        // 1. Packet does not have a store in it.
2773239310Sdim        // 2. If the first operand of the nvj is newified, and the second
2774239310Sdim        //    operand is also a reg, it (second reg) is not defined in
2775239310Sdim        //    the same packet.
2776239310Sdim        // 3. If the second operand of the nvj is newified, (which means
2777239310Sdim        //    first operand is also a reg), first reg is not defined in
2778239310Sdim        //    the same packet.
2779239310Sdim        if (PacketSU->getInstr()->getDesc().mayStore()               ||
2780239310Sdim            PacketSU->getInstr()->getOpcode() == Hexagon::ALLOCFRAME ||
2781239310Sdim            // Check #2.
2782239310Sdim            (!secondRegMatch && NextMI->getOperand(1).isReg() &&
2783239310Sdim             PacketSU->getInstr()->modifiesRegister(
2784239310Sdim                               NextMI->getOperand(1).getReg(), QRI)) ||
2785239310Sdim            // Check #3.
2786239310Sdim            (secondRegMatch &&
2787239310Sdim             PacketSU->getInstr()->modifiesRegister(
2788239310Sdim                               NextMI->getOperand(0).getReg(), QRI))) {
2789239310Sdim          Dependence = true;
2790239310Sdim          break;
2791239310Sdim        }
2792239310Sdim      }
2793239310Sdim      if (!Dependence)
2794239310Sdim        GlueToNewValueJump = true;
2795239310Sdim      else
2796239310Sdim        return false;
2797239310Sdim    }
2798239310Sdim  }
2799239310Sdim
2800239310Sdim  if (SUJ->isSucc(SUI)) {
2801239310Sdim    for (unsigned i = 0;
2802239310Sdim         (i < SUJ->Succs.size()) && !FoundSequentialDependence;
2803239310Sdim         ++i) {
2804239310Sdim
2805239310Sdim      if (SUJ->Succs[i].getSUnit() != SUI) {
2806239310Sdim        continue;
2807239310Sdim      }
2808239310Sdim
2809239310Sdim      SDep::Kind DepType = SUJ->Succs[i].getKind();
2810239310Sdim
2811239310Sdim      // For direct calls:
2812239310Sdim      // Ignore register dependences for call instructions for
2813239310Sdim      // packetization purposes except for those due to r31 and
2814239310Sdim      // predicate registers.
2815239310Sdim      //
2816239310Sdim      // For indirect calls:
2817239310Sdim      // Same as direct calls + check for true dependences to the register
2818239310Sdim      // used in the indirect call.
2819239310Sdim      //
2820239310Sdim      // We completely ignore Order dependences for call instructions
2821239310Sdim      //
2822239310Sdim      // For returns:
2823239310Sdim      // Ignore register dependences for return instructions like jumpr,
2824239310Sdim      // dealloc return unless we have dependencies on the explicit uses
2825239310Sdim      // of the registers used by jumpr (like r31) or dealloc return
2826239310Sdim      // (like r29 or r30).
2827239310Sdim      //
2828239310Sdim      // TODO: Currently, jumpr is handling only return of r31. So, the
2829239310Sdim      // following logic (specificaly IsCallDependent) is working fine.
2830239310Sdim      // We need to enable jumpr for register other than r31 and then,
2831239310Sdim      // we need to rework the last part, where it handles indirect call
2832239310Sdim      // of that (IsCallDependent) function. Bug 6216 is opened for this.
2833239310Sdim      //
2834239310Sdim      unsigned DepReg = 0;
2835239310Sdim      const TargetRegisterClass* RC = NULL;
2836239310Sdim      if (DepType == SDep::Data) {
2837239310Sdim        DepReg = SUJ->Succs[i].getReg();
2838239310Sdim        RC = QRI->getMinimalPhysRegClass(DepReg);
2839239310Sdim      }
2840239310Sdim      if ((MCIDI.isCall() || MCIDI.isReturn()) &&
2841239310Sdim          (!IsRegDependence(DepType) ||
2842239310Sdim            !IsCallDependent(I, DepType, SUJ->Succs[i].getReg()))) {
2843239310Sdim        /* do nothing */
2844239310Sdim      }
2845239310Sdim
2846239310Sdim      // For instructions that can be promoted to dot-new, try to promote.
2847239310Sdim      else if ((DepType == SDep::Data) &&
2848239310Sdim               CanPromoteToDotNew(I, SUJ, DepReg, MIToSUnit, II, RC) &&
2849239310Sdim               PromoteToDotNew(I, DepType, II, RC)) {
2850239310Sdim        PromotedToDotNew = true;
2851239310Sdim        /* do nothing */
2852239310Sdim      }
2853239310Sdim
2854239310Sdim      else if ((DepType == SDep::Data) &&
2855239310Sdim               (QII->isNewValueJump(I))) {
2856239310Sdim        /* do nothing */
2857239310Sdim      }
2858239310Sdim
2859239310Sdim      // For predicated instructions, if the predicates are complements
2860239310Sdim      // then there can be no dependence.
2861239310Sdim      else if (QII->isPredicated(I) &&
2862239310Sdim               QII->isPredicated(J) &&
2863239310Sdim          ArePredicatesComplements(I, J, MIToSUnit)) {
2864239310Sdim        /* do nothing */
2865239310Sdim
2866239310Sdim      }
2867239310Sdim      else if (IsDirectJump(I) &&
2868239310Sdim               !MCIDJ.isBranch() &&
2869239310Sdim               !MCIDJ.isCall() &&
2870239310Sdim               (DepType == SDep::Order)) {
2871239310Sdim        // Ignore Order dependences between unconditional direct branches
2872239310Sdim        // and non-control-flow instructions
2873239310Sdim        /* do nothing */
2874239310Sdim      }
2875239310Sdim      else if (MCIDI.isConditionalBranch() && (DepType != SDep::Data) &&
2876239310Sdim               (DepType != SDep::Output)) {
2877239310Sdim        // Ignore all dependences for jumps except for true and output
2878239310Sdim        // dependences
2879239310Sdim        /* do nothing */
2880239310Sdim      }
2881239310Sdim
2882239310Sdim      // Ignore output dependences due to superregs. We can
2883239310Sdim      // write to two different subregisters of R1:0 for instance
2884239310Sdim      // in the same cycle
2885239310Sdim      //
2886239310Sdim
2887239310Sdim      //
2888239310Sdim      // Let the
2889239310Sdim      // If neither I nor J defines DepReg, then this is a
2890239310Sdim      // superfluous output dependence. The dependence must be of the
2891239310Sdim      // form:
2892239310Sdim      //  R0 = ...
2893239310Sdim      //  R1 = ...
2894239310Sdim      // and there is an output dependence between the two instructions
2895239310Sdim      // with
2896239310Sdim      // DepReg = D0
2897239310Sdim      // We want to ignore these dependences.
2898239310Sdim      // Ideally, the dependence constructor should annotate such
2899239310Sdim      // dependences. We can then avoid this relatively expensive check.
2900239310Sdim      //
2901239310Sdim      else if (DepType == SDep::Output) {
2902239310Sdim        // DepReg is the register that's responsible for the dependence.
2903239310Sdim        unsigned DepReg = SUJ->Succs[i].getReg();
2904239310Sdim
2905239310Sdim        // Check if I and J really defines DepReg.
2906239310Sdim        if (I->definesRegister(DepReg) ||
2907239310Sdim            J->definesRegister(DepReg)) {
2908239310Sdim          FoundSequentialDependence = true;
2909239310Sdim          break;
2910239310Sdim        }
2911239310Sdim      }
2912239310Sdim
2913239310Sdim      // We ignore Order dependences for
2914239310Sdim      // 1. Two loads unless they are volatile.
2915239310Sdim      // 2. Two stores in V4 unless they are volatile.
2916239310Sdim      else if ((DepType == SDep::Order) &&
2917243830Sdim               !I->hasOrderedMemoryRef() &&
2918243830Sdim               !J->hasOrderedMemoryRef()) {
2919239310Sdim        if (QRI->Subtarget.hasV4TOps() &&
2920239310Sdim            // hexagonv4 allows dual store.
2921239310Sdim            MCIDI.mayStore() && MCIDJ.mayStore()) {
2922239310Sdim          /* do nothing */
2923239310Sdim        }
2924239310Sdim        // store followed by store-- not OK on V2
2925239310Sdim        // store followed by load -- not OK on all (OK if addresses
2926239310Sdim        // are not aliased)
2927239310Sdim        // load followed by store -- OK on all
2928239310Sdim        // load followed by load  -- OK on all
2929239310Sdim        else if ( !MCIDJ.mayStore()) {
2930239310Sdim          /* do nothing */
2931239310Sdim        }
2932239310Sdim        else {
2933239310Sdim          FoundSequentialDependence = true;
2934239310Sdim          break;
2935239310Sdim        }
2936239310Sdim      }
2937239310Sdim
2938239310Sdim      // For V4, special case ALLOCFRAME. Even though there is dependency
2939239310Sdim      // between ALLOCAFRAME and subsequent store, allow it to be
2940239310Sdim      // packetized in a same packet. This implies that the store is using
2941239310Sdim      // caller's SP. Hense, offset needs to be updated accordingly.
2942239310Sdim      else if (DepType == SDep::Data
2943239310Sdim               && QRI->Subtarget.hasV4TOps()
2944239310Sdim               && J->getOpcode() == Hexagon::ALLOCFRAME
2945239310Sdim               && (I->getOpcode() == Hexagon::STrid
2946239310Sdim                   || I->getOpcode() == Hexagon::STriw
2947239310Sdim                   || I->getOpcode() == Hexagon::STrib)
2948239310Sdim               && I->getOperand(0).getReg() == QRI->getStackRegister()
2949239310Sdim               && QII->isValidOffset(I->getOpcode(),
2950239310Sdim                                     I->getOperand(1).getImm() -
2951239310Sdim                                     (FrameSize + HEXAGON_LRFP_SIZE)))
2952239310Sdim      {
2953239310Sdim        GlueAllocframeStore = true;
2954239310Sdim        // Since this store is to be glued with allocframe in the same
2955239310Sdim        // packet, it will use SP of the previous stack frame, i.e
2956239310Sdim        // caller's SP. Therefore, we need to recalculate offset according
2957239310Sdim        // to this change.
2958239310Sdim        I->getOperand(1).setImm(I->getOperand(1).getImm() -
2959239310Sdim                                        (FrameSize + HEXAGON_LRFP_SIZE));
2960239310Sdim      }
2961239310Sdim
2962239310Sdim      //
2963239310Sdim      // Skip over anti-dependences. Two instructions that are
2964239310Sdim      // anti-dependent can share a packet
2965239310Sdim      //
2966239310Sdim      else if (DepType != SDep::Anti) {
2967239310Sdim        FoundSequentialDependence = true;
2968239310Sdim        break;
2969239310Sdim      }
2970239310Sdim    }
2971239310Sdim
2972239310Sdim    if (FoundSequentialDependence) {
2973239310Sdim      Dependence = true;
2974239310Sdim      return false;
2975239310Sdim    }
2976239310Sdim  }
2977239310Sdim
2978239310Sdim  return true;
2979239310Sdim}
2980239310Sdim
2981239310Sdim// isLegalToPruneDependencies
2982239310Sdimbool HexagonPacketizerList::isLegalToPruneDependencies(SUnit *SUI, SUnit *SUJ) {
2983239310Sdim  MachineInstr *I = SUI->getInstr();
2984239310Sdim  assert(I && SUJ->getInstr() && "Unable to packetize null instruction!");
2985239310Sdim
2986239310Sdim  const unsigned FrameSize = MF.getFrameInfo()->getStackSize();
2987239310Sdim
2988239310Sdim  if (Dependence) {
2989239310Sdim
2990239310Sdim    // Check if the instruction was promoted to a dot-new. If so, demote it
2991239310Sdim    // back into a dot-old.
2992239310Sdim    if (PromotedToDotNew) {
2993239310Sdim      DemoteToDotOld(I);
2994239310Sdim    }
2995239310Sdim
2996239310Sdim    // Check if the instruction (must be a store) was glued with an Allocframe
2997239310Sdim    // instruction. If so, restore its offset to its original value, i.e. use
2998239310Sdim    // curent SP instead of caller's SP.
2999239310Sdim    if (GlueAllocframeStore) {
3000239310Sdim      I->getOperand(1).setImm(I->getOperand(1).getImm() +
3001239310Sdim                                             FrameSize + HEXAGON_LRFP_SIZE);
3002239310Sdim    }
3003239310Sdim
3004239310Sdim    return false;
3005239310Sdim  }
3006239310Sdim  return true;
3007239310Sdim}
3008239310Sdim
3009239310SdimMachineBasicBlock::iterator
3010239310SdimHexagonPacketizerList::addToPacket(MachineInstr *MI) {
3011239310Sdim
3012239310Sdim    MachineBasicBlock::iterator MII = MI;
3013239310Sdim    MachineBasicBlock *MBB = MI->getParent();
3014239310Sdim
3015239310Sdim    const HexagonInstrInfo *QII = (const HexagonInstrInfo *) TII;
3016239310Sdim
3017239310Sdim    if (GlueToNewValueJump) {
3018239310Sdim
3019239310Sdim      ++MII;
3020239310Sdim      MachineInstr *nvjMI = MII;
3021239310Sdim      assert(ResourceTracker->canReserveResources(MI));
3022239310Sdim      ResourceTracker->reserveResources(MI);
3023249423Sdim      if ((QII->isExtended(MI) || QII->isConstExtended(MI)) &&
3024239310Sdim          !tryAllocateResourcesForConstExt(MI)) {
3025239310Sdim        endPacket(MBB, MI);
3026239310Sdim        ResourceTracker->reserveResources(MI);
3027239310Sdim        assert(canReserveResourcesForConstExt(MI) &&
3028239310Sdim               "Ensure that there is a slot");
3029239310Sdim        reserveResourcesForConstExt(MI);
3030239310Sdim        // Reserve resources for new value jump constant extender.
3031239310Sdim        assert(canReserveResourcesForConstExt(MI) &&
3032239310Sdim               "Ensure that there is a slot");
3033239310Sdim        reserveResourcesForConstExt(nvjMI);
3034239310Sdim        assert(ResourceTracker->canReserveResources(nvjMI) &&
3035239310Sdim               "Ensure that there is a slot");
3036239310Sdim
3037239310Sdim      } else if (   // Extended instruction takes two slots in the packet.
3038239310Sdim        // Try reserve and allocate 4-byte in the current packet first.
3039239310Sdim        (QII->isExtended(nvjMI)
3040239310Sdim            && (!tryAllocateResourcesForConstExt(nvjMI)
3041239310Sdim                || !ResourceTracker->canReserveResources(nvjMI)))
3042239310Sdim        || // For non-extended instruction, no need to allocate extra 4 bytes.
3043249423Sdim        (!QII->isExtended(nvjMI) &&
3044239310Sdim              !ResourceTracker->canReserveResources(nvjMI)))
3045239310Sdim      {
3046239310Sdim        endPacket(MBB, MI);
3047239310Sdim        // A new and empty packet starts.
3048239310Sdim        // We are sure that the resources requirements can be satisfied.
3049239310Sdim        // Therefore, do not need to call "canReserveResources" anymore.
3050239310Sdim        ResourceTracker->reserveResources(MI);
3051239310Sdim        if (QII->isExtended(nvjMI))
3052239310Sdim          reserveResourcesForConstExt(nvjMI);
3053239310Sdim      }
3054239310Sdim      // Here, we are sure that "reserveResources" would succeed.
3055239310Sdim      ResourceTracker->reserveResources(nvjMI);
3056239310Sdim      CurrentPacketMIs.push_back(MI);
3057239310Sdim      CurrentPacketMIs.push_back(nvjMI);
3058239310Sdim    } else {
3059249423Sdim      if (   (QII->isExtended(MI) || QII->isConstExtended(MI))
3060239310Sdim          && (   !tryAllocateResourcesForConstExt(MI)
3061239310Sdim              || !ResourceTracker->canReserveResources(MI)))
3062239310Sdim      {
3063239310Sdim        endPacket(MBB, MI);
3064239310Sdim        // Check if the instruction was promoted to a dot-new. If so, demote it
3065239310Sdim        // back into a dot-old
3066239310Sdim        if (PromotedToDotNew) {
3067239310Sdim          DemoteToDotOld(MI);
3068239310Sdim        }
3069239310Sdim        reserveResourcesForConstExt(MI);
3070239310Sdim      }
3071239310Sdim      // In case that "MI" is not an extended insn,
3072239310Sdim      // the resource availability has already been checked.
3073239310Sdim      ResourceTracker->reserveResources(MI);
3074239310Sdim      CurrentPacketMIs.push_back(MI);
3075239310Sdim    }
3076239310Sdim    return MII;
3077239310Sdim}
3078239310Sdim
3079239310Sdim//===----------------------------------------------------------------------===//
3080239310Sdim//                         Public Constructor Functions
3081239310Sdim//===----------------------------------------------------------------------===//
3082239310Sdim
3083239310SdimFunctionPass *llvm::createHexagonPacketizer() {
3084239310Sdim  return new HexagonPacketizer();
3085239310Sdim}
3086239310Sdim
3087