[Hexagon] Factoring classes out of store patterns.

llvm-svn: 228602
This commit is contained in:
Colin LeMahieu 2015-02-09 20:33:46 +00:00
parent 9be5d1ece8
commit 955c4ff9c3
2 changed files with 53 additions and 45 deletions

View File

@ -3383,12 +3383,34 @@ class Storex_simple_pat<PatFrag Store, PatFrag Value, InstHexagon MI>
: Pat<(Store Value:$Rt, (i32 IntRegs:$Rs)),
(MI IntRegs:$Rs, 0, Value:$Rt)>;
// Patterns for generating stores, where the address takes different forms,
// and where the value being stored is transformed through the value modifier
// ValueMod. The address forms are same as above.
class Storexm_fi_pat<PatFrag Store, PatFrag Value, PatFrag ValueMod,
InstHexagon MI>
: Pat<(Store Value:$Rs, AddrFI:$fi),
(MI AddrFI:$fi, 0, (ValueMod Value:$Rs))>;
class Storexm_add_pat<PatFrag Store, PatFrag Value, PatFrag ImmPred,
PatFrag ValueMod, InstHexagon MI>
: Pat<(Store Value:$Rt, (add (i32 IntRegs:$Rs), ImmPred:$Off)),
(MI IntRegs:$Rs, imm:$Off, (ValueMod Value:$Rt))>;
class Storexm_simple_pat<PatFrag Store, PatFrag Value, PatFrag ValueMod,
InstHexagon MI>
: Pat<(Store Value:$Rt, (i32 IntRegs:$Rs)),
(MI IntRegs:$Rs, 0, (ValueMod Value:$Rt))>;
multiclass Storex_pat<PatFrag Store, PatFrag Value, PatLeaf ImmPred,
InstHexagon MI> {
def: Storex_fi_pat <Store, Value, MI>;
def: Storex_add_pat <Store, Value, ImmPred, MI>;
}
multiclass Storexm_pat<PatFrag Store, PatFrag Value, PatLeaf ImmPred,
PatFrag ValueMod, InstHexagon MI> {
def: Storexm_fi_pat <Store, Value, ValueMod, MI>;
def: Storexm_add_pat <Store, Value, ImmPred, ValueMod, MI>;
}
// Regular stores in the DAG have two operands: value and address.
// Atomic stores also have two, but they are reversed: address, value.
// To use atomic stores with the patterns, they need to have their operands
@ -3397,47 +3419,38 @@ multiclass Storex_pat<PatFrag Store, PatFrag Value, PatLeaf ImmPred,
class SwapSt<PatFrag F>
: PatFrag<(ops node:$val, node:$ptr), F.Fragment>;
let AddedComplexity = 20 in {
defm: Storex_pat<truncstorei8, I32, s11_0ExtPred, S2_storerb_io>;
defm: Storex_pat<truncstorei16, I32, s11_1ExtPred, S2_storerh_io>;
defm: Storex_pat<store, I32, s11_2ExtPred, S2_storeri_io>;
defm: Storex_pat<store, I64, s11_3ExtPred, S2_storerd_io>;
defm: Storex_pat<SwapSt<atomic_store_8>, I32, s11_0ExtPred, S2_storerb_io>;
defm: Storex_pat<SwapSt<atomic_store_16>, I32, s11_1ExtPred, S2_storerh_io>;
defm: Storex_pat<SwapSt<atomic_store_32>, I32, s11_2ExtPred, S2_storeri_io>;
defm: Storex_pat<SwapSt<atomic_store_64>, I64, s11_3ExtPred, S2_storerd_io>;
}
// Simple patterns should be tried with the least priority.
def: Storex_simple_pat<truncstorei8, I32, S2_storerb_io>;
def: Storex_simple_pat<truncstorei16, I32, S2_storerh_io>;
def: Storex_simple_pat<store, I32, S2_storeri_io>;
def: Storex_simple_pat<store, I64, S2_storerd_io>;
def: Storex_simple_pat<SwapSt<atomic_store_8>, I32, S2_storerb_io>;
def: Storex_simple_pat<SwapSt<atomic_store_16>, I32, S2_storerh_io>;
def: Storex_simple_pat<SwapSt<atomic_store_32>, I32, S2_storeri_io>;
def: Storex_simple_pat<SwapSt<atomic_store_64>, I64, S2_storerd_io>;
def : Pat<(truncstorei8 (i32 IntRegs:$src1), ADDRriS11_0:$addr),
(S2_storerb_io AddrFI:$addr, 0, (i32 IntRegs:$src1))>;
def : Pat<(truncstorei16 (i32 IntRegs:$src1), ADDRriS11_1:$addr),
(S2_storerh_io AddrFI:$addr, 0, (i32 IntRegs:$src1))>;
def : Pat<(store (i32 IntRegs:$src1), ADDRriS11_2:$addr),
(S2_storeri_io AddrFI:$addr, 0, (i32 IntRegs:$src1))>;
def : Pat<(store (i64 DoubleRegs:$src1), ADDRriS11_3:$addr),
(S2_storerd_io AddrFI:$addr, 0, (i64 DoubleRegs:$src1))>;
let AddedComplexity = 10 in {
def : Pat<(truncstorei8 (i32 IntRegs:$src1), (add IntRegs:$src2,
s11_0ExtPred:$offset)),
(S2_storerb_io IntRegs:$src2, s11_0ImmPred:$offset,
(i32 IntRegs:$src1))>;
def : Pat<(truncstorei16 (i32 IntRegs:$src1), (add IntRegs:$src2,
s11_1ExtPred:$offset)),
(S2_storerh_io IntRegs:$src2, s11_1ImmPred:$offset,
(i32 IntRegs:$src1))>;
def : Pat<(store (i32 IntRegs:$src1), (add IntRegs:$src2,
s11_2ExtPred:$offset)),
(S2_storeri_io IntRegs:$src2, s11_2ImmPred:$offset,
(i32 IntRegs:$src1))>;
def : Pat<(store (i64 DoubleRegs:$src1), (add IntRegs:$src2,
s11_3ExtPred:$offset)),
(S2_storerd_io IntRegs:$src2, s11_3ImmPred:$offset,
(i64 DoubleRegs:$src1))>;
let AddedComplexity = 20 in {
defm: Storexm_pat<truncstorei8, I64, s11_0ExtPred, LoReg, S2_storerb_io>;
defm: Storexm_pat<truncstorei16, I64, s11_1ExtPred, LoReg, S2_storerh_io>;
defm: Storexm_pat<truncstorei32, I64, s11_2ExtPred, LoReg, S2_storeri_io>;
}
// memh(Rx++#s4:1)=Rt.H
def: Storexm_simple_pat<truncstorei8, I64, LoReg, S2_storerb_io>;
def: Storexm_simple_pat<truncstorei16, I64, LoReg, S2_storerh_io>;
def: Storexm_simple_pat<truncstorei32, I64, LoReg, S2_storeri_io>;
// Store predicate.
let isExtendable = 1, opExtendable = 1, isExtentSigned = 1, opExtentBits = 13,

View File

@ -1,17 +1,12 @@
; RUN: llc -march=hexagon -mcpu=hexagonv4 -disable-hexagon-misched < %s | FileCheck %s
; RUN: llc -march=hexagon -disable-hexagon-misched < %s | FileCheck %s
; Check that we generate dual stores in one packet in V4
; CHECK: memw(r{{[0-9]+}}{{ *}}+{{ *}}#{{[0-9]+}}){{ *}}={{ *}}##500000
; CHECK-NEXT: memw(r{{[0-9]+}}{{ *}}+{{ *}}#{{[0-9]+}}){{ *}}={{ *}}##100000
; CHECK-NEXT: }
; CHECK: memw(r{{[0-9]+}}{{ *}}+{{ *}}#{{[0-9]+}}){{ *}}=
; CHECK-NEXT: memw(r{{[0-9]+}}{{ *}}+{{ *}}#{{[0-9]+}}){{ *}}=
@Reg = global i32 0, align 4
define i32 @main() nounwind {
define i32 @main(i32 %v, i32* %p1, i32* %p2) nounwind {
entry:
%number= alloca i32, align 4
store i32 500000, i32* %number, align 4
%number1= alloca i32, align 4
store i32 100000, i32* %number1, align 4
store i32 %v, i32* %p1, align 4
store i32 %v, i32* %p2, align 4
ret i32 0
}