aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorKyrylo Tkachov <kyrylo.tkachov@arm.com>2014-11-24 11:37:34 +0000
committerKyrylo Tkachov <ktkachov@gcc.gnu.org>2014-11-24 11:37:34 +0000
commitd8354ad712d12de5b9f5ebfd1ea5f47ffb0da01e (patch)
treeaa17303c7e2d2d4da3b47ab67c5f9d78024a20d0 /gcc
parentcd0cb23271a815fa6472029791c76cd604e19708 (diff)
downloadgcc-d8354ad712d12de5b9f5ebfd1ea5f47ffb0da01e.zip
gcc-d8354ad712d12de5b9f5ebfd1ea5f47ffb0da01e.tar.gz
gcc-d8354ad712d12de5b9f5ebfd1ea5f47ffb0da01e.tar.bz2
[AArch64][4/5] Implement fusion of ARDP+LDR
* config/aarch64/aarch64.c (AARCH64_FUSE_ADRP_LDR): Define. (cortexa53_tunings): Specify AARCH64_FUSE_ADRP_LDR in fuseable_ops. (aarch_macro_fusion_pair_p): Handle AARCH64_FUSE_ADRP_LDR. From-SVN: r218014
Diffstat (limited to 'gcc')
-rw-r--r--gcc/ChangeLog6
-rw-r--r--gcc/config/aarch64/aarch64.c35
2 files changed, 40 insertions, 1 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index d58c8c3..60a6b22 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,5 +1,11 @@
2014-11-24 Kyrylo Tkachov <kyrylo.tkachov@arm.com>
+ * config/aarch64/aarch64.c (AARCH64_FUSE_ADRP_LDR): Define.
+ (cortexa53_tunings): Specify AARCH64_FUSE_ADRP_LDR in fuseable_ops.
+ (aarch_macro_fusion_pair_p): Handle AARCH64_FUSE_ADRP_LDR.
+
+2014-11-24 Kyrylo Tkachov <kyrylo.tkachov@arm.com>
+
* config/aarch64/aarch64.c (AARCH64_FUSE_MOVK_MOVK): Define.
(cortexa53_tunings): Specify AARCH64_FUSE_MOVK_MOVK in fuseable_ops.
(cortexa57_tunings): Likewise.
diff --git a/gcc/config/aarch64/aarch64.c b/gcc/config/aarch64/aarch64.c
index 5598b5b..ee9a962 100644
--- a/gcc/config/aarch64/aarch64.c
+++ b/gcc/config/aarch64/aarch64.c
@@ -309,6 +309,7 @@ static const struct cpu_vector_cost cortexa57_vector_cost =
#define AARCH64_FUSE_MOV_MOVK (1 << 0)
#define AARCH64_FUSE_ADRP_ADD (1 << 1)
#define AARCH64_FUSE_MOVK_MOVK (1 << 2)
+#define AARCH64_FUSE_ADRP_LDR (1 << 3)
#if HAVE_DESIGNATED_INITIALIZERS && GCC_VERSION >= 2007
__extension__
@@ -332,7 +333,8 @@ static const struct tune_params cortexa53_tunings =
&generic_vector_cost,
NAMED_PARAM (memmov_cost, 4),
NAMED_PARAM (issue_rate, 2),
- NAMED_PARAM (fuseable_ops, (AARCH64_FUSE_MOV_MOVK | AARCH64_FUSE_ADRP_ADD | AARCH64_FUSE_MOVK_MOVK))
+ NAMED_PARAM (fuseable_ops, (AARCH64_FUSE_MOV_MOVK | AARCH64_FUSE_ADRP_ADD
+ | AARCH64_FUSE_MOVK_MOVK | AARCH64_FUSE_ADRP_LDR))
};
static const struct tune_params cortexa57_tunings =
@@ -10485,6 +10487,37 @@ aarch_macro_fusion_pair_p (rtx_insn *prev, rtx_insn *curr)
return true;
}
+ if (simple_sets_p
+ && (aarch64_tune_params->fuseable_ops & AARCH64_FUSE_ADRP_LDR))
+ {
+ /* We're trying to match:
+ prev (adrp) == (set (reg r0)
+ (high (symbol_ref ("SYM"))))
+ curr (ldr) == (set (reg r1)
+ (mem (lo_sum (reg r0)
+ (symbol_ref ("SYM")))))
+ or
+ curr (ldr) == (set (reg r1)
+ (zero_extend (mem
+ (lo_sum (reg r0)
+ (symbol_ref ("SYM")))))) */
+ if (satisfies_constraint_Ush (SET_SRC (prev_set))
+ && REG_P (SET_DEST (prev_set)) && REG_P (SET_DEST (curr_set)))
+ {
+ rtx curr_src = SET_SRC (curr_set);
+
+ if (GET_CODE (curr_src) == ZERO_EXTEND)
+ curr_src = XEXP (curr_src, 0);
+
+ if (MEM_P (curr_src) && GET_CODE (XEXP (curr_src, 0)) == LO_SUM
+ && REG_P (XEXP (XEXP (curr_src, 0), 0))
+ && REGNO (XEXP (XEXP (curr_src, 0), 0))
+ == REGNO (SET_DEST (prev_set))
+ && rtx_equal_p (XEXP (XEXP (curr_src, 0), 1),
+ XEXP (SET_SRC (prev_set), 0)))
+ return true;
+ }
+ }
return false;
}