Index: include/llvm/IR/IntrinsicsPowerPC.td =================================================================== --- include/llvm/IR/IntrinsicsPowerPC.td +++ include/llvm/IR/IntrinsicsPowerPC.td @@ -203,19 +203,19 @@ // source address with a single pointer. def int_ppc_altivec_stvx : Intrinsic<[], [llvm_v4i32_ty, llvm_ptr_ty], - [IntrArgMemOnly]>; + [IntrWriteMem, IntrArgMemOnly]>; def int_ppc_altivec_stvxl : Intrinsic<[], [llvm_v4i32_ty, llvm_ptr_ty], - [IntrArgMemOnly]>; + [IntrWriteMem, IntrArgMemOnly]>; def int_ppc_altivec_stvebx : Intrinsic<[], [llvm_v16i8_ty, llvm_ptr_ty], - [IntrArgMemOnly]>; + [IntrWriteMem, IntrArgMemOnly]>; def int_ppc_altivec_stvehx : Intrinsic<[], [llvm_v8i16_ty, llvm_ptr_ty], - [IntrArgMemOnly]>; + [IntrWriteMem, IntrArgMemOnly]>; def int_ppc_altivec_stvewx : Intrinsic<[], [llvm_v4i32_ty, llvm_ptr_ty], - [IntrArgMemOnly]>; + [IntrWriteMem, IntrArgMemOnly]>; // Comparisons setting a vector. def int_ppc_altivec_vcmpbfp : GCCBuiltin<"__builtin_altivec_vcmpbfp">, @@ -749,20 +749,20 @@ IntrArgMemOnly]>; def int_ppc_vsx_stxvl : Intrinsic<[], [llvm_v4i32_ty, llvm_ptr_ty, llvm_i64_ty], - [IntrArgMemOnly]>; + [IntrWriteMem, IntrArgMemOnly]>; def int_ppc_vsx_stxvll : Intrinsic<[], [llvm_v4i32_ty, llvm_ptr_ty, llvm_i64_ty], - [IntrArgMemOnly]>; + [IntrWriteMem, IntrArgMemOnly]>; // Vector store. -def int_ppc_vsx_stxvw4x : - Intrinsic<[], [llvm_v4i32_ty, llvm_ptr_ty], [IntrArgMemOnly]>; -def int_ppc_vsx_stxvd2x : - Intrinsic<[], [llvm_v2f64_ty, llvm_ptr_ty], [IntrArgMemOnly]>; -def int_ppc_vsx_stxvw4x_be : - Intrinsic<[], [llvm_v4i32_ty, llvm_ptr_ty], [IntrArgMemOnly]>; -def int_ppc_vsx_stxvd2x_be : - Intrinsic<[], [llvm_v2f64_ty, llvm_ptr_ty], [IntrArgMemOnly]>; +def int_ppc_vsx_stxvw4x : Intrinsic<[], [llvm_v4i32_ty, llvm_ptr_ty], + [IntrWriteMem, IntrArgMemOnly]>; +def int_ppc_vsx_stxvd2x : Intrinsic<[], [llvm_v2f64_ty, llvm_ptr_ty], + [IntrWriteMem, IntrArgMemOnly]>; +def int_ppc_vsx_stxvw4x_be : Intrinsic<[], [llvm_v4i32_ty, llvm_ptr_ty], + [IntrWriteMem, IntrArgMemOnly]>; +def int_ppc_vsx_stxvd2x_be : Intrinsic<[], [llvm_v2f64_ty, llvm_ptr_ty], + [IntrWriteMem, IntrArgMemOnly]>; // Vector and scalar maximum. def int_ppc_vsx_xvmaxdp : PowerPC_VSX_Vec_DDD_Intrinsic<"xvmaxdp">; def int_ppc_vsx_xvmaxsp : PowerPC_VSX_Vec_FFF_Intrinsic<"xvmaxsp">; @@ -953,7 +953,7 @@ class PowerPC_QPX_Store_Intrinsic : PowerPC_QPX_Intrinsic; + [IntrWriteMem, IntrArgMemOnly]>; //===----------------------------------------------------------------------===// // PowerPC QPX Intrinsic Definitions. Index: lib/Target/PowerPC/PPCISelDAGToDAG.cpp =================================================================== --- lib/Target/PowerPC/PPCISelDAGToDAG.cpp +++ lib/Target/PowerPC/PPCISelDAGToDAG.cpp @@ -2964,7 +2964,11 @@ SelectAddrIdxOnly(LD->getBasePtr(), Base, Offset)) { SDValue Chain = LD->getChain(); SDValue Ops[] = { Base, Offset, Chain }; - CurDAG->SelectNodeTo(N, PPC::LXVDSX, N->getValueType(0), Ops); + SDNode *NewN = CurDAG->SelectNodeTo(N, PPC::LXVDSX, + N->getValueType(0), Ops); + MachineSDNode::mmo_iterator MemOp = MF->allocateMemRefsArray(1); + MemOp[0] = LD->getMemOperand(); + cast(NewN)->setMemRefs(MemOp, MemOp + 1); return; } } Index: lib/Target/PowerPC/PPCInstr64Bit.td =================================================================== --- lib/Target/PowerPC/PPCInstr64Bit.td +++ lib/Target/PowerPC/PPCInstr64Bit.td @@ -253,11 +253,11 @@ Requires<[IsISA3_0]>; } -let Defs = [CR0], mayStore = 1, hasSideEffects = 0 in +let Defs = [CR0], mayStore = 1, mayLoad = 0, hasSideEffects = 0 in def STDCX : XForm_1<31, 214, (outs), (ins g8rc:$rS, memrr:$dst), "stdcx. $rS, $dst", IIC_LdStSTDCX, []>, isDOT; -let mayStore = 1, hasSideEffects = 0 in +let mayStore = 1, mayLoad = 0, hasSideEffects = 0 in def STDAT : X_RD5_RS5_IM5<31, 742, (outs), (ins g8rc:$rS, g8rc:$rA, u5imm:$FC), "stdat $rS, $rA, $FC", IIC_LdStStore>, isPPC64, Requires<[IsISA3_0]>; @@ -1082,7 +1082,7 @@ } // Stores with Update (pre-inc). -let PPC970_Unit = 2, mayStore = 1 in { +let PPC970_Unit = 2, mayStore = 1, mayLoad = 0 in { let Interpretation64Bit = 1, isCodeGenOnly = 1 in { def STBU8 : DForm_1<39, (outs ptr_rc_nor0:$ea_res), (ins g8rc:$rS, memri:$dst), "stbu $rS, $dst", IIC_LdStStoreUpd, []>, Index: lib/Target/PowerPC/PPCInstrAltivec.td =================================================================== --- lib/Target/PowerPC/PPCInstrAltivec.td +++ lib/Target/PowerPC/PPCInstrAltivec.td @@ -407,7 +407,7 @@ "mtvscr $vB", IIC_LdStLoad, [(int_ppc_altivec_mtvscr v4i32:$vB)]>; -let PPC970_Unit = 2 in { // Loads. +let PPC970_Unit = 2, mayLoad = 1, mayStore = 0 in { // Loads. def LVEBX: XForm_1<31, 7, (outs vrrc:$vD), (ins memrr:$src), "lvebx $vD, $src", IIC_LdStLoad, [(set v16i8:$vD, (int_ppc_altivec_lvebx xoaddr:$src))]>; @@ -434,7 +434,7 @@ [(set v16i8:$vD, (int_ppc_altivec_lvsr xoaddr:$src))]>, PPC970_Unit_LSU; -let PPC970_Unit = 2 in { // Stores. +let PPC970_Unit = 2, mayStore = 1, mayLoad = 0 in { // Stores. def STVEBX: XForm_8<31, 135, (outs), (ins vrrc:$rS, memrr:$dst), "stvebx $rS, $dst", IIC_LdStStore, [(int_ppc_altivec_stvebx v16i8:$rS, xoaddr:$dst)]>; Index: lib/Target/PowerPC/PPCInstrInfo.td =================================================================== --- lib/Target/PowerPC/PPCInstrInfo.td +++ lib/Target/PowerPC/PPCInstrInfo.td @@ -114,9 +114,9 @@ def PPCstfiwx : SDNode<"PPCISD::STFIWX", SDT_PPCstfiwx, [SDNPHasChain, SDNPMayStore]>; def PPClfiwax : SDNode<"PPCISD::LFIWAX", SDT_PPClfiwx, - [SDNPHasChain, SDNPMayLoad]>; + [SDNPHasChain, SDNPMayLoad, SDNPMemOperand]>; def PPClfiwzx : SDNode<"PPCISD::LFIWZX", SDT_PPClfiwx, - [SDNPHasChain, SDNPMayLoad]>; + [SDNPHasChain, SDNPMayLoad, SDNPMemOperand]>; def PPClxsizx : SDNode<"PPCISD::LXSIZX", SDT_PPCLxsizx, [SDNPHasChain, SDNPMayLoad]>; def PPCstxsix : SDNode<"PPCISD::STXSIX", SDT_PPCstxsix, @@ -243,7 +243,7 @@ [SDNPHasChain, SDNPOptInGlue]>; def PPClbrx : SDNode<"PPCISD::LBRX", SDT_PPClbrx, - [SDNPHasChain, SDNPMayLoad]>; + [SDNPHasChain, SDNPMayLoad, SDNPMemOperand]>; def PPCstbrx : SDNode<"PPCISD::STBRX", SDT_PPCstbrx, [SDNPHasChain, SDNPMayStore]>; @@ -1642,7 +1642,7 @@ } // Instructions to support atomic operations -let mayLoad = 1, hasSideEffects = 0 in { +let mayLoad = 1, mayStore = 0, hasSideEffects = 0 in { def LBARX : XForm_1<31, 52, (outs gprc:$rD), (ins memrr:$src), "lbarx $rD, $src", IIC_LdStLWARX, []>, Requires<[HasPartwordAtomics]>; @@ -1675,7 +1675,7 @@ Requires<[IsISA3_0]>; } -let Defs = [CR0], mayStore = 1, hasSideEffects = 0 in { +let Defs = [CR0], mayStore = 1, mayLoad = 0, hasSideEffects = 0 in { def STBCX : XForm_1<31, 694, (outs), (ins gprc:$rS, memrr:$dst), "stbcx. $rS, $dst", IIC_LdStSTWCX, []>, isDOT, Requires<[HasPartwordAtomics]>; @@ -1688,7 +1688,7 @@ "stwcx. $rS, $dst", IIC_LdStSTWCX, []>, isDOT; } -let mayStore = 1, hasSideEffects = 0 in +let mayStore = 1, mayLoad = 0, hasSideEffects = 0 in def STWAT : X_RD5_RS5_IM5<31, 710, (outs), (ins gprc:$rS, gprc:$rA, u5imm:$FC), "stwat $rS, $rA, $FC", IIC_LdStStore>, Requires<[IsISA3_0]>; @@ -1734,7 +1734,7 @@ // Unindexed (r+i) Loads with Update (preinc). -let mayLoad = 1, hasSideEffects = 0 in { +let mayLoad = 1, mayStore = 0, hasSideEffects = 0 in { def LBZU : DForm_1<35, (outs gprc:$rD, ptr_rc_nor0:$ea_result), (ins memri:$addr), "lbzu $rD, $addr", IIC_LdStLoadUpd, []>, RegConstraint<"$addr.reg = $ea_result">, @@ -1807,7 +1807,7 @@ // Indexed (r+r) Loads. // -let PPC970_Unit = 2 in { +let PPC970_Unit = 2, mayLoad = 1, mayStore = 0 in { def LBZX : XForm_1<31, 87, (outs gprc:$rD), (ins memrr:$src), "lbzx $rD, $src", IIC_LdStLoad, [(set i32:$rD, (zextloadi8 xaddr:$src))]>; @@ -1821,8 +1821,6 @@ def LWZX : XForm_1<31, 23, (outs gprc:$rD), (ins memrr:$src), "lwzx $rD, $src", IIC_LdStLoad, [(set i32:$rD, (load xaddr:$src))]>; - - def LHBRX : XForm_1<31, 790, (outs gprc:$rD), (ins memrr:$src), "lhbrx $rD, $src", IIC_LdStLoad, [(set i32:$rD, (PPClbrx xoaddr:$src, i16))]>; @@ -1854,7 +1852,7 @@ // // Unindexed (r+i) Stores. -let PPC970_Unit = 2 in { +let PPC970_Unit = 2, mayStore = 1, mayLoad = 0 in { def STB : DForm_1<38, (outs), (ins gprc:$rS, memri:$src), "stb $rS, $src", IIC_LdStStore, [(truncstorei8 i32:$rS, iaddr:$src)]>; @@ -1873,7 +1871,7 @@ } // Unindexed (r+i) Stores with Update (preinc). -let PPC970_Unit = 2, mayStore = 1 in { +let PPC970_Unit = 2, mayStore = 1, mayLoad = 0 in { def STBU : DForm_1<39, (outs ptr_rc_nor0:$ea_res), (ins gprc:$rS, memri:$dst), "stbu $rS, $dst", IIC_LdStStoreUpd, []>, RegConstraint<"$dst.reg = $ea_res">, NoEncode<"$ea_res">; @@ -1942,7 +1940,7 @@ } // Indexed (r+r) Stores with Update (preinc). -let PPC970_Unit = 2, mayStore = 1 in { +let PPC970_Unit = 2, mayStore = 1, mayLoad = 0 in { def STBUX : XForm_8<31, 247, (outs ptr_rc_nor0:$ea_res), (ins gprc:$rS, memrr:$dst), "stbux $rS, $dst", IIC_LdStStoreUpd, []>, RegConstraint<"$dst.ptrreg = $ea_res">, NoEncode<"$ea_res">, Index: lib/Target/PowerPC/PPCInstrVSX.td =================================================================== --- lib/Target/PowerPC/PPCInstrVSX.td +++ lib/Target/PowerPC/PPCInstrVSX.td @@ -62,7 +62,7 @@ ]>; def PPClxvd2x : SDNode<"PPCISD::LXVD2X", SDT_PPClxvd2x, - [SDNPHasChain, SDNPMayLoad]>; + [SDNPHasChain, SDNPMayLoad, SDNPMemOperand]>; def PPCstxvd2x : SDNode<"PPCISD::STXVD2X", SDT_PPCstxvd2x, [SDNPHasChain, SDNPMayStore]>; def PPCxxswapd : SDNode<"PPCISD::XXSWAPD", SDT_PPCxxswapd, [SDNPHasChain]>; @@ -117,7 +117,7 @@ let Uses = [RM] in { // Load indexed instructions - let mayLoad = 1 in { + let mayLoad = 1, mayStore = 0 in { let CodeSize = 3 in def LXSDX : XX1Form<31, 588, (outs vsfrc:$XT), (ins memrr:$src), @@ -142,7 +142,7 @@ } // mayLoad // Store indexed instructions - let mayStore = 1 in { + let mayStore = 1, mayLoad = 0 in { let CodeSize = 3 in def STXSDX : XX1Form<31, 716, (outs), (ins vsfrc:$XT, memrr:$dst), @@ -1197,7 +1197,7 @@ [(set v4i32:$XT, (or v4i32:$XA, (vnot_ppc v4i32:$XB)))]>; // VSX scalar loads introduced in ISA 2.07 - let mayLoad = 1 in { + let mayLoad = 1, mayStore = 0 in { let CodeSize = 3 in def LXSSPX : XX1Form<31, 524, (outs vssrc:$XT), (ins memrr:$src), "lxsspx $XT, $src", IIC_LdStLFD, @@ -1211,7 +1211,7 @@ } // mayLoad // VSX scalar stores introduced in ISA 2.07 - let mayStore = 1 in { + let mayStore = 1, mayLoad = 0 in { let CodeSize = 3 in def STXSSPX : XX1Form<31, 652, (outs), (ins vssrc:$XT, memrr:$dst), "stxsspx $XT, $dst", IIC_LdStSTFD, @@ -2335,7 +2335,7 @@ // When adding new D-Form loads/stores, be sure to update the ImmToIdxMap in // PPCRegisterInfo::PPCRegisterInfo and maybe save yourself some debugging. - let mayLoad = 1 in { + let mayLoad = 1, mayStore = 0 in { // Load Vector def LXV : DQ_RD6_RS5_DQ12<61, 1, (outs vsrc:$XT), (ins memrix16:$src), "lxv $XT, $src", IIC_LdStLFD, []>, UseVSXReg; @@ -2383,7 +2383,7 @@ // When adding new D-Form loads/stores, be sure to update the ImmToIdxMap in // PPCRegisterInfo::PPCRegisterInfo and maybe save yourself some debugging. - let mayStore = 1 in { + let mayStore = 1, mayLoad = 0 in { // Store Vector def STXV : DQ_RD6_RS5_DQ12<61, 5, (outs), (ins vsrc:$XT, memrix16:$dst), "stxv $XT, $dst", IIC_LdStSTFD, []>, UseVSXReg; Index: test/CodeGen/PowerPC/swaps-le-7.ll =================================================================== --- test/CodeGen/PowerPC/swaps-le-7.ll +++ test/CodeGen/PowerPC/swaps-le-7.ll @@ -11,11 +11,11 @@ ; CHECK-LABEL: @zg ; CHECK: xxspltd ; CHECK-NEXT: xxspltd -; CHECK-NEXT: xxswapd ; CHECK-NEXT: xvmuldp ; CHECK-NEXT: xvmuldp ; CHECK-NEXT: xvsubdp ; CHECK-NEXT: xvadddp +; CHECK-NEXT: xxswapd ; CHECK-NEXT: xxpermdi ; CHECK-NEXT: xvsubdp ; CHECK-NEXT: xxswapd @@ -52,4 +52,4 @@ ret void } -attributes #0 = { noinline } \ No newline at end of file +attributes #0 = { noinline }