mirror of
https://github.com/c64scene-ar/llvm-6502.git
synced 2025-03-01 01:30:36 +00:00
Rename get_VSPLI_elt -> get_VSPLTI_elt
Canonicalize BUILD_VECTOR's that match VSPLTI's into a single type for each form, eliminating a bunch of Pat patterns in the .td file and allowing us to CSE stuff more aggressively. This implements PowerPC/buildvec_canonicalize.ll:VSPLTI git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@27614 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
parent
fd4297fa0f
commit
e87192a854
@ -429,11 +429,11 @@ unsigned PPC::getVSPLTImmediate(SDNode *N, unsigned EltSize) {
|
|||||||
return cast<ConstantSDNode>(N->getOperand(0))->getValue() / EltSize;
|
return cast<ConstantSDNode>(N->getOperand(0))->getValue() / EltSize;
|
||||||
}
|
}
|
||||||
|
|
||||||
/// get_VSPLI_elt - If this is a build_vector of constants which can be formed
|
/// get_VSPLTI_elt - If this is a build_vector of constants which can be formed
|
||||||
/// by using a vspltis[bhw] instruction of the specified element size, return
|
/// by using a vspltis[bhw] instruction of the specified element size, return
|
||||||
/// the constant being splatted. The ByteSize field indicates the number of
|
/// the constant being splatted. The ByteSize field indicates the number of
|
||||||
/// bytes of each element [124] -> [bhw].
|
/// bytes of each element [124] -> [bhw].
|
||||||
SDOperand PPC::get_VSPLI_elt(SDNode *N, unsigned ByteSize, SelectionDAG &DAG) {
|
SDOperand PPC::get_VSPLTI_elt(SDNode *N, unsigned ByteSize, SelectionDAG &DAG) {
|
||||||
SDOperand OpVal(0, 0);
|
SDOperand OpVal(0, 0);
|
||||||
|
|
||||||
// If ByteSize of the splat is bigger than the element size of the
|
// If ByteSize of the splat is bigger than the element size of the
|
||||||
@ -920,7 +920,7 @@ SDOperand PPCTargetLowering::LowerOperation(SDOperand Op, SelectionDAG &DAG) {
|
|||||||
// Load it out.
|
// Load it out.
|
||||||
return DAG.getLoad(Op.getValueType(), Store, FIdx, DAG.getSrcValue(NULL));
|
return DAG.getLoad(Op.getValueType(), Store, FIdx, DAG.getSrcValue(NULL));
|
||||||
}
|
}
|
||||||
case ISD::BUILD_VECTOR:
|
case ISD::BUILD_VECTOR: {
|
||||||
// If this is a case we can't handle, return null and let the default
|
// If this is a case we can't handle, return null and let the default
|
||||||
// expansion code take care of it. If we CAN select this case, return Op.
|
// expansion code take care of it. If we CAN select this case, return Op.
|
||||||
|
|
||||||
@ -937,13 +937,34 @@ SDOperand PPCTargetLowering::LowerOperation(SDOperand Op, SelectionDAG &DAG) {
|
|||||||
return Op;
|
return Op;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (PPC::get_VSPLI_elt(Op.Val, 1, DAG).Val || // vspltisb
|
// Check to see if this is something we can use VSPLTI* to form.
|
||||||
PPC::get_VSPLI_elt(Op.Val, 2, DAG).Val || // vspltish
|
MVT::ValueType CanonicalVT = MVT::Other;
|
||||||
PPC::get_VSPLI_elt(Op.Val, 4, DAG).Val) // vspltisw
|
SDNode *CST = 0;
|
||||||
|
|
||||||
|
if ((CST = PPC::get_VSPLTI_elt(Op.Val, 4, DAG).Val)) // vspltisw
|
||||||
|
CanonicalVT = MVT::v4i32;
|
||||||
|
else if ((CST = PPC::get_VSPLTI_elt(Op.Val, 2, DAG).Val)) // vspltish
|
||||||
|
CanonicalVT = MVT::v8i16;
|
||||||
|
else if ((CST = PPC::get_VSPLTI_elt(Op.Val, 1, DAG).Val)) // vspltisb
|
||||||
|
CanonicalVT = MVT::v16i8;
|
||||||
|
|
||||||
|
// If this matches one of the vsplti* patterns, force it to the canonical
|
||||||
|
// type for the pattern.
|
||||||
|
if (CST) {
|
||||||
|
if (Op.getValueType() != CanonicalVT) {
|
||||||
|
// Convert the splatted element to the right element type.
|
||||||
|
SDOperand Elt = DAG.getNode(ISD::TRUNCATE,
|
||||||
|
MVT::getVectorBaseType(CanonicalVT),
|
||||||
|
SDOperand(CST, 0));
|
||||||
|
std::vector<SDOperand> Ops(MVT::getVectorNumElements(CanonicalVT), Elt);
|
||||||
|
SDOperand Res = DAG.getNode(ISD::BUILD_VECTOR, CanonicalVT, Ops);
|
||||||
|
Op = DAG.getNode(ISD::BIT_CONVERT, Op.getValueType(), Res);
|
||||||
|
}
|
||||||
return Op;
|
return Op;
|
||||||
|
}
|
||||||
|
|
||||||
return SDOperand();
|
return SDOperand();
|
||||||
|
}
|
||||||
case ISD::VECTOR_SHUFFLE: {
|
case ISD::VECTOR_SHUFFLE: {
|
||||||
SDOperand V1 = Op.getOperand(0);
|
SDOperand V1 = Op.getOperand(0);
|
||||||
SDOperand V2 = Op.getOperand(1);
|
SDOperand V2 = Op.getOperand(1);
|
||||||
|
@ -131,11 +131,11 @@ namespace llvm {
|
|||||||
/// specified isSplatShuffleMask VECTOR_SHUFFLE mask.
|
/// specified isSplatShuffleMask VECTOR_SHUFFLE mask.
|
||||||
unsigned getVSPLTImmediate(SDNode *N, unsigned EltSize);
|
unsigned getVSPLTImmediate(SDNode *N, unsigned EltSize);
|
||||||
|
|
||||||
/// get_VSPLI_elt - If this is a build_vector of constants which can be
|
/// get_VSPLTI_elt - If this is a build_vector of constants which can be
|
||||||
/// formed by using a vspltis[bhw] instruction of the specified element
|
/// formed by using a vspltis[bhw] instruction of the specified element
|
||||||
/// size, return the constant being splatted. The ByteSize field indicates
|
/// size, return the constant being splatted. The ByteSize field indicates
|
||||||
/// the number of bytes of each element [124] -> [bhw].
|
/// the number of bytes of each element [124] -> [bhw].
|
||||||
SDOperand get_VSPLI_elt(SDNode *N, unsigned ByteSize, SelectionDAG &DAG);
|
SDOperand get_VSPLTI_elt(SDNode *N, unsigned ByteSize, SelectionDAG &DAG);
|
||||||
}
|
}
|
||||||
|
|
||||||
class PPCTargetLowering : public TargetLowering {
|
class PPCTargetLowering : public TargetLowering {
|
||||||
|
@ -111,26 +111,26 @@ def VSPLTW_shuffle_mask : PatLeaf<(build_vector), [{
|
|||||||
|
|
||||||
// VSPLTISB_get_imm xform function: convert build_vector to VSPLTISB imm.
|
// VSPLTISB_get_imm xform function: convert build_vector to VSPLTISB imm.
|
||||||
def VSPLTISB_get_imm : SDNodeXForm<build_vector, [{
|
def VSPLTISB_get_imm : SDNodeXForm<build_vector, [{
|
||||||
return PPC::get_VSPLI_elt(N, 1, *CurDAG);
|
return PPC::get_VSPLTI_elt(N, 1, *CurDAG);
|
||||||
}]>;
|
}]>;
|
||||||
def vecspltisb : PatLeaf<(build_vector), [{
|
def vecspltisb : PatLeaf<(build_vector), [{
|
||||||
return PPC::get_VSPLI_elt(N, 1, *CurDAG).Val != 0;
|
return PPC::get_VSPLTI_elt(N, 1, *CurDAG).Val != 0;
|
||||||
}], VSPLTISB_get_imm>;
|
}], VSPLTISB_get_imm>;
|
||||||
|
|
||||||
// VSPLTISH_get_imm xform function: convert build_vector to VSPLTISH imm.
|
// VSPLTISH_get_imm xform function: convert build_vector to VSPLTISH imm.
|
||||||
def VSPLTISH_get_imm : SDNodeXForm<build_vector, [{
|
def VSPLTISH_get_imm : SDNodeXForm<build_vector, [{
|
||||||
return PPC::get_VSPLI_elt(N, 2, *CurDAG);
|
return PPC::get_VSPLTI_elt(N, 2, *CurDAG);
|
||||||
}]>;
|
}]>;
|
||||||
def vecspltish : PatLeaf<(build_vector), [{
|
def vecspltish : PatLeaf<(build_vector), [{
|
||||||
return PPC::get_VSPLI_elt(N, 2, *CurDAG).Val != 0;
|
return PPC::get_VSPLTI_elt(N, 2, *CurDAG).Val != 0;
|
||||||
}], VSPLTISH_get_imm>;
|
}], VSPLTISH_get_imm>;
|
||||||
|
|
||||||
// VSPLTISW_get_imm xform function: convert build_vector to VSPLTISW imm.
|
// VSPLTISW_get_imm xform function: convert build_vector to VSPLTISW imm.
|
||||||
def VSPLTISW_get_imm : SDNodeXForm<build_vector, [{
|
def VSPLTISW_get_imm : SDNodeXForm<build_vector, [{
|
||||||
return PPC::get_VSPLI_elt(N, 4, *CurDAG);
|
return PPC::get_VSPLTI_elt(N, 4, *CurDAG);
|
||||||
}]>;
|
}]>;
|
||||||
def vecspltisw : PatLeaf<(build_vector), [{
|
def vecspltisw : PatLeaf<(build_vector), [{
|
||||||
return PPC::get_VSPLI_elt(N, 4, *CurDAG).Val != 0;
|
return PPC::get_VSPLTI_elt(N, 4, *CurDAG).Val != 0;
|
||||||
}], VSPLTISW_get_imm>;
|
}], VSPLTISW_get_imm>;
|
||||||
|
|
||||||
//===----------------------------------------------------------------------===//
|
//===----------------------------------------------------------------------===//
|
||||||
@ -439,13 +439,13 @@ def VSRW : VX1_Int< 644, "vsrw" , int_ppc_altivec_vsrw>;
|
|||||||
|
|
||||||
def VSPLTISB : VXForm_3<780, (ops VRRC:$vD, s5imm:$SIMM),
|
def VSPLTISB : VXForm_3<780, (ops VRRC:$vD, s5imm:$SIMM),
|
||||||
"vspltisb $vD, $SIMM", VecPerm,
|
"vspltisb $vD, $SIMM", VecPerm,
|
||||||
[(set VRRC:$vD, (v4f32 vecspltisb:$SIMM))]>;
|
[(set VRRC:$vD, (v16i8 vecspltisb:$SIMM))]>;
|
||||||
def VSPLTISH : VXForm_3<844, (ops VRRC:$vD, s5imm:$SIMM),
|
def VSPLTISH : VXForm_3<844, (ops VRRC:$vD, s5imm:$SIMM),
|
||||||
"vspltish $vD, $SIMM", VecPerm,
|
"vspltish $vD, $SIMM", VecPerm,
|
||||||
[(set VRRC:$vD, (v4f32 vecspltish:$SIMM))]>;
|
[(set VRRC:$vD, (v8i16 vecspltish:$SIMM))]>;
|
||||||
def VSPLTISW : VXForm_3<908, (ops VRRC:$vD, s5imm:$SIMM),
|
def VSPLTISW : VXForm_3<908, (ops VRRC:$vD, s5imm:$SIMM),
|
||||||
"vspltisw $vD, $SIMM", VecPerm,
|
"vspltisw $vD, $SIMM", VecPerm,
|
||||||
[(set VRRC:$vD, (v4f32 vecspltisw:$SIMM))]>;
|
[(set VRRC:$vD, (v4i32 vecspltisw:$SIMM))]>;
|
||||||
|
|
||||||
// Vector Pack.
|
// Vector Pack.
|
||||||
def VPKPX : VX1_Int<782, "vpkpx", int_ppc_altivec_vpkpx>;
|
def VPKPX : VX1_Int<782, "vpkpx", int_ppc_altivec_vpkpx>;
|
||||||
@ -540,7 +540,7 @@ def : Pat<(int_ppc_altivec_dstst GPRC:$rA, GPRC:$rB, imm:$STRM),
|
|||||||
def : Pat<(int_ppc_altivec_dststt GPRC:$rA, GPRC:$rB, imm:$STRM),
|
def : Pat<(int_ppc_altivec_dststt GPRC:$rA, GPRC:$rB, imm:$STRM),
|
||||||
(DSTST 1, imm:$STRM, GPRC:$rA, GPRC:$rB)>;
|
(DSTST 1, imm:$STRM, GPRC:$rA, GPRC:$rB)>;
|
||||||
|
|
||||||
// Undef/Zero.
|
// Undef.
|
||||||
def : Pat<(v16i8 (undef)), (v16i8 (IMPLICIT_DEF_VRRC))>;
|
def : Pat<(v16i8 (undef)), (v16i8 (IMPLICIT_DEF_VRRC))>;
|
||||||
def : Pat<(v8i16 (undef)), (v8i16 (IMPLICIT_DEF_VRRC))>;
|
def : Pat<(v8i16 (undef)), (v8i16 (IMPLICIT_DEF_VRRC))>;
|
||||||
def : Pat<(v4i32 (undef)), (v4i32 (IMPLICIT_DEF_VRRC))>;
|
def : Pat<(v4i32 (undef)), (v4i32 (IMPLICIT_DEF_VRRC))>;
|
||||||
@ -602,19 +602,6 @@ def:Pat<(vector_shuffle (v16i8 VRRC:$vA), undef, VMRGHH_unary_shuffle_mask:$in),
|
|||||||
def:Pat<(vector_shuffle (v16i8 VRRC:$vA), undef, VMRGHW_unary_shuffle_mask:$in),
|
def:Pat<(vector_shuffle (v16i8 VRRC:$vA), undef, VMRGHW_unary_shuffle_mask:$in),
|
||||||
(VMRGHW VRRC:$vA, VRRC:$vA)>;
|
(VMRGHW VRRC:$vA, VRRC:$vA)>;
|
||||||
|
|
||||||
// Immediate vector formation with vsplti*.
|
|
||||||
def : Pat<(v16i8 vecspltisb:$invec), (v16i8 (VSPLTISB vecspltisb:$invec))>;
|
|
||||||
def : Pat<(v16i8 vecspltish:$invec), (v16i8 (VSPLTISH vecspltish:$invec))>;
|
|
||||||
def : Pat<(v16i8 vecspltisw:$invec), (v16i8 (VSPLTISW vecspltisw:$invec))>;
|
|
||||||
|
|
||||||
def : Pat<(v8i16 vecspltisb:$invec), (v8i16 (VSPLTISB vecspltisb:$invec))>;
|
|
||||||
def : Pat<(v8i16 vecspltish:$invec), (v8i16 (VSPLTISH vecspltish:$invec))>;
|
|
||||||
def : Pat<(v8i16 vecspltisw:$invec), (v8i16 (VSPLTISW vecspltisw:$invec))>;
|
|
||||||
|
|
||||||
def : Pat<(v4i32 vecspltisb:$invec), (v4i32 (VSPLTISB vecspltisb:$invec))>;
|
|
||||||
def : Pat<(v4i32 vecspltish:$invec), (v4i32 (VSPLTISH vecspltish:$invec))>;
|
|
||||||
def : Pat<(v4i32 vecspltisw:$invec), (v4i32 (VSPLTISW vecspltisw:$invec))>;
|
|
||||||
|
|
||||||
// Logical Operations
|
// Logical Operations
|
||||||
def : Pat<(v16i8 (vnot VRRC:$vA)), (v16i8 (VNOR VRRC:$vA, VRRC:$vA))>;
|
def : Pat<(v16i8 (vnot VRRC:$vA)), (v16i8 (VNOR VRRC:$vA, VRRC:$vA))>;
|
||||||
def : Pat<(v8i16 (vnot VRRC:$vA)), (v8i16 (VNOR VRRC:$vA, VRRC:$vA))>;
|
def : Pat<(v8i16 (vnot VRRC:$vA)), (v8i16 (VNOR VRRC:$vA, VRRC:$vA))>;
|
||||||
|
Loading…
x
Reference in New Issue
Block a user