<s> Register IndReg = DI -> getOperand ( <NUM_LIT> ) . getReg ( ) ; MachineOperand & Opnd2 = DI -> getOperand ( <NUM_LIT> ) ; int64_t V ; if ( MRI -> getVRegDef ( IndReg ) == Phi && checkForImmediate ( Opnd2 , V ) ) { Register UpdReg = DI -> getOperand ( <NUM_LIT> ) . getReg ( ) ; IndMap . insert ( std :: make_pair ( UpdReg , std :: make_pair ( IndReg , V ) ) ) ; } } } } SmallVector < MachineOperand , <NUM_LIT> > Cond ; MachineBasicBlock * TB = nullptr , * FB = nullptr ; bool NotAnalyzed = TII -> analyzeBranch ( * ExitingBlock , TB , FB , Cond , false ) ; if ( NotAnalyzed ) return false ; unsigned PredR , PredPos , PredRegFlags ; if ( ! TII -> getPredReg ( Cond , PredR , PredPos , PredRegFlags ) ) return false ; MachineInstr * PredI = MRI -> getVRegDef ( PredR ) ; if ( ! PredI -> isCompare ( ) ) return false ; Register CmpReg1 , CmpReg2 ; int CmpImm = <NUM_LIT> , CmpMask = <NUM_LIT> ; bool CmpAnalyzed = TII -> analyzeCompare ( * PredI , CmpReg1 , CmpReg2 , CmpMask , CmpImm ) ; if ( ! CmpAnalyzed ) return false ; InductionMap :: iterator IndMapEnd = IndMap . end ( ) ; InductionMap :: iterator F = IndMapEnd ; if ( CmpReg1 != <NUM_LIT> ) { InductionMap :: iterator F1 = IndMap . find ( CmpReg1 ) ; if ( F1 != IndMapEnd ) F = F1 ; } if ( CmpReg2 != <NUM_LIT> ) {

InductionMap :: iterator F2 = IndMap . find ( CmpReg2 ) ;


<s> bool NotAnalyzed = TII -> analyzeBranch ( * Latch , LTB , LFB , LCond , false ) ; if ( NotAnalyzed ) return nullptr ; if ( TB == Latch ) TB = ( LTB == Header ) ? LTB : LFB ; else FB = ( LTB == Header ) ? LTB : LFB ; } assert ( ( ! FB || TB == Header || FB == Header ) && <STR_LIT> ) ; if ( ! TB || ( FB && TB != Header && FB != Header ) ) return nullptr ; bool Negated = TII -> predOpcodeHasNot ( Cond ) ^ ( TB != Header ) ; unsigned PredReg , PredPos , PredRegFlags ; if ( ! TII -> getPredReg ( Cond , PredReg , PredPos , PredRegFlags ) ) return nullptr ; MachineInstr * CondI = MRI -> getVRegDef ( PredReg ) ; unsigned CondOpc = CondI -> getOpcode ( ) ; Register CmpReg1 , CmpReg2 ; int Mask = <NUM_LIT> , ImmValue = <NUM_LIT> ; bool AnalyzedCmp = TII -> analyzeCompare ( * CondI , CmpReg1 , CmpReg2 , Mask , ImmValue ) ; if ( ! AnalyzedCmp ) return nullptr ; OldInsts . push_back ( CondI ) ; OldInsts . push_back ( IVOp ) ; Comparison :: Kind Cmp ; bool isSwapped = false ; const MachineOperand & Op1 = CondI -> getOperand ( <NUM_LIT> ) ; const MachineOperand & Op2 = CondI -> getOperand ( <NUM_LIT> ) ; const MachineOperand * EndValue = nullptr ; if ( Op1 . isReg ( ) ) { if ( Op2 . isImm ( ) || Op1 . getReg ( ) == IVReg ) EndValue = & Op2 ;


<s> for ( unsigned i = <NUM_LIT> , e = MI -> getNumOperands ( ) ; i != e ; ++ i ) { const MachineOperand & MO = MI -> getOperand ( i ) ; if ( ! MO . isReg ( ) || ! MO . isDef ( ) ) continue ; Register Reg = MO . getReg ( ) ; MachineRegisterInfo :: use_iterator nextI ; for ( MachineRegisterInfo :: use_iterator I = MRI -> use_begin ( Reg ) , E = MRI -> use_end ( ) ; I != E ; I = nextI ) { nextI = std :: next ( I ) ; MachineInstr * UseMI = I -> getParent ( ) ; if ( UseMI == MI ) continue ; if ( I -> isDebug ( ) ) I -> setReg ( <NUM_LIT> ) ; } } MI -> eraseFromParent ( ) ; for ( unsigned i = <NUM_LIT> ; i < DeadPhis . size ( ) ; ++ i ) DeadPhis [ i ] -> eraseFromParent ( ) ;


<s> const MachineOperand & S1 = DI -> getOperand ( <NUM_LIT> ) ; const MachineOperand & S2 = DI -> getOperand ( <NUM_LIT> ) ; int64_t V1 , V2 ; if ( ! checkForImmediate ( S1 , V1 ) || ! checkForImmediate ( S2 , V2 ) ) return false ; TV = V2 | ( V1 << <NUM_LIT> ) ; break ; } case TargetOpcode :: REG_SEQUENCE : { const MachineOperand & S1 = DI -> getOperand ( <NUM_LIT> ) ; const MachineOperand & S3 = DI -> getOperand ( <NUM_LIT> ) ; int64_t V1 , V3 ; if ( ! checkForImmediate ( S1 , V1 ) || ! checkForImmediate ( S3 , V3 ) ) return false ; unsigned Sub2 = DI -> getOperand ( <NUM_LIT> ) . getImm ( ) ; unsigned Sub4 = DI -> getOperand ( <NUM_LIT> ) . getImm ( ) ; if ( Sub2 == <STR_LIT> && Sub4 == <STR_LIT> ) TV = V1 | ( V3 << <NUM_LIT> ) ; else if ( Sub2 == <STR_LIT> && Sub4 == <STR_LIT> ) TV = V3 | ( V1 << <NUM_LIT> ) ; else llvm_unreachable ( <STR_LIT> ) ; break ; }


<s> if ( ! checkForImmediate ( S1 , V1 ) || ! checkForImmediate ( S3 , V3 ) ) return false ; unsigned Sub2 = DI -> getOperand ( <NUM_LIT> ) . getImm ( ) ; unsigned Sub4 = DI -> getOperand ( <NUM_LIT> ) . getImm ( ) ; if ( Sub2 == <STR_LIT> && Sub4 == <STR_LIT> ) TV = V1 | ( V3 << <NUM_LIT> ) ; else if ( Sub2 == <STR_LIT> && Sub4 == <STR_LIT> ) TV = V3 | ( V1 << <NUM_LIT> ) ; else llvm_unreachable ( <STR_LIT> ) ; break ; } default : return false ; } switch ( MO . getSubReg ( ) ) { case <STR_LIT> : Val = TV & <NUM_LIT> ; break ; case <STR_LIT> : Val = ( TV >> <NUM_LIT> ) & <NUM_LIT> ; break ; default : Val = TV ; break ; }


<s> else if ( L -> contains ( FB ) ) LoopStart = FB ; else return false ; } else LoopStart = TopBlock ; DEBUG ( dbgs ( ) << <STR_LIT> ; L -> dump ( ) ) ; DebugLoc DL ; if ( InsertPos != Preheader -> end ( ) ) DL = InsertPos -> getDebugLoc ( ) ; if ( TripCount -> isReg ( ) ) { unsigned CountReg = MRI -> createVirtualRegister ( & <STR_LIT> ) ; BuildMI ( * Preheader , InsertPos , DL , TII -> get ( TargetOpcode :: COPY ) , CountReg ) . addReg ( TripCount -> getReg ( ) , <NUM_LIT> , TripCount -> getSubReg ( ) ) ; BuildMI ( * Preheader , InsertPos , DL , TII -> get ( LOOP_r ) ) . addMBB ( LoopStart ) . addReg ( CountReg ) ; } else { assert ( TripCount -> isImm ( ) && <STR_LIT> ) ; int64_t CountImm = TripCount -> getImm ( ) ; if ( ! TII -> isValidOffset ( LOOP_i , CountImm ) ) { unsigned CountReg = MRI -> createVirtualRegister ( & <STR_LIT> ) ; BuildMI ( * Preheader , InsertPos , DL , TII -> get ( <STR_LIT> ) , CountReg ) . addImm ( CountImm ) ; BuildMI ( * Preheader , InsertPos , DL , TII -> get ( LOOP_r ) ) . addMBB ( LoopStart ) . addReg ( CountReg ) ; } else BuildMI ( * Preheader , InsertPos , DL , TII -> get ( LOOP_i ) ) . addMBB ( LoopStart ) . addImm ( CountImm ) ; } LoopStart -> setHasAddressTaken ( ) ; BlockAddress :: get ( const_cast < BasicBlock * > ( LoopStart -> getBasicBlock ( ) ) ) ; DebugLoc LastIDL = LastI -> getDebugLoc ( ) ; BuildMI ( * LastMBB , LastI , LastIDL , TII -> get ( ENDLOOP ) ) . addMBB ( LoopStart ) ;

if ( LastI -> getOpcode ( ) == <STR_LIT> || LastI -> getOpcode ( ) == <STR_LIT> ) {


<s> I != E && I -> isPHI ( ) ; ++ I ) { MachineInstr * PN = & * I ; for ( unsigned i = <NUM_LIT> , n = PN -> getNumOperands ( ) ; i < n ; i += <NUM_LIT> ) { MachineOperand & MO = PN -> getOperand ( i + <NUM_LIT> ) ; if ( MO . getMBB ( ) != Latch ) MO . setMBB ( NewPH ) ; } } } SmallVector < MachineOperand , <NUM_LIT> > Tmp2 ; SmallVector < MachineOperand , <NUM_LIT> > EmptyCond ; TB = FB = nullptr ; for ( MBBVector :: iterator I = Preds . begin ( ) , E = Preds . end ( ) ; I != E ; ++ I ) { MachineBasicBlock * PB = * I ; if ( PB != Latch ) { Tmp2 . clear ( ) ; bool NotAnalyzed = TII -> analyzeBranch ( * PB , TB , FB , Tmp2 , false ) ; ( void ) NotAnalyzed ; assert ( ! NotAnalyzed && <STR_LIT> ) ; if ( TB != Header && ( Tmp2 . empty ( ) || FB != Header ) ) TII -> InsertBranch ( * PB , NewPH , nullptr , EmptyCond , DL ) ; PB -> ReplaceUsesOfBlockWith ( Header , NewPH ) ; } } TB = FB = nullptr ; bool LatchNotAnalyzed = TII -> analyzeBranch ( * Latch , TB , FB , Tmp2 , false ) ; ( void ) LatchNotAnalyzed ; assert ( ! LatchNotAnalyzed && <STR_LIT> ) ; if ( ! TB && ! FB ) TII -> InsertBranch ( * Latch , Header , nullptr , EmptyCond , DL ) ; TII -> InsertBranch ( * NewPH , Header , nullptr , EmptyCond , DL ) ; NewPH -> addSuccessor ( Header ) ; MachineLoop * ParentLoop = L -> getParentLoop ( ) ; if ( ParentLoop ) ParentLoop -> addBasicBlockToLoop ( NewPH , MLI -> getBase ( ) ) ; if ( MDT ) { if ( MachineDomTreeNode * HN = MDT -> getNode ( Header ) ) { if ( MachineDomTreeNode * DHN = HN -> getIDom ( ) ) {

MDT -> addNewBlock ( NewPH , DHN -> getBlock ( ) ) ;


<s> MachineBasicBlock * TB = nullptr , * FB = nullptr ; bool NotAnalyzed = TII -> analyzeBranch ( * ExitingBlock , TB , FB , Cond , false ) ; if ( NotAnalyzed ) return false ; unsigned PredR , PredPos , PredRegFlags ; if ( ! TII -> getPredReg ( Cond , PredR , PredPos , PredRegFlags ) ) return false ; MachineInstr * PredI = MRI -> getVRegDef ( PredR ) ; if ( ! PredI -> isCompare ( ) ) return false ; unsigned CmpReg1 = <NUM_LIT> , CmpReg2 = <NUM_LIT> ; int CmpImm = <NUM_LIT> , CmpMask = <NUM_LIT> ; bool CmpAnalyzed = TII -> analyzeCompare ( * PredI , CmpReg1 , CmpReg2 , CmpMask , CmpImm ) ; if ( ! CmpAnalyzed ) return false ; InductionMap :: iterator IndMapEnd = IndMap . end ( ) ; InductionMap :: iterator F = IndMapEnd ; if ( CmpReg1 != <NUM_LIT> ) { InductionMap :: iterator F1 = IndMap . find ( CmpReg1 ) ; if ( F1 != IndMapEnd ) F = F1 ; } if ( CmpReg2 != <NUM_LIT> ) { InductionMap :: iterator F2 = IndMap . find ( CmpReg2 ) ; if ( F2 != IndMapEnd ) { if ( F != IndMapEnd ) return false ;


<s> typedef MachineBasicBlock :: instr_iterator instr_iterator ; for ( instr_iterator I = Header -> instr_begin ( ) , E = Header -> instr_end ( ) ; I != E && I -> isPHI ( ) ; ++ I ) { MachineInstr * Phi = & * I ; for ( unsigned i = <NUM_LIT> , n = Phi -> getNumOperands ( ) ; i < n ; i += <NUM_LIT> ) { if ( Phi -> getOperand ( i + <NUM_LIT> ) . getMBB ( ) != Latch ) continue ; unsigned PhiOpReg = Phi -> getOperand ( i ) . getReg ( ) ; MachineInstr * DI = MRI -> getVRegDef ( PhiOpReg ) ; unsigned UpdOpc = DI -> getOpcode ( ) ; bool isAdd = ( UpdOpc == <STR_LIT> || UpdOpc == <STR_LIT> ) ; if ( isAdd ) { unsigned IndReg = DI -> getOperand ( <NUM_LIT> ) . getReg ( ) ; MachineOperand & Opnd2 = DI -> getOperand ( <NUM_LIT> ) ; int64_t V ; if ( MRI -> getVRegDef ( IndReg ) == Phi && checkForImmediate ( Opnd2 , V ) ) { unsigned UpdReg = DI -> getOperand ( <NUM_LIT> ) . getReg ( ) ; IndMap . insert ( std :: make_pair ( UpdReg , std :: make_pair ( IndReg , V ) ) ) ; } } } } SmallVector < MachineOperand , <NUM_LIT> > Cond ; MachineBasicBlock * TB = nullptr , * FB = nullptr ; bool NotAnalyzed = TII -> analyzeBranch ( * ExitingBlock , TB , FB , Cond , false ) ; if ( NotAnalyzed ) return false ; unsigned PredR , PredPos , PredRegFlags ; if ( ! TII -> getPredReg ( Cond , PredR , PredPos , PredRegFlags ) ) return false ; MachineInstr * PredI = MRI -> getVRegDef ( PredR ) ; if ( ! PredI -> isCompare ( ) ) return false ; unsigned CmpReg1 = <NUM_LIT> , CmpReg2 = <NUM_LIT> ; int CmpImm = <NUM_LIT> , CmpMask = <NUM_LIT> ; bool CmpAnalyzed = TII -> analyzeCompare ( * PredI , CmpReg1 , CmpReg2 , CmpMask , CmpImm ) ; if ( ! CmpAnalyzed ) return false ; InductionMap :: iterator IndMapEnd = IndMap . end ( ) ; InductionMap :: iterator F = IndMapEnd ;


<s> for ( MachineBasicBlock * S : Preheader -> successors ( ) ) { if ( S == HB ) continue ; MachineLoop * T = MLI -> getLoopFor ( S ) ; if ( T && T -> getHeader ( ) == S ) return nullptr ; }


<s> if ( HB -> pred_size ( ) != <NUM_LIT> || HB -> hasAddressTaken ( ) ) return nullptr ; MachineBasicBlock * Preheader = nullptr ; for ( MachineBasicBlock * P : HB -> predecessors ( ) ) { if ( P == LB ) continue ; if ( Preheader ) return nullptr ; Preheader = P ; }

for ( MachineBasicBlock * S : Preheader -> successors ( ) ) {


<s> if ( ! InitialValue ) return nullptr ; SmallVector < MachineOperand , <NUM_LIT> > Cond ; MachineBasicBlock * TB = nullptr , * FB = nullptr ; bool NotAnalyzed = TII -> analyzeBranch ( * ExitingBlock , TB , FB , Cond , false ) ; if ( NotAnalyzed ) return nullptr ; MachineBasicBlock * Header = L -> getHeader ( ) ; assert ( TB && <STR_LIT> ) ; if ( ExitingBlock != Latch && ( TB == Latch || FB == Latch ) ) { MachineBasicBlock * LTB = <NUM_LIT> , * LFB = <NUM_LIT> ; SmallVector < MachineOperand , <NUM_LIT> > LCond ; bool NotAnalyzed = TII -> analyzeBranch ( * Latch , LTB , LFB , LCond , false ) ; if ( NotAnalyzed ) return nullptr ; if ( TB == Latch ) TB = ( LTB == Header ) ? LTB : LFB ; else FB = ( LTB == Header ) ? LTB : LFB ; } assert ( ( ! FB || TB == Header || FB == Header ) && <STR_LIT> ) ; if ( ! TB || ( FB && TB != Header && FB != Header ) ) return nullptr ; bool Negated = TII -> predOpcodeHasNot ( Cond ) ^ ( TB != Header ) ; unsigned PredReg , PredPos , PredRegFlags ; if ( ! TII -> getPredReg ( Cond , PredReg , PredPos , PredRegFlags ) ) return nullptr ; MachineInstr * CondI = MRI -> getVRegDef ( PredReg ) ; unsigned CondOpc = CondI -> getOpcode ( ) ; unsigned CmpReg1 = <NUM_LIT> , CmpReg2 = <NUM_LIT> ; int Mask = <NUM_LIT> , ImmValue = <NUM_LIT> ; bool AnalyzedCmp = TII -> analyzeCompare ( * CondI , CmpReg1 , CmpReg2 , Mask , ImmValue ) ; if ( ! AnalyzedCmp ) return nullptr ; OldInsts . push_back ( CondI ) ;


<s> SmallVector < MachineOperand , <NUM_LIT> > LCond ; bool NotAnalyzed = TII -> analyzeBranch ( * Latch , LTB , LFB , LCond , false ) ; if ( NotAnalyzed ) return nullptr ; if ( TB == Latch ) TB = ( LTB == Header ) ? LTB : LFB ; else FB = ( LTB == Header ) ? LTB : LFB ; } assert ( ( ! FB || TB == Header || FB == Header ) && <STR_LIT> ) ; if ( ! TB || ( FB && TB != Header && FB != Header ) ) return nullptr ; bool Negated = TII -> predOpcodeHasNot ( Cond ) ^ ( TB != Header ) ; unsigned PredReg , PredPos , PredRegFlags ; if ( ! TII -> getPredReg ( Cond , PredReg , PredPos , PredRegFlags ) ) return nullptr ; MachineInstr * CondI = MRI -> getVRegDef ( PredReg ) ; unsigned CondOpc = CondI -> getOpcode ( ) ; unsigned CmpReg1 = <NUM_LIT> , CmpReg2 = <NUM_LIT> ; int Mask = <NUM_LIT> , ImmValue = <NUM_LIT> ; bool AnalyzedCmp = TII -> analyzeCompare ( * CondI , CmpReg1 , CmpReg2 , Mask , ImmValue ) ; if ( ! AnalyzedCmp ) return nullptr ; OldInsts . push_back ( CondI ) ; OldInsts . push_back ( IVOp ) ; Comparison :: Kind Cmp ; bool isSwapped = false ; const MachineOperand & Op1 = CondI -> getOperand ( <NUM_LIT> ) ; const MachineOperand & Op2 = CondI -> getOperand ( <NUM_LIT> ) ; const MachineOperand * EndValue = nullptr ; if ( Op1 . isReg ( ) ) { if ( Op2 . isImm ( ) || Op1 . getReg ( ) == IVReg ) EndValue = & Op2 ; else { EndValue = & Op1 ; isSwapped = true ; } } if ( ! EndValue ) return nullptr ; Cmp = getComparisonKind ( CondOpc , InitialValue , EndValue , IVBump ) ; if ( ! Cmp ) return nullptr ; if ( Negated ) Cmp = Comparison :: getNegatedComparison ( Cmp ) ; if ( isSwapped ) Cmp = Comparison :: getSwappedComparison ( Cmp ) ; if ( InitialValue -> isReg ( ) ) { unsigned R = InitialValue -> getReg ( ) ; MachineBasicBlock * DefBB = MRI -> getVRegDef ( R ) -> getParent ( ) ; if ( ! MDT -> properlyDominates ( DefBB , Header ) ) return nullptr ;

OldInsts . push_back ( MRI -> getVRegDef ( R ) ) ;


<s> if ( MI -> getDesc ( ) . isCall ( ) && MI -> getOpcode ( ) != <STR_LIT> ) return true ; for ( unsigned i = <NUM_LIT> , e = MI -> getNumOperands ( ) ; i != e ; ++ i ) { const MachineOperand & MO = MI -> getOperand ( i ) ; if ( ! MO . isReg ( ) || ! MO . isDef ( ) ) continue ; unsigned R = MO . getReg ( ) ; if ( IsInnerHWLoop && ( R == <STR_LIT> || R == <STR_LIT> || R == <STR_LIT> || R == <STR_LIT> ) ) return true ; if ( ! IsInnerHWLoop && ( R == <STR_LIT> || R == <STR_LIT> ) ) return true ;


<s> for ( MachineRegisterInfo :: use_instr_nodbg_iterator I = MRI -> use_instr_nodbg_begin ( Reg ) , E = MRI -> use_instr_nodbg_end ( ) ; I != E ; ++ I ) { MachineInstr * MI = & * I ; unsigned CmpReg1 = <NUM_LIT> , CmpReg2 = <NUM_LIT> ; int CmpMask = <NUM_LIT> , CmpValue = <NUM_LIT> ; if ( ! TII -> analyzeCompare ( * MI , CmpReg1 , CmpReg2 , CmpMask , CmpValue ) ) continue ; MachineBasicBlock * TBB = <NUM_LIT> , * FBB = <NUM_LIT> ; SmallVector < MachineOperand , <NUM_LIT> > Cond ; if ( TII -> analyzeBranch ( * MI -> getParent ( ) , TBB , FBB , Cond , false ) ) continue ; Comparison :: Kind Cmp = getComparisonKind ( MI -> getOpcode ( ) , <NUM_LIT> , <NUM_LIT> , <NUM_LIT> ) ; if ( Cmp == <NUM_LIT> ) continue ;

if ( TII -> predOpcodeHasNot ( Cond ) ^ ( TBB != MBB ) ) Cmp = Comparison :: getNegatedComparison ( Cmp ) ;


<s> for ( MachineRegisterInfo :: use_instr_nodbg_iterator I = MRI -> use_instr_nodbg_begin ( Reg ) , E = MRI -> use_instr_nodbg_end ( ) ; I != E ; ++ I ) { MachineInstr * MI = & * I ; unsigned CmpReg1 = <NUM_LIT> , CmpReg2 = <NUM_LIT> ; int CmpMask = <NUM_LIT> , CmpValue = <NUM_LIT> ; if ( ! TII -> analyzeCompare ( * MI , CmpReg1 , CmpReg2 , CmpMask , CmpValue ) ) continue ; MachineBasicBlock * TBB = <NUM_LIT> , * FBB = <NUM_LIT> ; SmallVector < MachineOperand , <NUM_LIT> > Cond ; if ( TII -> analyzeBranch ( * MI -> getParent ( ) , TBB , FBB , Cond , false ) ) continue ; Comparison :: Kind Cmp = getComparisonKind ( MI -> getOpcode ( ) , <NUM_LIT> , <NUM_LIT> , <NUM_LIT> ) ; if ( Cmp == <NUM_LIT> ) continue ; if ( TII -> predOpcodeHasNot ( Cond ) ^ ( TBB != MBB ) ) Cmp = Comparison :: getNegatedComparison ( Cmp ) ; if ( CmpReg2 != <NUM_LIT> && CmpReg2 == Reg ) Cmp = Comparison :: getSwappedComparison ( Cmp ) ; if ( Comparison :: isSigned ( Cmp ) ) return false ; if ( ( Cmp & Comparison :: G ) || Cmp == Comparison :: NE ) return false ; } if ( ! Def -> isCopy ( ) && ! Def -> isPHI ( ) ) return false ;


<s> use_nodbg_iterator End = MRI -> use_nodbg_end ( ) ; if ( std :: next ( I ) != End || ! I . getOperand ( ) . getParent ( ) -> isPHI ( ) ) return false ; MachineInstr * OnePhi = I . getOperand ( ) . getParent ( ) ; for ( unsigned j = <NUM_LIT> , f = OnePhi -> getNumOperands ( ) ; j != f ; ++ j ) { const MachineOperand & OPO = OnePhi -> getOperand ( j ) ; if ( ! OPO . isReg ( ) || ! OPO . isDef ( ) ) continue ; unsigned OPReg = OPO . getReg ( ) ; use_nodbg_iterator nextJ ; for ( use_nodbg_iterator J = MRI -> use_nodbg_begin ( OPReg ) ; J != End ; J = nextJ ) { nextJ = std :: next ( J ) ; MachineOperand & Use = J . getOperand ( ) ; MachineInstr * UseMI = Use . getParent ( ) ; if ( MI != UseMI ) return false ; }


<s> if ( std :: next ( I ) != End || ! I . getOperand ( ) . getParent ( ) -> isPHI ( ) ) return false ; MachineInstr * OnePhi = I . getOperand ( ) . getParent ( ) ; for ( unsigned j = <NUM_LIT> , f = OnePhi -> getNumOperands ( ) ; j != f ; ++ j ) { const MachineOperand & OPO = OnePhi -> getOperand ( j ) ; if ( ! OPO . isReg ( ) || ! OPO . isDef ( ) ) continue ; unsigned OPReg = OPO . getReg ( ) ; use_nodbg_iterator nextJ ; for ( use_nodbg_iterator J = MRI -> use_nodbg_begin ( OPReg ) ; J != End ; J = nextJ ) { nextJ = std :: next ( J ) ; MachineOperand & Use = J . getOperand ( ) ; MachineInstr * UseMI = Use . getParent ( ) ;


<s> DEBUG ( dbgs ( ) << <STR_LIT> << * MI ) ; for ( unsigned i = <NUM_LIT> , e = MI -> getNumOperands ( ) ; i != e ; ++ i ) { const MachineOperand & MO = MI -> getOperand ( i ) ; if ( ! MO . isReg ( ) || ! MO . isDef ( ) ) continue ; unsigned Reg = MO . getReg ( ) ; MachineRegisterInfo :: use_iterator nextI ; for ( MachineRegisterInfo :: use_iterator I = MRI -> use_begin ( Reg ) , E = MRI -> use_end ( ) ; I != E ; I = nextI ) { nextI = std :: next ( I ) ; MachineOperand & Use = I . getOperand ( ) ; MachineInstr * UseMI = Use . getParent ( ) ; if ( UseMI == MI ) continue ; if ( Use . isDebug ( ) ) UseMI -> getOperand ( <NUM_LIT> ) . setReg ( <NUM_LIT> ) ; } } MI -> eraseFromParent ( ) ;

for ( unsigned i = <NUM_LIT> ; i < DeadPhis . size ( ) ; ++ i ) DeadPhis [ i ] -> eraseFromParent ( ) ;


<s> bool <ISA_LIT>HardwareLoops :: checkForImmediate ( const MachineOperand & MO , int64_t & Val ) const { if ( MO . isImm ( ) ) { Val = MO . getImm ( ) ; return true ; } if ( ! MO . isReg ( ) ) return false ; int64_t TV ; Register R = MO . getReg ( ) ; if ( ! Register :: isVirtualRegister ( R ) ) return false ; MachineInstr * DI = MRI -> getVRegDef ( R ) ; unsigned DOpc = DI -> getOpcode ( ) ; switch ( DOpc ) { case TargetOpcode :: COPY : case <STR_LIT> : case <STR_LIT> : case <STR_LIT> : case <STR_LIT> : if ( ! checkForImmediate ( DI -> getOperand ( <NUM_LIT> ) , TV ) ) return false ; break ; case <STR_LIT> : case <STR_LIT> : case <STR_LIT> : case <STR_LIT> : case <STR_LIT> : { const MachineOperand & S1 = DI -> getOperand ( <NUM_LIT> ) ; const MachineOperand & S2 = DI -> getOperand ( <NUM_LIT> ) ; int64_t V1 , V2 ;

if ( ! checkForImmediate ( S1 , V1 ) || ! checkForImmediate ( S2 , V2 ) ) return false ;


<s> LLVM_DEBUG ( dbgs ( ) << <STR_LIT> << printMBBReference ( * * L -> block_begin ( ) ) ) ; for ( MachineBasicBlock * MBB : L -> getBlocks ( ) ) { if ( A == MBB ) return false ;


<s> if ( checkForImmediate ( * InitVal , Imm ) ) return ( EndVal -> getImm ( ) == Imm ) ; Register Reg = InitVal -> getReg ( ) ; if ( ! Register :: isVirtualRegister ( Reg ) ) return true ; MachineInstr * Def = MRI -> getVRegDef ( Reg ) ; if ( ! Def ) return true ; if ( Def -> isPHI ( ) && ! phiMayWrapOrUnderflow ( Def , EndVal , Def -> getParent ( ) , L , LoopFeederPhi ) ) return false ; if ( Def -> isCopy ( ) && ! loopCountMayWrapOrUnderFlow ( & ( Def -> getOperand ( <NUM_LIT> ) ) , EndVal , Def -> getParent ( ) , L , LoopFeederPhi ) ) return false ; for ( MachineRegisterInfo :: use_instr_nodbg_iterator I = MRI -> use_instr_nodbg_begin ( Reg ) , E = MRI -> use_instr_nodbg_end ( ) ; I != E ; ++ I ) { MachineInstr * MI = & * I ; Register CmpReg1 , CmpReg2 ; int CmpMask = <NUM_LIT> , CmpValue = <NUM_LIT> ; if ( ! TII -> analyzeCompare ( * MI , CmpReg1 , CmpReg2 , CmpMask , CmpValue ) ) continue ; MachineBasicBlock * TBB = nullptr , * FBB = nullptr ; SmallVector < MachineOperand , <NUM_LIT> > Cond ; if ( TII -> analyzeBranch ( * MI -> getParent ( ) , TBB , FBB , Cond , false ) ) continue ; Comparison :: Kind Cmp = getComparisonKind ( MI -> getOpcode ( ) , nullptr , nullptr , <NUM_LIT> ) ; if ( Cmp == <NUM_LIT> ) continue ; if ( TII -> predOpcodeHasNot ( Cond ) ^ ( TBB != MBB ) ) Cmp = Comparison :: getNegatedComparison ( Cmp ) ; if ( CmpReg2 != <NUM_LIT> && CmpReg2 == Reg ) Cmp = Comparison :: getSwappedComparison ( Cmp ) ; if ( Comparison :: isSigned ( Cmp ) ) return false ; if ( ( Cmp & Comparison :: G ) || Cmp == Comparison :: NE ) return false ; } if ( ! Def -> isCopy ( ) && ! Def -> isPHI ( ) ) return false ; return true ;


<s> MachineOperand & Use = * I ; MachineInstr * UseMI = I -> getParent ( ) ; if ( UseMI == MI ) continue ; if ( Use . isDebug ( ) ) UseMI -> getOperand ( <NUM_LIT> ) . setReg ( <NUM_LIT> ) ; } } MI -> eraseFromParent ( ) ;


<s> I != E && I -> isPHI ( ) ; ++ I ) { MachineInstr * Phi = & * I ; for ( unsigned i = <NUM_LIT> , n = Phi -> getNumOperands ( ) ; i < n ; i += <NUM_LIT> ) { if ( Phi -> getOperand ( i + <NUM_LIT> ) . getMBB ( ) != Latch ) continue ; Register PhiOpReg = Phi -> getOperand ( i ) . getReg ( ) ; MachineInstr * DI = MRI -> getVRegDef ( PhiOpReg ) ; if ( DI -> getDesc ( ) . isAdd ( ) ) { Register IndReg = DI -> getOperand ( <NUM_LIT> ) . getReg ( ) ; MachineOperand & Opnd2 = DI -> getOperand ( <NUM_LIT> ) ; int64_t V ; if ( MRI -> getVRegDef ( IndReg ) == Phi && checkForImmediate ( Opnd2 , V ) ) { Register UpdReg = DI -> getOperand ( <NUM_LIT> ) . getReg ( ) ; IndMap . insert ( std :: make_pair ( UpdReg , std :: make_pair ( IndReg , V ) ) ) ; } } } } SmallVector < MachineOperand , <NUM_LIT> > Cond ; MachineBasicBlock * TB = nullptr , * FB = nullptr ; bool NotAnalyzed = TII -> analyzeBranch ( * ExitingBlock , TB , FB , Cond , false ) ; if ( NotAnalyzed ) return false ; unsigned PredR , PredPos , PredRegFlags ; if ( ! TII -> getPredReg ( Cond , PredR , PredPos , PredRegFlags ) ) return false ; MachineInstr * PredI = MRI -> getVRegDef ( PredR ) ; if ( ! PredI -> isCompare ( ) ) return false ; unsigned CmpReg1 = <NUM_LIT> , CmpReg2 = <NUM_LIT> ; int CmpImm = <NUM_LIT> , CmpMask = <NUM_LIT> ; bool CmpAnalyzed = TII -> analyzeCompare ( * PredI , CmpReg1 , CmpReg2 , CmpMask , CmpImm ) ; if ( ! CmpAnalyzed ) return false ; InductionMap :: iterator IndMapEnd = IndMap . end ( ) ; InductionMap :: iterator F = IndMapEnd ; if ( CmpReg1 != <NUM_LIT> ) { InductionMap :: iterator F1 = IndMap . find ( CmpReg1 ) ; if ( F1 != IndMapEnd ) F = F1 ; }


<s> int CmpMask = <NUM_LIT> , CmpValue = <NUM_LIT> ; if ( ! TII -> analyzeCompare ( * MI , CmpReg1 , CmpReg2 , CmpMask , CmpValue ) ) continue ; MachineBasicBlock * TBB = nullptr , * FBB = nullptr ; SmallVector < MachineOperand , <NUM_LIT> > Cond ; if ( TII -> analyzeBranch ( * MI -> getParent ( ) , TBB , FBB , Cond , false ) ) continue ; Comparison :: Kind Cmp = getComparisonKind ( MI -> getOpcode ( ) , nullptr , nullptr , <NUM_LIT> ) ; if ( Cmp == <NUM_LIT> ) continue ; if ( TII -> predOpcodeHasNot ( Cond ) ^ ( TBB != MBB ) ) Cmp = Comparison :: getNegatedComparison ( Cmp ) ; if ( CmpReg2 != <NUM_LIT> && CmpReg2 == Reg ) Cmp = Comparison :: getSwappedComparison ( Cmp ) ; if ( Comparison :: isSigned ( Cmp ) ) return false ; if ( ( Cmp & Comparison :: G ) || Cmp == Comparison :: NE ) return false ; } if ( ! Def -> isCopy ( ) && ! Def -> isPHI ( ) ) return false ;


<s> if ( Dist == <NUM_LIT> ) return nullptr ; bool Exact = ( Dist % IVBump ) == <NUM_LIT> ; if ( Cmp == Comparison :: NE ) { if ( ! Exact ) return nullptr ; if ( ( Dist < <NUM_LIT> ) ^ ( IVBump < <NUM_LIT> ) ) return nullptr ; } if ( CmpHasEqual ) Dist = Dist > <NUM_LIT> ? Dist + <NUM_LIT> : Dist - <NUM_LIT> ; if ( ( CmpLess && Dist < <NUM_LIT> ) || ( CmpGreater && Dist > <NUM_LIT> ) ) return nullptr ; int64_t Dist1 = ( IVBump > <NUM_LIT> ) ? ( Dist + ( IVBump - <NUM_LIT> ) ) / IVBump : ( - Dist + ( - IVBump - <NUM_LIT> ) ) / ( - IVBump ) ; assert ( Dist1 > <NUM_LIT> && <STR_LIT> ) ; uint64_t Count = Dist1 ; if ( Count > <NUM_LIT> ) return nullptr ; return new CountValue ( CountValue :: CV_Immediate , Count ) ; } if ( ! isPowerOf2_64 ( std :: abs ( IVBump ) ) ) return nullptr ; MachineBasicBlock * PH = Loop -> getLoopPreheader ( ) ; assert ( PH && <STR_LIT> ) ; MachineBasicBlock :: iterator InsertPos = PH -> getFirstTerminator ( ) ; DebugLoc DL ; if ( InsertPos != PH -> end ( ) ) DL = InsertPos -> getDebugLoc ( ) ; if ( IVBump < <NUM_LIT> ) { std :: swap ( Start , End ) ; IVBump = - IVBump ; } bool RegToImm = Start -> isReg ( ) && End -> isImm ( ) ; bool RegToReg = Start -> isReg ( ) && End -> isReg ( ) ; int64_t StartV = <NUM_LIT> , EndV = <NUM_LIT> ; if ( Start -> isImm ( ) ) StartV = Start -> getImm ( ) ; if ( End -> isImm ( ) ) EndV = End -> getImm ( ) ; int64_t AdjV = <NUM_LIT> ; if ( CmpHasEqual ) { if ( Start -> isImm ( ) ) StartV -- ; else if ( End -> isImm ( ) ) EndV ++ ; else AdjV += <NUM_LIT> ; } if ( Cmp != Comparison :: NE ) { if ( Start -> isImm ( ) ) StartV -= ( IVBump - <NUM_LIT> ) ; else if ( End -> isImm ( ) ) EndV += ( IVBump - <NUM_LIT> ) ; else AdjV += ( IVBump - <NUM_LIT> ) ; } unsigned R = <NUM_LIT> , SR = <NUM_LIT> ; if ( Start -> isReg ( ) ) {


<s> if ( ExitingBlock != L -> getLoopLatch ( ) ) { MachineBasicBlock * TB = <NUM_LIT> , * FB = <NUM_LIT> ; SmallVector < MachineOperand , <NUM_LIT> > Cond ; if ( TII -> AnalyzeBranch ( * ExitingBlock , TB , FB , Cond , false ) ) return false ; if ( L -> contains ( TB ) ) LoopStart = TB ; else if ( L -> contains ( FB ) ) LoopStart = FB ; else return false ; } else LoopStart = TopBlock ; DEBUG ( dbgs ( ) << <STR_LIT> ; L -> dump ( ) ) ; DebugLoc DL ; if ( InsertPos != Preheader -> end ( ) ) DL = InsertPos -> getDebugLoc ( ) ; if ( TripCount -> isReg ( ) ) { unsigned CountReg = MRI -> createVirtualRegister ( & <STR_LIT> ) ; BuildMI ( * Preheader , InsertPos , DL , TII -> get ( TargetOpcode :: COPY ) , CountReg ) . addReg ( TripCount -> getReg ( ) , <NUM_LIT> , TripCount -> getSubReg ( ) ) ; BuildMI ( * Preheader , InsertPos , DL , TII -> get ( LOOP_r ) ) . addMBB ( LoopStart ) . addReg ( CountReg ) ; } else { assert ( TripCount -> isImm ( ) && <STR_LIT> ) ; int64_t CountImm = TripCount -> getImm ( ) ; if ( ! TII -> isValidOffset ( LOOP_i , CountImm ) ) { unsigned CountReg = MRI -> createVirtualRegister ( & <STR_LIT> ) ; BuildMI ( * Preheader , InsertPos , DL , TII -> get ( <STR_LIT> ) , CountReg ) . addImm ( CountImm ) ; BuildMI ( * Preheader , InsertPos , DL , TII -> get ( LOOP_r ) ) . addMBB ( LoopStart ) . addReg ( CountReg ) ; } else BuildMI ( * Preheader , InsertPos , DL , TII -> get ( LOOP_i ) ) . addMBB ( LoopStart ) . addImm ( CountImm ) ; } LoopStart -> setHasAddressTaken ( ) ; BlockAddress :: get ( const_cast < BasicBlock * > ( LoopStart -> getBasicBlock ( ) ) ) ; DebugLoc LastIDL = LastI -> getDebugLoc ( ) ; BuildMI ( * LastMBB , LastI , LastIDL , TII -> get ( ENDLOOP ) ) . addMBB ( LoopStart ) ;


<s> for ( instr_iterator I = Header -> instr_begin ( ) , E = Header -> instr_end ( ) ; I != E && I -> isPHI ( ) ; ++ I ) { MachineInstr * PN = & * I ; for ( unsigned i = <NUM_LIT> , n = PN -> getNumOperands ( ) ; i < n ; i += <NUM_LIT> ) { MachineOperand & MO = PN -> getOperand ( i + <NUM_LIT> ) ; if ( MO . getMBB ( ) != Latch ) MO . setMBB ( NewPH ) ; } } } SmallVector < MachineOperand , <NUM_LIT> > Tmp2 ; SmallVector < MachineOperand , <NUM_LIT> > EmptyCond ; TB = FB = nullptr ; for ( MBBVector :: iterator I = Preds . begin ( ) , E = Preds . end ( ) ; I != E ; ++ I ) { MachineBasicBlock * PB = * I ; if ( PB != Latch ) { Tmp2 . clear ( ) ; bool NotAnalyzed = TII -> AnalyzeBranch ( * PB , TB , FB , Tmp2 , false ) ; ( void ) NotAnalyzed ; assert ( ! NotAnalyzed && <STR_LIT> ) ; if ( TB != Header && ( Tmp2 . empty ( ) || FB != Header ) ) TII -> InsertBranch ( * PB , NewPH , nullptr , EmptyCond , DL ) ; PB -> ReplaceUsesOfBlockWith ( Header , NewPH ) ; } } TB = FB = nullptr ; bool LatchNotAnalyzed = TII -> AnalyzeBranch ( * Latch , TB , FB , Tmp2 , false ) ; ( void ) LatchNotAnalyzed ; assert ( ! LatchNotAnalyzed && <STR_LIT> ) ; if ( ! TB && ! FB ) TII -> InsertBranch ( * Latch , Header , nullptr , EmptyCond , DL ) ; TII -> InsertBranch ( * NewPH , Header , nullptr , EmptyCond , DL ) ; NewPH -> addSuccessor ( Header ) ; MachineLoop * ParentLoop = L -> getParentLoop ( ) ;

if ( ParentLoop ) ParentLoop -> addBasicBlockToLoop ( NewPH , MLI -> getBase ( ) ) ;


<s> typedef std :: map < unsigned , RegisterBump > InductionMap ; InductionMap IndMap ; typedef MachineBasicBlock :: instr_iterator instr_iterator ; for ( instr_iterator I = Header -> instr_begin ( ) , E = Header -> instr_end ( ) ; I != E && I -> isPHI ( ) ; ++ I ) { MachineInstr * Phi = & * I ; for ( unsigned i = <NUM_LIT> , n = Phi -> getNumOperands ( ) ; i < n ; i += <NUM_LIT> ) { if ( Phi -> getOperand ( i + <NUM_LIT> ) . getMBB ( ) != Latch ) continue ; unsigned PhiOpReg = Phi -> getOperand ( i ) . getReg ( ) ; MachineInstr * DI = MRI -> getVRegDef ( PhiOpReg ) ; unsigned UpdOpc = DI -> getOpcode ( ) ; bool isAdd = ( UpdOpc == <STR_LIT> || UpdOpc == <STR_LIT> ) ; if ( isAdd ) { unsigned IndReg = DI -> getOperand ( <NUM_LIT> ) . getReg ( ) ; MachineOperand & Opnd2 = DI -> getOperand ( <NUM_LIT> ) ; int64_t V ; if ( MRI -> getVRegDef ( IndReg ) == Phi && checkForImmediate ( Opnd2 , V ) ) { unsigned UpdReg = DI -> getOperand ( <NUM_LIT> ) . getReg ( ) ; IndMap . insert ( std :: make_pair ( UpdReg , std :: make_pair ( IndReg , V ) ) ) ; } } } } SmallVector < MachineOperand , <NUM_LIT> > Cond ; MachineBasicBlock * TB = nullptr , * FB = nullptr ; bool NotAnalyzed = TII -> AnalyzeBranch ( * ExitingBlock , TB , FB , Cond , false ) ; if ( NotAnalyzed ) return false ; unsigned PredR , PredPos , PredRegFlags ; if ( ! TII -> getPredReg ( Cond , PredR , PredPos , PredRegFlags ) ) return false ;

MachineInstr * PredI = MRI -> getVRegDef ( PredR ) ;


<s> if ( ! isImmediate ( MO ) ) { CmpRegs . insert ( MO . getReg ( ) ) ; continue ; } if ( CmpImmOp ) return false ; CmpImmOp = & MO ; } } else if ( MO . isImm ( ) ) { if ( CmpImmOp ) return false ; CmpImmOp = & MO ; } } if ( CmpRegs . empty ( ) ) return false ; for ( RegisterInductionSet :: iterator I = IndRegs . begin ( ) , E = IndRegs . end ( ) ; I != E ; ++ I ) { if ( CmpRegs . count ( I -> first ) ) return true ; const RegisterBump & RB = I -> second ; if ( CmpRegs . count ( RB . first ) ) { if ( ! CmpImmOp ) { MachineInstr * IndI = nullptr ; MachineInstr * nonIndI = nullptr ; MachineOperand * IndMO = nullptr ; MachineOperand * nonIndMO = nullptr ; for ( unsigned i = <NUM_LIT> , n = PredDef -> getNumOperands ( ) ; i < n ; ++ i ) { MachineOperand & MO = PredDef -> getOperand ( i ) ; if ( MO . isReg ( ) && MO . getReg ( ) == RB . first ) { DEBUG ( dbgs ( ) << <STR_LIT> << i << <STR_LIT> << * ( MRI -> getVRegDef ( I -> first ) ) ) ; if ( IndI ) return false ; IndI = MRI -> getVRegDef ( I -> first ) ; IndMO = & MO ; } else if ( MO . isReg ( ) ) { DEBUG ( dbgs ( ) << <STR_LIT> << i << <STR_LIT> << * ( MRI -> getVRegDef ( MO . getReg ( ) ) ) ) ; if ( nonIndI ) return false ; nonIndI = MRI -> getVRegDef ( MO . getReg ( ) ) ; nonIndMO = & MO ; } } if ( IndI && nonIndI && nonIndI -> getOpcode ( ) == <STR_LIT> && nonIndI -> getOperand ( <NUM_LIT> ) . isImm ( ) && nonIndI -> getOperand ( <NUM_LIT> ) . getImm ( ) == - RB . second ) { bool Order = orderBumpCompare ( IndI , PredDef ) ; if ( Order ) { IndMO -> setReg ( I -> first ) ; nonIndMO -> setReg ( nonIndI -> getOperand ( <NUM_LIT> ) . getReg ( ) ) ; return true ; } } return false ; } Comparison :: Kind Cmp = getComparisonKind ( PredDef -> getOpcode ( ) , <NUM_LIT> , <NUM_LIT> , <NUM_LIT> ) ;

if ( ! Cmp || Comparison :: isUnsigned ( Cmp ) ) return false ;


<s> if ( ! TII -> getPredReg ( Cond , PredReg , PredPos , PredRegFlags ) ) return nullptr ; MachineInstr * CondI = MRI -> getVRegDef ( PredReg ) ; unsigned CondOpc = CondI -> getOpcode ( ) ; unsigned CmpReg1 = <NUM_LIT> , CmpReg2 = <NUM_LIT> ; int Mask = <NUM_LIT> , ImmValue = <NUM_LIT> ; bool AnalyzedCmp = TII -> analyzeCompare ( CondI , CmpReg1 , CmpReg2 , Mask , ImmValue ) ; if ( ! AnalyzedCmp ) return nullptr ; OldInsts . push_back ( CondI ) ; OldInsts . push_back ( IVOp ) ; Comparison :: Kind Cmp ; bool isSwapped = false ; const MachineOperand & Op1 = CondI -> getOperand ( <NUM_LIT> ) ; const MachineOperand & Op2 = CondI -> getOperand ( <NUM_LIT> ) ; const MachineOperand * EndValue = nullptr ; if ( Op1 . isReg ( ) ) { if ( Op2 . isImm ( ) || Op1 . getReg ( ) == IVReg ) EndValue = & Op2 ; else { EndValue = & Op1 ; isSwapped = true ; } } if ( ! EndValue ) return nullptr ; Cmp = getComparisonKind ( CondOpc , InitialValue , EndValue , IVBump ) ; if ( ! Cmp ) return nullptr ; if ( Negated ) Cmp = Comparison :: getNegatedComparison ( Cmp ) ; if ( isSwapped ) Cmp = Comparison :: getSwappedComparison ( Cmp ) ; if ( InitialValue -> isReg ( ) ) { unsigned R = InitialValue -> getReg ( ) ; MachineBasicBlock * DefBB = MRI -> getVRegDef ( R ) -> getParent ( ) ; if ( ! MDT -> properlyDominates ( DefBB , Header ) ) return nullptr ; OldInsts . push_back ( MRI -> getVRegDef ( R ) ) ; } if ( EndValue -> isReg ( ) ) { unsigned R = EndValue -> getReg ( ) ; MachineBasicBlock * DefBB = MRI -> getVRegDef ( R ) -> getParent ( ) ; if ( ! MDT -> properlyDominates ( DefBB , Header ) ) return nullptr ;


<s> for ( MachineLoop :: iterator I = L -> begin ( ) , E = L -> end ( ) ; I != E ; ++ I ) { Changed |= convertToHardwareLoop ( * I ) ; } if ( Changed ) { return Changed ; } CountValue * TripCount = getTripCount ( L ) ; if ( TripCount == <NUM_LIT> ) { return false ; } if ( containsInvalidInstruction ( L ) ) { return false ; } MachineBasicBlock * Preheader = L -> getLoopPreheader ( ) ; if ( Preheader == <NUM_LIT> ) { return false ; } MachineBasicBlock :: iterator InsertPos = Preheader -> getFirstTerminator ( ) ; MachineBasicBlock * LastMBB = L -> getExitingBlock ( ) ; if ( LastMBB == <NUM_LIT> ) { return false ; } MachineBasicBlock :: iterator LastI = LastMBB -> getFirstTerminator ( ) ; MachineBasicBlock * LoopStart = L -> getTopBlock ( ) ; if ( L -> getLoopLatch ( ) != LastMBB ) { LoopStart = L -> getLoopLatch ( ) ; if ( ! LastMBB -> isSuccessor ( LoopStart ) ) { return false ; } } DEBUG ( dbgs ( ) << <STR_LIT> ; L -> dump ( ) ) ; if ( TripCount -> isReg ( ) ) { MachineFunction * MF = LastMBB -> getParent ( ) ; const TargetRegisterClass * RC = MF -> getRegInfo ( ) . getRegClass ( TripCount -> getReg ( ) ) ; unsigned CountReg = MF -> getRegInfo ( ) . createVirtualRegister ( RC ) ; BuildMI ( * Preheader , InsertPos , InsertPos -> getDebugLoc ( ) , TII -> get ( TargetOpcode :: COPY ) , CountReg ) . addReg ( TripCount -> getReg ( ) ) ; if ( TripCount -> isNeg ( ) ) { unsigned CountReg1 = CountReg ; CountReg = MF -> getRegInfo ( ) . createVirtualRegister ( RC ) ; BuildMI ( * Preheader , InsertPos , InsertPos -> getDebugLoc ( ) , TII -> get ( <STR_LIT> ) , CountReg ) . addReg ( CountReg1 ) ; } BuildMI ( * Preheader , InsertPos , InsertPos -> getDebugLoc ( ) , TII -> get ( <STR_LIT> ) ) . addMBB ( LoopStart ) . addReg ( CountReg ) ; } else { assert ( TripCount -> isImm ( ) && <STR_LIT> ) ; int64_t CountImm = TripCount -> getImm ( ) ; BuildMI ( * Preheader , InsertPos , InsertPos -> getDebugLoc ( ) , TII -> get ( <STR_LIT> ) ) . addMBB ( LoopStart ) . addImm ( CountImm ) ; }


<s> if ( Preheader == <NUM_LIT> ) { return false ; } MachineBasicBlock :: iterator InsertPos = Preheader -> getFirstTerminator ( ) ; MachineBasicBlock * LastMBB = L -> getExitingBlock ( ) ; if ( LastMBB == <NUM_LIT> ) { return false ; } MachineBasicBlock :: iterator LastI = LastMBB -> getFirstTerminator ( ) ; MachineBasicBlock * LoopStart = L -> getTopBlock ( ) ; if ( L -> getLoopLatch ( ) != LastMBB ) { LoopStart = L -> getLoopLatch ( ) ; if ( ! LastMBB -> isSuccessor ( LoopStart ) ) { return false ; } } DEBUG ( dbgs ( ) << <STR_LIT> ; L -> dump ( ) ) ; if ( TripCount -> isReg ( ) ) { MachineFunction * MF = LastMBB -> getParent ( ) ; const TargetRegisterClass * RC = MF -> getRegInfo ( ) . getRegClass ( TripCount -> getReg ( ) ) ; unsigned CountReg = MF -> getRegInfo ( ) . createVirtualRegister ( RC ) ; BuildMI ( * Preheader , InsertPos , InsertPos -> getDebugLoc ( ) , TII -> get ( TargetOpcode :: COPY ) , CountReg ) . addReg ( TripCount -> getReg ( ) ) ; if ( TripCount -> isNeg ( ) ) { unsigned CountReg1 = CountReg ; CountReg = MF -> getRegInfo ( ) . createVirtualRegister ( RC ) ; BuildMI ( * Preheader , InsertPos , InsertPos -> getDebugLoc ( ) , TII -> get ( <STR_LIT> ) , CountReg ) . addReg ( CountReg1 ) ; } BuildMI ( * Preheader , InsertPos , InsertPos -> getDebugLoc ( ) , TII -> get ( <STR_LIT> ) ) . addMBB ( LoopStart ) . addReg ( CountReg ) ; } else { assert ( TripCount -> isImm ( ) && <STR_LIT> ) ; int64_t CountImm = TripCount -> getImm ( ) ; BuildMI ( * Preheader , InsertPos , InsertPos -> getDebugLoc ( ) , TII -> get ( <STR_LIT> ) ) . addMBB ( LoopStart ) . addImm ( CountImm ) ; } LoopStart -> setHasAddressTaken ( ) ; BlockAddress :: get ( const_cast < BasicBlock * > ( LoopStart -> getBasicBlock ( ) ) ) ; DebugLoc dl = LastI -> getDebugLoc ( ) ; BuildMI ( * LastMBB , LastI , dl , TII -> get ( <STR_LIT> ) ) . addMBB ( LoopStart ) ; if ( LastI -> getOpcode ( ) == <STR_LIT> || LastI -> getOpcode ( ) == <STR_LIT> ) { MachineBasicBlock * BranchTarget = LastI -> getOperand ( <NUM_LIT> ) . getMBB ( ) ; LastI = LastMBB -> erase ( LastI ) ; if ( ! L -> contains ( BranchTarget ) ) {


<s> LLVM_DEBUG ( dbgs ( ) << <STR_LIT> << printMBBReference ( * Blocks [ <NUM_LIT> ] ) ) ; for ( unsigned i = <NUM_LIT> , e = Blocks . size ( ) ; i != e ; ++ i ) { MachineBasicBlock * MBB = Blocks [ i ] ; for ( MachineBasicBlock :: iterator MII = MBB -> begin ( ) , E = MBB -> end ( ) ; MII != E ; ++ MII ) { const MachineInstr * MI = & * MII ;

if ( isInvalidLoopOperation ( MI , IsInnerHWLoop ) ) {


<s> MachineBasicBlock * MBB = Blocks [ i ] ; for ( MachineBasicBlock :: iterator MII = MBB -> begin ( ) , E = MBB -> end ( ) ; MII != E ; ++ MII ) { const MachineInstr * MI = & * MII ; if ( isInvalidLoopOperation ( MI , IsInnerHWLoop ) ) { LLVM_DEBUG ( dbgs ( ) << <STR_LIT> ; MI -> dump ( ) ; ) ; return true ; }


<s> else return false ; } else LoopStart = TopBlock ; LLVM_DEBUG ( dbgs ( ) << <STR_LIT> ; L -> dump ( ) ) ; DebugLoc DL ; if ( InsertPos != Preheader -> end ( ) ) DL = InsertPos -> getDebugLoc ( ) ; if ( TripCount -> isReg ( ) ) { unsigned CountReg = MRI -> createVirtualRegister ( & <STR_LIT> ) ; BuildMI ( * Preheader , InsertPos , DL , TII -> get ( TargetOpcode :: COPY ) , CountReg ) . addReg ( TripCount -> getReg ( ) , <NUM_LIT> , TripCount -> getSubReg ( ) ) ; BuildMI ( * Preheader , InsertPos , DL , TII -> get ( LOOP_r ) ) . addMBB ( LoopStart ) . addReg ( CountReg ) ; } else { assert ( TripCount -> isImm ( ) && <STR_LIT> ) ; int64_t CountImm = TripCount -> getImm ( ) ; if ( ! TII -> isValidOffset ( LOOP_i , CountImm , TRI ) ) { unsigned CountReg = MRI -> createVirtualRegister ( & <STR_LIT> ) ; BuildMI ( * Preheader , InsertPos , DL , TII -> get ( <STR_LIT> ) , CountReg ) . addImm ( CountImm ) ; BuildMI ( * Preheader , InsertPos , DL , TII -> get ( LOOP_r ) ) . addMBB ( LoopStart ) . addReg ( CountReg ) ; } else BuildMI ( * Preheader , InsertPos , DL , TII -> get ( LOOP_i ) ) . addMBB ( LoopStart ) . addImm ( CountImm ) ; } LoopStart -> setHasAddressTaken ( ) ; BlockAddress :: get ( const_cast < BasicBlock * > ( LoopStart -> getBasicBlock ( ) ) ) ; DebugLoc LastIDL = LastI -> getDebugLoc ( ) ; BuildMI ( * LastMBB , LastI , LastIDL , TII -> get ( ENDLOOP ) ) . addMBB ( LoopStart ) ; if ( LastI -> getOpcode ( ) == <STR_LIT> || LastI -> getOpcode ( ) == <STR_LIT> ) { MachineBasicBlock * BranchTarget = LastI -> getOperand ( <NUM_LIT> ) . getMBB ( ) ; LastI = LastMBB -> erase ( LastI ) ; if ( ! L -> contains ( BranchTarget ) ) { if ( LastI != LastMBB -> end ( ) ) LastI = LastMBB -> erase ( LastI ) ; SmallVector < MachineOperand , <NUM_LIT> > Cond ; TII -> insertBranch ( * LastMBB , BranchTarget , nullptr , Cond , LastIDL ) ; } } else { LastMBB -> erase ( LastI ) ; } delete TripCount ; for ( unsigned i = <NUM_LIT> ; i < OldInsts . size ( ) ; ++ i ) removeIfDead ( OldInsts [ i ] ) ; ++ NumHWLoops ; if ( L0Used ) RecL1used = true ;


<s> LLVM_DEBUG ( dbgs ( ) << <STR_LIT> << printMBBReference ( * Blocks [ <NUM_LIT> ] ) ) ; for ( unsigned i = <NUM_LIT> , e = Blocks . size ( ) ; i != e ; ++ i ) { MachineBasicBlock * MBB = Blocks [ i ] ; if ( A == MBB ) return false ; } MachineInstr * Def = MRI -> getVRegDef ( MO -> getReg ( ) ) ; LoopFeederPhi . insert ( std :: make_pair ( MO -> getReg ( ) , Def ) ) ; return true ; } else return false ;


<s> unsigned Reg = MO . getReg ( ) ; MachineRegisterInfo :: use_iterator nextI ; for ( MachineRegisterInfo :: use_iterator I = MRI -> use_begin ( Reg ) , E = MRI -> use_end ( ) ; I != E ; I = nextI ) { nextI = std :: next ( I ) ; MachineOperand & Use = * I ; MachineInstr * UseMI = I -> getParent ( ) ; if ( UseMI == MI ) continue ; if ( Use . isDebug ( ) ) UseMI -> getOperand ( <NUM_LIT> ) . setReg ( <NUM_LIT> ) ;


<s> bool <ISA_LIT>HardwareLoops :: runOnMachineFunction ( MachineFunction & MF ) { LLVM_DEBUG ( dbgs ( ) << <STR_LIT> ) ; if ( skipFunction ( MF . getFunction ( ) ) ) return false ; bool Changed = false ; MLI = & getAnalysis < MachineLoopInfo > ( ) ; MRI = & MF . getRegInfo ( ) ; MDT = & getAnalysis < MachineDominatorTree > ( ) ; const <ISA_LIT>Subtarget & HST = MF . getSubtarget < <ISA_LIT>Subtarget > ( ) ; TII = HST . getInstrInfo ( ) ; TRI = HST . getRegisterInfo ( ) ;

for ( auto & L : * MLI ) if ( ! L -> getParentLoop ( ) ) {


<s> if ( Phi -> getOperand ( i + <NUM_LIT> ) . getMBB ( ) != Latch ) continue ; unsigned PhiOpReg = Phi -> getOperand ( i ) . getReg ( ) ; MachineInstr * DI = MRI -> getVRegDef ( PhiOpReg ) ; unsigned UpdOpc = DI -> getOpcode ( ) ; bool isAdd = ( UpdOpc == <STR_LIT> || UpdOpc == <STR_LIT> ) ; if ( isAdd ) { unsigned IndReg = DI -> getOperand ( <NUM_LIT> ) . getReg ( ) ; MachineOperand & Opnd2 = DI -> getOperand ( <NUM_LIT> ) ; int64_t V ; if ( MRI -> getVRegDef ( IndReg ) == Phi && checkForImmediate ( Opnd2 , V ) ) { unsigned UpdReg = DI -> getOperand ( <NUM_LIT> ) . getReg ( ) ; IndMap . insert ( std :: make_pair ( UpdReg , std :: make_pair ( IndReg , V ) ) ) ; } } } } SmallVector < MachineOperand , <NUM_LIT> > Cond ; MachineBasicBlock * TB = nullptr , * FB = nullptr ; bool NotAnalyzed = TII -> AnalyzeBranch ( * ExitingBlock , TB , FB , Cond , false ) ; if ( NotAnalyzed ) return false ; unsigned PredR , PredPos , PredRegFlags ;

if ( ! TII -> getPredReg ( Cond , PredR , PredPos , PredRegFlags ) ) return false ;


<s> IndMap . insert ( std :: make_pair ( UpdReg , std :: make_pair ( IndReg , V ) ) ) ; } } } } SmallVector < MachineOperand , <NUM_LIT> > Cond ; MachineBasicBlock * TB = nullptr , * FB = nullptr ; bool NotAnalyzed = TII -> AnalyzeBranch ( * ExitingBlock , TB , FB , Cond , false ) ; if ( NotAnalyzed ) return false ; unsigned PredR , PredPos , PredRegFlags ; if ( ! TII -> getPredReg ( Cond , PredR , PredPos , PredRegFlags ) ) return false ; MachineInstr * PredI = MRI -> getVRegDef ( PredR ) ; if ( ! PredI -> isCompare ( ) ) return false ; unsigned CmpReg1 = <NUM_LIT> , CmpReg2 = <NUM_LIT> ; int CmpImm = <NUM_LIT> , CmpMask = <NUM_LIT> ; bool CmpAnalyzed = TII -> analyzeCompare ( * PredI , CmpReg1 , CmpReg2 , CmpMask , CmpImm ) ; if ( ! CmpAnalyzed ) return false ; InductionMap :: iterator IndMapEnd = IndMap . end ( ) ;

InductionMap :: iterator F = IndMapEnd ;


<s> unsigned CmpReg1 = <NUM_LIT> , CmpReg2 = <NUM_LIT> ; int CmpMask = <NUM_LIT> , CmpValue = <NUM_LIT> ; if ( ! TII -> analyzeCompare ( * MI , CmpReg1 , CmpReg2 , CmpMask , CmpValue ) ) continue ; MachineBasicBlock * TBB = <NUM_LIT> , * FBB = <NUM_LIT> ; SmallVector < MachineOperand , <NUM_LIT> > Cond ; if ( TII -> AnalyzeBranch ( * MI -> getParent ( ) , TBB , FBB , Cond , false ) ) continue ; Comparison :: Kind Cmp = getComparisonKind ( MI -> getOpcode ( ) , <NUM_LIT> , <NUM_LIT> , <NUM_LIT> ) ; if ( Cmp == <NUM_LIT> ) continue ; if ( TII -> predOpcodeHasNot ( Cond ) ^ ( TBB != MBB ) ) Cmp = Comparison :: getNegatedComparison ( Cmp ) ; if ( CmpReg2 != <NUM_LIT> && CmpReg2 == Reg ) Cmp = Comparison :: getSwappedComparison ( Cmp ) ; if ( Comparison :: isSigned ( Cmp ) ) return false ; if ( ( Cmp & Comparison :: G ) || Cmp == Comparison :: NE ) return false ;


<s> } } else { assert ( Header -> pred_size ( ) == <NUM_LIT> ) ; for ( instr_iterator I = Header -> instr_begin ( ) , E = Header -> instr_end ( ) ; I != E && I -> isPHI ( ) ; ++ I ) { MachineInstr * PN = & * I ; for ( unsigned i = <NUM_LIT> , n = PN -> getNumOperands ( ) ; i < n ; i += <NUM_LIT> ) { MachineOperand & MO = PN -> getOperand ( i + <NUM_LIT> ) ; if ( MO . getMBB ( ) != Latch ) MO . setMBB ( NewPH ) ; } } } SmallVector < MachineOperand , <NUM_LIT> > Tmp2 ; SmallVector < MachineOperand , <NUM_LIT> > EmptyCond ; TB = FB = nullptr ; for ( MBBVector :: iterator I = Preds . begin ( ) , E = Preds . end ( ) ; I != E ; ++ I ) { MachineBasicBlock * PB = * I ; if ( PB != Latch ) { Tmp2 . clear ( ) ; bool NotAnalyzed = TII -> AnalyzeBranch ( * PB , TB , FB , Tmp2 , false ) ; ( void ) NotAnalyzed ; assert ( ! NotAnalyzed && <STR_LIT> ) ; if ( TB != Header && ( Tmp2 . empty ( ) || FB != Header ) ) TII -> InsertBranch ( * PB , NewPH , nullptr , EmptyCond , DL ) ; PB -> ReplaceUsesOfBlockWith ( Header , NewPH ) ; } } TB = FB = nullptr ; bool LatchNotAnalyzed = TII -> AnalyzeBranch ( * Latch , TB , FB , Tmp2 , false ) ; ( void ) LatchNotAnalyzed ; assert ( ! LatchNotAnalyzed && <STR_LIT> ) ; if ( ! TB && ! FB ) TII -> InsertBranch ( * Latch , Header , nullptr , EmptyCond , DL ) ; TII -> InsertBranch ( * NewPH , Header , nullptr , EmptyCond , DL ) ; NewPH -> addSuccessor ( Header ) ; MachineLoop * ParentLoop = L -> getParentLoop ( ) ; if ( ParentLoop ) ParentLoop -> addBasicBlockToLoop ( NewPH , MLI -> getBase ( ) ) ; if ( MDT ) {

MachineDomTreeNode * HDom = MDT -> getNode ( Header ) ;


<s> case <STR_LIT> : case <STR_LIT> : { if ( ! checkForImmediate ( DI -> getOperand ( <NUM_LIT> ) , TV ) ) return false ; break ; } case <STR_LIT> : case <STR_LIT> : case <STR_LIT> : case <STR_LIT> : case <STR_LIT> : { const MachineOperand & S1 = DI -> getOperand ( <NUM_LIT> ) ; const MachineOperand & S2 = DI -> getOperand ( <NUM_LIT> ) ; int64_t V1 , V2 ; if ( ! checkForImmediate ( S1 , V1 ) || ! checkForImmediate ( S2 , V2 ) ) return false ; TV = V2 | ( V1 << <NUM_LIT> ) ; break ; } case TargetOpcode :: REG_SEQUENCE : { const MachineOperand & S1 = DI -> getOperand ( <NUM_LIT> ) ; const MachineOperand & S3 = DI -> getOperand ( <NUM_LIT> ) ; int64_t V1 , V3 ; if ( ! checkForImmediate ( S1 , V1 ) || ! checkForImmediate ( S3 , V3 ) ) return false ; unsigned Sub2 = DI -> getOperand ( <NUM_LIT> ) . getImm ( ) ; unsigned Sub4 = DI -> getOperand ( <NUM_LIT> ) . getImm ( ) ; if ( Sub2 == <STR_LIT> && Sub4 == <STR_LIT> ) TV = V1 | ( V3 << <NUM_LIT> ) ; else if ( Sub2 == <STR_LIT> && Sub4 == <STR_LIT> ) TV = V3 | ( V1 << <NUM_LIT> ) ; else llvm_unreachable ( <STR_LIT> ) ; break ; } default : return false ; } switch ( MO . getSubReg ( ) ) { case <STR_LIT> : Val = TV & <NUM_LIT> ; break ; case <STR_LIT> :


<s> InductionMap IndMap ; typedef MachineBasicBlock :: instr_iterator instr_iterator ; for ( instr_iterator I = Header -> instr_begin ( ) , E = Header -> instr_end ( ) ; I != E && I -> isPHI ( ) ; ++ I ) { MachineInstr * Phi = & * I ; for ( unsigned i = <NUM_LIT> , n = Phi -> getNumOperands ( ) ; i < n ; i += <NUM_LIT> ) { if ( Phi -> getOperand ( i + <NUM_LIT> ) . getMBB ( ) != Latch ) continue ; unsigned PhiOpReg = Phi -> getOperand ( i ) . getReg ( ) ; MachineInstr * DI = MRI -> getVRegDef ( PhiOpReg ) ; unsigned UpdOpc = DI -> getOpcode ( ) ; bool isAdd = ( UpdOpc == <STR_LIT> || UpdOpc == <STR_LIT> ) ; if ( isAdd ) { unsigned IndReg = DI -> getOperand ( <NUM_LIT> ) . getReg ( ) ; MachineOperand & Opnd2 = DI -> getOperand ( <NUM_LIT> ) ; int64_t V ; if ( MRI -> getVRegDef ( IndReg ) == Phi && checkForImmediate ( Opnd2 , V ) ) { unsigned UpdReg = DI -> getOperand ( <NUM_LIT> ) . getReg ( ) ; IndMap . insert ( std :: make_pair ( UpdReg , std :: make_pair ( IndReg , V ) ) ) ; } } } } SmallVector < MachineOperand , <NUM_LIT> > Cond ; MachineBasicBlock * TB = nullptr , * FB = nullptr ; bool NotAnalyzed = TII -> analyzeBranch ( * ExitingBlock , TB , FB , Cond , false ) ; if ( NotAnalyzed ) return false ; unsigned PredR , PredPos , PredRegFlags ; if ( ! TII -> getPredReg ( Cond , PredR , PredPos , PredRegFlags ) ) return false ; MachineInstr * PredI = MRI -> getVRegDef ( PredR ) ; if ( ! PredI -> isCompare ( ) ) return false ; unsigned CmpReg1 = <NUM_LIT> , CmpReg2 = <NUM_LIT> ; int CmpImm = <NUM_LIT> , CmpMask = <NUM_LIT> ; bool CmpAnalyzed = TII -> analyzeCompare ( * PredI , CmpReg1 , CmpReg2 , CmpMask , CmpImm ) ;


<s> NewPreheader = true ; } MachineBasicBlock :: iterator InsertPos = Preheader -> getFirstTerminator ( ) ; SmallVector < MachineInstr * , <NUM_LIT> > OldInsts ; CountValue * TripCount = getLoopTripCount ( L , OldInsts ) ; if ( TripCount == <NUM_LIT> ) return false ; if ( TripCount -> isReg ( ) ) { MachineInstr * TCDef = MRI -> getVRegDef ( TripCount -> getReg ( ) ) ; MachineBasicBlock * BBDef = TCDef -> getParent ( ) ; if ( ! NewPreheader ) { if ( ! MDT -> dominates ( BBDef , Preheader ) ) return false ; } else { if ( ! MDT -> properlyDominates ( BBDef , L -> getHeader ( ) ) ) return false ; } } MachineBasicBlock * LoopStart = L -> getTopBlock ( ) ; if ( L -> getLoopLatch ( ) != LastMBB ) { LoopStart = L -> getLoopLatch ( ) ; if ( ! LastMBB -> isSuccessor ( LoopStart ) ) return false ; } DEBUG ( dbgs ( ) << <STR_LIT> ; L -> dump ( ) ) ; DebugLoc DL ; if ( InsertPos != Preheader -> end ( ) ) DL = InsertPos -> getDebugLoc ( ) ; if ( TripCount -> isReg ( ) ) { unsigned CountReg = MRI -> createVirtualRegister ( & <STR_LIT> ) ; BuildMI ( * Preheader , InsertPos , DL , TII -> get ( TargetOpcode :: COPY ) , CountReg ) . addReg ( TripCount -> getReg ( ) , <NUM_LIT> , TripCount -> getSubReg ( ) ) ; BuildMI ( * Preheader , InsertPos , DL , TII -> get ( <STR_LIT> ) ) . addMBB ( LoopStart ) . addReg ( CountReg ) ; } else { assert ( TripCount -> isImm ( ) && <STR_LIT> ) ; int64_t CountImm = TripCount -> getImm ( ) ; if ( ! TII -> isValidOffset ( <STR_LIT> , CountImm ) ) { unsigned CountReg = MRI -> createVirtualRegister ( & <STR_LIT> ) ; BuildMI ( * Preheader , InsertPos , DL , TII -> get ( <STR_LIT> ) , CountReg ) . addImm ( CountImm ) ; BuildMI ( * Preheader , InsertPos , DL , TII -> get ( <STR_LIT> ) ) . addMBB ( LoopStart ) . addReg ( CountReg ) ; } else BuildMI ( * Preheader , InsertPos , DL , TII -> get ( <STR_LIT> ) ) . addMBB ( LoopStart ) . addImm ( CountImm ) ;


<s> I != E && I -> isPHI ( ) ; ++ I ) { MachineInstr * PN = & * I ; for ( unsigned i = <NUM_LIT> , n = PN -> getNumOperands ( ) ; i < n ; i += <NUM_LIT> ) { MachineOperand & MO = PN -> getOperand ( i + <NUM_LIT> ) ; if ( MO . getMBB ( ) != Latch ) MO . setMBB ( NewPH ) ; } } } SmallVector < MachineOperand , <NUM_LIT> > Tmp2 ; SmallVector < MachineOperand , <NUM_LIT> > EmptyCond ; TB = FB = <NUM_LIT> ; for ( MBBVector :: iterator I = Preds . begin ( ) , E = Preds . end ( ) ; I != E ; ++ I ) { MachineBasicBlock * PB = * I ; if ( PB != Latch ) { Tmp2 . clear ( ) ; bool NotAnalyzed = TII -> AnalyzeBranch ( * PB , TB , FB , Tmp2 , false ) ; ( void ) NotAnalyzed ; assert ( ! NotAnalyzed && <STR_LIT> ) ; if ( TB != Header && ( Tmp2 . empty ( ) || FB != Header ) ) TII -> InsertBranch ( * PB , NewPH , <NUM_LIT> , EmptyCond , DL ) ; PB -> ReplaceUsesOfBlockWith ( Header , NewPH ) ; } } TB = FB = <NUM_LIT> ; bool LatchNotAnalyzed = TII -> AnalyzeBranch ( * Latch , TB , FB , Tmp2 , false ) ; ( void ) LatchNotAnalyzed ; assert ( ! LatchNotAnalyzed && <STR_LIT> ) ; if ( ! TB && ! FB ) TII -> InsertBranch ( * Latch , Header , <NUM_LIT> , EmptyCond , DL ) ; TII -> InsertBranch ( * NewPH , Header , <NUM_LIT> , EmptyCond , DL ) ; NewPH -> addSuccessor ( Header ) ;


<s> MachineFunction * MF = Header -> getParent ( ) ; DebugLoc DL ; if ( ! Latch || Header -> hasAddressTaken ( ) ) return <NUM_LIT> ; typedef MachineBasicBlock :: instr_iterator instr_iterator ; typedef MachineBasicBlock :: pred_iterator pred_iterator ; typedef std :: vector < MachineBasicBlock * > MBBVector ; MBBVector Preds ( Header -> pred_begin ( ) , Header -> pred_end ( ) ) ; SmallVector < MachineOperand , <NUM_LIT> > Tmp1 ; MachineBasicBlock * TB = <NUM_LIT> , * FB = <NUM_LIT> ; if ( TII -> AnalyzeBranch ( * Latch , TB , FB , Tmp1 , false ) ) return <NUM_LIT> ; for ( MBBVector :: iterator I = Preds . begin ( ) , E = Preds . end ( ) ; I != E ; ++ I ) { MachineBasicBlock * PB = * I ; if ( PB != Latch ) { bool NotAnalyzed = TII -> AnalyzeBranch ( * PB , TB , FB , Tmp1 , false ) ; if ( NotAnalyzed ) return <NUM_LIT> ; } } MachineBasicBlock * NewPH = MF -> CreateMachineBasicBlock ( ) ; MF -> insert ( Header , NewPH ) ; if ( Header -> pred_size ( ) > <NUM_LIT> ) { for ( instr_iterator I = Header -> instr_begin ( ) , E = Header -> instr_end ( ) ; I != E && I -> isPHI ( ) ; ++ I ) { MachineInstr * PN = & * I ; const MCInstrDesc & PD = TII -> get ( TargetOpcode :: PHI ) ; MachineInstr * NewPN = MF -> CreateMachineInstr ( PD , DL ) ; NewPH -> insert ( NewPH -> end ( ) , NewPN ) ; unsigned PR = PN -> getOperand ( <NUM_LIT> ) . getReg ( ) ; const TargetRegisterClass * RC = MRI -> getRegClass ( PR ) ; unsigned NewPR = MRI -> createVirtualRegister ( RC ) ; NewPN -> addOperand ( MachineOperand :: CreateReg ( NewPR , true ) ) ;

for ( unsigned i = <NUM_LIT> , n = PN -> getNumOperands ( ) ; i < n ; i += <NUM_LIT> ) {


<s> if ( MRI -> use_nodbg_empty ( Reg ) ) continue ; typedef MachineRegisterInfo :: use_nodbg_iterator use_nodbg_iterator ; use_nodbg_iterator I = MRI -> use_nodbg_begin ( Reg ) ; use_nodbg_iterator End = MRI -> use_nodbg_end ( ) ; if ( llvm :: next ( I ) != End || ! I . getOperand ( ) . getParent ( ) -> isPHI ( ) ) return false ; MachineInstr * OnePhi = I . getOperand ( ) . getParent ( ) ; for ( unsigned j = <NUM_LIT> , f = OnePhi -> getNumOperands ( ) ; j != f ; ++ j ) { const MachineOperand & OPO = OnePhi -> getOperand ( j ) ; if ( ! OPO . isReg ( ) || ! OPO . isDef ( ) ) continue ; unsigned OPReg = OPO . getReg ( ) ; use_nodbg_iterator nextJ ; for ( use_nodbg_iterator J = MRI -> use_nodbg_begin ( OPReg ) ; J != End ; J = nextJ ) { nextJ = llvm :: next ( J ) ;

MachineOperand & Use = J . getOperand ( ) ;


<s> } else LoopStart = TopBlock ; DEBUG ( dbgs ( ) << <STR_LIT> ; L -> dump ( ) ) ; DebugLoc DL ; if ( InsertPos != Preheader -> end ( ) ) DL = InsertPos -> getDebugLoc ( ) ; if ( TripCount -> isReg ( ) ) { unsigned CountReg = MRI -> createVirtualRegister ( & <STR_LIT> ) ; BuildMI ( * Preheader , InsertPos , DL , TII -> get ( TargetOpcode :: COPY ) , CountReg ) . addReg ( TripCount -> getReg ( ) , <NUM_LIT> , TripCount -> getSubReg ( ) ) ; BuildMI ( * Preheader , InsertPos , DL , TII -> get ( LOOP_r ) ) . addMBB ( LoopStart ) . addReg ( CountReg ) ; } else { assert ( TripCount -> isImm ( ) && <STR_LIT> ) ; int64_t CountImm = TripCount -> getImm ( ) ; if ( ! TII -> isValidOffset ( LOOP_i , CountImm ) ) { unsigned CountReg = MRI -> createVirtualRegister ( & <STR_LIT> ) ; BuildMI ( * Preheader , InsertPos , DL , TII -> get ( <STR_LIT> ) , CountReg ) . addImm ( CountImm ) ; BuildMI ( * Preheader , InsertPos , DL , TII -> get ( LOOP_r ) ) . addMBB ( LoopStart ) . addReg ( CountReg ) ; } else BuildMI ( * Preheader , InsertPos , DL , TII -> get ( LOOP_i ) ) . addMBB ( LoopStart ) . addImm ( CountImm ) ; } LoopStart -> setHasAddressTaken ( ) ; BlockAddress :: get ( const_cast < BasicBlock * > ( LoopStart -> getBasicBlock ( ) ) ) ; DebugLoc LastIDL = LastI -> getDebugLoc ( ) ; BuildMI ( * LastMBB , LastI , LastIDL , TII -> get ( ENDLOOP ) ) . addMBB ( LoopStart ) ; if ( LastI -> getOpcode ( ) == <STR_LIT> || LastI -> getOpcode ( ) == <STR_LIT> ) { MachineBasicBlock * BranchTarget = LastI -> getOperand ( <NUM_LIT> ) . getMBB ( ) ; LastI = LastMBB -> erase ( LastI ) ; if ( ! L -> contains ( BranchTarget ) ) { if ( LastI != LastMBB -> end ( ) ) LastI = LastMBB -> erase ( LastI ) ; SmallVector < MachineOperand , <NUM_LIT> > Cond ; TII -> InsertBranch ( * LastMBB , BranchTarget , nullptr , Cond , LastIDL ) ; } } else { LastMBB -> erase ( LastI ) ; } delete TripCount ; for ( unsigned i = <NUM_LIT> ; i < OldInsts . size ( ) ; ++ i ) removeIfDead ( OldInsts [ i ] ) ;


<s> MachineBasicBlock * Header = L -> getHeader ( ) ; assert ( TB && <STR_LIT> ) ; if ( ExitingBlock != Latch && ( TB == Latch || FB == Latch ) ) { MachineBasicBlock * LTB = <NUM_LIT> , * LFB = <NUM_LIT> ; SmallVector < MachineOperand , <NUM_LIT> > LCond ; bool NotAnalyzed = TII -> analyzeBranch ( * Latch , LTB , LFB , LCond , false ) ; if ( NotAnalyzed ) return nullptr ; if ( TB == Latch ) TB = ( LTB == Header ) ? LTB : LFB ; else FB = ( LTB == Header ) ? LTB : LFB ; } assert ( ( ! FB || TB == Header || FB == Header ) && <STR_LIT> ) ; if ( ! TB || ( FB && TB != Header && FB != Header ) ) return nullptr ; bool Negated = TII -> predOpcodeHasNot ( Cond ) ^ ( TB != Header ) ; unsigned PredReg , PredPos , PredRegFlags ; if ( ! TII -> getPredReg ( Cond , PredReg , PredPos , PredRegFlags ) ) return nullptr ; MachineInstr * CondI = MRI -> getVRegDef ( PredReg ) ; unsigned CondOpc = CondI -> getOpcode ( ) ; unsigned CmpReg1 = <NUM_LIT> , CmpReg2 = <NUM_LIT> ; int Mask = <NUM_LIT> , ImmValue = <NUM_LIT> ; bool AnalyzedCmp = TII -> analyzeCompare ( * CondI , CmpReg1 , CmpReg2 , Mask , ImmValue ) ; if ( ! AnalyzedCmp ) return nullptr ; OldInsts . push_back ( CondI ) ; OldInsts . push_back ( IVOp ) ; Comparison :: Kind Cmp ; bool isSwapped = false ; const MachineOperand & Op1 = CondI -> getOperand ( <NUM_LIT> ) ; const MachineOperand & Op2 = CondI -> getOperand ( <NUM_LIT> ) ; const MachineOperand * EndValue = nullptr ; if ( Op1 . isReg ( ) ) { if ( Op2 . isImm ( ) || Op1 . getReg ( ) == IVReg ) EndValue = & Op2 ; else { EndValue = & Op1 ; isSwapped = true ; } }


<s> switch ( DOpc ) { case TargetOpcode :: COPY : case <STR_LIT> : case <STR_LIT> : case <STR_LIT> : case <STR_LIT> : { if ( ! checkForImmediate ( DI -> getOperand ( <NUM_LIT> ) , TV ) ) return false ; break ; } case <STR_LIT> : case <STR_LIT> : case <STR_LIT> : case <STR_LIT> : case <STR_LIT> : { const MachineOperand & S1 = DI -> getOperand ( <NUM_LIT> ) ; const MachineOperand & S2 = DI -> getOperand ( <NUM_LIT> ) ; int64_t V1 , V2 ; if ( ! checkForImmediate ( S1 , V1 ) || ! checkForImmediate ( S2 , V2 ) ) return false ; TV = V2 | ( static_cast < uint64_t > ( V1 ) << <NUM_LIT> ) ; break ; } case TargetOpcode :: REG_SEQUENCE : { const MachineOperand & S1 = DI -> getOperand ( <NUM_LIT> ) ; const MachineOperand & S3 = DI -> getOperand ( <NUM_LIT> ) ; int64_t V1 , V3 ; if ( ! checkForImmediate ( S1 , V1 ) || ! checkForImmediate ( S3 , V3 ) ) return false ; unsigned Sub2 = DI -> getOperand ( <NUM_LIT> ) . getImm ( ) ; unsigned Sub4 = DI -> getOperand ( <NUM_LIT> ) . getImm ( ) ; if ( Sub2 == <STR_LIT> && Sub4 == <STR_LIT> ) TV = V1 | ( V3 << <NUM_LIT> ) ; else if ( Sub2 == <STR_LIT> && Sub4 == <STR_LIT> ) TV = V3 | ( V1 << <NUM_LIT> ) ; else llvm_unreachable ( <STR_LIT> ) ; break ;


<s> void <ISA_LIT>HardwareLoops :: removeIfDead ( MachineInstr * MI ) { SmallVector < MachineInstr * , <NUM_LIT> > DeadPhis ; if ( isDead ( MI , DeadPhis ) ) { LLVM_DEBUG ( dbgs ( ) << <STR_LIT> << * MI ) ; for ( unsigned i = <NUM_LIT> , e = MI -> getNumOperands ( ) ; i != e ; ++ i ) {

const MachineOperand & MO = MI -> getOperand ( i ) ;


<s> if ( ! MO . isReg ( ) || ! MO . isDef ( ) ) continue ; Register Reg = MO . getReg ( ) ; for ( MachineOperand & MO : llvm :: make_early_inc_range ( MRI -> use_operands ( Reg ) ) ) { MachineInstr * UseMI = MO . getParent ( ) ; if ( UseMI == MI ) continue ; if ( MO . isDebug ( ) ) MO . setReg ( <NUM_LIT> ) ; } } MI -> eraseFromParent ( ) ; for ( unsigned i = <NUM_LIT> ; i < DeadPhis . size ( ) ; ++ i ) DeadPhis [ i ] -> eraseFromParent ( ) ; }


<s> if ( ( Dist < <NUM_LIT> ) ^ ( IVBump < <NUM_LIT> ) ) return nullptr ; } if ( CmpHasEqual ) Dist = Dist > <NUM_LIT> ? Dist + <NUM_LIT> : Dist - <NUM_LIT> ; assert ( ( ! CmpLess || Dist > <NUM_LIT> ) && <STR_LIT> ) ; assert ( ( ! CmpGreater || Dist < <NUM_LIT> ) && <STR_LIT> ) ; int64_t Dist1 = ( IVBump > <NUM_LIT> ) ? ( Dist + ( IVBump - <NUM_LIT> ) ) / IVBump : ( - Dist + ( - IVBump - <NUM_LIT> ) ) / ( - IVBump ) ; assert ( Dist1 > <NUM_LIT> && <STR_LIT> ) ; uint64_t Count = Dist1 ; if ( Count > <NUM_LIT> ) return nullptr ; return new CountValue ( CountValue :: CV_Immediate , Count ) ; } if ( ! isPowerOf2_64 ( abs64 ( IVBump ) ) ) return nullptr ; MachineBasicBlock * PH = Loop -> getLoopPreheader ( ) ; assert ( PH && <STR_LIT> ) ; MachineBasicBlock :: iterator InsertPos = PH -> getFirstTerminator ( ) ; DebugLoc DL = ( InsertPos != PH -> end ( ) ) ? InsertPos -> getDebugLoc ( ) : DebugLoc ( ) ; if ( IVBump < <NUM_LIT> ) { std :: swap ( Start , End ) ; IVBump = - IVBump ; } bool RegToImm = Start -> isReg ( ) && End -> isImm ( ) ; bool RegToReg = Start -> isReg ( ) && End -> isReg ( ) ; int64_t StartV = <NUM_LIT> , EndV = <NUM_LIT> ; if ( Start -> isImm ( ) ) StartV = Start -> getImm ( ) ; if ( End -> isImm ( ) ) EndV = End -> getImm ( ) ; int64_t AdjV = <NUM_LIT> ; if ( CmpHasEqual ) { if ( Start -> isImm ( ) ) StartV -- ; else if ( End -> isImm ( ) ) EndV ++ ; else AdjV += <NUM_LIT> ; } if ( Cmp != Comparison :: NE ) { if ( Start -> isImm ( ) ) StartV -= ( IVBump - <NUM_LIT> ) ; else if ( End -> isImm ( ) ) EndV += ( IVBump - <NUM_LIT> ) ; else AdjV += ( IVBump - <NUM_LIT> ) ; } unsigned R = <NUM_LIT> , SR = <NUM_LIT> ; if ( Start -> isReg ( ) ) { R = Start -> getReg ( ) ; SR = Start -> getSubReg ( ) ; } else { R = End -> getReg ( ) ; SR = End -> getSubReg ( ) ; } const TargetRegisterClass * RC = MRI -> getRegClass ( R ) ;

if ( ! SR && RC == & <STR_LIT> ) return nullptr ;


<s> for ( unsigned i = <NUM_LIT> , e = Blocks . size ( ) ; i != e ; ++ i ) { MachineBasicBlock * MBB = Blocks [ i ] ; for ( MachineBasicBlock :: iterator MII = MBB -> begin ( ) , E = MBB -> end ( ) ; MII != E ; ++ MII ) { const MachineInstr * MI = & * MII ; if ( isInvalidLoopOperation ( MI ) ) return true ;


<s> const std :: vector < MachineBasicBlock * > & Blocks = L -> getBlocks ( ) ; for ( unsigned i = <NUM_LIT> , e = Blocks . size ( ) ; i != e ; ++ i ) { MachineBasicBlock * MBB = Blocks [ i ] ; for ( MachineBasicBlock :: iterator MII = MBB -> begin ( ) , E = MBB -> end ( ) ; MII != E ; ++ MII ) { const MachineInstr * MI = & * MII ; if ( isInvalidLoopOperation ( MI ) ) return true ;


<s> Contents . R . Reg = v ; Contents . R . Sub = u ; } else { Contents . ImmVal = v ; }


<s> return new <ISA_LIT>HardwareLoops ( ) ;


<s> FunctionPass * llvm :: create<ISA_LIT>HardwareLoops ( ) { return new <ISA_LIT>HardwareLoops ( ) ;


<s> unsigned PhiOpReg = Phi -> getOperand ( i ) . getReg ( ) ; MachineInstr * DI = MRI -> getVRegDef ( PhiOpReg ) ; unsigned UpdOpc = DI -> getOpcode ( ) ; bool isAdd = ( UpdOpc == <STR_LIT> ) ; if ( isAdd ) { unsigned IndReg = DI -> getOperand ( <NUM_LIT> ) . getReg ( ) ; if ( MRI -> getVRegDef ( IndReg ) == Phi ) { unsigned UpdReg = DI -> getOperand ( <NUM_LIT> ) . getReg ( ) ; int64_t V = DI -> getOperand ( <NUM_LIT> ) . getImm ( ) ; IndMap . insert ( std :: make_pair ( UpdReg , std :: make_pair ( IndReg , V ) ) ) ; } } } } SmallVector < MachineOperand , <NUM_LIT> > Cond ; MachineBasicBlock * TB = nullptr , * FB = nullptr ; bool NotAnalyzed = TII -> AnalyzeBranch ( * Latch , TB , FB , Cond , false ) ; if ( NotAnalyzed ) return false ; unsigned CSz = Cond . size ( ) ; assert ( CSz == <NUM_LIT> || CSz == <NUM_LIT> ) ; unsigned PredR = Cond [ CSz - <NUM_LIT> ] . getReg ( ) ; MachineInstr * PredI = MRI -> getVRegDef ( PredR ) ; if ( ! PredI -> isCompare ( ) ) return false ; unsigned CmpReg1 = <NUM_LIT> , CmpReg2 = <NUM_LIT> ; int CmpImm = <NUM_LIT> , CmpMask = <NUM_LIT> ; bool CmpAnalyzed = TII -> analyzeCompare ( PredI , CmpReg1 , CmpReg2 , CmpMask , CmpImm ) ; if ( ! CmpAnalyzed ) return false ; InductionMap :: iterator IndMapEnd = IndMap . end ( ) ; InductionMap :: iterator F = IndMapEnd ; if ( CmpReg1 != <NUM_LIT> ) { InductionMap :: iterator F1 = IndMap . find ( CmpReg1 ) ; if ( F1 != IndMapEnd ) F = F1 ; } if ( CmpReg2 != <NUM_LIT> ) { InductionMap :: iterator F2 = IndMap . find ( CmpReg2 ) ; if ( F2 != IndMapEnd ) {


<s> if ( MO . isUse ( ) ) { unsigned R = MO . getReg ( ) ; if ( ! defWithImmediate ( R ) ) { CmpRegs . insert ( MO . getReg ( ) ) ; continue ; } if ( CmpImmOp ) return false ; CmpImmOp = & MO ; } } else if ( MO . isImm ( ) ) { if ( CmpImmOp ) return false ; CmpImmOp = & MO ; } } if ( CmpRegs . empty ( ) ) return false ; for ( RegisterInductionSet :: iterator I = IndRegs . begin ( ) , E = IndRegs . end ( ) ; I != E ; ++ I ) { if ( CmpRegs . count ( I -> first ) ) return true ; const RegisterBump & RB = I -> second ; if ( CmpRegs . count ( RB . first ) ) { if ( ! CmpImmOp ) return false ; int64_t CmpImm = getImmediate ( * CmpImmOp ) ; int64_t V = RB . second ; if ( V > <NUM_LIT> && CmpImm + V < CmpImm ) return false ; if ( V < <NUM_LIT> && CmpImm + V > CmpImm ) return false ; CmpImm += V ; if ( CmpImmOp -> isImm ( ) && ! isInt < <NUM_LIT> > ( CmpImm ) ) return false ; MachineInstr * BumpI = MRI -> getVRegDef ( I -> first ) ; bool Order = orderBumpCompare ( BumpI , PredDef ) ; if ( ! Order ) return false ; setImmediate ( * CmpImmOp , CmpImm ) ; for ( unsigned i = <NUM_LIT> , n = PredDef -> getNumOperands ( ) ; i < n ; ++ i ) { MachineOperand & MO = PredDef -> getOperand ( i ) ; if ( MO . isReg ( ) && MO . getReg ( ) == RB . first ) { MO . setReg ( I -> first ) ;


<s> AU . addRequired < MachineLoopInfo > ( ) ;

MachineFunctionPass :: getAnalysisUsage ( AU ) ;


<s> if ( MO . isImm ( ) ) return MO . getImm ( ) ; assert ( MO . isReg ( ) ) ; unsigned R = MO . getReg ( ) ;

MachineInstr * DI = defWithImmediate ( R ) ;


<s> if ( MO . isImm ( ) ) return MO . getImm ( ) ;


<s> else if ( MBB == Latch ) IVReg = IV_Phi -> getOperand ( i ) . getReg ( ) ; } if ( ! InitialValue ) return nullptr ; SmallVector < MachineOperand , <NUM_LIT> > Cond ; MachineBasicBlock * TB = nullptr , * FB = nullptr ; bool NotAnalyzed = TII -> AnalyzeBranch ( * Latch , TB , FB , Cond , false ) ; if ( NotAnalyzed ) return nullptr ; MachineBasicBlock * Header = L -> getHeader ( ) ; assert ( TB && <STR_LIT> ) ; assert ( ( ! FB || TB == Header || FB == Header ) && <STR_LIT> ) ; if ( ! TB || ( FB && TB != Header && FB != Header ) ) return nullptr ; bool Negated = ( Cond . size ( ) > <NUM_LIT> ) ^ ( TB != Header ) ; unsigned PredReg = Cond [ Cond . size ( ) - <NUM_LIT> ] . getReg ( ) ; MachineInstr * CondI = MRI -> getVRegDef ( PredReg ) ; unsigned CondOpc = CondI -> getOpcode ( ) ; unsigned CmpReg1 = <NUM_LIT> , CmpReg2 = <NUM_LIT> ; int Mask = <NUM_LIT> , ImmValue = <NUM_LIT> ; bool AnalyzedCmp = TII -> analyzeCompare ( CondI , CmpReg1 , CmpReg2 , Mask , ImmValue ) ; if ( ! AnalyzedCmp ) return nullptr ; OldInsts . push_back ( CondI ) ; OldInsts . push_back ( IVOp ) ; Comparison :: Kind Cmp ; bool isSwapped = false ; const MachineOperand & Op1 = CondI -> getOperand ( <NUM_LIT> ) ; const MachineOperand & Op2 = CondI -> getOperand ( <NUM_LIT> ) ; const MachineOperand * EndValue = nullptr ; if ( Op1 . isReg ( ) ) { if ( Op2 . isImm ( ) || Op1 . getReg ( ) == IVReg ) EndValue = & Op2 ; else { EndValue = & Op1 ; isSwapped = true ; } }


<s> unsigned getReg ( ) const { assert ( isReg ( ) && <STR_LIT> ) ;


<s> unsigned getSubReg ( ) const { assert ( isReg ( ) && <STR_LIT> ) ;


<s> if ( ( Cmp & L ) || ( Cmp & G ) ) return ( Kind ) ( Cmp ^ ( L | G ) ) ;


<s> static Kind getSwappedComparison ( Kind Cmp ) { assert ( ( ! ( ( Cmp & L ) && ( Cmp & G ) ) ) && <STR_LIT> ) ;

if ( ( Cmp & L ) || ( Cmp & G ) ) return ( Kind ) ( Cmp ^ ( L | G ) ) ;


<s> <ISA_LIT>HardwareLoops ( ) : MachineFunctionPass ( ID ) { initialize<ISA_LIT>HardwareLoopsPass ( * PassRegistry :: getPassRegistry ( ) ) ;


<s> initialize<ISA_LIT>HardwareLoopsPass ( * PassRegistry :: getPassRegistry ( ) ) ;


<s> const MachineOperand & OPO = OnePhi -> getOperand ( j ) ; if ( ! OPO . isReg ( ) || ! OPO . isDef ( ) ) continue ; unsigned OPReg = OPO . getReg ( ) ; use_nodbg_iterator nextJ ; for ( use_nodbg_iterator J = MRI -> use_nodbg_begin ( OPReg ) ; J != End ; J = nextJ ) { nextJ = std :: next ( J ) ; MachineOperand & Use = * J ;

MachineInstr * UseMI = Use . getParent ( ) ;


<s> const MachineOperand & MO = MI -> getOperand ( i ) ; if ( ! MO . isReg ( ) || ! MO . isDef ( ) ) continue ; unsigned R = MO . getReg ( ) ; if ( R == <STR_LIT> || R == <STR_LIT> || R == <STR_LIT> || R == <STR_LIT> ) return true ; }


<s> bool <ISA_LIT>HardwareLoops :: isInvalidLoopOperation ( const MachineInstr * MI ) const { if ( MI -> getDesc ( ) . isCall ( ) ) return true ; if ( isHardwareLoop ( MI ) ) return true ; for ( unsigned i = <NUM_LIT> , e = MI -> getNumOperands ( ) ; i != e ; ++ i ) { const MachineOperand & MO = MI -> getOperand ( i ) ; if ( ! MO . isReg ( ) || ! MO . isDef ( ) ) continue ; unsigned R = MO . getReg ( ) ; if ( R == <STR_LIT> || R == <STR_LIT> || R == <STR_LIT> || R == <STR_LIT> ) return true ;


<s> MachineBasicBlock * BB = BumpI -> getParent ( ) ; if ( CmpI -> getParent ( ) != BB ) return false ; typedef MachineBasicBlock :: instr_iterator instr_iterator ; for ( instr_iterator I = BumpI , E = BB -> instr_end ( ) ; I != E ; ++ I ) if ( & * I == CmpI ) return true ; unsigned PredR = CmpI -> getOperand ( <NUM_LIT> ) . getReg ( ) ; bool FoundBump = false ; instr_iterator CmpIt = CmpI , NextIt = std :: next ( CmpIt ) ; for ( instr_iterator I = NextIt , E = BB -> instr_end ( ) ; I != E ; ++ I ) { MachineInstr * In = & * I ; for ( unsigned i = <NUM_LIT> , n = In -> getNumOperands ( ) ; i < n ; ++ i ) { MachineOperand & MO = In -> getOperand ( i ) ; if ( MO . isReg ( ) && MO . isUse ( ) ) { if ( MO . getReg ( ) == PredR ) return false ; } } if ( In == BumpI ) { instr_iterator After = BumpI ; instr_iterator From = CmpI ; BB -> splice ( std :: next ( After ) , BB , From ) ; FoundBump = true ; break ; } } assert ( FoundBump && <STR_LIT> ) ; return FoundBump ;


<s> instr_iterator CmpIt = CmpI , NextIt = std :: next ( CmpIt ) ; for ( instr_iterator I = NextIt , E = BB -> instr_end ( ) ; I != E ; ++ I ) { MachineInstr * In = & * I ; for ( unsigned i = <NUM_LIT> , n = In -> getNumOperands ( ) ; i < n ; ++ i ) { MachineOperand & MO = In -> getOperand ( i ) ; if ( MO . isReg ( ) && MO . isUse ( ) ) { if ( MO . getReg ( ) == PredR ) return false ; } } if ( In == BumpI ) {


<s> void print ( raw_ostream & OS , const TargetMachine * TM = nullptr ) const { const TargetRegisterInfo * TRI = TM ? TM -> getRegisterInfo ( ) : nullptr ; if ( isReg ( ) ) {

OS << PrintReg ( Contents . R . Reg , TRI , Contents . R . Sub ) ;


<s> OS << PrintReg ( Contents . R . Reg , TRI , Contents . R . Sub ) ; }


<s> SmallVector < MachineInstr * , <NUM_LIT> > DeadPhis ; if ( isDead ( MI , DeadPhis ) ) { DEBUG ( dbgs ( ) << <STR_LIT> << * MI ) ; for ( unsigned i = <NUM_LIT> , e = MI -> getNumOperands ( ) ; i != e ; ++ i ) { const MachineOperand & MO = MI -> getOperand ( i ) ; if ( ! MO . isReg ( ) || ! MO . isDef ( ) ) continue ; unsigned Reg = MO . getReg ( ) ; MachineRegisterInfo :: use_iterator nextI ; for ( MachineRegisterInfo :: use_iterator I = MRI -> use_begin ( Reg ) , E = MRI -> use_end ( ) ; I != E ; I = nextI ) { nextI = std :: next ( I ) ; MachineOperand & Use = * I ; MachineInstr * UseMI = I -> getParent ( ) ; if ( UseMI == MI ) continue ; if ( Use . isDebug ( ) ) UseMI -> getOperand ( <NUM_LIT> ) . setReg ( <NUM_LIT> ) ; } } MI -> eraseFromParent ( ) ;

for ( unsigned i = <NUM_LIT> ; i < DeadPhis . size ( ) ; ++ i ) DeadPhis [ i ] -> eraseFromParent ( ) ;


<s> bool <ISA_LIT>HardwareLoops :: runOnMachineFunction ( MachineFunction & MF ) { DEBUG ( dbgs ( ) << <STR_LIT> ) ; bool Changed = false ; MLI = & getAnalysis < MachineLoopInfo > ( ) ; MRI = & MF . getRegInfo ( ) ; MDT = & getAnalysis < MachineDominatorTree > ( ) ; TM = static_cast < const <ISA_LIT>TargetMachine * > ( & MF . getTarget ( ) ) ;

TII = static_cast < const <ISA_LIT>InstrInfo * > ( TM -> getInstrInfo ( ) ) ;


<s> TM = static_cast < const <ISA_LIT>TargetMachine * > ( & MF . getTarget ( ) ) ; TII = static_cast < const <ISA_LIT>InstrInfo * > ( TM -> getInstrInfo ( ) ) ; TRI = static_cast < const <ISA_LIT>RegisterInfo * > ( TM -> getRegisterInfo ( ) ) ; for ( MachineLoopInfo :: iterator I = MLI -> begin ( ) , E = MLI -> end ( ) ; I != E ; ++ I ) { MachineLoop * L = * I ; if ( ! L -> getParentLoop ( ) ) Changed |= convertToHardwareLoop ( L ) ; }


<s> return ; } const TargetRegisterClass * RC = MRI -> getRegClass ( R ) ; unsigned NewR = MRI -> createVirtualRegister ( RC ) ; MachineBasicBlock & B = * DI -> getParent ( ) ; DebugLoc DL = DI -> getDebugLoc ( ) ; BuildMI ( B , DI , DL , TII -> get ( DI -> getOpcode ( ) ) , NewR ) . addImm ( Val ) ;


<s> if ( MO . isImm ( ) ) { MO . setImm ( Val ) ; return ; } assert ( MO . isReg ( ) ) ; unsigned R = MO . getReg ( ) ; MachineInstr * DI = defWithImmediate ( R ) ; if ( MRI -> hasOneNonDBGUse ( R ) ) { DI -> getOperand ( <NUM_LIT> ) . setImm ( Val ) ; return ; } const TargetRegisterClass * RC = MRI -> getRegClass ( R ) ; unsigned NewR = MRI -> createVirtualRegister ( RC ) ;

MachineBasicBlock & B = * DI -> getParent ( ) ;


<s> if ( TII -> isZeroCost ( MI -> getOpcode ( ) ) ) return ; if ( ! Resources -> canReserveResources ( * MI ) || isNewStore ( * MI ) ) { assert ( TII -> mayBeNewStore ( * MI ) && <STR_LIT> ) ; MachineFunction * MF = MI -> getParent ( ) -> getParent ( ) ; MachineInstr * NewMI = MF -> CreateMachineInstr ( TII -> get ( TII -> getDotNewOp ( * MI ) ) , MI -> getDebugLoc ( ) ) ; if ( Resources -> canReserveResources ( * NewMI ) ) Resources -> reserveResources ( * NewMI ) ; else Resources -> reserveResources ( * MI ) ; MF -> deleteMachineInstr ( NewMI ) ; } else Resources -> reserveResources ( * MI ) ; LLVM_DEBUG ( dbgs ( ) << <STR_LIT> << * MI ) ; if ( TII -> mayBeCurLoad ( * MI ) ) for ( auto & S : SU -> Succs ) if ( S . isAssignedRegDep ( ) && S . getLatency ( ) == <NUM_LIT> && S . getSUnit ( ) -> NumPredsLeft == <NUM_LIT> ) { UsesDotCur = S . getSUnit ( ) ; DotCurPNum = PacketNum ; break ; } if ( SU == UsesDotCur ) { UsesDotCur = nullptr ; DotCurPNum = - <NUM_LIT> ; } UsesLoad = MI -> mayLoad ( ) ; if ( TII -> isHVXVec ( * MI ) && ! MI -> mayLoad ( ) && ! MI -> mayStore ( ) ) for ( auto & S : SU -> Succs ) if ( S . isAssignedRegDep ( ) && S . getLatency ( ) == <NUM_LIT> && TII -> mayBeNewStore ( * S . getSUnit ( ) -> getInstr ( ) ) && Resources -> canReserveResources ( * S . getSUnit ( ) -> getInstr ( ) ) ) {


<s> MachineInstr * NewMI = MF -> CreateMachineInstr ( TII -> get ( TII -> getDotNewOp ( * MI ) ) , MI -> getDebugLoc ( ) ) ; if ( Resources -> canReserveResources ( * NewMI ) ) RetVal = NoHazard ; LLVM_DEBUG ( dbgs ( ) << <STR_LIT> << ( RetVal == NoHazard ) << <STR_LIT> ) ; MF -> deleteMachineInstr ( NewMI ) ; } return RetVal ;


<s> HazardType RetVal = Hazard ; if ( isNewStore ( * MI ) ) { MachineFunction * MF = MI -> getParent ( ) -> getParent ( ) ; MachineInstr * NewMI = MF -> CreateMachineInstr ( TII -> get ( TII -> getDotNewOp ( * MI ) ) , MI -> getDebugLoc ( ) ) ; if ( Resources -> canReserveResources ( * NewMI ) ) RetVal = NoHazard ; LLVM_DEBUG ( dbgs ( ) << <STR_LIT> << ( RetVal == NoHazard ) << <STR_LIT> ) ;


<s> <ISA_LIT>HazardRecognizer ( const InstrItineraryData * II , const <ISA_LIT>InstrInfo * HII , const <ISA_LIT>Subtarget & ST ) : Resources ( ST . createDFAPacketizer ( II ) ) , TII ( HII ) {


<s> if ( ! TII -> mayBeNewStore ( MI ) ) return false ; MachineOperand & MO = MI . getOperand ( MI . getNumOperands ( ) - <NUM_LIT> ) ; return ( MO . isReg ( ) && RegDefs . count ( MO . getReg ( ) ) != <NUM_LIT> ) ;


<s> DEBUG ( dbgs ( ) << <STR_LIT> ) ; Resources -> clearResources ( ) ; if ( DotCurPNum != - <NUM_LIT> && DotCurPNum != ( int ) PacketNum ) { UsesDotCur = nullptr ; DotCurPNum = - <NUM_LIT> ; } PacketNum ++ ; RegDefs . clear ( ) ;


<s> MF -> DeleteMachineInstr ( NewMI ) ; } else Resources -> reserveResources ( * MI ) ; DEBUG ( dbgs ( ) << <STR_LIT> << * MI ) ; if ( TII -> mayBeCurLoad ( * MI ) ) for ( auto & S : SU -> Succs ) if ( S . isAssignedRegDep ( ) && S . getLatency ( ) == <NUM_LIT> && SU -> getHeight ( ) == S . getSUnit ( ) -> getHeight ( ) ) { UsesDotCur = S . getSUnit ( ) ; DotCurPNum = PacketNum ; break ; }


<s> void <ISA_LIT>HazardRecognizer :: EmitInstruction ( SUnit * SU ) { MachineInstr * MI = SU -> getInstr ( ) ; if ( ! MI ) return ; for ( const MachineOperand & MO : MI -> operands ( ) ) if ( MO . isReg ( ) && MO . isDef ( ) && ! MO . isImplicit ( ) ) RegDefs . insert ( MO . getReg ( ) ) ; if ( TII -> isZeroCost ( MI -> getOpcode ( ) ) ) return ; if ( ! Resources -> canReserveResources ( * MI ) ) { assert ( TII -> mayBeNewStore ( * MI ) && <STR_LIT> ) ; MachineFunction * MF = MI -> getParent ( ) -> getParent ( ) ; MachineInstr * NewMI = MF -> CreateMachineInstr ( TII -> get ( TII -> getDotNewOp ( * MI ) ) , MI -> getDebugLoc ( ) ) ; assert ( Resources -> canReserveResources ( * NewMI ) ) ;

Resources -> reserveResources ( * NewMI ) ;


<s> HazardType RetVal = Hazard ; if ( TII -> mayBeNewStore ( * MI ) ) { MachineOperand & MO = MI -> getOperand ( MI -> getNumOperands ( ) - <NUM_LIT> ) ; if ( ! MO . isReg ( ) || RegDefs . count ( MO . getReg ( ) ) == <NUM_LIT> ) return Hazard ; MachineFunction * MF = MI -> getParent ( ) -> getParent ( ) ; MachineInstr * NewMI = MF -> CreateMachineInstr ( TII -> get ( TII -> getDotNewOp ( * MI ) ) , MI -> getDebugLoc ( ) ) ; if ( Resources -> canReserveResources ( * NewMI ) ) RetVal = NoHazard ; DEBUG ( dbgs ( ) << <STR_LIT> << ( RetVal == NoHazard ) << <STR_LIT> ) ; MF -> DeleteMachineInstr ( NewMI ) ; } return RetVal ; } if ( SU == UsesDotCur && DotCurPNum != ( int ) PacketNum ) { DEBUG ( dbgs ( ) << <STR_LIT> << PacketNum << <STR_LIT> << * MI ) ; return Hazard ; } return NoHazard ;


<s> PacketNum = <NUM_LIT> ; UsesDotCur = nullptr ; DotCurPNum = - <NUM_LIT> ;


<s> bool <ISA_LIT>HazardRecognizer :: ShouldPreferAnother ( SUnit * SU ) {

return UsesDotCur && ( ( SU == UsesDotCur ) ^ ( DotCurPNum == ( int ) PacketNum ) ) ;


<s> bool <ISA_LIT>HazardRecognizer :: ShouldPreferAnother ( SUnit * SU ) { return UsesDotCur && ( ( SU == UsesDotCur ) ^ ( DotCurPNum == ( int ) PacketNum ) ) ;


<s> void <ISA_LIT>HazardRecognizer :: AdvanceCycle ( ) { DEBUG ( dbgs ( ) << <STR_LIT> ) ; Resources -> clearResources ( ) ; if ( DotCurPNum != - <NUM_LIT> && DotCurPNum != ( int ) PacketNum ) { UsesDotCur = nullptr ;


<s> DotCurPNum = - <NUM_LIT> ; } UsesLoad = false ; PrefVectorStoreNew = nullptr ; PacketNum ++ ; RegDefs . clear ( ) ;


<s> assert ( Resources -> canReserveResources ( * NewMI ) ) ; Resources -> reserveResources ( * NewMI ) ; MF -> DeleteMachineInstr ( NewMI ) ; } else Resources -> reserveResources ( * MI ) ; DEBUG ( dbgs ( ) << <STR_LIT> << * MI ) ; if ( TII -> mayBeCurLoad ( * MI ) ) for ( auto & S : SU -> Succs ) if ( S . isAssignedRegDep ( ) && S . getLatency ( ) == <NUM_LIT> && S . getSUnit ( ) -> NumPredsLeft == <NUM_LIT> ) { UsesDotCur = S . getSUnit ( ) ; DotCurPNum = PacketNum ; break ; }


<s> DEBUG ( dbgs ( ) << <STR_LIT> ) ; Resources -> clearResources ( ) ; PacketNum = <NUM_LIT> ; UsesDotCur = nullptr ; DotCurPNum = - <NUM_LIT> ; UsesLoad = false ;


<s> DotCurPNum = - <NUM_LIT> ; UsesLoad = false ; PrefVectorStoreNew = nullptr ;


<s> if ( SU == UsesDotCur ) { UsesDotCur = nullptr ; DotCurPNum = - <NUM_LIT> ; } UsesLoad = MI -> mayLoad ( ) ; if ( TII -> isHVXVec ( * MI ) && ! MI -> mayLoad ( ) && ! MI -> mayStore ( ) ) for ( auto & S : SU -> Succs ) if ( S . isAssignedRegDep ( ) && S . getLatency ( ) == <NUM_LIT> && TII -> mayBeNewStore ( * S . getSUnit ( ) -> getInstr ( ) ) && Resources -> canReserveResources ( * S . getSUnit ( ) -> getInstr ( ) ) ) { PrefVectorStoreNew = S . getSUnit ( ) ; break ;


<s> LLVM_DEBUG ( dbgs ( ) << <STR_LIT> << PacketNum << <STR_LIT> << * MI ) ; HazardType RetVal = Hazard ; if ( TII -> mayBeNewStore ( * MI ) ) { MachineOperand & MO = MI -> getOperand ( MI -> getNumOperands ( ) - <NUM_LIT> ) ; if ( ! MO . isReg ( ) || RegDefs . count ( MO . getReg ( ) ) == <NUM_LIT> ) return Hazard ; MachineFunction * MF = MI -> getParent ( ) -> getParent ( ) ;

MachineInstr * NewMI = MF -> CreateMachineInstr ( TII -> get ( TII -> getDotNewOp ( * MI ) ) , MI -> getDebugLoc ( ) ) ;


<s> DotCurPNum = - <NUM_LIT> ; } UsesLoad = false ; PrefVectorStoreNew = nullptr ; PacketNum ++ ;


<s> void <ISA_LIT>HazardRecognizer :: EmitInstruction ( SUnit * SU ) { MachineInstr * MI = SU -> getInstr ( ) ; if ( ! MI ) return ; for ( const MachineOperand & MO : MI -> operands ( ) ) if ( MO . isReg ( ) && MO . isDef ( ) && ! MO . isImplicit ( ) ) RegDefs . insert ( MO . getReg ( ) ) ; if ( TII -> isZeroCost ( MI -> getOpcode ( ) ) ) return ; if ( ! Resources -> canReserveResources ( * MI ) ) { assert ( TII -> mayBeNewStore ( * MI ) && <STR_LIT> ) ; MachineFunction * MF = MI -> getParent ( ) -> getParent ( ) ; MachineInstr * NewMI = MF -> CreateMachineInstr ( TII -> get ( TII -> getDotNewOp ( * MI ) ) , MI -> getDebugLoc ( ) ) ; assert ( Resources -> canReserveResources ( * NewMI ) ) ; Resources -> reserveResources ( * NewMI ) ; MF -> DeleteMachineInstr ( NewMI ) ; } else Resources -> reserveResources ( * MI ) ; LLVM_DEBUG ( dbgs ( ) << <STR_LIT> << * MI ) ; if ( TII -> mayBeCurLoad ( * MI ) ) for ( auto & S : SU -> Succs ) if ( S . isAssignedRegDep ( ) && S . getLatency ( ) == <NUM_LIT> && S . getSUnit ( ) -> NumPredsLeft == <NUM_LIT> ) { UsesDotCur = S . getSUnit ( ) ; DotCurPNum = PacketNum ; break ; } if ( SU == UsesDotCur ) { UsesDotCur = nullptr ; DotCurPNum = - <NUM_LIT> ; } UsesLoad = MI -> mayLoad ( ) ; if ( TII -> isHVXVec ( * MI ) && ! MI -> mayLoad ( ) && ! MI -> mayStore ( ) ) for ( auto & S : SU -> Succs ) if ( S . isAssignedRegDep ( ) && S . getLatency ( ) == <NUM_LIT> && TII -> mayBeNewStore ( * S . getSUnit ( ) -> getInstr ( ) ) && Resources -> canReserveResources ( * S . getSUnit ( ) -> getInstr ( ) ) ) { PrefVectorStoreNew = S . getSUnit ( ) ; break ; }


<s> if ( TII -> mayBeNewStore ( * MI ) ) { MachineOperand & MO = MI -> getOperand ( MI -> getNumOperands ( ) - <NUM_LIT> ) ; if ( ! MO . isReg ( ) || RegDefs . count ( MO . getReg ( ) ) == <NUM_LIT> ) return Hazard ; MachineFunction * MF = MI -> getParent ( ) -> getParent ( ) ; MachineInstr * NewMI = MF -> CreateMachineInstr ( TII -> get ( TII -> getDotNewOp ( * MI ) ) , MI -> getDebugLoc ( ) ) ; if ( Resources -> canReserveResources ( * NewMI ) ) RetVal = NoHazard ;

LLVM_DEBUG ( dbgs ( ) << <STR_LIT> << ( RetVal == NoHazard ) << <STR_LIT> ) ;


<s> LLVM_DEBUG ( dbgs ( ) << <STR_LIT> << PacketNum << <STR_LIT> << * MI ) ; HazardType RetVal = Hazard ; if ( TII -> mayBeNewStore ( * MI ) ) { MachineOperand & MO = MI -> getOperand ( MI -> getNumOperands ( ) - <NUM_LIT> ) ; if ( ! MO . isReg ( ) || RegDefs . count ( MO . getReg ( ) ) == <NUM_LIT> ) return Hazard ; MachineFunction * MF = MI -> getParent ( ) -> getParent ( ) ; MachineInstr * NewMI = MF -> CreateMachineInstr ( TII -> get ( TII -> getDotNewOp ( * MI ) ) , MI -> getDebugLoc ( ) ) ; if ( Resources -> canReserveResources ( * NewMI ) ) RetVal = NoHazard ; LLVM_DEBUG ( dbgs ( ) << <STR_LIT> << ( RetVal == NoHazard ) << <STR_LIT> ) ; MF -> DeleteMachineInstr ( NewMI ) ; } return RetVal ;


<s> <ISA_LIT>HazardRecognizer ( const InstrItineraryData * II , const <ISA_LIT>InstrInfo * HII , const <ISA_LIT>Subtarget & ST ) : Resources ( ST . createDFAPacketizer ( II ) ) , TII ( HII ) , PacketNum ( <NUM_LIT> ) , UsesDotCur ( nullptr ) , DotCurPNum ( - <NUM_LIT> ) {


<s> UsesDotCur = nullptr ; DotCurPNum = - <NUM_LIT> ; UsesLoad = false ; PrefVectorStoreNew = nullptr ;


<s> return UsesDotCur && ( ( SU == UsesDotCur ) ^ ( DotCurPNum == ( int ) PacketNum ) ) ;


<s> bool <ISA_LIT>HazardRecognizer :: ShouldPreferAnother ( SUnit * SU ) { if ( PrefVectorStoreNew != nullptr && PrefVectorStoreNew != SU ) return true ; if ( UsesLoad && SU -> isInstr ( ) && SU -> getInstr ( ) -> mayLoad ( ) ) return true ; return UsesDotCur && ( ( SU == UsesDotCur ) ^ ( DotCurPNum == ( int ) PacketNum ) ) ;


<s> explicit <ISA_LIT>InstPrinter ( const MCAsmInfo & MAI , const MCInstrInfo & MII , const MCRegisterInfo & MRI ) : MCInstPrinter ( MAI , MII , MRI ) {


<s> if ( isSigned ) return ~ ( - <NUM_LIT> << ( bits - <NUM_LIT> ) ) ;


<s> unsigned bits = ( TSFlags >> <STR_LIT> ) & <STR_LIT> ;

if ( isSigned ) return ~ ( - <NUM_LIT> << ( bits - <NUM_LIT> ) ) ;


<s> MCInstrInfo const & getMII ( ) const {


<s> unsigned bits = ( TSFlags >> <STR_LIT> ) & <STR_LIT> ; if ( isSigned ) return - <NUM_LIT> << ( bits - <NUM_LIT> ) ; return <NUM_LIT> ;


<s> explicit <ISA_LIT>InstPrinter ( MCAsmInfo const & MAI , MCInstrInfo const & MII , MCRegisterInfo const & MRI ) : MCInstPrinter ( MAI , MII , MRI ) , MII ( MII ) {


<s> static bool isExtendable ( uint64_t TSFlags ) {

return ( TSFlags >> <STR_LIT> ) & <STR_LIT> ;


<s> static bool isExtended ( uint64_t TSFlags ) { return ( TSFlags >> <STR_LIT> ) & <STR_LIT> ;


<s> assert ( ( isExtendable ( MII . TSFlags ) || isExtended ( MII . TSFlags ) ) && <STR_LIT> ) ;

if ( MO . isExpr ( ) || isExtended ( MII . TSFlags ) ) {


<s> const MCOperand & MO = MI -> getOperand ( OpNo ) ; const MCInstrDesc & MII = getMII ( ) . get ( MI -> getOpcode ( ) ) ; assert ( ( isExtendable ( MII . TSFlags ) || isExtended ( MII . TSFlags ) ) && <STR_LIT> ) ; if ( MO . isExpr ( ) || isExtended ( MII . TSFlags ) ) {


<s> O << <STR_LIT> ; } else if ( MO . isImm ( ) ) { int ImmValue = MO . getImm ( ) ; if ( ImmValue < getMinValue ( MII . TSFlags ) || ImmValue > getMaxValue ( MII . TSFlags ) ) O << <STR_LIT> ;


<s> } else if ( MO . isImm ( ) ) { int ImmValue = MO . getImm ( ) ; if ( ImmValue < getMinValue ( MII . TSFlags ) || ImmValue > getMaxValue ( MII . TSFlags ) ) O << <STR_LIT> ; }


<s> void <ISA_LIT>InstPrinter :: printFrameIndexOperand ( const MCInst * MI , unsigned OpNo , raw_ostream & O ) const { const MCOperand & MO0 = MI -> getOperand ( OpNo ) ;

const MCOperand & MO1 = MI -> getOperand ( OpNo + <NUM_LIT> ) ;


<s> MO . getExpr ( ) -> print ( O , & MAI ) ; } else if ( MO . isImm ( ) ) {

O << MI -> getOperand ( OpNo ) . getImm ( ) ;


<s> const MCOperand & MO = MI -> getOperand ( OpNo ) ; if ( MO . isExpr ( ) ) { MO . getExpr ( ) -> print ( O , & MAI ) ;


<s> HasExtender = false ; printInstruction ( MCI . getOperand ( <NUM_LIT> ) . getInst ( ) , OS ) ; } else printInstruction ( & MCI , OS ) ; setExtender ( MCI ) ; OS << <STR_LIT> ; } auto Separator = <STR_LIT> ; if ( <ISA_LIT>MCInstrInfo :: isInnerLoop ( * MI ) ) { OS << Separator ; Separator = <STR_LIT> ; MCInst ME ; ME . setOpcode ( <STR_LIT> ) ; printInstruction ( & ME , OS ) ; } if ( <ISA_LIT>MCInstrInfo :: isOuterLoop ( * MI ) ) {


<s> assert ( <ISA_LIT>MCInstrInfo :: bundleSize ( * MI ) <= HEXAGON_PACKET_SIZE ) ; HasExtender = false ; for ( auto const & I : <ISA_LIT>MCInstrInfo :: bundleInstructions ( * MI ) ) { MCInst const & MCI = * I . getInst ( ) ; if ( <ISA_LIT>MCInstrInfo :: isDuplex ( MII , MCI ) ) { printInstruction ( MCI . getOperand ( <NUM_LIT> ) . getInst ( ) , OS ) ; OS << '\v' ; HasExtender = false ;


<s> const MCOperand & MO1 = MI -> getOperand ( OpNo + <NUM_LIT> ) ; printRegName ( O , MO0 . getReg ( ) ) ;


<s> const MCOperand & MO0 = MI -> getOperand ( OpNo ) ; const MCOperand & MO1 = MI -> getOperand ( OpNo + <NUM_LIT> ) ;


<s> const MCOperand & MO = MI -> getOperand ( OpNo ) ; if ( MO . isReg ( ) ) { printRegName ( O , MO . getReg ( ) ) ; } else if ( MO . isExpr ( ) ) {

MO . getExpr ( ) -> print ( O , & MAI ) ;


<s> void <ISA_LIT>InstPrinter :: printRegName ( raw_ostream & OS , unsigned RegNo ) const { OS << getRegisterName ( RegNo ) ;


<s> void <ISA_LIT>InstPrinter :: printRegName ( raw_ostream & OS , unsigned RegNo ) const {


<s> assert ( ( ( Imm & <NUM_LIT> ) == <NUM_LIT> ) && <STR_LIT> ) ; O << formatImm ( Imm / <NUM_LIT> ) ;


<s> void <ISA_LIT>InstPrinter :: prints3_6ImmOperand ( MCInst const * MI , unsigned OpNo , raw_ostream & O ) const { int64_t Imm = MI -> getOperand ( OpNo ) . getImm ( ) ;

assert ( ( ( Imm & <NUM_LIT> ) == <NUM_LIT> ) && <STR_LIT> ) ;


<s> void <ISA_LIT>InstPrinter :: prints3_7ImmOperand ( MCInst const * MI , unsigned OpNo , raw_ostream & O ) const { int64_t Imm = MI -> getOperand ( OpNo ) . getImm ( ) ; assert ( ( ( Imm & <NUM_LIT> ) == <NUM_LIT> ) && <STR_LIT> ) ;


<s> void <ISA_LIT>InstPrinter :: prints3_7ImmOperand ( MCInst const * MI , unsigned OpNo , raw_ostream & O ) const { int64_t Imm = MI -> getOperand ( OpNo ) . getImm ( ) ;


<s> void <ISA_LIT>InstPrinter :: prints4_6ImmOperand ( MCInst const * MI , unsigned OpNo , raw_ostream & O ) const { int64_t Imm = MI -> getOperand ( OpNo ) . getImm ( ) ; assert ( ( ( Imm & <NUM_LIT> ) == <NUM_LIT> ) && <STR_LIT> ) ; O << formatImm ( Imm / <NUM_LIT> ) ;


<s> assert ( ( ( Imm & <NUM_LIT> ) == <NUM_LIT> ) && <STR_LIT> ) ;


<s> if ( HasExtender || <ISA_LIT>MCInstrInfo :: isConstExtended ( MII , * MI ) ) if ( <ISA_LIT>MCInstrInfo :: getExtendableOp ( MII , * MI ) == OpNo ) O << <STR_LIT> ;


<s> void <ISA_LIT>InstPrinter :: printBrtarget ( MCInst const * MI , unsigned OpNo , raw_ostream & O ) const { MCOperand const & MO = MI -> getOperand ( OpNo ) ; assert ( MO . isExpr ( ) ) ;

MCExpr const & Expr = * MO . getExpr ( ) ;


<s> if ( <ISA_LIT>MCInstrInfo :: getExtendableOp ( MII , * MI ) == OpNo && ( HasExtender || <ISA_LIT>MCInstrInfo :: isConstExtended ( MII , * MI ) ) ) O << <STR_LIT> ; MCOperand const & MO = MI -> getOperand ( OpNo ) ; if ( MO . isReg ( ) ) { O << getRegisterName ( MO . getReg ( ) ) ; } else if ( MO . isExpr ( ) ) {


<s> MCOperand const & MO = MI -> getOperand ( OpNo ) ; if ( MO . isReg ( ) ) { O << getRegisterName ( MO . getReg ( ) ) ; } else if ( MO . isExpr ( ) ) { int64_t Value ; if ( MO . getExpr ( ) -> evaluateAsAbsolute ( Value ) ) O << formatImm ( Value ) ;


<s> void <ISA_LIT>InstPrinter :: printRegName ( raw_ostream & O , unsigned RegNo ) const {


<s> void <ISA_LIT>InstPrinter :: printBranchOperand ( const MCInst * MI , unsigned OpNo , raw_ostream & O ) const { assert ( <STR_LIT> ) ;


<s> void <ISA_LIT>InstPrinter :: printFrameIndexOperand ( const MCInst * MI , unsigned OpNo , raw_ostream & O ) const { const MCOperand & MO0 = MI -> getOperand ( OpNo ) ; const MCOperand & MO1 = MI -> getOperand ( OpNo + <NUM_LIT> ) ; O << getRegisterName ( MO0 . getReg ( ) ) << <STR_LIT> << MO1 . getImm ( ) ;


<s> O << getRegisterName ( MO0 . getReg ( ) ) << <STR_LIT> << MO1 . getImm ( ) ;


<s> O << MI -> getOperand ( OpNo ) . getImm ( ) ;


<s> Nop . setOpcode ( <STR_LIT> ) ; printInstruction ( & Nop , O ) ; O << packetPadding << endPacket ; } printInstruction ( MI , O ) ; printAnnotation ( O , Annot ) ;


<s> const MCOperand & MO1 = MI -> getOperand ( OpNo + <NUM_LIT> ) ; O << getRegisterName ( MO0 . getReg ( ) ) ;


<s> void <ISA_LIT>InstPrinter :: printNOneImmOperand ( const MCInst * MI , unsigned OpNo , raw_ostream & O ) const { O << - <NUM_LIT> ;


<s> void <ISA_LIT>InstPrinter :: printNOneImmOperand ( const MCInst * MI , unsigned OpNo , raw_ostream & O ) const {


<s> if ( MO . isReg ( ) ) { O << getRegisterName ( MO . getReg ( ) ) ; } else if ( MO . isExpr ( ) ) { O << * MO . getExpr ( ) ; } else if ( MO . isImm ( ) ) { printImmOperand ( MI , OpNo , O ) ; } else { assert ( false && <STR_LIT> ) ; }


<s> void <ISA_LIT>InstPrinter :: printOperand ( const MCInst * MI , unsigned OpNo , raw_ostream & O ) const { const MCOperand & MO = MI -> getOperand ( OpNo ) ; if ( MO . isReg ( ) ) { O << getRegisterName ( MO . getReg ( ) ) ;


<s> void <ISA_LIT>InstPrinter :: printSymbol ( const MCInst * MI , unsigned OpNo , raw_ostream & O , bool hi ) const { const MCOperand & MO = MI -> getOperand ( OpNo ) ; O << '#' << ( hi ? <STR_LIT> : <STR_LIT> ) << '(' ; if ( MO . isImm ( ) ) { O << '#' ; printOperand ( MI , OpNo , O ) ; } else { assert ( <STR_LIT> ) ; printOperand ( MI , OpNo , O ) ; } O << ')' ;


<s> void <ISA_LIT>InstPrinter :: printUnsignedImmOperand ( const MCInst * MI , unsigned OpNo , raw_ostream & O ) const {


<s> <ISA_LIT>AsmInstPrinter :: <ISA_LIT>AsmInstPrinter ( MCInstPrinter * RawPrinter ) : MCInstPrinter ( * RawPrinter ) , RawPrinter ( RawPrinter ) {


<s> auto PacketBundle = Contents . rsplit ( '\n' ) ; auto HeadTail = PacketBundle . first . split ( '\n' ) ; auto Preamble = <STR_LIT> ; auto Separator = <STR_LIT> ; while ( ! HeadTail . first . empty ( ) ) { O << Separator ; StringRef Inst ; auto Duplex = HeadTail . first . split ( '\v' ) ; if ( ! Duplex . second . empty ( ) ) { O << Duplex . first << <STR_LIT> ; Inst = Duplex . second ; } else Inst = Duplex . first ; O << Preamble ; O << Inst ; HeadTail = HeadTail . second . split ( '\n' ) ; Preamble = <STR_LIT> ; Separator = <STR_LIT> ;


<s> std :: string Buffer ; { raw_string_ostream TempStream ( Buffer ) ; RawPrinter -> printInst ( MI , TempStream , <STR_LIT> , STI ) ; } StringRef Contents ( Buffer ) ; auto PacketBundle = Contents . rsplit ( '\n' ) ; auto HeadTail = PacketBundle . first . split ( '\n' ) ; auto Preamble = <STR_LIT> ; auto Separator = <STR_LIT> ; while ( ! HeadTail . first . empty ( ) ) { O << Separator ; StringRef Inst ; auto Duplex = HeadTail . first . split ( '\v' ) ; if ( ! Duplex . second . empty ( ) ) { O << Duplex . first << <STR_LIT> ; Inst = Duplex . second ; } else Inst = Duplex . first ;


<s> printRegName ( O , MO . getReg ( ) ) ; } else if ( MO . isExpr ( ) ) { O << * MO . getExpr ( ) ; } else if ( MO . isImm ( ) ) { printImmOperand ( MI , OpNo , O ) ;


<s> if ( MO . isReg ( ) ) { printRegName ( O , MO . getReg ( ) ) ; } else if ( MO . isExpr ( ) ) { O << * MO . getExpr ( ) ; } else if ( MO . isImm ( ) ) { printImmOperand ( MI , OpNo , O ) ; } else { llvm_unreachable ( <STR_LIT> ) ;


<s> RawPrinter -> printRegName ( O , RegNo ) ;


<s> void printSymbolLo ( MCInst const * MI , unsigned OpNo , raw_ostream & O ) const {


<s> <ISA_LIT>InstPrinter :: <ISA_LIT>InstPrinter ( MCAsmInfo const & MAI , MCInstrInfo const & MII , MCRegisterInfo const & MRI ) : MCInstPrinter ( MAI , MII , MRI ) , MII ( MII ) , HasExtender ( false ) {


<s> void <ISA_LIT>InstPrinter :: printAbsAddrOperand ( MCInst const * MI , unsigned OpNo , raw_ostream & O ) const {


<s> void <ISA_LIT>InstPrinter :: printBranchOperand ( MCInst const * MI , unsigned OpNo , raw_ostream & O ) const {


<s> void <ISA_LIT>InstPrinter :: printCallOperand ( MCInst const * MI , unsigned OpNo , raw_ostream & O ) const {


<s> assert ( MI -> getOperand ( OpNo ) . isExpr ( ) && <STR_LIT> ) ; printOperand ( MI , OpNo , O ) ;


<s> void <ISA_LIT>InstPrinter :: printConstantPool ( MCInst const * MI , unsigned OpNo , raw_ostream & O ) const {

assert ( MI -> getOperand ( OpNo ) . isExpr ( ) && <STR_LIT> ) ;


<s> void <ISA_LIT>InstPrinter :: printExtOperand ( MCInst const * MI , unsigned OpNo , raw_ostream & O ) const {


<s> HasExtender = false ; for ( auto const & I : <ISA_LIT>MCInstrInfo :: bundleInstructions ( * MI ) ) { MCInst const & MCI = * I . getInst ( ) ; if ( <ISA_LIT>MCInstrInfo :: isDuplex ( MII , MCI ) ) { printInstruction ( MCI . getOperand ( <NUM_LIT> ) . getInst ( ) , OS ) ; OS << '\v' ; HasExtender = false ; printInstruction ( MCI . getOperand ( <NUM_LIT> ) . getInst ( ) , OS ) ; } else printInstruction ( & MCI , OS ) ; setExtender ( MCI ) ; OS << <STR_LIT> ; }


<s> O << - MI -> getOperand ( OpNo ) . getImm ( ) ;


<s> void <ISA_LIT>InstPrinter :: printNOneImmOperand ( MCInst const * MI , unsigned OpNo , raw_ostream & O ) const { O << - <NUM_LIT> ;


<s> void <ISA_LIT>InstPrinter :: printPredicateOperand ( MCInst const * MI , unsigned OpNo , raw_ostream & O ) const {


<s> void <ISA_LIT>InstPrinter :: printRegName ( raw_ostream & O , unsigned RegNo ) const { O << getRegName ( RegNo ) ;


<s> assert ( Success ) ; ( void ) Success ; assert ( ( ( Imm & <NUM_LIT> ) == <NUM_LIT> ) && <STR_LIT> ) ; O << formatImm ( Imm / <NUM_LIT> ) ;


<s> void <ISA_LIT>InstPrinter :: prints3_6ImmOperand ( MCInst const * MI , unsigned OpNo , raw_ostream & O ) const { int64_t Imm ; bool Success = MI -> getOperand ( OpNo ) . getExpr ( ) -> evaluateAsAbsolute ( Imm ) ; Imm = SignExtend64 < <NUM_LIT> > ( Imm ) ;


<s> int64_t Imm ; bool Success = MI -> getOperand ( OpNo ) . getExpr ( ) -> evaluateAsAbsolute ( Imm ) ; Imm = SignExtend64 < <NUM_LIT> > ( Imm ) ; assert ( Success ) ; ( void ) Success ;


<s> assert ( Success ) ; ( void ) Success ; assert ( ( ( Imm & <NUM_LIT> ) == <NUM_LIT> ) && <STR_LIT> ) ;


<s> bool Success = MI -> getOperand ( OpNo ) . getExpr ( ) -> evaluateAsAbsolute ( Imm ) ; Imm = SignExtend64 < <NUM_LIT> > ( Imm ) ; assert ( Success ) ; ( void ) Success ; assert ( ( ( Imm & <NUM_LIT> ) == <NUM_LIT> ) && <STR_LIT> ) ; O << formatImm ( Imm / <NUM_LIT> ) ;


<s> int64_t Imm ; bool Success = MI -> getOperand ( OpNo ) . getExpr ( ) -> evaluateAsAbsolute ( Imm ) ; Imm = SignExtend64 < <NUM_LIT> > ( Imm ) ; assert ( Success ) ; ( void ) Success ; assert ( ( ( Imm & <NUM_LIT> ) == <NUM_LIT> ) && <STR_LIT> ) ; O << formatImm ( Imm / <NUM_LIT> ) ;


<s> O << MI -> getOperand ( OpNo ) . getImm ( ) ;


<s> void <ISA_LIT>InstPrinter :: printImmOperand ( const MCInst * MI , unsigned OpNo , raw_ostream & O ) const {


<s> assert ( MI -> isEndPacket ( ) && <STR_LIT> ) ; if ( MI -> isStartPacket ( ) ) { <ISA_LIT>MCInst Nop ; StringRef NoAnnot ; Nop . setOpcode ( <STR_LIT> ) ; Nop . setStartPacket ( MI -> isStartPacket ( ) ) ; printInst ( & Nop , O , NoAnnot ) ; } if ( MI -> isEndPacket ( ) ) O << packetPadding << endPacket ; printInstruction ( MI , O ) ; } else { if ( MI -> isStartPacket ( ) ) O << packetPadding << startPacket << '\n' ; printInstruction ( MI , O ) ; if ( MI -> isEndPacket ( ) ) O << '\n' << packetPadding << endPacket ; } printAnnotation ( O , Annot ) ;


<s> StringRef NoAnnot ; Nop . setOpcode ( <STR_LIT> ) ; <ISA_LIT>MCInstrInfo :: setPacketBegin ( Nop , <ISA_LIT>MCInstrInfo :: isPacketBegin ( * MI ) ) ; printInst ( & Nop , O , NoAnnot , STI ) ; } if ( <ISA_LIT>MCInstrInfo :: isPacketEnd ( * MI ) ) O << PacketPadding << endPacket ; printInstruction ( MI , O ) ; } else { if ( <ISA_LIT>MCInstrInfo :: isPacketBegin ( * MI ) ) O << PacketPadding << startPacket << '\n' ; printInstruction ( MI , O ) ; if ( <ISA_LIT>MCInstrInfo :: isPacketEnd ( * MI ) ) O << '\n' << PacketPadding << endPacket ; }