PATCH: R600/SI: Do abs/neg folding with ComplexPatterns
Matt Arsenault
Matthew.Arsenault at amd.com
Wed Jul 30 12:36:45 PDT 2014
On 07/29/2014 08:40 PM, Tom Stellard wrote:
>
> In my updated patch I've removed a few layers of inheritance. The VOP*Inst
> classes still exist, but if you need to make define a custom instruction, you
> can use the VOP*_Helper classes which let you specify the ins, outs, asm,
> and patterns directly.
>
> I've also added a VOPProfile class that can be used for specifying the
> operands for an instruction.
>
LGTM except for 3 typos I found. The new patterns are still impressively
complicated, but I don't have any better ideas
> diff --git a/lib/Target/R600/SIInstrInfo.cpp b/lib/Target/R600/SIInstrInfo.cpp
> index 06529a2..b9ebc0f 100644
> --- a/lib/Target/R600/SIInstrInfo.cpp
> +++ b/lib/Target/R600/SIInstrInfo.cpp
> @@ -388,14 +388,14 @@ bool SIInstrInfo::expandPostRAPseudo(MachineBasicBlock::iterator MI) const {
> MachineInstr *SIInstrInfo::commuteInstruction(MachineInstr *MI,
> bool NewMI) const {
>
> - MachineRegisterInfo &MRI = MI->getParent()->getParent()->getRegInfo();
> if (MI->getNumOperands() < 3 || !MI->getOperand(1).isReg())
> return nullptr;
>
> - // Cannot commute VOP2 if src0 is SGPR.
> - if (isVOP2(MI->getOpcode()) && MI->getOperand(1).isReg() &&
> - RI.isSGPRClass(MRI.getRegClass(MI->getOperand(1).getReg())))
> - return nullptr;
> + // Make sure it s legal to commute operands for VOP2.
> + if (isVOP2(MI->getOpcode()) &&
> + (!isOperandLegal(MI, 1, &MI->getOperand(2)) ||
> + !isOperandLegal(MI, 2, &MI->getOperand(1))))
> + return nullptr;
>
> if (!MI->getOperand(2).isReg()) {
> // XXX: Commute instructions with FPImm operands
> @@ -896,8 +896,36 @@ unsigned SIInstrInfo::split64BitImm(SmallVectorImpl<MachineInstr *> &Worklist,
> return Dst;
> }
>
> +bool SIInstrInfo::isOperandLegal(const MachineInstr *MI, unsigned OpIdx,
> + const MachineOperand *MO) const {
> + const MachineRegisterInfo &MRI = MI->getParent()->getParent()->getRegInfo();
> + const MCInstrDesc &InstDesc = get(MI->getOpcode());
> + const MCOperandInfo &OpInfo = InstDesc.OpInfo[OpIdx];
> + const TargetRegisterClass *DefinedRC =
> + OpInfo.RegClass != -1 ? RI.getRegClass(OpInfo.RegClass) : nullptr;
> + if (!MO)
> + MO = &MI->getOperand(OpIdx);
> +
> + if (MO->isReg()) {
> + assert(DefinedRC);
> + const TargetRegisterClass *RC = MRI.getRegClass(MO->getReg());
> + return RI.getCommonSubClass(RC, RI.getRegClass(OpInfo.RegClass));
> + }
> +
> +
> + // Handle non-register types that are treated like immediates.
> + assert(MO->isImm() || MO->isFPImm() || MO->isTargetIndex() || MO->isFI());
> +
> + if (!DefinedRC)
> + // This opperand expects an immediate
> + return true;
Typo: opperand. Also move the comment before the if so the body of it
doesn't look like it's on 2 lines
> class Constants {
> int TWO_PI = 0x40c90fdb;
> diff --git a/lib/Target/R600/MCTargetDesc/SIMCCodeEmitter.cpp b/lib/Target/R600/MCTargetDesc/SIMCCodeEmitter.cpp
> index 78776c1..8cdf878 100644
> --- a/lib/Target/R600/MCTargetDesc/SIMCCodeEmitter.cpp
> +++ b/lib/Target/R600/MCTargetDesc/SIMCCodeEmitter.cpp
> @@ -14,6 +14,7 @@
> //===----------------------------------------------------------------------===//
>
> #include "AMDGPU.h"
> +#include "SIDefines.h"
> #include "MCTargetDesc/AMDGPUMCTargetDesc.h"
> #include "MCTargetDesc/AMDGPUMCCodeEmitter.h"
> #include "MCTargetDesc/AMDGPUFixupKinds.h"
> @@ -84,6 +85,15 @@ MCCodeEmitter *llvm::createSIMCCodeEmitter(const MCInstrInfo &MCII,
>
> bool SIMCCodeEmitter::isSrcOperand(const MCInstrDesc &Desc,
> unsigned OpNo) const {
> + // FIXME: We need a better way to figure out which operands can be immediate
> + // values
> + //
> + // Some VOP* instructions like ADDC use VReg32 as the register class
> + // for source 0, becuase they read VCC and can't take an SGPR as an
Typo: becuase
> +// Returns the input arguments for VOP3 instructions for the given SrcVT.
> +class getIns64 <RegisterClass Src0RC, RegisterClass Src1RC,
> + RegisterClass Src2RC, int NumSrcArgs,
> + bit HasModifiers> {
> +
> + dag ret =
> + !if (!eq(NumSrcArgs, 1),
> + !if (!eq(HasModifiers, 1),
> + // VOP1 with modifiers
> + (ins InputModsNoDefault:$src0_modifiers, Src0RC:$src0,
> + i32imm:$clamp, i32imm:$omod)
> + /* else */,
> + // VOP1 without modifiers
> + (ins Src0RC:$src0)
> + /* endif */ ),
> + !if (!eq(NumSrcArgs, 2),
> + !if (!eq(HasModifiers, 1),
> + // VOP 2 with modifiers
> + (ins InputModsNoDefault:$src0_modifiers, Src0RC:$src0,
> + InputModsNoDefault:$src1_modifiers, Src1RC:$src1,
> + i32imm:$clamp, i32imm:$omod)
> + /* else */,
> + // VOP2 without modifiers
> + (ins Src0RC:$src0, Src1RC:$src1)
> + /* endif */ )
> + /* NumSrcArgs == 3 */,
> + !if (!eq(HasModifiers, 1),
> + // VOP3 with modifiers
> + (ins InputModsNoDefault:$src0_modifiers, Src0RC:$src0,
> + InputModsNoDefault:$src1_modifiers, Src1RC:$src1,
> + InputModsNoDefault:$src2_modifiers, Src2RC:$src2,
> + i32imm:$clamp, i32imm:$omod)
> + /* else */,
> + // VOP3 without modifiers
> + (ins Src0RC:$src0, Src1RC:$src1, Src2RC:$src2)
> + /* endif */ )));
> +}
> +
> +// Returns the assembly string for the inputs and outputs of a VOP[12C]
> +// instruction. This does not add the _e32 suffix, so it can be re-sued
Typo: re-sued
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20140730/8d3615e2/attachment.html>
More information about the llvm-commits
mailing list