?? c-parse.y
字號:
/* YACC parser for C syntax and for Objective C. -*-c-*- Copyright (C) 1987, 88, 89, 92, 93, 94, 1995 Free Software Foundation, Inc.This file is part of GNU CC.GNU CC is free software; you can redistribute it and/or modifyit under the terms of the GNU General Public License as published bythe Free Software Foundation; either version 2, or (at your option)any later version.GNU CC is distributed in the hope that it will be useful,but WITHOUT ANY WARRANTY; without even the implied warranty ofMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See theGNU General Public License for more details.You should have received a copy of the GNU General Public Licensealong with GNU CC; see the file COPYING. If not, write tothe Free Software Foundation, 59 Temple Place - Suite 330,Boston, MA 02111-1307, USA. *//* This file defines the grammar of C and that of Objective C. ifobjc ... end ifobjc conditionals contain code for Objective C only. ifc ... end ifc conditionals contain code for C only. Sed commands in Makefile.in are used to convert this file into c-parse.y and into objc-parse.y. *//* To whomever it may concern: I have heard that such a thing was once written by AT&T, but I have never seen it. */%expect 34/* These are the 23 conflicts you should get in parse.output; the state numbers may vary if minor changes in the grammar are made.State 42 contains 1 shift/reduce conflict. (Two ways to parse ATTRIBUTE.)State 44 contains 1 shift/reduce conflict. (Two ways to recover from error.)State 103 contains 1 shift/reduce conflict. (Two ways to recover from error.)State 110 contains 1 shift/reduce conflict. (Two ways to parse ATTRIBUTE.)State 111 contains 1 shift/reduce conflict. (Two ways to recover from error.)State 115 contains 1 shift/reduce conflict. (Two ways to recover from error.)State 132 contains 1 shift/reduce conflict. (See comment at component_decl.)State 180 contains 1 shift/reduce conflict. (Two ways to parse ATTRIBUTE.)State 194 contains 2 shift/reduce conflict. (Four ways to parse this.)State 202 contains 1 shift/reduce conflict. (Two ways to recover from error.)State 214 contains 1 shift/reduce conflict. (Two ways to recover from error.)State 220 contains 1 shift/reduce conflict. (Two ways to recover from error.)State 304 contains 2 shift/reduce conflicts. (Four ways to parse this.)State 335 contains 2 shift/reduce conflicts. (Four ways to parse this.)State 347 contains 1 shift/reduce conflict. (Two ways to parse ATTRIBUTES.)State 352 contains 1 shift/reduce conflict. (Two ways to parse ATTRIBUTES.)State 383 contains 2 shift/reduce conflicts. (Four ways to parse this.)State 434 contains 2 shift/reduce conflicts. (Four ways to parse this.) */%{#include <stdio.h>#include <errno.h>#include <setjmp.h>#include "config.h"#include "tree.h"#include "input.h"#include "c-lex.h"#include "c-tree.h"#include "flags.h"#ifdef MULTIBYTE_CHARS#include <stdlib.h>#include <locale.h>#endif/* Since parsers are distinct for each language, put the language string definition here. */char *language_string = "GNU C";#ifndef errnoextern int errno;#endifvoid yyerror ();/* Like YYERROR but do call yyerror. */#define YYERROR1 { yyerror ("syntax error"); YYERROR; }/* Cause the `yydebug' variable to be defined. */#define YYDEBUG 1%}%start program%union {long itype; tree ttype; enum tree_code code; char *filename; int lineno; int ends_in_label; }/* All identifiers that are not reserved words and are not declared typedefs in the current block */%token IDENTIFIER/* All identifiers that are declared typedefs in the current block. In some contexts, they are treated just like IDENTIFIER, but they can also serve as typespecs in declarations. */%token TYPENAME/* Reserved words that specify storage class. yylval contains an IDENTIFIER_NODE which indicates which one. */%token SCSPEC/* Reserved words that specify type. yylval contains an IDENTIFIER_NODE which indicates which one. */%token TYPESPEC/* Reserved words that qualify type: "const" or "volatile". yylval contains an IDENTIFIER_NODE which indicates which one. */%token TYPE_QUAL/* Character or numeric constants. yylval is the node for the constant. */%token CONSTANT/* String constants in raw form. yylval is a STRING_CST node. */%token STRING/* "...", used for functions with variable arglists. */%token ELLIPSIS/* the reserved words *//* SCO include files test "ASM", so use something else. */%token SIZEOF ENUM STRUCT UNION IF ELSE WHILE DO FOR SWITCH CASE DEFAULT%token BREAK CONTINUE RETURN GOTO ASM_KEYWORD TYPEOF ALIGNOF%token ATTRIBUTE EXTENSION LABEL%token REALPART IMAGPART/* Add precedence rules to solve dangling else s/r conflict */%nonassoc IF%nonassoc ELSE/* Define the operator tokens and their precedences. The value is an integer because, if used, it is the tree code to use in the expression made from the operator. */%right <code> ASSIGN '='%right <code> '?' ':'%left <code> OROR%left <code> ANDAND%left <code> '|'%left <code> '^'%left <code> '&'%left <code> EQCOMPARE%left <code> ARITHCOMPARE%left <code> LSHIFT RSHIFT%left <code> '+' '-'%left <code> '*' '/' '%'%right <code> UNARY PLUSPLUS MINUSMINUS%left HYPERUNARY%left <code> POINTSAT '.' '(' '['/* The Objective-C keywords. These are included in C and in Objective C, so that the token codes are the same in both. */%token INTERFACE IMPLEMENTATION END SELECTOR DEFS ENCODE%token CLASSNAME PUBLIC PRIVATE PROTECTED PROTOCOL OBJECTNAME CLASS ALIAS/* Objective-C string constants in raw form. yylval is an OBJC_STRING_CST node. */%token OBJC_STRING%type <code> unop%type <ttype> identifier IDENTIFIER TYPENAME CONSTANT expr nonnull_exprlist exprlist%type <ttype> expr_no_commas cast_expr unary_expr primary string STRING%type <ttype> typed_declspecs reserved_declspecs%type <ttype> typed_typespecs reserved_typespecquals%type <ttype> declmods typespec typespecqual_reserved%type <ttype> SCSPEC TYPESPEC TYPE_QUAL nonempty_type_quals maybe_type_qual%type <ttype> initdecls notype_initdecls initdcl notype_initdcl%type <ttype> init maybeasm%type <ttype> asm_operands nonnull_asm_operands asm_operand asm_clobbers%type <ttype> maybe_attribute attributes attribute attribute_list attrib%type <ttype> any_word%type <ttype> compstmt%type <ttype> declarator%type <ttype> notype_declarator after_type_declarator%type <ttype> parm_declarator%type <ttype> structsp component_decl_list component_decl_list2%type <ttype> component_decl components component_declarator%type <ttype> enumlist enumerator%type <ttype> typename absdcl absdcl1 type_quals%type <ttype> xexpr parms parm identifiers%type <ttype> parmlist parmlist_1 parmlist_2%type <ttype> parmlist_or_identifiers parmlist_or_identifiers_1%type <ttype> identifiers_or_typenames%type <itype> setspecs%type <ends_in_label> lineno_stmt_or_label lineno_stmt_or_labels stmt_or_label%type <filename> save_filename%type <lineno> save_lineno%{/* Number of statements (loosely speaking) seen so far. */static int stmt_count;/* Input file and line number of the end of the body of last simple_if; used by the stmt-rule immediately after simple_if returns. */static char *if_stmt_file;static int if_stmt_line;/* List of types and structure classes of the current declaration. */static tree current_declspecs;static tree prefix_attributes = NULL_TREE;/* Stack of saved values of current_declspecs and prefix_attributes. */static tree declspec_stack;/* 1 if we explained undeclared var errors. */static int undeclared_variable_notice;/* Tell yyparse how to print a token's value, if yydebug is set. */#define YYPRINT(FILE,YYCHAR,YYLVAL) yyprint(FILE,YYCHAR,YYLVAL)extern void yyprint ();%}%%program: /* empty */ { if (pedantic) pedwarn ("ANSI C forbids an empty source file"); finish_file (); } | extdefs { /* In case there were missing closebraces, get us back to the global binding level. */ while (! global_bindings_p ()) poplevel (0, 0, 0); finish_file (); } ;/* the reason for the strange actions in this rule is so that notype_initdecls when reached via datadef can find a valid list of type and sc specs in $0. */extdefs: {$<ttype>$ = NULL_TREE; } extdef | extdefs {$<ttype>$ = NULL_TREE; } extdef ;extdef: fndef | datadef | ASM_KEYWORD '(' expr ')' ';' { STRIP_NOPS ($3); if ((TREE_CODE ($3) == ADDR_EXPR && TREE_CODE (TREE_OPERAND ($3, 0)) == STRING_CST) || TREE_CODE ($3) == STRING_CST) assemble_asm ($3); else error ("argument of `asm' is not a constant string"); } ;datadef: setspecs notype_initdecls ';' { if (pedantic) error ("ANSI C forbids data definition with no type or storage class"); else if (!flag_traditional) warning ("data definition has no type or storage class"); current_declspecs = TREE_VALUE (declspec_stack); prefix_attributes = TREE_PURPOSE (declspec_stack); declspec_stack = TREE_CHAIN (declspec_stack); resume_momentary ($1); } | declmods setspecs notype_initdecls ';' { current_declspecs = TREE_VALUE (declspec_stack); prefix_attributes = TREE_PURPOSE (declspec_stack); declspec_stack = TREE_CHAIN (declspec_stack); resume_momentary ($2); } | typed_declspecs setspecs initdecls ';' { current_declspecs = TREE_VALUE (declspec_stack); prefix_attributes = TREE_PURPOSE (declspec_stack); declspec_stack = TREE_CHAIN (declspec_stack); resume_momentary ($2); } | declmods ';' { pedwarn ("empty declaration"); } | typed_declspecs ';' { shadow_tag ($1); } | error ';' | error '}' | ';' { if (pedantic) pedwarn ("ANSI C does not allow extra `;' outside of a function"); } ;fndef: typed_declspecs setspecs declarator { if (! start_function ($1, $3, prefix_attributes, NULL_TREE, 0)) YYERROR1; reinit_parse_for_function (); } xdecls { store_parm_decls (); } compstmt_or_error { finish_function (0); current_declspecs = TREE_VALUE (declspec_stack); prefix_attributes = TREE_PURPOSE (declspec_stack); declspec_stack = TREE_CHAIN (declspec_stack); resume_momentary ($2); } | typed_declspecs setspecs declarator error { current_declspecs = TREE_VALUE (declspec_stack); prefix_attributes = TREE_PURPOSE (declspec_stack); declspec_stack = TREE_CHAIN (declspec_stack); resume_momentary ($2); } | declmods setspecs notype_declarator { if (! start_function ($1, $3, prefix_attributes, NULL_TREE, 0)) YYERROR1; reinit_parse_for_function (); } xdecls { store_parm_decls (); } compstmt_or_error { finish_function (0); current_declspecs = TREE_VALUE (declspec_stack); prefix_attributes = TREE_PURPOSE (declspec_stack); declspec_stack = TREE_CHAIN (declspec_stack); resume_momentary ($2); } | declmods setspecs notype_declarator error { current_declspecs = TREE_VALUE (declspec_stack); prefix_attributes = TREE_PURPOSE (declspec_stack); declspec_stack = TREE_CHAIN (declspec_stack); resume_momentary ($2); } | setspecs notype_declarator { if (! start_function (NULL_TREE, $2, prefix_attributes, NULL_TREE, 0)) YYERROR1; reinit_parse_for_function (); } xdecls { store_parm_decls (); } compstmt_or_error { finish_function (0); current_declspecs = TREE_VALUE (declspec_stack); prefix_attributes = TREE_PURPOSE (declspec_stack); declspec_stack = TREE_CHAIN (declspec_stack); resume_momentary ($1); } | setspecs notype_declarator error { current_declspecs = TREE_VALUE (declspec_stack); prefix_attributes = TREE_PURPOSE (declspec_stack); declspec_stack = TREE_CHAIN (declspec_stack); resume_momentary ($1); } ;identifier: IDENTIFIER | TYPENAME ;unop: '&' { $$ = ADDR_EXPR; } | '-' { $$ = NEGATE_EXPR; } | '+' { $$ = CONVERT_EXPR; } | PLUSPLUS { $$ = PREINCREMENT_EXPR; } | MINUSMINUS { $$ = PREDECREMENT_EXPR; } | '~' { $$ = BIT_NOT_EXPR; } | '!' { $$ = TRUTH_NOT_EXPR; } ;expr: nonnull_exprlist { $$ = build_compound_expr ($1); } ;exprlist: /* empty */ { $$ = NULL_TREE; } | nonnull_exprlist ;nonnull_exprlist: expr_no_commas { $$ = build_tree_list (NULL_TREE, $1); } | nonnull_exprlist ',' expr_no_commas { chainon ($1, build_tree_list (NULL_TREE, $3)); } ;unary_expr: primary | '*' cast_expr %prec UNARY { $$ = build_indirect_ref ($2, "unary *"); } /* __extension__ turns off -pedantic for following primary. */ | EXTENSION { $<itype>1 = pedantic; pedantic = 0; } cast_expr %prec UNARY { $$ = $3; pedantic = $<itype>1; } | unop cast_expr %prec UNARY { $$ = build_unary_op ($1, $2, 0); overflow_warning ($$); } /* Refer to the address of a label as a pointer. */ | ANDAND identifier { tree label = lookup_label ($2); if (pedantic)
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -