OSDN Git Service

2012-02-28 Richard Guenther <rguenther@suse.de>
authorrguenth <rguenth@138bc75d-0d04-0410-961f-82ee72b054a4>
Tue, 28 Feb 2012 09:15:49 +0000 (09:15 +0000)
committerrguenth <rguenth@138bc75d-0d04-0410-961f-82ee72b054a4>
Tue, 28 Feb 2012 09:15:49 +0000 (09:15 +0000)
PR tree-optimization/52402
* ipa-prop.c (ipa_modify_call_arguments): Properly use
mis-aligned types when creating the accesses at the call site.

* gcc.dg/torture/pr52402.c: New testcase.

git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@184619 138bc75d-0d04-0410-961f-82ee72b054a4

gcc/ChangeLog
gcc/ipa-prop.c
gcc/testsuite/ChangeLog
gcc/testsuite/gcc.dg/torture/pr52402.c [new file with mode: 0644]

index a89a8ff..24df23a 100644 (file)
@@ -1,3 +1,9 @@
+2012-02-28  Richard Guenther  <rguenther@suse.de>
+
+       PR tree-optimization/52402
+       * ipa-prop.c (ipa_modify_call_arguments): Properly use
+       mis-aligned types when creating the accesses at the call site.
+
 2012-02-28  Georg-Johann Lay  <avr@gjlay.de>
 
        * config/avr/builtins.def: New file.
index 6d76adb..3856793 100644 (file)
@@ -2508,9 +2508,27 @@ ipa_modify_call_arguments (struct cgraph_edge *cs, gimple stmt,
                }
            }
 
-         expr = fold_build2_loc (loc, MEM_REF, adj->type, base, off);
-         if (adj->by_ref)
-           expr = build_fold_addr_expr (expr);
+         if (!adj->by_ref)
+           {
+             tree type = adj->type;
+             unsigned int align;
+             unsigned HOST_WIDE_INT misalign;
+             align = get_pointer_alignment_1 (base, &misalign);
+             misalign += (double_int_sext (tree_to_double_int (off),
+                                           TYPE_PRECISION (TREE_TYPE (off))).low
+                          * BITS_PER_UNIT);
+             misalign = misalign & (align - 1);
+             if (misalign != 0)
+               align = (misalign & -misalign);
+             if (align < TYPE_ALIGN (type))
+               type = build_aligned_type (type, align);
+             expr = fold_build2_loc (loc, MEM_REF, type, base, off);
+           }
+         else
+           {
+             expr = fold_build2_loc (loc, MEM_REF, adj->type, base, off);
+             expr = build_fold_addr_expr (expr);
+           }
 
          expr = force_gimple_operand_gsi (&gsi, expr,
                                           adj->by_ref
index ee4e5f3..7a3af58 100644 (file)
@@ -1,5 +1,10 @@
 2012-02-28  Richard Guenther  <rguenther@suse.de>
 
+       PR tree-optimization/52402
+       * gcc.dg/torture/pr52402.c: New testcase.
+
+2012-02-28  Richard Guenther  <rguenther@suse.de>
+
        PR lto/52400
        * g++.dg/lto/pr52400_0.C: New testcase.
 
diff --git a/gcc/testsuite/gcc.dg/torture/pr52402.c b/gcc/testsuite/gcc.dg/torture/pr52402.c
new file mode 100644 (file)
index 0000000..5bd51fb
--- /dev/null
@@ -0,0 +1,28 @@
+/* { dg-do run } */
+
+typedef int v4si __attribute__((vector_size(16)));
+struct T { v4si i[2]; int j; } __attribute__((packed));
+
+static v4si __attribute__((noinline))
+foo (struct T t)
+{
+  return t.i[0];
+}
+
+static struct T *__attribute__((noinline))
+init ()
+{
+  char *p = __builtin_malloc (sizeof (struct T) + 1);
+  p++;
+  __builtin_memset (p, 1, sizeof (struct T));
+  return (struct T *)p;
+}
+
+int main()
+{
+  struct T *p;
+  p = init ();
+  if (foo (*p)[0] != 0x01010101)
+    __builtin_abort ();
+  return 0;
+}