On 11/1/24 5:07 AM, Simon Martin wrote:
Since r10-3793-g1a37b6d9a7e57c, we ICE upon the following valid code
with -std=c++17 and above

=== cut here ===
struct Base {
   unsigned int *intarray;
};
template <typename T> struct Sub : public Base {
   bool Get(int i) {
     return (Base::intarray[++i] == 0);
   }
};
=== cut here ===

The problem is that from c++17 on, we use -fstrong-eval-order and need
to wrap the array access expression into a SAVE_EXPR, and end up calling
contains_placeholder_p with a SCOPE_REF, that it does not handle well.

This patch fixes this by skipping the first operand of SCOPE_REFs in
contains_placeholder_p.

Code in gcc/ shouldn't refer to tree codes from cp-tree.def.

We probably shouldn't do the strong-eval-order transformation when processing_template_decl anyway.

Successfully tested on x86_64-pc-linux-gnu.

        PR c++/117158

gcc/ChangeLog:

        * tree.cc (contains_placeholder_p): Skip the first operand of
        SCOPE_REFs.

gcc/testsuite/ChangeLog:

        * g++.dg/parse/crash77.C: New test.

---
  gcc/testsuite/g++.dg/parse/crash77.C | 13 +++++++++++++
  gcc/tree.cc                          |  3 +++
  2 files changed, 16 insertions(+)
  create mode 100644 gcc/testsuite/g++.dg/parse/crash77.C

diff --git a/gcc/testsuite/g++.dg/parse/crash77.C 
b/gcc/testsuite/g++.dg/parse/crash77.C
new file mode 100644
index 00000000000..25a426fa6d6
--- /dev/null
+++ b/gcc/testsuite/g++.dg/parse/crash77.C
@@ -0,0 +1,13 @@
+// PR c++/117158
+// { dg-do "compile" }
+
+struct Base {
+  unsigned int *intarray;
+};
+
+template <typename T>
+struct Sub : public Base {
+    bool Get(int i) {
+       return (Base::intarray[++i] == 0);
+    }
+};
diff --git a/gcc/tree.cc b/gcc/tree.cc
index b4c059d3b0d..7f8911002d0 100644
--- a/gcc/tree.cc
+++ b/gcc/tree.cc
@@ -4122,6 +4122,9 @@ contains_placeholder_p (const_tree exp)
    if (!exp)
      return false;
+ if (TREE_CODE (exp) == SCOPE_REF)
+    exp = TREE_OPERAND (exp, 1);
+
    code = TREE_CODE (exp);
    if (code == PLACEHOLDER_EXPR)
      return true;

Reply via email to