re PR c++/54359 ([C++0x] decltype in member function's trailing return type when...
authorJason Merrill <jason@redhat.com>
Sun, 17 Mar 2013 02:38:21 +0000 (22:38 -0400)
committerJason Merrill <jason@gcc.gnu.org>
Sun, 17 Mar 2013 02:38:21 +0000 (22:38 -0400)
PR c++/54359
* parser.c (cp_parser_direct_declarator): Fix late return
for out-of-class defn of member function.

From-SVN: r196740

gcc/cp/ChangeLog
gcc/cp/parser.c
gcc/testsuite/g++.dg/cpp0x/trailing8.C [new file with mode: 0644]

index 22d408b..739795b 100644 (file)
@@ -1,5 +1,9 @@
 2013-03-16  Jason Merrill  <jason@redhat.com>
 
+       PR c++/54359
+       * parser.c (cp_parser_direct_declarator): Fix late return
+       for out-of-class defn of member function.
+
        PR c++/55357
        * semantics.c (maybe_add_lambda_conv_op): Clear DECL_NAME of copied
        parms to avoid duplicate -Wshadow warnings.
index 3f56ff1..66684dc 100644 (file)
@@ -16367,6 +16367,8 @@ cp_parser_direct_declarator (cp_parser* parser,
                  tree exception_specification;
                  tree late_return;
                  tree attrs;
+                 bool memfn = (member_p || (pushed_scope
+                                            && CLASS_TYPE_P (pushed_scope)));
 
                  is_declarator = true;
 
@@ -16383,7 +16385,7 @@ cp_parser_direct_declarator (cp_parser* parser,
                  attrs = cp_parser_std_attribute_spec_seq (parser);
 
                  late_return = (cp_parser_late_return_type_opt
-                                (parser, member_p ? cv_quals : -1));
+                                (parser, memfn ? cv_quals : -1));
 
                  /* Parse the virt-specifier-seq.  */
                  virt_specifiers = cp_parser_virt_specifier_seq_opt (parser);
diff --git a/gcc/testsuite/g++.dg/cpp0x/trailing8.C b/gcc/testsuite/g++.dg/cpp0x/trailing8.C
new file mode 100644 (file)
index 0000000..304845e
--- /dev/null
@@ -0,0 +1,25 @@
+// PR c++/54359
+// { dg-require-effective-target c++11 }
+
+int& ref(int& x) { return x; }
+const int& ref(const int& x) { return x; }
+
+class A {
+    int x;
+    int f() const;
+    auto test1() const -> decltype(this);
+    auto test2() const -> decltype(ref(x));
+    auto test3() const -> decltype(f());
+};
+
+auto A::test1() const -> decltype(this) {
+    return this;
+}
+
+auto A::test2() const -> decltype(ref(x)) {
+    return ref(x);
+}
+
+auto A::test3() const -> decltype(f()) {
+    return f();
+}