@@ -456,6 +456,30 @@ static bool isSplitEdge(const MachineBasicBlock *MBB) {
456
456
return true ;
457
457
}
458
458
459
+ static const TargetRegisterClass *
460
+ getLargestLegalRegClass (Register Reg, const MachineFunction *MF,
461
+ const MachineRegisterInfo &MRI) {
462
+ const TargetInstrInfo *TII = MF->getSubtarget ().getInstrInfo ();
463
+ const TargetRegisterClass *OldRC = MRI.getRegClass (Reg);
464
+ const TargetRegisterInfo *TRI = MRI.getTargetRegisterInfo ();
465
+ const TargetRegisterClass *NewRC = TRI->getLargestLegalSuperClass (OldRC, *MF);
466
+ // Stop early if there is no room to grow.
467
+ if (NewRC == OldRC)
468
+ return OldRC;
469
+
470
+ // Accumulate constraints from all uses.
471
+ for (MachineOperand &MO : MRI.reg_nodbg_operands (Reg)) {
472
+ // Apply the effect of the given operand to NewRC.
473
+ MachineInstr *MI = MO.getParent ();
474
+ unsigned OpNo = &MO - &MI->getOperand (0 );
475
+ NewRC = MI->getRegClassConstraintEffect (OpNo, NewRC, TII, TRI);
476
+ if (!NewRC || NewRC == OldRC) {
477
+ return OldRC;
478
+ }
479
+ }
480
+ return NewRC;
481
+ }
482
+
459
483
bool CoalescerPair::setRegisters (const MachineInstr *MI) {
460
484
SrcReg = DstReg = Register ();
461
485
SrcIdx = DstIdx = 0 ;
@@ -477,7 +501,9 @@ bool CoalescerPair::setRegisters(const MachineInstr *MI) {
477
501
Flipped = true ;
478
502
}
479
503
480
- const MachineRegisterInfo &MRI = MI->getMF ()->getRegInfo ();
504
+ const MachineFunction *MF = MI->getMF ();
505
+
506
+ const MachineRegisterInfo &MRI = MF->getRegInfo ();
481
507
const TargetRegisterClass *SrcRC = MRI.getRegClass (Src);
482
508
483
509
if (Dst.isPhysical ()) {
@@ -509,19 +535,41 @@ bool CoalescerPair::setRegisters(const MachineInstr *MI) {
509
535
510
536
NewRC = TRI.getCommonSuperRegClass (SrcRC, SrcSub, DstRC, DstSub, SrcIdx,
511
537
DstIdx);
512
- if (!NewRC)
513
- return false ;
538
+ if (!NewRC) {
539
+ auto SuperDstRC = getLargestLegalRegClass (Dst, MF, MRI);
540
+ if (SuperDstRC != DstRC)
541
+ NewRC = TRI.getCommonSuperRegClass (SrcRC, SrcSub, SuperDstRC, DstSub,
542
+ SrcIdx, DstIdx);
543
+ if (!NewRC)
544
+ return false ;
545
+ }
514
546
} else if (DstSub) {
515
547
// SrcReg will be merged with a sub-register of DstReg.
516
548
SrcIdx = DstSub;
517
549
NewRC = TRI.getMatchingSuperRegClass (DstRC, SrcRC, DstSub);
550
+ if (!NewRC) {
551
+ auto SuperDstRC = getLargestLegalRegClass (Dst, MF, MRI);
552
+ if (SuperDstRC != DstRC)
553
+ NewRC = TRI.getMatchingSuperRegClass (SuperDstRC, SrcRC, DstSub);
554
+ }
518
555
} else if (SrcSub) {
519
556
// DstReg will be merged with a sub-register of SrcReg.
520
557
DstIdx = SrcSub;
521
558
NewRC = TRI.getMatchingSuperRegClass (SrcRC, DstRC, SrcSub);
559
+ if (!NewRC) {
560
+ auto SuperDstRC = getLargestLegalRegClass (Dst, MF, MRI);
561
+ if (SuperDstRC != DstRC)
562
+ NewRC = TRI.getMatchingSuperRegClass (SrcRC, SuperDstRC, SrcSub);
563
+ }
564
+
522
565
} else {
523
566
// This is a straight copy without sub-registers.
524
567
NewRC = TRI.getCommonSubClass (DstRC, SrcRC);
568
+ if (!NewRC) {
569
+ auto SuperDstRC = getLargestLegalRegClass (Dst, MF, MRI);
570
+ if (SuperDstRC != DstRC)
571
+ NewRC = TRI.getCommonSubClass (SuperDstRC, SrcRC);
572
+ }
525
573
}
526
574
527
575
// The combined constraint may be impossible to satisfy.
0 commit comments