From 626236d9bc9ee3f7dc7dc55b18ea4cb77624bf7e Mon Sep 17 00:00:00 2001 From: Hal Finkel Date: Thu, 2 Oct 2014 22:34:22 +0000 Subject: [PATCH] [PowerPC] Modern Book-E cores support sync Older Book-E cores, such as the PPC 440, support only msync (which has the same encoding as sync 0), but not any of the other sync forms. Newer Book-E cores, however, do support sync, and for performance reasons we should allow the use of the more-general form. This refactors msync use into its own feature group so that it applies by default only to older Book-E cores (of the relevant cores, we only have definitions for the PPC440/450 currently). git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@218923 91177308-0d34-0410-b5e6-96231b3b80d8 --- lib/Target/PowerPC/PPC.td | 9 +++++++-- lib/Target/PowerPC/PPCInstrInfo.td | 29 ++++++++++++++--------------- lib/Target/PowerPC/PPCSubtarget.cpp | 1 + lib/Target/PowerPC/PPCSubtarget.h | 2 ++ test/CodeGen/PowerPC/ppc440-msync.ll | 1 + 5 files changed, 25 insertions(+), 17 deletions(-) diff --git a/lib/Target/PowerPC/PPC.td b/lib/Target/PowerPC/PPC.td index 13d3f31d6f3..8f4c1ee77a7 100644 --- a/lib/Target/PowerPC/PPC.td +++ b/lib/Target/PowerPC/PPC.td @@ -90,6 +90,9 @@ def FeatureLDBRX : SubtargetFeature<"ldbrx","HasLDBRX", "true", "Enable the ldbrx instruction">; def FeatureBookE : SubtargetFeature<"booke", "IsBookE", "true", "Enable Book E instructions">; +def FeatureMSYNC : SubtargetFeature<"msync", "HasOnlyMSYNC", "true", + "Has only the msync instruction instead of sync", + [FeatureBookE]>; def FeatureE500 : SubtargetFeature<"e500", "IsE500", "true", "Enable E500/E500mc instructions">; def FeaturePPC4xx : SubtargetFeature<"ppc4xx", "IsPPC4xx", "true", @@ -196,10 +199,12 @@ include "PPCInstrInfo.td" def : Processor<"generic", G3Itineraries, [Directive32]>; def : ProcessorModel<"440", PPC440Model, [Directive440, FeatureISEL, FeatureFRES, FeatureFRSQRTE, - FeatureBookE, DeprecatedMFTB]>; + FeatureBookE, FeatureMSYNC, + DeprecatedMFTB]>; def : ProcessorModel<"450", PPC440Model, [Directive440, FeatureISEL, FeatureFRES, FeatureFRSQRTE, - FeatureBookE, DeprecatedMFTB]>; + FeatureBookE, FeatureMSYNC, + DeprecatedMFTB]>; def : Processor<"601", G3Itineraries, [Directive601]>; def : Processor<"602", G3Itineraries, [Directive602]>; def : Processor<"603", G3Itineraries, [Directive603, diff --git a/lib/Target/PowerPC/PPCInstrInfo.td b/lib/Target/PowerPC/PPCInstrInfo.td index 11c60448e4c..fe85e8209f7 100644 --- a/lib/Target/PowerPC/PPCInstrInfo.td +++ b/lib/Target/PowerPC/PPCInstrInfo.td @@ -665,6 +665,8 @@ def In32BitMode : Predicate<"!PPCSubTarget->isPPC64()">; def In64BitMode : Predicate<"PPCSubTarget->isPPC64()">; def IsBookE : Predicate<"PPCSubTarget->isBookE()">; def IsNotBookE : Predicate<"!PPCSubTarget->isBookE()">; +def HasOnlyMSYNC : Predicate<"PPCSubTarget->hasOnlyMSYNC()">; +def HasSYNC : Predicate<"!PPCSubTarget->hasOnlyMSYNC()">; def IsPPC4xx : Predicate<"PPCSubTarget->isPPC4xx()">; def IsPPC6xx : Predicate<"PPCSubTarget->isPPC6xx()">; def IsE500 : Predicate<"PPCSubTarget->isE500()">; @@ -1695,22 +1697,19 @@ def STMW : DForm_1<47, (outs), (ins gprc:$rS, memri:$dst), "stmw $rS, $dst", IIC_LdStLMW, []>; def SYNC : XForm_24_sync<31, 598, (outs), (ins i32imm:$L), - "sync $L", IIC_LdStSync, []>, Requires<[IsNotBookE]>; + "sync $L", IIC_LdStSync, []>; let isCodeGenOnly = 1 in { def MSYNC : XForm_24_sync<31, 598, (outs), (ins), - "msync", IIC_LdStSync, []>, Requires<[IsBookE]> { + "msync", IIC_LdStSync, []> { let L = 0; } } -// FIXME: We should use a specific flag to check for the presence of the sync -// instruction instead of relying on IsBookE. -// For example, the PPC A2 supports SYNC despite being a BookE processor. -def : Pat<(int_ppc_sync), (SYNC 0)>, Requires<[IsNotBookE]>; -def : Pat<(int_ppc_lwsync), (SYNC 1)>, Requires<[IsNotBookE]>; -def : Pat<(int_ppc_sync), (MSYNC)>, Requires<[IsBookE]>; -def : Pat<(int_ppc_lwsync), (MSYNC)>, Requires<[IsBookE]>; +def : Pat<(int_ppc_sync), (SYNC 0)>, Requires<[HasSYNC]>; +def : Pat<(int_ppc_lwsync), (SYNC 1)>, Requires<[HasSYNC]>; +def : Pat<(int_ppc_sync), (MSYNC)>, Requires<[HasOnlyMSYNC]>; +def : Pat<(int_ppc_lwsync), (MSYNC)>, Requires<[HasOnlyMSYNC]>; //===----------------------------------------------------------------------===// // PPC32 Arithmetic Instructions. @@ -2550,8 +2549,8 @@ def : Pat<(f64 (extloadf32 xaddr:$src)), def : Pat<(f64 (fextend f32:$src)), (COPY_TO_REGCLASS $src, F8RC)>; -def : Pat<(atomic_fence (imm), (imm)), (SYNC 0)>, Requires<[IsNotBookE]>; -def : Pat<(atomic_fence (imm), (imm)), (MSYNC)>, Requires<[IsBookE]>; +def : Pat<(atomic_fence (imm), (imm)), (SYNC 0)>, Requires<[HasSYNC]>; +def : Pat<(atomic_fence (imm), (imm)), (MSYNC)>, Requires<[HasOnlyMSYNC]>; // Additional FNMSUB patterns: -a*c + b == -(a*c - b) def : Pat<(fma (fneg f64:$A), f64:$C, f64:$B), @@ -3249,10 +3248,10 @@ class PPCAsmPseudo def : InstAlias<"sc", (SC 0)>; -def : InstAlias<"sync", (SYNC 0)>, Requires<[IsNotBookE]>; -def : InstAlias<"msync", (SYNC 0)>, Requires<[IsNotBookE]>; -def : InstAlias<"lwsync", (SYNC 1)>, Requires<[IsNotBookE]>; -def : InstAlias<"ptesync", (SYNC 2)>, Requires<[IsNotBookE]>; +def : InstAlias<"sync", (SYNC 0)>, Requires<[HasSYNC]>; +def : InstAlias<"msync", (SYNC 0)>, Requires<[HasSYNC]>; +def : InstAlias<"lwsync", (SYNC 1)>, Requires<[HasSYNC]>; +def : InstAlias<"ptesync", (SYNC 2)>, Requires<[HasSYNC]>; def : InstAlias<"wait", (WAIT 0)>; def : InstAlias<"waitrsv", (WAIT 1)>; diff --git a/lib/Target/PowerPC/PPCSubtarget.cpp b/lib/Target/PowerPC/PPCSubtarget.cpp index da4a57015c6..ba8bda9ec2c 100644 --- a/lib/Target/PowerPC/PPCSubtarget.cpp +++ b/lib/Target/PowerPC/PPCSubtarget.cpp @@ -109,6 +109,7 @@ void PPCSubtarget::initializeEnvironment() { HasPOPCNTD = false; HasLDBRX = false; IsBookE = false; + HasOnlyMSYNC = false; IsPPC4xx = false; IsPPC6xx = false; IsE500 = false; diff --git a/lib/Target/PowerPC/PPCSubtarget.h b/lib/Target/PowerPC/PPCSubtarget.h index 993afdf82b5..9e4953f20d9 100644 --- a/lib/Target/PowerPC/PPCSubtarget.h +++ b/lib/Target/PowerPC/PPCSubtarget.h @@ -103,6 +103,7 @@ protected: bool HasPOPCNTD; bool HasLDBRX; bool IsBookE; + bool HasOnlyMSYNC; bool IsE500; bool IsPPC4xx; bool IsPPC6xx; @@ -219,6 +220,7 @@ public: bool hasPOPCNTD() const { return HasPOPCNTD; } bool hasLDBRX() const { return HasLDBRX; } bool isBookE() const { return IsBookE; } + bool hasOnlyMSYNC() const { return HasOnlyMSYNC; } bool isPPC4xx() const { return IsPPC4xx; } bool isPPC6xx() const { return IsPPC6xx; } bool isE500() const { return IsE500; } diff --git a/test/CodeGen/PowerPC/ppc440-msync.ll b/test/CodeGen/PowerPC/ppc440-msync.ll index 1274173256c..3f4e7fd0d2d 100644 --- a/test/CodeGen/PowerPC/ppc440-msync.ll +++ b/test/CodeGen/PowerPC/ppc440-msync.ll @@ -1,4 +1,5 @@ ; RUN: llc < %s -march=ppc32 | FileCheck %s +; RUN: llc < %s -march=ppc64 -mcpu=a2 | FileCheck %s ; RUN: llc < %s -march=ppc32 -mcpu=440 | FileCheck %s -check-prefix=BE-CHK define i32 @has_a_fence(i32 %a, i32 %b) nounwind { -- 2.11.0