Hello! When moving precompute_register_parameters, I didn't notice that the call was wrapped with NO_DEFER_POP/OK_DEFER_POP.
Attached patch fixes this oversight. 2015-07-17 Uros Bizjak <ubiz...@gmail.com> PR rtl-optimization/66891 * calls.c (expand_call): Wrap precompute_register_parameters with NO_DEFER_POP/OK_DEFER_POP to prevent deferred pops. testsuite/ChangeLog: 2015-07-17 Uros Bizjak <ubiz...@gmail.com> PR target/66891 * gcc.target/i386/pr66891.c: New test. Bootstrapped and regression tested on x86_64-linux-gnu {,-m32}, committed to mainline SVN as obvious. Uros.
Index: calls.c =================================================================== --- calls.c (revision 225857) +++ calls.c (working copy) @@ -3144,6 +3144,10 @@ expand_call (tree exp, rtx target, int ignore) compute_argument_addresses (args, argblock, num_actuals); + /* Stack is properly aligned, pops can't safely be deferred during + the evaluation of the arguments. */ + NO_DEFER_POP; + /* Precompute all register parameters. It isn't safe to compute anything once we have started filling any specific hard regs. TLS symbols sometimes need a call to resolve. Precompute @@ -3151,6 +3155,8 @@ expand_call (tree exp, rtx target, int ignore) to avoid unaligned stack in the called function. */ precompute_register_parameters (num_actuals, args, ®_parm_seen); + OK_DEFER_POP; + /* Perform stack alignment before the first push (the last arg). */ if (argblock == 0 && adjusted_args_size.constant > reg_parm_stack_space Index: testsuite/gcc.target/i386/pr66891.c =================================================================== --- testsuite/gcc.target/i386/pr66891.c (revision 0) +++ testsuite/gcc.target/i386/pr66891.c (revision 0) @@ -0,0 +1,16 @@ +/* { dg-do compile { target ia32 } } */ +/* { dg-options "-O2" } */ + +__attribute__((__stdcall__)) void fn1(); + +int a; + +static void fn2() { + for (;;) + ; +} + +void fn3() { + fn1(0); + fn2(a == 0); +}