This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[PATCH, rtl-optimization]: Fix PR rtl-optimization/33638


Hello!

This patch fixes the problem with -fforce-addr, where we blindly move
calculation of a function argument stack slot address into the
temporary, but we fail to update REG_DEP_TRUE of a function call,
breaking the dependancy chain.

The failure silently propagates up to dse1 pass, where "unused" stack
slot is removed.

The problem starts at expand, where we generate:

;; bscale = __builtin_powf (2.0e+0, (real4) D.1062)
(insn 1310 1309 1311 t.f:61 (set (reg:SF 646)
        (float:SF (reg:SI 182 [ D.1062 ]))) -1 (nil))

(insn 1311 1310 1312 t.f:61 (parallel [
            (set (reg/f:SI 647)
                (plus:SI (reg/f:SI 56 virtual-outgoing-args)
                    (const_int 4 [0x4])))
            (clobber (reg:CC 17 flags))
        ]) -1 (nil))

(insn 1312 1311 1313 t.f:61 (set (mem:SF (reg/f:SI 647) [0 S4 A32])
        (reg:SF 646)) -1 (nil))

(insn 1313 1312 1314 t.f:61 (set (reg:SF 648)
        (mem/u/c/i:SF (symbol_ref/u:SI ("*.LC4") [flags 0x2]) [9 S4
A32])) -1 (nil))

(insn 1314 1313 1315 t.f:61 (set (mem:SF (reg/f:SI 56
virtual-outgoing-args) [0 S4 A32])
        (reg:SF 648)) -1 (nil))

(call_insn/u 1315 1314 1316 t.f:61 (set (reg:SF 8 st)
        (call (mem:QI (symbol_ref:SI ("powf") [flags 0x41]
<function_decl 0xb7c3a200 __builtin_powf>) [0 S1 A8])
            (const_int 8 [0x8]))) -1 (nil)
    (expr_list:REG_DEP_TRUE (use (mem/i:SF (reg/f:SI 56
virtual-outgoing-args) [0 S4 A32]))
        (expr_list:REG_DEP_TRUE (use (mem/i:SF (plus:SI (reg/f:SI 56
virtual-outgoing-args)
                        (const_int 4 [0x4])) [0 S4 A32]))
            (nil))))


Note, that (call_insn 1315) still refers to "mem (v-o-a + 4)", where
the argument's address is in fact "mem (reg 647)", generated in (insn
1311).

There are two solutions to this problem:

a) update call_insn dependencies with temporary pointer or
b) prevent v-o-a and stack_reg referred addresses to be pushed to a temporary.

Attached patch implements b). Patch was bootstrapped and regression
tested on i686-pc-linux-gnu. OK for mainline?

Unfortunatelly, I was not able to construct short test case, but at
the end of the day, the problem looks kind of obvious.

2007-10-08  Uros Bizjak  <ubizjak@gmail.com>

	PR rtl-optimization/33638
	* explow.c (memory_address): When -fforce-addr is in effect,
	do not force addresses using virtual_outgoing_args_rtx or
	stack_pointer_rtx to a temporary register.

Uros.

Index: explow.c
===================================================================
--- explow.c    (revision 129120)
+++ explow.c    (working copy)
@@ -488,7 +488,13 @@ memory_address (enum machine_mode mode,
     win2:
       x = oldx;
     win:
-      if (flag_force_addr && ! cse_not_expected && !REG_P (x))
+      if (flag_force_addr && ! cse_not_expected && !REG_P (x)
+         /* Do not force address using v_o_a and SP to a temporary.
+            The code below does not update function call's argument
+            dependencies, so dependency chain is broken when
+            function arguments are passed on the stack.  */
+         && ! reg_mentioned_p (virtual_outgoing_args_rtx, x)
+         && ! reg_mentioned_p (stack_pointer_rtx, x))
        {
          x = force_operand (x, NULL_RTX);
          x = force_reg (Pmode, x);


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]