FIELD, /* Declaration inside struct or union */
TYPENAME}; /* Typename (inside cast or sizeof) */
+/* States indicating how grokdeclarator() should handle declspecs marked
+ with __attribute__((deprecated)). An object declared as
+ __attribute__((deprecated)) suppresses warnings of uses of other
+ deprecated items. */
+
+enum deprecated_states {
+ DEPRECATED_NORMAL,
+ DEPRECATED_SUPPRESS
+};
+
\f
/* Nonzero if we have seen an invalid cross reference
to a struct, union, or enum, but not yet printed the message. */
/* True means we've initialized exception handling. */
bool c_eh_initialized_p;
-/* While defining an enum type, this is 1 plus the last enumerator
- constant value. Note that will do not have to save this or `enum_overflow'
- around nested function definition since such a definition could only
- occur in an enum value expression and we don't use these variables in
- that case. */
-
-static tree enum_next_value;
-
-/* Nonzero means that there was overflow computing enum_next_value. */
-
-static int enum_overflow;
-
/* The file and line that the prototype came from if this is an
old-style definition; used for diagnostics in
store_parm_decls_oldstyle. */
union lang_tree_node
GTY((desc ("TREE_CODE (&%h.generic) == IDENTIFIER_NODE"),
- chain_next ("TREE_CODE (&%h.generic) == INTEGER_TYPE ? (union lang_tree_node *) TYPE_NEXT_VARIANT (&%h.generic) : (GIMPLE_TUPLE_P (&%h.generic) ? (union lang_tree_node *) 0 : (union lang_tree_node *) TREE_CHAIN (&%h.generic))")))
+ chain_next ("TREE_CODE (&%h.generic) == INTEGER_TYPE ? (union lang_tree_node *) TYPE_NEXT_VARIANT (&%h.generic) : ((union lang_tree_node *) GENERIC_NEXT (&%h.generic))")))
{
union tree_node GTY ((tag ("0"),
desc ("tree_node_structure (&%h)")))
static tree c_make_fname_decl (tree, int);
static tree grokdeclarator (const struct c_declarator *,
struct c_declspecs *,
- enum decl_context, bool, tree *);
+ enum decl_context, bool, tree *,
+ enum deprecated_states);
static tree grokparms (struct c_arg_info *, bool);
static void layout_array_type (tree);
\f
return t;
}
\f
-/* States indicating how grokdeclarator() should handle declspecs marked
- with __attribute__((deprecated)). An object declared as
- __attribute__((deprecated)) suppresses warnings of uses of other
- deprecated items. */
-
-enum deprecated_states {
- DEPRECATED_NORMAL,
- DEPRECATED_SUPPRESS
-};
-
-static enum deprecated_states deprecated_state = DEPRECATED_NORMAL;
void
c_print_identifier (FILE *file, tree node, int indent)
DECL_SIZE (newdecl) = DECL_SIZE (olddecl);
DECL_SIZE_UNIT (newdecl) = DECL_SIZE_UNIT (olddecl);
DECL_MODE (newdecl) = DECL_MODE (olddecl);
- if (TREE_CODE (olddecl) != FUNCTION_DECL)
- if (DECL_ALIGN (olddecl) > DECL_ALIGN (newdecl))
- {
- DECL_ALIGN (newdecl) = DECL_ALIGN (olddecl);
- DECL_USER_ALIGN (newdecl) |= DECL_ALIGN (olddecl);
- }
+ if (DECL_ALIGN (olddecl) > DECL_ALIGN (newdecl))
+ {
+ DECL_ALIGN (newdecl) = DECL_ALIGN (olddecl);
+ DECL_USER_ALIGN (newdecl) |= DECL_ALIGN (olddecl);
+ }
}
type_name->specs->attrs = NULL_TREE;
type = grokdeclarator (type_name->declarator, type_name->specs, TYPENAME,
- false, NULL);
+ false, NULL, DEPRECATED_NORMAL);
/* Apply attributes. */
decl_attributes (&type, attrs, 0);
{
tree decl;
tree tem;
+ enum deprecated_states deprecated_state = DEPRECATED_NORMAL;
/* An object declared as __attribute__((deprecated)) suppresses
warnings of uses of other deprecated items. */
deprecated_state = DEPRECATED_SUPPRESS;
decl = grokdeclarator (declarator, declspecs,
- NORMAL, initialized, NULL);
+ NORMAL, initialized, NULL,
+ deprecated_state);
if (!decl)
return 0;
- deprecated_state = DEPRECATED_NORMAL;
-
if (warn_main > 0 && TREE_CODE (decl) != FUNCTION_DECL
&& MAIN_NAME_P (DECL_NAME (decl)))
warning (OPT_Wmain, "%q+D is usually a function", decl);
void
finish_decl (tree decl, tree init, tree asmspec_tree)
{
- tree type = TREE_TYPE (decl);
+ tree type;
int was_incomplete = (DECL_SIZE (decl) == 0);
const char *asmspec = 0;
|| TREE_CODE (decl) == FIELD_DECL))
objc_check_decl (decl);
+ type = TREE_TYPE (decl);
+
/* Deduce size of array from initialization, if not already known. */
if (TREE_CODE (type) == ARRAY_TYPE
&& TYPE_DOMAIN (type) == 0
grokparm (const struct c_parm *parm)
{
tree decl = grokdeclarator (parm->declarator, parm->specs, PARM, false,
- NULL);
+ NULL, DEPRECATED_NORMAL);
decl_attributes (&decl, parm->attrs, 0);
{
tree decl;
- decl = grokdeclarator (parm->declarator, parm->specs, PARM, false, NULL);
+ decl = grokdeclarator (parm->declarator, parm->specs, PARM, false, NULL,
+ DEPRECATED_NORMAL);
decl_attributes (&decl, parm->attrs, 0);
decl = pushdecl (decl);
}
\f
+
+/* Print warning about variable length array if necessary. */
+
+static void
+warn_variable_length_array (const char *name, tree size)
+{
+ int ped = !flag_isoc99 && pedantic && warn_vla != 0;
+ int const_size = TREE_CONSTANT (size);
+
+ if (ped)
+ {
+ if (const_size)
+ {
+ if (name)
+ pedwarn ("ISO C90 forbids array %qs whose size "
+ "can%'t be evaluated",
+ name);
+ else
+ pedwarn ("ISO C90 forbids array whose size "
+ "can%'t be evaluated");
+ }
+ else
+ {
+ if (name)
+ pedwarn ("ISO C90 forbids variable length array %qs",
+ name);
+ else
+ pedwarn ("ISO C90 forbids variable length array");
+ }
+ }
+ else if (warn_vla > 0)
+ {
+ if (const_size)
+ {
+ if (name)
+ warning (OPT_Wvla,
+ "the size of array %qs can"
+ "%'t be evaluated", name);
+ else
+ warning (OPT_Wvla,
+ "the size of array can %'t be evaluated");
+ }
+ else
+ {
+ if (name)
+ warning (OPT_Wvla,
+ "variable length array %qs is used",
+ name);
+ else
+ warning (OPT_Wvla,
+ "variable length array is used");
+ }
+ }
+}
+
/* Given declspecs and a declarator,
determine the name and type of the object declared
and construct a ..._DECL node for it.
INITIALIZED is true if the decl has an initializer.
WIDTH is non-NULL for bit-fields, and is a pointer to an INTEGER_CST node
representing the width of the bit-field.
+ DEPRECATED_STATE is a deprecated_states value indicating whether
+ deprecation warnings should be suppressed.
In the TYPENAME case, DECLARATOR is really an absolute declarator.
It may also be so in the PARM case, for a prototype where the
static tree
grokdeclarator (const struct c_declarator *declarator,
struct c_declspecs *declspecs,
- enum decl_context decl_context, bool initialized, tree *width)
+ enum decl_context decl_context, bool initialized, tree *width,
+ enum deprecated_states deprecated_state)
{
tree type = declspecs->type;
bool threadp = declspecs->thread_p;
nonconstant even if it is (eg) a const variable
with known value. */
size_varies = 1;
-
- if (!flag_isoc99 && pedantic)
- {
- if (TREE_CONSTANT (size))
- pedwarn ("ISO C90 forbids array %qs whose size "
- "can%'t be evaluated",
- name);
- else
- pedwarn ("ISO C90 forbids variable-size array %qs",
- name);
- }
+ warn_variable_length_array (orig_name, size);
}
if (integer_zerop (size))
}
value = grokdeclarator (declarator, declspecs, FIELD, false,
- width ? &width : NULL);
+ width ? &width : NULL, DEPRECATED_NORMAL);
finish_decl (value, NULL_TREE, NULL_TREE);
DECL_INITIAL (value) = width;
may be used to declare the individual values as they are read. */
tree
-start_enum (tree name)
+start_enum (struct c_enum_contents *the_enum, tree name)
{
tree enumtype = 0;
TYPE_VALUES (enumtype) = 0;
}
- enum_next_value = integer_zero_node;
- enum_overflow = 0;
+ the_enum->enum_next_value = integer_zero_node;
+ the_enum->enum_overflow = 0;
if (flag_short_enums)
TYPE_PACKED (enumtype) = 1;
Assignment of sequential values by default is handled here. */
tree
-build_enumerator (tree name, tree value)
+build_enumerator (struct c_enum_contents *the_enum, tree name, tree value)
{
tree decl, type;
in the default. */
if (value == 0)
{
- value = enum_next_value;
- if (enum_overflow)
+ value = the_enum->enum_next_value;
+ if (the_enum->enum_overflow)
error ("overflow in enumeration values");
}
}
/* Set basis for default for next value. */
- enum_next_value = build_binary_op (PLUS_EXPR, value, integer_one_node, 0);
- enum_overflow = tree_int_cst_lt (enum_next_value, value);
+ the_enum->enum_next_value = build_binary_op (PLUS_EXPR, value,
+ integer_one_node, 0);
+ the_enum->enum_overflow = tree_int_cst_lt (the_enum->enum_next_value, value);
/* Now create a declaration for the enum value name. */
error message in c_finish_bc_stmt. */
c_break_label = c_cont_label = size_zero_node;
- decl1 = grokdeclarator (declarator, declspecs, FUNCDEF, true, NULL);
+ decl1 = grokdeclarator (declarator, declspecs, FUNCDEF, true, NULL,
+ DEPRECATED_NORMAL);
/* If the declarator is not suitable for a function definition,
cause a syntax error. */
declare_parm_level ();
restype = TREE_TYPE (TREE_TYPE (current_function_decl));
- /* Promote the value to int before returning it. */
- if (c_promoting_integer_type_p (restype))
- {
- /* It retains unsignedness if not really getting wider. */
- if (TYPE_UNSIGNED (restype)
- && (TYPE_PRECISION (restype)
- == TYPE_PRECISION (integer_type_node)))
- restype = unsigned_type_node;
- else
- restype = integer_type_node;
- }
-
resdecl = build_decl (RESULT_DECL, NULL_TREE, restype);
DECL_ARTIFICIAL (resdecl) = 1;
DECL_IGNORED_P (resdecl) = 1;
TREE_NO_WARNING (fndecl) = 1;
}
- /* With just -Wextra, complain only if function returns both with
- and without a value. */
- if (extra_warnings
- && current_function_returns_value
- && current_function_returns_null)
- warning (OPT_Wextra, "this function may return with or without a value");
-
/* Store the end of the function, so that we get good line number
info for the epilogue. */
cfun->function_end_locus = input_location;
- /* Keep track of functions declared with the "constructor" and
- "destructor" attribute. */
- c_record_cdtor_fn (fndecl);
-
/* Finalize the ELF visibility for the function. */
c_determine_visibility (fndecl);
c_write_global_declarations_1 (BLOCK_VARS (DECL_INITIAL (t)));
c_write_global_declarations_1 (BLOCK_VARS (ext_block));
- /* Call functions declared with the "constructor" or "destructor"
- attribute. */
- c_build_cdtor_fns ();
-
/* We're done parsing; proceed to optimize and emit assembly.
FIXME: shouldn't be the front end's responsibility to call this. */
cgraph_optimize ();