mirror of
				https://github.com/c64scene-ar/llvm-6502.git
				synced 2025-11-04 05:17:07 +00:00 
			
		
		
		
	R600/SI: Fix incorrect commute operation in shrink instructions pass
We were commuting the instruction by still shrinking it using the original opcode. NOTE: This is a candidate for the 3.5 branch. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@214463 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
		@@ -668,6 +668,10 @@ bool SIInstrInfo::isImmOperandLegal(const MachineInstr *MI, unsigned OpNo,
 | 
				
			|||||||
  return RI.regClassCanUseImmediate(OpInfo.RegClass);
 | 
					  return RI.regClassCanUseImmediate(OpInfo.RegClass);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					bool SIInstrInfo::hasVALU32BitEncoding(unsigned Opcode) const {
 | 
				
			||||||
 | 
					  return AMDGPU::getVOPe32(Opcode) != -1;
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
bool SIInstrInfo::verifyInstruction(const MachineInstr *MI,
 | 
					bool SIInstrInfo::verifyInstruction(const MachineInstr *MI,
 | 
				
			||||||
                                    StringRef &ErrInfo) const {
 | 
					                                    StringRef &ErrInfo) const {
 | 
				
			||||||
  uint16_t Opcode = MI->getOpcode();
 | 
					  uint16_t Opcode = MI->getOpcode();
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -115,6 +115,10 @@ public:
 | 
				
			|||||||
  bool isImmOperandLegal(const MachineInstr *MI, unsigned OpNo,
 | 
					  bool isImmOperandLegal(const MachineInstr *MI, unsigned OpNo,
 | 
				
			||||||
                         const MachineOperand &MO) const;
 | 
					                         const MachineOperand &MO) const;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  /// \brief Return true if this 64-bit VALU instruction has a 32-bit encoding.
 | 
				
			||||||
 | 
					  /// This function will return false if you pass it a 32-bit instruction.
 | 
				
			||||||
 | 
					  bool hasVALU32BitEncoding(unsigned Opcode) const;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  bool verifyInstruction(const MachineInstr *MI,
 | 
					  bool verifyInstruction(const MachineInstr *MI,
 | 
				
			||||||
                         StringRef &ErrInfo) const override;
 | 
					                         StringRef &ErrInfo) const override;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -125,9 +125,7 @@ bool SIShrinkInstructions::runOnMachineFunction(MachineFunction &MF) {
 | 
				
			|||||||
      Next = std::next(I);
 | 
					      Next = std::next(I);
 | 
				
			||||||
      MachineInstr &MI = *I;
 | 
					      MachineInstr &MI = *I;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
      int Op32 = AMDGPU::getVOPe32(MI.getOpcode());
 | 
					      if (!TII->hasVALU32BitEncoding(MI.getOpcode()))
 | 
				
			||||||
 | 
					 | 
				
			||||||
      if (Op32 == -1)
 | 
					 | 
				
			||||||
        continue;
 | 
					        continue;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
      if (!canShrink(MI, TII, TRI, MRI)) {
 | 
					      if (!canShrink(MI, TII, TRI, MRI)) {
 | 
				
			||||||
@@ -138,6 +136,13 @@ bool SIShrinkInstructions::runOnMachineFunction(MachineFunction &MF) {
 | 
				
			|||||||
          continue;
 | 
					          continue;
 | 
				
			||||||
      }
 | 
					      }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					      int Op32 = AMDGPU::getVOPe32(MI.getOpcode());
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					      // Op32 could be -1 here if we started with an instruction that had a
 | 
				
			||||||
 | 
					      // a 32-bit encoding and then commuted it to an instruction that did not.
 | 
				
			||||||
 | 
					      if (Op32 == -1)
 | 
				
			||||||
 | 
					        continue;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
      if (TII->isVOPC(Op32)) {
 | 
					      if (TII->isVOPC(Op32)) {
 | 
				
			||||||
        unsigned DstReg = MI.getOperand(0).getReg();
 | 
					        unsigned DstReg = MI.getOperand(0).getReg();
 | 
				
			||||||
        if (TargetRegisterInfo::isVirtualRegister(DstReg)) {
 | 
					        if (TargetRegisterInfo::isVirtualRegister(DstReg)) {
 | 
				
			||||||
 
 | 
				
			|||||||
							
								
								
									
										41
									
								
								test/CodeGen/R600/vop-shrink.ll
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										41
									
								
								test/CodeGen/R600/vop-shrink.ll
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,41 @@
 | 
				
			|||||||
 | 
					; RUN: llc -march=r600 -mcpu=SI -verify-machineinstrs< %s | FileCheck -check-prefix=SI -check-prefix=FUNC %s
 | 
				
			||||||
 | 
					; XXX: This testis for a bug in the SIShrinkInstruction pass and it will be
 | 
				
			||||||
 | 
					;       relevant once we are selecting 64-bit instructions.  We are
 | 
				
			||||||
 | 
					;       currently selecting mostly 32-bit instruction, so the
 | 
				
			||||||
 | 
					;       SIShrinkInstructions pass isn't doing much.
 | 
				
			||||||
 | 
					; XFAIL: *
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					; Test that we correctly commute a sub instruction
 | 
				
			||||||
 | 
					; FUNC-LABEL: @sub_rev
 | 
				
			||||||
 | 
					; SI-NOT: V_SUB_I32_e32 v{{[0-9]+}}, s
 | 
				
			||||||
 | 
					; SI: V_SUBREV_I32_e32 v{{[0-9]+}}, s
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					; ModuleID = 'vop-shrink.ll'
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					define void @sub_rev(i32 addrspace(1)* %out, <4 x i32> %sgpr, i32 %cond) {
 | 
				
			||||||
 | 
					entry:
 | 
				
			||||||
 | 
					  %vgpr = call i32 @llvm.r600.read.tidig.x() #1
 | 
				
			||||||
 | 
					  %tmp = icmp eq i32 %cond, 0
 | 
				
			||||||
 | 
					  br i1 %tmp, label %if, label %else
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					if:                                               ; preds = %entry
 | 
				
			||||||
 | 
					  %tmp1 = getelementptr i32 addrspace(1)* %out, i32 1
 | 
				
			||||||
 | 
					  %tmp2 = extractelement <4 x i32> %sgpr, i32 1
 | 
				
			||||||
 | 
					  store i32 %tmp2, i32 addrspace(1)* %out
 | 
				
			||||||
 | 
					  br label %endif
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					else:                                             ; preds = %entry
 | 
				
			||||||
 | 
					  %tmp3 = extractelement <4 x i32> %sgpr, i32 2
 | 
				
			||||||
 | 
					  %tmp4 = sub i32 %vgpr, %tmp3
 | 
				
			||||||
 | 
					  store i32 %tmp4, i32 addrspace(1)* %out
 | 
				
			||||||
 | 
					  br label %endif
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					endif:                                            ; preds = %else, %if
 | 
				
			||||||
 | 
					  ret void
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					; Function Attrs: nounwind readnone
 | 
				
			||||||
 | 
					declare i32 @llvm.r600.read.tidig.x() #0
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					attributes #0 = { nounwind readnone }
 | 
				
			||||||
 | 
					attributes #1 = { readnone }
 | 
				
			||||||
		Reference in New Issue
	
	Block a user