Patchwork [C++] PR 54526

login
register
mail settings
Submitter Paolo Carlini
Date Sept. 25, 2012, 10:47 a.m.
Message ID <50618BB6.5070601@oracle.com>
Download mbox | patch
Permalink /patch/186766/
State New
Headers show

Comments

Paolo Carlini - Sept. 25, 2012, 10:47 a.m.
Hi,

if I understand correctly, in C++11 mode we should simply accept what we 
used to accept only with -fpermissive.

Tested x86_64-linux.

Thanks,
Paolo.

//////////////////////
/cp
2012-09-25  Paolo Carlini  <paolo.carlini@oracle.com>

	PR c++/54526
	* parser.c (cp_parser_template_id): In C++11 mode simply accept
	X<::A>.

/testsuite
2012-09-25  Paolo Carlini  <paolo.carlini@oracle.com>

	PR c++/54526
	* g++.dg/cpp0x/parse2.C: New.
	* g++.dg/parse/error11.C: Adjust.
	* g++.dg/parse/error12.C: Likewise.
Jason Merrill - Sept. 25, 2012, 1:24 p.m.
On 09/25/2012 06:47 AM, Paolo Carlini wrote:
> if I understand correctly, in C++11 mode we should simply accept what we
> used to accept only with -fpermissive.

Let's also mention -std=c++11 as an alternative to -fpermissive in the 
note.  OK with that change.

Jason

Patch

Index: cp/parser.c
===================================================================
--- cp/parser.c	(revision 191695)
+++ cp/parser.c	(working copy)
@@ -12479,9 +12479,11 @@  cp_parser_template_id (cp_parser *parser,
 	  return error_mark_node;
 	}
       /* Otherwise, emit an error about the invalid digraph, but continue
-	 parsing because we got our argument list.  */
-      if (permerror (next_token->location,
-		     "%<<::%> cannot begin a template-argument list"))
+	 parsing because we got our argument list.  In C++11 do not emit
+	 any error, per 2.5/3.  */
+      if (cxx_dialect < cxx0x
+	  && permerror (next_token->location,
+			"%<<::%> cannot begin a template-argument list"))
 	{
 	  static bool hint = false;
 	  inform (next_token->location,
Index: testsuite/g++.dg/parse/error11.C
===================================================================
--- testsuite/g++.dg/parse/error11.C	(revision 191695)
+++ testsuite/g++.dg/parse/error11.C	(working copy)
@@ -16,22 +16,22 @@  struct Foo
   };
 
   void method(void) {
-    typename Foo<::B>::template Nested<::B> n; // { dg-error "17:'<::' cannot begin" "17-begin" }
-// { dg-message "17:'<:' is an alternate spelling" "17-alt" { target *-*-* } 19 }
-// { dg-error "39:'<::' cannot begin" "39-begin" { target *-*-* } 19 }
-// { dg-message "39:'<:' is an alternate spelling" "39-alt" { target *-*-* } 19 }
+    typename Foo<::B>::template Nested<::B> n; // { dg-error "17:'<::' cannot begin" "17-begin" { target c++98 } }
+// { dg-message "17:'<:' is an alternate spelling" "17-alt" { target c++98 } 19 }
+// { dg-error "39:'<::' cannot begin" "39-begin" { target c++98 } 19 }
+// { dg-message "39:'<:' is an alternate spelling" "39-alt" { target c++98 } 19 }
     n.template Nested<B>::method();
-    n.template Nested<::B>::method();  // { dg-error "22:'<::' cannot begin" "error" }
-// { dg-message "22:'<:' is an alternate" "note" { target *-*-* } 24 }
+    n.template Nested<::B>::method();  // { dg-error "22:'<::' cannot begin" "error" { target c++98 } }
+// { dg-message "22:'<:' is an alternate" "note" { target c++98 } 24 }
     Nested<B>::method();
-    Nested<::B>::method(); // { dg-error "11:'<::' cannot begin" "error" }
-// { dg-message "11:'<:' is an alternate" "note" { target *-*-* } 27 }
+    Nested<::B>::method(); // { dg-error "11:'<::' cannot begin" "error" { target c++98 } }
+// { dg-message "11:'<:' is an alternate" "note" { target c++98 } 27 }
   }
 };
 
 template <int N> struct Foo2 {};
-template struct Foo2<::B>;  // { dg-error "21:'<::' cannot begin" "begin" }
-// { dg-message "21:'<:' is an alternate" "alt" { target *-*-* } 33 }
+template struct Foo2<::B>;  // { dg-error "21:'<::' cannot begin" "begin" { target c++98 } }
+// { dg-message "21:'<:' is an alternate" "alt" { target c++98 } 33 }
 // { dg-message "25:type/value mismatch" "mismatch" { target *-*-* } 33 }
 // { dg-error "25:expected a constant" "const" { target *-*-* } 33 }
 
@@ -39,11 +39,11 @@  int value = 0;
 
 void func(void)
 {
-  Foo<::B> f; // { dg-error "cannot begin" "begin" }
-// { dg-message "alternate spelling" "alt" { target *-*-* } 42 }
+  Foo<::B> f; // { dg-error "cannot begin" "begin" { target c++98 } }
+// { dg-message "alternate spelling" "alt" { target c++98 } 42 }
   f.Foo<B>::method();
-  f.Foo<::B>::method(); // { dg-error "8:cannot begin" "begin" }
-// { dg-message "8:alternate spelling" "alt" { target *-*-* } 45 }
+  f.Foo<::B>::method(); // { dg-error "8:cannot begin" "begin" { target c++98 } }
+// { dg-message "8:alternate spelling" "alt" { target c++98 } 45 }
 
   // Check cases where we the token sequence is the correct one, but there
   //  was no digraph or whitespaces in the middle, so we should not emit
@@ -63,9 +63,9 @@  void func(void)
   Foo[::value] = 0;
 }
 
-template struct Foo<::B>; // { dg-error "20:'<::' cannot begin" "begin" }
-// { dg-message "20:is an alternate" "alt" { target *-*-* } 66 }
+template struct Foo<::B>; // { dg-error "20:'<::' cannot begin" "begin" { target c++98 } }
+// { dg-message "20:is an alternate" "alt" { target c++98 } 66 }
 
 // On the first error message, an additional note about the use of 
 //  -fpermissive should be present
-// { dg-message "17:\\(if you use '-fpermissive' G\\+\\+ will accept your code\\)" "-fpermissive" { target *-*-* } 19 }
+// { dg-message "17:\\(if you use '-fpermissive' G\\+\\+ will accept your code\\)" "-fpermissive" { target c++98 } 19 }
Index: testsuite/g++.dg/parse/error12.C
===================================================================
--- testsuite/g++.dg/parse/error12.C	(revision 191695)
+++ testsuite/g++.dg/parse/error12.C	(working copy)
@@ -8,6 +8,6 @@  struct B;
 template <class A>
 struct Foo {};
 
-Foo<::B> foo;   // { dg-bogus "error" "error in place of warning" }
-// { dg-warning "4: '<::' cannot begin a template-argument list" "warning <::" { target *-*-* } 11 }
-// { dg-message "4:'<:' is an alternate spelling for '.'. Insert whitespace between '<' and '::'" "note <:" { target *-*-* } 11 }
+Foo<::B> foo;   // { dg-bogus "error" "error in place of warning" { target c++98 } }
+// { dg-warning "4: '<::' cannot begin a template-argument list" "warning <::" { target c++98 } 11 }
+// { dg-message "4:'<:' is an alternate spelling for '.'. Insert whitespace between '<' and '::'" "note <:" { target c++98 } 11 }
Index: testsuite/g++.dg/cpp0x/parse2.C
===================================================================
--- testsuite/g++.dg/cpp0x/parse2.C	(revision 0)
+++ testsuite/g++.dg/cpp0x/parse2.C	(working copy)
@@ -0,0 +1,12 @@ 
+// PR c++/54526
+// { dg-do compile { target c++11 } }
+
+template <class T>
+struct X { };
+
+struct A { };
+
+int main()
+{
+  X<::A> x;
+}