@@ -3230,6 +3230,21 @@ SDValue SITargetLowering::LowerCallResult(
3230
3230
Val = DAG.getCopyFromReg(Chain, DL, VA.getLocReg(), VA.getLocVT(), InGlue);
3231
3231
Chain = Val.getValue(1);
3232
3232
InGlue = Val.getValue(2);
3233
+
3234
+ // For i1 return value allocated to an SGPR, we want the dst reg for the
3235
+ // above CopyFromReg not to be of VReg_1 when emitting machine code.
3236
+ // This requires creating an addional CopyToReg followed by another
3237
+ // CopyFromReg.
3238
+ if (RVLocs.size() == 1 && VA.getLocVT() == MVT::i1) {
3239
+ const SIRegisterInfo *TRI = Subtarget->getRegisterInfo();
3240
+ MachineRegisterInfo &MRI = DAG.getMachineFunction().getRegInfo();
3241
+
3242
+ if (TRI->isSGPRReg(MRI, VA.getLocReg())) {
3243
+ Register TmpVReg = MRI.createVirtualRegister(TRI->getBoolRC());
3244
+ SDValue TmpCopyTo = DAG.getCopyToReg(Chain, DL, TmpVReg, Val);
3245
+ Val = DAG.getCopyFromReg(TmpCopyTo, DL, TmpVReg, MVT::i1);
3246
+ }
3247
+ }
3233
3248
} else if (VA.isMemLoc()) {
3234
3249
report_fatal_error("TODO: return values in memory");
3235
3250
} else
@@ -15863,6 +15878,21 @@ static bool isCopyFromRegOfInlineAsm(const SDNode *N) {
15863
15878
return false;
15864
15879
}
15865
15880
15881
+ LLVM_ATTRIBUTE_UNUSED
15882
+ static bool isCopyFromRegForI1Return(const SDNode *N) {
15883
+ assert(N->getOpcode() == ISD::CopyFromReg);
15884
+ SDNode *N1 = N->getOperand(0).getNode();
15885
+ if (N1->getOpcode() != ISD::CopyToReg)
15886
+ return false;
15887
+ SDNode *N2 = N1->getOperand(0).getNode();
15888
+ if (N2->getOpcode() != ISD::CopyFromReg)
15889
+ return false;
15890
+ SDNode *N3 = N2->getOperand(0).getNode();
15891
+ if (N3->getOpcode() != ISD::CALLSEQ_END)
15892
+ return false;
15893
+ return true;
15894
+ }
15895
+
15866
15896
bool SITargetLowering::isSDNodeSourceOfDivergence(const SDNode *N,
15867
15897
FunctionLoweringInfo *FLI,
15868
15898
UniformityInfo *UA) const {
@@ -15880,7 +15910,8 @@ bool SITargetLowering::isSDNodeSourceOfDivergence(const SDNode *N,
15880
15910
if (const Value *V = FLI->getValueFromVirtualReg(R->getReg()))
15881
15911
return UA->isDivergent(V);
15882
15912
15883
- assert(Reg == FLI->DemoteRegister || isCopyFromRegOfInlineAsm(N));
15913
+ assert(Reg == FLI->DemoteRegister || isCopyFromRegOfInlineAsm(N) ||
15914
+ isCopyFromRegForI1Return(N));
15884
15915
return !TRI->isSGPRReg(MRI, Reg);
15885
15916
}
15886
15917
case ISD::LOAD: {
0 commit comments