diff options
-rw-r--r-- | gcc/ChangeLog | 6 | ||||
-rw-r--r-- | gcc/rtlanal.c | 28 |
2 files changed, 29 insertions, 5 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 594b247..e0a9cc0 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,9 @@ +2017-06-30 Richard Earnshaw <rearnsha@arm.com> + + * rtlanal.c (insn_rtx_cost): If a parallel contains exactly one + comparison set and one other set, use the cost of the non-comparison + set. + 2017-06-30 Nathan Sidwell <nathan@acm.org> * ggc.h: Replace all 'static inline' with plain 'inline'. Fix diff --git a/gcc/rtlanal.c b/gcc/rtlanal.c index bf4183e..9bfae8c 100644 --- a/gcc/rtlanal.c +++ b/gcc/rtlanal.c @@ -5263,23 +5263,41 @@ insn_rtx_cost (rtx pat, bool speed) int i, cost; rtx set; - /* Extract the single set rtx from the instruction pattern. - We can't use single_set since we only have the pattern. */ + /* Extract the single set rtx from the instruction pattern. We + can't use single_set since we only have the pattern. We also + consider PARALLELs of a normal set and a single comparison. In + that case we use the cost of the non-comparison SET operation, + which is most-likely to be the real cost of this operation. */ if (GET_CODE (pat) == SET) set = pat; else if (GET_CODE (pat) == PARALLEL) { set = NULL_RTX; + rtx comparison = NULL_RTX; + for (i = 0; i < XVECLEN (pat, 0); i++) { rtx x = XVECEXP (pat, 0, i); if (GET_CODE (x) == SET) { - if (set) - return 0; - set = x; + if (GET_CODE (SET_SRC (x)) == COMPARE) + { + if (comparison) + return 0; + comparison = x; + } + else + { + if (set) + return 0; + set = x; + } } } + + if (!set && comparison) + set = comparison; + if (!set) return 0; } |