[llvm-commits] [llvm] r48412 - in /llvm/trunk: include/llvm/Target/TargetInstrInfo.h lib/CodeGen/LowerSubregs.cpp lib/CodeGen/SelectionDAG/ScheduleDAG.cpp lib/Target/Target.td lib/Target/TargetSelectionDAG.td lib/Target/X86/X86ISelDAGToDAG.cpp lib/Target/X86/X86Instr64bit.td lib/Target/X86/X86InstrInfo.cpp utils/TableGen/CodeEmitterGen.cpp utils/TableGen/CodeGenTarget.cpp utils/TableGen/InstrInfoEmitter.cpp

Christopher Lamb christopher.lamb at gmail.com
Mon Mar 17 22:19:27 PDT 2008


On Mar 16, 2008, at 11:44 PM, Evan Cheng wrote:

> Hi Chris,
>
> Thanks. This patch is a step in the right direction. However it will
> likely needs to be revised again soon.

I expected so.

> Sorry I wasn't being clearer earlier. The other Chris and I now feel
> that it isn't necessary to have a separate form of insert_subreg for
> inserting into an undef. The register allocator will treat
> IMPLICIT_DEF defined interval as a special zero length interval. This
> will allow these insert_subreg instructions to be coalesced away.

I assumed as much, and in this patch insert_subreg into undef doesn't  
use a separate instruction. The new instruction subreg_to_reg is used  
to model converting a subreg to a register with the rest of the  
register set to a value which an immediate operand. The coalescer  
will need to treat this instruction differently that than an  
insert_subreg, as it has side affects other than simply inserting a  
value (namely setting the rest of the register to an immediate value).

> Let's talk again when we are there in a day or so.

Sure thing.

--
Chris

> On Mar 15, 2008, at 8:12 PM, Christopher Lamb wrote:
>
>> Author: clamb
>> Date: Sat Mar 15 22:12:01 2008
>> New Revision: 48412
>>
>> URL: http://llvm.org/viewvc/llvm-project?rev=48412&view=rev
>> Log:
>> Make insert_subreg a two-address instruction, vastly simplifying
>> LowerSubregs pass. Add a new TII, subreg_to_reg, which is like
>> insert_subreg except that it takes an immediate implicit value to
>> insert into rather than a register.
>>
>>
>> Modified:
>>    llvm/trunk/include/llvm/Target/TargetInstrInfo.h
>>    llvm/trunk/lib/CodeGen/LowerSubregs.cpp
>>    llvm/trunk/lib/CodeGen/SelectionDAG/ScheduleDAG.cpp
>>    llvm/trunk/lib/Target/Target.td
>>    llvm/trunk/lib/Target/TargetSelectionDAG.td
>>    llvm/trunk/lib/Target/X86/X86ISelDAGToDAG.cpp
>>    llvm/trunk/lib/Target/X86/X86Instr64bit.td
>>    llvm/trunk/lib/Target/X86/X86InstrInfo.cpp
>>    llvm/trunk/utils/TableGen/CodeEmitterGen.cpp
>>    llvm/trunk/utils/TableGen/CodeGenTarget.cpp
>>    llvm/trunk/utils/TableGen/InstrInfoEmitter.cpp
>>
>> Modified: llvm/trunk/include/llvm/Target/TargetInstrInfo.h
>> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/ 
>> Target/TargetInstrInfo.h?rev=48412&r1=48411&r2=48412&view=diff
>>
>> =
>> =
>> =
>> =
>> =
>> =
>> =
>> =
>> ===================================================================== 
>> =
>> --- llvm/trunk/include/llvm/Target/TargetInstrInfo.h (original)
>> +++ llvm/trunk/include/llvm/Target/TargetInstrInfo.h Sat Mar 15
>> 22:12:01 2008
>> @@ -50,16 +50,8 @@
>>     DECLARE = 3,
>>     EXTRACT_SUBREG = 4,
>>     INSERT_SUBREG = 5,
>> -    IMPLICIT_DEF = 6
>> -  };
>> -
>> -  // Target independent implict values for use with subreg insert.
>> All targets
>> -  // that support insert_subreg support IMPL_VAL_UNDEF. Support for
>> the other
>> -  // values is target dependent.
>> -  enum ImplictVal {
>> -    IMPL_VAL_UNDEF = 0,
>> -    IMPL_VAL_ZERO  = 1,
>> -    LAST_IMPL_VAL  = 3
>> +    IMPLICIT_DEF = 6,
>> +    SUBREG_TO_REG = 7
>>   };
>>
>>   unsigned getNumOpcodes() const { return NumOpcodes; }
>>
>> Modified: llvm/trunk/lib/CodeGen/LowerSubregs.cpp
>> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/CodeGen/ 
>> LowerSubregs.cpp?rev=48412&r1=48411&r2=48412&view=diff
>>
>> =
>> =
>> =
>> =
>> =
>> =
>> =
>> =
>> ===================================================================== 
>> =
>> --- llvm/trunk/lib/CodeGen/LowerSubregs.cpp (original)
>> +++ llvm/trunk/lib/CodeGen/LowerSubregs.cpp Sat Mar 15 22:12:01 2008
>> @@ -35,6 +35,7 @@
>>
>>     bool LowerExtract(MachineInstr *MI);
>>     bool LowerInsert(MachineInstr *MI);
>> +    bool LowerSubregToReg(MachineInstr *MI);
>>   };
>>
>>   char LowerSubregsInstructionPass::ID = 0;
>> @@ -54,29 +55,28 @@
>>           MI->getOperand(1).isRegister() && MI-
>>> getOperand(1).isUse() &&
>>           MI->getOperand(2).isImmediate() && "Malformed
>> extract_subreg");
>>
>> +   unsigned DstReg   = MI->getOperand(0).getReg();
>>    unsigned SuperReg = MI->getOperand(1).getReg();
>> -   unsigned SubIdx = MI->getOperand(2).getImm();
>> +   unsigned SubIdx   = MI->getOperand(2).getImm();
>> +   unsigned SrcReg   = TRI.getSubReg(SuperReg, SubIdx);
>>
>>    assert(TargetRegisterInfo::isPhysicalRegister(SuperReg) &&
>>           "Extract supperg source must be a physical register");
>> -   unsigned SrcReg = TRI.getSubReg(SuperReg, SubIdx);
>> -   unsigned DstReg = MI->getOperand(0).getReg();
>> -
>> +   assert(TargetRegisterInfo::isPhysicalRegister(DstReg) &&
>> +          "Insert destination must be in a physical register");
>> +
>>    DOUT << "subreg: CONVERTING: " << *MI;
>>
>>    if (SrcReg != DstReg) {
>> -     const TargetRegisterClass *TRC = 0;
>> -     if (TargetRegisterInfo::isPhysicalRegister(DstReg)) {
>> -       TRC = TRI.getPhysicalRegisterRegClass(DstReg);
>> -     } else {
>> -       TRC = MF.getRegInfo().getRegClass(DstReg);
>> -     }
>> +     const TargetRegisterClass *TRC =
>> TRI.getPhysicalRegisterRegClass(DstReg);
>>      assert(TRC == TRI.getPhysicalRegisterRegClass(SrcReg) &&
>>              "Extract subreg and Dst must be of same register  
>> class");
>> -
>>      TII.copyRegToReg(*MBB, MI, DstReg, SrcReg, TRC, TRC);
>> +
>> +#ifndef NDEBUG
>>      MachineBasicBlock::iterator dMI = MI;
>>      DOUT << "subreg: " << *(--dMI);
>> +#endif
>>    }
>>
>>    DOUT << "\n";
>> @@ -84,115 +84,80 @@
>>    return true;
>> }
>>
>> -
>> -bool LowerSubregsInstructionPass::LowerInsert(MachineInstr *MI) {
>> +bool LowerSubregsInstructionPass::LowerSubregToReg(MachineInstr
>> *MI) {
>>   MachineBasicBlock *MBB = MI->getParent();
>>   MachineFunction &MF = *MBB->getParent();
>>   const TargetRegisterInfo &TRI = *MF.getTarget().getRegisterInfo();
>>   const TargetInstrInfo &TII = *MF.getTarget().getInstrInfo();
>>   assert((MI->getOperand(0).isRegister() && MI-
>>> getOperand(0).isDef()) &&
>> -         ((MI->getOperand(1).isRegister() && MI-
>>> getOperand(1).isUse()) ||
>> -            MI->getOperand(1).isImmediate()) &&
>> +         MI->getOperand(1).isImmediate() &&
>>          (MI->getOperand(2).isRegister() && MI-
>>> getOperand(2).isUse()) &&
>> -          MI->getOperand(3).isImmediate() && "Invalid
>> insert_subreg");
>> +          MI->getOperand(3).isImmediate() && "Invalid
>> subreg_to_reg");
>>
>> -  // Check if we're inserting into an implicit undef value.
>> -  bool isImplicit = MI->getOperand(1).isImmediate();
>> -  unsigned DstReg = MI->getOperand(0).getReg();
>> -  unsigned SrcReg = isImplicit ? DstReg : MI->getOperand(1).getReg 
>> ();
>> -  unsigned InsReg = MI->getOperand(2).getReg();
>> -  unsigned SubIdx = MI->getOperand(3).getImm();
>> +  unsigned DstReg  = MI->getOperand(0).getReg();
>> +  unsigned InsReg  = MI->getOperand(2).getReg();
>> +  unsigned SubIdx  = MI->getOperand(3).getImm();
>>
>> -  assert(SubIdx != 0 && "Invalid index for extract_subreg");
>> +  assert(SubIdx != 0 && "Invalid index for insert_subreg");
>>   unsigned DstSubReg = TRI.getSubReg(DstReg, SubIdx);
>> -
>> -  assert(TargetRegisterInfo::isPhysicalRegister(SrcReg) &&
>> -         "Insert superreg source must be in a physical register");
>> +
>>   assert(TargetRegisterInfo::isPhysicalRegister(DstReg) &&
>>          "Insert destination must be in a physical register");
>>   assert(TargetRegisterInfo::isPhysicalRegister(InsReg) &&
>>          "Inserted value must be in a physical register");
>>
>>   DOUT << "subreg: CONVERTING: " << *MI;
>> -
>> -  // Check whether the implict subreg copy has side affects or not.
>> Only copies
>> -  // into an undef value have no side affects, that is they can be
>> eliminated
>> -  // without changing the semantics of the program.
>> -  bool copyHasSideAffects = isImplicit?
>> -                  MI->getOperand(1).getImm() !=
>> TargetInstrInfo::IMPL_VAL_UNDEF
>> -                  : false;
>> -
>> -  // If the inserted register is already allocated into a  
>> subregister
>> -  // of the destination, we copy the subreg into the source
>> -  // However, this is only safe if the insert instruction is the  
>> kill
>> -  // of the source register
>> -  bool revCopyOrder = TRI.isSubRegister(DstReg, InsReg);
>> -  if (revCopyOrder && (InsReg != DstSubReg || copyHasSideAffects)) {
>> -    if (isImplicit || MI->getOperand(1).isKill()) {
>> -      DstSubReg = TRI.getSubReg(SrcReg, SubIdx);
>> -      // Insert sub-register copy
>> -      const TargetRegisterClass *TRC1 = 0;
>> -      if (TargetRegisterInfo::isPhysicalRegister(InsReg)) {
>> -        TRC1 = TRI.getPhysicalRegisterRegClass(InsReg);
>> -      } else {
>> -        TRC1 = MF.getRegInfo().getRegClass(InsReg);
>> -      }
>> -      TII.copyRegToReg(*MBB, MI, DstSubReg, InsReg, TRC1, TRC1);
>> +
>> +  // Insert sub-register copy
>> +  const TargetRegisterClass *TRC0 =
>> TRI.getPhysicalRegisterRegClass(DstSubReg);
>> +  const TargetRegisterClass *TRC1 =
>> TRI.getPhysicalRegisterRegClass(InsReg);
>> +  TII.copyRegToReg(*MBB, MI, DstSubReg, InsReg, TRC0, TRC1);
>>
>> #ifndef NDEBUG
>> -      MachineBasicBlock::iterator dMI = MI;
>> -      DOUT << "subreg: " << *(--dMI);
>> -#endif
>> -    } else {
>> -      assert(0 && "Don't know how to convert this insert");
>> -    }
>> -  }
>> -#ifndef NDEBUG
>> -  if (InsReg == DstSubReg && !copyHasSideAffects) {
>> -     DOUT << "subreg: Eliminated subreg copy\n";
>> -  }
>> +  MachineBasicBlock::iterator dMI = MI;
>> +  DOUT << "subreg: " << *(--dMI);
>> #endif
>>
>> -  if (SrcReg != DstReg) {
>> -    // Insert super-register copy
>> -    const TargetRegisterClass *TRC0 = 0;
>> -    if (TargetRegisterInfo::isPhysicalRegister(DstReg)) {
>> -      TRC0 = TRI.getPhysicalRegisterRegClass(DstReg);
>> -    } else {
>> -      TRC0 = MF.getRegInfo().getRegClass(DstReg);
>> -    }
>> -    assert(TRC0 == TRI.getPhysicalRegisterRegClass(SrcReg) &&
>> -            "Insert superreg and Dst must be of same register
>> class");
>> +  DOUT << "\n";
>> +  MBB->remove(MI);
>> +  return true;
>> +}
>>
>> -    TII.copyRegToReg(*MBB, MI, DstReg, SrcReg, TRC0, TRC0);
>> +bool LowerSubregsInstructionPass::LowerInsert(MachineInstr *MI) {
>> +  MachineBasicBlock *MBB = MI->getParent();
>> +  MachineFunction &MF = *MBB->getParent();
>> +  const TargetRegisterInfo &TRI = *MF.getTarget().getRegisterInfo();
>> +  const TargetInstrInfo &TII = *MF.getTarget().getInstrInfo();
>> +  assert((MI->getOperand(0).isRegister() && MI-
>>> getOperand(0).isDef()) &&
>> +         (MI->getOperand(1).isRegister() && MI-
>>> getOperand(1).isUse()) &&
>> +         (MI->getOperand(2).isRegister() && MI-
>>> getOperand(2).isUse()) &&
>> +          MI->getOperand(3).isImmediate() && "Invalid
>> insert_subreg");
>> +
>> +  unsigned DstReg = MI->getOperand(0).getReg();
>> +  unsigned SrcReg = MI->getOperand(1).getReg();
>> +  unsigned InsReg = MI->getOperand(2).getReg();
>> +  unsigned SubIdx = MI->getOperand(3).getImm();
>>
>> -#ifndef NDEBUG
>> -    MachineBasicBlock::iterator dMI = MI;
>> -    DOUT << "subreg: " << *(--dMI);
>> -#endif
>> -  }
>> +  assert(DstReg == SrcReg && "insert_subreg not a two-address
>> instruction?");
>> +  assert(SubIdx != 0 && "Invalid index for insert_subreg");
>> +  unsigned DstSubReg = TRI.getSubReg(DstReg, SubIdx);
>>
>> -#ifndef NDEBUG
>> -  if (SrcReg == DstReg) {
>> -     DOUT << "subreg: Eliminated superreg copy\n";
>> -  }
>> -#endif
>> +  assert(TargetRegisterInfo::isPhysicalRegister(SrcReg) &&
>> +         "Insert superreg source must be in a physical register");
>> +  assert(TargetRegisterInfo::isPhysicalRegister(InsReg) &&
>> +         "Inserted value must be in a physical register");
>>
>> -  if (!revCopyOrder && (InsReg != DstSubReg ||  
>> copyHasSideAffects)) {
>> -    // Insert sub-register copy
>> -    const TargetRegisterClass *TRC1 = 0;
>> -    if (TargetRegisterInfo::isPhysicalRegister(InsReg)) {
>> -      TRC1 = TRI.getPhysicalRegisterRegClass(InsReg);
>> -    } else {
>> -      TRC1 = MF.getRegInfo().getRegClass(InsReg);
>> -    }
>> -    TII.copyRegToReg(*MBB, MI, DstSubReg, InsReg, TRC1, TRC1);
>> +  DOUT << "subreg: CONVERTING: " << *MI;
>> +
>> +  // Insert sub-register copy
>> +  const TargetRegisterClass *TRC0 =
>> TRI.getPhysicalRegisterRegClass(DstSubReg);
>> +  const TargetRegisterClass *TRC1 =
>> TRI.getPhysicalRegisterRegClass(InsReg);
>> +  TII.copyRegToReg(*MBB, MI, DstSubReg, InsReg, TRC0, TRC1);
>>
>> #ifndef NDEBUG
>> -    MachineBasicBlock::iterator dMI = MI;
>> -    DOUT << "subreg: " << *(--dMI);
>> +  MachineBasicBlock::iterator dMI = MI;
>> +  DOUT << "subreg: " << *(--dMI);
>> #endif
>> -  }
>>
>>   DOUT << "\n";
>>   MBB->remove(MI);
>> @@ -220,6 +185,8 @@
>>         MadeChange |= LowerExtract(MI);
>>       } else if (MI->getOpcode() == TargetInstrInfo::INSERT_SUBREG) {
>>         MadeChange |= LowerInsert(MI);
>> +      } else if (MI->getOpcode() ==  
>> TargetInstrInfo::SUBREG_TO_REG) {
>> +        MadeChange |= LowerSubregToReg(MI);
>>       }
>>     }
>>   }
>>
>> Modified: llvm/trunk/lib/CodeGen/SelectionDAG/ScheduleDAG.cpp
>> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/CodeGen/ 
>> SelectionDAG/ScheduleDAG.cpp?rev=48412&r1=48411&r2=48412&view=diff
>>
>> =
>> =
>> =
>> =
>> =
>> =
>> =
>> =
>> ===================================================================== 
>> =
>> --- llvm/trunk/lib/CodeGen/SelectionDAG/ScheduleDAG.cpp (original)
>> +++ llvm/trunk/lib/CodeGen/SelectionDAG/ScheduleDAG.cpp Sat Mar 15
>> 22:12:01 2008
>> @@ -661,26 +661,24 @@
>>                            DenseMap<SDOperand, unsigned>  
>> &VRBaseMap) {
>>   unsigned VRBase = 0;
>>   unsigned Opc = Node->getTargetOpcode();
>> -  if (Opc == TargetInstrInfo::EXTRACT_SUBREG) {
>> -    // If the node is only used by a CopyToReg and the dest reg is
>> a vreg, use
>> -    // the CopyToReg'd destination register instead of creating a
>> new vreg.
>> -    for (SDNode::use_iterator UI = Node->use_begin(), E = Node-
>>> use_end();
>> -         UI != E; ++UI) {
>> -      SDNode *Use = *UI;
>> -      if (Use->getOpcode() == ISD::CopyToReg &&
>> -          Use->getOperand(2).Val == Node) {
>> -        unsigned DestReg = cast<RegisterSDNode>(Use->getOperand(1))-
>>> getReg();
>> -        if (TargetRegisterInfo::isVirtualRegister(DestReg)) {
>> -          VRBase = DestReg;
>> -          break;
>> -        }
>> +
>> +  // If the node is only used by a CopyToReg and the dest reg is a
>> vreg, use
>> +  // the CopyToReg'd destination register instead of creating a new
>> vreg.
>> +  for (SDNode::use_iterator UI = Node->use_begin(), E = Node-
>>> use_end();
>> +       UI != E; ++UI) {
>> +    SDNode *Use = *UI;
>> +    if (Use->getOpcode() == ISD::CopyToReg &&
>> +        Use->getOperand(2).Val == Node) {
>> +      unsigned DestReg = cast<RegisterSDNode>(Use->getOperand(1))-
>>> getReg();
>> +      if (TargetRegisterInfo::isVirtualRegister(DestReg)) {
>> +        VRBase = DestReg;
>> +        break;
>>       }
>>     }
>> -
>> +  }
>> +
>> +  if (Opc == TargetInstrInfo::EXTRACT_SUBREG) {
>>     unsigned SubIdx = cast<ConstantSDNode>(Node->getOperand(1))-
>>> getValue();
>> -
>> -    // TODO: If the node is a use of a CopyFromReg from a physical
>> register
>> -    // fold the extract into the copy now
>>
>>     // Create the extract_subreg machine instruction.
>>     MachineInstr *MI =
>> @@ -707,36 +705,14 @@
>>     AddOperand(MI, Node->getOperand(0), 0, 0, VRBaseMap);
>>     MI->addOperand(MachineOperand::CreateImm(SubIdx));
>>
>> -  } else if (Opc == TargetInstrInfo::INSERT_SUBREG) {
>> +  } else if (Opc == TargetInstrInfo::INSERT_SUBREG ||
>> +             Opc == TargetInstrInfo::SUBREG_TO_REG) {
>>     SDOperand N0 = Node->getOperand(0);
>>     SDOperand N1 = Node->getOperand(1);
>>     SDOperand N2 = Node->getOperand(2);
>>     unsigned SubReg = getVR(N1, VRBaseMap);
>>     unsigned SubIdx = cast<ConstantSDNode>(N2)->getValue();
>>
>> -    // TODO: Add tracking info to MachineRegisterInfo of which
>> vregs are subregs
>> -    // to allow coalescing in the allocator
>> -
>> -    // If the node is only used by a CopyToReg and the dest reg is
>> a vreg, use
>> -    // the CopyToReg'd destination register instead of creating a
>> new vreg.
>> -    // If the CopyToReg'd destination register is physical, then
>> fold the
>> -    // insert into the copy
>> -    for (SDNode::use_iterator UI = Node->use_begin(), E = Node-
>>> use_end();
>> -         UI != E; ++UI) {
>> -      SDNode *Use = *UI;
>> -      if (Use->getOpcode() == ISD::CopyToReg &&
>> -          Use->getOperand(2).Val == Node) {
>> -        unsigned DestReg = cast<RegisterSDNode>(Use->getOperand(1))-
>>> getReg();
>> -        if (TargetRegisterInfo::isVirtualRegister(DestReg)) {
>> -          VRBase = DestReg;
>> -          break;
>> -        }
>> -      }
>> -    }
>> -
>> -    // Create the insert_subreg machine instruction.
>> -    MachineInstr *MI =
>> -      new MachineInstr(BB, TII->get 
>> (TargetInstrInfo::INSERT_SUBREG));
>>
>>     // Figure out the register class to create for the destreg.
>>     const TargetRegisterClass *TRC = 0;
>> @@ -749,19 +725,23 @@
>>       VRBase = MRI.createVirtualRegister(TRC); // Create the reg
>>     }
>>
>> +    // Create the insert_subreg or subreg_to_reg machine  
>> instruction.
>> +    MachineInstr *MI =
>> +      new MachineInstr(BB, TII->get(Opc));
>>     MI->addOperand(MachineOperand::CreateReg(VRBase, true));
>>
>> -    // If N0 is a constant then it indicates the insert is being  
>> done
>> -    // into a target specific constant value, not a register.
>> -    if (const ConstantSDNode *SD = dyn_cast<ConstantSDNode>(N0))
>> +    // If creating a subreg_to_reg, then the first input operand
>> +    // is an implicit value immediate, otherwise it's a register
>> +    if (Opc == TargetInstrInfo::SUBREG_TO_REG) {
>> +      const ConstantSDNode *SD = cast<ConstantSDNode>(N0);
>>       MI->addOperand(MachineOperand::CreateImm(SD->getValue()));
>> -    else
>> +    } else
>>       AddOperand(MI, N0, 0, 0, VRBaseMap);
>>     // Add the subregster being inserted
>>     AddOperand(MI, N1, 0, 0, VRBaseMap);
>>     MI->addOperand(MachineOperand::CreateImm(SubIdx));
>>   } else
>> -    assert(0 && "Node is not a subreg insert or extract");
>> +    assert(0 && "Node is not insert_subreg, extract_subreg, or
>> subreg_to_reg");
>>
>>   bool isNew = VRBaseMap.insert(std::make_pair(SDOperand(Node,0),
>> VRBase));
>>   assert(isNew && "Node emitted out of order - early");
>> @@ -777,7 +757,8 @@
>>
>>     // Handle subreg insert/extract specially
>>     if (Opc == TargetInstrInfo::EXTRACT_SUBREG ||
>> -        Opc == TargetInstrInfo::INSERT_SUBREG) {
>> +        Opc == TargetInstrInfo::INSERT_SUBREG ||
>> +        Opc == TargetInstrInfo::SUBREG_TO_REG) {
>>       EmitSubregNode(Node, VRBaseMap);
>>       return;
>>     }
>>
>> Modified: llvm/trunk/lib/Target/Target.td
>> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/ 
>> Target.td?rev=48412&r1=48411&r2=48412&view=diff
>>
>> =
>> =
>> =
>> =
>> =
>> =
>> =
>> =
>> ===================================================================== 
>> =
>> --- llvm/trunk/lib/Target/Target.td (original)
>> +++ llvm/trunk/lib/Target/Target.td Sat Mar 15 22:12:01 2008
>> @@ -366,6 +366,7 @@
>>   let AsmString = "";
>>   let Namespace = "TargetInstrInfo";
>>   let neverHasSideEffects = 1;
>> +  let Constraints = "$supersrc = $dst";
>> }
>> def IMPLICIT_DEF : Instruction {
>>   let OutOperandList = (ops unknown:$dst);
>> @@ -374,6 +375,13 @@
>>   let Namespace = "TargetInstrInfo";
>>   let neverHasSideEffects = 1;
>> }
>> +def SUBREG_TO_REG : Instruction {
>> +  let OutOperandList = (ops unknown:$dst);
>> +  let InOperandList = (ops unknown:$implsrc, unknown:$subsrc,
>> i32imm:$subidx);
>> +  let AsmString = "";
>> +  let Namespace = "TargetInstrInfo";
>> +  let neverHasSideEffects = 1;
>> +}
>>
>> //
>> =
>> =
>> =
>> --------------------------------------------------------------------- 
>> -=
>> ==//
>> // AsmWriter - This class can be implemented by targets that need to
>> customize
>>
>> Modified: llvm/trunk/lib/Target/TargetSelectionDAG.td
>> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/ 
>> TargetSelectionDAG.td?rev=48412&r1=48411&r2=48412&view=diff
>>
>> =
>> =
>> =
>> =
>> =
>> =
>> =
>> =
>> ===================================================================== 
>> =
>> --- llvm/trunk/lib/Target/TargetSelectionDAG.td (original)
>> +++ llvm/trunk/lib/Target/TargetSelectionDAG.td Sat Mar 15 22:12:01
>> 2008
>> @@ -918,11 +918,3 @@
>> def SDT_dwarf_loc : SDTypeProfile<0, 3,
>>                       [SDTCisInt<0>, SDTCisInt<1>, SDTCisInt<2>]>;
>> def dwarf_loc : SDNode<"ISD::DEBUG_LOC", SDT_dwarf_loc,
>> [SDNPHasChain]>;
>> -
>> -//
>> =
>> =
>> =
>> --------------------------------------------------------------------- 
>> -=
>> ==//
>> -// Implict value insert subreg support.
>> -//
>> -// These should match the enum TargetInstrInfo::ImplictVal.
>> -def tii_impl_val_undef : PatLeaf<(i32 0)>;
>> -def tii_impl_val_zero  : PatLeaf<(i32 1)>;
>> -
>>
>> Modified: llvm/trunk/lib/Target/X86/X86ISelDAGToDAG.cpp
>> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/X86/ 
>> X86ISelDAGToDAG.cpp?rev=48412&r1=48411&r2=48412&view=diff
>>
>> =
>> =
>> =
>> =
>> =
>> =
>> =
>> =
>> ===================================================================== 
>> =
>> --- llvm/trunk/lib/Target/X86/X86ISelDAGToDAG.cpp (original)
>> +++ llvm/trunk/lib/Target/X86/X86ISelDAGToDAG.cpp Sat Mar 15
>> 22:12:01 2008
>> @@ -1529,39 +1529,36 @@
>>     }
>>
>>     case ISD::ANY_EXTEND: {
>> +      // Check if the type  extended to supports subregs.
>> +      if (NVT == MVT::i8)
>> +        break;
>> +
>>       SDOperand N0 = Node->getOperand(0);
>> +      // Get the subregsiter index for the type to extend.
>> +      MVT::ValueType N0VT = N0.getValueType();
>> +      unsigned Idx = (N0VT == MVT::i32) ? X86::SUBREG_32BIT :
>> +                      (N0VT == MVT::i16) ? X86::SUBREG_16BIT :
>> +                        (Subtarget->is64Bit()) ? X86::SUBREG_8BIT :
>> 0;
>> +
>> +      // If we don't have a subreg Idx, let generated ISel have a
>> try.
>> +      if (Idx == 0)
>> +        break;
>> +
>> +      // If we have an index, generate an insert_subreg into undef.
>>       AddToISelQueue(N0);
>> -      if (NVT == MVT::i64 || NVT == MVT::i32 || NVT == MVT::i16) {
>> -        SDOperand SRIdx;
>> -        switch(N0.getValueType()) {
>> -        case MVT::i32:
>> -          SRIdx = CurDAG->getTargetConstant(X86::SUBREG_32BIT,
>> MVT::i32);
>> -          break;
>> -        case MVT::i16:
>> -          SRIdx = CurDAG->getTargetConstant(X86::SUBREG_16BIT,
>> MVT::i32);
>> -          break;
>> -        case MVT::i8:
>> -          if (Subtarget->is64Bit())
>> -            SRIdx = CurDAG->getTargetConstant(X86::SUBREG_8BIT,
>> MVT::i32);
>> -          break;
>> -        default: assert(0 && "Unknown any_extend!");
>> -        }
>> -        if (SRIdx.Val) {
>> -          SDOperand ImplVal =
>> -              CurDAG-
>>> getTargetConstant(X86InstrInfo::IMPL_VAL_UNDEF, MVT::i32);
>> -          SDNode *ResNode = CurDAG->getTargetNode 
>> (X86::INSERT_SUBREG,
>> -                                                  NVT, ImplVal, N0,
>> SRIdx);
>> +      SDOperand Undef =
>> +                  SDOperand(CurDAG-
>>> getTargetNode(X86::IMPLICIT_DEF, NVT), 0);
>> +      SDOperand SRIdx = CurDAG->getTargetConstant(Idx, MVT::i32);
>> +      SDNode *ResNode = CurDAG->getTargetNode(X86::INSERT_SUBREG,
>> +                                                NVT, Undef, N0,
>> SRIdx);
>>
>> #ifndef NDEBUG
>> -          DOUT << std::string(Indent-2, ' ') << "=> ";
>> -          DEBUG(ResNode->dump(CurDAG));
>> -          DOUT << "\n";
>> -          Indent -= 2;
>> +      DOUT << std::string(Indent-2, ' ') << "=> ";
>> +      DEBUG(ResNode->dump(CurDAG));
>> +      DOUT << "\n";
>> +      Indent -= 2;
>> #endif
>> -          return ResNode;
>> -        } // Otherwise let generated ISel handle it.
>> -      }
>> -      break;
>> +      return ResNode;
>>     }
>>
>>     case ISD::SIGN_EXTEND_INREG: {
>>
>> Modified: llvm/trunk/lib/Target/X86/X86Instr64bit.td
>> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/X86/ 
>> X86Instr64bit.td?rev=48412&r1=48411&r2=48412&view=diff
>>
>> =
>> =
>> =
>> =
>> =
>> =
>> =
>> =
>> ===================================================================== 
>> =
>> --- llvm/trunk/lib/Target/X86/X86Instr64bit.td (original)
>> +++ llvm/trunk/lib/Target/X86/X86Instr64bit.td Sat Mar 15 22:12:01
>> 2008
>> @@ -1202,43 +1202,43 @@
>>
>>
>> // Zero-extension
>> -def : Pat<(i64 (zext GR32:$src)), (INSERT_SUBREG tii_impl_val_zero,
>> -                                            GR32:$src,
>> x86_subreg_32bit)>;
>> +def : Pat<(i64 (zext GR32:$src)),
>> +          (SUBREG_TO_REG (i64 0), GR32:$src, x86_subreg_32bit)>;
>>
>> // zextload bool -> zextload byte
>> def : Pat<(zextloadi64i1 addr:$src), (MOVZX64rm8 addr:$src)>;
>>
>> -def : Pat<(zextloadi64i32 addr:$src), (INSERT_SUBREG
>> tii_impl_val_zero,
>> -                                        (MOV32rm addr:$src),
>> x86_subreg_32bit)>;
>> +def : Pat<(zextloadi64i32 addr:$src),
>> +          (SUBREG_TO_REG (i64 0), (MOV32rm addr:$src),
>> x86_subreg_32bit)>;
>>
>> // extload
>> def : Pat<(extloadi64i1 addr:$src),  (MOVZX64rm8  addr:$src)>;
>> def : Pat<(extloadi64i8 addr:$src),  (MOVZX64rm8  addr:$src)>;
>> def : Pat<(extloadi64i16 addr:$src), (MOVZX64rm16 addr:$src)>;
>> -def : Pat<(extloadi64i32 addr:$src), (INSERT_SUBREG
>> tii_impl_val_undef,
>> -                                        (MOV32rm addr:$src),
>> x86_subreg_32bit)>;
>> +def : Pat<(extloadi64i32 addr:$src),
>> +          (INSERT_SUBREG (i64 (IMPLICIT_DEF)), (MOV32rm addr:$src),
>> +                                                   
>> x86_subreg_32bit)>;
>>
>> // anyext -> zext
>> def : Pat<(i64 (anyext GR8 :$src)), (MOVZX64rr8  GR8 :$src)>;
>> def : Pat<(i64 (anyext GR16:$src)), (MOVZX64rr16 GR16:$src)>;
>> -def : Pat<(i64 (anyext GR32:$src)), (INSERT_SUBREG
>> tii_impl_val_undef,
>> -                                        GR32:$src,
>> x86_subreg_32bit)>;
>> +def : Pat<(i64 (anyext GR32:$src)),
>> +          (INSERT_SUBREG (i64 (IMPLICIT_DEF)), GR32:$src,
>> x86_subreg_32bit)>;
>>
>> def : Pat<(i64 (anyext (loadi8  addr:$src))), (MOVZX64rm8  addr:
>> $src)>;
>> def : Pat<(i64 (anyext (loadi16 addr:$src))), (MOVZX64rm16 addr:
>> $src)>;
>> -def : Pat<(i64 (anyext (loadi32 addr:$src))), (INSERT_SUBREG
>> tii_impl_val_undef,
>> -                                                (MOV32rm addr:$src),
>> -                                                   
>> x86_subreg_32bit)>;
>> +def : Pat<(i64 (anyext (loadi32 addr:$src))),
>> +          (INSERT_SUBREG (i64 (IMPLICIT_DEF)), (MOV32rm addr:$src),
>> +
>> x86_subreg_32bit)>;
>>
>> //
>> =
>> =
>> =
>> --------------------------------------------------------------------- 
>> -=
>> ==//
>> // Some peepholes
>> //
>> =
>> =
>> =
>> --------------------------------------------------------------------- 
>> -=
>> ==//
>>
>> -
>> // r & (2^32-1) ==> mov32 + implicit zext
>> def : Pat<(and GR64:$src, i64immFFFFFFFF),
>> -          (INSERT_SUBREG tii_impl_val_zero,
>> -            (MOV32rr (EXTRACT_SUBREG GR64:$src, x86_subreg_32bit)),
>> +          (SUBREG_TO_REG (i64 0),
>> +            (i32 (EXTRACT_SUBREG GR64:$src, x86_subreg_32bit)),
>>             x86_subreg_32bit)>;
>>
>> // (shl x, 1) ==> (add x, x)
>>
>> Modified: llvm/trunk/lib/Target/X86/X86InstrInfo.cpp
>> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/X86/ 
>> X86InstrInfo.cpp?rev=48412&r1=48411&r2=48412&view=diff
>>
>> =
>> =
>> =
>> =
>> =
>> =
>> =
>> =
>> ===================================================================== 
>> =
>> --- llvm/trunk/lib/Target/X86/X86InstrInfo.cpp (original)
>> +++ llvm/trunk/lib/Target/X86/X86InstrInfo.cpp Sat Mar 15 22:12:01
>> 2008
>> @@ -920,10 +920,11 @@
>>
>>       // Build and insert into an implicit UNDEF value. This is OK
>> because
>>       // well be shifting and then extracting the lower 16-bits.
>> +      MachineInstr *Undef = BuildMI(get(X86::IMPLICIT_DEF),
>> leaInReg);
>> +
>>       MachineInstr *Ins =
>>        BuildMI(get(X86::INSERT_SUBREG),leaInReg)
>> -                    .addImm(X86InstrInfo::IMPL_VAL_UNDEF)
>> -                    .addReg(Src).addImm(X86::SUBREG_16BIT);
>> +
>>                     .addReg
>> (leaInReg).addReg(Src).addImm(X86::SUBREG_16BIT);
>>
>>       NewMI = BuildMI(get(Opc), leaOutReg)
>>         .addReg(0).addImm(1 << ShAmt).addReg(leaInReg).addImm(0);
>> @@ -933,6 +934,7 @@
>>          .addReg(leaOutReg).addImm(X86::SUBREG_16BIT);
>>       Ext->copyKillDeadInfo(MI);
>>
>> +      MFI->insert(MBBI, Undef);
>>       MFI->insert(MBBI, Ins);            // Insert the insert_subreg
>>       LV.instructionChanged(MI, NewMI);  // Update live variables
>>       LV.addVirtualRegisterKilled(leaInReg, NewMI);
>>
>> Modified: llvm/trunk/utils/TableGen/CodeEmitterGen.cpp
>> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/utils/TableGen/ 
>> CodeEmitterGen.cpp?rev=48412&r1=48411&r2=48412&view=diff
>>
>> =
>> =
>> =
>> =
>> =
>> =
>> =
>> =
>> ===================================================================== 
>> =
>> --- llvm/trunk/utils/TableGen/CodeEmitterGen.cpp (original)
>> +++ llvm/trunk/utils/TableGen/CodeEmitterGen.cpp Sat Mar 15 22:12:01
>> 2008
>> @@ -30,7 +30,8 @@
>>         R->getName() == "DECLARE" ||
>>         R->getName() == "EXTRACT_SUBREG" ||
>>         R->getName() == "INSERT_SUBREG" ||
>> -        R->getName() == "IMPLICIT_DEF") continue;
>> +        R->getName() == "IMPLICIT_DEF" ||
>> +        R->getName() == "SUBREG_TO_REG") continue;
>>
>>     BitsInit *BI = R->getValueAsBitsInit("Inst");
>>
>> @@ -105,7 +106,8 @@
>>         R->getName() == "DECLARE" ||
>>         R->getName() == "EXTRACT_SUBREG" ||
>>         R->getName() == "INSERT_SUBREG" ||
>> -        R->getName() == "IMPLICIT_DEF") {
>> +        R->getName() == "IMPLICIT_DEF" ||
>> +        R->getName() == "SUBREG_TO_REG") {
>>       o << "    0U";
>>       continue;
>>     }
>> @@ -139,7 +141,8 @@
>>         InstName == "DECLARE"||
>>         InstName == "EXTRACT_SUBREG" ||
>>         InstName == "INSERT_SUBREG" ||
>> -        InstName == "IMPLICIT_DEF") continue;
>> +        InstName == "IMPLICIT_DEF" ||
>> +        InstName == "SUBREG_TO_REG") continue;
>>
>>     BitsInit *BI = R->getValueAsBitsInit("Inst");
>>     const std::vector<RecordVal> &Vals = R->getValues();
>>
>> Modified: llvm/trunk/utils/TableGen/CodeGenTarget.cpp
>> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/utils/TableGen/ 
>> CodeGenTarget.cpp?rev=48412&r1=48411&r2=48412&view=diff
>>
>> =
>> =
>> =
>> =
>> =
>> =
>> =
>> =
>> ===================================================================== 
>> =
>> --- llvm/trunk/utils/TableGen/CodeGenTarget.cpp (original)
>> +++ llvm/trunk/utils/TableGen/CodeGenTarget.cpp Sat Mar 15 22:12:01
>> 2008
>> @@ -309,6 +309,11 @@
>>     throw "Could not find 'IMPLICIT_DEF' instruction!";
>>   const CodeGenInstruction *IMPLICIT_DEF = &I->second;
>>
>> +  I = getInstructions().find("SUBREG_TO_REG");
>> +  if (I == Instructions.end())
>> +    throw "Could not find 'SUBREG_TO_REG' instruction!";
>> +  const CodeGenInstruction *SUBREG_TO_REG = &I->second;
>> +
>>   // Print out the rest of the instructions now.
>>   NumberedInstructions.push_back(PHI);
>>   NumberedInstructions.push_back(INLINEASM);
>> @@ -317,6 +322,7 @@
>>   NumberedInstructions.push_back(EXTRACT_SUBREG);
>>   NumberedInstructions.push_back(INSERT_SUBREG);
>>   NumberedInstructions.push_back(IMPLICIT_DEF);
>> +  NumberedInstructions.push_back(SUBREG_TO_REG);
>>   for (inst_iterator II = inst_begin(), E = inst_end(); II != E; + 
>> +II)
>>     if (&II->second != PHI &&
>>         &II->second != INLINEASM &&
>> @@ -324,7 +330,8 @@
>>         &II->second != DECLARE &&
>>         &II->second != EXTRACT_SUBREG &&
>>         &II->second != INSERT_SUBREG &&
>> -        &II->second != IMPLICIT_DEF)
>> +        &II->second != IMPLICIT_DEF &&
>> +        &II->second != SUBREG_TO_REG)
>>       NumberedInstructions.push_back(&II->second);
>> }
>>
>>
>> Modified: llvm/trunk/utils/TableGen/InstrInfoEmitter.cpp
>> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/utils/TableGen/ 
>> InstrInfoEmitter.cpp?rev=48412&r1=48411&r2=48412&view=diff
>>
>> =
>> =
>> =
>> =
>> =
>> =
>> =
>> =
>> ===================================================================== 
>> =
>> --- llvm/trunk/utils/TableGen/InstrInfoEmitter.cpp (original)
>> +++ llvm/trunk/utils/TableGen/InstrInfoEmitter.cpp Sat Mar 15
>> 22:12:01 2008
>> @@ -411,7 +411,8 @@
>>         R->getName() != "DECLARE" &&
>>         R->getName() != "EXTRACT_SUBREG" &&
>>         R->getName() != "INSERT_SUBREG" &&
>> -        R->getName() != "IMPLICIT_DEF")
>> +        R->getName() != "IMPLICIT_DEF" &&
>> +        R->getName() != "SUBREG_TO_REG")
>>       throw R->getName() + " doesn't have a field named '" +
>>             Val->getValue() + "'!";
>>     return;
>>
>>
>> _______________________________________________
>> llvm-commits mailing list
>> llvm-commits at cs.uiuc.edu
>> http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits
>
> _______________________________________________
> llvm-commits mailing list
> llvm-commits at cs.uiuc.edu
> http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits

--
Christopher Lamb



-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20080317/8db07795/attachment.html>


More information about the llvm-commits mailing list