Update preferred_stack_boundary only when expanding function call
authorH.J. Lu <hongjiu.lu@intel.com>
Fri, 14 Jun 2019 16:24:56 +0000 (16:24 +0000)
committerH.J. Lu <hjl@gcc.gnu.org>
Fri, 14 Jun 2019 16:24:56 +0000 (09:24 -0700)
locate_and_pad_parm is called when expanding function call from
initialize_argument_information and when generating function body
from assign_parm_find_entry_rtl:

  /* Remember if the outgoing parameter requires extra alignment on the
     calling function side.  */
  if (crtl->stack_alignment_needed < boundary)
    crtl->stack_alignment_needed = boundary;
  if (crtl->preferred_stack_boundary < boundary)
    crtl->preferred_stack_boundary = boundary;

stack_alignment_needed and preferred_stack_boundary should be updated
only when expanding function call, not when generating function body.

Add update_stack_alignment_for_call to update stack alignment when
outgoing parameter is passed in the stack.

gcc/

PR rtl-optimization/90765
* calls.c (update_stack_alignment_for_call): New function.
(expand_call): Call update_stack_alignment_for_call when
outgoing parameter is passed in the stack.
(emit_library_call_value_1): Likewise.
* function.c (locate_and_pad_parm): Don't update
stack_alignment_needed and preferred_stack_boundary.

gcc/testsuite/

PR rtl-optimization/90765
* gcc.target/i386/pr90765-1.c: New test.
* gcc.target/i386/pr90765-2.c: Likewise.

From-SVN: r272296

gcc/ChangeLog
gcc/calls.c
gcc/function.c
gcc/testsuite/ChangeLog
gcc/testsuite/gcc.target/i386/pr90765-1.c [new file with mode: 0644]
gcc/testsuite/gcc.target/i386/pr90765-2.c [new file with mode: 0644]

index deba76066594090bf205e5295b2ed5d7ba3d1cf4..de1753ea05e41e11dc8a269b2f5fe321871c2dcc 100644 (file)
@@ -1,4 +1,14 @@
-2019-06-14  Hongtao Liu  <hongtao.liu@intel.com>
+2019-06-14  H.J. Lu  <hongjiu.lu@intel.com>
+
+       PR rtl-optimization/90765
+       * calls.c (update_stack_alignment_for_call): New function.
+       (expand_call): Call update_stack_alignment_for_call when
+       outgoing parameter is passed in the stack.
+       (emit_library_call_value_1): Likewise.
+       * function.c (locate_and_pad_parm): Don't update
+       stack_alignment_needed and preferred_stack_boundary.
+
+2019-06-14  H.J. Lu  <hongjiu.lu@intel.com>
 
        PR target/90877
        * config/i386/i386-features.c
index c8a426800411bc320dd1821e59bb599560c8cb07..6ab138e7bb04b21a385cd9095fc014165b8753b5 100644 (file)
@@ -3226,6 +3226,19 @@ can_implement_as_sibling_call_p (tree exp,
   return true;
 }
 
+/* Update stack alignment when the parameter is passed in the stack
+   since the outgoing parameter requires extra alignment on the calling
+   function side. */
+
+static void
+update_stack_alignment_for_call (struct locate_and_pad_arg_data *locate)
+{
+  if (crtl->stack_alignment_needed < locate->boundary)
+    crtl->stack_alignment_needed = locate->boundary;
+  if (crtl->preferred_stack_boundary < locate->boundary)
+    crtl->preferred_stack_boundary = locate->boundary;
+}
+
 /* Generate all the code for a CALL_EXPR exp
    and return an rtx for its value.
    Store the value in TARGET (specified as an rtx) if convenient.
@@ -3703,6 +3716,12 @@ expand_call (tree exp, rtx target, int ignore)
   /* Ensure current function's preferred stack boundary is at least
      what we need.  Stack alignment may also increase preferred stack
      boundary.  */
+  for (i = 0; i < num_actuals; i++)
+    if (reg_parm_stack_space > 0
+       || args[i].reg == 0
+       || args[i].partial != 0
+       || args[i].pass_on_stack)
+      update_stack_alignment_for_call (&args[i].locate);
   if (crtl->preferred_stack_boundary < preferred_stack_boundary)
     crtl->preferred_stack_boundary = preferred_stack_boundary;
   else
@@ -4961,6 +4980,12 @@ emit_library_call_value_1 (int retval, rtx orgfun, rtx value,
       targetm.calls.function_arg_advance (args_so_far, mode, (tree) 0, true);
     }
 
+  for (int i = 0; i < nargs; i++)
+    if (reg_parm_stack_space > 0
+       || argvec[i].reg == 0
+       || argvec[i].partial != 0)
+      update_stack_alignment_for_call (&argvec[i].locate);
+
   /* If this machine requires an external definition for library
      functions, write one out.  */
   assemble_external_libcall (fun);
index e30ee259becc1cffb312fa186339ffd86a60de1c..45b65dc0fd2f18e0925e729fc10291c3c25169d9 100644 (file)
@@ -4021,13 +4021,6 @@ locate_and_pad_parm (machine_mode passed_mode, tree type, int in_regs,
        }
     }
 
-  /* Remember if the outgoing parameter requires extra alignment on the
-     calling function side.  */
-  if (crtl->stack_alignment_needed < boundary)
-    crtl->stack_alignment_needed = boundary;
-  if (crtl->preferred_stack_boundary < boundary)
-    crtl->preferred_stack_boundary = boundary;
-
   if (ARGS_GROW_DOWNWARD)
     {
       locate->slot_offset.constant = -initial_offset_ptr->constant;
index c7604d6dc4ddafe149c4768633870c09c2960d78..3d64fb04d10a1a325e9a3f511532555cdc782303 100644 (file)
@@ -1,3 +1,9 @@
+2019-06-14  H.J. Lu  <hongjiu.lu@intel.com>
+
+       PR rtl-optimization/90765
+       * gcc.target/i386/pr90765-1.c: New test.
+       * gcc.target/i386/pr90765-2.c: Likewise.
+
 2019-06-14  Marek Polacek  <polacek@redhat.com>
 
        PR c++/90884 - stray note with -Wctor-dtor-privacy.
diff --git a/gcc/testsuite/gcc.target/i386/pr90765-1.c b/gcc/testsuite/gcc.target/i386/pr90765-1.c
new file mode 100644 (file)
index 0000000..178c3ff
--- /dev/null
@@ -0,0 +1,11 @@
+/* { dg-do compile } */
+/* { dg-options "-O2 -mavx512f" } */
+/* { dg-final { scan-assembler-not "and\[lq\]?\[\\t \]*\\$-64,\[\\t \]*%\[re\]?sp" } } */
+
+typedef int __v16si __attribute__ ((__vector_size__ (64)));
+
+void
+foo (__v16si x, int i0, int i1, int i2, int i3, int i4, int i5, __v16si *p)
+{
+  *p = x;
+}
diff --git a/gcc/testsuite/gcc.target/i386/pr90765-2.c b/gcc/testsuite/gcc.target/i386/pr90765-2.c
new file mode 100644 (file)
index 0000000..45cf1f0
--- /dev/null
@@ -0,0 +1,18 @@
+/* { dg-do compile } */
+/* { dg-options "-O2 -mavx512f" } */
+/* { dg-final { scan-assembler "and\[lq\]?\[\\t \]*\\$-64,\[\\t \]*%\[re\]?sp" } } */
+/* { dg-skip-if "" { x86_64-*-mingw* } } */
+
+typedef int __v16si __attribute__ ((__vector_size__ (64)));
+
+extern void foo (__v16si, __v16si, __v16si, __v16si, __v16si, __v16si,
+                __v16si, __v16si, __v16si, int, int, int, int, int,
+                int, __v16si *);
+
+extern __v16si x, y;
+
+void
+bar (void)
+{
+  foo (x, x, x, x, x, x, x, x, x, 0, 1, 2, 3, 4, 5, &y);
+}