case VAR_DECL:
/* Warnings for unused variables. */
if (!TREE_USED (p)
+ && !TREE_NO_WARNING (p)
&& !DECL_IN_SYSTEM_HEADER (p)
&& DECL_NAME (p)
&& !DECL_ARTIFICIAL (p)
&& !(DECL_EXTERNAL (olddecl) && !DECL_EXTERNAL (newdecl))
/* Don't warn about forward parameter decls. */
&& !(TREE_CODE (newdecl) == PARM_DECL
- && TREE_ASM_WRITTEN (olddecl) && !TREE_ASM_WRITTEN (newdecl)))
+ && TREE_ASM_WRITTEN (olddecl) && !TREE_ASM_WRITTEN (newdecl))
+ /* Don't warn about a variable definition following a declaration. */
+ && !(TREE_CODE (newdecl) == VAR_DECL
+ && DECL_INITIAL (newdecl) && !DECL_INITIAL (olddecl)))
{
warning (OPT_Wredundant_decls, "redundant redeclaration of %q+D",
newdecl);
tree newtype = NULL, oldtype = NULL;
if (!diagnose_mismatched_decls (newdecl, olddecl, &newtype, &oldtype))
- return false;
+ {
+ /* Avoid `unused variable' and other warnings warnings for OLDDECL. */
+ TREE_NO_WARNING (olddecl) = 1;
+ return false;
+ }
merge_decls (newdecl, olddecl, newtype, oldtype);
return true;
&& !TREE_STATIC (decl))
warning (0, "ignoring asm-specifier for non-static local "
"variable %q+D", decl);
- else if (C_DECL_REGISTER (decl))
- change_decl_assembler_name (decl, get_identifier (asmspec));
else
set_user_assembler_name (decl, asmspec);
}
else
type = build_array_type (type, itype);
- if (size_varies)
- C_TYPE_VARIABLE_SIZE (type) = 1;
-
- /* The GCC extension for zero-length arrays differs from
- ISO flexible array members in that sizeof yields
- zero. */
- if (size && integer_zerop (size))
+ if (type != error_mark_node)
{
- TYPE_SIZE (type) = bitsize_zero_node;
- TYPE_SIZE_UNIT (type) = size_zero_node;
+ if (size_varies)
+ C_TYPE_VARIABLE_SIZE (type) = 1;
+
+ /* The GCC extension for zero-length arrays differs from
+ ISO flexible array members in that sizeof yields
+ zero. */
+ if (size && integer_zerop (size))
+ {
+ TYPE_SIZE (type) = bitsize_zero_node;
+ TYPE_SIZE_UNIT (type) = size_zero_node;
+ }
}
if (decl_context != PARM
if (TREE_CODE (type) == ARRAY_TYPE
&& COMPLETE_TYPE_P (type)
- && TREE_CODE (TYPE_SIZE (type)) == INTEGER_CST
+ && TREE_CODE (TYPE_SIZE_UNIT (type)) == INTEGER_CST
&& TREE_OVERFLOW (TYPE_SIZE_UNIT (type)))
{
error ("size of array %qs is too large", name);
/* At file scope, the presence of a `static' or `register' storage
class specifier, or the absence of all storage class specifiers
makes this declaration a definition (perhaps tentative). Also,
- the absence of both `static' and `register' makes it public. */
+ the absence of `static' makes it public. */
if (current_scope == file_scope)
{
- TREE_PUBLIC (decl) = !(storage_class == csc_static
- || storage_class == csc_register);
+ TREE_PUBLIC (decl) = storage_class != csc_static;
TREE_STATIC (decl) = !extern_ref;
}
/* Not at file scope, only `static' makes a static definition. */
cgraph_build_static_cdtor (method_type, body, DEFAULT_INIT_PRIORITY);
}
-/* Perform final processing on one file scope's declarations (or the
- external scope's declarations), GLOBALS. */
+/* A subroutine of c_write_global_declarations. Perform final processing
+ on one file scope's declarations (or the external scope's declarations),
+ GLOBALS. */
+
static void
c_write_global_declarations_1 (tree globals)
{
- size_t len = list_length (globals);
- tree *vec = XNEWVEC (tree, len);
- size_t i;
tree decl;
+ bool reconsider;
/* Process the decls in the order they were written. */
- for (i = 0, decl = globals; i < len; i++, decl = TREE_CHAIN (decl))
+ for (decl = globals; decl; decl = TREE_CHAIN (decl))
{
- vec[i] = decl;
/* Check for used but undefined static functions using the C
standard's definition of "used", and set TREE_NO_WARNING so
that check_global_declarations doesn't repeat the check. */
pedwarn ("%q+F used but never defined", decl);
TREE_NO_WARNING (decl) = 1;
}
+
+ wrapup_global_declaration_1 (decl);
+ }
+
+ do
+ {
+ reconsider = false;
+ for (decl = globals; decl; decl = TREE_CHAIN (decl))
+ reconsider |= wrapup_global_declaration_2 (decl);
}
+ while (reconsider);
- wrapup_global_declarations (vec, len);
- check_global_declarations (vec, len);
+ for (decl = globals; decl; decl = TREE_CHAIN (decl))
+ check_global_declaration_1 (decl);
+}
+
+/* A subroutine of c_write_global_declarations Emit debug information for each
+ of the declarations in GLOBALS. */
+
+static void
+c_write_global_declarations_2 (tree globals)
+{
+ tree decl;
- free (vec);
+ for (decl = globals; decl ; decl = TREE_CHAIN (decl))
+ debug_hooks->global_decl (decl);
}
+/* Preserve the external declarations scope across a garbage collect. */
+static GTY(()) tree ext_block;
+
void
c_write_global_declarations (void)
{
- tree ext_block, t;
+ tree t;
/* We don't want to do this if generating a PCH. */
if (pch_file)
external_scope = 0;
gcc_assert (!current_scope);
- /* Process all file scopes in this compilation, and the external_scope,
- through wrapup_global_declarations and check_global_declarations. */
- for (t = all_translation_units; t; t = TREE_CHAIN (t))
- c_write_global_declarations_1 (BLOCK_VARS (DECL_INITIAL (t)));
if (ext_block)
{
tree tmp = BLOCK_VARS (ext_block);
dump_end (TDI_tu, stream);
}
}
+
+ /* Process all file scopes in this compilation, and the external_scope,
+ through wrapup_global_declarations and check_global_declarations. */
+ for (t = all_translation_units; t; t = TREE_CHAIN (t))
+ c_write_global_declarations_1 (BLOCK_VARS (DECL_INITIAL (t)));
c_write_global_declarations_1 (BLOCK_VARS (ext_block));
/* Generate functions to call static constructors and destructors
/* We're done parsing; proceed to optimize and emit assembly.
FIXME: shouldn't be the front end's responsibility to call this. */
cgraph_optimize ();
+
+ /* After cgraph has had a chance to emit everything that's going to
+ be emitted, output debug information for globals. */
+ if (errorcount == 0 && sorrycount == 0)
+ {
+ timevar_push (TV_SYMOUT);
+ for (t = all_translation_units; t; t = TREE_CHAIN (t))
+ c_write_global_declarations_2 (BLOCK_VARS (DECL_INITIAL (t)));
+ c_write_global_declarations_2 (BLOCK_VARS (ext_block));
+ timevar_pop (TV_SYMOUT);
+ }
+
+ ext_block = NULL;
}
#include "gt-c-decl.h"