Index: lib/Target/Mips/MipsInstructionSelector.cpp =================================================================== --- lib/Target/Mips/MipsInstructionSelector.cpp +++ lib/Target/Mips/MipsInstructionSelector.cpp @@ -436,6 +436,18 @@ .add(I.getOperand(3)); break; } + case G_IMPLICIT_DEF: { + MI = BuildMI(MBB, I, I.getDebugLoc(), TII.get(Mips::IMPLICIT_DEF)) + .add(I.getOperand(0)); + + // Set class based on register bank, there can be fpr and gpr implicit def. + MRI.setRegClass(MI->getOperand(0).getReg(), + getRegClassForTypeOnBank( + MRI.getType(I.getOperand(0).getReg()).getSizeInBits(), + *RBI.getRegBank(I.getOperand(0).getReg(), MRI, TRI), + RBI)); + break; + } case G_CONSTANT: { MachineIRBuilder B(I); if (!materialize32BitImm(I.getOperand(0).getReg(), Index: lib/Target/Mips/MipsLegalizerInfo.cpp =================================================================== --- lib/Target/Mips/MipsLegalizerInfo.cpp +++ lib/Target/Mips/MipsLegalizerInfo.cpp @@ -43,6 +43,9 @@ {p0, p0, 32, 8}}) .minScalar(0, s32); + getActionDefinitionsBuilder(G_IMPLICIT_DEF) + .legalFor({s32, s64}); + getActionDefinitionsBuilder(G_UNMERGE_VALUES) .legalFor({{s32, s64}}); Index: lib/Target/Mips/MipsRegisterBankInfo.cpp =================================================================== --- lib/Target/Mips/MipsRegisterBankInfo.cpp +++ lib/Target/Mips/MipsRegisterBankInfo.cpp @@ -149,6 +149,7 @@ case TargetOpcode::G_STORE: case TargetOpcode::G_PHI: case TargetOpcode::G_SELECT: + case TargetOpcode::G_IMPLICIT_DEF: return true; default: return false; @@ -230,6 +231,9 @@ addUseDef(MI->getOperand(2).getReg(), MRI); addUseDef(MI->getOperand(3).getReg(), MRI); } + + if (MI->getOpcode() == TargetOpcode::G_IMPLICIT_DEF) + addDefUses(MI->getOperand(0).getReg(), MRI); } bool MipsRegisterBankInfo::TypeInfoForMF::visit( @@ -495,6 +499,24 @@ } break; } + case G_IMPLICIT_DEF: { + unsigned Size = MRI.getType(MI.getOperand(0).getReg()).getSizeInBits(); + InstType InstTy = InstType::Integer; + if (!MRI.getType(MI.getOperand(0).getReg()).isPointer()) { + InstTy = TI.determineInstType(&MI); + } + + if (InstTy == InstType::FloatingPoint) { // fprb + OperandsMapping = Size == 32 ? &Mips::ValueMappings[Mips::SPRIdx] + : &Mips::ValueMappings[Mips::DPRIdx]; + } else { // gprb + OperandsMapping = Size == 32 ? &Mips::ValueMappings[Mips::GPRIdx] + : &Mips::ValueMappings[Mips::DPRIdx]; + if (Size == 64) + MappingID = CustomMappingID; + } + break; + } case G_UNMERGE_VALUES: { OperandsMapping = getOperandsMapping({&Mips::ValueMappings[Mips::GPRIdx], &Mips::ValueMappings[Mips::GPRIdx], @@ -638,7 +660,8 @@ case TargetOpcode::G_LOAD: case TargetOpcode::G_STORE: case TargetOpcode::G_PHI: - case TargetOpcode::G_SELECT: { + case TargetOpcode::G_SELECT: + case TargetOpcode::G_IMPLICIT_DEF: { Helper.narrowScalar(MI, 0, LLT::scalar(32)); // Handle new instructions. while (!NewInstrs.empty()) { Index: test/CodeGen/Mips/GlobalISel/instruction-select/implicit_def.mir =================================================================== --- /dev/null +++ test/CodeGen/Mips/GlobalISel/instruction-select/implicit_def.mir @@ -0,0 +1,114 @@ +# NOTE: Assertions have been autogenerated by utils/update_mir_test_checks.py +# RUN: llc -O0 -mtriple=mipsel-linux-gnu -run-pass=instruction-select -verify-machineinstrs %s -o - | FileCheck %s -check-prefixes=MIPS32 +--- | + + declare void @f_i32(i32) + define void @g_i32() {entry: ret void} + + declare void @f_i64(i64) + define void @g_i64() {entry: ret void} + + declare void @f_float(float) + define void @g_float() {entry: ret void} + + declare void @f_double(double) + define void @g_double() {entry: ret void} + +... +--- +name: g_i32 +alignment: 2 +legalized: true +regBankSelected: true +tracksRegLiveness: true +body: | + bb.1.entry: + ; MIPS32-LABEL: name: g_i32 + ; MIPS32: [[DEF:%[0-9]+]]:gpr32 = IMPLICIT_DEF + ; MIPS32: ADJCALLSTACKDOWN 16, 0, implicit-def $sp, implicit $sp + ; MIPS32: $a0 = COPY [[DEF]] + ; MIPS32: JAL @f_i32, csr_o32, implicit-def $ra, implicit-def $sp, implicit $a0 + ; MIPS32: ADJCALLSTACKUP 16, 0, implicit-def $sp, implicit $sp + ; MIPS32: RetRA + %0:gprb(s32) = G_IMPLICIT_DEF + ADJCALLSTACKDOWN 16, 0, implicit-def $sp, implicit $sp + $a0 = COPY %0(s32) + JAL @f_i32, csr_o32, implicit-def $ra, implicit-def $sp, implicit $a0 + ADJCALLSTACKUP 16, 0, implicit-def $sp, implicit $sp + RetRA + +... +--- +name: g_i64 +alignment: 2 +legalized: true +regBankSelected: true +tracksRegLiveness: true +body: | + bb.1.entry: + ; MIPS32-LABEL: name: g_i64 + ; MIPS32: [[DEF:%[0-9]+]]:gpr32 = IMPLICIT_DEF + ; MIPS32: [[DEF1:%[0-9]+]]:gpr32 = IMPLICIT_DEF + ; MIPS32: ADJCALLSTACKDOWN 16, 0, implicit-def $sp, implicit $sp + ; MIPS32: $a0 = COPY [[DEF]] + ; MIPS32: $a1 = COPY [[DEF1]] + ; MIPS32: JAL @f_i64, csr_o32, implicit-def $ra, implicit-def $sp, implicit $a0, implicit $a1 + ; MIPS32: ADJCALLSTACKUP 16, 0, implicit-def $sp, implicit $sp + ; MIPS32: RetRA + %3:gprb(s32) = G_IMPLICIT_DEF + %4:gprb(s32) = G_IMPLICIT_DEF + ADJCALLSTACKDOWN 16, 0, implicit-def $sp, implicit $sp + $a0 = COPY %3(s32) + $a1 = COPY %4(s32) + JAL @f_i64, csr_o32, implicit-def $ra, implicit-def $sp, implicit $a0, implicit $a1 + ADJCALLSTACKUP 16, 0, implicit-def $sp, implicit $sp + RetRA + +... +--- +name: g_float +alignment: 2 +legalized: true +regBankSelected: true +tracksRegLiveness: true +body: | + bb.1.entry: + ; MIPS32-LABEL: name: g_float + ; MIPS32: [[DEF:%[0-9]+]]:fgr32 = IMPLICIT_DEF + ; MIPS32: ADJCALLSTACKDOWN 16, 0, implicit-def $sp, implicit $sp + ; MIPS32: $f12 = COPY [[DEF]] + ; MIPS32: JAL @f_float, csr_o32, implicit-def $ra, implicit-def $sp, implicit $f12 + ; MIPS32: ADJCALLSTACKUP 16, 0, implicit-def $sp, implicit $sp + ; MIPS32: RetRA + %0:fprb(s32) = G_IMPLICIT_DEF + ADJCALLSTACKDOWN 16, 0, implicit-def $sp, implicit $sp + $f12 = COPY %0(s32) + JAL @f_float, csr_o32, implicit-def $ra, implicit-def $sp, implicit $f12 + ADJCALLSTACKUP 16, 0, implicit-def $sp, implicit $sp + RetRA + +... +--- +name: g_double +alignment: 2 +legalized: true +regBankSelected: true +tracksRegLiveness: true +body: | + bb.1.entry: + ; MIPS32-LABEL: name: g_double + ; MIPS32: [[DEF:%[0-9]+]]:afgr64 = IMPLICIT_DEF + ; MIPS32: ADJCALLSTACKDOWN 16, 0, implicit-def $sp, implicit $sp + ; MIPS32: $d6 = COPY [[DEF]] + ; MIPS32: JAL @f_double, csr_o32, implicit-def $ra, implicit-def $sp, implicit $d6 + ; MIPS32: ADJCALLSTACKUP 16, 0, implicit-def $sp, implicit $sp + ; MIPS32: RetRA + %0:fprb(s64) = G_IMPLICIT_DEF + ADJCALLSTACKDOWN 16, 0, implicit-def $sp, implicit $sp + $d6 = COPY %0(s64) + JAL @f_double, csr_o32, implicit-def $ra, implicit-def $sp, implicit $d6 + ADJCALLSTACKUP 16, 0, implicit-def $sp, implicit $sp + RetRA + +... + Index: test/CodeGen/Mips/GlobalISel/legalizer/implicit_def.mir =================================================================== --- /dev/null +++ test/CodeGen/Mips/GlobalISel/legalizer/implicit_def.mir @@ -0,0 +1,105 @@ +# NOTE: Assertions have been autogenerated by utils/update_mir_test_checks.py +# RUN: llc -O0 -mtriple=mipsel-linux-gnu -run-pass=legalizer -verify-machineinstrs %s -o - | FileCheck %s -check-prefixes=MIPS32 +--- | + + declare void @f_i32(i32) + define void @g_i32() {entry: ret void} + + declare void @f_i64(i64) + define void @g_i64() {entry: ret void} + + declare void @f_float(float) + define void @g_float() {entry: ret void} + + declare void @f_double(double) + define void @g_double() {entry: ret void} + +... +--- +name: g_i32 +alignment: 2 +tracksRegLiveness: true +body: | + bb.1.entry: + ; MIPS32-LABEL: name: g_i32 + ; MIPS32: [[DEF:%[0-9]+]]:_(s32) = G_IMPLICIT_DEF + ; MIPS32: ADJCALLSTACKDOWN 16, 0, implicit-def $sp, implicit $sp + ; MIPS32: $a0 = COPY [[DEF]](s32) + ; MIPS32: JAL @f_i32, csr_o32, implicit-def $ra, implicit-def $sp, implicit $a0 + ; MIPS32: ADJCALLSTACKUP 16, 0, implicit-def $sp, implicit $sp + ; MIPS32: RetRA + %0:_(s32) = G_IMPLICIT_DEF + ADJCALLSTACKDOWN 16, 0, implicit-def $sp, implicit $sp + $a0 = COPY %0(s32) + JAL @f_i32, csr_o32, implicit-def $ra, implicit-def $sp, implicit $a0 + ADJCALLSTACKUP 16, 0, implicit-def $sp, implicit $sp + RetRA + +... +--- +name: g_i64 +alignment: 2 +tracksRegLiveness: true +body: | + bb.1.entry: + ; MIPS32-LABEL: name: g_i64 + ; MIPS32: [[DEF:%[0-9]+]]:_(s64) = G_IMPLICIT_DEF + ; MIPS32: ADJCALLSTACKDOWN 16, 0, implicit-def $sp, implicit $sp + ; MIPS32: [[UV:%[0-9]+]]:_(s32), [[UV1:%[0-9]+]]:_(s32) = G_UNMERGE_VALUES [[DEF]](s64) + ; MIPS32: $a0 = COPY [[UV]](s32) + ; MIPS32: $a1 = COPY [[UV1]](s32) + ; MIPS32: JAL @f_i64, csr_o32, implicit-def $ra, implicit-def $sp, implicit $a0, implicit $a1 + ; MIPS32: ADJCALLSTACKUP 16, 0, implicit-def $sp, implicit $sp + ; MIPS32: RetRA + %0:_(s64) = G_IMPLICIT_DEF + ADJCALLSTACKDOWN 16, 0, implicit-def $sp, implicit $sp + %1:_(s32), %2:_(s32) = G_UNMERGE_VALUES %0(s64) + $a0 = COPY %1(s32) + $a1 = COPY %2(s32) + JAL @f_i64, csr_o32, implicit-def $ra, implicit-def $sp, implicit $a0, implicit $a1 + ADJCALLSTACKUP 16, 0, implicit-def $sp, implicit $sp + RetRA + +... +--- +name: g_float +alignment: 2 +tracksRegLiveness: true +body: | + bb.1.entry: + ; MIPS32-LABEL: name: g_float + ; MIPS32: [[DEF:%[0-9]+]]:_(s32) = G_IMPLICIT_DEF + ; MIPS32: ADJCALLSTACKDOWN 16, 0, implicit-def $sp, implicit $sp + ; MIPS32: $f12 = COPY [[DEF]](s32) + ; MIPS32: JAL @f_float, csr_o32, implicit-def $ra, implicit-def $sp, implicit $f12 + ; MIPS32: ADJCALLSTACKUP 16, 0, implicit-def $sp, implicit $sp + ; MIPS32: RetRA + %0:_(s32) = G_IMPLICIT_DEF + ADJCALLSTACKDOWN 16, 0, implicit-def $sp, implicit $sp + $f12 = COPY %0(s32) + JAL @f_float, csr_o32, implicit-def $ra, implicit-def $sp, implicit $f12 + ADJCALLSTACKUP 16, 0, implicit-def $sp, implicit $sp + RetRA + +... +--- +name: g_double +alignment: 2 +tracksRegLiveness: true +body: | + bb.1.entry: + ; MIPS32-LABEL: name: g_double + ; MIPS32: [[DEF:%[0-9]+]]:_(s64) = G_IMPLICIT_DEF + ; MIPS32: ADJCALLSTACKDOWN 16, 0, implicit-def $sp, implicit $sp + ; MIPS32: $d6 = COPY [[DEF]](s64) + ; MIPS32: JAL @f_double, csr_o32, implicit-def $ra, implicit-def $sp, implicit $d6 + ; MIPS32: ADJCALLSTACKUP 16, 0, implicit-def $sp, implicit $sp + ; MIPS32: RetRA + %0:_(s64) = G_IMPLICIT_DEF + ADJCALLSTACKDOWN 16, 0, implicit-def $sp, implicit $sp + $d6 = COPY %0(s64) + JAL @f_double, csr_o32, implicit-def $ra, implicit-def $sp, implicit $d6 + ADJCALLSTACKUP 16, 0, implicit-def $sp, implicit $sp + RetRA + +... Index: test/CodeGen/Mips/GlobalISel/llvm-ir/implicit_def.ll =================================================================== --- /dev/null +++ test/CodeGen/Mips/GlobalISel/llvm-ir/implicit_def.ll @@ -0,0 +1,83 @@ +; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py +; RUN: llc -O0 -mtriple=mipsel-linux-gnu -global-isel -verify-machineinstrs %s -o -| FileCheck %s -check-prefixes=MIPS32 + +declare void @f_i32(i32) +define void @g_i32() { +; MIPS32-LABEL: g_i32: +; MIPS32: # %bb.0: # %entry +; MIPS32-NEXT: addiu $sp, $sp, -24 +; MIPS32-NEXT: .cfi_def_cfa_offset 24 +; MIPS32-NEXT: sw $ra, 20($sp) # 4-byte Folded Spill +; MIPS32-NEXT: .cfi_offset 31, -4 +; MIPS32-NEXT: # implicit-def: $a0 +; MIPS32-NEXT: jal f_i32 +; MIPS32-NEXT: nop +; MIPS32-NEXT: lw $ra, 20($sp) # 4-byte Folded Reload +; MIPS32-NEXT: addiu $sp, $sp, 24 +; MIPS32-NEXT: jr $ra +; MIPS32-NEXT: nop +entry: + call void @f_i32(i32 undef) + ret void +} + +declare void @f_i64(i64) +define void @g_i64() { +; MIPS32-LABEL: g_i64: +; MIPS32: # %bb.0: # %entry +; MIPS32-NEXT: addiu $sp, $sp, -24 +; MIPS32-NEXT: .cfi_def_cfa_offset 24 +; MIPS32-NEXT: sw $ra, 20($sp) # 4-byte Folded Spill +; MIPS32-NEXT: .cfi_offset 31, -4 +; MIPS32-NEXT: # implicit-def: $a0 +; MIPS32-NEXT: # implicit-def: $a1 +; MIPS32-NEXT: jal f_i64 +; MIPS32-NEXT: nop +; MIPS32-NEXT: lw $ra, 20($sp) # 4-byte Folded Reload +; MIPS32-NEXT: addiu $sp, $sp, 24 +; MIPS32-NEXT: jr $ra +; MIPS32-NEXT: nop +entry: + call void @f_i64(i64 undef) + ret void +} + +declare void @f_float(float) +define void @g_float() { +; MIPS32-LABEL: g_float: +; MIPS32: # %bb.0: # %entry +; MIPS32-NEXT: addiu $sp, $sp, -24 +; MIPS32-NEXT: .cfi_def_cfa_offset 24 +; MIPS32-NEXT: sw $ra, 20($sp) # 4-byte Folded Spill +; MIPS32-NEXT: .cfi_offset 31, -4 +; MIPS32-NEXT: # implicit-def: $f12 +; MIPS32-NEXT: jal f_float +; MIPS32-NEXT: nop +; MIPS32-NEXT: lw $ra, 20($sp) # 4-byte Folded Reload +; MIPS32-NEXT: addiu $sp, $sp, 24 +; MIPS32-NEXT: jr $ra +; MIPS32-NEXT: nop +entry: + call void @f_float(float undef) + ret void +} + +declare void @f_double(double) +define void @g_double() { +; MIPS32-LABEL: g_double: +; MIPS32: # %bb.0: # %entry +; MIPS32-NEXT: addiu $sp, $sp, -24 +; MIPS32-NEXT: .cfi_def_cfa_offset 24 +; MIPS32-NEXT: sw $ra, 20($sp) # 4-byte Folded Spill +; MIPS32-NEXT: .cfi_offset 31, -4 +; MIPS32-NEXT: # implicit-def: $d6 +; MIPS32-NEXT: jal f_double +; MIPS32-NEXT: nop +; MIPS32-NEXT: lw $ra, 20($sp) # 4-byte Folded Reload +; MIPS32-NEXT: addiu $sp, $sp, 24 +; MIPS32-NEXT: jr $ra +; MIPS32-NEXT: nop +entry: + call void @f_double(double undef) + ret void +} Index: test/CodeGen/Mips/GlobalISel/regbankselect/implicit_def.mir =================================================================== --- /dev/null +++ test/CodeGen/Mips/GlobalISel/regbankselect/implicit_def.mir @@ -0,0 +1,110 @@ +# NOTE: Assertions have been autogenerated by utils/update_mir_test_checks.py +# RUN: llc -O0 -mtriple=mipsel-linux-gnu -run-pass=regbankselect -verify-machineinstrs %s -o - | FileCheck %s -check-prefixes=MIPS32 +--- | + + declare void @f_i32(i32) + define void @g_i32() {entry: ret void} + + declare void @f_i64(i64) + define void @g_i64() {entry: ret void} + + declare void @f_float(float) + define void @g_float() {entry: ret void} + + declare void @f_double(double) + define void @g_double() {entry: ret void} + +... +--- +name: g_i32 +alignment: 2 +legalized: true +tracksRegLiveness: true +body: | + bb.1.entry: + ; MIPS32-LABEL: name: g_i32 + ; MIPS32: [[DEF:%[0-9]+]]:gprb(s32) = G_IMPLICIT_DEF + ; MIPS32: ADJCALLSTACKDOWN 16, 0, implicit-def $sp, implicit $sp + ; MIPS32: $a0 = COPY [[DEF]](s32) + ; MIPS32: JAL @f_i32, csr_o32, implicit-def $ra, implicit-def $sp, implicit $a0 + ; MIPS32: ADJCALLSTACKUP 16, 0, implicit-def $sp, implicit $sp + ; MIPS32: RetRA + %0:_(s32) = G_IMPLICIT_DEF + ADJCALLSTACKDOWN 16, 0, implicit-def $sp, implicit $sp + $a0 = COPY %0(s32) + JAL @f_i32, csr_o32, implicit-def $ra, implicit-def $sp, implicit $a0 + ADJCALLSTACKUP 16, 0, implicit-def $sp, implicit $sp + RetRA + +... +--- +name: g_i64 +alignment: 2 +legalized: true +tracksRegLiveness: true +body: | + bb.1.entry: + ; MIPS32-LABEL: name: g_i64 + ; MIPS32: [[DEF:%[0-9]+]]:gprb(s32) = G_IMPLICIT_DEF + ; MIPS32: [[DEF1:%[0-9]+]]:gprb(s32) = G_IMPLICIT_DEF + ; MIPS32: ADJCALLSTACKDOWN 16, 0, implicit-def $sp, implicit $sp + ; MIPS32: $a0 = COPY [[DEF]](s32) + ; MIPS32: $a1 = COPY [[DEF1]](s32) + ; MIPS32: JAL @f_i64, csr_o32, implicit-def $ra, implicit-def $sp, implicit $a0, implicit $a1 + ; MIPS32: ADJCALLSTACKUP 16, 0, implicit-def $sp, implicit $sp + ; MIPS32: RetRA + %0:_(s64) = G_IMPLICIT_DEF + ADJCALLSTACKDOWN 16, 0, implicit-def $sp, implicit $sp + %1:_(s32), %2:_(s32) = G_UNMERGE_VALUES %0(s64) + $a0 = COPY %1(s32) + $a1 = COPY %2(s32) + JAL @f_i64, csr_o32, implicit-def $ra, implicit-def $sp, implicit $a0, implicit $a1 + ADJCALLSTACKUP 16, 0, implicit-def $sp, implicit $sp + RetRA + +... +--- +name: g_float +alignment: 2 +legalized: true +tracksRegLiveness: true +body: | + bb.1.entry: + ; MIPS32-LABEL: name: g_float + ; MIPS32: [[DEF:%[0-9]+]]:fprb(s32) = G_IMPLICIT_DEF + ; MIPS32: ADJCALLSTACKDOWN 16, 0, implicit-def $sp, implicit $sp + ; MIPS32: $f12 = COPY [[DEF]](s32) + ; MIPS32: JAL @f_float, csr_o32, implicit-def $ra, implicit-def $sp, implicit $f12 + ; MIPS32: ADJCALLSTACKUP 16, 0, implicit-def $sp, implicit $sp + ; MIPS32: RetRA + %0:_(s32) = G_IMPLICIT_DEF + ADJCALLSTACKDOWN 16, 0, implicit-def $sp, implicit $sp + $f12 = COPY %0(s32) + JAL @f_float, csr_o32, implicit-def $ra, implicit-def $sp, implicit $f12 + ADJCALLSTACKUP 16, 0, implicit-def $sp, implicit $sp + RetRA + +... +--- +name: g_double +alignment: 2 +legalized: true +tracksRegLiveness: true +registers: +body: | + bb.1.entry: + ; MIPS32-LABEL: name: g_double + ; MIPS32: [[DEF:%[0-9]+]]:fprb(s64) = G_IMPLICIT_DEF + ; MIPS32: ADJCALLSTACKDOWN 16, 0, implicit-def $sp, implicit $sp + ; MIPS32: $d6 = COPY [[DEF]](s64) + ; MIPS32: JAL @f_double, csr_o32, implicit-def $ra, implicit-def $sp, implicit $d6 + ; MIPS32: ADJCALLSTACKUP 16, 0, implicit-def $sp, implicit $sp + ; MIPS32: RetRA + %0:_(s64) = G_IMPLICIT_DEF + ADJCALLSTACKDOWN 16, 0, implicit-def $sp, implicit $sp + $d6 = COPY %0(s64) + JAL @f_double, csr_o32, implicit-def $ra, implicit-def $sp, implicit $d6 + ADJCALLSTACKUP 16, 0, implicit-def $sp, implicit $sp + RetRA + +...