Makefile.in (STRICT2_WARN): Add -Wno-variadic-macros.
* Makefile.in (STRICT2_WARN): Add -Wno-variadic-macros. * tree.c (build0, build1, build2, build3, build4): Split out from... (build): ... here. Call them. * tree.h (build, _buildN1, _buildN2, _buildC1, _buildC2): New. * convert.c (convert_to_integer): Remove extra build argument. * tree-inline.c (expand_call_inline): Likewise. ada/ * misc.c (record_code_position): Add third build arg for RTL_EXPR. java/ * parse.y (switch_label): Use make_node for DEFAULT_EXPR. From-SVN: r78126
This commit is contained in:
parent
e5b7921933
commit
4221057e8f
10 changed files with 243 additions and 120 deletions
|
@ -1,3 +1,13 @@
|
|||
2004-02-19 Richard Henderson <rth@redhat.com>
|
||||
|
||||
* Makefile.in (STRICT2_WARN): Add -Wno-variadic-macros.
|
||||
* tree.c (build0, build1, build2, build3, build4): Split out from...
|
||||
(build): ... here. Call them.
|
||||
* tree.h (build, _buildN1, _buildN2, _buildC1, _buildC2): New.
|
||||
|
||||
* convert.c (convert_to_integer): Remove extra build argument.
|
||||
* tree-inline.c (expand_call_inline): Likewise.
|
||||
|
||||
2004-02-19 Richard Henderson <rth@redhat.com>
|
||||
|
||||
* c-opts.c (warn_variadic_macros): New.
|
||||
|
|
|
@ -159,10 +159,12 @@ coverageexts = .{gcda,gcno}
|
|||
# STRICT_WARN and STRICT2_WARN are the additional warning flags to
|
||||
# apply to the back end and the C front end, which may be compiled
|
||||
# with other compilers. This is partially controlled by configure in
|
||||
# stage1, as not all versions of gcc understand -Wno-long-long.
|
||||
# stage1, as not all versions of gcc understand -Wno-long-long or
|
||||
# -Wno-variadic-macros.
|
||||
LOOSE_WARN = -W -Wall -Wwrite-strings -Wstrict-prototypes -Wmissing-prototypes
|
||||
STRICT_WARN = @strict1_warn@
|
||||
STRICT2_WARN = -pedantic -Wno-long-long -Wold-style-definition @WERROR@
|
||||
STRICT2_WARN = -pedantic -Wno-long-long -Wold-style-definition \
|
||||
-Wno-variadic-macros @WERROR@
|
||||
|
||||
# This is set by --enable-checking. The idea is to catch forgotten
|
||||
# "extern" tags in header files.
|
||||
|
|
|
@ -1,3 +1,7 @@
|
|||
2004-02-19 Richard Henderson <rth@redhat.com>
|
||||
|
||||
* misc.c (record_code_position): Add third build arg for RTL_EXPR.
|
||||
|
||||
2004-02-18 Emmanuel Briot <briot@act-europe.fr>
|
||||
|
||||
* ali.ads, ali.adb (First_Sdep_Entry): No longer a constant, so that
|
||||
|
|
|
@ -804,7 +804,7 @@ record_code_position (Node_Id gnat_node)
|
|||
addressable needs some fixups and also for above reason. */
|
||||
save_gnu_tree (gnat_node,
|
||||
build (RTL_EXPR, void_type_node, NULL_TREE,
|
||||
(tree) emit_note (NOTE_INSN_DELETED)),
|
||||
(tree) emit_note (NOTE_INSN_DELETED), NULL_TREE),
|
||||
1);
|
||||
}
|
||||
|
||||
|
|
|
@ -523,8 +523,7 @@ convert_to_integer (tree type, tree expr)
|
|||
return convert (type,
|
||||
fold (build (ex_form, typex,
|
||||
convert (typex, arg0),
|
||||
convert (typex, arg1),
|
||||
0)));
|
||||
convert (typex, arg1))));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,3 +1,7 @@
|
|||
2004-02-19 Richard Henderson <rth@redhat.com>
|
||||
|
||||
* parse.y (switch_label): Use make_node for DEFAULT_EXPR.
|
||||
|
||||
2004-02-16 Geoffrey Keating <geoffk@apple.com>
|
||||
|
||||
* Make-lang.in (java.install-man): Add extra dependencies.
|
||||
|
|
|
@ -1635,7 +1635,7 @@ switch_label:
|
|||
}
|
||||
| DEFAULT_TK REL_CL_TK
|
||||
{
|
||||
tree lab = build (DEFAULT_EXPR, NULL_TREE, NULL_TREE);
|
||||
tree lab = make_node (DEFAULT_EXPR);
|
||||
EXPR_WFL_LINECOL (lab) = $1.location;
|
||||
java_method_add_stmt (current_function_decl, lab);
|
||||
}
|
||||
|
|
|
@ -1377,7 +1377,7 @@ expand_call_inline (tree *tp, int *walk_subtrees, void *data)
|
|||
statements within the function to jump to. The type of the
|
||||
statement expression is the return type of the function call. */
|
||||
stmt = NULL;
|
||||
expr = build (BLOCK, TREE_TYPE (TREE_TYPE (fn)), stmt);
|
||||
expr = build (BLOCK, TREE_TYPE (TREE_TYPE (fn)));
|
||||
#endif /* INLINER_FOR_JAVA */
|
||||
|
||||
/* Local declarations will be replaced by their equivalents in this
|
||||
|
|
311
gcc/tree.c
311
gcc/tree.c
|
@ -2286,127 +2286,31 @@ stabilize_reference_1 (tree e)
|
|||
|
||||
/* Low-level constructors for expressions. */
|
||||
|
||||
/* Build an expression of code CODE, data type TYPE,
|
||||
and operands as specified by the arguments ARG1 and following arguments.
|
||||
Expressions and reference nodes can be created this way.
|
||||
Constants, decls, types and misc nodes cannot be. */
|
||||
/* Build an expression of code CODE, data type TYPE, and operands as
|
||||
specified. Expressions and reference nodes can be created this way.
|
||||
Constants, decls, types and misc nodes cannot be.
|
||||
|
||||
We define 5 non-variadic functions, from 0 to 4 arguments. This is
|
||||
enough for all extant tree codes. These functions can be called
|
||||
directly (preferably!), but can also be obtained via GCC preprocessor
|
||||
magic within the build macro. */
|
||||
|
||||
tree
|
||||
build (enum tree_code code, tree tt, ...)
|
||||
build0 (enum tree_code code, tree tt)
|
||||
{
|
||||
tree t;
|
||||
int length;
|
||||
int i;
|
||||
int fro;
|
||||
int constant;
|
||||
va_list p;
|
||||
tree node;
|
||||
|
||||
va_start (p, tt);
|
||||
#ifdef ENABLE_CHECKING
|
||||
if (TREE_CODE_LENGTH (code) != 0)
|
||||
abort ();
|
||||
#endif
|
||||
|
||||
t = make_node (code);
|
||||
length = TREE_CODE_LENGTH (code);
|
||||
TREE_TYPE (t) = tt;
|
||||
|
||||
/* Below, we automatically set TREE_SIDE_EFFECTS and TREE_READONLY for the
|
||||
result based on those same flags for the arguments. But if the
|
||||
arguments aren't really even `tree' expressions, we shouldn't be trying
|
||||
to do this. */
|
||||
fro = first_rtl_op (code);
|
||||
|
||||
/* Expressions without side effects may be constant if their
|
||||
arguments are as well. */
|
||||
constant = (TREE_CODE_CLASS (code) == '<'
|
||||
|| TREE_CODE_CLASS (code) == '1'
|
||||
|| TREE_CODE_CLASS (code) == '2'
|
||||
|| TREE_CODE_CLASS (code) == 'c');
|
||||
|
||||
if (length == 2)
|
||||
{
|
||||
/* This is equivalent to the loop below, but faster. */
|
||||
tree arg0 = va_arg (p, tree);
|
||||
tree arg1 = va_arg (p, tree);
|
||||
|
||||
TREE_OPERAND (t, 0) = arg0;
|
||||
TREE_OPERAND (t, 1) = arg1;
|
||||
TREE_READONLY (t) = 1;
|
||||
if (arg0 && fro > 0)
|
||||
{
|
||||
if (TREE_SIDE_EFFECTS (arg0))
|
||||
TREE_SIDE_EFFECTS (t) = 1;
|
||||
if (!TREE_READONLY (arg0))
|
||||
TREE_READONLY (t) = 0;
|
||||
if (!TREE_CONSTANT (arg0))
|
||||
constant = 0;
|
||||
}
|
||||
|
||||
if (arg1 && fro > 1)
|
||||
{
|
||||
if (TREE_SIDE_EFFECTS (arg1))
|
||||
TREE_SIDE_EFFECTS (t) = 1;
|
||||
if (!TREE_READONLY (arg1))
|
||||
TREE_READONLY (t) = 0;
|
||||
if (!TREE_CONSTANT (arg1))
|
||||
constant = 0;
|
||||
}
|
||||
}
|
||||
else if (length == 1)
|
||||
{
|
||||
tree arg0 = va_arg (p, tree);
|
||||
|
||||
/* The only one-operand cases we handle here are those with side-effects.
|
||||
Others are handled with build1. So don't bother checked if the
|
||||
arg has side-effects since we'll already have set it.
|
||||
|
||||
??? This really should use build1 too. */
|
||||
if (TREE_CODE_CLASS (code) != 's')
|
||||
abort ();
|
||||
TREE_OPERAND (t, 0) = arg0;
|
||||
}
|
||||
else
|
||||
{
|
||||
for (i = 0; i < length; i++)
|
||||
{
|
||||
tree operand = va_arg (p, tree);
|
||||
|
||||
TREE_OPERAND (t, i) = operand;
|
||||
if (operand && fro > i)
|
||||
{
|
||||
if (TREE_SIDE_EFFECTS (operand))
|
||||
TREE_SIDE_EFFECTS (t) = 1;
|
||||
if (!TREE_CONSTANT (operand))
|
||||
constant = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
va_end (p);
|
||||
|
||||
TREE_CONSTANT (t) = constant;
|
||||
|
||||
if (code == CALL_EXPR && !TREE_SIDE_EFFECTS (t))
|
||||
{
|
||||
/* Calls have side-effects, except those to const or
|
||||
pure functions. */
|
||||
i = call_expr_flags (t);
|
||||
if (!(i & (ECF_CONST | ECF_PURE)))
|
||||
TREE_SIDE_EFFECTS (t) = 1;
|
||||
|
||||
/* And even those have side-effects if their arguments do. */
|
||||
else for (node = TREE_OPERAND (t, 1); node; node = TREE_CHAIN (node))
|
||||
if (TREE_SIDE_EFFECTS (TREE_VALUE (node)))
|
||||
{
|
||||
TREE_SIDE_EFFECTS (t) = 1;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return t;
|
||||
}
|
||||
|
||||
/* Same as above, but only builds for unary operators.
|
||||
Saves lions share of calls to `build'; cuts down use
|
||||
of varargs, which is expensive for RISC machines. */
|
||||
|
||||
tree
|
||||
build1 (enum tree_code code, tree type, tree node)
|
||||
{
|
||||
|
@ -2435,9 +2339,7 @@ build1 (enum tree_code code, tree type, tree node)
|
|||
#endif
|
||||
|
||||
#ifdef ENABLE_CHECKING
|
||||
if (TREE_CODE_CLASS (code) == '2'
|
||||
|| TREE_CODE_CLASS (code) == '<'
|
||||
|| TREE_CODE_LENGTH (code) != 1)
|
||||
if (TREE_CODE_LENGTH (code) != 1)
|
||||
abort ();
|
||||
#endif /* ENABLE_CHECKING */
|
||||
|
||||
|
@ -2512,6 +2414,191 @@ build1 (enum tree_code code, tree type, tree node)
|
|||
return t;
|
||||
}
|
||||
|
||||
#define PROCESS_ARG(N) \
|
||||
do { \
|
||||
TREE_OPERAND (t, N) = arg##N; \
|
||||
if (arg##N && fro > N) \
|
||||
{ \
|
||||
if (TREE_SIDE_EFFECTS (arg##N)) \
|
||||
side_effects = 1; \
|
||||
if (!TREE_READONLY (arg##N)) \
|
||||
read_only = 0; \
|
||||
if (!TREE_CONSTANT (arg##N)) \
|
||||
constant = 0; \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
tree
|
||||
build2 (enum tree_code code, tree tt, tree arg0, tree arg1)
|
||||
{
|
||||
bool constant, read_only, side_effects;
|
||||
tree t;
|
||||
int fro;
|
||||
|
||||
#ifdef ENABLE_CHECKING
|
||||
if (TREE_CODE_LENGTH (code) != 2)
|
||||
abort ();
|
||||
#endif
|
||||
|
||||
t = make_node (code);
|
||||
TREE_TYPE (t) = tt;
|
||||
|
||||
/* Below, we automatically set TREE_SIDE_EFFECTS and TREE_READONLY for the
|
||||
result based on those same flags for the arguments. But if the
|
||||
arguments aren't really even `tree' expressions, we shouldn't be trying
|
||||
to do this. */
|
||||
fro = first_rtl_op (code);
|
||||
|
||||
/* Expressions without side effects may be constant if their
|
||||
arguments are as well. */
|
||||
constant = (TREE_CODE_CLASS (code) == '<'
|
||||
|| TREE_CODE_CLASS (code) == '2');
|
||||
read_only = 1;
|
||||
side_effects = TREE_SIDE_EFFECTS (t);
|
||||
|
||||
PROCESS_ARG(0);
|
||||
PROCESS_ARG(1);
|
||||
|
||||
if (code == CALL_EXPR && !side_effects)
|
||||
{
|
||||
tree node;
|
||||
int i;
|
||||
|
||||
/* Calls have side-effects, except those to const or
|
||||
pure functions. */
|
||||
i = call_expr_flags (t);
|
||||
if (!(i & (ECF_CONST | ECF_PURE)))
|
||||
side_effects = 1;
|
||||
|
||||
/* And even those have side-effects if their arguments do. */
|
||||
else for (node = TREE_OPERAND (t, 1); node; node = TREE_CHAIN (node))
|
||||
if (TREE_SIDE_EFFECTS (TREE_VALUE (node)))
|
||||
{
|
||||
side_effects = 1;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
TREE_READONLY (t) = read_only;
|
||||
TREE_CONSTANT (t) = constant;
|
||||
TREE_SIDE_EFFECTS (t) = side_effects;
|
||||
|
||||
return t;
|
||||
}
|
||||
|
||||
tree
|
||||
build3 (enum tree_code code, tree tt, tree arg0, tree arg1, tree arg2)
|
||||
{
|
||||
bool constant, read_only, side_effects;
|
||||
tree t;
|
||||
int fro;
|
||||
|
||||
/* ??? Quite a lot of existing code passes one too many arguments to
|
||||
CALL_EXPR. Not going to fix them, because CALL_EXPR is about to
|
||||
grow a new argument, so it would just mean changing them back. */
|
||||
if (code == CALL_EXPR)
|
||||
{
|
||||
if (arg2 != NULL_TREE)
|
||||
abort ();
|
||||
return build2 (code, tt, arg0, arg1);
|
||||
}
|
||||
|
||||
#ifdef ENABLE_CHECKING
|
||||
if (TREE_CODE_LENGTH (code) != 3)
|
||||
abort ();
|
||||
#endif
|
||||
|
||||
t = make_node (code);
|
||||
TREE_TYPE (t) = tt;
|
||||
|
||||
fro = first_rtl_op (code);
|
||||
|
||||
side_effects = TREE_SIDE_EFFECTS (t);
|
||||
|
||||
PROCESS_ARG(0);
|
||||
PROCESS_ARG(1);
|
||||
PROCESS_ARG(2);
|
||||
|
||||
TREE_SIDE_EFFECTS (t) = side_effects;
|
||||
|
||||
return t;
|
||||
}
|
||||
|
||||
tree
|
||||
build4 (enum tree_code code, tree tt, tree arg0, tree arg1,
|
||||
tree arg2, tree arg3)
|
||||
{
|
||||
bool constant, read_only, side_effects;
|
||||
tree t;
|
||||
int fro;
|
||||
|
||||
#ifdef ENABLE_CHECKING
|
||||
if (TREE_CODE_LENGTH (code) != 4)
|
||||
abort ();
|
||||
#endif
|
||||
|
||||
t = make_node (code);
|
||||
TREE_TYPE (t) = tt;
|
||||
|
||||
fro = first_rtl_op (code);
|
||||
|
||||
side_effects = TREE_SIDE_EFFECTS (t);
|
||||
|
||||
PROCESS_ARG(0);
|
||||
PROCESS_ARG(1);
|
||||
PROCESS_ARG(2);
|
||||
PROCESS_ARG(3);
|
||||
|
||||
TREE_SIDE_EFFECTS (t) = side_effects;
|
||||
|
||||
return t;
|
||||
}
|
||||
|
||||
/* Backup definition for non-gcc build compilers. */
|
||||
|
||||
tree
|
||||
(build) (enum tree_code code, tree tt, ...)
|
||||
{
|
||||
tree t, arg0, arg1, arg2, arg3;
|
||||
int length = TREE_CODE_LENGTH (code);
|
||||
va_list p;
|
||||
|
||||
va_start (p, tt);
|
||||
switch (length)
|
||||
{
|
||||
case 0:
|
||||
t = build0 (code, tt);
|
||||
break;
|
||||
case 1:
|
||||
arg0 = va_arg (p, tree);
|
||||
t = build1 (code, tt, arg0);
|
||||
break;
|
||||
case 2:
|
||||
arg0 = va_arg (p, tree);
|
||||
arg1 = va_arg (p, tree);
|
||||
t = build2 (code, tt, arg0, arg1);
|
||||
break;
|
||||
case 3:
|
||||
arg0 = va_arg (p, tree);
|
||||
arg1 = va_arg (p, tree);
|
||||
arg2 = va_arg (p, tree);
|
||||
t = build3 (code, tt, arg0, arg1, arg2);
|
||||
break;
|
||||
case 4:
|
||||
arg0 = va_arg (p, tree);
|
||||
arg1 = va_arg (p, tree);
|
||||
arg2 = va_arg (p, tree);
|
||||
arg3 = va_arg (p, tree);
|
||||
t = build4 (code, tt, arg0, arg1, arg2, arg3);
|
||||
break;
|
||||
default:
|
||||
abort ();
|
||||
}
|
||||
va_end (p);
|
||||
|
||||
return t;
|
||||
}
|
||||
|
||||
/* Similar except don't specify the TREE_TYPE
|
||||
and leave the TREE_SIDE_EFFECTS as 0.
|
||||
It is permissible for arguments to be null,
|
||||
|
|
19
gcc/tree.h
19
gcc/tree.h
|
@ -2112,13 +2112,30 @@ extern tree maybe_get_identifier (const char *);
|
|||
extern tree build (enum tree_code, tree, ...);
|
||||
extern tree build_nt (enum tree_code, ...);
|
||||
|
||||
#if GCC_VERSION >= 3000 || __STDC_VERSION__ >= 199901L
|
||||
/* Use preprocessor trickery to map "build" to "buildN" where N is the
|
||||
expected number of arguments. This is used for both efficiency (no
|
||||
varargs), and checking (verifying number of passed arguments). */
|
||||
#define build(code, ...) \
|
||||
_buildN1(build, _buildC1(__VA_ARGS__))(code, __VA_ARGS__)
|
||||
#define _buildN1(BASE, X) _buildN2(BASE, X)
|
||||
#define _buildN2(BASE, X) BASE##X
|
||||
#define _buildC1(...) _buildC2(__VA_ARGS__,9,8,7,6,5,4,3,2,1,0,0)
|
||||
#define _buildC2(x,a1,a2,a3,a4,a5,a6,a7,a8,a9,c,...) c
|
||||
#endif
|
||||
|
||||
extern tree build0 (enum tree_code, tree);
|
||||
extern tree build1 (enum tree_code, tree, tree);
|
||||
extern tree build2 (enum tree_code, tree, tree, tree);
|
||||
extern tree build3 (enum tree_code, tree, tree, tree, tree);
|
||||
extern tree build4 (enum tree_code, tree, tree, tree, tree, tree);
|
||||
|
||||
extern tree build_int_2_wide (unsigned HOST_WIDE_INT, HOST_WIDE_INT);
|
||||
extern tree build_vector (tree, tree);
|
||||
extern tree build_constructor (tree, tree);
|
||||
extern tree build_real_from_int_cst (tree, tree);
|
||||
extern tree build_complex (tree, tree, tree);
|
||||
extern tree build_string (int, const char *);
|
||||
extern tree build1 (enum tree_code, tree, tree);
|
||||
extern tree build_tree_list (tree, tree);
|
||||
extern tree build_decl (enum tree_code, tree, tree);
|
||||
extern tree build_block (tree, tree, tree, tree, tree);
|
||||
|
|
Loading…
Add table
Reference in a new issue