Skip to content

Commit

Permalink
[GlobalISel] Change representation of shuffle masks in MachineOperand.
Browse files Browse the repository at this point in the history
We're planning to remove the shufflemask operand from ShuffleVectorInst
(D72467); fix GlobalISel so it doesn't depend on that Constant.

The change to prelegalizercombiner-shuffle-vector.mir happens because
the input contains a literal "-1" in the mask (so the parser/verifier
weren't really handling it properly). We now treat it as equivalent to
"undef" in all contexts.

Differential Revision: https://reviews.llvm.org/D72663
  • Loading branch information
efriedma-quic committed Jan 14, 2020
1 parent 989bed9 commit e68e4cb
Show file tree
Hide file tree
Showing 12 changed files with 38 additions and 61 deletions.
2 changes: 2 additions & 0 deletions llvm/include/llvm/CodeGen/MachineFunction.h
Expand Up @@ -796,6 +796,8 @@ class MachineFunction {
/// Allocate and initialize a register mask with @p NumRegister bits.
uint32_t *allocateRegMask();

ArrayRef<int> allocateShuffleMask(ArrayRef<int> Mask);

/// Allocate and construct an extra info structure for a `MachineInstr`.
///
/// This is allocated on the function's allocator and so lives the life of
Expand Down
2 changes: 1 addition & 1 deletion llvm/include/llvm/CodeGen/MachineInstrBuilder.h
Expand Up @@ -250,7 +250,7 @@ class MachineInstrBuilder {
return *this;
}

const MachineInstrBuilder &addShuffleMask(const Constant *Val) const {
const MachineInstrBuilder &addShuffleMask(ArrayRef<int> Val) const {
MI->addOperand(*MF, MachineOperand::CreateShuffleMask(Val));
return *this;
}
Expand Down
11 changes: 6 additions & 5 deletions llvm/include/llvm/CodeGen/MachineOperand.h
Expand Up @@ -163,7 +163,8 @@ class MachineOperand {
MachineInstr *ParentMI;

/// Contents union - This contains the payload for the various operand types.
union {
union ContentsUnion {
ContentsUnion() {}
MachineBasicBlock *MBB; // For MO_MachineBasicBlock.
const ConstantFP *CFP; // For MO_FPImmediate.
const ConstantInt *CI; // For MO_CImmediate. Integers > 64bit.
Expand All @@ -174,7 +175,7 @@ class MachineOperand {
unsigned CFIIndex; // For MO_CFI.
Intrinsic::ID IntrinsicID; // For MO_IntrinsicID.
unsigned Pred; // For MO_Predicate
const Constant *ShuffleMask; // For MO_ShuffleMask
ArrayRef<int> ShuffleMask; // For MO_ShuffleMask

struct { // For MO_Register.
// Register number is in SmallContents.RegNo.
Expand Down Expand Up @@ -587,7 +588,7 @@ class MachineOperand {
return Contents.Pred;
}

const Constant *getShuffleMask() const {
ArrayRef<int> getShuffleMask() const {
assert(isShuffleMask() && "Wrong MachineOperand accessor");
return Contents.ShuffleMask;
}
Expand Down Expand Up @@ -915,9 +916,9 @@ class MachineOperand {
return Op;
}

static MachineOperand CreateShuffleMask(const Constant *C) {
static MachineOperand CreateShuffleMask(ArrayRef<int> Mask) {
MachineOperand Op(MachineOperand::MO_ShuffleMask);
Op.Contents.ShuffleMask = C;
Op.Contents.ShuffleMask = Mask;
return Op;
}

Expand Down
3 changes: 1 addition & 2 deletions llvm/lib/CodeGen/GlobalISel/CombinerHelper.cpp
Expand Up @@ -239,8 +239,7 @@ bool CombinerHelper::matchCombineShuffleVector(MachineInstr &MI,
// vectors.
unsigned NumConcat = DstNumElts / SrcNumElts;
SmallVector<int, 8> ConcatSrcs(NumConcat, -1);
SmallVector<int, 8> Mask;
ShuffleVectorInst::getShuffleMask(MI.getOperand(3).getShuffleMask(), Mask);
ArrayRef<int> Mask = MI.getOperand(3).getShuffleMask();
for (unsigned i = 0; i != DstNumElts; ++i) {
int Idx = Mask[i];
// Undef value.
Expand Down
5 changes: 4 additions & 1 deletion llvm/lib/CodeGen/GlobalISel/IRTranslator.cpp
Expand Up @@ -1933,11 +1933,14 @@ bool IRTranslator::translateExtractElement(const User &U,

bool IRTranslator::translateShuffleVector(const User &U,
MachineIRBuilder &MIRBuilder) {
SmallVector<int, 8> Mask;
ShuffleVectorInst::getShuffleMask(cast<Constant>(U.getOperand(2)), Mask);
ArrayRef<int> MaskAlloc = MF->allocateShuffleMask(Mask);
MIRBuilder.buildInstr(TargetOpcode::G_SHUFFLE_VECTOR)
.addDef(getOrCreateVReg(U))
.addUse(getOrCreateVReg(*U.getOperand(0)))
.addUse(getOrCreateVReg(*U.getOperand(1)))
.addShuffleMask(cast<Constant>(U.getOperand(2)));
.addShuffleMask(MaskAlloc);
return true;
}

Expand Down
5 changes: 1 addition & 4 deletions llvm/lib/CodeGen/GlobalISel/LegalizerHelper.cpp
Expand Up @@ -4202,10 +4202,7 @@ LegalizerHelper::lowerShuffleVector(MachineInstr &MI) {
LLT DstTy = MRI.getType(DstReg);
LLT IdxTy = LLT::scalar(32);

const Constant *ShufMask = MI.getOperand(3).getShuffleMask();

SmallVector<int, 32> Mask;
ShuffleVectorInst::getShuffleMask(ShufMask, Mask);
ArrayRef<int> Mask = MI.getOperand(3).getShuffleMask();

if (DstTy.isScalar()) {
if (Src0Ty.isVector())
Expand Down
25 changes: 5 additions & 20 deletions llvm/lib/CodeGen/MIRParser/MIParser.cpp
Expand Up @@ -2421,23 +2421,13 @@ bool MIParser::parseShuffleMaskOperand(MachineOperand &Dest) {
if (expectAndConsume(MIToken::lparen))
return error("expected syntax shufflemask(<integer or undef>, ...)");

SmallVector<Constant *, 32> ShufMask;
LLVMContext &Ctx = MF.getFunction().getContext();
Type *I32Ty = Type::getInt32Ty(Ctx);

bool AllZero = true;
bool AllUndef = true;

SmallVector<int, 32> ShufMask;
do {
if (Token.is(MIToken::kw_undef)) {
ShufMask.push_back(UndefValue::get(I32Ty));
AllZero = false;
ShufMask.push_back(-1);
} else if (Token.is(MIToken::IntegerLiteral)) {
AllUndef = false;
const APSInt &Int = Token.integerValue();
if (!Int.isNullValue())
AllZero = false;
ShufMask.push_back(ConstantInt::get(I32Ty, Int.getExtValue()));
ShufMask.push_back(Int.getExtValue());
} else
return error("expected integer constant");

Expand All @@ -2447,13 +2437,8 @@ bool MIParser::parseShuffleMaskOperand(MachineOperand &Dest) {
if (expectAndConsume(MIToken::rparen))
return error("shufflemask should be terminated by ')'.");

if (AllZero || AllUndef) {
VectorType *VT = VectorType::get(I32Ty, ShufMask.size());
Constant *C = AllZero ? Constant::getNullValue(VT) : UndefValue::get(VT);
Dest = MachineOperand::CreateShuffleMask(C);
} else
Dest = MachineOperand::CreateShuffleMask(ConstantVector::get(ShufMask));

ArrayRef<int> MaskAlloc = MF.allocateShuffleMask(ShufMask);
Dest = MachineOperand::CreateShuffleMask(MaskAlloc);
return false;
}

Expand Down
6 changes: 6 additions & 0 deletions llvm/lib/CodeGen/MachineFunction.cpp
Expand Up @@ -484,6 +484,12 @@ uint32_t *MachineFunction::allocateRegMask() {
return Mask;
}

ArrayRef<int> MachineFunction::allocateShuffleMask(ArrayRef<int> Mask) {
int* AllocMask = Allocator.Allocate<int>(Mask.size());
copy(Mask, AllocMask);
return {AllocMask, Mask.size()};
}

#if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP)
LLVM_DUMP_METHOD void MachineFunction::dump() const {
print(dbgs());
Expand Down
12 changes: 6 additions & 6 deletions llvm/lib/CodeGen/MachineOperand.cpp
Expand Up @@ -930,13 +930,13 @@ void MachineOperand::print(raw_ostream &OS, ModuleSlotTracker &MST,
}
case MachineOperand::MO_ShuffleMask:
OS << "shufflemask(";
const Constant* C = getShuffleMask();
const int NumElts = C->getType()->getVectorNumElements();

ArrayRef<int> Mask = getShuffleMask();
StringRef Separator;
for (int I = 0; I != NumElts; ++I) {
OS << Separator;
C->getAggregateElement(I)->printAsOperand(OS, false, MST);
for (int Elt : Mask) {
if (Elt == -1)
OS << Separator << "undef";
else
OS << Separator << Elt;
Separator = ", ";
}

Expand Down
15 changes: 1 addition & 14 deletions llvm/lib/CodeGen/MachineVerifier.cpp
Expand Up @@ -1407,18 +1407,6 @@ void MachineVerifier::verifyPreISelGenericInstruction(const MachineInstr *MI) {
break;
}

const Constant *Mask = MaskOp.getShuffleMask();
auto *MaskVT = dyn_cast<VectorType>(Mask->getType());
if (!MaskVT || !MaskVT->getElementType()->isIntegerTy(32)) {
report("Invalid shufflemask constant type", MI);
break;
}

if (!Mask->getAggregateElement(0u)) {
report("Invalid shufflemask constant type", MI);
break;
}

LLT DstTy = MRI->getType(MI->getOperand(0).getReg());
LLT Src0Ty = MRI->getType(MI->getOperand(1).getReg());
LLT Src1Ty = MRI->getType(MI->getOperand(2).getReg());
Expand All @@ -1434,8 +1422,7 @@ void MachineVerifier::verifyPreISelGenericInstruction(const MachineInstr *MI) {
int SrcNumElts = Src0Ty.isVector() ? Src0Ty.getNumElements() : 1;
int DstNumElts = DstTy.isVector() ? DstTy.getNumElements() : 1;

SmallVector<int, 32> MaskIdxes;
ShuffleVectorInst::getShuffleMask(Mask, MaskIdxes);
ArrayRef<int> MaskIdxes = MaskOp.getShuffleMask();

if (static_cast<int>(MaskIdxes.size()) != DstNumElts)
report("Wrong result type for shufflemask", MI);
Expand Down
9 changes: 3 additions & 6 deletions llvm/lib/Target/AArch64/AArch64InstructionSelector.cpp
Expand Up @@ -3699,8 +3699,8 @@ bool AArch64InstructionSelector::tryOptVectorDup(MachineInstr &I) const {
return false;

// The shuffle's second operand doesn't matter if the mask is all zero.
const Constant *Mask = I.getOperand(3).getShuffleMask();
if (!isa<ConstantAggregateZero>(Mask))
ArrayRef<int> Mask = I.getOperand(3).getShuffleMask();
if (!all_of(Mask, [](int Elem) { return Elem == 0; }))
return false;

// We're done, now find out what kind of splat we need.
Expand Down Expand Up @@ -3778,15 +3778,12 @@ bool AArch64InstructionSelector::selectShuffleVector(
const LLT Src1Ty = MRI.getType(Src1Reg);
Register Src2Reg = I.getOperand(2).getReg();
const LLT Src2Ty = MRI.getType(Src2Reg);
const Constant *ShuffleMask = I.getOperand(3).getShuffleMask();
ArrayRef<int> Mask = I.getOperand(3).getShuffleMask();

MachineBasicBlock &MBB = *I.getParent();
MachineFunction &MF = *MBB.getParent();
LLVMContext &Ctx = MF.getFunction().getContext();

SmallVector<int, 8> Mask;
ShuffleVectorInst::getShuffleMask(ShuffleMask, Mask);

// G_SHUFFLE_VECTOR is weird in that the source operands can be scalars, if
// it's originated from a <1 x T> type. Those should have been lowered into
// G_BUILD_VECTOR earlier.
Expand Down
Expand Up @@ -135,7 +135,7 @@ body: |
; CHECK: liveins: $d0, $d1
; CHECK: [[COPY:%[0-9]+]]:_(<2 x s32>) = COPY $d0
; CHECK: [[COPY1:%[0-9]+]]:_(<2 x s32>) = COPY $d1
; CHECK: [[SHUF:%[0-9]+]]:_(<6 x s32>) = G_SHUFFLE_VECTOR [[COPY]](<2 x s32>), [[COPY1]], shufflemask(2, 3, 0, 1, 3, -1)
; CHECK: [[SHUF:%[0-9]+]]:_(<6 x s32>) = G_SHUFFLE_VECTOR [[COPY]](<2 x s32>), [[COPY1]], shufflemask(2, 3, 0, 1, 3, undef)
; CHECK: RET_ReallyLR implicit [[SHUF]](<6 x s32>)
%0:_(<2 x s32>) = COPY $d0
%1:_(<2 x s32>) = COPY $d1
Expand Down Expand Up @@ -277,7 +277,7 @@ body: |
; CHECK: liveins: $q0, $q1
; CHECK: [[COPY:%[0-9]+]]:_(<4 x s32>) = COPY $q0
; CHECK: [[COPY1:%[0-9]+]]:_(<4 x s32>) = COPY $q1
; CHECK: [[SHUF:%[0-9]+]]:_(<12 x s32>) = G_SHUFFLE_VECTOR [[COPY]](<4 x s32>), [[COPY1]], shufflemask(4, 5, 6, 7, 0, 1, 2, 3, 6, 7, -1, -1)
; CHECK: [[SHUF:%[0-9]+]]:_(<12 x s32>) = G_SHUFFLE_VECTOR [[COPY]](<4 x s32>), [[COPY1]], shufflemask(4, 5, 6, 7, 0, 1, 2, 3, 6, 7, undef, undef)
; CHECK: RET_ReallyLR implicit [[SHUF]](<12 x s32>)
%0:_(<4 x s32>) = COPY $q0
%1:_(<4 x s32>) = COPY $q1
Expand Down

0 comments on commit e68e4cb

Please sign in to comment.