From d1d116197acb550c188ac6a36fe5ab664d4d667f Mon Sep 17 00:00:00 2001 From: jason Date: Wed, 2 Nov 2011 20:16:56 +0000 Subject: * parser.c (cp_parser_decl_specifier_seq): Change "C++0x" to "C++11" in warnings. (cp_lexer_get_preprocessor_token): Likewise. (cp_parser_binary_expression): Likewise. git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@180795 138bc75d-0d04-0410-961f-82ee72b054a4 --- gcc/cp/parser.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) (limited to 'gcc/cp/parser.c') diff --git a/gcc/cp/parser.c b/gcc/cp/parser.c index 63f92620886..e543e870550 100644 --- a/gcc/cp/parser.c +++ b/gcc/cp/parser.c @@ -744,7 +744,7 @@ cp_lexer_get_preprocessor_token (cp_lexer *lexer, cp_token *token) /* Warn about the C++0x keyword (but still treat it as an identifier). */ warning (OPT_Wc__0x_compat, - "identifier %qE will become a keyword in C++0x", + "identifier %qE is a keyword in C++11", token->u.value); /* Clear out the C_RID_CODE so we don't warn about this @@ -7198,8 +7198,8 @@ cp_parser_binary_expression (cp_parser* parser, bool cast_p, && !parser->greater_than_is_operator_p) { if (warning_at (token->location, OPT_Wc__0x_compat, - "%<>>%> operator will be treated as" - " two right angle brackets in C++0x")) + "%<>>%> operator is treated as" + " two right angle brackets in C++11")) inform (token->location, "suggest parentheses around %<>>%> expression"); } @@ -10528,7 +10528,7 @@ cp_parser_decl_specifier_seq (cp_parser* parser, /* Complain about `auto' as a storage specifier, if we're complaining about C++0x compatibility. */ warning_at (token->location, OPT_Wc__0x_compat, "%" - " will change meaning in C++0x; please remove it"); + " changes meaning in C++11; please remove it"); /* Set the storage class anyway. */ cp_parser_set_storage_class (parser, decl_specs, RID_AUTO, -- cgit v1.2.1 From 4d6f53f47cd008d01308c1f051a91aa3e629b541 Mon Sep 17 00:00:00 2001 From: jason Date: Fri, 4 Nov 2011 16:16:09 +0000 Subject: PR c++/50941 * parser.c (cp_parser_userdef_string_literal): Fix string length. git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@180961 138bc75d-0d04-0410-961f-82ee72b054a4 --- gcc/cp/parser.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'gcc/cp/parser.c') diff --git a/gcc/cp/parser.c b/gcc/cp/parser.c index e543e870550..811b2faf32e 100644 --- a/gcc/cp/parser.c +++ b/gcc/cp/parser.c @@ -3681,8 +3681,8 @@ cp_parser_userdef_string_literal (cp_token *token) suffix_id = USERDEF_LITERAL_SUFFIX_ID (literal); name = cp_literal_operator_id (IDENTIFIER_POINTER (suffix_id)); value = USERDEF_LITERAL_VALUE (literal); - len = TREE_STRING_LENGTH (value) - 1; - + len = TREE_STRING_LENGTH (value) + / TREE_INT_CST_LOW (TYPE_SIZE_UNIT (TREE_TYPE (TREE_TYPE (value)))) - 1; /* Build up a call to the user-defined operator */ /* Lookup the name we got back from the id-expression. */ vec = make_tree_vector (); -- cgit v1.2.1 From ee239d9146b1867efae233ef57cc282c0f197275 Mon Sep 17 00:00:00 2001 From: jason Date: Fri, 4 Nov 2011 17:38:16 +0000 Subject: * parser.c (cp_parser_enumerator_list): Do not warn about trailing commas in C++0x mode. git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@180967 138bc75d-0d04-0410-961f-82ee72b054a4 --- gcc/cp/parser.c | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) (limited to 'gcc/cp/parser.c') diff --git a/gcc/cp/parser.c b/gcc/cp/parser.c index 811b2faf32e..2798eb7e7cb 100644 --- a/gcc/cp/parser.c +++ b/gcc/cp/parser.c @@ -14058,6 +14058,7 @@ cp_parser_elaborated_type_specifier (cp_parser* parser, enum-specifier: enum-head { enumerator-list [opt] } + enum-head { enumerator-list , } [C++0x] enum-head: enum-key identifier [opt] enum-base [opt] @@ -14077,6 +14078,8 @@ cp_parser_elaborated_type_specifier (cp_parser* parser, GNU Extensions: enum-key attributes[opt] identifier [opt] enum-base [opt] { enumerator-list [opt] }attributes[opt] + enum-key attributes[opt] identifier [opt] enum-base [opt] + { enumerator-list, }attributes[opt] [C++0x] Returns an ENUM_TYPE representing the enumeration, or NULL_TREE if the token stream isn't an enum-specifier after all. */ @@ -14416,8 +14419,9 @@ cp_parser_enumerator_list (cp_parser* parser, tree type) /* If the next token is a `}', there is a trailing comma. */ if (cp_lexer_next_token_is (parser->lexer, CPP_CLOSE_BRACE)) { - if (!in_system_header) - pedwarn (input_location, OPT_pedantic, "comma at end of enumerator list"); + if (cxx_dialect < cxx0x && !in_system_header) + pedwarn (input_location, OPT_pedantic, + "comma at end of enumerator list"); break; } } -- cgit v1.2.1 From 370478b178a3bdf01988c16782c90add8aea26aa Mon Sep 17 00:00:00 2001 From: dodji Date: Mon, 7 Nov 2011 21:28:50 +0000 Subject: PR c++/45114 - Support C++11 alias-declaration gcc/cp/ * cp-tree.h (TYPE_DECL_ALIAS_P, TYPE_ALIAS_P) (DECL_TYPE_TEMPLATE_P, DECL_ALIAS_TEMPLATE_P): New accessor macros. (TYPE_TEMPLATE_INFO): Get template info of an alias template specializations from its TYPE_DECL. (SET_TYPE_TEMPLATE_INFO): Set template info of alias template specializations into its TYPE_DECL. (DECL_CLASS_TEMPLATE_P): Re-write using the new DECL_TYPE_TEMPLATE_P. (enum cp_decl_spec): Add new ds_alias enumerator. (alias_type_or_template_p, alias_template_specialization_p): Declare new functions. * parser.c (cp_parser_alias_declaration): New static function. (cp_parser_check_decl_spec): Add "using" name for the `alias' declspec. (cp_parser_type_name): Update comment. Support simple-template-id representing alias template specializations in c++0x mode. (cp_parser_qualifying_entity): Update comment. Use cp_parser_type_name. (cp_parser_block_declaration): Handle alias-declaration in c++11. Update comment. (cp_parser_template_id): Handle specializations of alias templates. (cp_parser_member_declaration): Add alias-declaration production to comment. Support alias-declarations. (cp_parser_template_declaration_after_export): Handle alias templates in c++11. * decl.c (make_typename_type, make_unbound_class_template): Accept alias templates. (grokdeclarator): Set TYPE_DECL_ALIAS_P on alias declarations. * decl2.c (grokfield): Move template creation after setting up the TYPE_DECL of the alias, so that the TEMPLATE_DECL of the alias template actually carries the right type-id of the alias declaration. * pt.c (alias_type_or_template_p) (alias_template_specialization_p): Define new public functions. (maybe_process_partial_specialization): Reject partial specializations of alias templates. (primary_template_instantiation_p): Consider alias template instantiations. (push_template_decl_real): Assert that TYPE_DECLs of alias templates are different from those of class template. Store template info onto the TYPE_DECL of the alias template. (convert_template_argument): Strip aliases from template arguments. (lookup_template_class_1): Handle the creation of the specialization of an alias template. (tsubst_decl): Create a substituted copy of the TYPE_DECL of an member alias template. (tsubst): Handle substituting into the type of an alias template. Handle substituting UNBOUND_CLASS_TEMPLATE into BOUND_TEMPLATE_TEMPLATE_PARM. (do_type_instantiation): Better diagnostics when trying to explicitely instantiate a non-class template. * search.c (lookup_field_1, lookup_field_r): Support looking up alias templates. * semantics.c (finish_template_type): For instantiations of alias templates, return the TYPE_DECL of the actual alias and not the one of the aliased type. * error.c (dump_alias_template_specialization): New static function. (dump_type): Handle printing of alias templates and their specializations. templates. (dump_aggr_type): For specialization of alias templates, fetch arguments from the right place. (dump_decl): Print an alias-declaration like `using decl = type;' (dump_template_decl): Support printing of alias templates. gcc/testsuite/ * g++.dg/cpp0x/alias-decl-0.C: New test case. * g++.dg/cpp0x/alias-decl-1.C: Likewise. * g++.dg/cpp0x/alias-decl-3.C: Likewise. * g++.dg/cpp0x/alias-decl-4.C: Likewise. * g++.dg/cpp0x/alias-decl-6.C: Likewise. * g++.dg/cpp0x/alias-decl-7.C: Likewise. * g++.dg/cpp0x/alias-decl-8.C: Likewise. * g++.dg/cpp0x/alias-decl-9.C: Likewise. * g++.dg/cpp0x/alias-decl-10.C: Likewise. * g++.dg/ext/alias-decl-attr1.C: Likewise. * g++.dg/ext/alias-decl-attr2.C: Likewise. * g++.dg/ext/alias-decl-attr3.C: Likewise. * g++.dg/ext/alias-decl-attr4.C: Likewise. git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@181118 138bc75d-0d04-0410-961f-82ee72b054a4 --- gcc/cp/parser.c | 141 +++++++++++++++++++++++++++++++++++++++++++++++++++----- 1 file changed, 129 insertions(+), 12 deletions(-) (limited to 'gcc/cp/parser.c') diff --git a/gcc/cp/parser.c b/gcc/cp/parser.c index 2798eb7e7cb..fa0117ec3e4 100644 --- a/gcc/cp/parser.c +++ b/gcc/cp/parser.c @@ -1935,6 +1935,8 @@ static bool cp_parser_using_declaration (cp_parser *, bool); static void cp_parser_using_directive (cp_parser *); +static tree cp_parser_alias_declaration + (cp_parser *); static void cp_parser_asm_definition (cp_parser *); static void cp_parser_linkage_specification @@ -2509,6 +2511,7 @@ cp_parser_check_decl_spec (cp_decl_specifier_seq *decl_specs, "explicit", "friend", "typedef", + "using", "constexpr", "__complex", "__thread" @@ -5135,7 +5138,7 @@ cp_parser_nested_name_specifier (cp_parser *parser, this is either a class-name or a namespace-name (which corresponds to the class-or-namespace-name production in the grammar). For C++0x, it can also be a type-name that refers to an enumeration - type. + type or a simple-template-id. TYPENAME_KEYWORD_P is TRUE iff the `typename' keyword is in effect. TEMPLATE_KEYWORD_P is TRUE iff the `template' keyword is in effect. @@ -5211,8 +5214,8 @@ cp_parser_qualifying_entity (cp_parser *parser, /* Parse tentatively. */ cp_parser_parse_tentatively (parser); - /* Parse a typedef-name or enum-name. */ - scope = cp_parser_nonclass_name (parser); + /* Parse a type-name */ + scope = cp_parser_type_name (parser); /* "If the name found does not designate a namespace or a class, enumeration, or dependent type, the program is ill-formed." @@ -10150,8 +10153,8 @@ cp_parser_block_declaration (cp_parser *parser, namespace-alias-definition. */ else if (token1->keyword == RID_NAMESPACE) cp_parser_namespace_alias_definition (parser); - /* If the next keyword is `using', we have either a - using-declaration or a using-directive. */ + /* If the next keyword is `using', we have a + using-declaration, a using-directive, or an alias-declaration. */ else if (token1->keyword == RID_USING) { cp_token *token2; @@ -10163,6 +10166,14 @@ cp_parser_block_declaration (cp_parser *parser, token2 = cp_lexer_peek_nth_token (parser->lexer, 2); if (token2->keyword == RID_NAMESPACE) cp_parser_using_directive (parser); + /* If the second token after 'using' is '=', then we have an + alias-declaration. */ + else if (cxx_dialect >= cxx0x + && token2->type == CPP_NAME + && ((cp_lexer_peek_nth_token (parser->lexer, 3)->type == CPP_EQ) + || (cp_lexer_peek_nth_token (parser->lexer, 3)->keyword + == RID_ATTRIBUTE))) + cp_parser_alias_declaration (parser); /* Otherwise, it's a using-declaration. */ else cp_parser_using_declaration (parser, @@ -12343,7 +12354,7 @@ cp_parser_template_id (cp_parser *parser, /* Build a representation of the specialization. */ if (TREE_CODE (templ) == IDENTIFIER_NODE) template_id = build_min_nt (TEMPLATE_ID_EXPR, templ, arguments); - else if (DECL_CLASS_TEMPLATE_P (templ) + else if (DECL_TYPE_TEMPLATE_P (templ) || DECL_TEMPLATE_TEMPLATE_PARM_P (templ)) { bool entering_scope; @@ -13611,6 +13622,7 @@ cp_parser_simple_type_specifier (cp_parser* parser, class-name enum-name typedef-name + simple-template-id [in c++0x] enum-name: identifier @@ -13638,8 +13650,37 @@ cp_parser_type_name (cp_parser* parser) /* If it's not a class-name, keep looking. */ if (!cp_parser_parse_definitely (parser)) { - /* It must be a typedef-name or an enum-name. */ - return cp_parser_nonclass_name (parser); + if (cxx_dialect < cxx0x) + /* It must be a typedef-name or an enum-name. */ + return cp_parser_nonclass_name (parser); + + cp_parser_parse_tentatively (parser); + /* It is either a simple-template-id representing an + instantiation of an alias template... */ + type_decl = cp_parser_template_id (parser, + /*template_keyword_p=*/false, + /*check_dependency_p=*/false, + /*is_declaration=*/false); + /* Note that this must be an instantiation of an alias template + because [temp.names]/6 says: + + A template-id that names an alias template specialization + is a type-name. + + Whereas [temp.names]/7 says: + + A simple-template-id that names a class template + specialization is a class-name. */ + if (type_decl != NULL_TREE + && TREE_CODE (type_decl) == TYPE_DECL + && TYPE_DECL_ALIAS_P (type_decl)) + gcc_assert (DECL_TEMPLATE_INSTANTIATION (type_decl)); + else + cp_parser_simulate_error (parser); + + if (!cp_parser_parse_definitely (parser)) + /* ... Or a typedef-name or an enum-name. */ + return cp_parser_nonclass_name (parser); } return type_decl; @@ -14835,6 +14876,63 @@ cp_parser_using_declaration (cp_parser* parser, return true; } +/* Parse an alias-declaration. + + alias-declaration: + using identifier attribute-specifier-seq [opt] = type-id */ + +static tree +cp_parser_alias_declaration (cp_parser* parser) +{ + tree id, type, decl, dummy, attributes; + location_t id_location; + cp_declarator *declarator; + cp_decl_specifier_seq decl_specs; + + /* Look for the `using' keyword. */ + cp_parser_require_keyword (parser, RID_USING, RT_USING); + id_location = cp_lexer_peek_token (parser->lexer)->location; + id = cp_parser_identifier (parser); + attributes = cp_parser_attributes_opt (parser); + cp_parser_require (parser, CPP_EQ, RT_EQ); + + type = cp_parser_type_id (parser); + + /* A typedef-name can also be introduced by an alias-declaration. The + identifier following the using keyword becomes a typedef-name. It has + the same semantics as if it were introduced by the typedef + specifier. In particular, it does not define a new type and it shall + not appear in the type-id. */ + + clear_decl_specs (&decl_specs); + decl_specs.type = type; + decl_specs.attributes = attributes; + ++decl_specs.specs[(int) ds_typedef]; + ++decl_specs.specs[(int) ds_alias]; + + declarator = make_id_declarator (NULL_TREE, id, sfk_none); + declarator->id_loc = id_location; + + if (at_class_scope_p ()) + decl = grokfield (declarator, &decl_specs, NULL_TREE, false, + NULL_TREE, attributes); + else + decl = start_decl (declarator, &decl_specs, 0, + attributes, NULL_TREE, &dummy); + if (decl == error_mark_node) + return decl; + + cp_finish_decl (decl, NULL_TREE, 0, NULL_TREE, 0); + + /* If decl is a template, return its TEMPLATE_DECL so that it gets + added into the symbol table; otherwise, return the TYPE_DECL. */ + if (DECL_LANG_SPECIFIC (decl) + && DECL_TEMPLATE_INFO (decl) + && PRIMARY_TEMPLATE_P (DECL_TI_TEMPLATE (decl))) + decl = DECL_TI_TEMPLATE (decl); + return decl; +} + /* Parse a using-directive. using-directive: @@ -18532,6 +18630,7 @@ cp_parser_member_specification_opt (cp_parser* parser) :: [opt] nested-name-specifier template [opt] unqualified-id ; using-declaration template-declaration + alias-declaration member-declarator-list: member-declarator @@ -18599,10 +18698,25 @@ cp_parser_member_declaration (cp_parser* parser) /* Check for a using-declaration. */ if (cp_lexer_next_token_is_keyword (parser->lexer, RID_USING)) { - /* Parse the using-declaration. */ - cp_parser_using_declaration (parser, - /*access_declaration_p=*/false); - return; + if (cxx_dialect < cxx0x) + { + /* Parse the using-declaration. */ + cp_parser_using_declaration (parser, + /*access_declaration_p=*/false); + return; + } + else + { + tree decl; + cp_parser_parse_tentatively (parser); + decl = cp_parser_alias_declaration (parser); + if (cp_parser_parse_definitely (parser)) + finish_member_declaration (decl); + else + cp_parser_using_declaration (parser, + /*access_declaration_p=*/false); + return; + } } /* Check for @defs. */ @@ -20893,6 +21007,9 @@ cp_parser_template_declaration_after_export (cp_parser* parser, bool member_p) if (cp_lexer_next_token_is_keyword (parser->lexer, RID_TEMPLATE)) cp_parser_template_declaration_after_export (parser, member_p); + else if (cxx_dialect >= cxx0x + && cp_lexer_next_token_is_keyword (parser->lexer, RID_USING)) + decl = cp_parser_alias_declaration (parser); else { /* There are no access checks when parsing a template, as we do not -- cgit v1.2.1