@@ -530,6 +530,9 @@ AArch64TargetLowering::AArch64TargetLowering(const TargetMachine &TM,
530530 setOperationAction(ISD::XOR, MVT::i32, Custom);
531531 setOperationAction(ISD::XOR, MVT::i64, Custom);
532532
533+ setOperationAction(ISD::ADDRSPACECAST, MVT::i32, Custom);
534+ setOperationAction(ISD::ADDRSPACECAST, MVT::i64, Custom);
535+
533536 // Virtually no operation on f128 is legal, but LLVM can't expand them when
534537 // there's a valid register class, so we need custom operations in most cases.
535538 setOperationAction(ISD::FABS, MVT::f128, Expand);
@@ -6880,6 +6883,37 @@ static SDValue LowerTruncateVectorStore(SDLoc DL, StoreSDNode *ST,
68806883 ST->getBasePtr(), ST->getMemOperand());
68816884}
68826885
6886+ static SDValue LowerADDRSPACECAST(SDValue Op, SelectionDAG &DAG) {
6887+ SDLoc dl(Op);
6888+ SDValue Src = Op.getOperand(0);
6889+ MVT DestVT = Op.getSimpleValueType();
6890+ const TargetLowering &TLI = DAG.getTargetLoweringInfo();
6891+ AddrSpaceCastSDNode *N = cast<AddrSpaceCastSDNode>(Op.getNode());
6892+
6893+ unsigned SrcAS = N->getSrcAddressSpace();
6894+ unsigned DestAS = N->getDestAddressSpace();
6895+ assert(SrcAS != DestAS &&
6896+ "addrspacecast must be between different address spaces");
6897+ assert(TLI.getTargetMachine().getPointerSize(SrcAS) !=
6898+ TLI.getTargetMachine().getPointerSize(DestAS) &&
6899+ "addrspacecast must be between different ptr sizes");
6900+
6901+ if (SrcAS == ARM64AS::PTR32_SPTR) {
6902+ return DAG.getNode(ISD::SIGN_EXTEND, dl, DestVT, Src,
6903+ DAG.getTargetConstant(0, dl, DestVT));
6904+ } else if (SrcAS == ARM64AS::PTR32_UPTR) {
6905+ return DAG.getNode(ISD::ZERO_EXTEND, dl, DestVT, Src,
6906+ DAG.getTargetConstant(0, dl, DestVT));
6907+ } else if ((DestAS == ARM64AS::PTR32_SPTR) ||
6908+ (DestAS == ARM64AS::PTR32_UPTR)) {
6909+ SDValue Ext = DAG.getAnyExtOrTrunc(Src, dl, DestVT);
6910+ SDValue Trunc = DAG.getZeroExtendInReg(Ext, dl, DestVT);
6911+ return Trunc;
6912+ } else {
6913+ return Src;
6914+ }
6915+ }
6916+
68836917// Custom lowering for any store, vector or scalar and/or default or with
68846918// a truncate operations. Currently only custom lower truncate operation
68856919// from vector v4i16 to v4i8 or volatile stores of i128.
@@ -7541,6 +7575,8 @@ SDValue AArch64TargetLowering::LowerOperation(SDValue Op,
75417575 case ISD::SIGN_EXTEND:
75427576 case ISD::ZERO_EXTEND:
75437577 return LowerFixedLengthVectorIntExtendToSVE(Op, DAG);
7578+ case ISD::ADDRSPACECAST:
7579+ return LowerADDRSPACECAST(Op, DAG);
75447580 case ISD::SIGN_EXTEND_INREG: {
75457581 // Only custom lower when ExtraVT has a legal byte based element type.
75467582 EVT ExtraVT = cast<VTSDNode>(Op.getOperand(1))->getVT();
@@ -23558,6 +23594,26 @@ static SDValue performLOADCombine(SDNode *N,
2355823594 performTBISimplification(N->getOperand(1), DCI, DAG);
2355923595
2356023596 LoadSDNode *LD = cast<LoadSDNode>(N);
23597+ EVT RegVT = LD->getValueType(0);
23598+ EVT MemVT = LD->getMemoryVT();
23599+ const TargetLowering &TLI = DAG.getTargetLoweringInfo();
23600+ SDLoc DL(LD);
23601+
23602+ // Cast ptr32 and ptr64 pointers to the default address space before a load.
23603+ unsigned AddrSpace = LD->getAddressSpace();
23604+ if (AddrSpace == ARM64AS::PTR64 || AddrSpace == ARM64AS::PTR32_SPTR ||
23605+ AddrSpace == ARM64AS::PTR32_UPTR) {
23606+ MVT PtrVT = TLI.getPointerTy(DAG.getDataLayout());
23607+ if (PtrVT != LD->getBasePtr().getSimpleValueType()) {
23608+ SDValue Cast =
23609+ DAG.getAddrSpaceCast(DL, PtrVT, LD->getBasePtr(), AddrSpace, 0);
23610+ return DAG.getExtLoad(LD->getExtensionType(), DL, RegVT, LD->getChain(),
23611+ Cast, LD->getPointerInfo(), MemVT,
23612+ LD->getOriginalAlign(),
23613+ LD->getMemOperand()->getFlags());
23614+ }
23615+ }
23616+
2356123617 if (LD->isVolatile() || !Subtarget->isLittleEndian())
2356223618 return SDValue(N, 0);
2356323619
@@ -23567,13 +23623,11 @@ static SDValue performLOADCombine(SDNode *N,
2356723623 if (!LD->isNonTemporal())
2356823624 return SDValue(N, 0);
2356923625
23570- EVT MemVT = LD->getMemoryVT();
2357123626 if (MemVT.isScalableVector() || MemVT.getSizeInBits() <= 256 ||
2357223627 MemVT.getSizeInBits() % 256 == 0 ||
2357323628 256 % MemVT.getScalarSizeInBits() != 0)
2357423629 return SDValue(N, 0);
2357523630
23576- SDLoc DL(LD);
2357723631 SDValue Chain = LD->getChain();
2357823632 SDValue BasePtr = LD->getBasePtr();
2357923633 SDNodeFlags Flags = LD->getFlags();
@@ -23833,12 +23887,28 @@ static SDValue performSTORECombine(SDNode *N,
2383323887 SDValue Value = ST->getValue();
2383423888 SDValue Ptr = ST->getBasePtr();
2383523889 EVT ValueVT = Value.getValueType();
23890+ EVT MemVT = ST->getMemoryVT();
23891+ const TargetLowering &TLI = DAG.getTargetLoweringInfo();
23892+ SDLoc DL(ST);
2383623893
2383723894 auto hasValidElementTypeForFPTruncStore = [](EVT VT) {
2383823895 EVT EltVT = VT.getVectorElementType();
2383923896 return EltVT == MVT::f32 || EltVT == MVT::f64;
2384023897 };
2384123898
23899+ // Cast ptr32 and ptr64 pointers to the default address space before a store.
23900+ unsigned AddrSpace = ST->getAddressSpace();
23901+ if (AddrSpace == ARM64AS::PTR64 || AddrSpace == ARM64AS::PTR32_SPTR ||
23902+ AddrSpace == ARM64AS::PTR32_UPTR) {
23903+ MVT PtrVT = TLI.getPointerTy(DAG.getDataLayout());
23904+ if (PtrVT != Ptr.getSimpleValueType()) {
23905+ SDValue Cast = DAG.getAddrSpaceCast(DL, PtrVT, Ptr, AddrSpace, 0);
23906+ return DAG.getStore(Chain, DL, Value, Cast, ST->getPointerInfo(),
23907+ ST->getOriginalAlign(),
23908+ ST->getMemOperand()->getFlags(), ST->getAAInfo());
23909+ }
23910+ }
23911+
2384223912 if (SDValue Res = combineI8TruncStore(ST, DAG, Subtarget))
2384323913 return Res;
2384423914
@@ -23852,8 +23922,8 @@ static SDValue performSTORECombine(SDNode *N,
2385223922 ValueVT.isFixedLengthVector() &&
2385323923 ValueVT.getFixedSizeInBits() >= Subtarget->getMinSVEVectorSizeInBits() &&
2385423924 hasValidElementTypeForFPTruncStore(Value.getOperand(0).getValueType()))
23855- return DAG.getTruncStore(Chain, SDLoc(N) , Value.getOperand(0), Ptr,
23856- ST->getMemoryVT(), ST-> getMemOperand());
23925+ return DAG.getTruncStore(Chain, DL , Value.getOperand(0), Ptr, MemVT ,
23926+ ST->getMemOperand());
2385723927
2385823928 if (SDValue Split = splitStores(N, DCI, DAG, Subtarget))
2385923929 return Split;
@@ -27394,6 +27464,11 @@ void AArch64TargetLowering::ReplaceNodeResults(
2739427464 ReplaceATOMIC_LOAD_128Results(N, Results, DAG, Subtarget);
2739527465 return;
2739627466 }
27467+ case ISD::ADDRSPACECAST: {
27468+ SDValue V = LowerADDRSPACECAST(SDValue(N, 0), DAG);
27469+ Results.push_back(V);
27470+ return;
27471+ }
2739727472 case ISD::ATOMIC_LOAD:
2739827473 case ISD::LOAD: {
2739927474 MemSDNode *LoadNode = cast<MemSDNode>(N);
0 commit comments