summaryrefslogtreecommitdiff
path: root/gcc/c-decl.c
diff options
context:
space:
mode:
authorrth <rth@138bc75d-0d04-0410-961f-82ee72b054a4>2001-10-08 16:37:06 +0000
committerrth <rth@138bc75d-0d04-0410-961f-82ee72b054a4>2001-10-08 16:37:06 +0000
commit3b28840692db43ac6b8adc4245ed0ca1dcf73cbe (patch)
tree29cbaa01253970fbc753eff9f70ce21ac5d8b696 /gcc/c-decl.c
parent1c8ac6c6caead03f2964f0267387d02a793dc602 (diff)
downloadgcc-3b28840692db43ac6b8adc4245ed0ca1dcf73cbe.tar.gz
* c-common.h (struct c_lang_decl): Add declared_inline.
* c-tree.h (DECL_DECLARED_INLINE_P): New. * c-lang.c (c_disregard_inline_limits): Use it. * c-decl.c (duplicate_decls): Likewise. (pushdecl, redeclaration_error_message): Likewise. (pushdecl): Allocate DECL_LANG_SPECIFIC if needed. (grokdeclarator): Likewise. Set DECL_DECLARED_INLINE_P. Set DECL_INLINE if -finline-functions. (store_parm_decls): Don't allocate DECL_LANG_SPECIFIC here. * cp-tree.h (struct lang_decl_flags): Remove declared_inline. (DECL_DECLARED_INLINE_P): Use the bit in struct c_lang_decl. git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@46079 138bc75d-0d04-0410-961f-82ee72b054a4
Diffstat (limited to 'gcc/c-decl.c')
-rw-r--r--gcc/c-decl.c56
1 files changed, 40 insertions, 16 deletions
diff --git a/gcc/c-decl.c b/gcc/c-decl.c
index e35969464de..4ec34eace4d 100644
--- a/gcc/c-decl.c
+++ b/gcc/c-decl.c
@@ -1727,12 +1727,14 @@ duplicate_decls (newdecl, olddecl, different_binding_level)
/* Warn if function is now inline
but was previously declared not inline and has been called. */
if (TREE_CODE (olddecl) == FUNCTION_DECL
- && ! DECL_INLINE (olddecl) && DECL_INLINE (newdecl)
+ && ! DECL_DECLARED_INLINE_P (olddecl)
+ && DECL_DECLARED_INLINE_P (newdecl)
&& TREE_USED (olddecl))
warning_with_decl (newdecl,
"`%s' declared inline after being called");
if (TREE_CODE (olddecl) == FUNCTION_DECL
- && ! DECL_INLINE (olddecl) && DECL_INLINE (newdecl)
+ && ! DECL_DECLARED_INLINE_P (olddecl)
+ && DECL_DECLARED_INLINE_P (newdecl)
&& DECL_INITIAL (olddecl) != 0)
warning_with_decl (newdecl,
"`%s' declared inline after its definition");
@@ -1976,10 +1978,11 @@ duplicate_decls (newdecl, olddecl, different_binding_level)
{
/* If either decl says `inline', this fn is inline,
unless its definition was passed already. */
- if (DECL_INLINE (newdecl) && DECL_INITIAL (olddecl) == 0)
- DECL_INLINE (olddecl) = 1;
+ if (DECL_DECLARED_INLINE_P (newdecl)
+ && DECL_DECLARED_INLINE_P (olddecl) == 0)
+ DECL_DECLARED_INLINE_P (olddecl) = 1;
- DECL_INLINE (newdecl) = DECL_INLINE (olddecl);
+ DECL_DECLARED_INLINE_P (newdecl) = DECL_DECLARED_INLINE_P (olddecl);
}
if (DECL_BUILT_IN (olddecl))
@@ -2056,6 +2059,11 @@ pushdecl (x)
register tree name = DECL_NAME (x);
register struct binding_level *b = current_binding_level;
+ /* Functions need the lang_decl data. */
+ if (TREE_CODE (x) == FUNCTION_DECL && ! DECL_LANG_SPECIFIC (x))
+ DECL_LANG_SPECIFIC (x) = (struct lang_decl *)
+ ggc_alloc_cleared (sizeof (struct lang_decl));
+
DECL_CONTEXT (x) = current_function_decl;
/* A local extern declaration for a function doesn't constitute nesting.
A local auto declaration does, since it's a forward decl
@@ -2351,7 +2359,8 @@ pushdecl (x)
&& oldglobal != 0
&& TREE_CODE (x) == FUNCTION_DECL
&& TREE_CODE (oldglobal) == FUNCTION_DECL
- && DECL_EXTERNAL (x) && ! DECL_INLINE (x))
+ && DECL_EXTERNAL (x)
+ && ! DECL_DECLARED_INLINE_P (x))
{
/* We have one. Their types must agree. */
if (! comptypes (TREE_TYPE (x),
@@ -2361,8 +2370,10 @@ pushdecl (x)
{
/* Inner extern decl is inline if global one is.
Copy enough to really inline it. */
- if (DECL_INLINE (oldglobal))
+ if (DECL_DECLARED_INLINE_P (oldglobal))
{
+ DECL_DECLARED_INLINE_P (x)
+ = DECL_DECLARED_INLINE_P (oldglobal);
DECL_INLINE (x) = DECL_INLINE (oldglobal);
DECL_INITIAL (x) = (current_function_decl == oldglobal
? 0 : DECL_INITIAL (oldglobal));
@@ -2613,8 +2624,9 @@ redeclaration_error_message (newdecl, olddecl)
if (DECL_INITIAL (olddecl) != 0 && DECL_INITIAL (newdecl) != 0
/* However, defining once as extern inline and a second
time in another way is ok. */
- && ! (DECL_INLINE (olddecl) && DECL_EXTERNAL (olddecl)
- && ! (DECL_INLINE (newdecl) && DECL_EXTERNAL (newdecl))))
+ && ! (DECL_DECLARED_INLINE_P (olddecl) && DECL_EXTERNAL (olddecl)
+ && ! (DECL_DECLARED_INLINE_P (newdecl)
+ && DECL_EXTERNAL (newdecl))))
return 1;
return 0;
}
@@ -4913,6 +4925,9 @@ grokdeclarator (declarator, declspecs, decl_context, initialized)
decl = build_decl (FUNCTION_DECL, declarator, type);
decl = build_decl_attribute_variant (decl, decl_attr);
+ DECL_LANG_SPECIFIC (decl) = (struct lang_decl *)
+ ggc_alloc_cleared (sizeof (struct lang_decl));
+
if (pedantic && type_quals && ! DECL_IN_SYSTEM_HEADER (decl))
pedwarn ("ISO C forbids qualified function types");
@@ -4929,17 +4944,28 @@ grokdeclarator (declarator, declspecs, decl_context, initialized)
= !(specbits & ((1 << (int) RID_STATIC) | (1 << (int) RID_AUTO)));
/* Record presence of `inline', if it is reasonable. */
- if (inlinep)
+ if (MAIN_NAME_P (declarator))
{
- if (MAIN_NAME_P (declarator))
+ if (inlinep)
warning ("cannot inline function `main'");
- else
- /* Assume that otherwise the function can be inlined. */
- DECL_INLINE (decl) = 1;
+ }
+ else if (inlinep)
+ {
+ /* Assume that otherwise the function can be inlined. */
+ DECL_INLINE (decl) = 1;
+ DECL_DECLARED_INLINE_P (decl) = 1;
if (specbits & (1 << (int) RID_EXTERN))
current_extern_inline = 1;
}
+ /* If -finline-functions, assume it can be inlined. This does
+ two things: let the function be deferred until it is actually
+ needed, and let dwarf2 know that the function is inlinable. */
+ else if (flag_inline_trees == 2)
+ {
+ DECL_INLINE (decl) = 1;
+ DECL_DECLARED_INLINE_P (decl) = 0;
+ }
}
else
{
@@ -6593,8 +6619,6 @@ store_parm_decls ()
init_function_start (fndecl, input_filename, lineno);
/* Begin the statement tree for this function. */
- DECL_LANG_SPECIFIC (current_function_decl)
- =((struct lang_decl *) ggc_alloc_cleared (sizeof (struct lang_decl)));
begin_stmt_tree (&DECL_SAVED_TREE (current_function_decl));
/* If this is a nested function, save away the sizes of any