diff options
Diffstat (limited to 'sys-devel/gcc/files/gcc-14.0.0_pre20231015-pycryptodome-ice.patch')
-rw-r--r-- | sys-devel/gcc/files/gcc-14.0.0_pre20231015-pycryptodome-ice.patch | 212 |
1 files changed, 212 insertions, 0 deletions
diff --git a/sys-devel/gcc/files/gcc-14.0.0_pre20231015-pycryptodome-ice.patch b/sys-devel/gcc/files/gcc-14.0.0_pre20231015-pycryptodome-ice.patch new file mode 100644 index 000000000000..377f68511f78 --- /dev/null +++ b/sys-devel/gcc/files/gcc-14.0.0_pre20231015-pycryptodome-ice.patch @@ -0,0 +1,212 @@ +https://gcc.gnu.org/PR111845 +https://gcc.gnu.org/git/?p=gcc.git;a=commit;h=f1744dd50bb1661c98b694ff907cb0a1be4f6134 + +From f1744dd50bb1661c98b694ff907cb0a1be4f6134 Mon Sep 17 00:00:00 2001 +From: Jakub Jelinek <jakub@redhat.com> +Date: Wed, 18 Oct 2023 12:37:40 +0200 +Subject: [PATCH] tree-ssa-math-opts: Fix up match_uaddc_usubc [PR111845] + +GCC ICEs on the first testcase. Successful match_uaddc_usubc ends up with +some dead stmts which DCE will remove (hopefully) later all. +The ICE is because one of the dead stmts refers to a freed SSA_NAME. +The code already gsi_removes a couple of stmts in the + /* Remove some statements which can't be kept in the IL because they + use SSA_NAME whose setter is going to be removed too. */ +section for the same reason (the reason for the freed SSA_NAMEs is that +we don't really have a replacement for those cases - all we have after +a match is combined overflow from the addition/subtraction of 2 operands + a +[0, 1] carry in, but not the individual overflows from the former 2 +additions), but for the last (most significant) limb case, where we try +to match x = op1 + op2 + carry1 + carry2; or +x = op1 - op2 - carry1 - carry2; we just gsi_replace the final stmt, but +left around the 2 temporary stmts as dead; if we were unlucky enough that +those referenced the carry flag that went away, it ICEs. + +So, the following patch remembers those temporary statements (rather than +trying to rediscover them more expensively) and removes them before the +final one is replaced. + +While working on it, I've noticed we didn't support all the reassociated +possibilities of writing the addition of 4 operands or subtracting 3 +operands from one, we supported e.g. +x = ((op1 + op2) + op3) + op4; +x = op1 + ((op2 + op3) + op4); +but not +x = (op1 + (op2 + op3)) + op4; +x = op1 + (op2 + (op3 + op4)); +Fixed by the change to inspect also rhs[2] when rhs[1] didn't yield what +we were searching for (if non-NULL) - rhs[0] is inspected in the first +loop and has different handling for the MINUS_EXPR case. + +2023-10-18 Jakub Jelinek <jakub@redhat.com> + + PR tree-optimization/111845 + * tree-ssa-math-opts.cc (match_uaddc_usubc): Remember temporary + statements for the 4 operand addition or subtraction of 3 operands + from 1 operand cases and remove them when successful. Look for + nested additions even from rhs[2], not just rhs[1]. + + * gcc.dg/pr111845.c: New test. + * gcc.target/i386/pr111845.c: New test. +--- + gcc/testsuite/gcc.dg/pr111845.c | 16 ++++++++ + gcc/testsuite/gcc.target/i386/pr111845.c | 47 +++++++++++++++++++++++ + gcc/tree-ssa-math-opts.cc | 48 +++++++++++++++--------- + 3 files changed, 94 insertions(+), 17 deletions(-) + create mode 100644 gcc/testsuite/gcc.dg/pr111845.c + create mode 100644 gcc/testsuite/gcc.target/i386/pr111845.c + +diff --git a/gcc/testsuite/gcc.dg/pr111845.c b/gcc/testsuite/gcc.dg/pr111845.c +new file mode 100644 +index 000000000000..1bcb4f88e6f1 +--- /dev/null ++++ b/gcc/testsuite/gcc.dg/pr111845.c +@@ -0,0 +1,16 @@ ++/* PR tree-optimization/111845 */ ++/* { dg-do compile } */ ++/* { dg-options "-O2 --param tree-reassoc-width=2" } */ ++ ++int a, b; ++unsigned int c, d, e; ++ ++void ++foo (int x) ++{ ++ b += d; ++ c += b < d; ++ b += e = a < x; ++ c += b; ++ c += b < e; ++} +diff --git a/gcc/testsuite/gcc.target/i386/pr111845.c b/gcc/testsuite/gcc.target/i386/pr111845.c +new file mode 100644 +index 000000000000..d52110a40422 +--- /dev/null ++++ b/gcc/testsuite/gcc.target/i386/pr111845.c +@@ -0,0 +1,47 @@ ++/* PR tree-optimization/111845 */ ++/* { dg-do compile } */ ++/* { dg-options "-O2 -g -masm=att" } */ ++/* { dg-final { scan-assembler-times "\tadcq\t" 8 { target lp64 } } } */ ++/* { dg-final { scan-assembler-times "\tadcl\t" 8 { target ia32 } } } */ ++ ++unsigned long l, m; ++ ++__attribute__((noipa)) void ++foo (unsigned long x, unsigned long y, unsigned long h, unsigned long i, int a, int b) ++{ ++ unsigned long c, d; ++ unsigned long e = __builtin_add_overflow (x, y, &c); ++ unsigned long f = __builtin_add_overflow (c, a < b, &d); ++ m = ((h + i) + e) + f; ++ l = d; ++} ++ ++__attribute__((noipa)) void ++bar (unsigned long x, unsigned long y, unsigned long h, unsigned long i, int a, int b) ++{ ++ unsigned long c, d; ++ unsigned long e = __builtin_add_overflow (x, y, &c); ++ unsigned long f = __builtin_add_overflow (c, a < b, &d); ++ m = (h + (i + e)) + f; ++ l = d; ++} ++ ++__attribute__((noipa)) void ++baz (unsigned long x, unsigned long y, unsigned long h, unsigned long i, int a, int b) ++{ ++ unsigned long c, d; ++ unsigned long e = __builtin_add_overflow (x, y, &c); ++ unsigned long f = __builtin_add_overflow (c, a < b, &d); ++ m = h + (i + (e + f)); ++ l = d; ++} ++ ++__attribute__((noipa)) void ++qux (unsigned long x, unsigned long y, unsigned long h, unsigned long i, int a, int b) ++{ ++ unsigned long c, d; ++ unsigned long e = __builtin_add_overflow (x, y, &c); ++ unsigned long f = __builtin_add_overflow (c, a < b, &d); ++ m = h + ((i + e) + f); ++ l = d; ++} +diff --git a/gcc/tree-ssa-math-opts.cc b/gcc/tree-ssa-math-opts.cc +index 51c14d6bad9f..363f31646691 100644 +--- a/gcc/tree-ssa-math-opts.cc ++++ b/gcc/tree-ssa-math-opts.cc +@@ -4581,6 +4581,7 @@ match_uaddc_usubc (gimple_stmt_iterator *gsi, gimple *stmt, tree_code code) + if (!INTEGRAL_TYPE_P (type) || !TYPE_UNSIGNED (type)) + return false; + ++ auto_vec<gimple *, 2> temp_stmts; + if (code != BIT_IOR_EXPR && code != BIT_XOR_EXPR) + { + /* If overflow flag is ignored on the MSB limb, we can end up with +@@ -4615,26 +4616,29 @@ match_uaddc_usubc (gimple_stmt_iterator *gsi, gimple *stmt, tree_code code) + rhs[0] = gimple_assign_rhs1 (g); + tree &r = rhs[2] ? rhs[3] : rhs[2]; + r = r2; ++ temp_stmts.quick_push (g); + } + else + break; + } +- while (TREE_CODE (rhs[1]) == SSA_NAME && !rhs[3]) +- { +- gimple *g = SSA_NAME_DEF_STMT (rhs[1]); +- if (has_single_use (rhs[1]) +- && is_gimple_assign (g) +- && gimple_assign_rhs_code (g) == PLUS_EXPR) +- { +- rhs[1] = gimple_assign_rhs1 (g); +- if (rhs[2]) +- rhs[3] = gimple_assign_rhs2 (g); +- else +- rhs[2] = gimple_assign_rhs2 (g); +- } +- else +- break; +- } ++ for (int i = 1; i <= 2; ++i) ++ while (rhs[i] && TREE_CODE (rhs[i]) == SSA_NAME && !rhs[3]) ++ { ++ gimple *g = SSA_NAME_DEF_STMT (rhs[i]); ++ if (has_single_use (rhs[i]) ++ && is_gimple_assign (g) ++ && gimple_assign_rhs_code (g) == PLUS_EXPR) ++ { ++ rhs[i] = gimple_assign_rhs1 (g); ++ if (rhs[2]) ++ rhs[3] = gimple_assign_rhs2 (g); ++ else ++ rhs[2] = gimple_assign_rhs2 (g); ++ temp_stmts.quick_push (g); ++ } ++ else ++ break; ++ } + /* If there are just 3 addends or one minuend and two subtrahends, + check for UADDC or USUBC being pattern recognized earlier. + Say r = op1 + op2 + ovf1 + ovf2; where the (ovf1 + ovf2) part +@@ -5039,7 +5043,17 @@ match_uaddc_usubc (gimple_stmt_iterator *gsi, gimple *stmt, tree_code code) + g = gimple_build_assign (ilhs, IMAGPART_EXPR, + build1 (IMAGPART_EXPR, TREE_TYPE (ilhs), nlhs)); + if (rhs[2]) +- gsi_insert_before (gsi, g, GSI_SAME_STMT); ++ { ++ gsi_insert_before (gsi, g, GSI_SAME_STMT); ++ /* Remove some further statements which can't be kept in the IL because ++ they can use SSA_NAMEs whose setter is going to be removed too. */ ++ while (temp_stmts.length ()) ++ { ++ g = temp_stmts.pop (); ++ gsi2 = gsi_for_stmt (g); ++ gsi_remove (&gsi2, true); ++ } ++ } + else + gsi_replace (gsi, g, true); + /* Remove some statements which can't be kept in the IL because they +-- +2.39.3 |