@@ -77,6 +77,18 @@ XtensaTargetLowering::XtensaTargetLowering(const TargetMachine &TM,
77
77
}
78
78
79
79
setOperationAction (ISD::ConstantPool, PtrVT, Custom);
80
+ setOperationAction (ISD::GlobalAddress, PtrVT, Custom);
81
+ setOperationAction (ISD::BlockAddress, PtrVT, Custom);
82
+ setOperationAction (ISD::JumpTable, PtrVT, Custom);
83
+
84
+ // Expand jump table branches as address arithmetic followed by an
85
+ // indirect jump.
86
+ setOperationAction (ISD::BR_JT, MVT::Other, Custom);
87
+
88
+ setOperationPromotedToType (ISD::BR_CC, MVT::i1, MVT::i32 );
89
+ setOperationAction (ISD::BR_CC, MVT::i32 , Legal);
90
+ setOperationAction (ISD::BR_CC, MVT::i64 , Expand);
91
+ setOperationAction (ISD::BR_CC, MVT::f32 , Expand);
80
92
81
93
// Implement custom stack allocations
82
94
setOperationAction (ISD::DYNAMIC_STACKALLOC, PtrVT, Custom);
@@ -88,6 +100,12 @@ XtensaTargetLowering::XtensaTargetLowering(const TargetMachine &TM,
88
100
computeRegisterProperties (STI.getRegisterInfo ());
89
101
}
90
102
103
+ bool XtensaTargetLowering::isOffsetFoldingLegal (
104
+ const GlobalAddressSDNode *GA) const {
105
+ // The Xtensa target isn't yet aware of offsets.
106
+ return false ;
107
+ }
108
+
91
109
// ===----------------------------------------------------------------------===//
92
110
// Calling conventions
93
111
// ===----------------------------------------------------------------------===//
@@ -519,6 +537,72 @@ SDValue XtensaTargetLowering::LowerImmediate(SDValue Op,
519
537
return Op;
520
538
}
521
539
540
+ SDValue XtensaTargetLowering::LowerGlobalAddress (SDValue Op,
541
+ SelectionDAG &DAG) const {
542
+ const GlobalAddressSDNode *G = cast<GlobalAddressSDNode>(Op);
543
+ SDLoc DL (Op);
544
+ auto PtrVT = Op.getValueType ();
545
+ const GlobalValue *GV = G->getGlobal ();
546
+
547
+ SDValue CPAddr = DAG.getTargetConstantPool (GV, PtrVT, Align (4 ));
548
+ SDValue CPWrap = getAddrPCRel (CPAddr, DAG);
549
+
550
+ return CPWrap;
551
+ }
552
+
553
+ SDValue XtensaTargetLowering::LowerBlockAddress (SDValue Op,
554
+ SelectionDAG &DAG) const {
555
+ BlockAddressSDNode *Node = cast<BlockAddressSDNode>(Op);
556
+ const BlockAddress *BA = Node->getBlockAddress ();
557
+ EVT PtrVT = Op.getValueType ();
558
+
559
+ XtensaConstantPoolValue *CPV =
560
+ XtensaConstantPoolConstant::Create (BA, 0 , XtensaCP::CPBlockAddress);
561
+ SDValue CPAddr = DAG.getTargetConstantPool (CPV, PtrVT, Align (4 ));
562
+ SDValue CPWrap = getAddrPCRel (CPAddr, DAG);
563
+
564
+ return CPWrap;
565
+ }
566
+
567
+ SDValue XtensaTargetLowering::LowerBR_JT (SDValue Op, SelectionDAG &DAG) const {
568
+ SDValue Chain = Op.getOperand (0 );
569
+ SDValue Table = Op.getOperand (1 );
570
+ SDValue Index = Op.getOperand (2 );
571
+ SDLoc DL (Op);
572
+ JumpTableSDNode *JT = cast<JumpTableSDNode>(Table);
573
+ MachineFunction &MF = DAG.getMachineFunction ();
574
+ const MachineJumpTableInfo *MJTI = MF.getJumpTableInfo ();
575
+ SDValue TargetJT = DAG.getTargetJumpTable (JT->getIndex (), MVT::i32 );
576
+ const DataLayout &TD = DAG.getDataLayout ();
577
+ EVT PtrVT = Table.getValueType ();
578
+ unsigned EntrySize = MJTI->getEntrySize (TD);
579
+
580
+ Index = DAG.getNode (ISD::MUL, DL, Index.getValueType (), Index,
581
+ DAG.getConstant (EntrySize, DL, Index.getValueType ()));
582
+ SDValue Addr = DAG.getNode (ISD::ADD, DL, Index.getValueType (), Index, Table);
583
+ SDValue LD =
584
+ DAG.getLoad (PtrVT, DL, Chain, Addr,
585
+ MachinePointerInfo::getJumpTable (DAG.getMachineFunction ()));
586
+
587
+ return DAG.getNode (XtensaISD::BR_JT, DL, MVT::Other, LD.getValue (1 ), LD,
588
+ TargetJT);
589
+ }
590
+
591
+ SDValue XtensaTargetLowering::LowerJumpTable (SDValue Op,
592
+ SelectionDAG &DAG) const {
593
+ JumpTableSDNode *JT = cast<JumpTableSDNode>(Op);
594
+ EVT PtrVT = Op.getValueType ();
595
+
596
+ // Create a constant pool entry for the callee address
597
+ XtensaConstantPoolValue *CPV =
598
+ XtensaConstantPoolJumpTable::Create (*DAG.getContext (), JT->getIndex ());
599
+
600
+ // Get the address of the callee into a register
601
+ SDValue CPAddr = DAG.getTargetConstantPool (CPV, PtrVT, Align (4 ));
602
+
603
+ return getAddrPCRel (CPAddr, DAG);
604
+ }
605
+
522
606
SDValue XtensaTargetLowering::getAddrPCRel (SDValue Op,
523
607
SelectionDAG &DAG) const {
524
608
SDLoc DL (Op);
@@ -580,8 +664,16 @@ SDValue XtensaTargetLowering::LowerDYNAMIC_STACKALLOC(SDValue Op,
580
664
SDValue XtensaTargetLowering::LowerOperation (SDValue Op,
581
665
SelectionDAG &DAG) const {
582
666
switch (Op.getOpcode ()) {
667
+ case ISD::BR_JT:
668
+ return LowerBR_JT (Op, DAG);
583
669
case ISD::Constant:
584
670
return LowerImmediate (Op, DAG);
671
+ case ISD::GlobalAddress:
672
+ return LowerGlobalAddress (Op, DAG);
673
+ case ISD::BlockAddress:
674
+ return LowerBlockAddress (Op, DAG);
675
+ case ISD::JumpTable:
676
+ return LowerJumpTable (Op, DAG);
585
677
case ISD::ConstantPool:
586
678
return LowerConstantPool (cast<ConstantPoolSDNode>(Op), DAG);
587
679
case ISD::STACKSAVE:
@@ -597,6 +689,8 @@ SDValue XtensaTargetLowering::LowerOperation(SDValue Op,
597
689
598
690
const char *XtensaTargetLowering::getTargetNodeName (unsigned Opcode) const {
599
691
switch (Opcode) {
692
+ case XtensaISD::BR_JT:
693
+ return " XtensaISD::BR_JT" ;
600
694
case XtensaISD::CALL:
601
695
return " XtensaISD::CALL" ;
602
696
case XtensaISD::PCREL_WRAPPER:
0 commit comments