]> git.ipfire.org Git - thirdparty/gcc.git/commitdiff
c++: fix propagating REF_PARENTHESIZED_P [PR116379]
authorMarek Polacek <polacek@redhat.com>
Thu, 13 Feb 2025 20:56:16 +0000 (15:56 -0500)
committerMarek Polacek <polacek@redhat.com>
Fri, 14 Feb 2025 13:08:53 +0000 (08:08 -0500)
Here we have:

  template<typename T>
  struct X{
      T val;
      decltype(auto) value(){
  return (val);
      }
  };

where the return type of value should be 'int &' since '(val)' is an
expression, not a name, and decltype(auto) performs the type deduction
using the decltype rules.

The problem is that we weren't propagating REF_PARENTHESIZED_P
correctly: the return value of finish_non_static_data_member in this
test was a REFERENCE_REF_P, so we didn't set the flag.  We should
use force_paren_expr like below.

PR c++/116379

gcc/cp/ChangeLog:

* pt.cc (tsubst_expr) <COMPONENT_REF>: Use force_paren_expr to set
REF_PARENTHESIZED_P.

gcc/testsuite/ChangeLog:

* g++.dg/cpp1y/decltype-auto9.C: New test.

Reviewed-by: Jason Merrill <jason@redhat.com>
gcc/cp/pt.cc
gcc/testsuite/g++.dg/cpp1y/decltype-auto9.C [new file with mode: 0644]

index a2fc8813e9deb2d156433bfa80da404690de1448..5706a3987c34d09905c5acfaf55148b3bb094d19 100644 (file)
@@ -21712,8 +21712,8 @@ tsubst_expr (tree t, tree args, tsubst_flags_t complain, tree in_decl)
          {
            r = finish_non_static_data_member (member, object, NULL_TREE,
                                               complain);
-           if (TREE_CODE (r) == COMPONENT_REF)
-             REF_PARENTHESIZED_P (r) = REF_PARENTHESIZED_P (t);
+           if (REF_PARENTHESIZED_P (t))
+             force_paren_expr (r);
            RETURN (r);
          }
        else if (type_dependent_expression_p (object))
diff --git a/gcc/testsuite/g++.dg/cpp1y/decltype-auto9.C b/gcc/testsuite/g++.dg/cpp1y/decltype-auto9.C
new file mode 100644 (file)
index 0000000..1ccf95a
--- /dev/null
@@ -0,0 +1,15 @@
+// PR c++/116379
+// { dg-do compile { target c++14 } }
+
+template<typename T>
+struct X {
+  T val;
+  decltype(auto) value() { return (val); }
+};
+
+int main() {
+  int i = 0;
+  X<int&&> x{ static_cast<int&&>(i) };
+  using type = decltype(x.value());
+  using type = int&;
+}