Patchwork [C++11] There can be only one ref qualifier at most.

login
register
mail settings
Submitter Ed Smith-Rowland
Date April 4, 2013, 10:43 p.m.
Message ID <515E022E.6060208@verizon.net>
Download mbox | patch
Permalink /patch/233965/
State New
Headers show

Comments

Ed Smith-Rowland - April 4, 2013, 10:43 p.m.
This is a minor nit on the C++ reference qualifiers.
Obviously, ref quals are not a sequence.
Adding multiple ref quals did error out but this patch cleans up the 
error from a few unexpected tokens to one root cause.
Also _seq is removed from te cp_parser function name.

builds and passes all tests on x86_64-linux.

Ed

gcc/cp:

2013-04-05  Ed Smith-Rowland  <3dw4rd@verizon.net>

	* parser.c (cp_parser_ref_qualifier_seq_opt): Move to
	cp_parser_ref_qualifier_opt.  Error if more than one ref-qual found.

gcc/testsuite:

2013-04-05  Ed Smith-Rowland  <3dw4rd@verizon.net>

	* g++.dg/cpp0x/ref-qual-multi-neg.C: New test.
Jason Merrill - April 5, 2013, 3:20 a.m.
OK, thanks.

Jason

Patch

Index: gcc/cp/parser.c
===================================================================
--- gcc/cp/parser.c	(revision 197464)
+++ gcc/cp/parser.c	(working copy)
@@ -2020,7 +2020,7 @@ 
   (cp_parser *);
 static cp_virt_specifiers cp_parser_virt_specifier_seq_opt
   (cp_parser *);
-static cp_ref_qualifier cp_parser_ref_qualifier_seq_opt
+static cp_ref_qualifier cp_parser_ref_qualifier_opt
   (cp_parser *);
 static tree cp_parser_late_return_type_opt
   (cp_parser *, cp_cv_quals);
@@ -16463,7 +16463,7 @@ 
 		  /* Parse the cv-qualifier-seq.  */
 		  cv_quals = cp_parser_cv_qualifier_seq_opt (parser);
 		  /* Parse the ref-qualifier. */
-		  ref_qual = cp_parser_ref_qualifier_seq_opt (parser);
+		  ref_qual = cp_parser_ref_qualifier_opt (parser);
 		  /* And the exception-specification.  */
 		  exception_specification
 		    = cp_parser_exception_specification_opt (parser);
@@ -17031,25 +17031,46 @@ 
    Returns cp_ref_qualifier representing ref-qualifier. */
 
 static cp_ref_qualifier
-cp_parser_ref_qualifier_seq_opt (cp_parser* parser)
+cp_parser_ref_qualifier_opt (cp_parser* parser)
 {
   cp_ref_qualifier ref_qual = REF_QUAL_NONE;
-  cp_token *token = cp_lexer_peek_token (parser->lexer);
-  switch (token->type)
+
+  while (true)
     {
-    case CPP_AND:
-      ref_qual = REF_QUAL_LVALUE;
-      break;
-    case CPP_AND_AND:
-      ref_qual = REF_QUAL_RVALUE;
-      break;
+      cp_ref_qualifier curr_ref_qual = REF_QUAL_NONE;
+      cp_token *token = cp_lexer_peek_token (parser->lexer);
+
+      switch (token->type)
+	{
+	case CPP_AND:
+	  curr_ref_qual = REF_QUAL_LVALUE;
+	  break;
+
+	case CPP_AND_AND:
+	  curr_ref_qual = REF_QUAL_RVALUE;
+	  break;
+
+	default:
+	  curr_ref_qual = REF_QUAL_NONE;
+	  break;
+	}
+
+      if (!curr_ref_qual)
+	break;
+      else if (ref_qual)
+	{
+	  error_at (token->location, "multiple ref-qualifiers");
+	  cp_lexer_purge_token (parser->lexer);
+	}
+      else
+	{
+	  ref_qual = curr_ref_qual;
+	  cp_lexer_consume_token (parser->lexer);
+	}
     }
 
   if (ref_qual)
-    {
-      maybe_warn_cpp0x (CPP0X_REF_QUALIFIER);
-      cp_lexer_consume_token (parser->lexer);
-    }
+    maybe_warn_cpp0x (CPP0X_REF_QUALIFIER);
 
   return ref_qual;
 }
Index: gcc/testsuite/g++.dg/cpp0x/ref-qual-multi-neg.C
===================================================================
--- gcc/testsuite/g++.dg/cpp0x/ref-qual-multi-neg.C	(revision 0)
+++ gcc/testsuite/g++.dg/cpp0x/ref-qual-multi-neg.C	(revision 0)
@@ -0,0 +1,7 @@ 
+// { dg-require-effective-target c++11 }
+
+class Foo
+{
+public:
+  void bar() const && & { }  // { dg-error "multiple ref-qualifiers" }
+};