OSDN Git Service

2009-02-06 Paolo Bonzini <bonzini@gnu.org>
[pf3gnuchains/gcc-fork.git] / gcc / c-parser.c
index 2b64c86..199a5a7 100644 (file)
@@ -1,6 +1,6 @@
 /* Parser for C and Objective-C.
    Copyright (C) 1987, 1988, 1989, 1992, 1993, 1994, 1995, 1996, 1997, 1998,
-   1999, 2000, 2001, 2002, 2003, 2004, 2005, 2007, 2008
+   1999, 2000, 2001, 2002, 2003, 2004, 2005, 2007, 2008, 2009
    Free Software Foundation, Inc.
 
    Parser actions based on the old Bison parser; structure somewhat
@@ -148,7 +148,7 @@ typedef struct c_token GTY (())
   ENUM_BITFIELD (rid) keyword : 8;
   /* If this token is a CPP_PRAGMA, this indicates the pragma that
      was seen.  Otherwise it is PRAGMA_NONE.  */
-  ENUM_BITFIELD (pragma_kind) pragma_kind : 7;
+  ENUM_BITFIELD (pragma_kind) pragma_kind : 8;
   /* The value associated with this token, if any.  */
   tree value;
   /* The location at which this token was found.  */
@@ -1605,7 +1605,7 @@ c_parser_enum_specifier (c_parser *parser)
   struct c_typespec ret;
   tree attrs;
   tree ident = NULL_TREE;
-  location_t ident_loc;
+  location_t ident_loc = UNKNOWN_LOCATION;  /* Quiet warning.  */
   gcc_assert (c_parser_next_token_is_keyword (parser, RID_ENUM));
   c_parser_consume_token (parser);
   attrs = c_parser_attributes (parser);
@@ -1634,7 +1634,7 @@ c_parser_enum_specifier (c_parser *parser)
          tree enum_decl;
          bool seen_comma;
          c_token *token;
-         location_t comma_loc;
+         location_t comma_loc = UNKNOWN_LOCATION;  /* Quiet warning.  */
          location_t value_loc;
          if (c_parser_next_token_is_not (parser, CPP_NAME))
            {
@@ -2098,8 +2098,7 @@ c_parser_typeof_specifier (c_parser *parser)
          if (DECL_P (e) || CONSTANT_CLASS_P (e))
            e = build1 (NOP_EXPR, void_type_node, e);
 
-         if (CAN_HAVE_LOCATION_P (e))
-           SET_EXPR_LOCATION (e, here);
+         protected_set_expr_location (e, here);
 
          add_stmt (e);
        }
@@ -3066,7 +3065,7 @@ c_parser_initelt (c_parser *parser)
         has been a single array designator and 2 otherwise.  */
       int des_seen = 0;
       /* Location of a designator.  */
-      location_t des_loc;
+      location_t des_loc = UNKNOWN_LOCATION;  /* Quiet warning.  */
       while (c_parser_next_token_is (parser, CPP_OPEN_SQUARE)
             || c_parser_next_token_is (parser, CPP_DOT))
        {
@@ -3091,14 +3090,14 @@ c_parser_initelt (c_parser *parser)
                  init.original_code = ERROR_MARK;
                  c_parser_error (parser, "expected identifier");
                  c_parser_skip_until_found (parser, CPP_COMMA, NULL);
-                 process_init_element (init);
+                 process_init_element (init, false);
                  return;
                }
            }
          else
            {
              tree first, second;
-             location_t ellipsis_loc;
+             location_t ellipsis_loc = UNKNOWN_LOCATION;  /* Quiet warning.  */
              /* ??? Following the old parser, [ objc-receiver
                 objc-message-args ] is accepted as an initializer,
                 being distinguished from a designator by what follows
@@ -3214,7 +3213,7 @@ c_parser_initelt (c_parser *parser)
                  init.original_code = ERROR_MARK;
                  c_parser_error (parser, "expected %<=%>");
                  c_parser_skip_until_found (parser, CPP_COMMA, NULL);
-                 process_init_element (init);
+                 process_init_element (init, false);
                  return;
                }
            }
@@ -3244,7 +3243,7 @@ c_parser_initval (c_parser *parser, struct c_expr *after)
          && TREE_CODE (init.value) != COMPOUND_LITERAL_EXPR)
        init = default_function_array_conversion (init);
     }
-  process_init_element (init);
+  process_init_element (init, false);
 }
 
 /* Parse a compound statement (possibly a function body) (C90 6.6.2,
@@ -3789,8 +3788,7 @@ c_parser_statement_after_labels (c_parser *parser)
      (recursively) all of the component statements should already have
      line numbers assigned.  ??? Can we discard no-op statements
      earlier?  */
-  if (stmt && CAN_HAVE_LOCATION_P (stmt))
-    SET_EXPR_LOCATION (stmt, loc);
+  protected_set_expr_location (stmt, loc);
 
   parser->in_if_block = in_if_block;
 }
@@ -3805,8 +3803,7 @@ c_parser_condition (c_parser *parser)
   loc = c_parser_peek_token (parser)->location;
   cond = c_objc_common_truthvalue_conversion 
     (loc, c_parser_expression_conv (parser).value);
-  if (CAN_HAVE_LOCATION_P (cond))
-    SET_EXPR_LOCATION (cond, loc);
+  protected_set_expr_location (cond, loc);
   if (warn_sequence_point)
     verify_sequence_points (cond);
   return cond;
@@ -3858,8 +3855,12 @@ c_parser_if_body (c_parser *parser, bool *if_p)
   *if_p = c_parser_next_token_is_keyword (parser, RID_IF);
   if (c_parser_next_token_is (parser, CPP_SEMICOLON))
     {
+      location_t loc = c_parser_peek_token (parser)->location;
       add_stmt (build_empty_stmt ());
       c_parser_consume_token (parser);
+      if (!c_parser_next_token_is_keyword (parser, RID_ELSE))
+       warning_at (loc, OPT_Wempty_body,
+                   "suggest braces around empty body in an %<if%> statement");
     }
   else if (c_parser_next_token_is (parser, CPP_OPEN_BRACE))
     add_stmt (c_parser_compound_statement (parser));
@@ -3883,6 +3884,9 @@ c_parser_else_body (c_parser *parser)
     c_parser_label (parser);
   if (c_parser_next_token_is (parser, CPP_SEMICOLON))
     {
+      warning_at (c_parser_peek_token (parser)->location,
+                 OPT_Wempty_body,
+                "suggest braces around empty body in an %<else%> statement");
       add_stmt (build_empty_stmt ());
       c_parser_consume_token (parser);
     }
@@ -4354,8 +4358,10 @@ c_parser_expr_no_commas (c_parser *parser, struct c_expr *after)
 {
   struct c_expr lhs, rhs, ret;
   enum tree_code code;
+  location_t op_location;
   gcc_assert (!after || c_dialect_objc ());
   lhs = c_parser_conditional_expression (parser, after);
+  op_location = c_parser_peek_token (parser)->location;
   switch (c_parser_peek_token (parser)->type)
     {
     case CPP_EQ:
@@ -4397,7 +4403,7 @@ c_parser_expr_no_commas (c_parser *parser, struct c_expr *after)
   c_parser_consume_token (parser);
   rhs = c_parser_expr_no_commas (parser, NULL);
   rhs = default_function_array_conversion (rhs);
-  ret.value = build_modify_expr (lhs.value, code, rhs.value);
+  ret.value = build_modify_expr (op_location, lhs.value, code, rhs.value);
   if (code == NOP_EXPR)
     ret.original_code = MODIFY_EXPR;
   else
@@ -4432,6 +4438,7 @@ c_parser_conditional_expression (c_parser *parser, struct c_expr *after)
 
   cond_loc = c_parser_peek_token (parser)->location;
   cond = c_parser_binary_expression (parser, after);
+  protected_set_expr_location (cond.value, cond_loc);
 
   if (c_parser_next_token_is_not (parser, CPP_QUERY))
     return cond;
@@ -4576,7 +4583,7 @@ c_parser_binary_expression (c_parser *parser, struct c_expr *after)
   } stack[NUM_PRECS];
   int sp;
   /* Location of the binary operator.  */
-  location_t binary_loc;
+  location_t binary_loc = UNKNOWN_LOCATION;  /* Quiet warning.  */
 #define POP                                                                  \
   do {                                                                       \
     switch (stack[sp].op)                                                    \
@@ -4829,7 +4836,7 @@ c_parser_unary_expression (c_parser *parser)
       c_parser_consume_token (parser);
       op = c_parser_cast_expression (parser, NULL);
       op = default_function_array_conversion (op);
-      ret.value = build_indirect_ref (op.value, "unary *", loc);
+      ret.value = build_indirect_ref (loc, op.value, "unary *");
       ret.original_code = ERROR_MARK;
       return ret;
     case CPP_PLUS:
@@ -4942,13 +4949,6 @@ c_parser_sizeof_expression (c_parser *parser)
       /* sizeof ( type-name ).  */
       skip_evaluation--;
       in_sizeof--;
-      if (type_name->declarator->kind == cdk_array
-         && type_name->declarator->u.array.vla_unspec_p)
-       {
-         /* C99 6.7.5.2p4 */
-         error_at (expr_loc,
-                   "%<[*]%> not allowed in other than a declaration");
-       }
       return c_expr_sizeof_type (type_name);
     }
   else
@@ -5082,6 +5082,17 @@ c_parser_postfix_expression (c_parser *parser)
   switch (c_parser_peek_token (parser)->type)
     {
     case CPP_NUMBER:
+      expr.value = c_parser_peek_token (parser)->value;
+      expr.original_code = ERROR_MARK;
+      loc = c_parser_peek_token (parser)->location;
+      c_parser_consume_token (parser);
+      if (TREE_CODE (expr.value) == FIXED_CST
+         && !targetm.fixed_point_supported_p ())
+       {
+         error_at (loc, "fixed-point types not supported for this target");
+         expr.value = error_mark_node;
+       }
+      break;
     case CPP_CHAR:
     case CPP_CHAR16:
     case CPP_CHAR32:
@@ -5266,10 +5277,21 @@ c_parser_postfix_expression (c_parser *parser)
                c_parser_consume_token (parser);
                while (c_parser_next_token_is (parser, CPP_DOT)
                       || c_parser_next_token_is (parser,
-                                                 CPP_OPEN_SQUARE))
+                                                 CPP_OPEN_SQUARE)
+                      || c_parser_next_token_is (parser,
+                                                 CPP_DEREF))
                  {
-                   if (c_parser_next_token_is (parser, CPP_DOT))
+                   if (c_parser_next_token_is (parser, CPP_DEREF))
+                     {
+                       loc = c_parser_peek_token (parser)->location;
+                       offsetof_ref = build_array_ref (offsetof_ref,
+                                                       integer_zero_node,
+                                                       loc);
+                       goto do_dot;
+                     }
+                   else if (c_parser_next_token_is (parser, CPP_DOT))
                      {
+                     do_dot:
                        c_parser_consume_token (parser);
                        if (c_parser_next_token_is_not (parser,
                                                        CPP_NAME))
@@ -5587,8 +5609,9 @@ c_parser_postfix_expression_after_primary (c_parser *parser,
              return expr;
            }
          c_parser_consume_token (parser);
-         expr.value = build_component_ref (build_indirect_ref (expr.value,
-                                                               "->", loc),
+         expr.value = build_component_ref (build_indirect_ref (loc,
+                                                               expr.value,
+                                                               "->"),
                                            ident);
          expr.original_code = ERROR_MARK;
          break;
@@ -5596,14 +5619,16 @@ c_parser_postfix_expression_after_primary (c_parser *parser,
          /* Postincrement.  */
          c_parser_consume_token (parser);
          expr = default_function_array_conversion (expr);
-         expr.value = build_unary_op (POSTINCREMENT_EXPR, expr.value, 0);
+         expr.value = build_unary_op (loc,
+                                      POSTINCREMENT_EXPR, expr.value, 0);
          expr.original_code = ERROR_MARK;
          break;
        case CPP_MINUS_MINUS:
          /* Postdecrement.  */
          c_parser_consume_token (parser);
          expr = default_function_array_conversion (expr);
-         expr.value = build_unary_op (POSTDECREMENT_EXPR, expr.value, 0);
+         expr.value = build_unary_op (loc,
+                                      POSTDECREMENT_EXPR, expr.value, 0);
          expr.original_code = ERROR_MARK;
          break;
        default:
@@ -7587,14 +7612,17 @@ c_parser_omp_for_loop (c_parser *parser, tree clauses, tree *par_clauses)
               && c_parser_peek_2nd_token (parser)->type == CPP_EQ)
        {
          struct c_expr init_exp;
+         location_t init_loc;
 
          decl = c_parser_postfix_expression (parser).value;
 
          c_parser_require (parser, CPP_EQ, "expected %<=%>");
+         init_loc = c_parser_peek_token (parser)->location;
 
          init_exp = c_parser_expr_no_commas (parser, NULL);
          init_exp = default_function_array_conversion (init_exp);
-         init = build_modify_expr (decl, NOP_EXPR, init_exp.value);
+         init = build_modify_expr (init_loc,
+                                   decl, NOP_EXPR, init_exp.value);
          init = c_process_expr_stmt (init);
 
          c_parser_skip_until_found (parser, CPP_SEMICOLON, "expected %<;%>");
@@ -7618,15 +7646,19 @@ c_parser_omp_for_loop (c_parser *parser, tree clauses, tree *par_clauses)
 
          cond = c_parser_expression_conv (parser).value;
          cond = c_objc_common_truthvalue_conversion (cond_loc, cond);
-         if (CAN_HAVE_LOCATION_P (cond))
-           SET_EXPR_LOCATION (cond, cond_loc);
+         protected_set_expr_location (cond, cond_loc);
        }
       c_parser_skip_until_found (parser, CPP_SEMICOLON, "expected %<;%>");
 
       /* Parse the increment expression.  */
       incr = NULL_TREE;
       if (c_parser_next_token_is_not (parser, CPP_CLOSE_PAREN))
-       incr = c_process_expr_stmt (c_parser_expression (parser).value);
+       {
+         location_t incr_loc = c_parser_peek_token (parser)->location;
+
+         incr = c_process_expr_stmt (c_parser_expression (parser).value);
+         protected_set_expr_location (incr, incr_loc);
+       }
       c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, "expected %<)%>");
 
       if (decl == NULL || decl == error_mark_node || init == error_mark_node)