summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--gcc/ChangeLog6
-rw-r--r--gcc/combine.c5
-rw-r--r--gcc/testsuite/ChangeLog5
-rw-r--r--gcc/testsuite/gcc.c-torture/execute/pr93908.c54
-rw-r--r--gcc/testsuite/gcc.target/s390/pr93908.c5
5 files changed, 72 insertions, 3 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index 78191a6b8c3..78a8d94eab9 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,9 @@
+2020-02-25 Jakub Jelinek <jakub@redhat.com>
+
+ PR rtl-optimization/93908
+ * combine.c (find_split_point): For store into ZERO_EXTRACT, and src
+ with mask.
+
2019-02-25 Eric Botcazou <ebotcazou@adacore.com>
* dwarf2out.c (dwarf2out_size_function): Run in early-DWARF mode.
diff --git a/gcc/combine.c b/gcc/combine.c
index d44b9c3bf95..58366a6d331 100644
--- a/gcc/combine.c
+++ b/gcc/combine.c
@@ -5130,10 +5130,9 @@ find_split_point (rtx *loc, rtx_insn *insn, bool set_src)
{
HOST_WIDE_INT pos = INTVAL (XEXP (SET_DEST (x), 2));
unsigned HOST_WIDE_INT len = INTVAL (XEXP (SET_DEST (x), 1));
- unsigned HOST_WIDE_INT src = INTVAL (SET_SRC (x));
rtx dest = XEXP (SET_DEST (x), 0);
- unsigned HOST_WIDE_INT mask
- = (HOST_WIDE_INT_1U << len) - 1;
+ unsigned HOST_WIDE_INT mask = (HOST_WIDE_INT_1U << len) - 1;
+ unsigned HOST_WIDE_INT src = INTVAL (SET_SRC (x)) & mask;
rtx or_mask;
if (BITS_BIG_ENDIAN)
diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog
index 3a22e8608df..922ae5c4b7a 100644
--- a/gcc/testsuite/ChangeLog
+++ b/gcc/testsuite/ChangeLog
@@ -1,3 +1,8 @@
+2020-02-25 Jakub Jelinek <jakub@redhat.com>
+
+ PR rtl-optimization/93908
+ * gcc.c-torture/execute/pr93908.c: New test.
+
2019-02-25 Eric Botcazou <ebotcazou@adacore.com>
* gnat.dg/lto24.adb: New test.
diff --git a/gcc/testsuite/gcc.c-torture/execute/pr93908.c b/gcc/testsuite/gcc.c-torture/execute/pr93908.c
new file mode 100644
index 00000000000..cb6e3dda2ea
--- /dev/null
+++ b/gcc/testsuite/gcc.c-torture/execute/pr93908.c
@@ -0,0 +1,54 @@
+/* PR rtl-optimization/93908 */
+
+struct T
+{
+ int b;
+ int c;
+ unsigned short d;
+ unsigned e:1, f:1, g:1, h:2, i:1, j:1;
+ signed int k:2;
+};
+
+struct S
+{
+ struct T s;
+ char c[64];
+} buf[2];
+
+__attribute__ ((noipa)) void *
+baz (void)
+{
+ static int cnt;
+ return (void *) &buf[cnt++];
+}
+
+static inline __attribute__ ((always_inline)) struct T *
+bar (const char *a)
+{
+ struct T *s;
+ s = baz ();
+ s->b = 1;
+ s->k = -1;
+ return s;
+}
+
+__attribute__ ((noipa)) void
+foo (const char *x, struct T **y)
+{
+ struct T *l = bar (x);
+ struct T *m = bar (x);
+ y[0] = l;
+ y[1] = m;
+}
+
+int
+main ()
+{
+ struct T *r[2];
+ foo ("foo", r);
+ if (r[0]->e || r[0]->f || r[0]->g || r[0]->h || r[0]->i || r[0]->j || r[0]->k != -1)
+ __builtin_abort ();
+ if (r[1]->e || r[1]->f || r[1]->g || r[1]->h || r[1]->i || r[1]->j || r[1]->k != -1)
+ __builtin_abort ();
+ return 0;
+}
diff --git a/gcc/testsuite/gcc.target/s390/pr93908.c b/gcc/testsuite/gcc.target/s390/pr93908.c
new file mode 100644
index 00000000000..e5949050a08
--- /dev/null
+++ b/gcc/testsuite/gcc.target/s390/pr93908.c
@@ -0,0 +1,5 @@
+/* PR rtl-optimization/93908 */
+/* { dg-do run { target s390_zEC12_hw } } */
+/* { dg-options "-O2 -march=zEC12 -mtune=z13" } */
+
+#include "../../gcc.c-torture/execute/pr93908.c"