Commit 5dea0c19 by Paul Brook Committed by Paul Brook

arm.c (output_move_double): Prefer LDRD to LDM.

2008-03-12  Paul Brook  <paul@codesourcery.com>

	gcc/
	* config/arm/arm.c (output_move_double): Prefer LDRD to LDM.

From-SVN: r133160
parent e066eba7
2008-03-12 Paul Brook <paul@codesourcery.com> 2008-03-12 Paul Brook <paul@codesourcery.com>
* config/arm/arm.c (output_move_double): Prefer LDRD to LDM.
2008-03-12 Paul Brook <paul@codesourcery.com>
* config/arm/thumb2.md: Extend peephole to cover 3-arg subs. * config/arm/thumb2.md: Extend peephole to cover 3-arg subs.
(thumb2_alusi3_short): Exclude PLUS and MINUS. (thumb2_alusi3_short): Exclude PLUS and MINUS.
(thumb2_addsi_shortim): Rename ... (thumb2_addsi_shortim): Rename ...
......
...@@ -9869,7 +9869,10 @@ output_move_double (rtx *operands) ...@@ -9869,7 +9869,10 @@ output_move_double (rtx *operands)
switch (GET_CODE (XEXP (operands[1], 0))) switch (GET_CODE (XEXP (operands[1], 0)))
{ {
case REG: case REG:
output_asm_insn ("ldm%(ia%)\t%m1, %M0", operands); if (TARGET_LDRD)
output_asm_insn ("ldr%(d%)\t%0, [%m1]", operands);
else
output_asm_insn ("ldm%(ia%)\t%m1, %M0", operands);
break; break;
case PRE_INC: case PRE_INC:
...@@ -9885,7 +9888,10 @@ output_move_double (rtx *operands) ...@@ -9885,7 +9888,10 @@ output_move_double (rtx *operands)
break; break;
case POST_INC: case POST_INC:
output_asm_insn ("ldm%(ia%)\t%m1!, %M0", operands); if (TARGET_LDRD)
output_asm_insn ("ldr%(d%)\t%0, [%m1], #8", operands);
else
output_asm_insn ("ldm%(ia%)\t%m1!, %M0", operands);
break; break;
case POST_DEC: case POST_DEC:
...@@ -9944,8 +9950,14 @@ output_move_double (rtx *operands) ...@@ -9944,8 +9950,14 @@ output_move_double (rtx *operands)
case LABEL_REF: case LABEL_REF:
case CONST: case CONST:
/* We might be able to use ldrd %0, %1 here. However the range is
different to ldr/adr, and it is broken on some ARMv7-M
implementations. */
output_asm_insn ("adr%?\t%0, %1", operands); output_asm_insn ("adr%?\t%0, %1", operands);
output_asm_insn ("ldm%(ia%)\t%0, %M0", operands); if (TARGET_LDRD)
output_asm_insn ("ldr%(d%)\t%0, [%0]", operands);
else
output_asm_insn ("ldm%(ia%)\t%0, %M0", operands);
break; break;
/* ??? This needs checking for thumb2. */ /* ??? This needs checking for thumb2. */
...@@ -9959,7 +9971,7 @@ output_move_double (rtx *operands) ...@@ -9959,7 +9971,7 @@ output_move_double (rtx *operands)
if (GET_CODE (XEXP (operands[1], 0)) == PLUS) if (GET_CODE (XEXP (operands[1], 0)) == PLUS)
{ {
if (GET_CODE (otherops[2]) == CONST_INT) if (GET_CODE (otherops[2]) == CONST_INT && !TARGET_LDRD)
{ {
switch ((int) INTVAL (otherops[2])) switch ((int) INTVAL (otherops[2]))
{ {
...@@ -10018,6 +10030,9 @@ output_move_double (rtx *operands) ...@@ -10018,6 +10030,9 @@ output_move_double (rtx *operands)
else else
output_asm_insn ("sub%?\t%0, %1, %2", otherops); output_asm_insn ("sub%?\t%0, %1, %2", otherops);
if (TARGET_LDRD)
return "ldr%(d%)\t%0, [%0]";
return "ldm%(ia%)\t%0, %M0"; return "ldm%(ia%)\t%0, %M0";
} }
else else
...@@ -10046,7 +10061,10 @@ output_move_double (rtx *operands) ...@@ -10046,7 +10061,10 @@ output_move_double (rtx *operands)
switch (GET_CODE (XEXP (operands[0], 0))) switch (GET_CODE (XEXP (operands[0], 0)))
{ {
case REG: case REG:
output_asm_insn ("stm%(ia%)\t%m0, %M1", operands); if (TARGET_LDRD)
output_asm_insn ("str%(d%)\t%1, [%m0]", operands);
else
output_asm_insn ("stm%(ia%)\t%m0, %M1", operands);
break; break;
case PRE_INC: case PRE_INC:
...@@ -10062,7 +10080,10 @@ output_move_double (rtx *operands) ...@@ -10062,7 +10080,10 @@ output_move_double (rtx *operands)
break; break;
case POST_INC: case POST_INC:
output_asm_insn ("stm%(ia%)\t%m0!, %M1", operands); if (TARGET_LDRD)
output_asm_insn ("str%(d%)\t%1, [%m0], #8", operands);
else
output_asm_insn ("stm%(ia%)\t%m0!, %M1", operands);
break; break;
case POST_DEC: case POST_DEC:
...@@ -10106,7 +10127,7 @@ output_move_double (rtx *operands) ...@@ -10106,7 +10127,7 @@ output_move_double (rtx *operands)
case PLUS: case PLUS:
otherops[2] = XEXP (XEXP (operands[0], 0), 1); otherops[2] = XEXP (XEXP (operands[0], 0), 1);
if (GET_CODE (otherops[2]) == CONST_INT) if (GET_CODE (otherops[2]) == CONST_INT && !TARGET_LDRD)
{ {
switch ((int) INTVAL (XEXP (XEXP (operands[0], 0), 1))) switch ((int) INTVAL (XEXP (XEXP (operands[0], 0), 1)))
{ {
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment