create new branch and first commit

This commit is contained in:
fanfuqiang 2018-08-20 04:10:13 +08:00
parent 9c1a6a1622
commit eadf46b4f3
209 changed files with 133388 additions and 257 deletions

42
src/Makefile Executable file → Normal file
View File

@ -1,6 +1,42 @@
$(HOSTLIBS)-$(CONFIG_PAX_RAP) += rap_plugin.so
always := $($(HOSTLIBS)-y)
GCC_PLUGINS_DIR := $(shell $(CC) -print-file-name=plugin)
rap_plugin-objs := $(patsubst $(srctree)/$(src)/%.c,%.o,$(wildcard $(srctree)/$(src)/*.c))
ifeq ($(PLUGINCC),$(HOSTCC))
HOSTLIBS := hostlibs
HOST_EXTRACFLAGS += -I$(GCC_PLUGINS_DIR)/include -I$(src)
HOST_EXTRACFLAGS += -std=gnu99 -ggdb -fvisibility=hidden
HOST_EXTRACFLAGS += -Wall -W
export HOST_EXTRACFLAGS
else
HOSTLIBS := hostcxxlibs
HOST_EXTRACXXFLAGS += -I$(GCC_PLUGINS_DIR)/include -I$(src)
HOST_EXTRACXXFLAGS += -std=gnu++98 -ggdb -fvisibility=hidden
HOST_EXTRACXXFLAGS += -fno-rtti -fno-exceptions -fasynchronous-unwind-tables
HOST_EXTRACXXFLAGS += -Wall -W
HOST_EXTRACXXFLAGS += -Wno-unused-parameter -Wno-narrowing -Wno-unused-variable
export HOST_EXTRACXXFLAGS
endif
ifneq ($(CFLAGS_KCOV), $(SANCOV_PLUGIN))
GCC_PLUGIN := $(filter-out $(SANCOV_PLUGIN), $(GCC_PLUGIN))
endif
export HOSTLIBS
$(HOSTLIBS)-y := $(foreach p,$(GCC_PLUGIN),$(if $(findstring /,$(p)),,$(p)))
always := $($(HOSTLIBS)-y)
$(foreach p,$($(HOSTLIBS)-y:%.so=%),$(eval $(p)-objs := $(p).o))
$(obj)/randomize_layout_plugin.o: $(objtree)/$(obj)/randomize_layout_seed.h
quiet_cmd_create_randomize_layout_seed = GENSEED $@
cmd_create_randomize_layout_seed = \
$(CONFIG_SHELL) $(srctree)/$(src)/gen-random-seed.sh $@ $(objtree)/include/generated/randomize_layout_hash.h
$(objtree)/$(obj)/randomize_layout_seed.h: FORCE
$(call if_changed,create_randomize_layout_seed)
targets += randomize_layout_seed.h randomize_layout_hash.h
subdir-y := $(GCC_PLUGIN_SUBDIR)
subdir- += $(GCC_PLUGIN_SUBDIR)
clean-files += *.so

491
src/checker_plugin.c Normal file
View File

@ -0,0 +1,491 @@
/*
* Copyright 2011-2017 by the PaX Team <pageexec@freemail.hu>
* Licensed under the GPL v2
*
* Note: the choice of the license means that the compilation process is
* NOT 'eligible' as defined by gcc's library exception to the GPL v3,
* but for the kernel it doesn't matter since it doesn't link against
* any of the gcc libraries
*
* gcc plugin to implement various sparse (source code checker) features
*
* TODO:
* - define separate __iomem, __percpu and __rcu address spaces (lots of code to patch)
*
* BUGS:
* - none known
*/
#include "gcc-common.h"
extern void c_register_addr_space (const char *str, addr_space_t as);
extern enum machine_mode default_addr_space_pointer_mode (addr_space_t);
extern enum machine_mode default_addr_space_address_mode (addr_space_t);
extern bool default_addr_space_valid_pointer_mode(enum machine_mode mode, addr_space_t as);
extern bool default_addr_space_legitimate_address_p(enum machine_mode mode, rtx mem, bool strict, addr_space_t as);
extern rtx default_addr_space_legitimize_address(rtx x, rtx oldx, enum machine_mode mode, addr_space_t as);
__visible int plugin_is_GPL_compatible;
static struct plugin_info checker_plugin_info = {
.version = "201602181345",
.help = "user\tturn on user/kernel address space checking\n"
"context\tturn on locking context checking\n"
};
#define ADDR_SPACE_KERNEL 0
#define ADDR_SPACE_FORCE_KERNEL 1
#define ADDR_SPACE_USER 2
#define ADDR_SPACE_FORCE_USER 3
#define ADDR_SPACE_IOMEM 0
#define ADDR_SPACE_FORCE_IOMEM 0
#define ADDR_SPACE_PERCPU 0
#define ADDR_SPACE_FORCE_PERCPU 0
#define ADDR_SPACE_RCU 0
#define ADDR_SPACE_FORCE_RCU 0
static enum machine_mode checker_addr_space_pointer_mode(addr_space_t addrspace)
{
return default_addr_space_pointer_mode(ADDR_SPACE_GENERIC);
}
static enum machine_mode checker_addr_space_address_mode(addr_space_t addrspace)
{
return default_addr_space_address_mode(ADDR_SPACE_GENERIC);
}
static bool checker_addr_space_valid_pointer_mode(enum machine_mode mode, addr_space_t as)
{
return default_addr_space_valid_pointer_mode(mode, as);
}
static bool checker_addr_space_legitimate_address_p(enum machine_mode mode, rtx mem, bool strict, addr_space_t as)
{
return default_addr_space_legitimate_address_p(mode, mem, strict, ADDR_SPACE_GENERIC);
}
static rtx checker_addr_space_legitimize_address(rtx x, rtx oldx, enum machine_mode mode, addr_space_t as)
{
return default_addr_space_legitimize_address(x, oldx, mode, as);
}
static bool checker_addr_space_subset_p(addr_space_t subset, addr_space_t superset)
{
if (subset == ADDR_SPACE_FORCE_KERNEL && superset == ADDR_SPACE_KERNEL)
return true;
if (subset == ADDR_SPACE_FORCE_USER && superset == ADDR_SPACE_USER)
return true;
if (subset == ADDR_SPACE_FORCE_IOMEM && superset == ADDR_SPACE_IOMEM)
return true;
if (subset == ADDR_SPACE_KERNEL && superset == ADDR_SPACE_FORCE_USER)
return true;
if (subset == ADDR_SPACE_KERNEL && superset == ADDR_SPACE_FORCE_IOMEM)
return true;
if (subset == ADDR_SPACE_USER && superset == ADDR_SPACE_FORCE_KERNEL)
return true;
if (subset == ADDR_SPACE_IOMEM && superset == ADDR_SPACE_FORCE_KERNEL)
return true;
return subset == superset;
}
static rtx checker_addr_space_convert(rtx op, tree from_type, tree to_type)
{
// addr_space_t from_as = TYPE_ADDR_SPACE(TREE_TYPE(from_type));
// addr_space_t to_as = TYPE_ADDR_SPACE(TREE_TYPE(to_type));
return op;
}
static void register_checker_address_spaces(void *event_data, void *data)
{
c_register_addr_space("__kernel", ADDR_SPACE_KERNEL);
c_register_addr_space("__force_kernel", ADDR_SPACE_FORCE_KERNEL);
c_register_addr_space("__user", ADDR_SPACE_USER);
c_register_addr_space("__force_user", ADDR_SPACE_FORCE_USER);
// c_register_addr_space("__iomem", ADDR_SPACE_IOMEM);
// c_register_addr_space("__force_iomem", ADDR_SPACE_FORCE_IOMEM);
// c_register_addr_space("__percpu", ADDR_SPACE_PERCPU);
// c_register_addr_space("__force_percpu", ADDR_SPACE_FORCE_PERCPU);
// c_register_addr_space("__rcu", ADDR_SPACE_RCU);
// c_register_addr_space("__force_rcu", ADDR_SPACE_FORCE_RCU);
targetm.addr_space.pointer_mode = checker_addr_space_pointer_mode;
targetm.addr_space.address_mode = checker_addr_space_address_mode;
targetm.addr_space.valid_pointer_mode = checker_addr_space_valid_pointer_mode;
targetm.addr_space.legitimate_address_p = checker_addr_space_legitimate_address_p;
// targetm.addr_space.legitimize_address = checker_addr_space_legitimize_address;
targetm.addr_space.subset_p = checker_addr_space_subset_p;
targetm.addr_space.convert = checker_addr_space_convert;
}
static bool split_context_attribute(tree args, tree *lock, tree *in, tree *out)
{
*in = TREE_VALUE(args);
if (TREE_CODE(*in) != INTEGER_CST) {
*lock = *in;
args = TREE_CHAIN(args);
*in = TREE_VALUE(args);
} else
*lock = NULL_TREE;
args = TREE_CHAIN(args);
if (*lock && !args)
return false;
*out = TREE_VALUE(args);
return true;
}
static tree handle_context_attribute(tree *node, tree name, tree args, int flags, bool *no_add_attrs)
{
*no_add_attrs = true;
tree lock, in, out;
if (TREE_CODE(*node) != FUNCTION_DECL) {
error("%qE attribute applies to functions only (%qD)", name, *node);
return NULL_TREE;
}
if (!split_context_attribute(args, &lock, &in, &out)) {
error("%qE attribute needs two integers after the lock expression", name);
return NULL_TREE;
}
if (TREE_CODE(in) != INTEGER_CST) {
error("the 'in' argument of the %qE attribute must be an integer (%qE)", name, in);
return NULL_TREE;
}
if (TREE_CODE(out) != INTEGER_CST) {
error("the 'out' argument of the %qE attribute must be an integer (%qE)", name, out);
return NULL_TREE;
}
*no_add_attrs = false;
return NULL_TREE;
}
static struct attribute_spec context_attr = {
.name = "context",
.min_length = 2,
.max_length = 3,
.decl_required = true,
.type_required = false,
.function_type_required = false,
.handler = handle_context_attribute,
#if BUILDING_GCC_VERSION >= 4007
.affects_type_identity = true
#endif
};
static void register_attributes(void *event_data, void *data)
{
register_attribute(&context_attr);
}
static const char context_function[] = "__context__";
static GTY(()) tree context_function_decl;
static const char context_error[] = "__context_error__";
static GTY(()) tree context_error_decl;
static void context_start_unit(void __unused *gcc_data, void __unused *user_data)
{
tree fntype, attr;
// void __context__(void *, int);
fntype = build_function_type_list(void_type_node, ptr_type_node, integer_type_node, NULL_TREE);
context_function_decl = build_fn_decl(context_function, fntype);
TREE_PUBLIC(context_function_decl) = 1;
TREE_USED(context_function_decl) = 1;
DECL_EXTERNAL(context_function_decl) = 1;
DECL_ARTIFICIAL(context_function_decl) = 1;
DECL_PRESERVE_P(context_function_decl) = 1;
// TREE_NOTHROW(context_function_decl) = 1;
// DECL_UNINLINABLE(context_function_decl) = 1;
DECL_ASSEMBLER_NAME(context_function_decl); // for LTO
lang_hooks.decls.pushdecl(context_function_decl);
// void __context_error__(const void *, int) __attribute__((error("context error")));
fntype = build_function_type_list(void_type_node, const_ptr_type_node, integer_type_node, NULL_TREE);
context_error_decl = build_fn_decl(context_error, fntype);
TREE_PUBLIC(context_error_decl) = 1;
TREE_USED(context_error_decl) = 1;
DECL_EXTERNAL(context_error_decl) = 1;
DECL_ARTIFICIAL(context_error_decl) = 1;
DECL_PRESERVE_P(context_error_decl) = 1;
// TREE_NOTHROW(context_error_decl) = 1;
// DECL_UNINLINABLE(context_error_decl) = 1;
TREE_THIS_VOLATILE(context_error_decl) = 1;
DECL_ASSEMBLER_NAME(context_error_decl);
attr = tree_cons(NULL, build_const_char_string(14, "context error"), NULL);
attr = tree_cons(get_identifier("error"), attr, NULL);
decl_attributes(&context_error_decl, attr, 0);
}
static bool context_gate(void)
{
tree context_attr;
return true;
context_attr = lookup_attribute("context", DECL_ATTRIBUTES(current_function_decl));
return context_attr != NULL_TREE;
}
static basic_block verify_context_before(gimple_stmt_iterator *gsi, tree context, tree inout, tree error)
{
gimple stmt;
basic_block cond_bb, join_bb, true_bb;
edge e;
location_t loc;
const char *file;
int line;
size_t len;
tree filename;
stmt = gsi_stmt(*gsi);
if (gimple_has_location(stmt)) {
loc = gimple_location(stmt);
file = gimple_filename(stmt);
line = gimple_lineno(stmt);
} else {
loc = DECL_SOURCE_LOCATION(current_function_decl);
file = DECL_SOURCE_FILE(current_function_decl);
line = DECL_SOURCE_LINE(current_function_decl);
}
gcc_assert(file);
// if (context != count) __context_error__(__FILE__, __LINE__);
stmt = gimple_build_cond(NE_EXPR, context, inout, NULL_TREE, NULL_TREE);
gimple_set_location(stmt, loc);
gsi_insert_before(gsi, stmt, GSI_NEW_STMT);
cond_bb = gsi_bb(*gsi);
gcc_assert(!gsi_end_p(*gsi));
gcc_assert(stmt == gsi_stmt(*gsi));
e = split_block(cond_bb, gsi_stmt(*gsi));
cond_bb = e->src;
join_bb = e->dest;
e->flags = EDGE_FALSE_VALUE;
e->probability = REG_BR_PROB_BASE;
true_bb = create_empty_bb(EXIT_BLOCK_PTR_FOR_FN(cfun)->prev_bb);
make_edge(cond_bb, true_bb, EDGE_TRUE_VALUE);
make_edge(true_bb, join_bb, EDGE_FALLTHRU);
set_immediate_dominator(CDI_DOMINATORS, true_bb, cond_bb);
set_immediate_dominator(CDI_DOMINATORS, join_bb, cond_bb);
gcc_assert(cond_bb->loop_father == join_bb->loop_father);
add_bb_to_loop(true_bb, cond_bb->loop_father);
// insert call to builtin_trap or __context_error__
*gsi = gsi_start_bb(true_bb);
// stmt = gimple_build_call(builtin_decl_implicit(BUILT_IN_TRAP), 0);
len = strlen(file) + 1;
filename = build_const_char_string(len, file);
filename = build1(ADDR_EXPR, const_ptr_type_node, filename);
stmt = gimple_build_call(error, 2, filename, build_int_cst(NULL_TREE, line));
gimple_set_location(stmt, loc);
gsi_insert_after(gsi, stmt, GSI_CONTINUE_LINKING);
*gsi = gsi_start_nondebug_bb(join_bb);
return join_bb;
}
static void update_context(gimple_stmt_iterator *gsi, tree context, int diff)
{
gimple assign;
tree op;
op = fold_build2_loc(UNKNOWN_LOCATION, PLUS_EXPR, integer_type_node, context, build_int_cst(integer_type_node, diff));
assign = gimple_build_assign(context, op);
gsi_insert_after(gsi, assign, GSI_NEW_STMT);
update_stmt(assign);
}
static basic_block track_context(basic_block bb, tree context)
{
gimple_stmt_iterator gsi;
gimple assign;
// adjust context according to the context information on any call stmt
for (gsi = gsi_start_bb(bb); !gsi_end_p(gsi); gsi_next(&gsi)) {
gimple stmt = gsi_stmt(gsi);
tree fndecl, context_attr;
tree lock, in, out;
int incount, outcount;
if (!is_gimple_call(stmt))
continue;
fndecl = gimple_call_fndecl(stmt);
if (!fndecl)
continue;
if (fndecl == context_function_decl) {
unsigned int num_ops = gimple_num_ops(stmt);
int diff = tree_to_shwi(gimple_op(stmt, num_ops - 1));
gcc_assert(diff);
update_context(&gsi, context, diff);
continue;
}
context_attr = lookup_attribute("context", DECL_ATTRIBUTES(fndecl));
if (!context_attr)
continue;
gcc_assert(split_context_attribute(TREE_VALUE(context_attr), &lock, &in, &out));
incount = tree_to_shwi(in);
outcount = tree_to_shwi(out);
bb = verify_context_before(&gsi, context, in, context_error_decl);
update_context(&gsi, context, outcount - incount);
}
return bb;
}
static bool bb_any_loop(basic_block bb)
{
return bb_loop_depth(bb) || (bb->flags & BB_IRREDUCIBLE_LOOP);
}
static unsigned int context_execute(void)
{
basic_block bb;
gimple assign;
gimple_stmt_iterator gsi;
tree context_attr, context;
tree lock, in, out;
loop_optimizer_init(LOOPS_NORMAL | LOOPS_HAVE_RECORDED_EXITS);
gcc_assert(current_loops);
calculate_dominance_info(CDI_DOMINATORS);
calculate_dominance_info(CDI_POST_DOMINATORS);
context_attr = lookup_attribute("context", DECL_ATTRIBUTES(current_function_decl));
if (context_attr) {
gcc_assert(split_context_attribute(TREE_VALUE(context_attr), &lock, &in, &out));
} else {
in = out = integer_zero_node;
}
// 1. create local context variable
context = create_tmp_var(integer_type_node, "context");
add_referenced_var(context);
mark_sym_for_renaming(context);
// 2. initialize local context variable
gcc_assert(single_succ_p(ENTRY_BLOCK_PTR_FOR_FN(cfun)));
bb = single_succ(ENTRY_BLOCK_PTR_FOR_FN(cfun));
if (!single_pred_p(bb)) {
gcc_assert(bb_any_loop(bb));
split_edge(single_succ_edge(ENTRY_BLOCK_PTR_FOR_FN(cfun)));
bb = single_succ(ENTRY_BLOCK_PTR_FOR_FN(cfun));
}
gsi = gsi_start_bb(bb);
assign = gimple_build_assign(context, in);
gsi_insert_before(&gsi, assign, GSI_NEW_STMT);
update_stmt(assign);
// 3. instrument each BB to track the local context variable
FOR_EACH_BB_FN(bb, cfun) {
bb = track_context(bb, context);
}
// 4. verify the local context variable against the expected state
if (EDGE_COUNT(EXIT_BLOCK_PTR_FOR_FN(cfun)->preds)) {
gcc_assert(single_pred_p(EXIT_BLOCK_PTR_FOR_FN(cfun)));
gsi = gsi_last_nondebug_bb(single_pred(EXIT_BLOCK_PTR_FOR_FN(cfun)));
verify_context_before(&gsi, context, out, context_error_decl);
}
free_dominance_info(CDI_DOMINATORS);
free_dominance_info(CDI_POST_DOMINATORS);
loop_optimizer_finalize();
return 0;
}
#define PASS_NAME context
#define PROPERTIES_REQUIRED PROP_gimple_leh | PROP_cfg
//#define TODO_FLAGS_START TODO_verify_ssa | TODO_verify_flow | TODO_verify_stmts
#define TODO_FLAGS_FINISH TODO_verify_ssa | TODO_verify_stmts | TODO_dump_func | TODO_verify_flow | TODO_update_ssa
#include "gcc-generate-gimple-pass.h"
__visible int plugin_init(struct plugin_name_args *plugin_info, struct plugin_gcc_version *version)
{
const char * const plugin_name = plugin_info->base_name;
const int argc = plugin_info->argc;
const struct plugin_argument * const argv = plugin_info->argv;
int i;
bool enable_user, enable_context;
static const struct ggc_root_tab gt_ggc_r_gt_checker[] = {
{
.base = &context_function_decl,
.nelt = 1,
.stride = sizeof(context_function_decl),
.cb = &gt_ggc_mx_tree_node,
.pchw = &gt_pch_nx_tree_node
},
{
.base = &context_error_decl,
.nelt = 1,
.stride = sizeof(context_error_decl),
.cb = &gt_ggc_mx_tree_node,
.pchw = &gt_pch_nx_tree_node
},
LAST_GGC_ROOT_TAB
};
// PASS_INFO(context, "ssa", 1, PASS_POS_INSERT_AFTER);
PASS_INFO(context, "phiprop", 1, PASS_POS_INSERT_AFTER);
if (!plugin_default_version_check(version, &gcc_version)) {
error_gcc_version(version);
return 1;
}
register_callback(plugin_name, PLUGIN_INFO, NULL, &checker_plugin_info);
enable_user = false;
enable_context = false;
for (i = 0; i < argc; ++i) {
if (!strcmp(argv[i].key, "user")) {
enable_user = true;
continue;
}
if (!strcmp(argv[i].key, "context")) {
enable_context = true;
continue;
}
error(G_("unknown option '-fplugin-arg-%s-%s'"), plugin_name, argv[i].key);
}
if (enable_user)
register_callback(plugin_name, PLUGIN_PRAGMAS, register_checker_address_spaces, NULL);
if (enable_context) {
register_callback(plugin_name, PLUGIN_ATTRIBUTES, register_attributes, NULL);
register_callback(plugin_name, PLUGIN_START_UNIT, context_start_unit, NULL);
register_callback(plugin_name, PLUGIN_REGISTER_GGC_ROOTS, NULL, (void *)&gt_ggc_r_gt_checker);
register_callback(plugin_name, PLUGIN_PASS_MANAGER_SETUP, NULL, &context_pass_info);
}
return 0;
}

158
src/colorize_plugin.c Normal file
View File

@ -0,0 +1,158 @@
/*
* Copyright 2012-2017 by PaX Team <pageexec@freemail.hu>
* Licensed under the GPL v2
*
* Note: the choice of the license means that the compilation process is
* NOT 'eligible' as defined by gcc's library exception to the GPL v3,
* but for the kernel it doesn't matter since it doesn't link against
* any of the gcc libraries
*
* gcc plugin to colorize diagnostic output
*
*/
#include "gcc-common.h"
__visible int plugin_is_GPL_compatible;
static struct plugin_info colorize_plugin_info = {
.version = "201602181345",
.help = "color=[never|always|auto]\tdetermine when to colorize\n",
};
#define GREEN "\033[32m\033[K"
#define LIGHTGREEN "\033[1;32m\033[K"
#define YELLOW "\033[33m\033[K"
#define LIGHTYELLOW "\033[1;33m\033[K"
#define RED "\033[31m\033[K"
#define LIGHTRED "\033[1;31m\033[K"
#define BLUE "\033[34m\033[K"
#define LIGHTBLUE "\033[1;34m\033[K"
#define BRIGHT "\033[1;m\033[K"
#define NORMAL "\033[m\033[K"
static diagnostic_starter_fn old_starter;
static diagnostic_finalizer_fn old_finalizer;
static void start_colorize(diagnostic_context *context, diagnostic_info *diagnostic)
{
const char *color;
char *newprefix;
switch (diagnostic->kind) {
case DK_NOTE:
color = LIGHTBLUE;
break;
case DK_PEDWARN:
case DK_WARNING:
color = LIGHTYELLOW;
break;
case DK_ERROR:
case DK_FATAL:
case DK_ICE:
case DK_PERMERROR:
case DK_SORRY:
color = LIGHTRED;
break;
default:
color = NORMAL;
}
old_starter(context, diagnostic);
if (-1 == asprintf(&newprefix, "%s%s" NORMAL, color, context->printer->prefix))
return;
pp_destroy_prefix(context->printer);
pp_set_prefix(context->printer, newprefix);
}
static void finalize_colorize(diagnostic_context *context, diagnostic_info *diagnostic)
{
old_finalizer(context, diagnostic);
}
static void colorize_arm(void)
{
old_starter = diagnostic_starter(global_dc);
old_finalizer = diagnostic_finalizer(global_dc);
diagnostic_starter(global_dc) = start_colorize;
diagnostic_finalizer(global_dc) = finalize_colorize;
}
static unsigned int colorize_rearm_execute(void)
{
if (diagnostic_starter(global_dc) == start_colorize)
return 0;
colorize_arm();
return 0;
}
#define PASS_NAME colorize_rearm
#define NO_GATE
#include "gcc-generate-simple_ipa-pass.h"
static void colorize_start_unit(void *gcc_data __unused, void *user_data __unused)
{
colorize_arm();
}
static bool should_colorize(void)
{
#if BUILDING_GCC_VERSION >= 4009
return false;
#else
char const *t = getenv("TERM");
return t && strcmp(t, "dumb") && isatty(STDERR_FILENO);
#endif
}
__visible int plugin_init(struct plugin_name_args *plugin_info, struct plugin_gcc_version *version)
{
const char * const plugin_name = plugin_info->base_name;
const int argc = plugin_info->argc;
const struct plugin_argument * const argv = plugin_info->argv;
int i;
bool colorize;
PASS_INFO(colorize_rearm, "*free_lang_data", 1, PASS_POS_INSERT_AFTER);
if (!plugin_default_version_check(version, &gcc_version)) {
error_gcc_version(version);
return 1;
}
register_callback(plugin_name, PLUGIN_INFO, NULL, &colorize_plugin_info);
colorize = getenv("GCC_COLORS") ? should_colorize() : false;
for (i = 0; i < argc; ++i) {
if (!strcmp(argv[i].key, "color")) {
if (!argv[i].value) {
error(G_("no value supplied for option '-fplugin-arg-%s-%s'"), plugin_name, argv[i].key);
continue;
}
if (!strcmp(argv[i].value, "always"))
colorize = true;
else if (!strcmp(argv[i].value, "never"))
colorize = false;
else if (!strcmp(argv[i].value, "auto"))
colorize = should_colorize();
else
error(G_("invalid option argument '-fplugin-arg-%s-%s=%s'"), plugin_name, argv[i].key, argv[i].value);
continue;
}
error(G_("unknown option '-fplugin-arg-%s-%s'"), plugin_name, argv[i].key);
}
if (colorize) {
// TODO: parse GCC_COLORS as used by gcc 4.9+
register_callback(plugin_name, PLUGIN_START_UNIT, &colorize_start_unit, NULL);
register_callback(plugin_name, PLUGIN_PASS_MANAGER_SETUP, NULL, &colorize_rearm_pass_info);
}
return 0;
}

577
src/constify_plugin.c Normal file
View File

@ -0,0 +1,577 @@
/*
* Copyright 2011 by Emese Revfy <re.emese@gmail.com>
* Copyright 2011-2017 by PaX Team <pageexec@freemail.hu>
* Licensed under the GPL v2, or (at your option) v3
*
* This gcc plugin constifies all structures which contain only function pointers or are explicitly marked for constification.
*
* Homepage:
* http://www.grsecurity.net/~ephox/const_plugin/
*
* Usage:
* $ gcc -I`gcc -print-file-name=plugin`/include -fPIC -shared -O2 -o constify_plugin.so constify_plugin.c
* $ gcc -fplugin=constify_plugin.so test.c -O2
*/
#include "gcc-common.h"
// unused C type flag in all versions 4.5-6
#define TYPE_CONSTIFY_VISITED(TYPE) TYPE_LANG_FLAG_4(TYPE)
__visible int plugin_is_GPL_compatible;
static bool enabled = true;
static struct plugin_info const_plugin_info = {
.version = "201607241840",
.help = "disable\tturn off constification\n",
};
static struct {
const char *name;
const char *asm_op;
} const_sections[] = {
{".init.rodata", "\t.section\t.init.rodata,\"a\""},
{".ref.rodata", "\t.section\t.ref.rodata,\"a\""},
{".devinit.rodata", "\t.section\t.devinit.rodata,\"a\""},
{".devexit.rodata", "\t.section\t.devexit.rodata,\"a\""},
{".cpuinit.rodata", "\t.section\t.cpuinit.rodata,\"a\""},
{".cpuexit.rodata", "\t.section\t.cpuexit.rodata,\"a\""},
{".meminit.rodata", "\t.section\t.meminit.rodata,\"a\""},
{".memexit.rodata", "\t.section\t.memexit.rodata,\"a\""},
{".data..read_only", "\t.section\t.data..read_only,\"a\""},
};
typedef struct {
bool has_fptr_field;
bool has_writable_field;
bool has_do_const_field;
bool has_no_const_field;
} constify_info;
static const_tree get_field_type(const_tree field)
{
return strip_array_types(TREE_TYPE(field));
}
static bool is_fptr(const_tree field)
{
const_tree ptr = get_field_type(field);
if (TREE_CODE(ptr) != POINTER_TYPE)
return false;
return TREE_CODE(TREE_TYPE(ptr)) == FUNCTION_TYPE;
}
/*
* determine whether the given structure type meets the requirements for automatic constification,
* including the constification attributes on nested structure types
*/
static void constifiable(const_tree node, constify_info *cinfo)
{
const_tree field;
gcc_assert(TREE_CODE(node) == RECORD_TYPE || TREE_CODE(node) == UNION_TYPE);
// e.g., pointer to structure fields while still constructing the structure type
if (TYPE_FIELDS(node) == NULL_TREE)
return;
for (field = TYPE_FIELDS(node); field; field = TREE_CHAIN(field)) {
const_tree type = get_field_type(field);
enum tree_code code = TREE_CODE(type);
if (node == type)
continue;
if (is_fptr(field))
cinfo->has_fptr_field = true;
else if (code == RECORD_TYPE || code == UNION_TYPE) {
if (lookup_attribute("do_const", TYPE_ATTRIBUTES(type)))
cinfo->has_do_const_field = true;
else if (lookup_attribute("no_const", TYPE_ATTRIBUTES(type)))
cinfo->has_no_const_field = true;
else
constifiable(type, cinfo);
} else if (!TREE_READONLY(field))
cinfo->has_writable_field = true;
}
}
static bool constified(const_tree node)
{
constify_info cinfo = {
.has_fptr_field = false,
.has_writable_field = false,
.has_do_const_field = false,
.has_no_const_field = false
};
gcc_assert(TREE_CODE(node) == RECORD_TYPE || TREE_CODE(node) == UNION_TYPE);
if (lookup_attribute("no_const", TYPE_ATTRIBUTES(node))) {
// gcc_assert(!TYPE_READONLY(node));
return false;
}
if (lookup_attribute("do_const", TYPE_ATTRIBUTES(node))) {
gcc_assert(TYPE_READONLY(node));
return true;
}
constifiable(node, &cinfo);
if ((!cinfo.has_fptr_field || cinfo.has_writable_field || cinfo.has_no_const_field) && !cinfo.has_do_const_field)
return false;
return TYPE_READONLY(node);
}
static void deconstify_tree(tree node);
static void deconstify_type(tree type)
{
tree field;
gcc_assert(TREE_CODE(type) == RECORD_TYPE || TREE_CODE(type) == UNION_TYPE);
for (field = TYPE_FIELDS(type); field; field = TREE_CHAIN(field)) {
const_tree fieldtype = get_field_type(field);
// special case handling of simple ptr-to-same-array-type members
if (TREE_CODE(TREE_TYPE(field)) == POINTER_TYPE) {
tree ptrtype = TREE_TYPE(TREE_TYPE(field));
if (TREE_TYPE(TREE_TYPE(field)) == type)
continue;
if (TREE_CODE(ptrtype) != RECORD_TYPE && TREE_CODE(ptrtype) != UNION_TYPE)
continue;
if (!constified(ptrtype))
continue;
if (TYPE_MAIN_VARIANT(ptrtype) == TYPE_MAIN_VARIANT(type))
TREE_TYPE(field) = build_pointer_type(build_qualified_type(type, TYPE_QUALS(ptrtype) & ~TYPE_QUAL_CONST));
continue;
}
if (TREE_CODE(fieldtype) != RECORD_TYPE && TREE_CODE(fieldtype) != UNION_TYPE)
continue;
if (!constified(fieldtype))
continue;
deconstify_tree(field);
TREE_READONLY(field) = 0;
}
TYPE_READONLY(type) = 0;
C_TYPE_FIELDS_READONLY(type) = 0;
if (lookup_attribute("do_const", TYPE_ATTRIBUTES(type))) {
TYPE_ATTRIBUTES(type) = copy_list(TYPE_ATTRIBUTES(type));
TYPE_ATTRIBUTES(type) = remove_attribute("do_const", TYPE_ATTRIBUTES(type));
}
}
static void deconstify_tree(tree node)
{
tree old_type, new_type, field;
old_type = TREE_TYPE(node);
while (TREE_CODE(old_type) == ARRAY_TYPE && TREE_CODE(TREE_TYPE(old_type)) != ARRAY_TYPE) {
node = TREE_TYPE(node) = copy_node(old_type);
old_type = TREE_TYPE(old_type);
}
gcc_assert(TREE_CODE(old_type) == RECORD_TYPE || TREE_CODE(old_type) == UNION_TYPE);
gcc_assert(TYPE_READONLY(old_type) && (TYPE_QUALS(old_type) & TYPE_QUAL_CONST));
new_type = build_qualified_type(old_type, TYPE_QUALS(old_type) & ~TYPE_QUAL_CONST);
TYPE_FIELDS(new_type) = copy_list(TYPE_FIELDS(new_type));
for (field = TYPE_FIELDS(new_type); field; field = TREE_CHAIN(field))
DECL_FIELD_CONTEXT(field) = new_type;
deconstify_type(new_type);
TREE_TYPE(node) = new_type;
}
static tree handle_no_const_attribute(tree *node, tree name, tree args __unused, int flags __unused, bool *no_add_attrs)
{
tree type;
constify_info cinfo = {
.has_fptr_field = false,
.has_writable_field = false,
.has_do_const_field = false,
.has_no_const_field = false
};
*no_add_attrs = true;
if (TREE_CODE(*node) == FUNCTION_DECL) {
error("%qE attribute does not apply to functions (%qF)", name, *node);
return NULL_TREE;
}
if (TREE_CODE(*node) == PARM_DECL) {
error("%qE attribute does not apply to function parameters (%qD)", name, *node);
return NULL_TREE;
}
if (TREE_CODE(*node) == VAR_DECL) {
error("%qE attribute does not apply to variables (%qD)", name, *node);
return NULL_TREE;
}
if (TYPE_P(*node)) {
type = *node;
} else {
if (TREE_CODE(*node) != TYPE_DECL) {
error("%qE attribute does not apply to %qD (%qT)", name, *node, TREE_TYPE(*node));
return NULL_TREE;
}
type = TREE_TYPE(*node);
}
if (TREE_CODE(type) != RECORD_TYPE && TREE_CODE(type) != UNION_TYPE) {
error("%qE attribute used on %qT applies to struct and union types only", name, type);
return NULL_TREE;
}
if (lookup_attribute(IDENTIFIER_POINTER(name), TYPE_ATTRIBUTES(type))) {
error("%qE attribute is already applied to the type %qT", name, type);
return NULL_TREE;
}
if (TYPE_P(*node)) {
if (lookup_attribute("do_const", TYPE_ATTRIBUTES(type)))
error("%qE attribute used on type %qT is incompatible with 'do_const'", name, type);
else
*no_add_attrs = false;
return NULL_TREE;
}
constifiable(type, &cinfo);
if ((cinfo.has_fptr_field && !cinfo.has_writable_field && !cinfo.has_no_const_field) || lookup_attribute("do_const", TYPE_ATTRIBUTES(type))) {
if (enabled) {
if TYPE_P(*node)
deconstify_type(*node);
else
deconstify_tree(*node);
}
if (TYPE_P(*node))
TYPE_CONSTIFY_VISITED(*node) = 1;
else
TYPE_CONSTIFY_VISITED(TREE_TYPE(*node)) = 1;
return NULL_TREE;
}
if (enabled && TYPE_FIELDS(type))
error("%qE attribute used on type %qT that is not constified", name, type);
return NULL_TREE;
}
static void constify_type(tree type)
{
gcc_assert(type == TYPE_MAIN_VARIANT(type));
TYPE_READONLY(type) = 1;
C_TYPE_FIELDS_READONLY(type) = 1;
TYPE_CONSTIFY_VISITED(type) = 1;
}
static tree handle_do_const_attribute(tree *node, tree name, tree args __unused, int flags __unused, bool *no_add_attrs)
{
*no_add_attrs = true;
if (!TYPE_P(*node)) {
error("%qE attribute applies to types only (%qD)", name, *node);
return NULL_TREE;
}
if (TREE_CODE(*node) != RECORD_TYPE && TREE_CODE(*node) != UNION_TYPE) {
error("%qE attribute used on %qT applies to struct and union types only", name, *node);
return NULL_TREE;
}
if (lookup_attribute(IDENTIFIER_POINTER(name), TYPE_ATTRIBUTES(*node))) {
error("%qE attribute used on %qT is already applied to the type", name, *node);
return NULL_TREE;
}
if (lookup_attribute("no_const", TYPE_ATTRIBUTES(*node))) {
error("%qE attribute used on %qT is incompatible with 'no_const'", name, *node);
return NULL_TREE;
}
*no_add_attrs = false;
return NULL_TREE;
}
static struct attribute_spec no_const_attr = {
.name = "no_const",
.min_length = 0,
.max_length = 0,
.decl_required = false,
.type_required = false,
.function_type_required = false,
.handler = handle_no_const_attribute,
#if BUILDING_GCC_VERSION >= 4007
.affects_type_identity = true
#endif
};
static struct attribute_spec do_const_attr = {
.name = "do_const",
.min_length = 0,
.max_length = 0,
.decl_required = false,
.type_required = false,
.function_type_required = false,
.handler = handle_do_const_attribute,
#if BUILDING_GCC_VERSION >= 4007
.affects_type_identity = true
#endif
};
static void register_attributes(void *event_data, void *data)
{
register_attribute(&no_const_attr);
register_attribute(&do_const_attr);
}
static void finish_type(void *event_data, void *data __unused)
{
tree type = (tree)event_data;
constify_info cinfo = {
.has_fptr_field = false,
.has_writable_field = false,
.has_do_const_field = false,
.has_no_const_field = false
};
if (type == NULL_TREE || type == error_mark_node)
return;
#if BUILDING_GCC_VERSION >= 5000
if (TREE_CODE(type) == ENUMERAL_TYPE)
return;
#endif
if (TYPE_FIELDS(type) == NULL_TREE || TYPE_CONSTIFY_VISITED(type))
return;
constifiable(type, &cinfo);
if (lookup_attribute("no_const", TYPE_ATTRIBUTES(type))) {
if ((cinfo.has_fptr_field && !cinfo.has_writable_field && !cinfo.has_no_const_field) || cinfo.has_do_const_field) {
deconstify_type(type);
TYPE_CONSTIFY_VISITED(type) = 1;
} else
error("'no_const' attribute used on type %qT that is not constified", type);
return;
}
if (lookup_attribute("do_const", TYPE_ATTRIBUTES(type))) {
if (!cinfo.has_writable_field && !cinfo.has_no_const_field) {
error("'do_const' attribute used on type %qT that is%sconstified", type, cinfo.has_fptr_field ? " " : " not ");
return;
}
constify_type(type);
return;
}
if (cinfo.has_fptr_field && !cinfo.has_writable_field && !cinfo.has_no_const_field) {
if (lookup_attribute("do_const", TYPE_ATTRIBUTES(type))) {
error("'do_const' attribute used on type %qT that is constified", type);
return;
}
constify_type(type);
// TYPE_ATTRIBUTES(type) = copy_list(TYPE_ATTRIBUTES(type));
// TYPE_ATTRIBUTES(type) = tree_cons(get_identifier("do_const"), NULL_TREE, TYPE_ATTRIBUTES(type));
return;
}
deconstify_type(type);
TYPE_CONSTIFY_VISITED(type) = 1;
}
static bool is_constified_var(varpool_node_ptr node)
{
tree var = NODE_DECL(node);
tree type = TREE_TYPE(var);
if (node->alias)
return false;
if (DECL_EXTERNAL(var))
return false;
// XXX handle more complex nesting of arrays/structs
if (TREE_CODE(type) == ARRAY_TYPE)
type = TREE_TYPE(type);
if (TREE_CODE(type) != RECORD_TYPE && TREE_CODE(type) != UNION_TYPE)
return false;
if (!TYPE_READONLY(type) || !C_TYPE_FIELDS_READONLY(type))
return false;
if (!TYPE_CONSTIFY_VISITED(type))
return false;
return true;
}
static void check_section_mismatch(varpool_node_ptr node)
{
tree var, section;
size_t i;
const char *name;
var = NODE_DECL(node);
name = get_decl_section_name(var);
section = lookup_attribute("section", DECL_ATTRIBUTES(var));
if (!section) {
if (name) {
fprintf(stderr, "DECL_SECTION [%s] ", name);
dump_varpool_node(stderr, node);
gcc_unreachable();
}
return;
} else
gcc_assert(name);
//fprintf(stderr, "SECTIONAME: [%s] ", get_decl_section_name(var));
//debug_tree(var);
gcc_assert(!TREE_CHAIN(section));
gcc_assert(TREE_VALUE(section));
section = TREE_VALUE(TREE_VALUE(section));
gcc_assert(!strcmp(TREE_STRING_POINTER(section), name));
//debug_tree(section);
for (i = 0; i < ARRAY_SIZE(const_sections); i++)
if (!strcmp(const_sections[i].name, name))
return;
error_at(DECL_SOURCE_LOCATION(var), "constified variable %qD placed into writable section %E", var, section);
}
// this works around a gcc bug/feature where uninitialized globals
// are moved into the .bss section regardless of any constification
// see gcc/varasm.c:bss_initializer_p()
static void fix_initializer(varpool_node_ptr node)
{
tree var = NODE_DECL(node);
tree type = TREE_TYPE(var);
if (DECL_INITIAL(var))
return;
DECL_INITIAL(var) = build_constructor(type, NULL);
// inform(DECL_SOURCE_LOCATION(var), "constified variable %qE moved into .rodata", var);
}
static void check_global_variables(void *event_data __unused, void *data __unused)
{
varpool_node_ptr node;
FOR_EACH_VARIABLE(node) {
if (!is_constified_var(node))
continue;
check_section_mismatch(node);
fix_initializer(node);
}
}
static unsigned int check_local_variables_execute(void)
{
unsigned int ret = 0;
tree var;
unsigned int i;
FOR_EACH_LOCAL_DECL(cfun, i, var) {
tree type = TREE_TYPE(var);
gcc_assert(DECL_P(var));
if (is_global_var(var))
continue;
if (TREE_CODE(type) != RECORD_TYPE && TREE_CODE(type) != UNION_TYPE)
continue;
if (!TYPE_READONLY(type) || !C_TYPE_FIELDS_READONLY(type))
continue;
if (!TYPE_CONSTIFY_VISITED(type))
continue;
error_at(DECL_SOURCE_LOCATION(var), "constified variable %qE cannot be local", var);
ret = 1;
}
return ret;
}
#define PASS_NAME check_local_variables
#define NO_GATE
#include "gcc-generate-gimple-pass.h"
static unsigned int (*old_section_type_flags)(tree decl, const char *name, int reloc);
static unsigned int constify_section_type_flags(tree decl, const char *name, int reloc)
{
size_t i;
for (i = 0; i < ARRAY_SIZE(const_sections); i++)
if (!strcmp(const_sections[i].name, name))
return 0;
return old_section_type_flags(decl, name, reloc);
}
static void constify_start_unit(void *gcc_data __unused, void *user_data __unused)
{
// size_t i;
// for (i = 0; i < ARRAY_SIZE(const_sections); i++)
// const_sections[i].section = get_unnamed_section(0, output_section_asm_op, const_sections[i].asm_op);
// const_sections[i].section = get_section(const_sections[i].name, 0, NULL);
old_section_type_flags = targetm.section_type_flags;
targetm.section_type_flags = constify_section_type_flags;
}
__visible int plugin_init(struct plugin_name_args *plugin_info, struct plugin_gcc_version *version)
{
const char * const plugin_name = plugin_info->base_name;
const int argc = plugin_info->argc;
const struct plugin_argument * const argv = plugin_info->argv;
int i;
PASS_INFO(check_local_variables, "ssa", 1, PASS_POS_INSERT_BEFORE);
if (!plugin_default_version_check(version, &gcc_version)) {
error_gcc_version(version);
return 1;
}
for (i = 0; i < argc; ++i) {
if (!(strcmp(argv[i].key, "disable"))) {
enabled = false;
continue;
}
error(G_("unknown option '-fplugin-arg-%s-%s'"), plugin_name, argv[i].key);
}
if (strncmp(lang_hooks.name, "GNU C", 5) && !strncmp(lang_hooks.name, "GNU C+", 6)) {
inform(UNKNOWN_LOCATION, G_("%s supports C only, not %s"), plugin_name, lang_hooks.name);
enabled = false;
}
register_callback(plugin_name, PLUGIN_INFO, NULL, &const_plugin_info);
if (enabled) {
register_callback(plugin_name, PLUGIN_ALL_IPA_PASSES_START, check_global_variables, NULL);
register_callback(plugin_name, PLUGIN_FINISH_TYPE, finish_type, NULL);
register_callback(plugin_name, PLUGIN_PASS_MANAGER_SETUP, NULL, &check_local_variables_pass_info);
register_callback(plugin_name, PLUGIN_START_UNIT, constify_start_unit, NULL);
}
register_callback(plugin_name, PLUGIN_ATTRIBUTES, register_attributes, NULL);
return 0;
}

View File

@ -0,0 +1,69 @@
/*
* Copyright 2011-2017 by Emese Revfy <re.emese@gmail.com>
* Licensed under the GPL v2, or (at your option) v3
*
* Homepage:
* https://github.com/ephox-gcc-plugins/cyclomatic_complexity
*
* http://en.wikipedia.org/wiki/Cyclomatic_complexity
* The complexity M is then defined as:
* M = E - N + 2P
* where
*
* E = the number of edges of the graph
* N = the number of nodes of the graph
* P = the number of connected components (exit nodes).
*
* Usage (4.5 - 5):
* $ make clean; make run
*/
#include "gcc-common.h"
__visible int plugin_is_GPL_compatible;
static struct plugin_info cyc_complexity_plugin_info = {
.version = "20160225",
.help = "Cyclomatic Complexity\n",
};
static unsigned int cyc_complexity_execute(void)
{
int complexity;
expanded_location xloc;
/* M = E - N + 2P */
complexity = n_edges_for_fn(cfun) - n_basic_blocks_for_fn(cfun) + 2;
xloc = expand_location(DECL_SOURCE_LOCATION(current_function_decl));
fprintf(stderr, "Cyclomatic Complexity %d %s:%s\n", complexity,
xloc.file, DECL_NAME_POINTER(current_function_decl));
return 0;
}
#define PASS_NAME cyc_complexity
#define NO_GATE
#define TODO_FLAGS_FINISH TODO_dump_func
#include "gcc-generate-gimple-pass.h"
__visible int plugin_init(struct plugin_name_args *plugin_info, struct plugin_gcc_version *version)
{
const char * const plugin_name = plugin_info->base_name;
PASS_INFO(cyc_complexity, "ssa", 1, PASS_POS_INSERT_AFTER);
if (!plugin_default_version_check(version, &gcc_version)) {
error_gcc_version(version);
return 1;
}
register_callback(plugin_name, PLUGIN_INFO, NULL,
&cyc_complexity_plugin_info);
register_callback(plugin_name, PLUGIN_PASS_MANAGER_SETUP, NULL,
&cyc_complexity_pass_info);
return 0;
}

136
src/gcc-common.h Executable file → Normal file
View File

@ -21,14 +21,22 @@
#include "rtl.h"
#include "tm_p.h"
#include "flags.h"
//#include "insn-attr.h"
//#include "insn-config.h"
//#include "insn-flags.h"
#include "hard-reg-set.h"
//#include "recog.h"
#include "output.h"
#include "except.h"
#include "function.h"
#include "toplev.h"
#if BUILDING_GCC_VERSION >= 5000
#include "expr.h"
#endif
#include "basic-block.h"
#include "intl.h"
#include "ggc.h"
//#include "regs.h"
#include "timevar.h"
#include "params.h"
@ -43,12 +51,18 @@
#include "memmodel.h"
#endif
#include "emit-rtl.h"
//#include "reload.h"
//#include "ira.h"
//#include "dwarf2asm.h"
#include "debug.h"
#include "target.h"
#include "langhooks.h"
#include "cfgloop.h"
//#include "hosthooks.h"
#include "cgraph.h"
#include "opts.h"
//#include "coverage.h"
//#include "value-prof.h"
#if BUILDING_GCC_VERSION == 4005
#include <sys/mman.h>
@ -60,6 +74,8 @@
#endif
#if BUILDING_GCC_VERSION >= 4006
//#include "c-tree.h"
//#include "cp/cp-tree.h"
#include "c-family/c-common.h"
#else
#include "c-common.h"
@ -78,8 +94,13 @@
#endif
#include "diagnostic.h"
//#include "tree-diagnostic.h"
#include "tree-dump.h"
#include "tree-pass.h"
#if BUILDING_GCC_VERSION >= 4009
#include "pass_manager.h"
#endif
//#include "df.h"
#include "predict.h"
#include "ipa-utils.h"
@ -90,6 +111,7 @@
#include "internal-fn.h"
#include "gimple-expr.h"
#include "gimple-fold.h"
//#include "diagnostic-color.h"
#include "context.h"
#include "tree-ssa-alias.h"
#include "tree-ssa.h"
@ -115,28 +137,34 @@
#include "ssa-iterators.h"
#endif
//#include "lto/lto.h"
#if BUILDING_GCC_VERSION >= 4007
//#include "data-streamer.h"
#else
//#include "lto-streamer.h"
#endif
//#include "lto-compress.h"
#if BUILDING_GCC_VERSION >= 5000
//#include "lto-section-names.h"
#include "builtins.h"
#endif
/* #include "expr.h" where are you... */
extern rtx emit_move_insn(rtx x, rtx y);
/* missing from basic_block.h... */
extern void debug_dominance_info(enum cdi_direction dir);
extern void debug_dominance_tree(enum cdi_direction dir, basic_block root);
void debug_dominance_info(enum cdi_direction dir);
void debug_dominance_tree(enum cdi_direction dir, basic_block root);
#if BUILDING_GCC_VERSION == 4006
extern void debug_gimple_stmt(gimple);
extern void debug_gimple_seq(gimple_seq);
extern void print_gimple_seq(FILE *, gimple_seq, int, int);
extern void print_gimple_stmt(FILE *, gimple, int, int);
extern void print_gimple_expr(FILE *, gimple, int, int);
extern void dump_gimple_stmt(pretty_printer *, gimple, int, int);
void debug_gimple_stmt(gimple);
void debug_gimple_seq(gimple_seq);
void print_gimple_seq(FILE *, gimple_seq, int, int);
void print_gimple_stmt(FILE *, gimple, int, int);
void print_gimple_expr(FILE *, gimple, int, int);
void dump_gimple_stmt(pretty_printer *, gimple, int, int);
#endif
#define __unused __attribute__((__unused__))
#define __unused __attribute__((unused))
#define __visible __attribute__((visibility("default")))
#define __weak __attribute__((weak))
#define DECL_NAME_POINTER(node) IDENTIFIER_POINTER(DECL_NAME(node))
#define DECL_NAME_LENGTH(node) IDENTIFIER_LENGTH(DECL_NAME(node))
@ -146,6 +174,36 @@ extern void dump_gimple_stmt(pretty_printer *, gimple, int, int);
/* should come from c-tree.h if only it were installed for gcc 4.5... */
#define C_TYPE_FIELDS_READONLY(TYPE) TREE_LANG_FLAG_1(TYPE)
static inline tree build_const_char_string(int len, const char *str)
{
tree cstr, elem, index, type;
cstr = build_string(len, str);
elem = build_type_variant(char_type_node, 1, 0);
index = build_index_type(size_int(len - 1));
type = build_array_type(elem, index);
TREE_TYPE(cstr) = type;
TREE_CONSTANT(cstr) = 1;
TREE_READONLY(cstr) = 1;
TREE_STATIC(cstr) = 1;
return cstr;
}
static inline void error_gcc_version(struct plugin_gcc_version *version)
{
error(G_("incompatible gcc/plugin versions: need %s %s %s %s but have %s %s %s %s"),
gcc_version.basever, gcc_version.datestamp, gcc_version.devphase, gcc_version.revision,
version->basever, version->datestamp, version->devphase, version->revision);
}
#define PASS_INFO(NAME, REF, ID, POS) \
struct register_pass_info NAME##_pass_info = { \
.pass = make_##NAME##_pass(), \
.reference_pass_name = REF, \
.ref_pass_instance_number = ID, \
.pos_op = POS, \
}
#if BUILDING_GCC_VERSION == 4005
#define FOR_EACH_LOCAL_DECL(FUN, I, D) \
for (tree vars = (FUN)->local_decls, (I) = 0; \
@ -172,6 +230,7 @@ static inline bool gimple_call_builtin_p(gimple stmt, enum built_in_function cod
fndecl = gimple_call_fndecl(stmt);
if (!fndecl || DECL_BUILT_IN_CLASS(fndecl) != BUILT_IN_NORMAL)
return false;
// print_node(stderr, "pax", fndecl, 4);
return DECL_FUNCTION_CODE(fndecl) == code;
}
@ -345,6 +404,23 @@ static inline bool gimple_store_p(gimple gs)
static inline void gimple_init_singleton(gimple g __unused)
{
}
enum expand_modifier {
EXPAND_NORMAL = 0,
EXPAND_STACK_PARM,
EXPAND_SUM,
EXPAND_CONST_ADDRESS,
EXPAND_INITIALIZER,
EXPAND_WRITE,
EXPAND_MEMORY
};
rtx expand_expr_real(tree, rtx, enum machine_mode, enum expand_modifier, rtx *);
static inline rtx expand_expr(tree exp, rtx target, enum machine_mode mode, enum expand_modifier modifier)
{
return expand_expr_real(exp, target, mode, modifier, NULL);
}
#endif
#if BUILDING_GCC_VERSION == 4007 || BUILDING_GCC_VERSION == 4008
@ -518,6 +594,28 @@ static inline const greturn *as_a_const_greturn(const_gimple stmt)
#define create_var_ann(var)
#define TODO_dump_func 0
#define TODO_dump_cgraph 0
#define VEC(T, A) vec<T, va_##A>
#define VEC_safe_push(T, A, V, O) vec_safe_push((V), (O));
#endif
#if BUILDING_GCC_VERSION == 4008 || BUILDING_GCC_VERSION == 4009
enum expand_modifier {
EXPAND_NORMAL = 0,
EXPAND_STACK_PARM,
EXPAND_SUM,
EXPAND_CONST_ADDRESS,
EXPAND_INITIALIZER,
EXPAND_WRITE,
EXPAND_MEMORY
};
rtx expand_expr_real(tree, rtx, enum machine_mode, enum expand_modifier, rtx *, bool);
static inline rtx expand_expr(tree exp, rtx target, enum machine_mode mode, enum expand_modifier modifier)
{
return expand_expr_real(exp, target, mode, modifier, NULL, false);
}
#endif
#if BUILDING_GCC_VERSION <= 4009
@ -527,6 +625,8 @@ static inline const greturn *as_a_const_greturn(const_gimple stmt)
#define section_name_prefix LTO_SECTION_NAME_PREFIX
#define fatal_error(loc, gmsgid, ...) fatal_error((gmsgid), __VA_ARGS__)
rtx emit_move_insn(rtx x, rtx y);
typedef struct rtx_def rtx_insn;
static inline const char *get_decl_section_name(const_tree decl)
@ -643,6 +743,11 @@ static inline const greturn *as_a_const_greturn(const_gimple stmt)
#define NODE_DECL(node) (node)->decl
#define cgraph_node_name(node) (node)->name()
#define NODE_IMPLICIT_ALIAS(node) (node)->cpp_implicit_alias
static inline opt_pass *get_pass_for_id(int id)
{
return g->get_passes()->get_pass_for_id(id);
}
#endif
#if BUILDING_GCC_VERSION >= 5000 && BUILDING_GCC_VERSION < 6000
@ -661,6 +766,8 @@ inline bool is_a_helper<const gassign *>::test(const_gimple gs)
#define TODO_verify_stmts TODO_verify_il
#define TODO_verify_rtl_sharing TODO_verify_il
//#define TREE_INT_CST_HIGH(NODE) ({ TREE_INT_CST_EXT_NUNITS(NODE) > 1 ? (unsigned HOST_WIDE_INT)TREE_INT_CST_ELT(NODE, 1) : 0; })
#define INSN_DELETED_P(insn) (insn)->deleted()
static inline const char *get_decl_section_name(const_tree decl)
@ -908,6 +1015,11 @@ static inline void debug_gimple_stmt(const_gimple s)
#define debug_gimple_stmt(s) debug_gimple_stmt(CONST_CAST_GIMPLE(s))
#endif
#if BUILDING_GCC_VERSION < 7001
#define SET_DECL_ALIGN(n, a) ({ DECL_ALIGN(n) = (a); })
#define SET_DECL_MODE(n, m) ({ DECL_MODE(n) = (m); })
#endif
#if BUILDING_GCC_VERSION >= 7000
#define get_inner_reference(exp, pbitsize, pbitpos, poffset, pmode, punsignedp, preversep, pvolatilep, keep_aligning) \
get_inner_reference(exp, pbitsize, pbitpos, poffset, pmode, punsignedp, preversep, pvolatilep)

3
src/gcc-generate-gimple-pass.h Executable file → Normal file
View File

@ -119,7 +119,7 @@ public:
#endif
#endif
virtual opt_pass * clone () { return new _PASS_NAME_PASS(); }
virtual opt_pass *clone() { return new _PASS_NAME_PASS(); }
#ifndef NO_EXECUTE
#if BUILDING_GCC_VERSION >= 5000
@ -136,6 +136,7 @@ opt_pass *_MAKE_PASS_NAME_PASS(void)
return new _PASS_NAME_PASS();
}
#else
struct opt_pass *_MAKE_PASS_NAME_PASS(void);
struct opt_pass *_MAKE_PASS_NAME_PASS(void)
{
return &_PASS_NAME_PASS.pass;

1
src/gcc-generate-ipa-pass.h Executable file → Normal file
View File

@ -225,6 +225,7 @@ opt_pass *_MAKE_PASS_NAME_PASS(void)
return new _PASS_NAME_PASS();
}
#else
struct opt_pass *_MAKE_PASS_NAME_PASS(void);
struct opt_pass *_MAKE_PASS_NAME_PASS(void)
{
return &_PASS_NAME_PASS.pass;

1
src/gcc-generate-rtl-pass.h Executable file → Normal file
View File

@ -136,6 +136,7 @@ opt_pass *_MAKE_PASS_NAME_PASS(void)
return new _PASS_NAME_PASS();
}
#else
struct opt_pass *_MAKE_PASS_NAME_PASS(void);
struct opt_pass *_MAKE_PASS_NAME_PASS(void)
{
return &_PASS_NAME_PASS.pass;

1
src/gcc-generate-simple_ipa-pass.h Executable file → Normal file
View File

@ -136,6 +136,7 @@ opt_pass *_MAKE_PASS_NAME_PASS(void)
return new _PASS_NAME_PASS();
}
#else
struct opt_pass *_MAKE_PASS_NAME_PASS(void);
struct opt_pass *_MAKE_PASS_NAME_PASS(void)
{
return &_PASS_NAME_PASS.pass;

8
src/gen-random-seed.sh Normal file
View File

@ -0,0 +1,8 @@
#!/bin/sh
if [ ! -f "$1" ]; then
SEED=`od -A n -t x8 -N 32 /dev/urandom | tr -d ' \n'`
echo "const char *randstruct_seed = \"$SEED\";" > "$1"
HASH=`echo -n "$SEED" | sha256sum | cut -d" " -f1 | tr -d ' \n'`
echo "#define RANDSTRUCT_HASHED_SEED \"$HASH\"" > "$2"
fi

View File

@ -0,0 +1,74 @@
/****************************************************************************
* *
* GNAT COMPILER COMPONENTS *
* *
* GNAT-SPECIFIC GCC TREE CODES *
* *
* Specification *
* *
* Copyright (C) 1992-2009, Free Software Foundation, Inc. *
* *
* GNAT is free software; you can redistribute it and/or modify it under *
* terms of the GNU General Public License as published by the Free Soft- *
* ware Foundation; either version 3, or (at your option) any later ver- *
* sion. GNAT is distributed in the hope that it will be useful, but WITH- *
* OUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY *
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License *
* for more details. You should have received a copy of the GNU General *
* Public License along with GCC; see the file COPYING3. If not see *
* <http://www.gnu.org/licenses/>. *
* *
* GNAT was originally developed by the GNAT team at New York University. *
* Extensive contributions were provided by Ada Core Technologies Inc. *
* *
****************************************************************************/
/* A type that is an unconstrained array. This node is never passed to GCC.
TREE_TYPE is the type of the fat pointer and TYPE_OBJECT_RECORD_TYPE is
the type of a record containing the template and data. */
DEFTREECODE (UNCONSTRAINED_ARRAY_TYPE, "unconstrained_array_type", tcc_type, 0)
/* A reference to an unconstrained array. This node only exists as an
intermediate node during the translation of a GNAT tree to a GCC tree;
it is never passed to GCC. The only field used is operand 0, which
is the fat pointer object. */
DEFTREECODE (UNCONSTRAINED_ARRAY_REF, "unconstrained_array_ref",
tcc_reference, 1)
/* An expression that returns an RTL suitable for its type. Operand 0
is an expression to be evaluated for side effects only. */
DEFTREECODE (NULL_EXPR, "null_expr", tcc_expression, 1)
/* Same as PLUS_EXPR, except that no modulo reduction is applied.
This is used for loops and never shows up in the tree. */
DEFTREECODE (PLUS_NOMOD_EXPR, "plus_nomod_expr", tcc_binary, 2)
/* Same as MINUS_EXPR, except that no modulo reduction is applied.
This is used for loops and never shows up in the tree. */
DEFTREECODE (MINUS_NOMOD_EXPR, "minus_nomod_expr", tcc_binary, 2)
/* Same as ADDR_EXPR, except that if the operand represents a bit field,
return the address of the byte containing the bit. This is used
for the Address attribute and never shows up in the tree. */
DEFTREECODE (ATTR_ADDR_EXPR, "attr_addr_expr", tcc_reference, 1)
/* Here are the tree codes for the statement types known to Ada. These
must be at the end of this file to allow IS_ADA_STMT to work. */
/* This is how record_code_position and insert_code_for work. The former
makes this tree node, whose operand is a statement. The latter inserts
the actual statements into this node. Gimplification consists of
just returning the inner statement. */
DEFTREECODE (STMT_STMT, "stmt_stmt", tcc_statement, 1)
/* A loop. LOOP_STMT_COND is the test to exit the loop. LOOP_STMT_UPDATE
is the statement to update the loop iteration variable at the continue
point. LOOP_STMT_BODY are the statements in the body of the loop. And
LOOP_STMT_LABEL points to the LABEL_DECL of the end label of the loop. */
DEFTREECODE (LOOP_STMT, "loop_stmt", tcc_statement, 4)
/* Conditionally exit a loop. EXIT_STMT_COND is the condition, which, if
true, will cause the loop to be exited. If no condition is specified,
the loop is unconditionally exited. EXIT_STMT_LABEL is the end label
corresponding to the loop to exit. */
DEFTREECODE (EXIT_STMT, "exit_stmt", tcc_statement, 2)

51
src/include/alias.h Normal file
View File

@ -0,0 +1,51 @@
/* Exported functions from alias.c
Copyright (C) 2004-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GCC_ALIAS_H
#define GCC_ALIAS_H
/* The type of an alias set. Code currently assumes that variables of
this type can take the values 0 (the alias set which aliases
everything) and -1 (sometimes indicating that the alias set is
unknown, sometimes indicating a memory barrier) and -2 (indicating
that the alias set should be set to a unique value but has not been
set yet). */
typedef int alias_set_type;
extern alias_set_type new_alias_set (void);
extern alias_set_type get_alias_set (tree);
extern alias_set_type get_deref_alias_set (tree);
extern alias_set_type get_varargs_alias_set (void);
extern alias_set_type get_frame_alias_set (void);
extern bool component_uses_parent_alias_set (const_tree);
extern bool alias_set_subset_of (alias_set_type, alias_set_type);
extern void record_alias_subset (alias_set_type, alias_set_type);
extern void record_component_aliases (tree);
extern int alias_sets_conflict_p (alias_set_type, alias_set_type);
extern int alias_sets_must_conflict_p (alias_set_type, alias_set_type);
extern int objects_must_conflict_p (tree, tree);
extern int nonoverlapping_memrefs_p (const_rtx, const_rtx, bool);
/* This alias set can be used to force a memory to conflict with all
other memories, creating a barrier across which no memory reference
can move. Note that there are other legacy ways to create such
memory barriers, including an address of SCRATCH. */
#define ALIAS_SET_MEMORY_BARRIER ((alias_set_type) -1)
#endif /* GCC_ALIAS_H */

7
src/include/all-tree.def Normal file
View File

@ -0,0 +1,7 @@
#include "tree.def"
END_OF_BASE_TREE_CODES
#include "c-family/c-common.def"
#include "ada/gcc-interface/ada-tree.def"
#include "cp/cp-tree.def"
#include "java/java-tree.def"
#include "objc/objc-tree.def"

66
src/include/alloc-pool.h Normal file
View File

@ -0,0 +1,66 @@
/* Functions to support a pool of allocatable objects
Copyright (C) 1997-2013 Free Software Foundation, Inc.
Contributed by Daniel Berlin <dan@cgsoftware.com>
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GCC is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef ALLOC_POOL_H
#define ALLOC_POOL_H
typedef unsigned long ALLOC_POOL_ID_TYPE;
typedef struct alloc_pool_list_def
{
struct alloc_pool_list_def *next;
}
*alloc_pool_list;
typedef struct alloc_pool_def
{
const char *name;
#ifdef ENABLE_CHECKING
ALLOC_POOL_ID_TYPE id;
#endif
size_t elts_per_block;
/* These are the elements that have been allocated at least once and freed. */
alloc_pool_list returned_free_list;
/* These are the elements that have not yet been allocated out of
the last block obtained from XNEWVEC. */
char* virgin_free_list;
/* The number of elements in the virgin_free_list that can be
allocated before needing another block. */
size_t virgin_elts_remaining;
size_t elts_allocated;
size_t elts_free;
size_t blocks_allocated;
alloc_pool_list block_list;
size_t block_size;
size_t elt_size;
}
*alloc_pool;
extern alloc_pool create_alloc_pool (const char *, size_t, size_t);
extern void free_alloc_pool (alloc_pool);
extern void empty_alloc_pool (alloc_pool);
extern void free_alloc_pool_if_empty (alloc_pool *);
extern void *pool_alloc (alloc_pool) ATTRIBUTE_MALLOC;
extern void pool_free (alloc_pool, void *);
extern void dump_alloc_pool_statistics (void);
#endif

441
src/include/ansidecl.h Normal file
View File

@ -0,0 +1,441 @@
/* ANSI and traditional C compatability macros
Copyright 1991, 1992, 1993, 1994, 1995, 1996, 1998, 1999, 2000, 2001,
2002, 2003, 2004, 2005, 2006, 2007, 2009, 2010
Free Software Foundation, Inc.
This file is part of the GNU C Library.
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA 02110-1301, USA. */
/* ANSI and traditional C compatibility macros
ANSI C is assumed if __STDC__ is #defined.
Macro ANSI C definition Traditional C definition
----- ---- - ---------- ----------- - ----------
ANSI_PROTOTYPES 1 not defined
PTR `void *' `char *'
PTRCONST `void *const' `char *'
LONG_DOUBLE `long double' `double'
const not defined `'
volatile not defined `'
signed not defined `'
VA_START(ap, var) va_start(ap, var) va_start(ap)
Note that it is safe to write "void foo();" indicating a function
with no return value, in all K+R compilers we have been able to test.
For declaring functions with prototypes, we also provide these:
PARAMS ((prototype))
-- for functions which take a fixed number of arguments. Use this
when declaring the function. When defining the function, write a
K+R style argument list. For example:
char *strcpy PARAMS ((char *dest, char *source));
...
char *
strcpy (dest, source)
char *dest;
char *source;
{ ... }
VPARAMS ((prototype, ...))
-- for functions which take a variable number of arguments. Use
PARAMS to declare the function, VPARAMS to define it. For example:
int printf PARAMS ((const char *format, ...));
...
int
printf VPARAMS ((const char *format, ...))
{
...
}
For writing functions which take variable numbers of arguments, we
also provide the VA_OPEN, VA_CLOSE, and VA_FIXEDARG macros. These
hide the differences between K+R <varargs.h> and C89 <stdarg.h> more
thoroughly than the simple VA_START() macro mentioned above.
VA_OPEN and VA_CLOSE are used *instead of* va_start and va_end.
Immediately after VA_OPEN, put a sequence of VA_FIXEDARG calls
corresponding to the list of fixed arguments. Then use va_arg
normally to get the variable arguments, or pass your va_list object
around. You do not declare the va_list yourself; VA_OPEN does it
for you.
Here is a complete example:
int
printf VPARAMS ((const char *format, ...))
{
int result;
VA_OPEN (ap, format);
VA_FIXEDARG (ap, const char *, format);
result = vfprintf (stdout, format, ap);
VA_CLOSE (ap);
return result;
}
You can declare variables either before or after the VA_OPEN,
VA_FIXEDARG sequence. Also, VA_OPEN and VA_CLOSE are the beginning
and end of a block. They must appear at the same nesting level,
and any variables declared after VA_OPEN go out of scope at
VA_CLOSE. Unfortunately, with a K+R compiler, that includes the
argument list. You can have multiple instances of VA_OPEN/VA_CLOSE
pairs in a single function in case you need to traverse the
argument list more than once.
For ease of writing code which uses GCC extensions but needs to be
portable to other compilers, we provide the GCC_VERSION macro that
simplifies testing __GNUC__ and __GNUC_MINOR__ together, and various
wrappers around __attribute__. Also, __extension__ will be #defined
to nothing if it doesn't work. See below.
This header also defines a lot of obsolete macros:
CONST, VOLATILE, SIGNED, PROTO, EXFUN, DEFUN, DEFUN_VOID,
AND, DOTS, NOARGS. Don't use them. */
#ifndef _ANSIDECL_H
#define _ANSIDECL_H 1
#ifdef __cplusplus
extern "C" {
#endif
/* Every source file includes this file,
so they will all get the switch for lint. */
/* LINTLIBRARY */
/* Using MACRO(x,y) in cpp #if conditionals does not work with some
older preprocessors. Thus we can't define something like this:
#define HAVE_GCC_VERSION(MAJOR, MINOR) \
(__GNUC__ > (MAJOR) || (__GNUC__ == (MAJOR) && __GNUC_MINOR__ >= (MINOR)))
and then test "#if HAVE_GCC_VERSION(2,7)".
So instead we use the macro below and test it against specific values. */
/* This macro simplifies testing whether we are using gcc, and if it
is of a particular minimum version. (Both major & minor numbers are
significant.) This macro will evaluate to 0 if we are not using
gcc at all. */
#ifndef GCC_VERSION
#define GCC_VERSION (__GNUC__ * 1000 + __GNUC_MINOR__)
#endif /* GCC_VERSION */
#if defined (__STDC__) || defined(__cplusplus) || defined (_AIX) || (defined (__mips) && defined (_SYSTYPE_SVR4)) || defined(_WIN32)
/* All known AIX compilers implement these things (but don't always
define __STDC__). The RISC/OS MIPS compiler defines these things
in SVR4 mode, but does not define __STDC__. */
/* eraxxon@alumni.rice.edu: The Compaq C++ compiler, unlike many other
C++ compilers, does not define __STDC__, though it acts as if this
was so. (Verified versions: 5.7, 6.2, 6.3, 6.5) */
#define ANSI_PROTOTYPES 1
#define PTR void *
#define PTRCONST void *const
#define LONG_DOUBLE long double
/* PARAMS is often defined elsewhere (e.g. by libintl.h), so wrap it in
a #ifndef. */
#ifndef PARAMS
#define PARAMS(ARGS) ARGS
#endif
#define VPARAMS(ARGS) ARGS
#define VA_START(VA_LIST, VAR) va_start(VA_LIST, VAR)
/* variadic function helper macros */
/* "struct Qdmy" swallows the semicolon after VA_OPEN/VA_FIXEDARG's
use without inhibiting further decls and without declaring an
actual variable. */
#define VA_OPEN(AP, VAR) { va_list AP; va_start(AP, VAR); { struct Qdmy
#define VA_CLOSE(AP) } va_end(AP); }
#define VA_FIXEDARG(AP, T, N) struct Qdmy
#undef const
#undef volatile
#undef signed
/* inline requires special treatment; it's in C99, and GCC >=2.7 supports
it too, but it's not in C89. */
#undef inline
#if __STDC_VERSION__ >= 199901L || defined(__cplusplus) || (defined(__SUNPRO_C) && defined(__C99FEATURES__))
/* it's a keyword */
#else
# if GCC_VERSION >= 2007
# define inline __inline__ /* __inline__ prevents -pedantic warnings */
# else
# define inline /* nothing */
# endif
#endif
/* These are obsolete. Do not use. */
#ifndef IN_GCC
#define CONST const
#define VOLATILE volatile
#define SIGNED signed
#define PROTO(type, name, arglist) type name arglist
#define EXFUN(name, proto) name proto
#define DEFUN(name, arglist, args) name(args)
#define DEFUN_VOID(name) name(void)
#define AND ,
#define DOTS , ...
#define NOARGS void
#endif /* ! IN_GCC */
#else /* Not ANSI C. */
#undef ANSI_PROTOTYPES
#define PTR char *
#define PTRCONST PTR
#define LONG_DOUBLE double
#define PARAMS(args) ()
#define VPARAMS(args) (va_alist) va_dcl
#define VA_START(va_list, var) va_start(va_list)
#define VA_OPEN(AP, VAR) { va_list AP; va_start(AP); { struct Qdmy
#define VA_CLOSE(AP) } va_end(AP); }
#define VA_FIXEDARG(AP, TYPE, NAME) TYPE NAME = va_arg(AP, TYPE)
/* some systems define these in header files for non-ansi mode */
#undef const
#undef volatile
#undef signed
#undef inline
#define const
#define volatile
#define signed
#define inline
#ifndef IN_GCC
#define CONST
#define VOLATILE
#define SIGNED
#define PROTO(type, name, arglist) type name ()
#define EXFUN(name, proto) name()
#define DEFUN(name, arglist, args) name arglist args;
#define DEFUN_VOID(name) name()
#define AND ;
#define DOTS
#define NOARGS
#endif /* ! IN_GCC */
#endif /* ANSI C. */
/* Define macros for some gcc attributes. This permits us to use the
macros freely, and know that they will come into play for the
version of gcc in which they are supported. */
#if (GCC_VERSION < 2007)
# define __attribute__(x)
#endif
/* Attribute __malloc__ on functions was valid as of gcc 2.96. */
#ifndef ATTRIBUTE_MALLOC
# if (GCC_VERSION >= 2096)
# define ATTRIBUTE_MALLOC __attribute__ ((__malloc__))
# else
# define ATTRIBUTE_MALLOC
# endif /* GNUC >= 2.96 */
#endif /* ATTRIBUTE_MALLOC */
/* Attributes on labels were valid as of gcc 2.93 and g++ 4.5. For
g++ an attribute on a label must be followed by a semicolon. */
#ifndef ATTRIBUTE_UNUSED_LABEL
# ifndef __cplusplus
# if GCC_VERSION >= 2093
# define ATTRIBUTE_UNUSED_LABEL ATTRIBUTE_UNUSED
# else
# define ATTRIBUTE_UNUSED_LABEL
# endif
# else
# if GCC_VERSION >= 4005
# define ATTRIBUTE_UNUSED_LABEL ATTRIBUTE_UNUSED ;
# else
# define ATTRIBUTE_UNUSED_LABEL
# endif
# endif
#endif
/* Similarly to ARG_UNUSED below. Prior to GCC 3.4, the C++ frontend
couldn't parse attributes placed after the identifier name, and now
the entire compiler is built with C++. */
#ifndef ATTRIBUTE_UNUSED
#if GCC_VERSION >= 3004
# define ATTRIBUTE_UNUSED __attribute__ ((__unused__))
#else
#define ATTRIBUTE_UNUSED
#endif
#endif /* ATTRIBUTE_UNUSED */
/* Before GCC 3.4, the C++ frontend couldn't parse attributes placed after the
identifier name. */
#if ! defined(__cplusplus) || (GCC_VERSION >= 3004)
# define ARG_UNUSED(NAME) NAME ATTRIBUTE_UNUSED
#else /* !__cplusplus || GNUC >= 3.4 */
# define ARG_UNUSED(NAME) NAME
#endif /* !__cplusplus || GNUC >= 3.4 */
#ifndef ATTRIBUTE_NORETURN
#define ATTRIBUTE_NORETURN __attribute__ ((__noreturn__))
#endif /* ATTRIBUTE_NORETURN */
/* Attribute `nonnull' was valid as of gcc 3.3. */
#ifndef ATTRIBUTE_NONNULL
# if (GCC_VERSION >= 3003)
# define ATTRIBUTE_NONNULL(m) __attribute__ ((__nonnull__ (m)))
# else
# define ATTRIBUTE_NONNULL(m)
# endif /* GNUC >= 3.3 */
#endif /* ATTRIBUTE_NONNULL */
/* Attribute `pure' was valid as of gcc 3.0. */
#ifndef ATTRIBUTE_PURE
# if (GCC_VERSION >= 3000)
# define ATTRIBUTE_PURE __attribute__ ((__pure__))
# else
# define ATTRIBUTE_PURE
# endif /* GNUC >= 3.0 */
#endif /* ATTRIBUTE_PURE */
/* Use ATTRIBUTE_PRINTF when the format specifier must not be NULL.
This was the case for the `printf' format attribute by itself
before GCC 3.3, but as of 3.3 we need to add the `nonnull'
attribute to retain this behavior. */
#ifndef ATTRIBUTE_PRINTF
#define ATTRIBUTE_PRINTF(m, n) __attribute__ ((__format__ (__printf__, m, n))) ATTRIBUTE_NONNULL(m)
#define ATTRIBUTE_PRINTF_1 ATTRIBUTE_PRINTF(1, 2)
#define ATTRIBUTE_PRINTF_2 ATTRIBUTE_PRINTF(2, 3)
#define ATTRIBUTE_PRINTF_3 ATTRIBUTE_PRINTF(3, 4)
#define ATTRIBUTE_PRINTF_4 ATTRIBUTE_PRINTF(4, 5)
#define ATTRIBUTE_PRINTF_5 ATTRIBUTE_PRINTF(5, 6)
#endif /* ATTRIBUTE_PRINTF */
/* Use ATTRIBUTE_FPTR_PRINTF when the format attribute is to be set on
a function pointer. Format attributes were allowed on function
pointers as of gcc 3.1. */
#ifndef ATTRIBUTE_FPTR_PRINTF
# if (GCC_VERSION >= 3001)
# define ATTRIBUTE_FPTR_PRINTF(m, n) ATTRIBUTE_PRINTF(m, n)
# else
# define ATTRIBUTE_FPTR_PRINTF(m, n)
# endif /* GNUC >= 3.1 */
# define ATTRIBUTE_FPTR_PRINTF_1 ATTRIBUTE_FPTR_PRINTF(1, 2)
# define ATTRIBUTE_FPTR_PRINTF_2 ATTRIBUTE_FPTR_PRINTF(2, 3)
# define ATTRIBUTE_FPTR_PRINTF_3 ATTRIBUTE_FPTR_PRINTF(3, 4)
# define ATTRIBUTE_FPTR_PRINTF_4 ATTRIBUTE_FPTR_PRINTF(4, 5)
# define ATTRIBUTE_FPTR_PRINTF_5 ATTRIBUTE_FPTR_PRINTF(5, 6)
#endif /* ATTRIBUTE_FPTR_PRINTF */
/* Use ATTRIBUTE_NULL_PRINTF when the format specifier may be NULL. A
NULL format specifier was allowed as of gcc 3.3. */
#ifndef ATTRIBUTE_NULL_PRINTF
# if (GCC_VERSION >= 3003)
# define ATTRIBUTE_NULL_PRINTF(m, n) __attribute__ ((__format__ (__printf__, m, n)))
# else
# define ATTRIBUTE_NULL_PRINTF(m, n)
# endif /* GNUC >= 3.3 */
# define ATTRIBUTE_NULL_PRINTF_1 ATTRIBUTE_NULL_PRINTF(1, 2)
# define ATTRIBUTE_NULL_PRINTF_2 ATTRIBUTE_NULL_PRINTF(2, 3)
# define ATTRIBUTE_NULL_PRINTF_3 ATTRIBUTE_NULL_PRINTF(3, 4)
# define ATTRIBUTE_NULL_PRINTF_4 ATTRIBUTE_NULL_PRINTF(4, 5)
# define ATTRIBUTE_NULL_PRINTF_5 ATTRIBUTE_NULL_PRINTF(5, 6)
#endif /* ATTRIBUTE_NULL_PRINTF */
/* Attribute `sentinel' was valid as of gcc 3.5. */
#ifndef ATTRIBUTE_SENTINEL
# if (GCC_VERSION >= 3005)
# define ATTRIBUTE_SENTINEL __attribute__ ((__sentinel__))
# else
# define ATTRIBUTE_SENTINEL
# endif /* GNUC >= 3.5 */
#endif /* ATTRIBUTE_SENTINEL */
#ifndef ATTRIBUTE_ALIGNED_ALIGNOF
# if (GCC_VERSION >= 3000)
# define ATTRIBUTE_ALIGNED_ALIGNOF(m) __attribute__ ((__aligned__ (__alignof__ (m))))
# else
# define ATTRIBUTE_ALIGNED_ALIGNOF(m)
# endif /* GNUC >= 3.0 */
#endif /* ATTRIBUTE_ALIGNED_ALIGNOF */
/* Useful for structures whose layout must much some binary specification
regardless of the alignment and padding qualities of the compiler. */
#ifndef ATTRIBUTE_PACKED
# define ATTRIBUTE_PACKED __attribute__ ((packed))
#endif
/* Attribute `hot' and `cold' was valid as of gcc 4.3. */
#ifndef ATTRIBUTE_COLD
# if (GCC_VERSION >= 4003)
# define ATTRIBUTE_COLD __attribute__ ((__cold__))
# else
# define ATTRIBUTE_COLD
# endif /* GNUC >= 4.3 */
#endif /* ATTRIBUTE_COLD */
#ifndef ATTRIBUTE_HOT
# if (GCC_VERSION >= 4003)
# define ATTRIBUTE_HOT __attribute__ ((__hot__))
# else
# define ATTRIBUTE_HOT
# endif /* GNUC >= 4.3 */
#endif /* ATTRIBUTE_HOT */
/* We use __extension__ in some places to suppress -pedantic warnings
about GCC extensions. This feature didn't work properly before
gcc 2.8. */
#if GCC_VERSION < 2008
#define __extension__
#endif
/* This is used to declare a const variable which should be visible
outside of the current compilation unit. Use it as
EXPORTED_CONST int i = 1;
This is because the semantics of const are different in C and C++.
"extern const" is permitted in C but it looks strange, and gcc
warns about it when -Wc++-compat is not used. */
#ifdef __cplusplus
#define EXPORTED_CONST extern const
#else
#define EXPORTED_CONST const
#endif
/* Be conservative and only use enum bitfields with C++ or GCC.
FIXME: provide a complete autoconf test for buggy enum bitfields. */
#ifdef __cplusplus
#define ENUM_BITFIELD(TYPE) enum TYPE
#elif (GCC_VERSION > 2000)
#define ENUM_BITFIELD(TYPE) __extension__ enum TYPE
#else
#define ENUM_BITFIELD(TYPE) unsigned int
#endif
#ifdef __cplusplus
}
#endif
#endif /* ansidecl.h */

2062
src/include/auto-host.h Normal file

File diff suppressed because it is too large Load Diff

121
src/include/b-header-vars Normal file
View File

@ -0,0 +1,121 @@
USER_H=xsaveoptintrin.h mm_malloc.h
HASHTAB_H=hashtab.h
OBSTACK_H=obstack.h
SPLAY_TREE_H=splay-tree.h
FIBHEAP_H=fibheap.h
PARTITION_H=partition.h
DWARF2_H=dwarf2.def
XREGEX_H=xregex.h
FNMATCH_H=fnmatch.h
LINKER_PLUGIN_API_H=plugin-api.h
LTO_SYMTAB_H=lto-symtab.h
BCONFIG_H=bconfig.h auto-host.h ansidecl.h
CONFIG_H=config.h auto-host.h ansidecl.h
TCONFIG_H=tconfig.h auto-host.h ansidecl.h
TM_P_H=tm_p.h config/i386/i386-protos.h tm-preds.h
GTM_H=tm.h options.h config/vxworks-dummy.h defaults.h insn-constants.h
TM_H=tm.h options.h config/vxworks-dummy.h i386-opts.h
VEC_H=vec.h statistics.h ggc.h gtype-desc.h statistics.h
HASH_TABLE_H=hashtab.h hash-table.h
EXCEPT_H=except.h hashtab.h
TARGET_H=tm.h options.h config/vxworks-dummy.h i386-opts.h target.h target.def target-hooks-macros.h insn-modes.h
C_TARGET_H=c-family/c-target.h c-family/c-target.def target-hooks-macros.h
COMMON_TARGET_H=common/common-target.h common-target.def target-hooks-macros.h
MACHMODE_H=machmode.h mode-classes.def insn-modes.h
HOOKS_H=hooks.h machmode.h mode-classes.def insn-modes.h
HOSTHOOKS_DEF_H=hosthooks-def.h hooks.h machmode.h mode-classes.def insn-modes.h
LANGHOOKS_DEF_H=langhooks-def.h hooks.h machmode.h mode-classes.def insn-modes.h
TARGET_DEF_H=target-def.h target-hooks-def.h hooks.h machmode.h mode-classes.def insn-modes.h targhooks.h
C_TARGET_DEF_H=c-family/c-target-def.h c-family/c-target-hooks-def.h coretypes.h tree.h all-tree.def tree.def c-family/c-common.def common-targhooks.h
COMMON_TARGET_DEF_H=common/common-target-def.h common/common-target-hooks-def.h hooks.h machmode.h mode-classes.def insn-modes.h
RTL_BASE_H=coretypes.h rtl.h rtl.def machmode.h mode-classes.def insn-modes.h reg-notes.def insn-notes.def hashtab.h
FIXED_VALUE_H=fixed-value.h machmode.h mode-classes.def insn-modes.h double-int.h
RTL_H=coretypes.h rtl.h rtl.def machmode.h mode-classes.def insn-modes.h reg-notes.def insn-notes.def i386-opts.h genrtl.h
RTL_ERROR_H=rtl-error.h coretypes.h rtl.h rtl.def machmode.h mode-classes.def insn-modes.h reg-notes.def insn-notes.def line-map.h input.h bversion.h diagnostic.def
READ_MD_H=hashtab.h read-md.h
PARAMS_H=params.h params.def
INTERNAL_FN_H=internal-fn.h internal-fn.def
TREE_H=coretypes.h tree.h all-tree.def tree.def c-family/c-common.def i386-opts.h real.h machmode.h mode-classes.def insn-modes.h fixed-value.h machmode.h mode-classes.def insn-modes.h double-int.h
REGSET_H=regset.h bitmap.h hashtab.h statistics.h hard-reg-set.h
BASIC_BLOCK_H=basic-block.h predict.h predict.def vec.h statistics.h ggc.h gtype-desc.h statistics.h function.h line-map.h input.h machmode.h mode-classes.def insn-modes.h cfg-flags.def cfghooks.h
GIMPLE_H=gimple.h gimple.def gsstruct.def pointer-set.h vec.h statistics.h ggc.h gtype-desc.h statistics.h ggc.h gtype-desc.h statistics.h basic-block.h predict.h predict.def vec.h statistics.h ggc.h gtype-desc.h statistics.h function.h i386-opts.h real.h machmode.h mode-classes.def insn-modes.h fixed-value.h machmode.h mode-classes.def insn-modes.h double-int.h tree-ssa-operands.h tree-ssa-alias.h internal-fn.h internal-fn.def
TRANS_MEM_H=trans-mem.h
GCOV_IO_H=gcov-io.h gcov-iov.h auto-host.h
COVERAGE_H=coverage.h gcov-io.h gcov-iov.h auto-host.h
DEMANGLE_H=demangle.h
RECOG_H=recog.h
ALIAS_H=alias.h
EMIT_RTL_H=emit-rtl.h
FLAGS_H=flags.h flag-types.h options.h flag-types.h config/i386/i386-opts.h
OPTIONS_H=options.h flag-types.h config/i386/i386-opts.h
FUNCTION_H=function.h line-map.h input.h machmode.h mode-classes.def insn-modes.h
EXPR_H=expr.h insn-config.h function.h i386-opts.h real.h machmode.h mode-classes.def insn-modes.h fixed-value.h machmode.h mode-classes.def insn-modes.h double-int.h machmode.h mode-classes.def insn-modes.h emit-rtl.h
OPTABS_H=optabs.h insn-codes.h insn-opinit.h
REGS_H=regs.h machmode.h mode-classes.def insn-modes.h hard-reg-set.h
SCHED_INT_H=sched-int.h insn-attr.h insn-attr-common.h hashtab.h statistics.h hard-reg-set.h
SEL_SCHED_IR_H=sel-sched-ir.h insn-attr.h insn-attr-common.h hashtab.h statistics.h hard-reg-set.h
SEL_SCHED_DUMP_H=sel-sched-dump.h sel-sched-ir.h insn-attr.h insn-attr-common.h hashtab.h statistics.h hard-reg-set.h
CFGLOOP_H=cfgloop.h basic-block.h predict.h predict.def vec.h statistics.h ggc.h gtype-desc.h statistics.h function.h hashtab.h statistics.h sbitmap.h
IPA_UTILS_H=ipa-utils.h coretypes.h tree.h all-tree.def tree.def c-family/c-common.def plugin-api.h is-a.h
IPA_REFERENCE_H=ipa-reference.h bitmap.h i386-opts.h real.h machmode.h mode-classes.def insn-modes.h fixed-value.h machmode.h mode-classes.def insn-modes.h double-int.h
CGRAPH_H=cgraph.h vec.h statistics.h ggc.h gtype-desc.h statistics.h coretypes.h tree.h all-tree.def tree.def c-family/c-common.def plugin-api.h is-a.h
DF_H=df.h bitmap.h line-map.h input.h machmode.h mode-classes.def insn-modes.h cfg-flags.def cfghooks.h alloc-pool.h timevar.h timevar.def
VALTRACK_H=valtrack.h bitmap.h hashtab.h hash-table.h
RESOURCE_H=resource.h hard-reg-set.h df.h bitmap.h line-map.h input.h machmode.h mode-classes.def insn-modes.h cfg-flags.def cfghooks.h alloc-pool.h timevar.h timevar.def
DDG_H=ddg.h sbitmap.h df.h bitmap.h line-map.h input.h machmode.h mode-classes.def insn-modes.h cfg-flags.def cfghooks.h alloc-pool.h timevar.h timevar.def
GCC_H=gcc.h version.h diagnostic-core.h line-map.h input.h bversion.h diagnostic.def
GGC_H=ggc.h gtype-desc.h statistics.h
GGC_INTERNAL_H=ggc-internal.h ggc.h gtype-desc.h statistics.h
TIMEVAR_H=timevar.h timevar.def
INSN_ATTR_H=insn-attr.h insn-attr-common.h insn-addr.h
INSN_ADDR_H=insn-addr.h
C_COMMON_H=c-family/c-common.h c-family/c-common.def coretypes.h tree.h all-tree.def tree.def c-family/c-common.def line-map.h input.h bversion.h diagnostic.def
C_PRAGMA_H=c-family/c-pragma.h cpplib.h
C_TREE_H=c/c-tree.h c-family/c-common.h c-family/c-common.def coretypes.h tree.h all-tree.def tree.def c-family/c-common.def obstack.h
SYSTEM_H=system.h hwint.h filenames.h
PREDICT_H=predict.h predict.def
CPPLIB_H=cpplib.h
INPUT_H=line-map.h input.h
OPTS_H=obstack.h
DECNUM_H=decimal128Local.h
BACKTRACE_H=backtrace.h
MKDEPS_H=mkdeps.h
SYMTAB_H=obstack.h
CPP_ID_DATA_H=cpp-id-data.h
CPP_INTERNAL_H=cpp-id-data.h
TREE_DUMP_H=tree-dump.h splay-tree.h dumpfile.h
TREE_PASS_H=tree-pass.h timevar.h timevar.def dumpfile.h
TREE_FLOW_H=tree-flow.h tree-flow-inline.h tree-ssa-operands.h bitmap.h i386-opts.h real.h machmode.h mode-classes.def insn-modes.h fixed-value.h machmode.h mode-classes.def insn-modes.h double-int.h tree-ssa-alias.h
TREE_SSA_LIVE_H=tree-ssa-live.h partition.h
SSAEXPAND_H=ssaexpand.h tree-ssa-live.h partition.h
PRETTY_PRINT_H=pretty-print.h obstack.h
TREE_PRETTY_PRINT_H=tree-pretty-print.h pretty-print.h obstack.h
GIMPLE_PRETTY_PRINT_H=gimple-pretty-print.h tree-pretty-print.h pretty-print.h obstack.h
DIAGNOSTIC_CORE_H=diagnostic-core.h line-map.h input.h bversion.h diagnostic.def
DIAGNOSTIC_H=diagnostic.h diagnostic-core.h obstack.h
DWARF2OUT_H=dwarf2out.h dwarf2.def
C_PRETTY_PRINT_H=c-family/c-pretty-print.h pretty-print.h i386-opts.h real.h machmode.h mode-classes.def insn-modes.h fixed-value.h machmode.h mode-classes.def insn-modes.h double-int.h
SCEV_H=tree-scalar-evolution.h ggc.h gtype-desc.h statistics.h tree-chrec.h params.h params.def
OMEGA_H=omega.h params.h params.def
TREE_DATA_REF_H=tree-data-ref.h omega.h params.h params.def graphds.h tree-scalar-evolution.h ggc.h gtype-desc.h statistics.h tree-chrec.h params.h params.def
TREE_INLINE_H=tree-inline.h
REAL_H=real.h machmode.h mode-classes.def insn-modes.h
IRA_INT_H=ira.h ira-int.h cfgloop.h basic-block.h predict.h predict.def vec.h statistics.h ggc.h gtype-desc.h statistics.h function.h hashtab.h statistics.h sbitmap.h alloc-pool.h
LRA_INT_H=lra.h bitmap.h insn-addr.h insn-codes.h lra-int.h
DBGCNT_H=dbgcnt.h dbgcnt.def
LTO_STREAMER_H=lto-streamer.h obstack.h alloc-pool.h
DATA_STREAMER_H=data-streamer.h vec.h statistics.h ggc.h gtype-desc.h statistics.h lto-streamer.h obstack.h alloc-pool.h
GIMPLE_STREAMER_H=gimple-streamer.h lto-streamer.h line-map.h input.h machmode.h mode-classes.def insn-modes.h
TREE_STREAMER_H=tree-streamer.h coretypes.h tree.h all-tree.def tree.def c-family/c-common.def i386-opts.h real.h machmode.h mode-classes.def insn-modes.h fixed-value.h machmode.h mode-classes.def insn-modes.h double-int.h
STREAMER_HOOKS_H=streamer-hooks.h coretypes.h tree.h all-tree.def tree.def c-family/c-common.def i386-opts.h real.h machmode.h mode-classes.def insn-modes.h fixed-value.h machmode.h mode-classes.def insn-modes.h double-int.h
TREE_VECTORIZER_H=tree-vectorizer.h tree-data-ref.h omega.h params.h params.def graphds.h tree-scalar-evolution.h ggc.h gtype-desc.h statistics.h tree-chrec.h params.h params.def tm.h options.h config/vxworks-dummy.h i386-opts.h target.h target.def target-hooks-macros.h insn-modes.h
IPA_PROP_H=ipa-prop.h coretypes.h tree.h all-tree.def tree.def c-family/c-common.def i386-opts.h real.h machmode.h mode-classes.def insn-modes.h fixed-value.h machmode.h mode-classes.def insn-modes.h double-int.h tree-ssa-operands.h tree-ssa-alias.h internal-fn.h internal-fn.def alloc-pool.h
IPA_INLINE_H=ipa-inline.h ipa-prop.h coretypes.h tree.h all-tree.def tree.def c-family/c-common.def i386-opts.h real.h machmode.h mode-classes.def insn-modes.h fixed-value.h machmode.h mode-classes.def insn-modes.h double-int.h tree-ssa-operands.h tree-ssa-alias.h internal-fn.h internal-fn.def alloc-pool.h
GSTAB_H=gstab.h stab.def
BITMAP_H=bitmap.h hashtab.h statistics.h
GCC_PLUGIN_H=gcc-plugin.h highlev-plugin-common.h plugin.def config.h auto-host.h hashtab.h
PLUGIN_H=plugin.h gcc-plugin.h highlev-plugin-common.h plugin.def config.h auto-host.h hashtab.h
PLUGIN_VERSION_H=plugin-version.h configargs.h
LIBFUNCS_H=libfuncs.h hashtab.h
GTFILES_H=gt-coverage.h gt-caller-save.h gt-symtab.h gt-alias.h gt-bitmap.h gt-cselib.h gt-cgraph.h gt-ipa-prop.h gt-ipa-cp.h gt-dbxout.h gt-dwarf2asm.h gt-dwarf2cfi.h gt-dwarf2out.h gt-tree-vect-generic.h gt-dojump.h gt-emit-rtl.h gt-explow.h gt-expr.h gt-function.h gt-except.h gt-gcse.h gt-godump.h gt-lists.h gt-optabs.h gt-profile.h gt-mcf.h gt-reg-stack.h gt-cfgrtl.h gt-sdbout.h gt-stor-layout.h gt-stringpool.h gt-tree.h gt-varasm.h gt-gimple.h gt-tree-mudflap.h gt-tree-ssanames.h gt-tree-eh.h gt-tree-ssa-address.h gt-tree-cfg.h gt-tree-dfa.h gt-tree-iterator.h gt-gimplify.h gt-tree-scalar-evolution.h gt-tree-profile.h gt-tree-nested.h gt-tree-parloops.h gt-omp-low.h gt-targhooks.h gt-i386.h gt-passes.h gt-cgraphunit.h gt-cgraphclones.h gt-tree-ssa-propagate.h gt-tree-phinodes.h gt-lto-symtab.h gt-trans-mem.h gt-asan.h gt-tsan.h gt-ada-decl.h gt-ada-trans.h gt-ada-utils.h gt-ada-misc.h gt-c-c-lang.h gt-c-c-decl.h gt-c-family-c-common.h gt-c-family-c-cppbuiltin.h gt-c-family-c-pragma.h gt-c-c-objc-common.h gt-c-c-parser.h gt-cp-rtti.h gt-cp-mangle.h gt-cp-name-lookup.h gt-cp-call.h gt-cp-decl.h gt-cp-decl2.h gt-cp-pt.h gt-cp-repo.h gt-cp-semantics.h gt-cp-tree.h gt-cp-parser.h gt-cp-method.h gt-cp-typeck2.h gt-c-family-c-common.h gt-c-family-c-lex.h gt-c-family-c-pragma.h gt-cp-class.h gt-cp-cp-objcp-common.h gt-cp-cp-lang.h gt-cp-except.h gt-fortran-f95-lang.h gt-fortran-trans-decl.h gt-fortran-trans-intrinsic.h gt-fortran-trans-io.h gt-fortran-trans-stmt.h gt-fortran-trans-types.h gt-go-go-lang.h gt-java-builtins.h gt-java-class.h gt-java-constants.h gt-java-decl.h gt-java-expr.h gt-java-jcf-parse.h gt-java-lang.h gt-java-mangle.h gt-java-resource.h gt-lto-lto-lang.h gt-lto-lto.h gt-objc-objc-act.h gt-objc-objc-runtime-shared-support.h gt-objc-objc-gnu-runtime-abi-01.h gt-objc-objc-next-runtime-abi-01.h gt-objc-objc-next-runtime-abi-02.h gt-c-c-parser.h gt-c-c-decl.h gt-c-c-objc-common.h gt-c-family-c-common.h gt-c-family-c-cppbuiltin.h gt-c-family-c-pragma.h gt-cp-rtti.h gt-cp-mangle.h gt-cp-name-lookup.h gt-cp-call.h gt-cp-decl.h gt-cp-decl2.h gt-cp-pt.h gt-cp-repo.h gt-cp-semantics.h gt-cp-tree.h gt-cp-parser.h gt-cp-method.h gt-cp-typeck2.h gt-c-family-c-common.h gt-c-family-c-lex.h gt-c-family-c-pragma.h gt-cp-class.h gt-cp-cp-objcp-common.h gt-objc-objc-act.h gt-objc-objc-runtime-shared-support.h gt-objc-objc-gnu-runtime-abi-01.h gt-objc-objc-next-runtime-abi-01.h gt-objc-objc-next-runtime-abi-02.h gt-c-family-c-cppbuiltin.h
GTFILES_LANG_H=gtype-ada.h gtype-c.h gtype-cp.h gtype-fortran.h gtype-go.h gtype-java.h gtype-lto.h gtype-objc.h gtype-objcp.h

974
src/include/basic-block.h Normal file
View File

@ -0,0 +1,974 @@
/* Define control flow data structures for the CFG.
Copyright (C) 1987-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GCC_BASIC_BLOCK_H
#define GCC_BASIC_BLOCK_H
#include "predict.h"
#include "vec.h"
#include "function.h"
/* Type we use to hold basic block counters. Should be at least
64bit. Although a counter cannot be negative, we use a signed
type, because erroneous negative counts can be generated when the
flow graph is manipulated by various optimizations. A signed type
makes those easy to detect. */
typedef HOST_WIDEST_INT gcov_type;
typedef unsigned HOST_WIDEST_INT gcov_type_unsigned;
/* Control flow edge information. */
struct GTY((user)) edge_def {
/* The two blocks at the ends of the edge. */
basic_block src;
basic_block dest;
/* Instructions queued on the edge. */
union edge_def_insns {
gimple_seq g;
rtx r;
} insns;
/* Auxiliary info specific to a pass. */
PTR aux;
/* Location of any goto implicit in the edge. */
location_t goto_locus;
/* The index number corresponding to this edge in the edge vector
dest->preds. */
unsigned int dest_idx;
int flags; /* see cfg-flags.def */
int probability; /* biased by REG_BR_PROB_BASE */
gcov_type count; /* Expected number of executions calculated
in profile.c */
};
/* Garbage collection and PCH support for edge_def. */
extern void gt_ggc_mx (edge_def *e);
extern void gt_pch_nx (edge_def *e);
extern void gt_pch_nx (edge_def *e, gt_pointer_operator, void *);
/* Masks for edge.flags. */
#define DEF_EDGE_FLAG(NAME,IDX) EDGE_##NAME = 1 << IDX ,
enum cfg_edge_flags {
#include "cfg-flags.def"
LAST_CFG_EDGE_FLAG /* this is only used for EDGE_ALL_FLAGS */
};
#undef DEF_EDGE_FLAG
/* Bit mask for all edge flags. */
#define EDGE_ALL_FLAGS ((LAST_CFG_EDGE_FLAG - 1) * 2 - 1)
/* The following four flags all indicate something special about an edge.
Test the edge flags on EDGE_COMPLEX to detect all forms of "strange"
control flow transfers. */
#define EDGE_COMPLEX \
(EDGE_ABNORMAL | EDGE_ABNORMAL_CALL | EDGE_EH | EDGE_PRESERVE)
/* Counter summary from the last set of coverage counts read by
profile.c. */
extern const struct gcov_ctr_summary *profile_info;
/* Working set size statistics for a given percentage of the entire
profile (sum_all from the counter summary). */
typedef struct gcov_working_set_info
{
/* Number of hot counters included in this working set. */
unsigned num_counters;
/* Smallest counter included in this working set. */
gcov_type min_counter;
} gcov_working_set_t;
/* Structure to gather statistic about profile consistency, per pass.
An array of this structure, indexed by pass static number, is allocated
in passes.c. The structure is defined here so that different CFG modes
can do their book-keeping via CFG hooks.
For every field[2], field[0] is the count before the pass runs, and
field[1] is the post-pass count. This allows us to monitor the effect
of each individual pass on the profile consistency.
This structure is not supposed to be used by anything other than passes.c
and one CFG hook per CFG mode. */
struct profile_record
{
/* The number of basic blocks where sum(freq) of the block's predecessors
doesn't match reasonably well with the incoming frequency. */
int num_mismatched_freq_in[2];
/* Likewise for a basic block's successors. */
int num_mismatched_freq_out[2];
/* The number of basic blocks where sum(count) of the block's predecessors
doesn't match reasonably well with the incoming frequency. */
int num_mismatched_count_in[2];
/* Likewise for a basic block's successors. */
int num_mismatched_count_out[2];
/* A weighted cost of the run-time of the function body. */
gcov_type time[2];
/* A weighted cost of the size of the function body. */
int size[2];
/* True iff this pass actually was run. */
bool run;
};
/* Declared in cfgloop.h. */
struct loop;
struct GTY(()) rtl_bb_info {
/* The first insn of the block is embedded into bb->il.x. */
/* The last insn of the block. */
rtx end_;
/* In CFGlayout mode points to insn notes/jumptables to be placed just before
and after the block. */
rtx header_;
rtx footer_;
};
struct GTY(()) gimple_bb_info {
/* Sequence of statements in this block. */
gimple_seq seq;
/* PHI nodes for this block. */
gimple_seq phi_nodes;
};
/* A basic block is a sequence of instructions with only one entry and
only one exit. If any one of the instructions are executed, they
will all be executed, and in sequence from first to last.
There may be COND_EXEC instructions in the basic block. The
COND_EXEC *instructions* will be executed -- but if the condition
is false the conditionally executed *expressions* will of course
not be executed. We don't consider the conditionally executed
expression (which might have side-effects) to be in a separate
basic block because the program counter will always be at the same
location after the COND_EXEC instruction, regardless of whether the
condition is true or not.
Basic blocks need not start with a label nor end with a jump insn.
For example, a previous basic block may just "conditionally fall"
into the succeeding basic block, and the last basic block need not
end with a jump insn. Block 0 is a descendant of the entry block.
A basic block beginning with two labels cannot have notes between
the labels.
Data for jump tables are stored in jump_insns that occur in no
basic block even though these insns can follow or precede insns in
basic blocks. */
/* Basic block information indexed by block number. */
struct GTY((chain_next ("%h.next_bb"), chain_prev ("%h.prev_bb"))) basic_block_def {
/* The edges into and out of the block. */
vec<edge, va_gc> *preds;
vec<edge, va_gc> *succs;
/* Auxiliary info specific to a pass. */
PTR GTY ((skip (""))) aux;
/* Innermost loop containing the block. */
struct loop *loop_father;
/* The dominance and postdominance information node. */
struct et_node * GTY ((skip (""))) dom[2];
/* Previous and next blocks in the chain. */
basic_block prev_bb;
basic_block next_bb;
union basic_block_il_dependent {
struct gimple_bb_info GTY ((tag ("0"))) gimple;
struct {
rtx head_;
struct rtl_bb_info * rtl;
} GTY ((tag ("1"))) x;
} GTY ((desc ("((%1.flags & BB_RTL) != 0)"))) il;
/* Various flags. See cfg-flags.def. */
int flags;
/* The index of this block. */
int index;
/* Expected number of executions: calculated in profile.c. */
gcov_type count;
/* Expected frequency. Normalized to be in range 0 to BB_FREQ_MAX. */
int frequency;
/* The discriminator for this block. The discriminator distinguishes
among several basic blocks that share a common locus, allowing for
more accurate sample-based profiling. */
int discriminator;
};
/* This ensures that struct gimple_bb_info is smaller than
struct rtl_bb_info, so that inlining the former into basic_block_def
is the better choice. */
typedef int __assert_gimple_bb_smaller_rtl_bb
[(int)sizeof(struct rtl_bb_info)
- (int)sizeof (struct gimple_bb_info)];
#define BB_FREQ_MAX 10000
/* Masks for basic_block.flags. */
#define DEF_BASIC_BLOCK_FLAG(NAME,IDX) BB_##NAME = 1 << IDX ,
enum cfg_bb_flags
{
#include "cfg-flags.def"
LAST_CFG_BB_FLAG /* this is only used for BB_ALL_FLAGS */
};
#undef DEF_BASIC_BLOCK_FLAG
/* Bit mask for all basic block flags. */
#define BB_ALL_FLAGS ((LAST_CFG_BB_FLAG - 1) * 2 - 1)
/* Bit mask for all basic block flags that must be preserved. These are
the bit masks that are *not* cleared by clear_bb_flags. */
#define BB_FLAGS_TO_PRESERVE \
(BB_DISABLE_SCHEDULE | BB_RTL | BB_NON_LOCAL_GOTO_TARGET \
| BB_HOT_PARTITION | BB_COLD_PARTITION)
/* Dummy bitmask for convenience in the hot/cold partitioning code. */
#define BB_UNPARTITIONED 0
/* Partitions, to be used when partitioning hot and cold basic blocks into
separate sections. */
#define BB_PARTITION(bb) ((bb)->flags & (BB_HOT_PARTITION|BB_COLD_PARTITION))
#define BB_SET_PARTITION(bb, part) do { \
basic_block bb_ = (bb); \
bb_->flags = ((bb_->flags & ~(BB_HOT_PARTITION|BB_COLD_PARTITION)) \
| (part)); \
} while (0)
#define BB_COPY_PARTITION(dstbb, srcbb) \
BB_SET_PARTITION (dstbb, BB_PARTITION (srcbb))
/* State of dominance information. */
enum dom_state
{
DOM_NONE, /* Not computed at all. */
DOM_NO_FAST_QUERY, /* The data is OK, but the fast query data are not usable. */
DOM_OK /* Everything is ok. */
};
/* What sort of profiling information we have. */
enum profile_status_d
{
PROFILE_ABSENT,
PROFILE_GUESSED,
PROFILE_READ,
PROFILE_LAST /* Last value, used by profile streaming. */
};
/* A structure to group all the per-function control flow graph data.
The x_* prefixing is necessary because otherwise references to the
fields of this struct are interpreted as the defines for backward
source compatibility following the definition of this struct. */
struct GTY(()) control_flow_graph {
/* Block pointers for the exit and entry of a function.
These are always the head and tail of the basic block list. */
basic_block x_entry_block_ptr;
basic_block x_exit_block_ptr;
/* Index by basic block number, get basic block struct info. */
vec<basic_block, va_gc> *x_basic_block_info;
/* Number of basic blocks in this flow graph. */
int x_n_basic_blocks;
/* Number of edges in this flow graph. */
int x_n_edges;
/* The first free basic block number. */
int x_last_basic_block;
/* UIDs for LABEL_DECLs. */
int last_label_uid;
/* Mapping of labels to their associated blocks. At present
only used for the gimple CFG. */
vec<basic_block, va_gc> *x_label_to_block_map;
enum profile_status_d x_profile_status;
/* Whether the dominators and the postdominators are available. */
enum dom_state x_dom_computed[2];
/* Number of basic blocks in the dominance tree. */
unsigned x_n_bbs_in_dom_tree[2];
/* Maximal number of entities in the single jumptable. Used to estimate
final flowgraph size. */
int max_jumptable_ents;
};
/* Defines for accessing the fields of the CFG structure for function FN. */
#define ENTRY_BLOCK_PTR_FOR_FUNCTION(FN) ((FN)->cfg->x_entry_block_ptr)
#define EXIT_BLOCK_PTR_FOR_FUNCTION(FN) ((FN)->cfg->x_exit_block_ptr)
#define basic_block_info_for_function(FN) ((FN)->cfg->x_basic_block_info)
#define n_basic_blocks_for_function(FN) ((FN)->cfg->x_n_basic_blocks)
#define n_edges_for_function(FN) ((FN)->cfg->x_n_edges)
#define last_basic_block_for_function(FN) ((FN)->cfg->x_last_basic_block)
#define label_to_block_map_for_function(FN) ((FN)->cfg->x_label_to_block_map)
#define profile_status_for_function(FN) ((FN)->cfg->x_profile_status)
#define BASIC_BLOCK_FOR_FUNCTION(FN,N) \
((*basic_block_info_for_function(FN))[(N)])
#define SET_BASIC_BLOCK_FOR_FUNCTION(FN,N,BB) \
((*basic_block_info_for_function(FN))[(N)] = (BB))
/* Defines for textual backward source compatibility. */
#define ENTRY_BLOCK_PTR (cfun->cfg->x_entry_block_ptr)
#define EXIT_BLOCK_PTR (cfun->cfg->x_exit_block_ptr)
#define basic_block_info (cfun->cfg->x_basic_block_info)
#define n_basic_blocks (cfun->cfg->x_n_basic_blocks)
#define n_edges (cfun->cfg->x_n_edges)
#define last_basic_block (cfun->cfg->x_last_basic_block)
#define label_to_block_map (cfun->cfg->x_label_to_block_map)
#define profile_status (cfun->cfg->x_profile_status)
#define BASIC_BLOCK(N) ((*basic_block_info)[(N)])
#define SET_BASIC_BLOCK(N,BB) ((*basic_block_info)[(N)] = (BB))
/* For iterating over basic blocks. */
#define FOR_BB_BETWEEN(BB, FROM, TO, DIR) \
for (BB = FROM; BB != TO; BB = BB->DIR)
#define FOR_EACH_BB_FN(BB, FN) \
FOR_BB_BETWEEN (BB, (FN)->cfg->x_entry_block_ptr->next_bb, (FN)->cfg->x_exit_block_ptr, next_bb)
#define FOR_EACH_BB(BB) FOR_EACH_BB_FN (BB, cfun)
#define FOR_EACH_BB_REVERSE_FN(BB, FN) \
FOR_BB_BETWEEN (BB, (FN)->cfg->x_exit_block_ptr->prev_bb, (FN)->cfg->x_entry_block_ptr, prev_bb)
#define FOR_EACH_BB_REVERSE(BB) FOR_EACH_BB_REVERSE_FN(BB, cfun)
/* For iterating over insns in basic block. */
#define FOR_BB_INSNS(BB, INSN) \
for ((INSN) = BB_HEAD (BB); \
(INSN) && (INSN) != NEXT_INSN (BB_END (BB)); \
(INSN) = NEXT_INSN (INSN))
/* For iterating over insns in basic block when we might remove the
current insn. */
#define FOR_BB_INSNS_SAFE(BB, INSN, CURR) \
for ((INSN) = BB_HEAD (BB), (CURR) = (INSN) ? NEXT_INSN ((INSN)): NULL; \
(INSN) && (INSN) != NEXT_INSN (BB_END (BB)); \
(INSN) = (CURR), (CURR) = (INSN) ? NEXT_INSN ((INSN)) : NULL)
#define FOR_BB_INSNS_REVERSE(BB, INSN) \
for ((INSN) = BB_END (BB); \
(INSN) && (INSN) != PREV_INSN (BB_HEAD (BB)); \
(INSN) = PREV_INSN (INSN))
#define FOR_BB_INSNS_REVERSE_SAFE(BB, INSN, CURR) \
for ((INSN) = BB_END (BB),(CURR) = (INSN) ? PREV_INSN ((INSN)) : NULL; \
(INSN) && (INSN) != PREV_INSN (BB_HEAD (BB)); \
(INSN) = (CURR), (CURR) = (INSN) ? PREV_INSN ((INSN)) : NULL)
/* Cycles through _all_ basic blocks, even the fake ones (entry and
exit block). */
#define FOR_ALL_BB(BB) \
for (BB = ENTRY_BLOCK_PTR; BB; BB = BB->next_bb)
#define FOR_ALL_BB_FN(BB, FN) \
for (BB = ENTRY_BLOCK_PTR_FOR_FUNCTION (FN); BB; BB = BB->next_bb)
/* Stuff for recording basic block info. */
#define BB_HEAD(B) (B)->il.x.head_
#define BB_END(B) (B)->il.x.rtl->end_
#define BB_HEADER(B) (B)->il.x.rtl->header_
#define BB_FOOTER(B) (B)->il.x.rtl->footer_
/* Special block numbers [markers] for entry and exit.
Neither of them is supposed to hold actual statements. */
#define ENTRY_BLOCK (0)
#define EXIT_BLOCK (1)
/* The two blocks that are always in the cfg. */
#define NUM_FIXED_BLOCKS (2)
#define set_block_for_insn(INSN, BB) (BLOCK_FOR_INSN (INSN) = BB)
extern void compute_bb_for_insn (void);
extern unsigned int free_bb_for_insn (void);
extern void update_bb_for_insn (basic_block);
extern void insert_insn_on_edge (rtx, edge);
basic_block split_edge_and_insert (edge, rtx);
extern void commit_one_edge_insertion (edge e);
extern void commit_edge_insertions (void);
extern edge unchecked_make_edge (basic_block, basic_block, int);
extern edge cached_make_edge (sbitmap, basic_block, basic_block, int);
extern edge make_edge (basic_block, basic_block, int);
extern edge make_single_succ_edge (basic_block, basic_block, int);
extern void remove_edge_raw (edge);
extern void redirect_edge_succ (edge, basic_block);
extern edge redirect_edge_succ_nodup (edge, basic_block);
extern void redirect_edge_pred (edge, basic_block);
extern basic_block create_basic_block_structure (rtx, rtx, rtx, basic_block);
extern void clear_bb_flags (void);
extern void dump_bb_info (FILE *, basic_block, int, int, bool, bool);
extern void dump_edge_info (FILE *, edge, int, int);
extern void brief_dump_cfg (FILE *, int);
extern void clear_edges (void);
extern void scale_bbs_frequencies_int (basic_block *, int, int, int);
extern void scale_bbs_frequencies_gcov_type (basic_block *, int, gcov_type,
gcov_type);
/* Structure to group all of the information to process IF-THEN and
IF-THEN-ELSE blocks for the conditional execution support. This
needs to be in a public file in case the IFCVT macros call
functions passing the ce_if_block data structure. */
typedef struct ce_if_block
{
basic_block test_bb; /* First test block. */
basic_block then_bb; /* THEN block. */
basic_block else_bb; /* ELSE block or NULL. */
basic_block join_bb; /* Join THEN/ELSE blocks. */
basic_block last_test_bb; /* Last bb to hold && or || tests. */
int num_multiple_test_blocks; /* # of && and || basic blocks. */
int num_and_and_blocks; /* # of && blocks. */
int num_or_or_blocks; /* # of || blocks. */
int num_multiple_test_insns; /* # of insns in && and || blocks. */
int and_and_p; /* Complex test is &&. */
int num_then_insns; /* # of insns in THEN block. */
int num_else_insns; /* # of insns in ELSE block. */
int pass; /* Pass number. */
} ce_if_block_t;
/* This structure maintains an edge list vector. */
/* FIXME: Make this a vec<edge>. */
struct edge_list
{
int num_edges;
edge *index_to_edge;
};
/* The base value for branch probability notes and edge probabilities. */
#define REG_BR_PROB_BASE 10000
/* This is the value which indicates no edge is present. */
#define EDGE_INDEX_NO_EDGE -1
/* EDGE_INDEX returns an integer index for an edge, or EDGE_INDEX_NO_EDGE
if there is no edge between the 2 basic blocks. */
#define EDGE_INDEX(el, pred, succ) (find_edge_index ((el), (pred), (succ)))
/* INDEX_EDGE_PRED_BB and INDEX_EDGE_SUCC_BB return a pointer to the basic
block which is either the pred or succ end of the indexed edge. */
#define INDEX_EDGE_PRED_BB(el, index) ((el)->index_to_edge[(index)]->src)
#define INDEX_EDGE_SUCC_BB(el, index) ((el)->index_to_edge[(index)]->dest)
/* INDEX_EDGE returns a pointer to the edge. */
#define INDEX_EDGE(el, index) ((el)->index_to_edge[(index)])
/* Number of edges in the compressed edge list. */
#define NUM_EDGES(el) ((el)->num_edges)
/* BB is assumed to contain conditional jump. Return the fallthru edge. */
#define FALLTHRU_EDGE(bb) (EDGE_SUCC ((bb), 0)->flags & EDGE_FALLTHRU \
? EDGE_SUCC ((bb), 0) : EDGE_SUCC ((bb), 1))
/* BB is assumed to contain conditional jump. Return the branch edge. */
#define BRANCH_EDGE(bb) (EDGE_SUCC ((bb), 0)->flags & EDGE_FALLTHRU \
? EDGE_SUCC ((bb), 1) : EDGE_SUCC ((bb), 0))
#define RDIV(X,Y) (((X) + (Y) / 2) / (Y))
/* Return expected execution frequency of the edge E. */
#define EDGE_FREQUENCY(e) RDIV ((e)->src->frequency * (e)->probability, \
REG_BR_PROB_BASE)
/* Return nonzero if edge is critical. */
#define EDGE_CRITICAL_P(e) (EDGE_COUNT ((e)->src->succs) >= 2 \
&& EDGE_COUNT ((e)->dest->preds) >= 2)
#define EDGE_COUNT(ev) vec_safe_length (ev)
#define EDGE_I(ev,i) (*ev)[(i)]
#define EDGE_PRED(bb,i) (*(bb)->preds)[(i)]
#define EDGE_SUCC(bb,i) (*(bb)->succs)[(i)]
/* Returns true if BB has precisely one successor. */
static inline bool
single_succ_p (const_basic_block bb)
{
return EDGE_COUNT (bb->succs) == 1;
}
/* Returns true if BB has precisely one predecessor. */
static inline bool
single_pred_p (const_basic_block bb)
{
return EDGE_COUNT (bb->preds) == 1;
}
/* Returns the single successor edge of basic block BB. Aborts if
BB does not have exactly one successor. */
static inline edge
single_succ_edge (const_basic_block bb)
{
gcc_checking_assert (single_succ_p (bb));
return EDGE_SUCC (bb, 0);
}
/* Returns the single predecessor edge of basic block BB. Aborts
if BB does not have exactly one predecessor. */
static inline edge
single_pred_edge (const_basic_block bb)
{
gcc_checking_assert (single_pred_p (bb));
return EDGE_PRED (bb, 0);
}
/* Returns the single successor block of basic block BB. Aborts
if BB does not have exactly one successor. */
static inline basic_block
single_succ (const_basic_block bb)
{
return single_succ_edge (bb)->dest;
}
/* Returns the single predecessor block of basic block BB. Aborts
if BB does not have exactly one predecessor.*/
static inline basic_block
single_pred (const_basic_block bb)
{
return single_pred_edge (bb)->src;
}
/* Iterator object for edges. */
typedef struct {
unsigned index;
vec<edge, va_gc> **container;
} edge_iterator;
static inline vec<edge, va_gc> *
ei_container (edge_iterator i)
{
gcc_checking_assert (i.container);
return *i.container;
}
#define ei_start(iter) ei_start_1 (&(iter))
#define ei_last(iter) ei_last_1 (&(iter))
/* Return an iterator pointing to the start of an edge vector. */
static inline edge_iterator
ei_start_1 (vec<edge, va_gc> **ev)
{
edge_iterator i;
i.index = 0;
i.container = ev;
return i;
}
/* Return an iterator pointing to the last element of an edge
vector. */
static inline edge_iterator
ei_last_1 (vec<edge, va_gc> **ev)
{
edge_iterator i;
i.index = EDGE_COUNT (*ev) - 1;
i.container = ev;
return i;
}
/* Is the iterator `i' at the end of the sequence? */
static inline bool
ei_end_p (edge_iterator i)
{
return (i.index == EDGE_COUNT (ei_container (i)));
}
/* Is the iterator `i' at one position before the end of the
sequence? */
static inline bool
ei_one_before_end_p (edge_iterator i)
{
return (i.index + 1 == EDGE_COUNT (ei_container (i)));
}
/* Advance the iterator to the next element. */
static inline void
ei_next (edge_iterator *i)
{
gcc_checking_assert (i->index < EDGE_COUNT (ei_container (*i)));
i->index++;
}
/* Move the iterator to the previous element. */
static inline void
ei_prev (edge_iterator *i)
{
gcc_checking_assert (i->index > 0);
i->index--;
}
/* Return the edge pointed to by the iterator `i'. */
static inline edge
ei_edge (edge_iterator i)
{
return EDGE_I (ei_container (i), i.index);
}
/* Return an edge pointed to by the iterator. Do it safely so that
NULL is returned when the iterator is pointing at the end of the
sequence. */
static inline edge
ei_safe_edge (edge_iterator i)
{
return !ei_end_p (i) ? ei_edge (i) : NULL;
}
/* Return 1 if we should continue to iterate. Return 0 otherwise.
*Edge P is set to the next edge if we are to continue to iterate
and NULL otherwise. */
static inline bool
ei_cond (edge_iterator ei, edge *p)
{
if (!ei_end_p (ei))
{
*p = ei_edge (ei);
return 1;
}
else
{
*p = NULL;
return 0;
}
}
/* This macro serves as a convenient way to iterate each edge in a
vector of predecessor or successor edges. It must not be used when
an element might be removed during the traversal, otherwise
elements will be missed. Instead, use a for-loop like that shown
in the following pseudo-code:
FOR (ei = ei_start (bb->succs); (e = ei_safe_edge (ei)); )
{
IF (e != taken_edge)
remove_edge (e);
ELSE
ei_next (&ei);
}
*/
#define FOR_EACH_EDGE(EDGE,ITER,EDGE_VEC) \
for ((ITER) = ei_start ((EDGE_VEC)); \
ei_cond ((ITER), &(EDGE)); \
ei_next (&(ITER)))
#define CLEANUP_EXPENSIVE 1 /* Do relatively expensive optimizations
except for edge forwarding */
#define CLEANUP_CROSSJUMP 2 /* Do crossjumping. */
#define CLEANUP_POST_REGSTACK 4 /* We run after reg-stack and need
to care REG_DEAD notes. */
#define CLEANUP_THREADING 8 /* Do jump threading. */
#define CLEANUP_NO_INSN_DEL 16 /* Do not try to delete trivially dead
insns. */
#define CLEANUP_CFGLAYOUT 32 /* Do cleanup in cfglayout mode. */
#define CLEANUP_CFG_CHANGED 64 /* The caller changed the CFG. */
/* In cfganal.c */
extern void bitmap_intersection_of_succs (sbitmap, sbitmap *, basic_block);
extern void bitmap_intersection_of_preds (sbitmap, sbitmap *, basic_block);
extern void bitmap_union_of_succs (sbitmap, sbitmap *, basic_block);
extern void bitmap_union_of_preds (sbitmap, sbitmap *, basic_block);
/* In lcm.c */
extern struct edge_list *pre_edge_lcm (int, sbitmap *, sbitmap *,
sbitmap *, sbitmap *, sbitmap **,
sbitmap **);
extern struct edge_list *pre_edge_rev_lcm (int, sbitmap *,
sbitmap *, sbitmap *,
sbitmap *, sbitmap **,
sbitmap **);
extern void compute_available (sbitmap *, sbitmap *, sbitmap *, sbitmap *);
/* In predict.c */
extern bool maybe_hot_bb_p (struct function *, const_basic_block);
extern bool maybe_hot_edge_p (edge);
extern bool probably_never_executed_bb_p (struct function *, const_basic_block);
extern bool optimize_bb_for_size_p (const_basic_block);
extern bool optimize_bb_for_speed_p (const_basic_block);
extern bool optimize_edge_for_size_p (edge);
extern bool optimize_edge_for_speed_p (edge);
extern bool optimize_loop_for_size_p (struct loop *);
extern bool optimize_loop_for_speed_p (struct loop *);
extern bool optimize_loop_nest_for_size_p (struct loop *);
extern bool optimize_loop_nest_for_speed_p (struct loop *);
extern bool gimple_predicted_by_p (const_basic_block, enum br_predictor);
extern bool rtl_predicted_by_p (const_basic_block, enum br_predictor);
extern void gimple_predict_edge (edge, enum br_predictor, int);
extern void rtl_predict_edge (edge, enum br_predictor, int);
extern void predict_edge_def (edge, enum br_predictor, enum prediction);
extern void guess_outgoing_edge_probabilities (basic_block);
extern void remove_predictions_associated_with_edge (edge);
extern bool edge_probability_reliable_p (const_edge);
extern bool br_prob_note_reliable_p (const_rtx);
extern bool predictable_edge_p (edge);
/* In cfg.c */
extern void init_flow (struct function *);
extern void debug_bb (basic_block);
extern basic_block debug_bb_n (int);
extern void dump_flow_info (FILE *, int);
extern void expunge_block (basic_block);
extern void link_block (basic_block, basic_block);
extern void unlink_block (basic_block);
extern void compact_blocks (void);
extern basic_block alloc_block (void);
extern void alloc_aux_for_blocks (int);
extern void clear_aux_for_blocks (void);
extern void free_aux_for_blocks (void);
extern void alloc_aux_for_edge (edge, int);
extern void alloc_aux_for_edges (int);
extern void clear_aux_for_edges (void);
extern void free_aux_for_edges (void);
/* In cfganal.c */
extern void find_unreachable_blocks (void);
extern bool mark_dfs_back_edges (void);
struct edge_list * create_edge_list (void);
void free_edge_list (struct edge_list *);
void print_edge_list (FILE *, struct edge_list *);
void verify_edge_list (FILE *, struct edge_list *);
int find_edge_index (struct edge_list *, basic_block, basic_block);
edge find_edge (basic_block, basic_block);
extern void remove_fake_edges (void);
extern void remove_fake_exit_edges (void);
extern void add_noreturn_fake_exit_edges (void);
extern void connect_infinite_loops_to_exit (void);
extern int post_order_compute (int *, bool, bool);
extern basic_block dfs_find_deadend (basic_block);
extern int inverted_post_order_compute (int *);
extern int pre_and_rev_post_order_compute (int *, int *, bool);
extern int dfs_enumerate_from (basic_block, int,
bool (*)(const_basic_block, const void *),
basic_block *, int, const void *);
extern void compute_dominance_frontiers (struct bitmap_head_def *);
extern bitmap compute_idf (bitmap, struct bitmap_head_def *);
/* In cfgrtl.c */
extern rtx block_label (basic_block);
extern rtx bb_note (basic_block);
extern bool purge_all_dead_edges (void);
extern bool purge_dead_edges (basic_block);
extern bool fixup_abnormal_edges (void);
extern basic_block force_nonfallthru_and_redirect (edge, basic_block, rtx);
extern bool contains_no_active_insn_p (const_basic_block);
extern bool forwarder_block_p (const_basic_block);
extern bool can_fallthru (basic_block, basic_block);
/* In cfgbuild.c. */
extern void find_many_sub_basic_blocks (sbitmap);
extern void rtl_make_eh_edge (sbitmap, basic_block, rtx);
enum replace_direction { dir_none, dir_forward, dir_backward, dir_both };
/* In cfgcleanup.c. */
extern bool cleanup_cfg (int);
extern int flow_find_cross_jump (basic_block, basic_block, rtx *, rtx *,
enum replace_direction*);
extern int flow_find_head_matching_sequence (basic_block, basic_block,
rtx *, rtx *, int);
extern bool delete_unreachable_blocks (void);
extern void update_br_prob_note (basic_block);
extern bool inside_basic_block_p (const_rtx);
extern bool control_flow_insn_p (const_rtx);
extern rtx get_last_bb_insn (basic_block);
/* In dominance.c */
enum cdi_direction
{
CDI_DOMINATORS = 1,
CDI_POST_DOMINATORS = 2
};
extern enum dom_state dom_info_state (enum cdi_direction);
extern void set_dom_info_availability (enum cdi_direction, enum dom_state);
extern bool dom_info_available_p (enum cdi_direction);
extern void calculate_dominance_info (enum cdi_direction);
extern void free_dominance_info (enum cdi_direction);
extern basic_block nearest_common_dominator (enum cdi_direction,
basic_block, basic_block);
extern basic_block nearest_common_dominator_for_set (enum cdi_direction,
bitmap);
extern void set_immediate_dominator (enum cdi_direction, basic_block,
basic_block);
extern basic_block get_immediate_dominator (enum cdi_direction, basic_block);
extern bool dominated_by_p (enum cdi_direction, const_basic_block, const_basic_block);
extern vec<basic_block> get_dominated_by (enum cdi_direction, basic_block);
extern vec<basic_block> get_dominated_by_region (enum cdi_direction,
basic_block *,
unsigned);
extern vec<basic_block> get_dominated_to_depth (enum cdi_direction,
basic_block, int);
extern vec<basic_block> get_all_dominated_blocks (enum cdi_direction,
basic_block);
extern void add_to_dominance_info (enum cdi_direction, basic_block);
extern void delete_from_dominance_info (enum cdi_direction, basic_block);
basic_block recompute_dominator (enum cdi_direction, basic_block);
extern void redirect_immediate_dominators (enum cdi_direction, basic_block,
basic_block);
extern void iterate_fix_dominators (enum cdi_direction,
vec<basic_block> , bool);
extern void verify_dominators (enum cdi_direction);
extern basic_block first_dom_son (enum cdi_direction, basic_block);
extern basic_block next_dom_son (enum cdi_direction, basic_block);
unsigned bb_dom_dfs_in (enum cdi_direction, basic_block);
unsigned bb_dom_dfs_out (enum cdi_direction, basic_block);
extern edge try_redirect_by_replacing_jump (edge, basic_block, bool);
extern void break_superblocks (void);
extern void relink_block_chain (bool);
extern void update_bb_profile_for_threading (basic_block, int, gcov_type, edge);
extern void init_rtl_bb_info (basic_block);
extern void initialize_original_copy_tables (void);
extern void free_original_copy_tables (void);
extern void set_bb_original (basic_block, basic_block);
extern basic_block get_bb_original (basic_block);
extern void set_bb_copy (basic_block, basic_block);
extern basic_block get_bb_copy (basic_block);
void set_loop_copy (struct loop *, struct loop *);
struct loop *get_loop_copy (struct loop *);
#include "cfghooks.h"
/* Return true when one of the predecessor edges of BB is marked with EDGE_EH. */
static inline bool
bb_has_eh_pred (basic_block bb)
{
edge e;
edge_iterator ei;
FOR_EACH_EDGE (e, ei, bb->preds)
{
if (e->flags & EDGE_EH)
return true;
}
return false;
}
/* Return true when one of the predecessor edges of BB is marked with EDGE_ABNORMAL. */
static inline bool
bb_has_abnormal_pred (basic_block bb)
{
edge e;
edge_iterator ei;
FOR_EACH_EDGE (e, ei, bb->preds)
{
if (e->flags & EDGE_ABNORMAL)
return true;
}
return false;
}
/* Return the fallthru edge in EDGES if it exists, NULL otherwise. */
static inline edge
find_fallthru_edge (vec<edge, va_gc> *edges)
{
edge e;
edge_iterator ei;
FOR_EACH_EDGE (e, ei, edges)
if (e->flags & EDGE_FALLTHRU)
break;
return e;
}
/* In cfgloopmanip.c. */
extern edge mfb_kj_edge;
extern bool mfb_keep_just (edge);
/* In cfgexpand.c. */
extern void rtl_profile_for_bb (basic_block);
extern void rtl_profile_for_edge (edge);
extern void default_rtl_profile (void);
/* In profile.c. */
extern gcov_working_set_t *find_working_set(unsigned pct_times_10);
/* Check tha probability is sane. */
static inline void
check_probability (int prob)
{
gcc_checking_assert (prob >= 0 && prob <= REG_BR_PROB_BASE);
}
/* Given PROB1 and PROB2, return PROB1*PROB2/REG_BR_PROB_BASE.
Used to combine BB probabilities. */
static inline int
combine_probabilities (int prob1, int prob2)
{
check_probability (prob1);
check_probability (prob2);
return RDIV (prob1 * prob2, REG_BR_PROB_BASE);
}
/* Apply probability PROB on frequency or count FREQ. */
static inline gcov_type
apply_probability (gcov_type freq, int prob)
{
check_probability (prob);
return RDIV (freq * prob, REG_BR_PROB_BASE);
}
/* Return inverse probability for PROB. */
static inline int
inverse_probability (int prob1)
{
check_probability (prob1);
return REG_BR_PROB_BASE - prob1;
}
#endif /* GCC_BASIC_BLOCK_H */

713
src/include/bitmap.h Normal file
View File

@ -0,0 +1,713 @@
/* Functions to support general ended bitmaps.
Copyright (C) 1997-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GCC_BITMAP_H
#define GCC_BITMAP_H
/* Implementation of sparse integer sets as a linked list.
This sparse set representation is suitable for sparse sets with an
unknown (a priori) universe. The set is represented as a double-linked
list of container nodes (struct bitmap_element_def). Each node consists
of an index for the first member that could be held in the container,
a small array of integers that represent the members in the container,
and pointers to the next and previous element in the linked list. The
elements in the list are sorted in ascending order, i.e. the head of
the list holds the element with the smallest member of the set.
For a given member I in the set:
- the element for I will have index is I / (bits per element)
- the position for I within element is I % (bits per element)
This representation is very space-efficient for large sparse sets, and
the size of the set can be changed dynamically without much overhead.
An important parameter is the number of bits per element. In this
implementation, there are 128 bits per element. This results in a
high storage overhead *per element*, but a small overall overhead if
the set is very sparse.
The downside is that many operations are relatively slow because the
linked list has to be traversed to test membership (i.e. member_p/
add_member/remove_member). To improve the performance of this set
representation, the last accessed element and its index are cached.
For membership tests on members close to recently accessed members,
the cached last element improves membership test to a constant-time
operation.
The following operations can always be performed in O(1) time:
* clear : bitmap_clear
* choose_one : (not implemented, but could be
implemented in constant time)
The following operations can be performed in O(E) time worst-case (with
E the number of elements in the linked list), but in O(1) time with a
suitable access patterns:
* member_p : bitmap_bit_p
* add_member : bitmap_set_bit
* remove_member : bitmap_clear_bit
The following operations can be performed in O(E) time:
* cardinality : bitmap_count_bits
* set_size : bitmap_last_set_bit (but this could
in constant time with a pointer to
the last element in the chain)
Additionally, the linked-list sparse set representation supports
enumeration of the members in O(E) time:
* forall : EXECUTE_IF_SET_IN_BITMAP
* set_copy : bitmap_copy
* set_intersection : bitmap_intersect_p /
bitmap_and / bitmap_and_into /
EXECUTE_IF_AND_IN_BITMAP
* set_union : bitmap_ior / bitmap_ior_into
* set_difference : bitmap_intersect_compl_p /
bitmap_and_comp / bitmap_and_comp_into /
EXECUTE_IF_AND_COMPL_IN_BITMAP
* set_disjuction : bitmap_xor_comp / bitmap_xor_comp_into
* set_compare : bitmap_equal_p
Some operations on 3 sets that occur frequently in in data flow problems
are also implemented:
* A | (B & C) : bitmap_ior_and_into
* A | (B & ~C) : bitmap_ior_and_compl /
bitmap_ior_and_compl_into
The storage requirements for linked-list sparse sets are O(E), with E->N
in the worst case (a sparse set with large distances between the values
of the set members).
The linked-list set representation works well for problems involving very
sparse sets. The canonical example in GCC is, of course, the "set of
sets" for some CFG-based data flow problems (liveness analysis, dominance
frontiers, etc.).
This representation also works well for data flow problems where the size
of the set may grow dynamically, but care must be taken that the member_p,
add_member, and remove_member operations occur with a suitable access
pattern.
For random-access sets with a known, relatively small universe size, the
SparseSet or simple bitmap representations may be more efficient than a
linked-list set. For random-access sets of unknown universe, a hash table
or a balanced binary tree representation is likely to be a more suitable
choice.
Traversing linked lists is usually cache-unfriendly, even with the last
accessed element cached.
Cache performance can be improved by keeping the elements in the set
grouped together in memory, using a dedicated obstack for a set (or group
of related sets). Elements allocated on obstacks are released to a
free-list and taken off the free list. If multiple sets are allocated on
the same obstack, elements freed from one set may be re-used for one of
the other sets. This usually helps avoid cache misses.
A single free-list is used for all sets allocated in GGC space. This is
bad for persistent sets, so persistent sets should be allocated on an
obstack whenever possible. */
#include "hashtab.h"
#include "statistics.h"
#include "obstack.h"
/* Fundamental storage type for bitmap. */
typedef unsigned long BITMAP_WORD;
/* BITMAP_WORD_BITS needs to be unsigned, but cannot contain casts as
it is used in preprocessor directives -- hence the 1u. */
#define BITMAP_WORD_BITS (CHAR_BIT * SIZEOF_LONG * 1u)
/* Number of words to use for each element in the linked list. */
#ifndef BITMAP_ELEMENT_WORDS
#define BITMAP_ELEMENT_WORDS ((128 + BITMAP_WORD_BITS - 1) / BITMAP_WORD_BITS)
#endif
/* Number of bits in each actual element of a bitmap. */
#define BITMAP_ELEMENT_ALL_BITS (BITMAP_ELEMENT_WORDS * BITMAP_WORD_BITS)
/* Obstack for allocating bitmaps and elements from. */
typedef struct GTY (()) bitmap_obstack {
struct bitmap_element_def *elements;
struct bitmap_head_def *heads;
struct obstack GTY ((skip)) obstack;
} bitmap_obstack;
/* Bitmap set element. We use a linked list to hold only the bits that
are set. This allows for use to grow the bitset dynamically without
having to realloc and copy a giant bit array.
The free list is implemented as a list of lists. There is one
outer list connected together by prev fields. Each element of that
outer is an inner list (that may consist only of the outer list
element) that are connected by the next fields. The prev pointer
is undefined for interior elements. This allows
bitmap_elt_clear_from to be implemented in unit time rather than
linear in the number of elements to be freed. */
typedef struct GTY((chain_next ("%h.next"), chain_prev ("%h.prev"))) bitmap_element_def {
struct bitmap_element_def *next; /* Next element. */
struct bitmap_element_def *prev; /* Previous element. */
unsigned int indx; /* regno/BITMAP_ELEMENT_ALL_BITS. */
BITMAP_WORD bits[BITMAP_ELEMENT_WORDS]; /* Bits that are set. */
} bitmap_element;
/* Head of bitmap linked list. The 'current' member points to something
already pointed to by the chain started by first, so GTY((skip)) it. */
typedef struct GTY(()) bitmap_head_def {
unsigned int indx; /* Index of last element looked at. */
unsigned int descriptor_id; /* Unique identifier for the allocation
site of this bitmap, for detailed
statistics gathering. */
bitmap_element *first; /* First element in linked list. */
bitmap_element * GTY((skip(""))) current; /* Last element looked at. */
bitmap_obstack *obstack; /* Obstack to allocate elements from.
If NULL, then use GGC allocation. */
} bitmap_head;
/* Global data */
extern bitmap_element bitmap_zero_bits; /* Zero bitmap element */
extern bitmap_obstack bitmap_default_obstack; /* Default bitmap obstack */
/* Clear a bitmap by freeing up the linked list. */
extern void bitmap_clear (bitmap);
/* Copy a bitmap to another bitmap. */
extern void bitmap_copy (bitmap, const_bitmap);
/* True if two bitmaps are identical. */
extern bool bitmap_equal_p (const_bitmap, const_bitmap);
/* True if the bitmaps intersect (their AND is non-empty). */
extern bool bitmap_intersect_p (const_bitmap, const_bitmap);
/* True if the complement of the second intersects the first (their
AND_COMPL is non-empty). */
extern bool bitmap_intersect_compl_p (const_bitmap, const_bitmap);
/* True if MAP is an empty bitmap. */
inline bool bitmap_empty_p (const_bitmap map)
{
return !map->first;
}
/* True if the bitmap has only a single bit set. */
extern bool bitmap_single_bit_set_p (const_bitmap);
/* Count the number of bits set in the bitmap. */
extern unsigned long bitmap_count_bits (const_bitmap);
/* Boolean operations on bitmaps. The _into variants are two operand
versions that modify the first source operand. The other variants
are three operand versions that to not destroy the source bitmaps.
The operations supported are &, & ~, |, ^. */
extern void bitmap_and (bitmap, const_bitmap, const_bitmap);
extern bool bitmap_and_into (bitmap, const_bitmap);
extern bool bitmap_and_compl (bitmap, const_bitmap, const_bitmap);
extern bool bitmap_and_compl_into (bitmap, const_bitmap);
#define bitmap_compl_and(DST, A, B) bitmap_and_compl (DST, B, A)
extern void bitmap_compl_and_into (bitmap, const_bitmap);
extern void bitmap_clear_range (bitmap, unsigned int, unsigned int);
extern void bitmap_set_range (bitmap, unsigned int, unsigned int);
extern bool bitmap_ior (bitmap, const_bitmap, const_bitmap);
extern bool bitmap_ior_into (bitmap, const_bitmap);
extern void bitmap_xor (bitmap, const_bitmap, const_bitmap);
extern void bitmap_xor_into (bitmap, const_bitmap);
/* DST = A | (B & C). Return true if DST changes. */
extern bool bitmap_ior_and_into (bitmap DST, const_bitmap B, const_bitmap C);
/* DST = A | (B & ~C). Return true if DST changes. */
extern bool bitmap_ior_and_compl (bitmap DST, const_bitmap A,
const_bitmap B, const_bitmap C);
/* A |= (B & ~C). Return true if A changes. */
extern bool bitmap_ior_and_compl_into (bitmap A,
const_bitmap B, const_bitmap C);
/* Clear a single bit in a bitmap. Return true if the bit changed. */
extern bool bitmap_clear_bit (bitmap, int);
/* Set a single bit in a bitmap. Return true if the bit changed. */
extern bool bitmap_set_bit (bitmap, int);
/* Return true if a register is set in a register set. */
extern int bitmap_bit_p (bitmap, int);
/* Debug functions to print a bitmap linked list. */
extern void debug_bitmap (const_bitmap);
extern void debug_bitmap_file (FILE *, const_bitmap);
/* Print a bitmap. */
extern void bitmap_print (FILE *, const_bitmap, const char *, const char *);
/* Initialize and release a bitmap obstack. */
extern void bitmap_obstack_initialize (bitmap_obstack *);
extern void bitmap_obstack_release (bitmap_obstack *);
extern void bitmap_register (bitmap MEM_STAT_DECL);
extern void dump_bitmap_statistics (void);
/* Initialize a bitmap header. OBSTACK indicates the bitmap obstack
to allocate from, NULL for GC'd bitmap. */
static inline void
bitmap_initialize_stat (bitmap head, bitmap_obstack *obstack MEM_STAT_DECL)
{
head->first = head->current = NULL;
head->obstack = obstack;
if (GATHER_STATISTICS)
bitmap_register (head PASS_MEM_STAT);
}
#define bitmap_initialize(h,o) bitmap_initialize_stat (h,o MEM_STAT_INFO)
/* Allocate and free bitmaps from obstack, malloc and gc'd memory. */
extern bitmap bitmap_obstack_alloc_stat (bitmap_obstack *obstack MEM_STAT_DECL);
#define bitmap_obstack_alloc(t) bitmap_obstack_alloc_stat (t MEM_STAT_INFO)
extern bitmap bitmap_gc_alloc_stat (ALONE_MEM_STAT_DECL);
#define bitmap_gc_alloc() bitmap_gc_alloc_stat (ALONE_MEM_STAT_INFO)
extern void bitmap_obstack_free (bitmap);
/* A few compatibility/functions macros for compatibility with sbitmaps */
inline void dump_bitmap (FILE *file, const_bitmap map)
{
bitmap_print (file, map, "", "\n");
}
extern unsigned bitmap_first_set_bit (const_bitmap);
extern unsigned bitmap_last_set_bit (const_bitmap);
/* Compute bitmap hash (for purposes of hashing etc.) */
extern hashval_t bitmap_hash(const_bitmap);
/* Allocate a bitmap from a bit obstack. */
#define BITMAP_ALLOC(OBSTACK) bitmap_obstack_alloc (OBSTACK)
/* Allocate a gc'd bitmap. */
#define BITMAP_GGC_ALLOC() bitmap_gc_alloc ()
/* Do any cleanup needed on a bitmap when it is no longer used. */
#define BITMAP_FREE(BITMAP) \
((void) (bitmap_obstack_free ((bitmap) BITMAP), (BITMAP) = (bitmap) NULL))
/* Iterator for bitmaps. */
typedef struct
{
/* Pointer to the current bitmap element. */
bitmap_element *elt1;
/* Pointer to 2nd bitmap element when two are involved. */
bitmap_element *elt2;
/* Word within the current element. */
unsigned word_no;
/* Contents of the actually processed word. When finding next bit
it is shifted right, so that the actual bit is always the least
significant bit of ACTUAL. */
BITMAP_WORD bits;
} bitmap_iterator;
/* Initialize a single bitmap iterator. START_BIT is the first bit to
iterate from. */
static inline void
bmp_iter_set_init (bitmap_iterator *bi, const_bitmap map,
unsigned start_bit, unsigned *bit_no)
{
bi->elt1 = map->first;
bi->elt2 = NULL;
/* Advance elt1 until it is not before the block containing start_bit. */
while (1)
{
if (!bi->elt1)
{
bi->elt1 = &bitmap_zero_bits;
break;
}
if (bi->elt1->indx >= start_bit / BITMAP_ELEMENT_ALL_BITS)
break;
bi->elt1 = bi->elt1->next;
}
/* We might have gone past the start bit, so reinitialize it. */
if (bi->elt1->indx != start_bit / BITMAP_ELEMENT_ALL_BITS)
start_bit = bi->elt1->indx * BITMAP_ELEMENT_ALL_BITS;
/* Initialize for what is now start_bit. */
bi->word_no = start_bit / BITMAP_WORD_BITS % BITMAP_ELEMENT_WORDS;
bi->bits = bi->elt1->bits[bi->word_no];
bi->bits >>= start_bit % BITMAP_WORD_BITS;
/* If this word is zero, we must make sure we're not pointing at the
first bit, otherwise our incrementing to the next word boundary
will fail. It won't matter if this increment moves us into the
next word. */
start_bit += !bi->bits;
*bit_no = start_bit;
}
/* Initialize an iterator to iterate over the intersection of two
bitmaps. START_BIT is the bit to commence from. */
static inline void
bmp_iter_and_init (bitmap_iterator *bi, const_bitmap map1, const_bitmap map2,
unsigned start_bit, unsigned *bit_no)
{
bi->elt1 = map1->first;
bi->elt2 = map2->first;
/* Advance elt1 until it is not before the block containing
start_bit. */
while (1)
{
if (!bi->elt1)
{
bi->elt2 = NULL;
break;
}
if (bi->elt1->indx >= start_bit / BITMAP_ELEMENT_ALL_BITS)
break;
bi->elt1 = bi->elt1->next;
}
/* Advance elt2 until it is not before elt1. */
while (1)
{
if (!bi->elt2)
{
bi->elt1 = bi->elt2 = &bitmap_zero_bits;
break;
}
if (bi->elt2->indx >= bi->elt1->indx)
break;
bi->elt2 = bi->elt2->next;
}
/* If we're at the same index, then we have some intersecting bits. */
if (bi->elt1->indx == bi->elt2->indx)
{
/* We might have advanced beyond the start_bit, so reinitialize
for that. */
if (bi->elt1->indx != start_bit / BITMAP_ELEMENT_ALL_BITS)
start_bit = bi->elt1->indx * BITMAP_ELEMENT_ALL_BITS;
bi->word_no = start_bit / BITMAP_WORD_BITS % BITMAP_ELEMENT_WORDS;
bi->bits = bi->elt1->bits[bi->word_no] & bi->elt2->bits[bi->word_no];
bi->bits >>= start_bit % BITMAP_WORD_BITS;
}
else
{
/* Otherwise we must immediately advance elt1, so initialize for
that. */
bi->word_no = BITMAP_ELEMENT_WORDS - 1;
bi->bits = 0;
}
/* If this word is zero, we must make sure we're not pointing at the
first bit, otherwise our incrementing to the next word boundary
will fail. It won't matter if this increment moves us into the
next word. */
start_bit += !bi->bits;
*bit_no = start_bit;
}
/* Initialize an iterator to iterate over the bits in MAP1 & ~MAP2.
*/
static inline void
bmp_iter_and_compl_init (bitmap_iterator *bi,
const_bitmap map1, const_bitmap map2,
unsigned start_bit, unsigned *bit_no)
{
bi->elt1 = map1->first;
bi->elt2 = map2->first;
/* Advance elt1 until it is not before the block containing start_bit. */
while (1)
{
if (!bi->elt1)
{
bi->elt1 = &bitmap_zero_bits;
break;
}
if (bi->elt1->indx >= start_bit / BITMAP_ELEMENT_ALL_BITS)
break;
bi->elt1 = bi->elt1->next;
}
/* Advance elt2 until it is not before elt1. */
while (bi->elt2 && bi->elt2->indx < bi->elt1->indx)
bi->elt2 = bi->elt2->next;
/* We might have advanced beyond the start_bit, so reinitialize for
that. */
if (bi->elt1->indx != start_bit / BITMAP_ELEMENT_ALL_BITS)
start_bit = bi->elt1->indx * BITMAP_ELEMENT_ALL_BITS;
bi->word_no = start_bit / BITMAP_WORD_BITS % BITMAP_ELEMENT_WORDS;
bi->bits = bi->elt1->bits[bi->word_no];
if (bi->elt2 && bi->elt1->indx == bi->elt2->indx)
bi->bits &= ~bi->elt2->bits[bi->word_no];
bi->bits >>= start_bit % BITMAP_WORD_BITS;
/* If this word is zero, we must make sure we're not pointing at the
first bit, otherwise our incrementing to the next word boundary
will fail. It won't matter if this increment moves us into the
next word. */
start_bit += !bi->bits;
*bit_no = start_bit;
}
/* Advance to the next bit in BI. We don't advance to the next
nonzero bit yet. */
static inline void
bmp_iter_next (bitmap_iterator *bi, unsigned *bit_no)
{
bi->bits >>= 1;
*bit_no += 1;
}
/* Advance to first set bit in BI. */
static inline void
bmp_iter_next_bit (bitmap_iterator * bi, unsigned *bit_no)
{
#if (GCC_VERSION >= 3004)
{
unsigned int n = __builtin_ctzl (bi->bits);
gcc_assert (sizeof (unsigned long) == sizeof (BITMAP_WORD));
bi->bits >>= n;
*bit_no += n;
}
#else
while (!(bi->bits & 1))
{
bi->bits >>= 1;
*bit_no += 1;
}
#endif
}
/* Advance to the next nonzero bit of a single bitmap, we will have
already advanced past the just iterated bit. Return true if there
is a bit to iterate. */
static inline bool
bmp_iter_set (bitmap_iterator *bi, unsigned *bit_no)
{
/* If our current word is nonzero, it contains the bit we want. */
if (bi->bits)
{
next_bit:
bmp_iter_next_bit (bi, bit_no);
return true;
}
/* Round up to the word boundary. We might have just iterated past
the end of the last word, hence the -1. It is not possible for
bit_no to point at the beginning of the now last word. */
*bit_no = ((*bit_no + BITMAP_WORD_BITS - 1)
/ BITMAP_WORD_BITS * BITMAP_WORD_BITS);
bi->word_no++;
while (1)
{
/* Find the next nonzero word in this elt. */
while (bi->word_no != BITMAP_ELEMENT_WORDS)
{
bi->bits = bi->elt1->bits[bi->word_no];
if (bi->bits)
goto next_bit;
*bit_no += BITMAP_WORD_BITS;
bi->word_no++;
}
/* Advance to the next element. */
bi->elt1 = bi->elt1->next;
if (!bi->elt1)
return false;
*bit_no = bi->elt1->indx * BITMAP_ELEMENT_ALL_BITS;
bi->word_no = 0;
}
}
/* Advance to the next nonzero bit of an intersecting pair of
bitmaps. We will have already advanced past the just iterated bit.
Return true if there is a bit to iterate. */
static inline bool
bmp_iter_and (bitmap_iterator *bi, unsigned *bit_no)
{
/* If our current word is nonzero, it contains the bit we want. */
if (bi->bits)
{
next_bit:
bmp_iter_next_bit (bi, bit_no);
return true;
}
/* Round up to the word boundary. We might have just iterated past
the end of the last word, hence the -1. It is not possible for
bit_no to point at the beginning of the now last word. */
*bit_no = ((*bit_no + BITMAP_WORD_BITS - 1)
/ BITMAP_WORD_BITS * BITMAP_WORD_BITS);
bi->word_no++;
while (1)
{
/* Find the next nonzero word in this elt. */
while (bi->word_no != BITMAP_ELEMENT_WORDS)
{
bi->bits = bi->elt1->bits[bi->word_no] & bi->elt2->bits[bi->word_no];
if (bi->bits)
goto next_bit;
*bit_no += BITMAP_WORD_BITS;
bi->word_no++;
}
/* Advance to the next identical element. */
do
{
/* Advance elt1 while it is less than elt2. We always want
to advance one elt. */
do
{
bi->elt1 = bi->elt1->next;
if (!bi->elt1)
return false;
}
while (bi->elt1->indx < bi->elt2->indx);
/* Advance elt2 to be no less than elt1. This might not
advance. */
while (bi->elt2->indx < bi->elt1->indx)
{
bi->elt2 = bi->elt2->next;
if (!bi->elt2)
return false;
}
}
while (bi->elt1->indx != bi->elt2->indx);
*bit_no = bi->elt1->indx * BITMAP_ELEMENT_ALL_BITS;
bi->word_no = 0;
}
}
/* Advance to the next nonzero bit in the intersection of
complemented bitmaps. We will have already advanced past the just
iterated bit. */
static inline bool
bmp_iter_and_compl (bitmap_iterator *bi, unsigned *bit_no)
{
/* If our current word is nonzero, it contains the bit we want. */
if (bi->bits)
{
next_bit:
bmp_iter_next_bit (bi, bit_no);
return true;
}
/* Round up to the word boundary. We might have just iterated past
the end of the last word, hence the -1. It is not possible for
bit_no to point at the beginning of the now last word. */
*bit_no = ((*bit_no + BITMAP_WORD_BITS - 1)
/ BITMAP_WORD_BITS * BITMAP_WORD_BITS);
bi->word_no++;
while (1)
{
/* Find the next nonzero word in this elt. */
while (bi->word_no != BITMAP_ELEMENT_WORDS)
{
bi->bits = bi->elt1->bits[bi->word_no];
if (bi->elt2 && bi->elt2->indx == bi->elt1->indx)
bi->bits &= ~bi->elt2->bits[bi->word_no];
if (bi->bits)
goto next_bit;
*bit_no += BITMAP_WORD_BITS;
bi->word_no++;
}
/* Advance to the next element of elt1. */
bi->elt1 = bi->elt1->next;
if (!bi->elt1)
return false;
/* Advance elt2 until it is no less than elt1. */
while (bi->elt2 && bi->elt2->indx < bi->elt1->indx)
bi->elt2 = bi->elt2->next;
*bit_no = bi->elt1->indx * BITMAP_ELEMENT_ALL_BITS;
bi->word_no = 0;
}
}
/* Loop over all bits set in BITMAP, starting with MIN and setting
BITNUM to the bit number. ITER is a bitmap iterator. BITNUM
should be treated as a read-only variable as it contains loop
state. */
#ifndef EXECUTE_IF_SET_IN_BITMAP
/* See sbitmap.h for the other definition of EXECUTE_IF_SET_IN_BITMAP. */
#define EXECUTE_IF_SET_IN_BITMAP(BITMAP, MIN, BITNUM, ITER) \
for (bmp_iter_set_init (&(ITER), (BITMAP), (MIN), &(BITNUM)); \
bmp_iter_set (&(ITER), &(BITNUM)); \
bmp_iter_next (&(ITER), &(BITNUM)))
#endif
/* Loop over all the bits set in BITMAP1 & BITMAP2, starting with MIN
and setting BITNUM to the bit number. ITER is a bitmap iterator.
BITNUM should be treated as a read-only variable as it contains
loop state. */
#define EXECUTE_IF_AND_IN_BITMAP(BITMAP1, BITMAP2, MIN, BITNUM, ITER) \
for (bmp_iter_and_init (&(ITER), (BITMAP1), (BITMAP2), (MIN), \
&(BITNUM)); \
bmp_iter_and (&(ITER), &(BITNUM)); \
bmp_iter_next (&(ITER), &(BITNUM)))
/* Loop over all the bits set in BITMAP1 & ~BITMAP2, starting with MIN
and setting BITNUM to the bit number. ITER is a bitmap iterator.
BITNUM should be treated as a read-only variable as it contains
loop state. */
#define EXECUTE_IF_AND_COMPL_IN_BITMAP(BITMAP1, BITMAP2, MIN, BITNUM, ITER) \
for (bmp_iter_and_compl_init (&(ITER), (BITMAP1), (BITMAP2), (MIN), \
&(BITNUM)); \
bmp_iter_and_compl (&(ITER), &(BITNUM)); \
bmp_iter_next (&(ITER), &(BITNUM)))
#endif /* GCC_BITMAP_H */

842
src/include/builtins.def Normal file
View File

@ -0,0 +1,842 @@
/* This file contains the definitions and documentation for the
builtins used in the GNU compiler.
Copyright (C) 2000-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
/* Before including this file, you should define a macro:
DEF_BUILTIN (ENUM, NAME, CLASS, TYPE, LIBTYPE, BOTH_P,
FALLBACK_P, NONANSI_P, ATTRS, IMPLICIT, COND)
This macro will be called once for each builtin function. The
ENUM will be of type `enum built_in_function', and will indicate
which builtin function is being processed. The NAME of the builtin
function (which will always start with `__builtin_') is a string
literal. The CLASS is of type `enum built_in_class' and indicates
what kind of builtin is being processed.
Some builtins are actually two separate functions. For example,
for `strcmp' there are two builtin functions; `__builtin_strcmp'
and `strcmp' itself. Both behave identically. Other builtins
define only the `__builtin' variant. If BOTH_P is TRUE, then this
builtin has both variants; otherwise, it is has only the first
variant.
TYPE indicates the type of the function. The symbols correspond to
enumerals from builtin-types.def. If BOTH_P is true, then LIBTYPE
is the type of the non-`__builtin_' variant. Otherwise, LIBTYPE
should be ignored.
If FALLBACK_P is true then, if for some reason, the compiler cannot
expand the builtin function directly, it will call the
corresponding library function (which does not have the
`__builtin_' prefix.
If NONANSI_P is true, then the non-`__builtin_' variant is not an
ANSI/ISO library function, and so we should pretend it does not
exist when compiling in ANSI conformant mode.
ATTRs is an attribute list as defined in builtin-attrs.def that
describes the attributes of this builtin function.
IMPLICIT specifies condition when the builtin can be produced by
compiler. For instance C90 reserves floorf function, but does not
define it's meaning. When user uses floorf we may assume that the
floorf has the meaning we expect, but we can't produce floorf by
simplifying floor((double)float) since the runtime need not implement
it.
The builtins is registered only if COND is true. */
/* A GCC builtin (like __builtin_saveregs) is provided by the
compiler, but does not correspond to a function in the standard
library. */
#undef DEF_GCC_BUILTIN
#define DEF_GCC_BUILTIN(ENUM, NAME, TYPE, ATTRS) \
DEF_BUILTIN (ENUM, "__builtin_" NAME, BUILT_IN_NORMAL, TYPE, BT_LAST, \
false, false, false, ATTRS, true, true)
/* Like DEF_GCC_BUILTIN, except we don't prepend "__builtin_". */
#undef DEF_SYNC_BUILTIN
#define DEF_SYNC_BUILTIN(ENUM, NAME, TYPE, ATTRS) \
DEF_BUILTIN (ENUM, NAME, BUILT_IN_NORMAL, TYPE, BT_LAST, \
false, false, false, ATTRS, true, true)
/* A library builtin (like __builtin_strchr) is a builtin equivalent
of an ANSI/ISO standard library function. In addition to the
`__builtin' version, we will create an ordinary version (e.g,
`strchr') as well. If we cannot compute the answer using the
builtin function, we will fall back to the standard library
version. */
#undef DEF_LIB_BUILTIN
#define DEF_LIB_BUILTIN(ENUM, NAME, TYPE, ATTRS) \
DEF_BUILTIN (ENUM, "__builtin_" NAME, BUILT_IN_NORMAL, TYPE, TYPE, \
true, true, false, ATTRS, true, true)
/* Like DEF_LIB_BUILTIN, except that the function is not one that is
specified by ANSI/ISO C. So, when we're being fully conformant we
ignore the version of these builtins that does not begin with
__builtin. */
#undef DEF_EXT_LIB_BUILTIN
#define DEF_EXT_LIB_BUILTIN(ENUM, NAME, TYPE, ATTRS) \
DEF_BUILTIN (ENUM, "__builtin_" NAME, BUILT_IN_NORMAL, TYPE, TYPE, \
true, true, true, ATTRS, false, true)
/* Like DEF_LIB_BUILTIN, except that the function is only a part of
the standard in C94 or above. */
#undef DEF_C94_BUILTIN
#define DEF_C94_BUILTIN(ENUM, NAME, TYPE, ATTRS) \
DEF_BUILTIN (ENUM, "__builtin_" NAME, BUILT_IN_NORMAL, TYPE, TYPE, \
true, true, !flag_isoc94, ATTRS, TARGET_C99_FUNCTIONS, true)
/* Like DEF_LIB_BUILTIN, except that the function is only a part of
the standard in C99 or above. */
#undef DEF_C99_BUILTIN
#define DEF_C99_BUILTIN(ENUM, NAME, TYPE, ATTRS) \
DEF_BUILTIN (ENUM, "__builtin_" NAME, BUILT_IN_NORMAL, TYPE, TYPE, \
true, true, !flag_isoc99, ATTRS, TARGET_C99_FUNCTIONS, true)
/* Builtin that is specified by C99 and C90 reserve the name for future use.
We can still recognize the builtin in C90 mode but we can't produce it
implicitly. */
#undef DEF_C99_C90RES_BUILTIN
#define DEF_C99_C90RES_BUILTIN(ENUM, NAME, TYPE, ATTRS) \
DEF_BUILTIN (ENUM, "__builtin_" NAME, BUILT_IN_NORMAL, TYPE, TYPE, \
true, true, !flag_isoc99, ATTRS, TARGET_C99_FUNCTIONS, true)
/* Builtin that C99 reserve the name for future use. We can still recognize
the builtin in C99 mode but we can't produce it implicitly. */
#undef DEF_EXT_C99RES_BUILTIN
#define DEF_EXT_C99RES_BUILTIN(ENUM, NAME, TYPE, ATTRS) \
DEF_BUILTIN (ENUM, "__builtin_" NAME, BUILT_IN_NORMAL, TYPE, TYPE, \
true, true, true, ATTRS, false, true)
/* Allocate the enum and the name for a builtin, but do not actually
define it here at all. */
#undef DEF_BUILTIN_STUB
#define DEF_BUILTIN_STUB(ENUM, NAME) \
DEF_BUILTIN (ENUM, NAME, BUILT_IN_NORMAL, BT_LAST, BT_LAST, false, false, \
false, ATTR_LAST, false, false)
/* Builtin used by the implementation of GNU OpenMP. None of these are
actually implemented in the compiler; they're all in libgomp. */
#undef DEF_GOMP_BUILTIN
#define DEF_GOMP_BUILTIN(ENUM, NAME, TYPE, ATTRS) \
DEF_BUILTIN (ENUM, "__builtin_" NAME, BUILT_IN_NORMAL, TYPE, TYPE, \
false, true, true, ATTRS, false, \
(flag_openmp || flag_tree_parallelize_loops))
/* Builtin used by the implementation of GNU TM. These
functions are mapped to the actual implementation of the STM library. */
#undef DEF_TM_BUILTIN
#define DEF_TM_BUILTIN(ENUM, NAME, TYPE, ATTRS) \
DEF_BUILTIN (ENUM, "__builtin_" NAME, BUILT_IN_NORMAL, TYPE, TYPE, \
true, true, true, ATTRS, false, flag_tm)
/* Builtin used by the implementation of libsanitizer. These
functions are mapped to the actual implementation of the
libtsan library. */
#undef DEF_SANITIZER_BUILTIN
#define DEF_SANITIZER_BUILTIN(ENUM, NAME, TYPE, ATTRS) \
DEF_BUILTIN (ENUM, "__builtin_" NAME, BUILT_IN_NORMAL, TYPE, TYPE, \
true, true, true, ATTRS, true, \
(flag_asan || flag_tsan))
/* Define an attribute list for math functions that are normally
"impure" because some of them may write into global memory for
`errno'. If !flag_errno_math they are instead "const". */
#undef ATTR_MATHFN_ERRNO
#define ATTR_MATHFN_ERRNO (flag_errno_math ? \
ATTR_NOTHROW_LEAF_LIST : ATTR_CONST_NOTHROW_LEAF_LIST)
/* Define an attribute list for math functions that are normally
"const" but if flag_rounding_math is set they are instead "pure".
This distinction accounts for the fact that some math functions
check the rounding mode which is akin to examining global
memory. */
#undef ATTR_MATHFN_FPROUNDING
#define ATTR_MATHFN_FPROUNDING (flag_rounding_math ? \
ATTR_PURE_NOTHROW_LEAF_LIST : ATTR_CONST_NOTHROW_LEAF_LIST)
/* Define an attribute list for math functions that are normally
"impure" because some of them may write into global memory for
`errno'. If !flag_errno_math, we can possibly use "pure" or
"const" depending on whether we care about FP rounding. */
#undef ATTR_MATHFN_FPROUNDING_ERRNO
#define ATTR_MATHFN_FPROUNDING_ERRNO (flag_errno_math ? \
ATTR_NOTHROW_LEAF_LIST : ATTR_MATHFN_FPROUNDING)
/* Define an attribute list for math functions that need to mind FP
rounding, but because they store into memory they are never "const"
or "pure". Use of this macro is mainly for documentation and
maintenance purposes. */
#undef ATTR_MATHFN_FPROUNDING_STORE
#define ATTR_MATHFN_FPROUNDING_STORE ATTR_NOTHROW_LEAF_LIST
/* Make sure 0 is not a legitimate builtin. */
DEF_BUILTIN_STUB(BUILT_IN_NONE, (const char *)0)
/* Category: math builtins. */
DEF_LIB_BUILTIN (BUILT_IN_ACOS, "acos", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_C90RES_BUILTIN (BUILT_IN_ACOSF, "acosf", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_ACOSH, "acosh", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_ACOSHF, "acoshf", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_ACOSHL, "acoshl", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_C90RES_BUILTIN (BUILT_IN_ACOSL, "acosl", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_LIB_BUILTIN (BUILT_IN_ASIN, "asin", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_C90RES_BUILTIN (BUILT_IN_ASINF, "asinf", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_ASINH, "asinh", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_ASINHF, "asinhf", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_ASINHL, "asinhl", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_C90RES_BUILTIN (BUILT_IN_ASINL, "asinl", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_LIB_BUILTIN (BUILT_IN_ATAN, "atan", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_LIB_BUILTIN (BUILT_IN_ATAN2, "atan2", BT_FN_DOUBLE_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_C90RES_BUILTIN (BUILT_IN_ATAN2F, "atan2f", BT_FN_FLOAT_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_C90RES_BUILTIN (BUILT_IN_ATAN2L, "atan2l", BT_FN_LONGDOUBLE_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_C90RES_BUILTIN (BUILT_IN_ATANF, "atanf", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_ATANH, "atanh", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_ATANHF, "atanhf", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_ATANHL, "atanhl", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_C90RES_BUILTIN (BUILT_IN_ATANL, "atanl", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CBRT, "cbrt", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CBRTF, "cbrtf", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CBRTL, "cbrtl", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_LIB_BUILTIN (BUILT_IN_CEIL, "ceil", BT_FN_DOUBLE_DOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_C90RES_BUILTIN (BUILT_IN_CEILF, "ceilf", BT_FN_FLOAT_FLOAT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_C90RES_BUILTIN (BUILT_IN_CEILL, "ceill", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_COPYSIGN, "copysign", BT_FN_DOUBLE_DOUBLE_DOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_COPYSIGNF, "copysignf", BT_FN_FLOAT_FLOAT_FLOAT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_COPYSIGNL, "copysignl", BT_FN_LONGDOUBLE_LONGDOUBLE_LONGDOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_LIB_BUILTIN (BUILT_IN_COS, "cos", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_C90RES_BUILTIN (BUILT_IN_COSF, "cosf", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_LIB_BUILTIN (BUILT_IN_COSH, "cosh", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_C90RES_BUILTIN (BUILT_IN_COSHF, "coshf", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_C90RES_BUILTIN (BUILT_IN_COSHL, "coshl", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_C90RES_BUILTIN (BUILT_IN_COSL, "cosl", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_EXT_LIB_BUILTIN (BUILT_IN_DREM, "drem", BT_FN_DOUBLE_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_DREMF, "dremf", BT_FN_FLOAT_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_DREML, "dreml", BT_FN_LONGDOUBLE_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_ERF, "erf", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_ERFC, "erfc", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_ERFCF, "erfcf", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_ERFCL, "erfcl", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_ERFF, "erff", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_ERFL, "erfl", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_LIB_BUILTIN (BUILT_IN_EXP, "exp", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_EXP10, "exp10", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_EXP10F, "exp10f", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_EXP10L, "exp10l", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_EXP2, "exp2", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_EXP2F, "exp2f", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_EXP2L, "exp2l", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_C90RES_BUILTIN (BUILT_IN_EXPF, "expf", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_C90RES_BUILTIN (BUILT_IN_EXPL, "expl", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_EXPM1, "expm1", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_EXPM1F, "expm1f", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_EXPM1L, "expm1l", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_LIB_BUILTIN (BUILT_IN_FABS, "fabs", BT_FN_DOUBLE_DOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_C90RES_BUILTIN (BUILT_IN_FABSF, "fabsf", BT_FN_FLOAT_FLOAT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_C90RES_BUILTIN (BUILT_IN_FABSL, "fabsl", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_FABSD32, "fabsd32", BT_FN_DFLOAT32_DFLOAT32, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_FABSD64, "fabsd64", BT_FN_DFLOAT64_DFLOAT64, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_FABSD128, "fabsd128", BT_FN_DFLOAT128_DFLOAT128, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_FDIM, "fdim", BT_FN_DOUBLE_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_FDIMF, "fdimf", BT_FN_FLOAT_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_FDIML, "fdiml", BT_FN_LONGDOUBLE_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_LIB_BUILTIN (BUILT_IN_FLOOR, "floor", BT_FN_DOUBLE_DOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_C90RES_BUILTIN (BUILT_IN_FLOORF, "floorf", BT_FN_FLOAT_FLOAT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_C90RES_BUILTIN (BUILT_IN_FLOORL, "floorl", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_FMA, "fma", BT_FN_DOUBLE_DOUBLE_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_FMAF, "fmaf", BT_FN_FLOAT_FLOAT_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_FMAL, "fmal", BT_FN_LONGDOUBLE_LONGDOUBLE_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_FMAX, "fmax", BT_FN_DOUBLE_DOUBLE_DOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_FMAXF, "fmaxf", BT_FN_FLOAT_FLOAT_FLOAT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_FMAXL, "fmaxl", BT_FN_LONGDOUBLE_LONGDOUBLE_LONGDOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_FMIN, "fmin", BT_FN_DOUBLE_DOUBLE_DOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_FMINF, "fminf", BT_FN_FLOAT_FLOAT_FLOAT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_FMINL, "fminl", BT_FN_LONGDOUBLE_LONGDOUBLE_LONGDOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_LIB_BUILTIN (BUILT_IN_FMOD, "fmod", BT_FN_DOUBLE_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_C90RES_BUILTIN (BUILT_IN_FMODF, "fmodf", BT_FN_FLOAT_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_C90RES_BUILTIN (BUILT_IN_FMODL, "fmodl", BT_FN_LONGDOUBLE_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_LIB_BUILTIN (BUILT_IN_FREXP, "frexp", BT_FN_DOUBLE_DOUBLE_INTPTR, ATTR_MATHFN_FPROUNDING_STORE)
DEF_C99_C90RES_BUILTIN (BUILT_IN_FREXPF, "frexpf", BT_FN_FLOAT_FLOAT_INTPTR, ATTR_MATHFN_FPROUNDING_STORE)
DEF_C99_C90RES_BUILTIN (BUILT_IN_FREXPL, "frexpl", BT_FN_LONGDOUBLE_LONGDOUBLE_INTPTR, ATTR_MATHFN_FPROUNDING_STORE)
DEF_EXT_LIB_BUILTIN (BUILT_IN_GAMMA, "gamma", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_STORE)
DEF_EXT_LIB_BUILTIN (BUILT_IN_GAMMAF, "gammaf", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_STORE)
DEF_EXT_LIB_BUILTIN (BUILT_IN_GAMMAL, "gammal", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_STORE)
DEF_EXT_LIB_BUILTIN (BUILT_IN_GAMMA_R, "gamma_r", BT_FN_DOUBLE_DOUBLE_INTPTR, ATTR_MATHFN_FPROUNDING_STORE)
DEF_EXT_LIB_BUILTIN (BUILT_IN_GAMMAF_R, "gammaf_r", BT_FN_FLOAT_FLOAT_INTPTR, ATTR_MATHFN_FPROUNDING_STORE)
DEF_EXT_LIB_BUILTIN (BUILT_IN_GAMMAL_R, "gammal_r", BT_FN_LONGDOUBLE_LONGDOUBLE_INTPTR, ATTR_MATHFN_FPROUNDING_STORE)
DEF_GCC_BUILTIN (BUILT_IN_HUGE_VAL, "huge_val", BT_FN_DOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_HUGE_VALF, "huge_valf", BT_FN_FLOAT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_HUGE_VALL, "huge_vall", BT_FN_LONGDOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_HYPOT, "hypot", BT_FN_DOUBLE_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_HYPOTF, "hypotf", BT_FN_FLOAT_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_HYPOTL, "hypotl", BT_FN_LONGDOUBLE_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_GCC_BUILTIN (BUILT_IN_ICEIL, "iceil", BT_FN_INT_DOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_ICEILF, "iceilf", BT_FN_INT_FLOAT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_ICEILL, "iceill", BT_FN_INT_LONGDOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_IFLOOR, "ifloor", BT_FN_INT_DOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_IFLOORF, "ifloorf", BT_FN_INT_FLOAT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_IFLOORL, "ifloorl", BT_FN_INT_LONGDOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_ILOGB, "ilogb", BT_FN_INT_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_ILOGBF, "ilogbf", BT_FN_INT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_ILOGBL, "ilogbl", BT_FN_INT_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_GCC_BUILTIN (BUILT_IN_INF, "inf", BT_FN_DOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_INFF, "inff", BT_FN_FLOAT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_INFL, "infl", BT_FN_LONGDOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_INFD32, "infd32", BT_FN_DFLOAT32, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_INFD64, "infd64", BT_FN_DFLOAT64, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_INFD128, "infd128", BT_FN_DFLOAT128, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_IRINT, "irint", BT_FN_INT_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_GCC_BUILTIN (BUILT_IN_IRINTF, "irintf", BT_FN_INT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_GCC_BUILTIN (BUILT_IN_IRINTL, "irintl", BT_FN_INT_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_GCC_BUILTIN (BUILT_IN_IROUND, "iround", BT_FN_INT_DOUBLE, ATTR_MATHFN_ERRNO)
DEF_GCC_BUILTIN (BUILT_IN_IROUNDF, "iroundf", BT_FN_INT_FLOAT, ATTR_MATHFN_ERRNO)
DEF_GCC_BUILTIN (BUILT_IN_IROUNDL, "iroundl", BT_FN_INT_LONGDOUBLE, ATTR_MATHFN_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_J0, "j0", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_J0F, "j0f", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_J0L, "j0l", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_J1, "j1", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_J1F, "j1f", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_J1L, "j1l", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_JN, "jn", BT_FN_DOUBLE_INT_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_JNF, "jnf", BT_FN_FLOAT_INT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_JNL, "jnl", BT_FN_LONGDOUBLE_INT_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_GCC_BUILTIN (BUILT_IN_LCEIL, "lceil", BT_FN_LONG_DOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_LCEILF, "lceilf", BT_FN_LONG_FLOAT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_LCEILL, "lceill", BT_FN_LONG_LONGDOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_LIB_BUILTIN (BUILT_IN_LDEXP, "ldexp", BT_FN_DOUBLE_DOUBLE_INT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_C90RES_BUILTIN (BUILT_IN_LDEXPF, "ldexpf", BT_FN_FLOAT_FLOAT_INT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_C90RES_BUILTIN (BUILT_IN_LDEXPL, "ldexpl", BT_FN_LONGDOUBLE_LONGDOUBLE_INT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_GCC_BUILTIN (BUILT_IN_LFLOOR, "lfloor", BT_FN_LONG_DOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_LFLOORF, "lfloorf", BT_FN_LONG_FLOAT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_LFLOORL, "lfloorl", BT_FN_LONG_LONGDOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_LGAMMA, "lgamma", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_STORE)
DEF_C99_BUILTIN (BUILT_IN_LGAMMAF, "lgammaf", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_STORE)
DEF_C99_BUILTIN (BUILT_IN_LGAMMAL, "lgammal", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_STORE)
DEF_EXT_LIB_BUILTIN (BUILT_IN_LGAMMA_R, "lgamma_r", BT_FN_DOUBLE_DOUBLE_INTPTR, ATTR_MATHFN_FPROUNDING_STORE)
DEF_EXT_LIB_BUILTIN (BUILT_IN_LGAMMAF_R, "lgammaf_r", BT_FN_FLOAT_FLOAT_INTPTR, ATTR_MATHFN_FPROUNDING_STORE)
DEF_EXT_LIB_BUILTIN (BUILT_IN_LGAMMAL_R, "lgammal_r", BT_FN_LONGDOUBLE_LONGDOUBLE_INTPTR, ATTR_MATHFN_FPROUNDING_STORE)
DEF_GCC_BUILTIN (BUILT_IN_LLCEIL, "llceil", BT_FN_LONGLONG_DOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_LLCEILF, "llceilf", BT_FN_LONGLONG_FLOAT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_LLCEILL, "llceill", BT_FN_LONGLONG_LONGDOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_LLFLOOR, "llfloor", BT_FN_LONGLONG_DOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_LLFLOORF, "llfloorf", BT_FN_LONGLONG_FLOAT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_LLFLOORL, "llfloorl", BT_FN_LONGLONG_LONGDOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_LLRINT, "llrint", BT_FN_LONGLONG_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_LLRINTF, "llrintf", BT_FN_LONGLONG_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_LLRINTL, "llrintl", BT_FN_LONGLONG_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_LLROUND, "llround", BT_FN_LONGLONG_DOUBLE, ATTR_MATHFN_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_LLROUNDF, "llroundf", BT_FN_LONGLONG_FLOAT, ATTR_MATHFN_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_LLROUNDL, "llroundl", BT_FN_LONGLONG_LONGDOUBLE, ATTR_MATHFN_ERRNO)
DEF_LIB_BUILTIN (BUILT_IN_LOG, "log", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_LIB_BUILTIN (BUILT_IN_LOG10, "log10", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_C90RES_BUILTIN (BUILT_IN_LOG10F, "log10f", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_C90RES_BUILTIN (BUILT_IN_LOG10L, "log10l", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_LOG1P, "log1p", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_LOG1PF, "log1pf", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_LOG1PL, "log1pl", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_LOG2, "log2", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_LOG2F, "log2f", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_LOG2L, "log2l", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_LOGB, "logb", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_LOGBF, "logbf", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_LOGBL, "logbl", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_C90RES_BUILTIN (BUILT_IN_LOGF, "logf", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_C90RES_BUILTIN (BUILT_IN_LOGL, "logl", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_LRINT, "lrint", BT_FN_LONG_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_LRINTF, "lrintf", BT_FN_LONG_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_LRINTL, "lrintl", BT_FN_LONG_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_LROUND, "lround", BT_FN_LONG_DOUBLE, ATTR_MATHFN_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_LROUNDF, "lroundf", BT_FN_LONG_FLOAT, ATTR_MATHFN_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_LROUNDL, "lroundl", BT_FN_LONG_LONGDOUBLE, ATTR_MATHFN_ERRNO)
DEF_LIB_BUILTIN (BUILT_IN_MODF, "modf", BT_FN_DOUBLE_DOUBLE_DOUBLEPTR, ATTR_MATHFN_FPROUNDING_STORE)
DEF_C99_C90RES_BUILTIN (BUILT_IN_MODFF, "modff", BT_FN_FLOAT_FLOAT_FLOATPTR, ATTR_MATHFN_FPROUNDING_STORE)
DEF_C99_C90RES_BUILTIN (BUILT_IN_MODFL, "modfl", BT_FN_LONGDOUBLE_LONGDOUBLE_LONGDOUBLEPTR, ATTR_MATHFN_FPROUNDING_STORE)
DEF_C99_BUILTIN (BUILT_IN_NAN, "nan", BT_FN_DOUBLE_CONST_STRING, ATTR_CONST_NOTHROW_NONNULL)
DEF_C99_BUILTIN (BUILT_IN_NANF, "nanf", BT_FN_FLOAT_CONST_STRING, ATTR_CONST_NOTHROW_NONNULL)
DEF_C99_BUILTIN (BUILT_IN_NANL, "nanl", BT_FN_LONGDOUBLE_CONST_STRING, ATTR_CONST_NOTHROW_NONNULL)
DEF_GCC_BUILTIN (BUILT_IN_NAND32, "nand32", BT_FN_DFLOAT32_CONST_STRING, ATTR_CONST_NOTHROW_NONNULL)
DEF_GCC_BUILTIN (BUILT_IN_NAND64, "nand64", BT_FN_DFLOAT64_CONST_STRING, ATTR_CONST_NOTHROW_NONNULL)
DEF_GCC_BUILTIN (BUILT_IN_NAND128, "nand128", BT_FN_DFLOAT128_CONST_STRING, ATTR_CONST_NOTHROW_NONNULL)
DEF_GCC_BUILTIN (BUILT_IN_NANS, "nans", BT_FN_DOUBLE_CONST_STRING, ATTR_CONST_NOTHROW_NONNULL)
DEF_GCC_BUILTIN (BUILT_IN_NANSF, "nansf", BT_FN_FLOAT_CONST_STRING, ATTR_CONST_NOTHROW_NONNULL)
DEF_GCC_BUILTIN (BUILT_IN_NANSL, "nansl", BT_FN_LONGDOUBLE_CONST_STRING, ATTR_CONST_NOTHROW_NONNULL)
DEF_C99_BUILTIN (BUILT_IN_NEARBYINT, "nearbyint", BT_FN_DOUBLE_DOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_NEARBYINTF, "nearbyintf", BT_FN_FLOAT_FLOAT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_NEARBYINTL, "nearbyintl", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_NEXTAFTER, "nextafter", BT_FN_DOUBLE_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_NEXTAFTERF, "nextafterf", BT_FN_FLOAT_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_NEXTAFTERL, "nextafterl", BT_FN_LONGDOUBLE_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_NEXTTOWARD, "nexttoward", BT_FN_DOUBLE_DOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_NEXTTOWARDF, "nexttowardf", BT_FN_FLOAT_FLOAT_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_NEXTTOWARDL, "nexttowardl", BT_FN_LONGDOUBLE_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_LIB_BUILTIN (BUILT_IN_POW, "pow", BT_FN_DOUBLE_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_POW10, "pow10", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_POW10F, "pow10f", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_POW10L, "pow10l", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_C90RES_BUILTIN (BUILT_IN_POWF, "powf", BT_FN_FLOAT_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_GCC_BUILTIN (BUILT_IN_POWI, "powi", BT_FN_DOUBLE_DOUBLE_INT, ATTR_MATHFN_FPROUNDING)
DEF_GCC_BUILTIN (BUILT_IN_POWIF, "powif", BT_FN_FLOAT_FLOAT_INT, ATTR_MATHFN_FPROUNDING)
DEF_GCC_BUILTIN (BUILT_IN_POWIL, "powil", BT_FN_LONGDOUBLE_LONGDOUBLE_INT, ATTR_MATHFN_FPROUNDING)
DEF_C99_C90RES_BUILTIN (BUILT_IN_POWL, "powl", BT_FN_LONGDOUBLE_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_REMAINDER, "remainder", BT_FN_DOUBLE_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_REMAINDERF, "remainderf", BT_FN_FLOAT_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_REMAINDERL, "remainderl", BT_FN_LONGDOUBLE_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_REMQUO, "remquo", BT_FN_DOUBLE_DOUBLE_DOUBLE_INTPTR, ATTR_MATHFN_FPROUNDING_STORE)
DEF_C99_BUILTIN (BUILT_IN_REMQUOF, "remquof", BT_FN_FLOAT_FLOAT_FLOAT_INTPTR, ATTR_MATHFN_FPROUNDING_STORE)
DEF_C99_BUILTIN (BUILT_IN_REMQUOL, "remquol", BT_FN_LONGDOUBLE_LONGDOUBLE_LONGDOUBLE_INTPTR, ATTR_MATHFN_FPROUNDING_STORE)
DEF_C99_BUILTIN (BUILT_IN_RINT, "rint", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_RINTF, "rintf", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_RINTL, "rintl", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_ROUND, "round", BT_FN_DOUBLE_DOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_ROUNDF, "roundf", BT_FN_FLOAT_FLOAT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_ROUNDL, "roundl", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_SCALB, "scalb", BT_FN_DOUBLE_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_SCALBF, "scalbf", BT_FN_FLOAT_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_SCALBL, "scalbl", BT_FN_LONGDOUBLE_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_SCALBLN, "scalbln", BT_FN_DOUBLE_DOUBLE_LONG, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_SCALBLNF, "scalblnf", BT_FN_FLOAT_FLOAT_LONG, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_SCALBLNL, "scalblnl", BT_FN_LONGDOUBLE_LONGDOUBLE_LONG, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_SCALBN, "scalbn", BT_FN_DOUBLE_DOUBLE_INT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_SCALBNF, "scalbnf", BT_FN_FLOAT_FLOAT_INT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_SCALBNL, "scalbnl", BT_FN_LONGDOUBLE_LONGDOUBLE_INT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_SIGNBIT, "signbit", BT_FN_INT_DOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_SIGNBITF, "signbitf", BT_FN_INT_FLOAT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_SIGNBITL, "signbitl", BT_FN_INT_LONGDOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_SIGNBITD32, "signbitd32", BT_FN_INT_DFLOAT32, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_SIGNBITD64, "signbitd64", BT_FN_INT_DFLOAT64, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_SIGNBITD128, "signbitd128", BT_FN_INT_DFLOAT128, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_SIGNIFICAND, "significand", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_SIGNIFICANDF, "significandf", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_SIGNIFICANDL, "significandl", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_LIB_BUILTIN (BUILT_IN_SIN, "sin", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_EXT_LIB_BUILTIN (BUILT_IN_SINCOS, "sincos", BT_FN_VOID_DOUBLE_DOUBLEPTR_DOUBLEPTR, ATTR_MATHFN_FPROUNDING_STORE)
DEF_EXT_LIB_BUILTIN (BUILT_IN_SINCOSF, "sincosf", BT_FN_VOID_FLOAT_FLOATPTR_FLOATPTR, ATTR_MATHFN_FPROUNDING_STORE)
DEF_EXT_LIB_BUILTIN (BUILT_IN_SINCOSL, "sincosl", BT_FN_VOID_LONGDOUBLE_LONGDOUBLEPTR_LONGDOUBLEPTR, ATTR_MATHFN_FPROUNDING_STORE)
DEF_C99_C90RES_BUILTIN (BUILT_IN_SINF, "sinf", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_LIB_BUILTIN (BUILT_IN_SINH, "sinh", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_C90RES_BUILTIN (BUILT_IN_SINHF, "sinhf", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_C90RES_BUILTIN (BUILT_IN_SINHL, "sinhl", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_C90RES_BUILTIN (BUILT_IN_SINL, "sinl", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_LIB_BUILTIN (BUILT_IN_SQRT, "sqrt", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_C90RES_BUILTIN (BUILT_IN_SQRTF, "sqrtf", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_C90RES_BUILTIN (BUILT_IN_SQRTL, "sqrtl", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_LIB_BUILTIN (BUILT_IN_TAN, "tan", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_C90RES_BUILTIN (BUILT_IN_TANF, "tanf", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_LIB_BUILTIN (BUILT_IN_TANH, "tanh", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_C90RES_BUILTIN (BUILT_IN_TANHF, "tanhf", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_C99_C90RES_BUILTIN (BUILT_IN_TANHL, "tanhl", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_C90RES_BUILTIN (BUILT_IN_TANL, "tanl", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_TGAMMA, "tgamma", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_TGAMMAF, "tgammaf", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_TGAMMAL, "tgammal", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_C99_BUILTIN (BUILT_IN_TRUNC, "trunc", BT_FN_DOUBLE_DOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_TRUNCF, "truncf", BT_FN_FLOAT_FLOAT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_TRUNCL, "truncl", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_Y0, "y0", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_Y0F, "y0f", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_Y0L, "y0l", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_Y1, "y1", BT_FN_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_Y1F, "y1f", BT_FN_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_Y1L, "y1l", BT_FN_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_YN, "yn", BT_FN_DOUBLE_INT_DOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_YNF, "ynf", BT_FN_FLOAT_INT_FLOAT, ATTR_MATHFN_FPROUNDING_ERRNO)
DEF_EXT_LIB_BUILTIN (BUILT_IN_YNL, "ynl", BT_FN_LONGDOUBLE_INT_LONGDOUBLE, ATTR_MATHFN_FPROUNDING_ERRNO)
/* Category: _Complex math builtins. */
DEF_C99_BUILTIN (BUILT_IN_CABS, "cabs", BT_FN_DOUBLE_COMPLEX_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CABSF, "cabsf", BT_FN_FLOAT_COMPLEX_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CABSL, "cabsl", BT_FN_LONGDOUBLE_COMPLEX_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CACOS, "cacos", BT_FN_COMPLEX_DOUBLE_COMPLEX_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CACOSF, "cacosf", BT_FN_COMPLEX_FLOAT_COMPLEX_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CACOSH, "cacosh", BT_FN_COMPLEX_DOUBLE_COMPLEX_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CACOSHF, "cacoshf", BT_FN_COMPLEX_FLOAT_COMPLEX_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CACOSHL, "cacoshl", BT_FN_COMPLEX_LONGDOUBLE_COMPLEX_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CACOSL, "cacosl", BT_FN_COMPLEX_LONGDOUBLE_COMPLEX_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CARG, "carg", BT_FN_DOUBLE_COMPLEX_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CARGF, "cargf", BT_FN_FLOAT_COMPLEX_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CARGL, "cargl", BT_FN_LONGDOUBLE_COMPLEX_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CASIN, "casin", BT_FN_COMPLEX_DOUBLE_COMPLEX_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CASINF, "casinf", BT_FN_COMPLEX_FLOAT_COMPLEX_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CASINH, "casinh", BT_FN_COMPLEX_DOUBLE_COMPLEX_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CASINHF, "casinhf", BT_FN_COMPLEX_FLOAT_COMPLEX_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CASINHL, "casinhl", BT_FN_COMPLEX_LONGDOUBLE_COMPLEX_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CASINL, "casinl", BT_FN_COMPLEX_LONGDOUBLE_COMPLEX_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CATAN, "catan", BT_FN_COMPLEX_DOUBLE_COMPLEX_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CATANF, "catanf", BT_FN_COMPLEX_FLOAT_COMPLEX_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CATANH, "catanh", BT_FN_COMPLEX_DOUBLE_COMPLEX_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CATANHF, "catanhf", BT_FN_COMPLEX_FLOAT_COMPLEX_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CATANHL, "catanhl", BT_FN_COMPLEX_LONGDOUBLE_COMPLEX_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CATANL, "catanl", BT_FN_COMPLEX_LONGDOUBLE_COMPLEX_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CCOS, "ccos", BT_FN_COMPLEX_DOUBLE_COMPLEX_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CCOSF, "ccosf", BT_FN_COMPLEX_FLOAT_COMPLEX_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CCOSH, "ccosh", BT_FN_COMPLEX_DOUBLE_COMPLEX_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CCOSHF, "ccoshf", BT_FN_COMPLEX_FLOAT_COMPLEX_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CCOSHL, "ccoshl", BT_FN_COMPLEX_LONGDOUBLE_COMPLEX_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CCOSL, "ccosl", BT_FN_COMPLEX_LONGDOUBLE_COMPLEX_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CEXP, "cexp", BT_FN_COMPLEX_DOUBLE_COMPLEX_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CEXPF, "cexpf", BT_FN_COMPLEX_FLOAT_COMPLEX_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CEXPL, "cexpl", BT_FN_COMPLEX_LONGDOUBLE_COMPLEX_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_GCC_BUILTIN (BUILT_IN_CEXPI, "cexpi", BT_FN_COMPLEX_DOUBLE_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_GCC_BUILTIN (BUILT_IN_CEXPIF, "cexpif", BT_FN_COMPLEX_FLOAT_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_GCC_BUILTIN (BUILT_IN_CEXPIL, "cexpil", BT_FN_COMPLEX_LONGDOUBLE_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CIMAG, "cimag", BT_FN_DOUBLE_COMPLEX_DOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_CIMAGF, "cimagf", BT_FN_FLOAT_COMPLEX_FLOAT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_CIMAGL, "cimagl", BT_FN_LONGDOUBLE_COMPLEX_LONGDOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_CLOG, "clog", BT_FN_COMPLEX_DOUBLE_COMPLEX_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CLOGF, "clogf", BT_FN_COMPLEX_FLOAT_COMPLEX_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CLOGL, "clogl", BT_FN_COMPLEX_LONGDOUBLE_COMPLEX_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_EXT_C99RES_BUILTIN (BUILT_IN_CLOG10, "clog10", BT_FN_COMPLEX_DOUBLE_COMPLEX_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_EXT_C99RES_BUILTIN (BUILT_IN_CLOG10F, "clog10f", BT_FN_COMPLEX_FLOAT_COMPLEX_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_EXT_C99RES_BUILTIN (BUILT_IN_CLOG10L, "clog10l", BT_FN_COMPLEX_LONGDOUBLE_COMPLEX_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CONJ, "conj", BT_FN_COMPLEX_DOUBLE_COMPLEX_DOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_CONJF, "conjf", BT_FN_COMPLEX_FLOAT_COMPLEX_FLOAT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_CONJL, "conjl", BT_FN_COMPLEX_LONGDOUBLE_COMPLEX_LONGDOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_CPOW, "cpow", BT_FN_COMPLEX_DOUBLE_COMPLEX_DOUBLE_COMPLEX_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CPOWF, "cpowf", BT_FN_COMPLEX_FLOAT_COMPLEX_FLOAT_COMPLEX_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CPOWL, "cpowl", BT_FN_COMPLEX_LONGDOUBLE_COMPLEX_LONGDOUBLE_COMPLEX_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CPROJ, "cproj", BT_FN_COMPLEX_DOUBLE_COMPLEX_DOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_CPROJF, "cprojf", BT_FN_COMPLEX_FLOAT_COMPLEX_FLOAT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_CPROJL, "cprojl", BT_FN_COMPLEX_LONGDOUBLE_COMPLEX_LONGDOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_CREAL, "creal", BT_FN_DOUBLE_COMPLEX_DOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_CREALF, "crealf", BT_FN_FLOAT_COMPLEX_FLOAT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_CREALL, "creall", BT_FN_LONGDOUBLE_COMPLEX_LONGDOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_CSIN, "csin", BT_FN_COMPLEX_DOUBLE_COMPLEX_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CSINF, "csinf", BT_FN_COMPLEX_FLOAT_COMPLEX_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CSINH, "csinh", BT_FN_COMPLEX_DOUBLE_COMPLEX_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CSINHF, "csinhf", BT_FN_COMPLEX_FLOAT_COMPLEX_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CSINHL, "csinhl", BT_FN_COMPLEX_LONGDOUBLE_COMPLEX_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CSINL, "csinl", BT_FN_COMPLEX_LONGDOUBLE_COMPLEX_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CSQRT, "csqrt", BT_FN_COMPLEX_DOUBLE_COMPLEX_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CSQRTF, "csqrtf", BT_FN_COMPLEX_FLOAT_COMPLEX_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CSQRTL, "csqrtl", BT_FN_COMPLEX_LONGDOUBLE_COMPLEX_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CTAN, "ctan", BT_FN_COMPLEX_DOUBLE_COMPLEX_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CTANF, "ctanf", BT_FN_COMPLEX_FLOAT_COMPLEX_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CTANH, "ctanh", BT_FN_COMPLEX_DOUBLE_COMPLEX_DOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CTANHF, "ctanhf", BT_FN_COMPLEX_FLOAT_COMPLEX_FLOAT, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CTANHL, "ctanhl", BT_FN_COMPLEX_LONGDOUBLE_COMPLEX_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
DEF_C99_BUILTIN (BUILT_IN_CTANL, "ctanl", BT_FN_COMPLEX_LONGDOUBLE_COMPLEX_LONGDOUBLE, ATTR_MATHFN_FPROUNDING)
/* Category: string/memory builtins. */
/* bcmp, bcopy and bzero have traditionally accepted NULL pointers
when the length parameter is zero, so don't apply attribute "nonnull". */
DEF_EXT_LIB_BUILTIN (BUILT_IN_BCMP, "bcmp", BT_FN_INT_CONST_PTR_CONST_PTR_SIZE, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_BCOPY, "bcopy", BT_FN_VOID_CONST_PTR_PTR_SIZE, ATTR_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_BZERO, "bzero", BT_FN_VOID_PTR_SIZE, ATTR_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_INDEX, "index", BT_FN_STRING_CONST_STRING_INT, ATTR_PURE_NOTHROW_NONNULL_LEAF)
DEF_LIB_BUILTIN (BUILT_IN_MEMCHR, "memchr", BT_FN_PTR_CONST_PTR_INT_SIZE, ATTR_PURE_NOTHROW_NONNULL_LEAF)
DEF_LIB_BUILTIN (BUILT_IN_MEMCMP, "memcmp", BT_FN_INT_CONST_PTR_CONST_PTR_SIZE, ATTR_PURE_NOTHROW_NONNULL_LEAF)
DEF_LIB_BUILTIN (BUILT_IN_MEMCPY, "memcpy", BT_FN_PTR_PTR_CONST_PTR_SIZE, ATTR_RET1_NOTHROW_NONNULL_LEAF)
DEF_LIB_BUILTIN (BUILT_IN_MEMMOVE, "memmove", BT_FN_PTR_PTR_CONST_PTR_SIZE, ATTR_RET1_NOTHROW_NONNULL_LEAF)
DEF_EXT_LIB_BUILTIN (BUILT_IN_MEMPCPY, "mempcpy", BT_FN_PTR_PTR_CONST_PTR_SIZE, ATTR_NOTHROW_NONNULL_LEAF)
DEF_LIB_BUILTIN (BUILT_IN_MEMSET, "memset", BT_FN_PTR_PTR_INT_SIZE, ATTR_RET1_NOTHROW_NONNULL_LEAF)
DEF_EXT_LIB_BUILTIN (BUILT_IN_RINDEX, "rindex", BT_FN_STRING_CONST_STRING_INT, ATTR_PURE_NOTHROW_NONNULL_LEAF)
DEF_EXT_LIB_BUILTIN (BUILT_IN_STPCPY, "stpcpy", BT_FN_STRING_STRING_CONST_STRING, ATTR_NOTHROW_NONNULL_LEAF)
DEF_EXT_LIB_BUILTIN (BUILT_IN_STPNCPY, "stpncpy", BT_FN_STRING_STRING_CONST_STRING_SIZE, ATTR_NOTHROW_NONNULL_LEAF)
DEF_EXT_LIB_BUILTIN (BUILT_IN_STRCASECMP, "strcasecmp", BT_FN_INT_CONST_STRING_CONST_STRING, ATTR_PURE_NOTHROW_NONNULL_LEAF)
DEF_LIB_BUILTIN (BUILT_IN_STRCAT, "strcat", BT_FN_STRING_STRING_CONST_STRING, ATTR_NOTHROW_NONNULL_LEAF)
DEF_LIB_BUILTIN (BUILT_IN_STRCHR, "strchr", BT_FN_STRING_CONST_STRING_INT, ATTR_PURE_NOTHROW_NONNULL_LEAF)
DEF_LIB_BUILTIN (BUILT_IN_STRCMP, "strcmp", BT_FN_INT_CONST_STRING_CONST_STRING, ATTR_PURE_NOTHROW_NONNULL_LEAF)
DEF_LIB_BUILTIN (BUILT_IN_STRCPY, "strcpy", BT_FN_STRING_STRING_CONST_STRING, ATTR_RET1_NOTHROW_NONNULL_LEAF)
DEF_LIB_BUILTIN (BUILT_IN_STRCSPN, "strcspn", BT_FN_SIZE_CONST_STRING_CONST_STRING, ATTR_PURE_NOTHROW_NONNULL_LEAF)
DEF_EXT_LIB_BUILTIN (BUILT_IN_STRDUP, "strdup", BT_FN_STRING_CONST_STRING, ATTR_MALLOC_NOTHROW_NONNULL_LEAF)
DEF_EXT_LIB_BUILTIN (BUILT_IN_STRNDUP, "strndup", BT_FN_STRING_CONST_STRING_SIZE, ATTR_MALLOC_NOTHROW_NONNULL_LEAF)
DEF_LIB_BUILTIN (BUILT_IN_STRLEN, "strlen", BT_FN_SIZE_CONST_STRING, ATTR_PURE_NOTHROW_NONNULL_LEAF)
DEF_EXT_LIB_BUILTIN (BUILT_IN_STRNCASECMP, "strncasecmp", BT_FN_INT_CONST_STRING_CONST_STRING_SIZE, ATTR_PURE_NOTHROW_NONNULL_LEAF)
DEF_LIB_BUILTIN (BUILT_IN_STRNCAT, "strncat", BT_FN_STRING_STRING_CONST_STRING_SIZE, ATTR_NOTHROW_NONNULL_LEAF)
DEF_LIB_BUILTIN (BUILT_IN_STRNCMP, "strncmp", BT_FN_INT_CONST_STRING_CONST_STRING_SIZE, ATTR_PURE_NOTHROW_NONNULL_LEAF)
DEF_LIB_BUILTIN (BUILT_IN_STRNCPY, "strncpy", BT_FN_STRING_STRING_CONST_STRING_SIZE, ATTR_NOTHROW_NONNULL_LEAF)
DEF_LIB_BUILTIN (BUILT_IN_STRPBRK, "strpbrk", BT_FN_STRING_CONST_STRING_CONST_STRING, ATTR_PURE_NOTHROW_NONNULL_LEAF)
DEF_LIB_BUILTIN (BUILT_IN_STRRCHR, "strrchr", BT_FN_STRING_CONST_STRING_INT, ATTR_PURE_NOTHROW_NONNULL_LEAF)
DEF_LIB_BUILTIN (BUILT_IN_STRSPN, "strspn", BT_FN_SIZE_CONST_STRING_CONST_STRING, ATTR_PURE_NOTHROW_NONNULL_LEAF)
DEF_LIB_BUILTIN (BUILT_IN_STRSTR, "strstr", BT_FN_STRING_CONST_STRING_CONST_STRING, ATTR_PURE_NOTHROW_NONNULL_LEAF)
/* Category: stdio builtins. */
DEF_LIB_BUILTIN (BUILT_IN_FPRINTF, "fprintf", BT_FN_INT_FILEPTR_CONST_STRING_VAR, ATTR_FORMAT_PRINTF_2_3)
DEF_EXT_LIB_BUILTIN (BUILT_IN_FPRINTF_UNLOCKED, "fprintf_unlocked", BT_FN_INT_FILEPTR_CONST_STRING_VAR, ATTR_FORMAT_PRINTF_2_3)
DEF_LIB_BUILTIN (BUILT_IN_PUTC, "putc", BT_FN_INT_INT_FILEPTR, ATTR_NONNULL_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_PUTC_UNLOCKED, "putc_unlocked", BT_FN_INT_INT_FILEPTR, ATTR_NONNULL_LIST)
DEF_LIB_BUILTIN (BUILT_IN_FPUTC, "fputc", BT_FN_INT_INT_FILEPTR, ATTR_NONNULL_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_FPUTC_UNLOCKED, "fputc_unlocked", BT_FN_INT_INT_FILEPTR, ATTR_NONNULL_LIST)
DEF_LIB_BUILTIN (BUILT_IN_FPUTS, "fputs", BT_FN_INT_CONST_STRING_FILEPTR, ATTR_NONNULL_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_FPUTS_UNLOCKED, "fputs_unlocked", BT_FN_INT_CONST_STRING_FILEPTR, ATTR_NONNULL_LIST)
DEF_LIB_BUILTIN (BUILT_IN_FSCANF, "fscanf", BT_FN_INT_FILEPTR_CONST_STRING_VAR, ATTR_FORMAT_SCANF_2_3)
DEF_LIB_BUILTIN (BUILT_IN_FWRITE, "fwrite", BT_FN_SIZE_CONST_PTR_SIZE_SIZE_FILEPTR, ATTR_NONNULL_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_FWRITE_UNLOCKED, "fwrite_unlocked", BT_FN_SIZE_CONST_PTR_SIZE_SIZE_FILEPTR, ATTR_NONNULL_LIST)
DEF_LIB_BUILTIN (BUILT_IN_PRINTF, "printf", BT_FN_INT_CONST_STRING_VAR, ATTR_FORMAT_PRINTF_1_2)
DEF_EXT_LIB_BUILTIN (BUILT_IN_PRINTF_UNLOCKED, "printf_unlocked", BT_FN_INT_CONST_STRING_VAR, ATTR_FORMAT_PRINTF_1_2)
DEF_LIB_BUILTIN (BUILT_IN_PUTCHAR, "putchar", BT_FN_INT_INT, ATTR_NULL)
DEF_EXT_LIB_BUILTIN (BUILT_IN_PUTCHAR_UNLOCKED, "putchar_unlocked", BT_FN_INT_INT, ATTR_NULL)
DEF_LIB_BUILTIN (BUILT_IN_PUTS, "puts", BT_FN_INT_CONST_STRING, ATTR_NONNULL_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_PUTS_UNLOCKED, "puts_unlocked", BT_FN_INT_CONST_STRING, ATTR_NONNULL_LIST)
DEF_LIB_BUILTIN (BUILT_IN_SCANF, "scanf", BT_FN_INT_CONST_STRING_VAR, ATTR_FORMAT_SCANF_1_2)
DEF_C99_BUILTIN (BUILT_IN_SNPRINTF, "snprintf", BT_FN_INT_STRING_SIZE_CONST_STRING_VAR, ATTR_FORMAT_PRINTF_NOTHROW_3_4)
DEF_LIB_BUILTIN (BUILT_IN_SPRINTF, "sprintf", BT_FN_INT_STRING_CONST_STRING_VAR, ATTR_FORMAT_PRINTF_NOTHROW_2_3)
DEF_LIB_BUILTIN (BUILT_IN_SSCANF, "sscanf", BT_FN_INT_CONST_STRING_CONST_STRING_VAR, ATTR_FORMAT_SCANF_NOTHROW_2_3)
DEF_LIB_BUILTIN (BUILT_IN_VFPRINTF, "vfprintf", BT_FN_INT_FILEPTR_CONST_STRING_VALIST_ARG, ATTR_FORMAT_PRINTF_2_0)
DEF_C99_BUILTIN (BUILT_IN_VFSCANF, "vfscanf", BT_FN_INT_FILEPTR_CONST_STRING_VALIST_ARG, ATTR_FORMAT_SCANF_2_0)
DEF_LIB_BUILTIN (BUILT_IN_VPRINTF, "vprintf", BT_FN_INT_CONST_STRING_VALIST_ARG, ATTR_FORMAT_PRINTF_1_0)
DEF_C99_BUILTIN (BUILT_IN_VSCANF, "vscanf", BT_FN_INT_CONST_STRING_VALIST_ARG, ATTR_FORMAT_SCANF_1_0)
DEF_C99_BUILTIN (BUILT_IN_VSNPRINTF, "vsnprintf", BT_FN_INT_STRING_SIZE_CONST_STRING_VALIST_ARG, ATTR_FORMAT_PRINTF_NOTHROW_3_0)
DEF_LIB_BUILTIN (BUILT_IN_VSPRINTF, "vsprintf", BT_FN_INT_STRING_CONST_STRING_VALIST_ARG, ATTR_FORMAT_PRINTF_NOTHROW_2_0)
DEF_C99_BUILTIN (BUILT_IN_VSSCANF, "vsscanf", BT_FN_INT_CONST_STRING_CONST_STRING_VALIST_ARG, ATTR_FORMAT_SCANF_NOTHROW_2_0)
/* Category: ctype builtins. */
DEF_LIB_BUILTIN (BUILT_IN_ISALNUM, "isalnum", BT_FN_INT_INT, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_LIB_BUILTIN (BUILT_IN_ISALPHA, "isalpha", BT_FN_INT_INT, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_ISASCII, "isascii", BT_FN_INT_INT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_ISBLANK, "isblank", BT_FN_INT_INT, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_LIB_BUILTIN (BUILT_IN_ISCNTRL, "iscntrl", BT_FN_INT_INT, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_LIB_BUILTIN (BUILT_IN_ISDIGIT, "isdigit", BT_FN_INT_INT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_LIB_BUILTIN (BUILT_IN_ISGRAPH, "isgraph", BT_FN_INT_INT, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_LIB_BUILTIN (BUILT_IN_ISLOWER, "islower", BT_FN_INT_INT, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_LIB_BUILTIN (BUILT_IN_ISPRINT, "isprint", BT_FN_INT_INT, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_LIB_BUILTIN (BUILT_IN_ISPUNCT, "ispunct", BT_FN_INT_INT, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_LIB_BUILTIN (BUILT_IN_ISSPACE, "isspace", BT_FN_INT_INT, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_LIB_BUILTIN (BUILT_IN_ISUPPER, "isupper", BT_FN_INT_INT, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_LIB_BUILTIN (BUILT_IN_ISXDIGIT, "isxdigit", BT_FN_INT_INT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_TOASCII, "toascii", BT_FN_INT_INT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_LIB_BUILTIN (BUILT_IN_TOLOWER, "tolower", BT_FN_INT_INT, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_LIB_BUILTIN (BUILT_IN_TOUPPER, "toupper", BT_FN_INT_INT, ATTR_PURE_NOTHROW_LEAF_LIST)
/* Category: wctype builtins. */
DEF_C94_BUILTIN (BUILT_IN_ISWALNUM, "iswalnum", BT_FN_INT_WINT, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_C94_BUILTIN (BUILT_IN_ISWALPHA, "iswalpha", BT_FN_INT_WINT, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_ISWBLANK, "iswblank", BT_FN_INT_WINT, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_C94_BUILTIN (BUILT_IN_ISWCNTRL, "iswcntrl", BT_FN_INT_WINT, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_C94_BUILTIN (BUILT_IN_ISWDIGIT, "iswdigit", BT_FN_INT_WINT, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_C94_BUILTIN (BUILT_IN_ISWGRAPH, "iswgraph", BT_FN_INT_WINT, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_C94_BUILTIN (BUILT_IN_ISWLOWER, "iswlower", BT_FN_INT_WINT, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_C94_BUILTIN (BUILT_IN_ISWPRINT, "iswprint", BT_FN_INT_WINT, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_C94_BUILTIN (BUILT_IN_ISWPUNCT, "iswpunct", BT_FN_INT_WINT, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_C94_BUILTIN (BUILT_IN_ISWSPACE, "iswspace", BT_FN_INT_WINT, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_C94_BUILTIN (BUILT_IN_ISWUPPER, "iswupper", BT_FN_INT_WINT, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_C94_BUILTIN (BUILT_IN_ISWXDIGIT, "iswxdigit", BT_FN_INT_WINT, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_C94_BUILTIN (BUILT_IN_TOWLOWER, "towlower", BT_FN_WINT_WINT, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_C94_BUILTIN (BUILT_IN_TOWUPPER, "towupper", BT_FN_WINT_WINT, ATTR_PURE_NOTHROW_LEAF_LIST)
/* Category: miscellaneous builtins. */
DEF_LIB_BUILTIN (BUILT_IN_ABORT, "abort", BT_FN_VOID, ATTR_NORETURN_NOTHROW_LEAF_LIST)
DEF_LIB_BUILTIN (BUILT_IN_ABS, "abs", BT_FN_INT_INT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_AGGREGATE_INCOMING_ADDRESS, "aggregate_incoming_address", BT_FN_PTR_VAR, ATTR_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_ALLOCA, "alloca", BT_FN_PTR_SIZE, ATTR_MALLOC_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_APPLY, "apply", BT_FN_PTR_PTR_FN_VOID_VAR_PTR_SIZE, ATTR_NULL)
DEF_GCC_BUILTIN (BUILT_IN_APPLY_ARGS, "apply_args", BT_FN_PTR_VAR, ATTR_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_BSWAP16, "bswap16", BT_FN_UINT16_UINT16, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_BSWAP32, "bswap32", BT_FN_UINT32_UINT32, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_BSWAP64, "bswap64", BT_FN_UINT64_UINT64, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_CLEAR_CACHE, "__clear_cache", BT_FN_VOID_PTR_PTR, ATTR_NOTHROW_LEAF_LIST)
/* [trans-mem]: Adjust BUILT_IN_TM_CALLOC if BUILT_IN_CALLOC is changed. */
DEF_LIB_BUILTIN (BUILT_IN_CALLOC, "calloc", BT_FN_PTR_SIZE_SIZE, ATTR_MALLOC_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_CLASSIFY_TYPE, "classify_type", BT_FN_INT_VAR, ATTR_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_CLZ, "clz", BT_FN_INT_UINT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_CLZIMAX, "clzimax", BT_FN_INT_UINTMAX, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_CLZL, "clzl", BT_FN_INT_ULONG, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_CLZLL, "clzll", BT_FN_INT_ULONGLONG, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_CONSTANT_P, "constant_p", BT_FN_INT_VAR, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_CTZ, "ctz", BT_FN_INT_UINT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_CTZIMAX, "ctzimax", BT_FN_INT_UINTMAX, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_CTZL, "ctzl", BT_FN_INT_ULONG, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_CTZLL, "ctzll", BT_FN_INT_ULONGLONG, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_CLRSB, "clrsb", BT_FN_INT_INT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_CLRSBIMAX, "clrsbimax", BT_FN_INT_INTMAX, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_CLRSBL, "clrsbl", BT_FN_INT_LONG, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_CLRSBLL, "clrsbll", BT_FN_INT_LONGLONG, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_DCGETTEXT, "dcgettext", BT_FN_STRING_CONST_STRING_CONST_STRING_INT, ATTR_FORMAT_ARG_2)
DEF_EXT_LIB_BUILTIN (BUILT_IN_DGETTEXT, "dgettext", BT_FN_STRING_CONST_STRING_CONST_STRING, ATTR_FORMAT_ARG_2)
DEF_GCC_BUILTIN (BUILT_IN_DWARF_CFA, "dwarf_cfa", BT_FN_PTR, ATTR_NULL)
DEF_GCC_BUILTIN (BUILT_IN_DWARF_SP_COLUMN, "dwarf_sp_column", BT_FN_UINT, ATTR_NULL)
DEF_GCC_BUILTIN (BUILT_IN_EH_RETURN, "eh_return", BT_FN_VOID_PTRMODE_PTR, ATTR_NORETURN_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_EH_RETURN_DATA_REGNO, "eh_return_data_regno", BT_FN_INT_INT, ATTR_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_EXECL, "execl", BT_FN_INT_CONST_STRING_CONST_STRING_VAR, ATTR_SENTINEL_NOTHROW_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_EXECLP, "execlp", BT_FN_INT_CONST_STRING_CONST_STRING_VAR, ATTR_SENTINEL_NOTHROW_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_EXECLE, "execle", BT_FN_INT_CONST_STRING_CONST_STRING_VAR, ATTR_NOTHROW_SENTINEL_1)
DEF_EXT_LIB_BUILTIN (BUILT_IN_EXECV, "execv", BT_FN_INT_CONST_STRING_PTR_CONST_STRING, ATTR_NOTHROW_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_EXECVP, "execvp", BT_FN_INT_CONST_STRING_PTR_CONST_STRING, ATTR_NOTHROW_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_EXECVE, "execve", BT_FN_INT_CONST_STRING_PTR_CONST_STRING_PTR_CONST_STRING, ATTR_NOTHROW_LIST)
DEF_LIB_BUILTIN (BUILT_IN_EXIT, "exit", BT_FN_VOID_INT, ATTR_NORETURN_NOTHROW_LIST)
DEF_GCC_BUILTIN (BUILT_IN_EXPECT, "expect", BT_FN_LONG_LONG_LONG, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_ASSUME_ALIGNED, "assume_aligned", BT_FN_PTR_CONST_PTR_SIZE_VAR, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_EXTEND_POINTER, "extend_pointer", BT_FN_UNWINDWORD_PTR, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_EXTRACT_RETURN_ADDR, "extract_return_addr", BT_FN_PTR_PTR, ATTR_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_FFS, "ffs", BT_FN_INT_INT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_FFSIMAX, "ffsimax", BT_FN_INT_INTMAX, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_FFSL, "ffsl", BT_FN_INT_LONG, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_FFSLL, "ffsll", BT_FN_INT_LONGLONG, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_FORK, "fork", BT_FN_PID, ATTR_NOTHROW_LIST)
DEF_GCC_BUILTIN (BUILT_IN_FRAME_ADDRESS, "frame_address", BT_FN_PTR_UINT, ATTR_NULL)
/* [trans-mem]: Adjust BUILT_IN_TM_FREE if BUILT_IN_FREE is changed. */
DEF_LIB_BUILTIN (BUILT_IN_FREE, "free", BT_FN_VOID_PTR, ATTR_NOTHROW_LIST)
DEF_GCC_BUILTIN (BUILT_IN_FROB_RETURN_ADDR, "frob_return_addr", BT_FN_PTR_PTR, ATTR_NULL)
DEF_EXT_LIB_BUILTIN (BUILT_IN_GETTEXT, "gettext", BT_FN_STRING_CONST_STRING, ATTR_FORMAT_ARG_1)
DEF_C99_BUILTIN (BUILT_IN_IMAXABS, "imaxabs", BT_FN_INTMAX_INTMAX, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_INIT_DWARF_REG_SIZES, "init_dwarf_reg_size_table", BT_FN_VOID_PTR, ATTR_NULL)
DEF_EXT_LIB_BUILTIN (BUILT_IN_FINITE, "finite", BT_FN_INT_DOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_FINITEF, "finitef", BT_FN_INT_FLOAT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_FINITEL, "finitel", BT_FN_INT_LONGDOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_FINITED32, "finited32", BT_FN_INT_DFLOAT32, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_FINITED64, "finited64", BT_FN_INT_DFLOAT64, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_FINITED128, "finited128", BT_FN_INT_DFLOAT128, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_FPCLASSIFY, "fpclassify", BT_FN_INT_INT_INT_INT_INT_INT_VAR, ATTR_CONST_NOTHROW_TYPEGENERIC_LEAF)
DEF_GCC_BUILTIN (BUILT_IN_ISFINITE, "isfinite", BT_FN_INT_VAR, ATTR_CONST_NOTHROW_TYPEGENERIC_LEAF)
DEF_GCC_BUILTIN (BUILT_IN_ISINF_SIGN, "isinf_sign", BT_FN_INT_VAR, ATTR_CONST_NOTHROW_TYPEGENERIC_LEAF)
DEF_C99_C90RES_BUILTIN (BUILT_IN_ISINF, "isinf", BT_FN_INT_VAR, ATTR_CONST_NOTHROW_TYPEGENERIC)
DEF_EXT_LIB_BUILTIN (BUILT_IN_ISINFF, "isinff", BT_FN_INT_FLOAT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_ISINFL, "isinfl", BT_FN_INT_LONGDOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_ISINFD32, "isinfd32", BT_FN_INT_DFLOAT32, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_ISINFD64, "isinfd64", BT_FN_INT_DFLOAT64, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_ISINFD128, "isinfd128", BT_FN_INT_DFLOAT128, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_C90RES_BUILTIN (BUILT_IN_ISNAN, "isnan", BT_FN_INT_VAR, ATTR_CONST_NOTHROW_TYPEGENERIC_LEAF)
DEF_EXT_LIB_BUILTIN (BUILT_IN_ISNANF, "isnanf", BT_FN_INT_FLOAT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_ISNANL, "isnanl", BT_FN_INT_LONGDOUBLE, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_ISNAND32, "isnand32", BT_FN_INT_DFLOAT32, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_ISNAND64, "isnand64", BT_FN_INT_DFLOAT64, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_ISNAND128, "isnand128", BT_FN_INT_DFLOAT128, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_ISNORMAL, "isnormal", BT_FN_INT_VAR, ATTR_CONST_NOTHROW_TYPEGENERIC_LEAF)
DEF_GCC_BUILTIN (BUILT_IN_ISGREATER, "isgreater", BT_FN_INT_VAR, ATTR_CONST_NOTHROW_TYPEGENERIC_LEAF)
DEF_GCC_BUILTIN (BUILT_IN_ISGREATEREQUAL, "isgreaterequal", BT_FN_INT_VAR, ATTR_CONST_NOTHROW_TYPEGENERIC_LEAF)
DEF_GCC_BUILTIN (BUILT_IN_ISLESS, "isless", BT_FN_INT_VAR, ATTR_CONST_NOTHROW_TYPEGENERIC_LEAF)
DEF_GCC_BUILTIN (BUILT_IN_ISLESSEQUAL, "islessequal", BT_FN_INT_VAR, ATTR_CONST_NOTHROW_TYPEGENERIC_LEAF)
DEF_GCC_BUILTIN (BUILT_IN_ISLESSGREATER, "islessgreater", BT_FN_INT_VAR, ATTR_CONST_NOTHROW_TYPEGENERIC_LEAF)
DEF_GCC_BUILTIN (BUILT_IN_ISUNORDERED, "isunordered", BT_FN_INT_VAR, ATTR_CONST_NOTHROW_TYPEGENERIC_LEAF)
DEF_LIB_BUILTIN (BUILT_IN_LABS, "labs", BT_FN_LONG_LONG, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN_LLABS, "llabs", BT_FN_LONGLONG_LONGLONG, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_LONGJMP, "longjmp", BT_FN_VOID_PTR_INT, ATTR_NORETURN_NOTHROW_LEAF_LIST)
/* [trans-mem]: Adjust BUILT_IN_TM_MALLOC if BUILT_IN_MALLOC is changed. */
DEF_LIB_BUILTIN (BUILT_IN_MALLOC, "malloc", BT_FN_PTR_SIZE, ATTR_MALLOC_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_NEXT_ARG, "next_arg", BT_FN_PTR_VAR, ATTR_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_PARITY, "parity", BT_FN_INT_UINT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_PARITYIMAX, "parityimax", BT_FN_INT_UINTMAX, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_PARITYL, "parityl", BT_FN_INT_ULONG, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_PARITYLL, "parityll", BT_FN_INT_ULONGLONG, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_POPCOUNT, "popcount", BT_FN_INT_UINT, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_POPCOUNTIMAX, "popcountimax", BT_FN_INT_UINTMAX, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_POPCOUNTL, "popcountl", BT_FN_INT_ULONG, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_POPCOUNTLL, "popcountll", BT_FN_INT_ULONGLONG, ATTR_CONST_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_PREFETCH, "prefetch", BT_FN_VOID_CONST_PTR_VAR, ATTR_NOVOPS_LEAF_LIST)
DEF_LIB_BUILTIN (BUILT_IN_REALLOC, "realloc", BT_FN_PTR_PTR_SIZE, ATTR_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_RETURN, "return", BT_FN_VOID_PTR, ATTR_NORETURN_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_RETURN_ADDRESS, "return_address", BT_FN_PTR_UINT, ATTR_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_SAVEREGS, "saveregs", BT_FN_PTR_VAR, ATTR_NULL)
DEF_GCC_BUILTIN (BUILT_IN_SETJMP, "setjmp", BT_FN_INT_PTR, ATTR_NULL)
DEF_EXT_LIB_BUILTIN (BUILT_IN_STRFMON, "strfmon", BT_FN_SSIZE_STRING_SIZE_CONST_STRING_VAR, ATTR_FORMAT_STRFMON_NOTHROW_3_4)
DEF_LIB_BUILTIN (BUILT_IN_STRFTIME, "strftime", BT_FN_SIZE_STRING_SIZE_CONST_STRING_CONST_PTR, ATTR_FORMAT_STRFTIME_NOTHROW_3_0)
DEF_GCC_BUILTIN (BUILT_IN_TRAP, "trap", BT_FN_VOID, ATTR_NORETURN_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_UNREACHABLE, "unreachable", BT_FN_VOID, ATTR_CONST_NORETURN_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_UNWIND_INIT, "unwind_init", BT_FN_VOID, ATTR_NULL)
DEF_GCC_BUILTIN (BUILT_IN_UPDATE_SETJMP_BUF, "update_setjmp_buf", BT_FN_VOID_PTR_INT, ATTR_NULL)
DEF_GCC_BUILTIN (BUILT_IN_VA_COPY, "va_copy", BT_FN_VOID_VALIST_REF_VALIST_ARG, ATTR_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_VA_END, "va_end", BT_FN_VOID_VALIST_REF, ATTR_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_VA_START, "va_start", BT_FN_VOID_VALIST_REF_VAR, ATTR_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_VA_ARG_PACK, "va_arg_pack", BT_FN_INT, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_VA_ARG_PACK_LEN, "va_arg_pack_len", BT_FN_INT, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN__EXIT, "_exit", BT_FN_VOID_INT, ATTR_NORETURN_NOTHROW_LEAF_LIST)
DEF_C99_BUILTIN (BUILT_IN__EXIT2, "_Exit", BT_FN_VOID_INT, ATTR_NORETURN_NOTHROW_LEAF_LIST)
/* Implementing nested functions. */
DEF_BUILTIN_STUB (BUILT_IN_INIT_TRAMPOLINE, "__builtin_init_trampoline")
DEF_BUILTIN_STUB (BUILT_IN_INIT_HEAP_TRAMPOLINE, "__builtin_init_heap_trampoline")
DEF_BUILTIN_STUB (BUILT_IN_ADJUST_TRAMPOLINE, "__builtin_adjust_trampoline")
DEF_BUILTIN_STUB (BUILT_IN_NONLOCAL_GOTO, "__builtin_nonlocal_goto")
/* Implementing __builtin_setjmp. */
DEF_BUILTIN_STUB (BUILT_IN_SETJMP_SETUP, "__builtin_setjmp_setup")
DEF_BUILTIN_STUB (BUILT_IN_SETJMP_DISPATCHER, "__builtin_setjmp_dispatcher")
DEF_BUILTIN_STUB (BUILT_IN_SETJMP_RECEIVER, "__builtin_setjmp_receiver")
/* Implementing variable sized local variables. */
DEF_BUILTIN_STUB (BUILT_IN_STACK_SAVE, "__builtin_stack_save")
DEF_BUILTIN_STUB (BUILT_IN_STACK_RESTORE, "__builtin_stack_restore")
DEF_BUILTIN_STUB (BUILT_IN_ALLOCA_WITH_ALIGN, "__builtin_alloca_with_align")
/* Object size checking builtins. */
DEF_GCC_BUILTIN (BUILT_IN_OBJECT_SIZE, "object_size", BT_FN_SIZE_CONST_PTR_INT, ATTR_PURE_NOTHROW_LEAF_LIST)
DEF_EXT_LIB_BUILTIN (BUILT_IN_MEMCPY_CHK, "__memcpy_chk", BT_FN_PTR_PTR_CONST_PTR_SIZE_SIZE, ATTR_RET1_NOTHROW_NONNULL_LEAF)
DEF_EXT_LIB_BUILTIN (BUILT_IN_MEMMOVE_CHK, "__memmove_chk", BT_FN_PTR_PTR_CONST_PTR_SIZE_SIZE, ATTR_RET1_NOTHROW_NONNULL_LEAF)
DEF_EXT_LIB_BUILTIN (BUILT_IN_MEMPCPY_CHK, "__mempcpy_chk", BT_FN_PTR_PTR_CONST_PTR_SIZE_SIZE, ATTR_NOTHROW_NONNULL_LEAF)
DEF_EXT_LIB_BUILTIN (BUILT_IN_MEMSET_CHK, "__memset_chk", BT_FN_PTR_PTR_INT_SIZE_SIZE, ATTR_NOTHROW_NONNULL_LEAF)
DEF_EXT_LIB_BUILTIN (BUILT_IN_STPCPY_CHK, "__stpcpy_chk", BT_FN_STRING_STRING_CONST_STRING_SIZE, ATTR_NOTHROW_NONNULL_LEAF)
DEF_EXT_LIB_BUILTIN (BUILT_IN_STPNCPY_CHK, "__stpncpy_chk", BT_FN_STRING_STRING_CONST_STRING_SIZE_SIZE, ATTR_NOTHROW_NONNULL_LEAF)
DEF_EXT_LIB_BUILTIN (BUILT_IN_STRCAT_CHK, "__strcat_chk", BT_FN_STRING_STRING_CONST_STRING_SIZE, ATTR_NOTHROW_NONNULL_LEAF)
DEF_EXT_LIB_BUILTIN (BUILT_IN_STRCPY_CHK, "__strcpy_chk", BT_FN_STRING_STRING_CONST_STRING_SIZE, ATTR_NOTHROW_NONNULL_LEAF)
DEF_EXT_LIB_BUILTIN (BUILT_IN_STRNCAT_CHK, "__strncat_chk", BT_FN_STRING_STRING_CONST_STRING_SIZE_SIZE, ATTR_NOTHROW_NONNULL_LEAF)
DEF_EXT_LIB_BUILTIN (BUILT_IN_STRNCPY_CHK, "__strncpy_chk", BT_FN_STRING_STRING_CONST_STRING_SIZE_SIZE, ATTR_NOTHROW_NONNULL_LEAF)
DEF_EXT_LIB_BUILTIN (BUILT_IN_SNPRINTF_CHK, "__snprintf_chk", BT_FN_INT_STRING_SIZE_INT_SIZE_CONST_STRING_VAR, ATTR_FORMAT_PRINTF_NOTHROW_5_6)
DEF_EXT_LIB_BUILTIN (BUILT_IN_SPRINTF_CHK, "__sprintf_chk", BT_FN_INT_STRING_INT_SIZE_CONST_STRING_VAR, ATTR_FORMAT_PRINTF_NOTHROW_4_5)
DEF_EXT_LIB_BUILTIN (BUILT_IN_VSNPRINTF_CHK, "__vsnprintf_chk", BT_FN_INT_STRING_SIZE_INT_SIZE_CONST_STRING_VALIST_ARG, ATTR_FORMAT_PRINTF_NOTHROW_5_0)
DEF_EXT_LIB_BUILTIN (BUILT_IN_VSPRINTF_CHK, "__vsprintf_chk", BT_FN_INT_STRING_INT_SIZE_CONST_STRING_VALIST_ARG, ATTR_FORMAT_PRINTF_NOTHROW_4_0)
DEF_EXT_LIB_BUILTIN (BUILT_IN_FPRINTF_CHK, "__fprintf_chk", BT_FN_INT_FILEPTR_INT_CONST_STRING_VAR, ATTR_FORMAT_PRINTF_3_4)
DEF_EXT_LIB_BUILTIN (BUILT_IN_PRINTF_CHK, "__printf_chk", BT_FN_INT_INT_CONST_STRING_VAR, ATTR_FORMAT_PRINTF_2_3)
DEF_EXT_LIB_BUILTIN (BUILT_IN_VFPRINTF_CHK, "__vfprintf_chk", BT_FN_INT_FILEPTR_INT_CONST_STRING_VALIST_ARG, ATTR_FORMAT_PRINTF_3_0)
DEF_EXT_LIB_BUILTIN (BUILT_IN_VPRINTF_CHK, "__vprintf_chk", BT_FN_INT_INT_CONST_STRING_VALIST_ARG, ATTR_FORMAT_PRINTF_2_0)
/* Profiling hooks. */
DEF_BUILTIN (BUILT_IN_PROFILE_FUNC_ENTER, "__cyg_profile_func_enter", BUILT_IN_NORMAL, BT_FN_VOID_PTR_PTR, BT_LAST,
false, false, false, ATTR_NULL, true, true)
DEF_BUILTIN (BUILT_IN_PROFILE_FUNC_EXIT, "__cyg_profile_func_exit", BUILT_IN_NORMAL, BT_FN_VOID_PTR_PTR, BT_LAST,
false, false, false, ATTR_NULL, true, true)
/* TLS thread pointer related builtins. */
DEF_BUILTIN (BUILT_IN_THREAD_POINTER, "__builtin_thread_pointer",
BUILT_IN_NORMAL, BT_FN_PTR, BT_LAST,
false, false, true, ATTR_CONST_NOTHROW_LIST, true,
targetm.have_tls)
DEF_BUILTIN (BUILT_IN_SET_THREAD_POINTER, "__builtin_set_thread_pointer",
BUILT_IN_NORMAL, BT_FN_VOID_PTR, BT_LAST,
false, false, true, ATTR_NOTHROW_LIST, true,
targetm.have_tls)
/* TLS emulation. */
DEF_BUILTIN (BUILT_IN_EMUTLS_GET_ADDRESS, targetm.emutls.get_address,
BUILT_IN_NORMAL,
BT_FN_PTR_PTR, BT_FN_PTR_PTR,
true, true, true, ATTR_CONST_NOTHROW_NONNULL_LEAF, false,
!targetm.have_tls)
DEF_BUILTIN (BUILT_IN_EMUTLS_REGISTER_COMMON,
targetm.emutls.register_common, BUILT_IN_NORMAL,
BT_FN_VOID_PTR_WORD_WORD_PTR, BT_FN_VOID_PTR_WORD_WORD_PTR,
true, true, true, ATTR_NOTHROW_LEAF_LIST, false,
!targetm.have_tls)
/* Exception support. */
DEF_BUILTIN_STUB (BUILT_IN_UNWIND_RESUME, "__builtin_unwind_resume")
DEF_BUILTIN_STUB (BUILT_IN_CXA_END_CLEANUP, "__builtin_cxa_end_cleanup")
DEF_BUILTIN_STUB (BUILT_IN_EH_POINTER, "__builtin_eh_pointer")
DEF_BUILTIN_STUB (BUILT_IN_EH_FILTER, "__builtin_eh_filter")
DEF_BUILTIN_STUB (BUILT_IN_EH_COPY_VALUES, "__builtin_eh_copy_values")
/* __FILE__, __LINE__, __FUNCTION__ as builtins. */
DEF_GCC_BUILTIN (BUILT_IN_FILE, "FILE", BT_FN_CONST_STRING, ATTR_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_FUNCTION, "FUNCTION", BT_FN_CONST_STRING, ATTR_NOTHROW_LEAF_LIST)
DEF_GCC_BUILTIN (BUILT_IN_LINE, "LINE", BT_FN_INT, ATTR_NOTHROW_LEAF_LIST)
/* Synchronization Primitives. */
#include "sync-builtins.def"
/* OpenMP builtins. */
#include "omp-builtins.def"
/* GTM builtins. */
#include "gtm-builtins.def"
/* Sanitizer builtins. */
#include "sanitizer.def"

4
src/include/bversion.h Normal file
View File

@ -0,0 +1,4 @@
#define BUILDING_GCC_MAJOR 4
#define BUILDING_GCC_MINOR 8
#define BUILDING_GCC_PATCHLEVEL 5
#define BUILDING_GCC_VERSION (BUILDING_GCC_MAJOR * 1000 + BUILDING_GCC_MINOR)

View File

@ -0,0 +1,62 @@
/* This file contains the definitions and documentation for the
additional tree codes used in the GNU C compiler (see tree.def
for the standard codes).
Copyright (C) 1987-2013 Free Software Foundation, Inc.
Written by Benjamin Chelf <chelf@codesourcery.com>
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
/* Tree nodes used in the C frontend. These are also shared with the
C++ and Objective C frontends. */
/* A C_MAYBE_CONST_EXPR, currently only used for C and Objective C,
tracks information about constancy of an expression and VLA type
sizes or VM expressions from typeof that need to be evaluated
before the main expression. It is used during parsing and removed
in c_fully_fold. C_MAYBE_CONST_EXPR_PRE is the expression to
evaluate first, if not NULL; C_MAYBE_CONST_EXPR_EXPR is the main
expression. If C_MAYBE_CONST_EXPR_INT_OPERANDS is set then the
expression may be used in an unevaluated part of an integer
constant expression, but not in an evaluated part. If
C_MAYBE_CONST_EXPR_NON_CONST is set then the expression contains
something that cannot occur in an evaluated part of a constant
expression (or outside of sizeof in C90 mode); otherwise it does
not. */
DEFTREECODE (C_MAYBE_CONST_EXPR, "c_maybe_const_expr", tcc_expression, 2)
/* An EXCESS_PRECISION_EXPR, currently only used for C and Objective
C, represents an expression evaluated in greater range or precision
than its type. The type of the EXCESS_PRECISION_EXPR is the
semantic type while the operand represents what is actually being
evaluated. */
DEFTREECODE (EXCESS_PRECISION_EXPR, "excess_precision_expr", tcc_expression, 1)
/* Used to represent a user-defined literal.
The operands are an IDENTIFIER for the suffix, the VALUE of the literal,
and for numeric literals the original string representation of the
number. */
DEFTREECODE (USERDEF_LITERAL, "userdef_literal", tcc_exceptional, 3)
/* Represents a 'sizeof' expression during C++ template expansion,
or for the purpose of -Wsizeof-pointer-memaccess warning. */
DEFTREECODE (SIZEOF_EXPR, "sizeof_expr", tcc_expression, 1)
/*
Local variables:
mode:c
End:
*/

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,114 @@
/* Definitions of Objective-C front-end entry points used for C and C++.
Copyright (C) 1987-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GCC_C_COMMON_OBJC_H
#define GCC_C_COMMON_OBJC_H
/* ObjC ivar visibility types. */
typedef enum objc_ivar_visibility_kind {
OBJC_IVAR_VIS_PROTECTED = 0,
OBJC_IVAR_VIS_PUBLIC = 1,
OBJC_IVAR_VIS_PRIVATE = 2,
OBJC_IVAR_VIS_PACKAGE = 3
} objc_ivar_visibility_kind;
/* Objective-C / Objective-C++ entry points. */
/* The following ObjC/ObjC++ functions are called by the C and/or C++
front-ends; they all must have corresponding stubs in stub-objc.c. */
extern void objc_write_global_declarations (void);
extern tree objc_is_class_name (tree);
extern tree objc_is_object_ptr (tree);
extern void objc_check_decl (tree);
extern void objc_check_global_decl (tree);
extern tree objc_common_type (tree, tree);
extern bool objc_compare_types (tree, tree, int, tree);
extern bool objc_have_common_type (tree, tree, int, tree);
extern bool objc_diagnose_private_ivar (tree);
extern void objc_volatilize_decl (tree);
extern tree objc_rewrite_function_call (tree, tree);
extern tree objc_message_selector (void);
extern tree objc_lookup_ivar (tree, tree);
extern void objc_clear_super_receiver (void);
extern int objc_is_public (tree, tree);
extern tree objc_is_id (tree);
extern void objc_declare_alias (tree, tree);
extern void objc_declare_class (tree);
extern void objc_declare_protocol (tree, tree);
extern tree objc_build_message_expr (tree, tree);
extern tree objc_finish_message_expr (tree, tree, tree, tree*);
extern tree objc_build_selector_expr (location_t, tree);
extern tree objc_build_protocol_expr (tree);
extern tree objc_build_encode_expr (tree);
extern tree objc_build_string_object (tree);
extern tree objc_get_protocol_qualified_type (tree, tree);
extern tree objc_get_class_reference (tree);
extern tree objc_get_class_ivars (tree);
extern bool objc_detect_field_duplicates (bool);
extern void objc_start_class_interface (tree, tree, tree, tree);
extern void objc_start_category_interface (tree, tree, tree, tree);
extern void objc_start_protocol (tree, tree, tree);
extern void objc_continue_interface (void);
extern void objc_finish_interface (void);
extern void objc_start_class_implementation (tree, tree);
extern void objc_start_category_implementation (tree, tree);
extern void objc_continue_implementation (void);
extern void objc_finish_implementation (void);
extern void objc_set_visibility (objc_ivar_visibility_kind);
extern tree objc_build_method_signature (bool, tree, tree, tree, bool);
extern void objc_add_method_declaration (bool, tree, tree);
extern bool objc_start_method_definition (bool, tree, tree, tree);
extern void objc_finish_method_definition (tree);
extern void objc_add_instance_variable (tree);
extern tree objc_build_keyword_decl (tree, tree, tree, tree);
extern tree objc_build_throw_stmt (location_t, tree);
extern void objc_begin_try_stmt (location_t, tree);
extern tree objc_finish_try_stmt (void);
extern void objc_begin_catch_clause (tree);
extern void objc_finish_catch_clause (void);
extern void objc_build_finally_clause (location_t, tree);
extern tree objc_build_synchronized (location_t, tree, tree);
extern int objc_static_init_needed_p (void);
extern tree objc_generate_static_init_call (tree);
extern tree objc_generate_write_barrier (tree, enum tree_code, tree);
extern void objc_set_method_opt (bool);
extern void objc_finish_foreach_loop (location_t, tree, tree, tree, tree, tree);
extern bool objc_method_decl (enum tree_code);
extern void objc_add_property_declaration (location_t, tree, bool, bool, bool,
bool, bool, bool, tree, tree);
extern tree objc_maybe_build_component_ref (tree, tree);
extern tree objc_build_class_component_ref (tree, tree);
extern tree objc_maybe_build_modify_expr (tree, tree);
extern tree objc_build_incr_expr_for_property_ref (location_t, enum tree_code,
tree, tree);
extern void objc_add_synthesize_declaration (location_t, tree);
extern void objc_add_dynamic_declaration (location_t, tree);
extern const char * objc_maybe_printable_name (tree, int);
extern bool objc_is_property_ref (tree);
extern bool objc_string_ref_type_p (tree);
extern void objc_check_format_arg (tree, tree);
extern void objc_finish_function (void);
extern void objc_maybe_warn_exceptions (location_t);
/* The following are provided by the C and C++ front-ends, and called by
ObjC/ObjC++. */
extern void *objc_get_current_scope (void);
extern void objc_mark_locals_volatile (void *);
#endif /* ! GCC_C_COMMON_OBJC_H */

View File

@ -0,0 +1,150 @@
/* Pragma related interfaces.
Copyright (C) 1995-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GCC_C_PRAGMA_H
#define GCC_C_PRAGMA_H
#include "cpplib.h" /* For enum cpp_ttype. */
/* Pragma identifiers built in to the front end parsers. Identifiers
for ancillary handlers will follow these. */
typedef enum pragma_kind {
PRAGMA_NONE = 0,
PRAGMA_OMP_ATOMIC,
PRAGMA_OMP_BARRIER,
PRAGMA_OMP_CRITICAL,
PRAGMA_OMP_FLUSH,
PRAGMA_OMP_FOR,
PRAGMA_OMP_MASTER,
PRAGMA_OMP_ORDERED,
PRAGMA_OMP_PARALLEL,
PRAGMA_OMP_PARALLEL_FOR,
PRAGMA_OMP_PARALLEL_SECTIONS,
PRAGMA_OMP_SECTION,
PRAGMA_OMP_SECTIONS,
PRAGMA_OMP_SINGLE,
PRAGMA_OMP_TASK,
PRAGMA_OMP_TASKWAIT,
PRAGMA_OMP_TASKYIELD,
PRAGMA_OMP_THREADPRIVATE,
PRAGMA_GCC_PCH_PREPROCESS,
PRAGMA_FIRST_EXTERNAL
} pragma_kind;
/* All clauses defined by OpenMP 2.5 and 3.0.
Used internally by both C and C++ parsers. */
typedef enum pragma_omp_clause {
PRAGMA_OMP_CLAUSE_NONE = 0,
PRAGMA_OMP_CLAUSE_COLLAPSE,
PRAGMA_OMP_CLAUSE_COPYIN,
PRAGMA_OMP_CLAUSE_COPYPRIVATE,
PRAGMA_OMP_CLAUSE_DEFAULT,
PRAGMA_OMP_CLAUSE_FIRSTPRIVATE,
PRAGMA_OMP_CLAUSE_IF,
PRAGMA_OMP_CLAUSE_LASTPRIVATE,
PRAGMA_OMP_CLAUSE_NOWAIT,
PRAGMA_OMP_CLAUSE_NUM_THREADS,
PRAGMA_OMP_CLAUSE_ORDERED,
PRAGMA_OMP_CLAUSE_PRIVATE,
PRAGMA_OMP_CLAUSE_REDUCTION,
PRAGMA_OMP_CLAUSE_SCHEDULE,
PRAGMA_OMP_CLAUSE_SHARED,
PRAGMA_OMP_CLAUSE_UNTIED,
PRAGMA_OMP_CLAUSE_FINAL,
PRAGMA_OMP_CLAUSE_MERGEABLE
} pragma_omp_clause;
extern struct cpp_reader* parse_in;
/* It's safe to always leave visibility pragma enabled as if
visibility is not supported on the host OS platform the
statements are ignored. */
extern void push_visibility (const char *, int);
extern bool pop_visibility (int);
extern void init_pragma (void);
/* Front-end wrappers for pragma registration. */
typedef void (*pragma_handler_1arg)(struct cpp_reader *);
/* A second pragma handler, which adds a void * argument allowing to pass extra
data to the handler. */
typedef void (*pragma_handler_2arg)(struct cpp_reader *, void *);
/* This union allows to abstract the different handlers. */
union gen_pragma_handler {
pragma_handler_1arg handler_1arg;
pragma_handler_2arg handler_2arg;
};
/* Internally used to keep the data of the handler. */
struct internal_pragma_handler_d {
union gen_pragma_handler handler;
/* Permits to know if handler is a pragma_handler_1arg (extra_data is false)
or a pragma_handler_2arg (extra_data is true). */
bool extra_data;
/* A data field which can be used when extra_data is true. */
void * data;
};
typedef struct internal_pragma_handler_d internal_pragma_handler;
extern void c_register_pragma (const char *space, const char *name,
pragma_handler_1arg handler);
extern void c_register_pragma_with_data (const char *space, const char *name,
pragma_handler_2arg handler,
void *data);
extern void c_register_pragma_with_expansion (const char *space,
const char *name,
pragma_handler_1arg handler);
extern void c_register_pragma_with_expansion_and_data (const char *space,
const char *name,
pragma_handler_2arg handler,
void *data);
extern void c_invoke_pragma_handler (unsigned int);
extern void maybe_apply_pragma_weak (tree);
extern void maybe_apply_pending_pragma_weaks (void);
extern tree maybe_apply_renaming_pragma (tree, tree);
extern void add_to_renaming_pragma_list (tree, tree);
extern enum cpp_ttype pragma_lex (tree *);
/* Flags for use with c_lex_with_flags. The values here were picked
so that 0 means to translate and join strings. */
#define C_LEX_STRING_NO_TRANSLATE 1 /* Do not lex strings into
execution character set. */
#define C_LEX_STRING_NO_JOIN 2 /* Do not concatenate strings
nor translate them into execution
character set. */
/* This is not actually available to pragma parsers. It's merely a
convenient location to declare this function for c-lex, after
having enum cpp_ttype declared. */
extern enum cpp_ttype c_lex_with_flags (tree *, location_t *, unsigned char *,
int);
extern void c_pp_lookup_pragma (unsigned int, const char **, const char **);
extern GTY(()) tree pragma_extern_prefix;
#endif /* GCC_C_PRAGMA_H */

View File

@ -0,0 +1,215 @@
/* Various declarations for the C and C++ pretty-printers.
Copyright (C) 2002-2013 Free Software Foundation, Inc.
Contributed by Gabriel Dos Reis <gdr@integrable-solutions.net>
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GCC_C_PRETTY_PRINTER
#define GCC_C_PRETTY_PRINTER
#include "tree.h"
#include "c-family/c-common.h"
#include "pretty-print.h"
typedef enum
{
pp_c_flag_abstract = 1 << 1,
pp_c_flag_gnu_v3 = 1 << 2,
pp_c_flag_last_bit = 3
} pp_c_pretty_print_flags;
/* The data type used to bundle information necessary for pretty-printing
a C or C++ entity. */
typedef struct c_pretty_print_info c_pretty_printer;
/* The type of a C pretty-printer 'member' function. */
typedef void (*c_pretty_print_fn) (c_pretty_printer *, tree);
/* The datatype that contains information necessary for pretty-printing
a tree that represents a C construct. Any pretty-printer for a
language using C/c++ syntax can derive from this datatype and reuse
facilities provided here. It can do so by having a subobject of type
c_pretty_printer and override the macro pp_c_base to return a pointer
to that subobject. Such a pretty-printer has the responsibility to
initialize the pp_base() part, then call pp_c_pretty_printer_init
to set up the components that are specific to the C pretty-printer.
A derived pretty-printer can override any function listed in the
vtable below. See cp/cxx-pretty-print.h and cp/cxx-pretty-print.c
for an example of derivation. */
struct c_pretty_print_info
{
pretty_printer base;
/* Points to the first element of an array of offset-list.
Not used yet. */
int *offset_list;
pp_flags flags;
/* These must be overridden by each of the C and C++ front-end to
reflect their understanding of syntactic productions when they differ. */
c_pretty_print_fn declaration;
c_pretty_print_fn declaration_specifiers;
c_pretty_print_fn declarator;
c_pretty_print_fn abstract_declarator;
c_pretty_print_fn direct_abstract_declarator;
c_pretty_print_fn type_specifier_seq;
c_pretty_print_fn direct_declarator;
c_pretty_print_fn ptr_operator;
c_pretty_print_fn parameter_list;
c_pretty_print_fn type_id;
c_pretty_print_fn simple_type_specifier;
c_pretty_print_fn function_specifier;
c_pretty_print_fn storage_class_specifier;
c_pretty_print_fn initializer;
c_pretty_print_fn statement;
c_pretty_print_fn constant;
c_pretty_print_fn id_expression;
c_pretty_print_fn primary_expression;
c_pretty_print_fn postfix_expression;
c_pretty_print_fn unary_expression;
c_pretty_print_fn multiplicative_expression;
c_pretty_print_fn conditional_expression;
c_pretty_print_fn assignment_expression;
c_pretty_print_fn expression;
};
/* Override the pp_base macro. Derived pretty-printers should not
touch this macro. Instead they should override pp_c_base instead. */
#undef pp_base
#define pp_base(PP) (&pp_c_base (PP)->base)
#define pp_c_tree_identifier(PPI, ID) \
pp_c_identifier (PPI, IDENTIFIER_POINTER (ID))
#define pp_declaration(PPI, T) \
pp_c_base (PPI)->declaration (pp_c_base (PPI), T)
#define pp_declaration_specifiers(PPI, D) \
pp_c_base (PPI)->declaration_specifiers (pp_c_base (PPI), D)
#define pp_abstract_declarator(PP, D) \
pp_c_base (PP)->abstract_declarator (pp_c_base (PP), D)
#define pp_type_specifier_seq(PPI, D) \
pp_c_base (PPI)->type_specifier_seq (pp_c_base (PPI), D)
#define pp_declarator(PPI, D) \
pp_c_base (PPI)->declarator (pp_c_base (PPI), D)
#define pp_direct_declarator(PPI, D) \
pp_c_base (PPI)->direct_declarator (pp_c_base (PPI), D)
#define pp_direct_abstract_declarator(PP, D) \
pp_c_base (PP)->direct_abstract_declarator (pp_c_base (PP), D)
#define pp_ptr_operator(PP, D) \
pp_c_base (PP)->ptr_operator (pp_c_base (PP), D)
#define pp_parameter_list(PPI, T) \
pp_c_base (PPI)->parameter_list (pp_c_base (PPI), T)
#define pp_type_id(PPI, D) \
pp_c_base (PPI)->type_id (pp_c_base (PPI), D)
#define pp_simple_type_specifier(PP, T) \
pp_c_base (PP)->simple_type_specifier (pp_c_base (PP), T)
#define pp_function_specifier(PP, D) \
pp_c_base (PP)->function_specifier (pp_c_base (PP), D)
#define pp_storage_class_specifier(PP, D) \
pp_c_base (PP)->storage_class_specifier (pp_c_base (PP), D);
#define pp_statement(PPI, S) \
pp_c_base (PPI)->statement (pp_c_base (PPI), S)
#define pp_constant(PP, E) \
pp_c_base (PP)->constant (pp_c_base (PP), E)
#define pp_id_expression(PP, E) \
pp_c_base (PP)->id_expression (pp_c_base (PP), E)
#define pp_primary_expression(PPI, E) \
pp_c_base (PPI)->primary_expression (pp_c_base (PPI), E)
#define pp_postfix_expression(PPI, E) \
pp_c_base (PPI)->postfix_expression (pp_c_base (PPI), E)
#define pp_unary_expression(PPI, E) \
pp_c_base (PPI)->unary_expression (pp_c_base (PPI), E)
#define pp_initializer(PPI, E) \
pp_c_base (PPI)->initializer (pp_c_base (PPI), E)
#define pp_multiplicative_expression(PPI, E) \
pp_c_base (PPI)->multiplicative_expression (pp_c_base (PPI), E)
#define pp_conditional_expression(PPI, E) \
pp_c_base (PPI)->conditional_expression (pp_c_base (PPI), E)
#define pp_assignment_expression(PPI, E) \
pp_c_base (PPI)->assignment_expression (pp_c_base (PPI), E)
#define pp_expression(PP, E) \
pp_c_base (PP)->expression (pp_c_base (PP), E)
/* Returns the c_pretty_printer base object of PRETTY-PRINTER. This
macro must be overridden by any subclass of c_pretty_print_info. */
#define pp_c_base(PP) (PP)
extern void pp_c_pretty_printer_init (c_pretty_printer *);
void pp_c_whitespace (c_pretty_printer *);
void pp_c_left_paren (c_pretty_printer *);
void pp_c_right_paren (c_pretty_printer *);
void pp_c_left_brace (c_pretty_printer *);
void pp_c_right_brace (c_pretty_printer *);
void pp_c_left_bracket (c_pretty_printer *);
void pp_c_right_bracket (c_pretty_printer *);
void pp_c_dot (c_pretty_printer *);
void pp_c_ampersand (c_pretty_printer *);
void pp_c_star (c_pretty_printer *);
void pp_c_arrow (c_pretty_printer *);
void pp_c_semicolon (c_pretty_printer *);
void pp_c_complement (c_pretty_printer *);
void pp_c_exclamation (c_pretty_printer *);
void pp_c_space_for_pointer_operator (c_pretty_printer *, tree);
/* Declarations. */
void pp_c_tree_decl_identifier (c_pretty_printer *, tree);
void pp_c_function_definition (c_pretty_printer *, tree);
void pp_c_attributes (c_pretty_printer *, tree);
void pp_c_attributes_display (c_pretty_printer *, tree);
void pp_c_cv_qualifiers (c_pretty_printer *pp, int qualifiers, bool func_type);
void pp_c_type_qualifier_list (c_pretty_printer *, tree);
void pp_c_parameter_type_list (c_pretty_printer *, tree);
void pp_c_declaration (c_pretty_printer *, tree);
void pp_c_declaration_specifiers (c_pretty_printer *, tree);
void pp_c_declarator (c_pretty_printer *, tree);
void pp_c_direct_declarator (c_pretty_printer *, tree);
void pp_c_specifier_qualifier_list (c_pretty_printer *, tree);
void pp_c_function_specifier (c_pretty_printer *, tree);
void pp_c_type_id (c_pretty_printer *, tree);
void pp_c_direct_abstract_declarator (c_pretty_printer *, tree);
void pp_c_type_specifier (c_pretty_printer *, tree);
void pp_c_storage_class_specifier (c_pretty_printer *, tree);
/* Statements. */
void pp_c_statement (c_pretty_printer *, tree);
/* Expressions. */
void pp_c_expression (c_pretty_printer *, tree);
void pp_c_logical_or_expression (c_pretty_printer *, tree);
void pp_c_expression_list (c_pretty_printer *, tree);
void pp_c_constructor_elts (c_pretty_printer *, vec<constructor_elt, va_gc> *);
void pp_c_call_argument_list (c_pretty_printer *, tree);
void pp_c_unary_expression (c_pretty_printer *, tree);
void pp_c_cast_expression (c_pretty_printer *, tree);
void pp_c_postfix_expression (c_pretty_printer *, tree);
void pp_c_primary_expression (c_pretty_printer *, tree);
void pp_c_init_declarator (c_pretty_printer *, tree);
void pp_c_constant (c_pretty_printer *, tree);
void pp_c_id_expression (c_pretty_printer *, tree);
void pp_c_ws_string (c_pretty_printer *, const char *);
void pp_c_identifier (c_pretty_printer *, const char *);
void pp_c_string_literal (c_pretty_printer *, tree);
void print_c_tree (FILE *file, tree t);
#endif /* GCC_C_PRETTY_PRINTER */

673
src/include/c-tree.h Normal file
View File

@ -0,0 +1,673 @@
/* Definitions for C parsing and type checking.
Copyright (C) 1987-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GCC_C_TREE_H
#define GCC_C_TREE_H
#include "c-family/c-common.h"
#include "diagnostic.h"
/* struct lang_identifier is private to c-decl.c, but langhooks.c needs to
know how big it is. This is sanity-checked in c-decl.c. */
#define C_SIZEOF_STRUCT_LANG_IDENTIFIER \
(sizeof (struct c_common_identifier) + 3 * sizeof (void *))
/* In a RECORD_TYPE or UNION_TYPE, nonzero if any component is read-only. */
#define C_TYPE_FIELDS_READONLY(TYPE) TREE_LANG_FLAG_1 (TYPE)
/* In a RECORD_TYPE or UNION_TYPE, nonzero if any component is volatile. */
#define C_TYPE_FIELDS_VOLATILE(TYPE) TREE_LANG_FLAG_2 (TYPE)
/* In a RECORD_TYPE or UNION_TYPE or ENUMERAL_TYPE
nonzero if the definition of the type has already started. */
#define C_TYPE_BEING_DEFINED(TYPE) TYPE_LANG_FLAG_0 (TYPE)
/* In an incomplete RECORD_TYPE or UNION_TYPE, a list of variable
declarations whose type would be completed by completing that type. */
#define C_TYPE_INCOMPLETE_VARS(TYPE) TYPE_VFIELD (TYPE)
/* In an IDENTIFIER_NODE, nonzero if this identifier is actually a
keyword. C_RID_CODE (node) is then the RID_* value of the keyword,
and C_RID_YYCODE is the token number wanted by Yacc. */
#define C_IS_RESERVED_WORD(ID) TREE_LANG_FLAG_0 (ID)
/* Record whether a type or decl was written with nonconstant size.
Note that TYPE_SIZE may have simplified to a constant. */
#define C_TYPE_VARIABLE_SIZE(TYPE) TYPE_LANG_FLAG_1 (TYPE)
#define C_DECL_VARIABLE_SIZE(TYPE) DECL_LANG_FLAG_0 (TYPE)
/* Record whether a type is defined inside a struct or union type.
This is used for -Wc++-compat. */
#define C_TYPE_DEFINED_IN_STRUCT(TYPE) TYPE_LANG_FLAG_2 (TYPE)
/* Record whether a typedef for type `int' was actually `signed int'. */
#define C_TYPEDEF_EXPLICITLY_SIGNED(EXP) DECL_LANG_FLAG_1 (EXP)
/* For a FUNCTION_DECL, nonzero if it was defined without an explicit
return type. */
#define C_FUNCTION_IMPLICIT_INT(EXP) DECL_LANG_FLAG_1 (EXP)
/* For a FUNCTION_DECL, nonzero if it was an implicit declaration. */
#define C_DECL_IMPLICIT(EXP) DECL_LANG_FLAG_2 (EXP)
/* For FUNCTION_DECLs, evaluates true if the decl is built-in but has
been declared. */
#define C_DECL_DECLARED_BUILTIN(EXP) \
DECL_LANG_FLAG_3 (FUNCTION_DECL_CHECK (EXP))
/* For FUNCTION_DECLs, evaluates true if the decl is built-in, has a
built-in prototype and does not have a non-built-in prototype. */
#define C_DECL_BUILTIN_PROTOTYPE(EXP) \
DECL_LANG_FLAG_6 (FUNCTION_DECL_CHECK (EXP))
/* Record whether a decl was declared register. This is strictly a
front-end flag, whereas DECL_REGISTER is used for code generation;
they may differ for structures with volatile fields. */
#define C_DECL_REGISTER(EXP) DECL_LANG_FLAG_4 (EXP)
/* Record whether a decl was used in an expression anywhere except an
unevaluated operand of sizeof / typeof / alignof. This is only
used for functions declared static but not defined, though outside
sizeof and typeof it is set for other function decls as well. */
#define C_DECL_USED(EXP) DECL_LANG_FLAG_5 (FUNCTION_DECL_CHECK (EXP))
/* Record whether a variable has been declared threadprivate by
#pragma omp threadprivate. */
#define C_DECL_THREADPRIVATE_P(DECL) DECL_LANG_FLAG_3 (VAR_DECL_CHECK (DECL))
/* Nonzero for a decl which either doesn't exist or isn't a prototype.
N.B. Could be simplified if all built-in decls had complete prototypes
(but this is presently difficult because some of them need FILE*). */
#define C_DECL_ISNT_PROTOTYPE(EXP) \
(EXP == 0 \
|| (!prototype_p (TREE_TYPE (EXP)) \
&& !DECL_BUILT_IN (EXP)))
/* For FUNCTION_TYPE, a hidden list of types of arguments. The same as
TYPE_ARG_TYPES for functions with prototypes, but created for functions
without prototypes. */
#define TYPE_ACTUAL_ARG_TYPES(NODE) TYPE_LANG_SLOT_1 (NODE)
/* For a CONSTRUCTOR, whether some initializer contains a
subexpression meaning it is not a constant expression. */
#define CONSTRUCTOR_NON_CONST(EXPR) TREE_LANG_FLAG_1 (CONSTRUCTOR_CHECK (EXPR))
/* Record parser information about an expression that is irrelevant
for code generation alongside a tree representing its value. */
struct c_expr
{
/* The value of the expression. */
tree value;
/* Record the original unary/binary operator of an expression, which may
have been changed by fold, STRING_CST for unparenthesized string
constants, C_MAYBE_CONST_EXPR for __builtin_constant_p calls
(even if parenthesized), for subexpressions, and for non-constant
initializers, or ERROR_MARK for other expressions (including
parenthesized expressions). */
enum tree_code original_code;
/* If not NULL, the original type of an expression. This will
differ from the type of the value field for an enum constant.
The type of an enum constant is a plain integer type, but this
field will be the enum type. */
tree original_type;
};
/* Type alias for struct c_expr. This allows to use the structure
inside the VEC types. */
typedef struct c_expr c_expr_t;
/* A varray of c_expr_t. */
/* Append a new c_expr_t element to V. */
#define C_EXPR_APPEND(V, ELEM) \
do { \
c_expr_t __elem = (ELEM); \
vec_safe_push (V, __elem); \
} while (0)
/* A kind of type specifier. Note that this information is currently
only used to distinguish tag definitions, tag references and typeof
uses. */
enum c_typespec_kind {
/* No typespec. This appears only in struct c_declspec. */
ctsk_none,
/* A reserved keyword type specifier. */
ctsk_resword,
/* A reference to a tag, previously declared, such as "struct foo".
This includes where the previous declaration was as a different
kind of tag, in which case this is only valid if shadowing that
tag in an inner scope. */
ctsk_tagref,
/* A reference to a tag, not previously declared in a visible
scope. */
ctsk_tagfirstref,
/* A definition of a tag such as "struct foo { int a; }". */
ctsk_tagdef,
/* A typedef name. */
ctsk_typedef,
/* An ObjC-specific kind of type specifier. */
ctsk_objc,
/* A typeof specifier. */
ctsk_typeof
};
/* A type specifier: this structure is created in the parser and
passed to declspecs_add_type only. */
struct c_typespec {
/* What kind of type specifier this is. */
enum c_typespec_kind kind;
/* Whether the expression has operands suitable for use in constant
expressions. */
bool expr_const_operands;
/* The specifier itself. */
tree spec;
/* An expression to be evaluated before the type specifier, in the
case of typeof specifiers, or NULL otherwise or if no such
expression is required for a particular typeof specifier. In
particular, when typeof is applied to an expression of variably
modified type, that expression must be evaluated in order to
determine array sizes that form part of the type, but the
expression itself (as opposed to the array sizes) forms no part
of the type and so needs to be recorded separately. */
tree expr;
};
/* A storage class specifier. */
enum c_storage_class {
csc_none,
csc_auto,
csc_extern,
csc_register,
csc_static,
csc_typedef
};
/* A type specifier keyword "void", "_Bool", "char", "int", "float",
"double", "_Decimal32", "_Decimal64", "_Decimal128", "_Fract", "_Accum",
or none of these. */
enum c_typespec_keyword {
cts_none,
cts_void,
cts_bool,
cts_char,
cts_int,
cts_float,
cts_int128,
cts_double,
cts_dfloat32,
cts_dfloat64,
cts_dfloat128,
cts_fract,
cts_accum
};
/* This enum lists all the possible declarator specifiers, storage
class or attribute that a user can write. There is at least one
enumerator per possible declarator specifier in the struct
c_declspecs below.
It is used to index the array of declspec locations in struct
c_declspecs. */
enum c_declspec_word {
cdw_typespec /* A catch-all for a typespec. */,
cdw_storage_class /* A catch-all for a storage class */,
cdw_attributes,
cdw_typedef,
cdw_explicit_signed,
cdw_deprecated,
cdw_default_int,
cdw_long,
cdw_long_long,
cdw_short,
cdw_signed,
cdw_unsigned,
cdw_complex,
cdw_inline,
cdw_noreturn,
cdw_thread,
cdw_const,
cdw_volatile,
cdw_restrict,
cdw_saturating,
cdw_alignas,
cdw_address_space,
cdw_number_of_elements /* This one must always be the last
enumerator. */
};
/* A sequence of declaration specifiers in C. When a new declaration
specifier is added, please update the enum c_declspec_word above
accordingly. */
struct c_declspecs {
source_location locations[cdw_number_of_elements];
/* The type specified, if a single type specifier such as a struct,
union or enum specifier, typedef name or typeof specifies the
whole type, or NULL_TREE if none or a keyword such as "void" or
"char" is used. Does not include qualifiers. */
tree type;
/* Any expression to be evaluated before the type, from a typeof
specifier. */
tree expr;
/* The attributes from a typedef decl. */
tree decl_attr;
/* When parsing, the attributes. Outside the parser, this will be
NULL; attributes (possibly from multiple lists) will be passed
separately. */
tree attrs;
/* The base-2 log of the greatest alignment required by an _Alignas
specifier, in bytes, or -1 if no such specifiers with nonzero
alignment. */
int align_log;
/* The storage class specifier, or csc_none if none. */
enum c_storage_class storage_class;
/* Any type specifier keyword used such as "int", not reflecting
modifiers such as "short", or cts_none if none. */
ENUM_BITFIELD (c_typespec_keyword) typespec_word : 8;
/* The kind of type specifier if one has been seen, ctsk_none
otherwise. */
ENUM_BITFIELD (c_typespec_kind) typespec_kind : 3;
/* Whether any expressions in typeof specifiers may appear in
constant expressions. */
BOOL_BITFIELD expr_const_operands : 1;
/* Whether any declaration specifiers have been seen at all. */
BOOL_BITFIELD declspecs_seen_p : 1;
/* Whether something other than a storage class specifier or
attribute has been seen. This is used to warn for the
obsolescent usage of storage class specifiers other than at the
start of the list. (Doing this properly would require function
specifiers to be handled separately from storage class
specifiers.) */
BOOL_BITFIELD non_sc_seen_p : 1;
/* Whether the type is specified by a typedef or typeof name. */
BOOL_BITFIELD typedef_p : 1;
/* Whether the type is explicitly "signed" or specified by a typedef
whose type is explicitly "signed". */
BOOL_BITFIELD explicit_signed_p : 1;
/* Whether the specifiers include a deprecated typedef. */
BOOL_BITFIELD deprecated_p : 1;
/* Whether the type defaulted to "int" because there were no type
specifiers. */
BOOL_BITFIELD default_int_p : 1;
/* Whether "long" was specified. */
BOOL_BITFIELD long_p : 1;
/* Whether "long" was specified more than once. */
BOOL_BITFIELD long_long_p : 1;
/* Whether "short" was specified. */
BOOL_BITFIELD short_p : 1;
/* Whether "signed" was specified. */
BOOL_BITFIELD signed_p : 1;
/* Whether "unsigned" was specified. */
BOOL_BITFIELD unsigned_p : 1;
/* Whether "complex" was specified. */
BOOL_BITFIELD complex_p : 1;
/* Whether "inline" was specified. */
BOOL_BITFIELD inline_p : 1;
/* Whether "_Noreturn" was speciied. */
BOOL_BITFIELD noreturn_p : 1;
/* Whether "__thread" was specified. */
BOOL_BITFIELD thread_p : 1;
/* Whether "const" was specified. */
BOOL_BITFIELD const_p : 1;
/* Whether "volatile" was specified. */
BOOL_BITFIELD volatile_p : 1;
/* Whether "restrict" was specified. */
BOOL_BITFIELD restrict_p : 1;
/* Whether "_Sat" was specified. */
BOOL_BITFIELD saturating_p : 1;
/* Whether any alignment specifier (even with zero alignment) was
specified. */
BOOL_BITFIELD alignas_p : 1;
/* The address space that the declaration belongs to. */
addr_space_t address_space;
};
/* The various kinds of declarators in C. */
enum c_declarator_kind {
/* An identifier. */
cdk_id,
/* A function. */
cdk_function,
/* An array. */
cdk_array,
/* A pointer. */
cdk_pointer,
/* Parenthesized declarator with nested attributes. */
cdk_attrs
};
typedef struct c_arg_tag_d {
/* The argument name. */
tree id;
/* The type of the argument. */
tree type;
} c_arg_tag;
/* Information about the parameters in a function declarator. */
struct c_arg_info {
/* A list of parameter decls. */
tree parms;
/* A list of structure, union and enum tags defined. */
vec<c_arg_tag, va_gc> *tags;
/* A list of argument types to go in the FUNCTION_TYPE. */
tree types;
/* A list of non-parameter decls (notably enumeration constants)
defined with the parameters. */
tree others;
/* A compound expression of VLA sizes from the parameters, or NULL.
In a function definition, these are used to ensure that
side-effects in sizes of arrays converted to pointers (such as a
parameter int i[n++]) take place; otherwise, they are
ignored. */
tree pending_sizes;
/* True when these arguments had [*]. */
BOOL_BITFIELD had_vla_unspec : 1;
};
/* A declarator. */
struct c_declarator {
/* The kind of declarator. */
enum c_declarator_kind kind;
location_t id_loc; /* Currently only set for cdk_id, cdk_array. */
/* Except for cdk_id, the contained declarator. For cdk_id, NULL. */
struct c_declarator *declarator;
union {
/* For identifiers, an IDENTIFIER_NODE or NULL_TREE if an abstract
declarator. */
tree id;
/* For functions. */
struct c_arg_info *arg_info;
/* For arrays. */
struct {
/* The array dimension, or NULL for [] and [*]. */
tree dimen;
/* The qualifiers inside []. */
int quals;
/* The attributes (currently ignored) inside []. */
tree attrs;
/* Whether [static] was used. */
BOOL_BITFIELD static_p : 1;
/* Whether [*] was used. */
BOOL_BITFIELD vla_unspec_p : 1;
} array;
/* For pointers, the qualifiers on the pointer type. */
int pointer_quals;
/* For attributes. */
tree attrs;
} u;
};
/* A type name. */
struct c_type_name {
/* The declaration specifiers. */
struct c_declspecs *specs;
/* The declarator. */
struct c_declarator *declarator;
};
/* A parameter. */
struct c_parm {
/* The declaration specifiers, minus any prefix attributes. */
struct c_declspecs *specs;
/* The attributes. */
tree attrs;
/* The declarator. */
struct c_declarator *declarator;
};
/* Used when parsing an enum. Initialized by start_enum. */
struct c_enum_contents
{
/* While defining an enum type, this is 1 plus the last enumerator
constant value. */
tree enum_next_value;
/* Nonzero means that there was overflow computing enum_next_value. */
int enum_overflow;
};
/* A type of reference to a static identifier in an inline
function. */
enum c_inline_static_type {
/* Identifier with internal linkage used in function that may be an
inline definition (i.e., file-scope static). */
csi_internal,
/* Modifiable object with static storage duration defined in
function that may be an inline definition (i.e., local
static). */
csi_modifiable
};
/* in c-parser.c */
extern void c_parse_init (void);
/* in c-aux-info.c */
extern void gen_aux_info_record (tree, int, int, int);
/* in c-decl.c */
struct c_spot_bindings;
struct c_struct_parse_info;
extern struct obstack parser_obstack;
extern tree c_break_label;
extern tree c_cont_label;
extern bool global_bindings_p (void);
extern void push_scope (void);
extern tree pop_scope (void);
extern void c_bindings_start_stmt_expr (struct c_spot_bindings *);
extern void c_bindings_end_stmt_expr (struct c_spot_bindings *);
extern void record_inline_static (location_t, tree, tree,
enum c_inline_static_type);
extern void c_init_decl_processing (void);
extern void c_print_identifier (FILE *, tree, int);
extern int quals_from_declspecs (const struct c_declspecs *);
extern struct c_declarator *build_array_declarator (location_t, tree,
struct c_declspecs *,
bool, bool);
extern tree build_enumerator (location_t, location_t, struct c_enum_contents *,
tree, tree);
extern tree check_for_loop_decls (location_t, bool);
extern void mark_forward_parm_decls (void);
extern void declare_parm_level (void);
extern void undeclared_variable (location_t, tree);
extern tree lookup_label_for_goto (location_t, tree);
extern tree declare_label (tree);
extern tree define_label (location_t, tree);
extern struct c_spot_bindings *c_get_switch_bindings (void);
extern void c_release_switch_bindings (struct c_spot_bindings *);
extern bool c_check_switch_jump_warnings (struct c_spot_bindings *,
location_t, location_t);
extern void finish_decl (tree, location_t, tree, tree, tree);
extern tree finish_enum (tree, tree, tree);
extern void finish_function (void);
extern tree finish_struct (location_t, tree, tree, tree,
struct c_struct_parse_info *);
extern struct c_arg_info *build_arg_info (void);
extern struct c_arg_info *get_parm_info (bool, tree);
extern tree grokfield (location_t, struct c_declarator *,
struct c_declspecs *, tree, tree *);
extern tree groktypename (struct c_type_name *, tree *, bool *);
extern tree grokparm (const struct c_parm *, tree *);
extern tree implicitly_declare (location_t, tree);
extern void keep_next_level (void);
extern void pending_xref_error (void);
extern void c_push_function_context (void);
extern void c_pop_function_context (void);
extern void push_parm_decl (const struct c_parm *, tree *);
extern struct c_declarator *set_array_declarator_inner (struct c_declarator *,
struct c_declarator *);
extern tree c_builtin_function (tree);
extern tree c_builtin_function_ext_scope (tree);
extern void shadow_tag (const struct c_declspecs *);
extern void shadow_tag_warned (const struct c_declspecs *, int);
extern tree start_enum (location_t, struct c_enum_contents *, tree);
extern int start_function (struct c_declspecs *, struct c_declarator *, tree);
extern tree start_decl (struct c_declarator *, struct c_declspecs *, bool,
tree);
extern tree start_struct (location_t, enum tree_code, tree,
struct c_struct_parse_info **);
extern void store_parm_decls (void);
extern void store_parm_decls_from (struct c_arg_info *);
extern tree xref_tag (enum tree_code, tree);
extern struct c_typespec parser_xref_tag (location_t, enum tree_code, tree);
extern struct c_parm *build_c_parm (struct c_declspecs *, tree,
struct c_declarator *);
extern struct c_declarator *build_attrs_declarator (tree,
struct c_declarator *);
extern struct c_declarator *build_function_declarator (struct c_arg_info *,
struct c_declarator *);
extern struct c_declarator *build_id_declarator (tree);
extern struct c_declarator *make_pointer_declarator (struct c_declspecs *,
struct c_declarator *);
extern struct c_declspecs *build_null_declspecs (void);
extern struct c_declspecs *declspecs_add_qual (source_location,
struct c_declspecs *, tree);
extern struct c_declspecs *declspecs_add_type (location_t,
struct c_declspecs *,
struct c_typespec);
extern struct c_declspecs *declspecs_add_scspec (source_location,
struct c_declspecs *, tree);
extern struct c_declspecs *declspecs_add_attrs (source_location,
struct c_declspecs *, tree);
extern struct c_declspecs *declspecs_add_addrspace (source_location,
struct c_declspecs *,
addr_space_t);
extern struct c_declspecs *declspecs_add_alignas (source_location,
struct c_declspecs *, tree);
extern struct c_declspecs *finish_declspecs (struct c_declspecs *);
/* in c-objc-common.c */
extern bool c_objc_common_init (void);
extern bool c_missing_noreturn_ok_p (tree);
extern bool c_warn_unused_global_decl (const_tree);
extern void c_initialize_diagnostics (diagnostic_context *);
extern bool c_vla_unspec_p (tree x, tree fn);
/* in c-typeck.c */
extern int in_alignof;
extern int in_sizeof;
extern int in_typeof;
extern tree c_last_sizeof_arg;
extern struct c_switch *c_switch_stack;
extern tree c_objc_common_truthvalue_conversion (location_t, tree);
extern tree require_complete_type (tree);
extern int same_translation_unit_p (const_tree, const_tree);
extern int comptypes (tree, tree);
extern int comptypes_check_different_types (tree, tree, bool *);
extern bool c_vla_type_p (const_tree);
extern bool c_mark_addressable (tree);
extern void c_incomplete_type_error (const_tree, const_tree);
extern tree c_type_promotes_to (tree);
extern struct c_expr default_function_array_conversion (location_t,
struct c_expr);
extern struct c_expr default_function_array_read_conversion (location_t,
struct c_expr);
extern void mark_exp_read (tree);
extern tree composite_type (tree, tree);
extern tree build_component_ref (location_t, tree, tree);
extern tree build_array_ref (location_t, tree, tree);
extern tree build_external_ref (location_t, tree, int, tree *);
extern void pop_maybe_used (bool);
extern struct c_expr c_expr_sizeof_expr (location_t, struct c_expr);
extern struct c_expr c_expr_sizeof_type (location_t, struct c_type_name *);
extern struct c_expr parser_build_unary_op (location_t, enum tree_code,
struct c_expr);
extern struct c_expr parser_build_binary_op (location_t,
enum tree_code, struct c_expr,
struct c_expr);
extern tree build_conditional_expr (location_t, tree, bool, tree, tree,
tree, tree);
extern tree build_compound_expr (location_t, tree, tree);
extern tree c_cast_expr (location_t, struct c_type_name *, tree);
extern tree build_c_cast (location_t, tree, tree);
extern void store_init_value (location_t, tree, tree, tree);
extern void error_init (const char *);
extern void pedwarn_init (location_t, int opt, const char *);
extern void maybe_warn_string_init (tree, struct c_expr);
extern void start_init (tree, tree, int);
extern void finish_init (void);
extern void really_start_incremental_init (tree);
extern void push_init_level (int, struct obstack *);
extern struct c_expr pop_init_level (int, struct obstack *);
extern void set_init_index (tree, tree, struct obstack *);
extern void set_init_label (tree, struct obstack *);
extern void process_init_element (struct c_expr, bool, struct obstack *);
extern tree build_compound_literal (location_t, tree, tree, bool);
extern void check_compound_literal_type (location_t, struct c_type_name *);
extern tree c_start_case (location_t, location_t, tree);
extern void c_finish_case (tree);
extern tree build_asm_expr (location_t, tree, tree, tree, tree, tree, bool);
extern tree build_asm_stmt (tree, tree);
extern int c_types_compatible_p (tree, tree);
extern tree c_begin_compound_stmt (bool);
extern tree c_end_compound_stmt (location_t, tree, bool);
extern void c_finish_if_stmt (location_t, tree, tree, tree, bool);
extern void c_finish_loop (location_t, tree, tree, tree, tree, tree, bool);
extern tree c_begin_stmt_expr (void);
extern tree c_finish_stmt_expr (location_t, tree);
extern tree c_process_expr_stmt (location_t, tree);
extern tree c_finish_expr_stmt (location_t, tree);
extern tree c_finish_return (location_t, tree, tree);
extern tree c_finish_bc_stmt (location_t, tree *, bool);
extern tree c_finish_goto_label (location_t, tree);
extern tree c_finish_goto_ptr (location_t, tree);
extern tree c_expr_to_decl (tree, bool *, bool *);
extern tree c_begin_omp_parallel (void);
extern tree c_finish_omp_parallel (location_t, tree, tree);
extern tree c_begin_omp_task (void);
extern tree c_finish_omp_task (location_t, tree, tree);
extern tree c_finish_omp_clauses (tree);
extern tree c_build_va_arg (location_t, tree, tree);
extern tree c_finish_transaction (location_t, tree, int);
extern tree c_build_function_call_vec (location_t, tree, vec<tree, va_gc> *,
vec<tree, va_gc> *);
/* Set to 0 at beginning of a function definition, set to 1 if
a return statement that specifies a return value is seen. */
extern int current_function_returns_value;
/* Set to 0 at beginning of a function definition, set to 1 if
a return statement with no argument is seen. */
extern int current_function_returns_null;
/* Set to 0 at beginning of a function definition, set to 1 if
a call to a noreturn function is seen. */
extern int current_function_returns_abnormally;
/* Mode used to build pointers (VOIDmode means ptr_mode). */
extern enum machine_mode c_default_pointer_mode;
/* In c-decl.c */
extern void c_finish_incomplete_decl (tree);
extern void c_write_global_declarations (void);
/* In c-errors.c */
extern void pedwarn_c90 (location_t, int opt, const char *, ...) ATTRIBUTE_GCC_DIAG(3,4);
extern void pedwarn_c99 (location_t, int opt, const char *, ...) ATTRIBUTE_GCC_DIAG(3,4);
#endif /* ! GCC_C_TREE_H */

186
src/include/cfg-flags.def Normal file
View File

@ -0,0 +1,186 @@
/* Flags on basic blocks and edges.
Copyright (C) 2012-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
/* This file defines flags that may appear on basic blocks or on
edges. Source files define DEF_BASIC_BLOCK_FLAG or DEF_EDGE_FLAG
appropriately before including this file. */
#if !defined(DEF_BASIC_BLOCK_FLAG) && !defined(DEF_EDGE_FLAG)
#error "You must define DEF_BASIC_BLOCK_FLAG or DEF_EDGE_FLAG"
#endif
#ifdef DEF_BASIC_BLOCK_FLAG
/* Masks for basic_block.flags.
The format of this file is: DEF_BASIC_BLOCK_FLAG(NAME, IDX).
NAME is the name of the basic block flag. A flag BB_#NAME will be
created and the name is used in dump_edge_info.
IDX is a sequence number that is used to determine the value
of the flag, which is 1 << IDX).
BB_HOT_PARTITION and BB_COLD_PARTITION should be preserved throughout
the compilation, so they are never cleared.
All other flags may be cleared by clear_bb_flags(). It is generally
a bad idea to rely on any flags being up-to-date. */
/* Only set on blocks that have just been created by create_bb. */
DEF_BASIC_BLOCK_FLAG(NEW, 0)
/* Set by find_unreachable_blocks. Do not rely on this being set in any
pass. */
DEF_BASIC_BLOCK_FLAG(REACHABLE, 1)
/* Set for blocks in an irreducible loop by loop analysis. */
DEF_BASIC_BLOCK_FLAG(IRREDUCIBLE_LOOP, 2)
/* Set on blocks that may actually not be single-entry single-exit block. */
DEF_BASIC_BLOCK_FLAG(SUPERBLOCK, 3)
/* Set on basic blocks that the scheduler should not touch. This is used
by SMS to prevent other schedulers from messing with the loop schedule. */
DEF_BASIC_BLOCK_FLAG(DISABLE_SCHEDULE, 4)
/* Set on blocks that should be put in a hot section. */
DEF_BASIC_BLOCK_FLAG(HOT_PARTITION, 5)
/* Set on blocks that should be put in a cold section. */
DEF_BASIC_BLOCK_FLAG(COLD_PARTITION, 6)
/* Set on block that was duplicated. */
DEF_BASIC_BLOCK_FLAG(DUPLICATED, 7)
/* Set if the label at the top of this block is the target of a non-local goto. */
DEF_BASIC_BLOCK_FLAG(NON_LOCAL_GOTO_TARGET, 8)
/* Set on blocks that are in RTL format. */
DEF_BASIC_BLOCK_FLAG(RTL, 9)
/* Set on blocks that are forwarder blocks.
Only used in cfgcleanup.c. */
DEF_BASIC_BLOCK_FLAG(FORWARDER_BLOCK, 10)
/* Set on blocks that cannot be threaded through.
Only used in cfgcleanup.c. */
DEF_BASIC_BLOCK_FLAG(NONTHREADABLE_BLOCK, 11)
/* Set on blocks that were modified in some way. This bit is set in
df_set_bb_dirty, but not cleared by df_analyze, so it can be used
to test whether a block has been modified prior to a df_analyze call. */
DEF_BASIC_BLOCK_FLAG(MODIFIED, 12)
/* A general visited flag for passes to use. */
DEF_BASIC_BLOCK_FLAG(VISITED, 13)
/* Set on blocks that are in a transaction. This is calculated on
demand, and is available after calling compute_transaction_bits(). */
DEF_BASIC_BLOCK_FLAG(IN_TRANSACTION, 14)
#endif
#ifdef DEF_EDGE_FLAG
/* Masks for edge.flags.
The format of this file is: DEF_EDGE_FLAG(NAME, IDX, STRING).
NAME is the name of the edge flag. A flag EDGE_#NAME will be
created and the name is used in dump_edge_info.
IDX is a sequence number that is used to determine the value
of the flag, which is 1 << IDX). */
/* 'Straight line' flow. In GIMPLE and in cfglayout mode, all normal
edges are fallthru edges. In cfgrtl mode, this flag really means
that control flow falls through to the next basic block in the line. */
DEF_EDGE_FLAG(FALLTHRU, 0)
/* Strange flow, like a computed jump or exception handling. Usually
this means that the edge cannot be split. */
DEF_EDGE_FLAG(ABNORMAL, 1)
/* Edge out of a basic block that ends with a CALL_INSN with abnormal
exit, like an exception or a non-local goto.
ABNORMAL_CALL edges also have ABNORMAL set.
This flag is only used for the RTL CFG. */
DEF_EDGE_FLAG(ABNORMAL_CALL, 2)
/* Exception edge. Exception handling edges represent possible control
transfers from a trapping instruction to an exception handler.
EH edges also have ABNORMAL set for the RTL CFG. */
DEF_EDGE_FLAG(EH, 3)
/* Never merge blocks via this edge. This is used for exception handling,
to prevent merging away edges to the post-landing-pad basic block.
This flag is only used for the RTL CFG. */
DEF_EDGE_FLAG(PRESERVE, 4)
/* Not a real edge. This is used to connect parts of the CFG that do
not halt, such as infinite loops and noreturn functions, to the
EXIT_BLOCK, so that traversing of the reverse CFG is possible. */
DEF_EDGE_FLAG(FAKE, 5)
/* A back edge, marked in a depth-first search of the CFG. Back edges
are hints that this edge may be part of a loop in the CFG. */
DEF_EDGE_FLAG(DFS_BACK, 6)
/* Edge in a part of the CFG that is an irreducible loop. */
DEF_EDGE_FLAG(IRREDUCIBLE_LOOP, 7)
/* Edge taken when controlling predicate is nonzero.
This is only used for the GIMPLE CFG. */
DEF_EDGE_FLAG(TRUE_VALUE, 8)
/* Edge taken when controlling predicate is zero.
This is only used for the GIMPLE CFG. */
DEF_EDGE_FLAG(FALSE_VALUE, 9)
/* Edge is executable. This is only used in GIMPLE SSA-CCP and VRP.
This is only used for the GIMPLE CFG. */
DEF_EDGE_FLAG(EXECUTABLE, 10)
/* Edge crosses between hot and cold sections, when we do partitioning.
This flag is only used for the RTL CFG. */
DEF_EDGE_FLAG(CROSSING, 11)
/* Edge from a sibcall CALL_INSN to exit.
SIBCALL edges also have ABNORMAL set.
This flag is only used for the RTL CFG. */
DEF_EDGE_FLAG(SIBCALL, 12)
/* Candidate for straight line flow. Only used in bb-reorder.c.
This flag is only used for the RTL CFG. */
DEF_EDGE_FLAG(CAN_FALLTHRU, 13)
/* Exit of a loop. This is only used in ifcvt.c.
This flag is only used for the RTL CFG. */
DEF_EDGE_FLAG(LOOP_EXIT, 14)
/* Uninstrumented edge out of a GIMPLE_TRANSACTION statement. */
DEF_EDGE_FLAG(TM_UNINSTRUMENTED, 15)
/* Abort (over) edge out of a GIMPLE_TRANSACTION statement. */
DEF_EDGE_FLAG(TM_ABORT, 16)
#endif
/*
Local variables:
mode:c
End:
*/

223
src/include/cfghooks.h Normal file
View File

@ -0,0 +1,223 @@
/* Hooks for cfg representation specific functions.
Copyright (C) 2003-2013 Free Software Foundation, Inc.
Contributed by Sebastian Pop <s.pop@laposte.net>
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GCC is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
/* Only basic-block.h includes this. */
struct cfg_hooks
{
/* Name of the corresponding ir. */
const char *name;
/* Debugging. */
int (*verify_flow_info) (void);
void (*dump_bb) (FILE *, basic_block, int, int);
void (*dump_bb_for_graph) (pretty_printer *, basic_block);
/* Basic CFG manipulation. */
/* Return new basic block. */
basic_block (*create_basic_block) (void *head, void *end, basic_block after);
/* Redirect edge E to the given basic block B and update underlying program
representation. Returns edge representing redirected branch (that may not
be equivalent to E in the case of duplicate edges being removed) or NULL
if edge is not easily redirectable for whatever reason. */
edge (*redirect_edge_and_branch) (edge e, basic_block b);
/* Same as the above but allows redirecting of fallthru edges. In that case
newly created forwarder basic block is returned. The edge must
not be abnormal. */
basic_block (*redirect_edge_and_branch_force) (edge, basic_block);
/* Returns true if it is possible to remove the edge by redirecting it
to the destination of the other edge going from its source. */
bool (*can_remove_branch_p) (const_edge);
/* Remove statements corresponding to a given basic block. */
void (*delete_basic_block) (basic_block);
/* Creates a new basic block just after basic block B by splitting
everything after specified instruction I. */
basic_block (*split_block) (basic_block b, void * i);
/* Move block B immediately after block A. */
bool (*move_block_after) (basic_block b, basic_block a);
/* Return true when blocks A and B can be merged into single basic block. */
bool (*can_merge_blocks_p) (basic_block a, basic_block b);
/* Merge blocks A and B. */
void (*merge_blocks) (basic_block a, basic_block b);
/* Predict edge E using PREDICTOR to given PROBABILITY. */
void (*predict_edge) (edge e, enum br_predictor predictor, int probability);
/* Return true if the one of outgoing edges is already predicted by
PREDICTOR. */
bool (*predicted_by_p) (const_basic_block bb, enum br_predictor predictor);
/* Return true when block A can be duplicated. */
bool (*can_duplicate_block_p) (const_basic_block a);
/* Duplicate block A. */
basic_block (*duplicate_block) (basic_block a);
/* Higher level functions representable by primitive operations above if
we didn't have some oddities in RTL and Tree representations. */
basic_block (*split_edge) (edge);
void (*make_forwarder_block) (edge);
/* Try to make the edge fallthru. */
void (*tidy_fallthru_edge) (edge);
/* Make the edge non-fallthru. */
basic_block (*force_nonfallthru) (edge);
/* Say whether a block ends with a call, possibly followed by some
other code that must stay with the call. */
bool (*block_ends_with_call_p) (basic_block);
/* Say whether a block ends with a conditional branch. Switches
and unconditional branches do not qualify. */
bool (*block_ends_with_condjump_p) (const_basic_block);
/* Add fake edges to the function exit for any non constant and non noreturn
calls, volatile inline assembly in the bitmap of blocks specified by
BLOCKS or to the whole CFG if BLOCKS is zero. Return the number of blocks
that were split.
The goal is to expose cases in which entering a basic block does not imply
that all subsequent instructions must be executed. */
int (*flow_call_edges_add) (sbitmap);
/* This function is called immediately after edge E is added to the
edge vector E->dest->preds. */
void (*execute_on_growing_pred) (edge);
/* This function is called immediately before edge E is removed from
the edge vector E->dest->preds. */
void (*execute_on_shrinking_pred) (edge);
/* A hook for duplicating loop in CFG, currently this is used
in loop versioning. */
bool (*cfg_hook_duplicate_loop_to_header_edge) (struct loop *, edge,
unsigned, sbitmap,
edge, vec<edge> *,
int);
/* Add condition to new basic block and update CFG used in loop
versioning. */
void (*lv_add_condition_to_bb) (basic_block, basic_block, basic_block,
void *);
/* Update the PHI nodes in case of loop versioning. */
void (*lv_adjust_loop_header_phi) (basic_block, basic_block,
basic_block, edge);
/* Given a condition BB extract the true/false taken/not taken edges
(depending if we are on tree's or RTL). */
void (*extract_cond_bb_edges) (basic_block, edge *, edge *);
/* Add PHI arguments queued in PENDINT_STMT list on edge E to edge
E->dest (only in tree-ssa loop versioning. */
void (*flush_pending_stmts) (edge);
/* True if a block contains no executable instructions. */
bool (*empty_block_p) (basic_block);
/* Split a basic block if it ends with a conditional branch and if
the other part of the block is not empty. */
basic_block (*split_block_before_cond_jump) (basic_block);
/* Do book-keeping of a basic block for the profile consistency checker. */
void (*account_profile_record) (basic_block, int, struct profile_record *);
};
extern void verify_flow_info (void);
extern void dump_bb (FILE *, basic_block, int, int);
extern void dump_bb_for_graph (pretty_printer *, basic_block);
extern edge redirect_edge_and_branch (edge, basic_block);
extern basic_block redirect_edge_and_branch_force (edge, basic_block);
extern bool can_remove_branch_p (const_edge);
extern void remove_branch (edge);
extern void remove_edge (edge);
extern edge split_block (basic_block, void *);
extern edge split_block_after_labels (basic_block);
extern bool move_block_after (basic_block, basic_block);
extern void delete_basic_block (basic_block);
extern basic_block split_edge (edge);
extern basic_block create_basic_block (void *, void *, basic_block);
extern basic_block create_empty_bb (basic_block);
extern bool can_merge_blocks_p (basic_block, basic_block);
extern void merge_blocks (basic_block, basic_block);
extern edge make_forwarder_block (basic_block, bool (*)(edge),
void (*) (basic_block));
extern basic_block force_nonfallthru (edge);
extern void tidy_fallthru_edge (edge);
extern void tidy_fallthru_edges (void);
extern void predict_edge (edge e, enum br_predictor predictor, int probability);
extern bool predicted_by_p (const_basic_block bb, enum br_predictor predictor);
extern bool can_duplicate_block_p (const_basic_block);
extern basic_block duplicate_block (basic_block, edge, basic_block);
extern bool block_ends_with_call_p (basic_block bb);
extern bool empty_block_p (basic_block);
extern basic_block split_block_before_cond_jump (basic_block);
extern bool block_ends_with_condjump_p (const_basic_block bb);
extern int flow_call_edges_add (sbitmap);
extern void execute_on_growing_pred (edge);
extern void execute_on_shrinking_pred (edge);
extern bool cfg_hook_duplicate_loop_to_header_edge (struct loop *loop, edge,
unsigned int ndupl,
sbitmap wont_exit,
edge orig,
vec<edge> *to_remove,
int flags);
extern void lv_flush_pending_stmts (edge);
extern void extract_cond_bb_edges (basic_block, edge *, edge*);
extern void lv_adjust_loop_header_phi (basic_block, basic_block, basic_block,
edge);
extern void lv_add_condition_to_bb (basic_block, basic_block, basic_block,
void *);
extern bool can_copy_bbs_p (basic_block *, unsigned);
extern void copy_bbs (basic_block *, unsigned, basic_block *,
edge *, unsigned, edge *, struct loop *,
basic_block);
void account_profile_record (struct profile_record *, int);
extern void cfg_layout_initialize (unsigned int);
extern void cfg_layout_finalize (void);
/* Hooks containers. */
extern struct cfg_hooks gimple_cfg_hooks;
extern struct cfg_hooks rtl_cfg_hooks;
extern struct cfg_hooks cfg_layout_rtl_cfg_hooks;
/* Declarations. */
extern enum ir_type current_ir_type (void);
extern void rtl_register_cfg_hooks (void);
extern void cfg_layout_rtl_register_cfg_hooks (void);
extern void gimple_register_cfg_hooks (void);
extern struct cfg_hooks get_cfg_hooks (void);
extern void set_cfg_hooks (struct cfg_hooks);

733
src/include/cfgloop.h Normal file
View File

@ -0,0 +1,733 @@
/* Natural loop functions
Copyright (C) 1987-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GCC_CFGLOOP_H
#define GCC_CFGLOOP_H
#include "basic-block.h"
#include "double-int.h"
#include "bitmap.h"
#include "sbitmap.h"
/* Structure to hold decision about unrolling/peeling. */
enum lpt_dec
{
LPT_NONE,
LPT_PEEL_COMPLETELY,
LPT_PEEL_SIMPLE,
LPT_UNROLL_CONSTANT,
LPT_UNROLL_RUNTIME,
LPT_UNROLL_STUPID
};
struct GTY (()) lpt_decision {
enum lpt_dec decision;
unsigned times;
};
/* The type of extend applied to an IV. */
enum iv_extend_code
{
IV_SIGN_EXTEND,
IV_ZERO_EXTEND,
IV_UNKNOWN_EXTEND
};
/* The structure describing a bound on number of iterations of a loop. */
struct GTY ((chain_next ("%h.next"))) nb_iter_bound {
/* The statement STMT is executed at most ... */
gimple stmt;
/* ... BOUND + 1 times (BOUND must be an unsigned constant).
The + 1 is added for the following reasons:
a) 0 would otherwise be unused, while we would need to care more about
overflows (as MAX + 1 is sometimes produced as the estimate on number
of executions of STMT).
b) it is consistent with the result of number_of_iterations_exit. */
double_int bound;
/* True if the statement will cause the loop to be leaved the (at most)
BOUND + 1-st time it is executed, that is, all the statements after it
are executed at most BOUND times. */
bool is_exit;
/* The next bound in the list. */
struct nb_iter_bound *next;
};
/* Description of the loop exit. */
struct GTY (()) loop_exit {
/* The exit edge. */
edge e;
/* Previous and next exit in the list of the exits of the loop. */
struct loop_exit *prev;
struct loop_exit *next;
/* Next element in the list of loops from that E exits. */
struct loop_exit *next_e;
};
typedef struct loop *loop_p;
/* An integer estimation of the number of iterations. Estimate_state
describes what is the state of the estimation. */
enum loop_estimation
{
/* Estimate was not computed yet. */
EST_NOT_COMPUTED,
/* Estimate is ready. */
EST_AVAILABLE
};
/* Structure to hold information for each natural loop. */
struct GTY ((chain_next ("%h.next"))) loop {
/* Index into loops array. */
int num;
/* Number of loop insns. */
unsigned ninsns;
/* Basic block of loop header. */
basic_block header;
/* Basic block of loop latch. */
basic_block latch;
/* For loop unrolling/peeling decision. */
struct lpt_decision lpt_decision;
/* Average number of executed insns per iteration. */
unsigned av_ninsns;
/* Number of blocks contained within the loop. */
unsigned num_nodes;
/* Superloops of the loop, starting with the outermost loop. */
vec<loop_p, va_gc> *superloops;
/* The first inner (child) loop or NULL if innermost loop. */
struct loop *inner;
/* Link to the next (sibling) loop. */
struct loop *next;
/* Auxiliary info specific to a pass. */
PTR GTY ((skip (""))) aux;
/* The number of times the latch of the loop is executed. This can be an
INTEGER_CST, or a symbolic expression representing the number of
iterations like "N - 1", or a COND_EXPR containing the runtime
conditions under which the number of iterations is non zero.
Don't access this field directly: number_of_latch_executions
computes and caches the computed information in this field. */
tree nb_iterations;
/* An integer guaranteed to be greater or equal to nb_iterations. Only
valid if any_upper_bound is true. */
double_int nb_iterations_upper_bound;
/* An integer giving an estimate on nb_iterations. Unlike
nb_iterations_upper_bound, there is no guarantee that it is at least
nb_iterations. */
double_int nb_iterations_estimate;
bool any_upper_bound;
bool any_estimate;
/* True if the loop can be parallel. */
bool can_be_parallel;
/* True if -Waggressive-loop-optimizations warned about this loop
already. */
bool warned_aggressive_loop_optimizations;
/* An integer estimation of the number of iterations. Estimate_state
describes what is the state of the estimation. */
enum loop_estimation estimate_state;
/* Upper bound on number of iterations of a loop. */
struct nb_iter_bound *bounds;
/* Head of the cyclic list of the exits of the loop. */
struct loop_exit *exits;
};
/* Flags for state of loop structure. */
enum
{
LOOPS_HAVE_PREHEADERS = 1,
LOOPS_HAVE_SIMPLE_LATCHES = 2,
LOOPS_HAVE_MARKED_IRREDUCIBLE_REGIONS = 4,
LOOPS_HAVE_RECORDED_EXITS = 8,
LOOPS_MAY_HAVE_MULTIPLE_LATCHES = 16,
LOOP_CLOSED_SSA = 32,
LOOPS_NEED_FIXUP = 64,
LOOPS_HAVE_FALLTHRU_PREHEADERS = 128
};
#define LOOPS_NORMAL (LOOPS_HAVE_PREHEADERS | LOOPS_HAVE_SIMPLE_LATCHES \
| LOOPS_HAVE_MARKED_IRREDUCIBLE_REGIONS)
#define AVOID_CFG_MODIFICATIONS (LOOPS_MAY_HAVE_MULTIPLE_LATCHES)
/* Structure to hold CFG information about natural loops within a function. */
struct GTY (()) loops {
/* State of loops. */
int state;
/* Array of the loops. */
vec<loop_p, va_gc> *larray;
/* Maps edges to the list of their descriptions as loop exits. Edges
whose sources or destinations have loop_father == NULL (which may
happen during the cfg manipulations) should not appear in EXITS. */
htab_t GTY((param_is (struct loop_exit))) exits;
/* Pointer to root of loop hierarchy tree. */
struct loop *tree_root;
};
/* Loop recognition. */
bool bb_loop_header_p (basic_block);
extern struct loops *flow_loops_find (struct loops *);
extern void disambiguate_loops_with_multiple_latches (void);
extern void flow_loops_free (struct loops *);
extern void flow_loops_dump (FILE *,
void (*)(const struct loop *, FILE *, int), int);
extern void flow_loop_dump (const struct loop *, FILE *,
void (*)(const struct loop *, FILE *, int), int);
struct loop *alloc_loop (void);
extern void flow_loop_free (struct loop *);
int flow_loop_nodes_find (basic_block, struct loop *);
unsigned fix_loop_structure (bitmap changed_bbs);
bool mark_irreducible_loops (void);
void release_recorded_exits (void);
void record_loop_exits (void);
void rescan_loop_exit (edge, bool, bool);
/* Loop data structure manipulation/querying. */
extern void flow_loop_tree_node_add (struct loop *, struct loop *);
extern void flow_loop_tree_node_remove (struct loop *);
extern void add_loop (struct loop *, struct loop *);
extern bool flow_loop_nested_p (const struct loop *, const struct loop *);
extern bool flow_bb_inside_loop_p (const struct loop *, const_basic_block);
extern struct loop * find_common_loop (struct loop *, struct loop *);
struct loop *superloop_at_depth (struct loop *, unsigned);
struct eni_weights_d;
extern unsigned tree_num_loop_insns (struct loop *, struct eni_weights_d *);
extern int num_loop_insns (const struct loop *);
extern int average_num_loop_insns (const struct loop *);
extern unsigned get_loop_level (const struct loop *);
extern bool loop_exit_edge_p (const struct loop *, const_edge);
extern bool loop_exits_to_bb_p (struct loop *, basic_block);
extern bool loop_exits_from_bb_p (struct loop *, basic_block);
extern void mark_loop_exit_edges (void);
extern location_t get_loop_location (struct loop *loop);
/* Loops & cfg manipulation. */
extern basic_block *get_loop_body (const struct loop *);
extern unsigned get_loop_body_with_size (const struct loop *, basic_block *,
unsigned);
extern basic_block *get_loop_body_in_dom_order (const struct loop *);
extern basic_block *get_loop_body_in_bfs_order (const struct loop *);
extern basic_block *get_loop_body_in_custom_order (const struct loop *,
int (*) (const void *, const void *));
extern vec<edge> get_loop_exit_edges (const struct loop *);
extern edge single_exit (const struct loop *);
extern edge single_likely_exit (struct loop *loop);
extern unsigned num_loop_branches (const struct loop *);
extern edge loop_preheader_edge (const struct loop *);
extern edge loop_latch_edge (const struct loop *);
extern void add_bb_to_loop (basic_block, struct loop *);
extern void remove_bb_from_loops (basic_block);
extern void cancel_loop_tree (struct loop *);
extern void delete_loop (struct loop *);
enum
{
CP_SIMPLE_PREHEADERS = 1,
CP_FALLTHRU_PREHEADERS = 2
};
basic_block create_preheader (struct loop *, int);
extern void create_preheaders (int);
extern void force_single_succ_latches (void);
extern void verify_loop_structure (void);
/* Loop analysis. */
extern bool just_once_each_iteration_p (const struct loop *, const_basic_block);
gcov_type expected_loop_iterations_unbounded (const struct loop *);
extern unsigned expected_loop_iterations (const struct loop *);
extern rtx doloop_condition_get (rtx);
void estimate_numbers_of_iterations_loop (struct loop *);
void record_niter_bound (struct loop *, double_int, bool, bool);
bool estimated_loop_iterations (struct loop *, double_int *);
bool max_loop_iterations (struct loop *, double_int *);
HOST_WIDE_INT estimated_loop_iterations_int (struct loop *);
HOST_WIDE_INT max_loop_iterations_int (struct loop *);
bool max_stmt_executions (struct loop *, double_int *);
bool estimated_stmt_executions (struct loop *, double_int *);
HOST_WIDE_INT max_stmt_executions_int (struct loop *);
HOST_WIDE_INT estimated_stmt_executions_int (struct loop *);
/* Loop manipulation. */
extern bool can_duplicate_loop_p (const struct loop *loop);
#define DLTHE_FLAG_UPDATE_FREQ 1 /* Update frequencies in
duplicate_loop_to_header_edge. */
#define DLTHE_RECORD_COPY_NUMBER 2 /* Record copy number in the aux
field of newly create BB. */
#define DLTHE_FLAG_COMPLETTE_PEEL 4 /* Update frequencies expecting
a complete peeling. */
extern edge create_empty_if_region_on_edge (edge, tree);
extern struct loop *create_empty_loop_on_edge (edge, tree, tree, tree, tree,
tree *, tree *, struct loop *);
extern struct loop * duplicate_loop (struct loop *, struct loop *);
extern void copy_loop_info (struct loop *loop, struct loop *target);
extern void duplicate_subloops (struct loop *, struct loop *);
extern bool duplicate_loop_to_header_edge (struct loop *, edge,
unsigned, sbitmap, edge,
vec<edge> *, int);
extern struct loop *loopify (edge, edge,
basic_block, edge, edge, bool,
unsigned, unsigned);
struct loop * loop_version (struct loop *, void *,
basic_block *, unsigned, unsigned, unsigned, bool);
extern bool remove_path (edge);
extern void unloop (struct loop *, bool *, bitmap);
extern void scale_loop_frequencies (struct loop *, int, int);
/* Induction variable analysis. */
/* The description of induction variable. The things are a bit complicated
due to need to handle subregs and extends. The value of the object described
by it can be obtained as follows (all computations are done in extend_mode):
Value in i-th iteration is
delta + mult * extend_{extend_mode} (subreg_{mode} (base + i * step)).
If first_special is true, the value in the first iteration is
delta + mult * base
If extend = UNKNOWN, first_special must be false, delta 0, mult 1 and value is
subreg_{mode} (base + i * step)
The get_iv_value function can be used to obtain these expressions.
??? Add a third mode field that would specify the mode in that inner
computation is done, which would enable it to be different from the
outer one? */
struct rtx_iv
{
/* Its base and step (mode of base and step is supposed to be extend_mode,
see the description above). */
rtx base, step;
/* The type of extend applied to it (IV_SIGN_EXTEND, IV_ZERO_EXTEND,
or IV_UNKNOWN_EXTEND). */
enum iv_extend_code extend;
/* Operations applied in the extended mode. */
rtx delta, mult;
/* The mode it is extended to. */
enum machine_mode extend_mode;
/* The mode the variable iterates in. */
enum machine_mode mode;
/* Whether the first iteration needs to be handled specially. */
unsigned first_special : 1;
};
/* The description of an exit from the loop and of the number of iterations
till we take the exit. */
struct niter_desc
{
/* The edge out of the loop. */
edge out_edge;
/* The other edge leading from the condition. */
edge in_edge;
/* True if we are able to say anything about number of iterations of the
loop. */
bool simple_p;
/* True if the loop iterates the constant number of times. */
bool const_iter;
/* Number of iterations if constant. */
unsigned HOST_WIDEST_INT niter;
/* Assumptions under that the rest of the information is valid. */
rtx assumptions;
/* Assumptions under that the loop ends before reaching the latch,
even if value of niter_expr says otherwise. */
rtx noloop_assumptions;
/* Condition under that the loop is infinite. */
rtx infinite;
/* Whether the comparison is signed. */
bool signed_p;
/* The mode in that niter_expr should be computed. */
enum machine_mode mode;
/* The number of iterations of the loop. */
rtx niter_expr;
};
extern void iv_analysis_loop_init (struct loop *);
extern bool iv_analyze (rtx, rtx, struct rtx_iv *);
extern bool iv_analyze_result (rtx, rtx, struct rtx_iv *);
extern bool iv_analyze_expr (rtx, rtx, enum machine_mode, struct rtx_iv *);
extern rtx get_iv_value (struct rtx_iv *, rtx);
extern bool biv_p (rtx, rtx);
extern void find_simple_exit (struct loop *, struct niter_desc *);
extern void iv_analysis_done (void);
extern struct niter_desc *get_simple_loop_desc (struct loop *loop);
extern void free_simple_loop_desc (struct loop *loop);
static inline struct niter_desc *
simple_loop_desc (struct loop *loop)
{
return (struct niter_desc *) loop->aux;
}
/* Accessors for the loop structures. */
/* Returns the loop with index NUM from current_loops. */
static inline struct loop *
get_loop (unsigned num)
{
return (*current_loops->larray)[num];
}
/* Returns the number of superloops of LOOP. */
static inline unsigned
loop_depth (const struct loop *loop)
{
return vec_safe_length (loop->superloops);
}
/* Returns the loop depth of the loop BB belongs to. */
static inline int
bb_loop_depth (const_basic_block bb)
{
return bb->loop_father ? loop_depth (bb->loop_father) : 0;
}
/* Returns the immediate superloop of LOOP, or NULL if LOOP is the outermost
loop. */
static inline struct loop *
loop_outer (const struct loop *loop)
{
unsigned n = vec_safe_length (loop->superloops);
if (n == 0)
return NULL;
return (*loop->superloops)[n - 1];
}
/* Returns true if LOOP has at least one exit edge. */
static inline bool
loop_has_exit_edges (const struct loop *loop)
{
return loop->exits->next->e != NULL;
}
/* Returns the list of loops in current_loops. */
static inline vec<loop_p, va_gc> *
get_loops (void)
{
if (!current_loops)
return NULL;
return current_loops->larray;
}
/* Returns the number of loops in current_loops (including the removed
ones and the fake loop that forms the root of the loop tree). */
static inline unsigned
number_of_loops (void)
{
if (!current_loops)
return 0;
return vec_safe_length (current_loops->larray);
}
/* Returns true if state of the loops satisfies all properties
described by FLAGS. */
static inline bool
loops_state_satisfies_p (unsigned flags)
{
return (current_loops->state & flags) == flags;
}
/* Sets FLAGS to the loops state. */
static inline void
loops_state_set (unsigned flags)
{
current_loops->state |= flags;
}
/* Clears FLAGS from the loops state. */
static inline void
loops_state_clear (unsigned flags)
{
if (!current_loops)
return;
current_loops->state &= ~flags;
}
/* Loop iterators. */
/* Flags for loop iteration. */
enum li_flags
{
LI_INCLUDE_ROOT = 1, /* Include the fake root of the loop tree. */
LI_FROM_INNERMOST = 2, /* Iterate over the loops in the reverse order,
starting from innermost ones. */
LI_ONLY_INNERMOST = 4 /* Iterate only over innermost loops. */
};
/* The iterator for loops. */
typedef struct
{
/* The list of loops to visit. */
vec<int> to_visit;
/* The index of the actual loop. */
unsigned idx;
} loop_iterator;
static inline void
fel_next (loop_iterator *li, loop_p *loop)
{
int anum;
while (li->to_visit.iterate (li->idx, &anum))
{
li->idx++;
*loop = get_loop (anum);
if (*loop)
return;
}
li->to_visit.release ();
*loop = NULL;
}
static inline void
fel_init (loop_iterator *li, loop_p *loop, unsigned flags)
{
struct loop *aloop;
unsigned i;
int mn;
li->idx = 0;
if (!current_loops)
{
li->to_visit.create (0);
*loop = NULL;
return;
}
li->to_visit.create (number_of_loops ());
mn = (flags & LI_INCLUDE_ROOT) ? 0 : 1;
if (flags & LI_ONLY_INNERMOST)
{
for (i = 0; vec_safe_iterate (current_loops->larray, i, &aloop); i++)
if (aloop != NULL
&& aloop->inner == NULL
&& aloop->num >= mn)
li->to_visit.quick_push (aloop->num);
}
else if (flags & LI_FROM_INNERMOST)
{
/* Push the loops to LI->TO_VISIT in postorder. */
for (aloop = current_loops->tree_root;
aloop->inner != NULL;
aloop = aloop->inner)
continue;
while (1)
{
if (aloop->num >= mn)
li->to_visit.quick_push (aloop->num);
if (aloop->next)
{
for (aloop = aloop->next;
aloop->inner != NULL;
aloop = aloop->inner)
continue;
}
else if (!loop_outer (aloop))
break;
else
aloop = loop_outer (aloop);
}
}
else
{
/* Push the loops to LI->TO_VISIT in preorder. */
aloop = current_loops->tree_root;
while (1)
{
if (aloop->num >= mn)
li->to_visit.quick_push (aloop->num);
if (aloop->inner != NULL)
aloop = aloop->inner;
else
{
while (aloop != NULL && aloop->next == NULL)
aloop = loop_outer (aloop);
if (aloop == NULL)
break;
aloop = aloop->next;
}
}
}
fel_next (li, loop);
}
#define FOR_EACH_LOOP(LI, LOOP, FLAGS) \
for (fel_init (&(LI), &(LOOP), FLAGS); \
(LOOP); \
fel_next (&(LI), &(LOOP)))
#define FOR_EACH_LOOP_BREAK(LI) \
{ \
(LI).to_visit.release (); \
break; \
}
/* The properties of the target. */
struct target_cfgloop {
/* Number of available registers. */
unsigned x_target_avail_regs;
/* Number of available registers that are call-clobbered. */
unsigned x_target_clobbered_regs;
/* Number of registers reserved for temporary expressions. */
unsigned x_target_res_regs;
/* The cost for register when there still is some reserve, but we are
approaching the number of available registers. */
unsigned x_target_reg_cost[2];
/* The cost for register when we need to spill. */
unsigned x_target_spill_cost[2];
};
extern struct target_cfgloop default_target_cfgloop;
#if SWITCHABLE_TARGET
extern struct target_cfgloop *this_target_cfgloop;
#else
#define this_target_cfgloop (&default_target_cfgloop)
#endif
#define target_avail_regs \
(this_target_cfgloop->x_target_avail_regs)
#define target_clobbered_regs \
(this_target_cfgloop->x_target_clobbered_regs)
#define target_res_regs \
(this_target_cfgloop->x_target_res_regs)
#define target_reg_cost \
(this_target_cfgloop->x_target_reg_cost)
#define target_spill_cost \
(this_target_cfgloop->x_target_spill_cost)
/* Register pressure estimation for induction variable optimizations & loop
invariant motion. */
extern unsigned estimate_reg_pressure_cost (unsigned, unsigned, bool, bool);
extern void init_set_costs (void);
/* Loop optimizer initialization. */
extern void loop_optimizer_init (unsigned);
extern void loop_optimizer_finalize (void);
/* Optimization passes. */
extern void unswitch_loops (void);
enum
{
UAP_PEEL = 1, /* Enables loop peeling. */
UAP_UNROLL = 2, /* Enables unrolling of loops if it seems profitable. */
UAP_UNROLL_ALL = 4 /* Enables unrolling of all loops. */
};
extern void unroll_and_peel_loops (int);
extern void doloop_optimize_loops (void);
extern void move_loop_invariants (void);
extern bool finite_loop_p (struct loop *);
extern void scale_loop_profile (struct loop *loop, int scale, gcov_type iteration_bound);
extern vec<basic_block> get_loop_hot_path (const struct loop *loop);
/* Returns the outermost loop of the loop nest that contains LOOP.*/
static inline struct loop *
loop_outermost (struct loop *loop)
{
unsigned n = vec_safe_length (loop->superloops);
if (n <= 1)
return loop;
return (*loop->superloops)[1];
}
#endif /* GCC_CFGLOOP_H */

1371
src/include/cgraph.h Normal file

File diff suppressed because it is too large Load Diff

105
src/include/cif-code.def Normal file
View File

@ -0,0 +1,105 @@
/* This file contains the definitions of the cgraph_inline_failed_t
enums used in GCC.
Copyright (C) 2008-2013 Free Software Foundation, Inc.
Contributed by Doug Kwan <dougkwan@google.com>
This file is part of GCC.
GCC is free software you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
/* The format of this file is
DEFCIFCODE(code, string).
Where symbol is the enumeration name without the ``''.
The argument STRING is a explain the failure. Except for OK,
which is a NULL pointer. */
/* Inlining successful. This must be the first code. */
DEFCIFCODE(OK , NULL)
/* Inlining failed for an unspecified reason. */
DEFCIFCODE(UNSPECIFIED , "")
/* Function has not be considered for inlining. This is the code for
functions that have not been rejected for inlining yet. */
DEFCIFCODE(FUNCTION_NOT_CONSIDERED, N_("function not considered for inlining"))
/* Inlining failed owing to unavailable function body. */
DEFCIFCODE(BODY_NOT_AVAILABLE, N_("function body not available"))
/* Extern inline function that has been redefined. */
DEFCIFCODE(REDEFINED_EXTERN_INLINE,
N_("redefined extern inline functions are not considered for "
"inlining"))
/* Function is not inlinable. */
DEFCIFCODE(FUNCTION_NOT_INLINABLE, N_("function not inlinable"))
/* Function is not overwritable. */
DEFCIFCODE(OVERWRITABLE, N_("function body can be overwritten at link time"))
/* Function is not an inlining candidate. */
DEFCIFCODE(FUNCTION_NOT_INLINE_CANDIDATE, N_("function not inline candidate"))
/* Inlining failed because of various limit parameters. */
DEFCIFCODE(LARGE_FUNCTION_GROWTH_LIMIT,
N_("--param large-function-growth limit reached"))
DEFCIFCODE(LARGE_STACK_FRAME_GROWTH_LIMIT,
N_("--param large-stack-frame-growth limit reached"))
DEFCIFCODE(MAX_INLINE_INSNS_SINGLE_LIMIT,
N_("--param max-inline-insns-single limit reached"))
DEFCIFCODE(MAX_INLINE_INSNS_AUTO_LIMIT,
N_("--param max-inline-insns-auto limit reached"))
DEFCIFCODE(INLINE_UNIT_GROWTH_LIMIT,
N_("--param inline-unit-growth limit reached"))
/* Recursive inlining. */
DEFCIFCODE(RECURSIVE_INLINING, N_("recursive inlining"))
/* Call is unlikely. */
DEFCIFCODE(UNLIKELY_CALL, N_("call is unlikely and code size would grow"))
/* Function is not declared as inline. */
DEFCIFCODE(NOT_DECLARED_INLINED,
N_("function not declared inline and code size would grow"))
/* Inlining suppressed due to size optimization. */
DEFCIFCODE(OPTIMIZING_FOR_SIZE,
N_("optimizing for size and code size would grow"))
/* Caller and callee disagree on the arguments. */
DEFCIFCODE(MISMATCHED_ARGUMENTS, N_("mismatched arguments"))
/* Call was originally indirect. */
DEFCIFCODE(ORIGINALLY_INDIRECT_CALL,
N_("originally indirect function call not considered for inlining"))
/* Ths edge represents an indirect edge with a yet-undetermined callee . */
DEFCIFCODE(INDIRECT_UNKNOWN_CALL,
N_("indirect function call with a yet undetermined callee"))
/* We can't inline different EH personalities together. */
DEFCIFCODE(EH_PERSONALITY, N_("exception handling personality mismatch"))
/* We can't inline if the callee can throw non-call exceptions but the
caller cannot. */
DEFCIFCODE(NON_CALL_EXCEPTIONS, N_("non-call exception handling mismatch"))
/* We can't inline because of mismatched target specific options. */
DEFCIFCODE(TARGET_OPTION_MISMATCH, N_("target specific option mismatch"))
/* We can't inline because of mismatched optimization levels. */
DEFCIFCODE(OPTIMIZATION_MISMATCH, N_("optimization level attribute mismatch"))

10
src/include/config.h Normal file
View File

@ -0,0 +1,10 @@
#ifndef GCC_CONFIG_H
#define GCC_CONFIG_H
#ifdef GENERATOR_FILE
#error config.h is for the host, not build, machine.
#endif
#include "auto-host.h"
#ifdef IN_GCC
# include "ansidecl.h"
#endif
#endif /* GCC_CONFIG_H */

View File

@ -0,0 +1,68 @@
/* Definitions needed when using stabs embedded in ELF sections.
Copyright (C) 1999-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GCC is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
Under Section 7 of GPL version 3, you are granted additional
permissions described in the GCC Runtime Library Exception, version
3.1, as published by the Free Software Foundation.
You should have received a copy of the GNU General Public License and
a copy of the GCC Runtime Library Exception along with this program;
see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
<http://www.gnu.org/licenses/>. */
/* This file may be included by any ELF target which wishes to
support -gstabs generating stabs in sections, as produced by gas
and understood by gdb. */
#ifndef GCC_DBX_ELF_H
#define GCC_DBX_ELF_H
/* Output DBX (stabs) debugging information if doing -gstabs. */
#define DBX_DEBUGGING_INFO 1
/* Make LBRAC and RBRAC addresses relative to the start of the
function. The native Solaris stabs debugging format works this
way, gdb expects it, and it reduces the number of relocation
entries... */
#define DBX_BLOCKS_FUNCTION_RELATIVE 1
/* ... but, to make this work, functions must appear prior to line info. */
#define DBX_FUNCTION_FIRST
/* When generating stabs debugging, use N_BINCL entries. */
#define DBX_USE_BINCL
/* There is no limit to the length of stabs strings. */
#ifndef DBX_CONTIN_LENGTH
#define DBX_CONTIN_LENGTH 0
#endif
/* Like block addresses, stabs line numbers are relative to the
current function. */
#define DBX_LINES_FUNCTION_RELATIVE 1
/* Generate a blank trailing N_SO to mark the end of the .o file, since
we can't depend upon the linker to mark .o file boundaries with
embedded stabs. */
#define DBX_OUTPUT_NULL_N_SO_AT_MAIN_SOURCE_FILE_END
#endif /* ! GCC_DBX_ELF_H */

435
src/include/config/elfos.h Normal file
View File

@ -0,0 +1,435 @@
/* elfos.h -- operating system specific defines to be used when
targeting GCC for some generic ELF system
Copyright (C) 1991-2013 Free Software Foundation, Inc.
Based on svr4.h contributed by Ron Guilmette (rfg@netcom.com).
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GCC is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
Under Section 7 of GPL version 3, you are granted additional
permissions described in the GCC Runtime Library Exception, version
3.1, as published by the Free Software Foundation.
You should have received a copy of the GNU General Public License and
a copy of the GCC Runtime Library Exception along with this program;
see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
<http://www.gnu.org/licenses/>. */
#define TARGET_OBJFMT_CPP_BUILTINS() \
do \
{ \
builtin_define ("__ELF__"); \
} \
while (0)
/* Define a symbol indicating that we are using elfos.h.
Some CPU specific configuration files use this. */
#define USING_ELFOS_H
/* The prefix to add to user-visible assembler symbols.
For ELF systems the convention is *not* to prepend a leading
underscore onto user-level symbol names. */
#undef USER_LABEL_PREFIX
#define USER_LABEL_PREFIX ""
/* The biggest alignment supported by ELF in bits. 32-bit ELF
supports section alignment up to (0x80000000 * 8), while
64-bit ELF supports (0x8000000000000000 * 8). If this macro
is not defined, the default is the largest alignment supported
by 32-bit ELF and representable on a 32-bit host. Use this
macro to limit the alignment which can be specified using
the `__attribute__ ((aligned (N)))' construct. */
#ifndef MAX_OFILE_ALIGNMENT
#define MAX_OFILE_ALIGNMENT (((unsigned int) 1 << 28) * 8)
#endif
/* Use periods rather than dollar signs in special g++ assembler names. */
#define NO_DOLLAR_IN_LABEL
/* Writing `int' for a bit-field forces int alignment for the structure. */
#ifndef PCC_BITFIELD_TYPE_MATTERS
#define PCC_BITFIELD_TYPE_MATTERS 1
#endif
/* All ELF targets can support DWARF-2. */
#define DWARF2_DEBUGGING_INFO 1
/* The GNU tools operate better with dwarf2, and it is required by some
psABI's. Since we don't have any native tools to be compatible with,
default to dwarf2. */
#ifndef PREFERRED_DEBUGGING_TYPE
#define PREFERRED_DEBUGGING_TYPE DWARF2_DEBUG
#endif
/* All SVR4 targets use the ELF object file format. */
#define OBJECT_FORMAT_ELF
/* Output #ident as a .ident. */
#undef TARGET_ASM_OUTPUT_IDENT
#define TARGET_ASM_OUTPUT_IDENT default_asm_output_ident_directive
#undef SET_ASM_OP
#define SET_ASM_OP "\t.set\t"
/* Most svr4 assemblers want a .file directive at the beginning of
their input file. */
#define TARGET_ASM_FILE_START_FILE_DIRECTIVE true
/* This is how to allocate empty space in some section. The .zero
pseudo-op is used for this on most svr4 assemblers. */
#define SKIP_ASM_OP "\t.zero\t"
#undef ASM_OUTPUT_SKIP
#define ASM_OUTPUT_SKIP(FILE, SIZE) \
fprintf ((FILE), "%s"HOST_WIDE_INT_PRINT_UNSIGNED"\n",\
SKIP_ASM_OP, (SIZE))
/* This is how to store into the string LABEL
the symbol_ref name of an internal numbered label where
PREFIX is the class of label and NUM is the number within the class.
This is suitable for output with `assemble_name'.
For most svr4 systems, the convention is that any symbol which begins
with a period is not put into the linker symbol table by the assembler. */
#undef ASM_GENERATE_INTERNAL_LABEL
#define ASM_GENERATE_INTERNAL_LABEL(LABEL, PREFIX, NUM) \
do \
{ \
char *__p; \
(LABEL)[0] = '*'; \
(LABEL)[1] = '.'; \
__p = stpcpy (&(LABEL)[2], PREFIX); \
sprint_ul (__p, (unsigned long) (NUM)); \
} \
while (0)
/* Output the label which precedes a jumptable. Note that for all svr4
systems where we actually generate jumptables (which is to say every
svr4 target except i386, where we use casesi instead) we put the jump-
tables into the .rodata section and since other stuff could have been
put into the .rodata section prior to any given jumptable, we have to
make sure that the location counter for the .rodata section gets pro-
perly re-aligned prior to the actual beginning of the jump table. */
#undef ALIGN_ASM_OP
#define ALIGN_ASM_OP "\t.align\t"
#ifndef ASM_OUTPUT_BEFORE_CASE_LABEL
#define ASM_OUTPUT_BEFORE_CASE_LABEL(FILE, PREFIX, NUM, TABLE) \
ASM_OUTPUT_ALIGN ((FILE), 2);
#endif
#undef ASM_OUTPUT_CASE_LABEL
#define ASM_OUTPUT_CASE_LABEL(FILE, PREFIX, NUM, JUMPTABLE) \
do \
{ \
ASM_OUTPUT_BEFORE_CASE_LABEL (FILE, PREFIX, NUM, JUMPTABLE) \
(*targetm.asm_out.internal_label) (FILE, PREFIX, NUM); \
} \
while (0)
/* The standard SVR4 assembler seems to require that certain builtin
library routines (e.g. .udiv) be explicitly declared as .globl
in each assembly file where they are referenced. */
#define ASM_OUTPUT_EXTERNAL_LIBCALL(FILE, FUN) \
(*targetm.asm_out.globalize_label) (FILE, XSTR (FUN, 0))
/* This says how to output assembler code to declare an
uninitialized external linkage data object. Under SVR4,
the linker seems to want the alignment of data objects
to depend on their types. We do exactly that here. */
#define COMMON_ASM_OP "\t.comm\t"
#undef ASM_OUTPUT_ALIGNED_COMMON
#define ASM_OUTPUT_ALIGNED_COMMON(FILE, NAME, SIZE, ALIGN) \
do \
{ \
fprintf ((FILE), "%s", COMMON_ASM_OP); \
assemble_name ((FILE), (NAME)); \
fprintf ((FILE), ","HOST_WIDE_INT_PRINT_UNSIGNED",%u\n", \
(SIZE), (ALIGN) / BITS_PER_UNIT); \
} \
while (0)
/* This says how to output assembler code to declare an
uninitialized internal linkage data object. Under SVR4,
the linker seems to want the alignment of data objects
to depend on their types. We do exactly that here. */
#define LOCAL_ASM_OP "\t.local\t"
#undef ASM_OUTPUT_ALIGNED_LOCAL
#define ASM_OUTPUT_ALIGNED_LOCAL(FILE, NAME, SIZE, ALIGN) \
do \
{ \
fprintf ((FILE), "%s", LOCAL_ASM_OP); \
assemble_name ((FILE), (NAME)); \
fprintf ((FILE), "\n"); \
ASM_OUTPUT_ALIGNED_COMMON (FILE, NAME, SIZE, ALIGN); \
} \
while (0)
/* This is the pseudo-op used to generate a contiguous sequence of byte
values from a double-quoted string WITHOUT HAVING A TERMINATING NUL
AUTOMATICALLY APPENDED. This is the same for most svr4 assemblers. */
#undef ASCII_DATA_ASM_OP
#define ASCII_DATA_ASM_OP "\t.ascii\t"
/* Support a read-only data section. */
#define READONLY_DATA_SECTION_ASM_OP "\t.section\t.rodata"
/* On svr4, we *do* have support for the .init and .fini sections, and we
can put stuff in there to be executed before and after `main'. We let
crtstuff.c and other files know this by defining the following symbols.
The definitions say how to change sections to the .init and .fini
sections. This is the same for all known svr4 assemblers. */
#define INIT_SECTION_ASM_OP "\t.section\t.init"
#define FINI_SECTION_ASM_OP "\t.section\t.fini"
/* Output assembly directive to move to the beginning of current section. */
#ifdef HAVE_GAS_SUBSECTION_ORDERING
# define ASM_SECTION_START_OP "\t.subsection\t-1"
# define ASM_OUTPUT_SECTION_START(FILE) \
fprintf ((FILE), "%s\n", ASM_SECTION_START_OP)
#endif
#define MAKE_DECL_ONE_ONLY(DECL) (DECL_WEAK (DECL) = 1)
/* Switch into a generic section. */
#define TARGET_ASM_NAMED_SECTION default_elf_asm_named_section
#undef TARGET_ASM_SELECT_RTX_SECTION
#define TARGET_ASM_SELECT_RTX_SECTION default_elf_select_rtx_section
#undef TARGET_ASM_SELECT_SECTION
#define TARGET_ASM_SELECT_SECTION default_elf_select_section
#undef TARGET_HAVE_SWITCHABLE_BSS_SECTIONS
#define TARGET_HAVE_SWITCHABLE_BSS_SECTIONS true
/* Define the strings used for the special svr4 .type and .size directives.
These strings generally do not vary from one system running svr4 to
another, but if a given system (e.g. m88k running svr) needs to use
different pseudo-op names for these, they may be overridden in the
file which includes this one. */
#define TYPE_ASM_OP "\t.type\t"
#define SIZE_ASM_OP "\t.size\t"
/* This is how we tell the assembler that a symbol is weak. */
#define ASM_WEAKEN_LABEL(FILE, NAME) \
do \
{ \
fputs ("\t.weak\t", (FILE)); \
assemble_name ((FILE), (NAME)); \
fputc ('\n', (FILE)); \
} \
while (0)
/* The following macro defines the format used to output the second
operand of the .type assembler directive. Different svr4 assemblers
expect various different forms for this operand. The one given here
is just a default. You may need to override it in your machine-
specific tm.h file (depending upon the particulars of your assembler). */
#define TYPE_OPERAND_FMT "@%s"
/* Write the extra assembler code needed to declare a function's result.
Most svr4 assemblers don't require any special declaration of the
result value, but there are exceptions. */
#ifndef ASM_DECLARE_RESULT
#define ASM_DECLARE_RESULT(FILE, RESULT)
#endif
/* These macros generate the special .type and .size directives which
are used to set the corresponding fields of the linker symbol table
entries in an ELF object file under SVR4. These macros also output
the starting labels for the relevant functions/objects. */
/* Write the extra assembler code needed to declare a function properly.
Some svr4 assemblers need to also have something extra said about the
function's return value. We allow for that here. */
#ifndef ASM_DECLARE_FUNCTION_NAME
#define ASM_DECLARE_FUNCTION_NAME(FILE, NAME, DECL) \
do \
{ \
ASM_OUTPUT_TYPE_DIRECTIVE (FILE, NAME, "function"); \
ASM_DECLARE_RESULT (FILE, DECL_RESULT (DECL)); \
ASM_OUTPUT_FUNCTION_LABEL (FILE, NAME, DECL); \
} \
while (0)
#endif
/* Write the extra assembler code needed to declare an object properly. */
#ifdef HAVE_GAS_GNU_UNIQUE_OBJECT
#define USE_GNU_UNIQUE_OBJECT flag_gnu_unique
#else
#define USE_GNU_UNIQUE_OBJECT 0
#endif
#define ASM_DECLARE_OBJECT_NAME(FILE, NAME, DECL) \
do \
{ \
HOST_WIDE_INT size; \
\
/* For template static data member instantiations or \
inline fn local statics and their guard variables, use \
gnu_unique_object so that they will be combined even under \
RTLD_LOCAL. Don't use gnu_unique_object for typeinfo, \
vtables and other read-only artificial decls. */ \
if (USE_GNU_UNIQUE_OBJECT && DECL_ONE_ONLY (DECL) \
&& (!DECL_ARTIFICIAL (DECL) || !TREE_READONLY (DECL))) \
ASM_OUTPUT_TYPE_DIRECTIVE (FILE, NAME, "gnu_unique_object"); \
else \
ASM_OUTPUT_TYPE_DIRECTIVE (FILE, NAME, "object"); \
\
size_directive_output = 0; \
if (!flag_inhibit_size_directive \
&& (DECL) && DECL_SIZE (DECL)) \
{ \
size_directive_output = 1; \
size = int_size_in_bytes (TREE_TYPE (DECL)); \
ASM_OUTPUT_SIZE_DIRECTIVE (FILE, NAME, size); \
} \
\
ASM_OUTPUT_LABEL (FILE, NAME); \
} \
while (0)
/* Output the size directive for a decl in rest_of_decl_compilation
in the case where we did not do so before the initializer.
Once we find the error_mark_node, we know that the value of
size_directive_output was set
by ASM_DECLARE_OBJECT_NAME when it was run for the same decl. */
#undef ASM_FINISH_DECLARE_OBJECT
#define ASM_FINISH_DECLARE_OBJECT(FILE, DECL, TOP_LEVEL, AT_END)\
do \
{ \
const char *name = XSTR (XEXP (DECL_RTL (DECL), 0), 0); \
HOST_WIDE_INT size; \
\
if (!flag_inhibit_size_directive \
&& DECL_SIZE (DECL) \
&& ! AT_END && TOP_LEVEL \
&& DECL_INITIAL (DECL) == error_mark_node \
&& !size_directive_output) \
{ \
size_directive_output = 1; \
size = int_size_in_bytes (TREE_TYPE (DECL)); \
ASM_OUTPUT_SIZE_DIRECTIVE (FILE, name, size); \
} \
} \
while (0)
/* This is how to declare the size of a function. */
#ifndef ASM_DECLARE_FUNCTION_SIZE
#define ASM_DECLARE_FUNCTION_SIZE(FILE, FNAME, DECL) \
do \
{ \
if (!flag_inhibit_size_directive) \
ASM_OUTPUT_MEASURED_SIZE (FILE, FNAME); \
} \
while (0)
#endif
/* A table of bytes codes used by the ASM_OUTPUT_ASCII and
ASM_OUTPUT_LIMITED_STRING macros. Each byte in the table
corresponds to a particular byte value [0..255]. For any
given byte value, if the value in the corresponding table
position is zero, the given character can be output directly.
If the table value is 1, the byte must be output as a \ooo
octal escape. If the tables value is anything else, then the
byte value should be output as a \ followed by the value
in the table. Note that we can use standard UN*X escape
sequences for many control characters, but we don't use
\a to represent BEL because some svr4 assemblers (e.g. on
the i386) don't know about that. Also, we don't use \v
since some versions of gas, such as 2.2 did not accept it. */
#define ELF_ASCII_ESCAPES \
"\1\1\1\1\1\1\1\1btn\1fr\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\
\0\0\"\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\\\0\0\0\
\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\1\
\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\
\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\
\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\
\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1\1"
/* Some svr4 assemblers have a limit on the number of characters which
can appear in the operand of a .string directive. If your assembler
has such a limitation, you should define STRING_LIMIT to reflect that
limit. Note that at least some svr4 assemblers have a limit on the
actual number of bytes in the double-quoted string, and that they
count each character in an escape sequence as one byte. Thus, an
escape sequence like \377 would count as four bytes.
If your target assembler doesn't support the .string directive, you
should define this to zero.
*/
#define ELF_STRING_LIMIT ((unsigned) 256)
#define STRING_ASM_OP "\t.string\t"
/* The routine used to output NUL terminated strings. We use a special
version of this for most svr4 targets because doing so makes the
generated assembly code more compact (and thus faster to assemble)
as well as more readable, especially for targets like the i386
(where the only alternative is to output character sequences as
comma separated lists of numbers). */
#define ASM_OUTPUT_LIMITED_STRING(FILE, STR) \
default_elf_asm_output_limited_string ((FILE), (STR))
/* The routine used to output sequences of byte values. We use a special
version of this for most svr4 targets because doing so makes the
generated assembly code more compact (and thus faster to assemble)
as well as more readable. Note that if we find subparts of the
character sequence which end with NUL (and which are shorter than
STRING_LIMIT) we output those using ASM_OUTPUT_LIMITED_STRING. */
#undef ASM_OUTPUT_ASCII
#define ASM_OUTPUT_ASCII(FILE, STR, LENGTH) \
default_elf_asm_output_ascii ((FILE), (STR), (LENGTH));
/* Allow the use of the -frecord-gcc-switches switch via the
elf_record_gcc_switches function defined in varasm.c. */
#undef TARGET_ASM_RECORD_GCC_SWITCHES
#define TARGET_ASM_RECORD_GCC_SWITCHES elf_record_gcc_switches
/* A C statement (sans semicolon) to output to the stdio stream STREAM
any text necessary for declaring the name of an external symbol
named NAME which is referenced in this compilation but not defined.
It is needed to properly support non-default visibility. */
#ifndef ASM_OUTPUT_EXTERNAL
#define ASM_OUTPUT_EXTERNAL(FILE, DECL, NAME) \
default_elf_asm_output_external (FILE, DECL, NAME)
#endif

View File

@ -0,0 +1,55 @@
/* Definitions for <stdint.h> types on systems using GNU libc or uClibc.
Copyright (C) 2008-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GCC is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
Under Section 7 of GPL version 3, you are granted additional
permissions described in the GCC Runtime Library Exception, version
3.1, as published by the Free Software Foundation.
You should have received a copy of the GNU General Public License and
a copy of the GCC Runtime Library Exception along with this program;
see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
<http://www.gnu.org/licenses/>. */
#define SIG_ATOMIC_TYPE "int"
#define INT8_TYPE "signed char"
#define INT16_TYPE "short int"
#define INT32_TYPE "int"
#define INT64_TYPE (LONG_TYPE_SIZE == 64 ? "long int" : "long long int")
#define UINT8_TYPE "unsigned char"
#define UINT16_TYPE "short unsigned int"
#define UINT32_TYPE "unsigned int"
#define UINT64_TYPE (LONG_TYPE_SIZE == 64 ? "long unsigned int" : "long long unsigned int")
#define INT_LEAST8_TYPE "signed char"
#define INT_LEAST16_TYPE "short int"
#define INT_LEAST32_TYPE "int"
#define INT_LEAST64_TYPE (LONG_TYPE_SIZE == 64 ? "long int" : "long long int")
#define UINT_LEAST8_TYPE "unsigned char"
#define UINT_LEAST16_TYPE "short unsigned int"
#define UINT_LEAST32_TYPE "unsigned int"
#define UINT_LEAST64_TYPE (LONG_TYPE_SIZE == 64 ? "long unsigned int" : "long long unsigned int")
#define INT_FAST8_TYPE "signed char"
#define INT_FAST16_TYPE (LONG_TYPE_SIZE == 64 ? "long int" : "int")
#define INT_FAST32_TYPE (LONG_TYPE_SIZE == 64 ? "long int" : "int")
#define INT_FAST64_TYPE (LONG_TYPE_SIZE == 64 ? "long int" : "long long int")
#define UINT_FAST8_TYPE "unsigned char"
#define UINT_FAST16_TYPE (LONG_TYPE_SIZE == 64 ? "long unsigned int" : "unsigned int")
#define UINT_FAST32_TYPE (LONG_TYPE_SIZE == 64 ? "long unsigned int" : "unsigned int")
#define UINT_FAST64_TYPE (LONG_TYPE_SIZE == 64 ? "long unsigned int" : "long long unsigned int")
#define INTPTR_TYPE (LONG_TYPE_SIZE == 64 ? "long int" : "int")
#define UINTPTR_TYPE (LONG_TYPE_SIZE == 64 ? "long unsigned int" : "unsigned int")

View File

@ -0,0 +1,123 @@
/* Definitions for systems using, at least optionally, a GNU
(glibc-based) userspace or other userspace with libc derived from
glibc (e.g. uClibc) or for which similar specs are appropriate.
Copyright (C) 1995-2013 Free Software Foundation, Inc.
Contributed by Eric Youngdale.
Modified for stabs-in-ELF by H.J. Lu (hjl@lucon.org).
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GCC is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
Under Section 7 of GPL version 3, you are granted additional
permissions described in the GCC Runtime Library Exception, version
3.1, as published by the Free Software Foundation.
You should have received a copy of the GNU General Public License and
a copy of the GCC Runtime Library Exception along with this program;
see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
<http://www.gnu.org/licenses/>. */
/* Don't assume anything about the header files. */
#define NO_IMPLICIT_EXTERN_C
#undef ASM_APP_ON
#define ASM_APP_ON "#APP\n"
#undef ASM_APP_OFF
#define ASM_APP_OFF "#NO_APP\n"
/* Provide a STARTFILE_SPEC appropriate for GNU userspace. Here we add
the GNU userspace magical crtbegin.o file (see crtstuff.c) which
provides part of the support for getting C++ file-scope static
object constructed before entering `main'. */
#if defined HAVE_LD_PIE
#define GNU_USER_TARGET_STARTFILE_SPEC \
"%{!shared: %{pg|p|profile:gcrt1.o%s;pie:Scrt1.o%s;:crt1.o%s}} \
crti.o%s %{static:crtbeginT.o%s;shared|pie:crtbeginS.o%s;:crtbegin.o%s}"
#else
#define GNU_USER_TARGET_STARTFILE_SPEC \
"%{!shared: %{pg|p|profile:gcrt1.o%s;:crt1.o%s}} \
crti.o%s %{static:crtbeginT.o%s;shared|pie:crtbeginS.o%s;:crtbegin.o%s}"
#endif
#undef STARTFILE_SPEC
#define STARTFILE_SPEC GNU_USER_TARGET_STARTFILE_SPEC
/* Provide a ENDFILE_SPEC appropriate for GNU userspace. Here we tack on
the GNU userspace magical crtend.o file (see crtstuff.c) which
provides part of the support for getting C++ file-scope static
object constructed before entering `main', followed by a normal
GNU userspace "finalizer" file, `crtn.o'. */
#define GNU_USER_TARGET_ENDFILE_SPEC \
"%{shared|pie:crtendS.o%s;:crtend.o%s} crtn.o%s"
#undef ENDFILE_SPEC
#define ENDFILE_SPEC GNU_USER_TARGET_ENDFILE_SPEC
/* This is for -profile to use -lc_p instead of -lc. */
#define GNU_USER_TARGET_CC1_SPEC "%{profile:-p}"
#ifndef CC1_SPEC
#define CC1_SPEC GNU_USER_TARGET_CC1_SPEC
#endif
/* The GNU C++ standard library requires that these macros be defined. */
#undef CPLUSPLUS_CPP_SPEC
#define CPLUSPLUS_CPP_SPEC "-D_GNU_SOURCE %(cpp)"
#define GNU_USER_TARGET_LIB_SPEC \
"%{pthread:-lpthread} \
%{shared:-lc} \
%{!shared:%{mieee-fp:-lieee} %{profile:-lc_p}%{!profile:-lc}}"
#undef LIB_SPEC
#define LIB_SPEC GNU_USER_TARGET_LIB_SPEC
#if defined(HAVE_LD_EH_FRAME_HDR)
#define LINK_EH_SPEC "%{!static:--eh-frame-hdr} "
#endif
#undef LINK_GCC_C_SEQUENCE_SPEC
#define LINK_GCC_C_SEQUENCE_SPEC \
"%{static:--start-group} %G %L %{static:--end-group}%{!static:%G}"
/* Use --as-needed -lgcc_s for eh support. */
#ifdef HAVE_LD_AS_NEEDED
#define USE_LD_AS_NEEDED 1
#endif
#define TARGET_POSIX_IO
#define TARGET_C99_FUNCTIONS 1
#define TARGET_HAS_SINCOS 1
/* Link -lasan early on the command line. For -static-libasan, don't link
it for -shared link, the executable should be compiled with -static-libasan
in that case, and for executable link link with --{,no-}whole-archive around
it to force everything into the executable. And similarly for -ltsan. */
#if defined(HAVE_LD_STATIC_DYNAMIC)
#undef LIBASAN_EARLY_SPEC
#define LIBASAN_EARLY_SPEC "%{!shared:libasan_preinit%O%s} " \
"%{static-libasan:%{!shared:" \
LD_STATIC_OPTION " --whole-archive -lasan --no-whole-archive " \
LD_DYNAMIC_OPTION "}}%{!static-libasan:-lasan}"
#undef LIBTSAN_EARLY_SPEC
#define LIBTSAN_EARLY_SPEC "%{static-libtsan:%{!shared:" \
LD_STATIC_OPTION " --whole-archive -ltsan --no-whole-archive " \
LD_DYNAMIC_OPTION "}}%{!static-libtsan:-ltsan}"
#endif
/* Additional libraries needed by -static-libasan. */
#undef STATIC_LIBASAN_LIBS
#define STATIC_LIBASAN_LIBS "-ldl -lpthread"
/* Additional libraries needed by -static-libtsan. */
#undef STATIC_LIBTSAN_LIBS
#define STATIC_LIBTSAN_LIBS "-ldl -lpthread"

View File

@ -0,0 +1,91 @@
/* Definitions for AT&T assembler syntax for the Intel 80386.
Copyright (C) 1988-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GCC is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
Under Section 7 of GPL version 3, you are granted additional
permissions described in the GCC Runtime Library Exception, version
3.1, as published by the Free Software Foundation.
You should have received a copy of the GNU General Public License and
a copy of the GCC Runtime Library Exception along with this program;
see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
<http://www.gnu.org/licenses/>. */
/* Define the syntax of instructions and addresses. */
/* Prefix for internally generated assembler labels. */
#define LPREFIX ".L"
/* Assembler pseudos to introduce constants of various size. */
#define ASM_BYTE "\t.byte\t"
#define ASM_SHORT "\t.value\t"
#define ASM_LONG "\t.long\t"
#define ASM_QUAD "\t.quad\t" /* Should not be used for 32bit compilation. */
/* How to output an ASCII string constant. */
#undef ASM_OUTPUT_ASCII
#define ASM_OUTPUT_ASCII(FILE, PTR, SIZE) \
do \
{ size_t i = 0, limit = (SIZE); \
while (i < limit) \
{ if (i%10 == 0) { if (i!=0) putc ('\n', (FILE)); \
fputs (ASM_BYTE, (FILE)); } \
else putc (',', (FILE)); \
fprintf ((FILE), "0x%x", ((PTR)[i++] & 0377)) ;} \
putc ('\n', (FILE)); \
} while (0)
/* Output at beginning of assembler file. */
#define TARGET_ASM_FILE_START_FILE_DIRECTIVE true
/* This is how to output an assembler line
that says to advance the location counter
to a multiple of 2**LOG bytes. */
#define ASM_OUTPUT_ALIGN(FILE,LOG) \
if ((LOG)!=0) fprintf ((FILE), "\t.align %d\n", 1<<(LOG))
/* This is how to output an assembler line
that says to advance the location counter by SIZE bytes. */
#undef ASM_OUTPUT_SKIP
#define ASM_OUTPUT_SKIP(FILE,SIZE) \
fprintf ((FILE), "\t.set .,.+%u\n", (int)(SIZE))
/* Can't use ASM_OUTPUT_SKIP in text section; it doesn't leave 0s. */
#define ASM_NO_SKIP_IN_TEXT 1
/* Define the syntax of labels and symbol definitions/declarations. */
/* The prefix to add for compiler private assembler symbols. */
#undef LOCAL_LABEL_PREFIX
#define LOCAL_LABEL_PREFIX "."
/* This is how to store into the string BUF
the symbol_ref name of an internal numbered label where
PREFIX is the class of label and NUM is the number within the class.
This is suitable for output with `assemble_name'. */
#undef ASM_GENERATE_INTERNAL_LABEL
#define ASM_GENERATE_INTERNAL_LABEL(BUF,PREFIX,NUMBER) \
sprintf ((BUF), LOCAL_LABEL_PREFIX "%s%ld", (PREFIX), (long)(NUMBER))
/* The prefix to add to user-visible assembler symbols. */
#undef USER_LABEL_PREFIX
#define USER_LABEL_PREFIX ""

View File

@ -0,0 +1,29 @@
/* Make configure files to produce biarch compiler defaulting to 64bit mode.
This file must be included very first, while the OS specific file later
to overwrite otherwise wrong defaults.
Copyright (C) 2001-2013 Free Software Foundation, Inc.
Contributed by Bo Thorsen <bo@suse.de>.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GCC is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
Under Section 7 of GPL version 3, you are granted additional
permissions described in the GCC Runtime Library Exception, version
3.1, as published by the Free Software Foundation.
You should have received a copy of the GNU General Public License and
a copy of the GCC Runtime Library Exception along with this program;
see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
<http://www.gnu.org/licenses/>. */
#define TARGET_64BIT_DEFAULT (OPTION_MASK_ISA_64BIT | OPTION_MASK_ABI_64)
#define TARGET_BI_ARCH 1

View File

@ -0,0 +1,72 @@
/* Common definitions for Intel 386 and AMD x86-64 systems using
GNU userspace. Copyright (C) 2012-2013 Free Software Foundation, Inc.
Contributed by Ilya Enkovich.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GCC is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
/* The svr4 ABI for the i386 says that records and unions are returned
in memory. In the 64bit compilation we will turn this flag off in
ix86_option_override_internal, as we never do pcc_struct_return
scheme on this target. */
#undef DEFAULT_PCC_STRUCT_RETURN
#define DEFAULT_PCC_STRUCT_RETURN 1
/* We arrange for the whole %fs segment to map the tls area. */
#undef TARGET_TLS_DIRECT_SEG_REFS_DEFAULT
#define TARGET_TLS_DIRECT_SEG_REFS_DEFAULT MASK_TLS_DIRECT_SEG_REFS
#define TARGET_OS_CPP_BUILTINS() \
do \
{ \
GNU_USER_TARGET_OS_CPP_BUILTINS(); \
} \
while (0)
#undef CPP_SPEC
#define CPP_SPEC "%{posix:-D_POSIX_SOURCE} %{pthread:-D_REENTRANT}"
#undef GNU_USER_TARGET_CC1_SPEC
#define GNU_USER_TARGET_CC1_SPEC "%(cc1_cpu) %{profile:-p}"
#undef CC1_SPEC
#define CC1_SPEC GNU_USER_TARGET_CC1_SPEC
/* Similar to standard GNU userspace, but adding -ffast-math support. */
#define GNU_USER_TARGET_MATHFILE_SPEC \
"%{Ofast|ffast-math|funsafe-math-optimizations:crtfastmath.o%s} \
%{mpc32:crtprec32.o%s} \
%{mpc64:crtprec64.o%s} \
%{mpc80:crtprec80.o%s}"
#undef ENDFILE_SPEC
#define ENDFILE_SPEC \
GNU_USER_TARGET_MATHFILE_SPEC " " \
GNU_USER_TARGET_ENDFILE_SPEC
/* Put all *tf routines in libgcc. */
#undef LIBGCC2_HAS_TF_MODE
#define LIBGCC2_HAS_TF_MODE 1
#define LIBGCC2_TF_CEXT q
#define TF_SIZE 113
#define TARGET_ASM_FILE_END file_end_indicate_exec_stack
/* The stack pointer needs to be moved while checking the stack. */
#define STACK_CHECK_MOVING_SP 1
/* Static stack checking is supported by means of probes. */
#define STACK_CHECK_STATIC_BUILTIN 1

View File

@ -0,0 +1,99 @@
/* Definitions for AMD x86-64 using GNU userspace.
Copyright (C) 2001-2013 Free Software Foundation, Inc.
Contributed by Jan Hubicka <jh@suse.cz>, based on linux.h.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GCC is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
Under Section 7 of GPL version 3, you are granted additional
permissions described in the GCC Runtime Library Exception, version
3.1, as published by the Free Software Foundation.
You should have received a copy of the GNU General Public License and
a copy of the GCC Runtime Library Exception along with this program;
see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
<http://www.gnu.org/licenses/>. */
/* Provide a LINK_SPEC. Here we provide support for the special GCC
options -static and -shared, which allow us to link things in one
of these three modes by applying the appropriate combinations of
options at link-time.
When the -shared link option is used a final link is not being
done. */
#if TARGET_64BIT_DEFAULT
#define SPEC_32 "m32"
#if TARGET_BI_ARCH == 2
#define SPEC_64 "m64"
#define SPEC_X32 "m32|m64:;"
#else
#define SPEC_64 "m32|mx32:;"
#define SPEC_X32 "mx32"
#endif
#else
#define SPEC_32 "m64|mx32:;"
#define SPEC_64 "m64"
#define SPEC_X32 "mx32"
#endif
#undef ASM_SPEC
#define ASM_SPEC "%{" SPEC_32 ":--32} \
%{" SPEC_64 ":--64} \
%{" SPEC_X32 ":--x32} \
%{!mno-sse2avx:%{mavx:-msse2avx}} %{msse2avx:%{!mavx:-msse2avx}}"
#define GNU_USER_TARGET_LINK_SPEC \
"%{" SPEC_64 ":-m " GNU_USER_LINK_EMULATION64 "} \
%{" SPEC_32 ":-m " GNU_USER_LINK_EMULATION32 "} \
%{" SPEC_X32 ":-m " GNU_USER_LINK_EMULATIONX32 "} \
%{shared:-shared} \
%{!shared: \
%{!static: \
%{rdynamic:-export-dynamic} \
%{" SPEC_32 ":-dynamic-linker " GNU_USER_DYNAMIC_LINKER32 "} \
%{" SPEC_64 ":-dynamic-linker " GNU_USER_DYNAMIC_LINKER64 "} \
%{" SPEC_X32 ":-dynamic-linker " GNU_USER_DYNAMIC_LINKERX32 "}} \
%{static:-static}}"
#undef LINK_SPEC
#define LINK_SPEC GNU_USER_TARGET_LINK_SPEC
#if TARGET_64BIT_DEFAULT
#if TARGET_BI_ARCH == 2
#define MULTILIB_DEFAULTS { "mx32" }
#else
#define MULTILIB_DEFAULTS { "m64" }
#endif
#else
#define MULTILIB_DEFAULTS { "m32" }
#endif
#ifdef TARGET_LIBC_PROVIDES_SSP
/* i386 glibc provides __stack_chk_guard in %gs:0x14,
x32 glibc provides it in %fs:0x18.
x86_64 glibc provides it in %fs:0x28. */
#define TARGET_THREAD_SSP_OFFSET \
(TARGET_64BIT ? (TARGET_X32 ? 0x18 : 0x28) : 0x14)
/* We only build the -fsplit-stack support in libgcc if the
assembler has full support for the CFI directives. */
#if HAVE_GAS_CFI_PERSONALITY_DIRECTIVE
#define TARGET_CAN_SPLIT_STACK
#endif
/* We steal the last transactional memory word. */
#define TARGET_THREAD_SPLIT_STACK_OFFSET \
(TARGET_64BIT ? (TARGET_X32 ? 0x40 : 0x70) : 0x30)
#endif
#undef WCHAR_TYPE
#define WCHAR_TYPE (TARGET_LP64 ? "int" : "long int")

View File

@ -0,0 +1,88 @@
/* Definitions for option handling for IA-32.
Copyright (C) 1988-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GCC is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
Under Section 7 of GPL version 3, you are granted additional
permissions described in the GCC Runtime Library Exception, version
3.1, as published by the Free Software Foundation.
You should have received a copy of the GNU General Public License and
a copy of the GCC Runtime Library Exception along with this program;
see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
<http://www.gnu.org/licenses/>. */
#ifndef I386_OPTS_H
#define I386_OPTS_H
/* Algorithm to expand string function with. */
enum stringop_alg
{
no_stringop,
libcall,
rep_prefix_1_byte,
rep_prefix_4_byte,
rep_prefix_8_byte,
loop_1_byte,
loop,
unrolled_loop
};
/* Available call abi. */
enum calling_abi
{
SYSV_ABI = 0,
MS_ABI = 1
};
enum fpmath_unit
{
FPMATH_387 = 1,
FPMATH_SSE = 2
};
enum tls_dialect
{
TLS_DIALECT_GNU,
TLS_DIALECT_GNU2,
TLS_DIALECT_SUN
};
enum cmodel {
CM_32, /* The traditional 32-bit ABI. */
CM_SMALL, /* Assumes all code and data fits in the low 31 bits. */
CM_KERNEL, /* Assumes all code and data fits in the high 31 bits. */
CM_MEDIUM, /* Assumes code fits in the low 31 bits; data unlimited. */
CM_LARGE, /* No assumptions. */
CM_SMALL_PIC, /* Assumes code+data+got/plt fits in a 31 bit region. */
CM_MEDIUM_PIC,/* Assumes code+got/plt fits in a 31 bit region. */
CM_LARGE_PIC /* No assumptions. */
};
enum pmode {
PMODE_SI, /* Pmode == SImode. */
PMODE_DI /* Pmode == DImode. */
};
enum asm_dialect {
ASM_ATT,
ASM_INTEL
};
enum ix86_veclibabi {
ix86_veclibabi_type_none,
ix86_veclibabi_type_svml,
ix86_veclibabi_type_acml
};
#endif

View File

@ -0,0 +1,326 @@
/* Definitions of target machine for GCC for IA-32.
Copyright (C) 1988-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GCC is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
/* In i386-common.c. */
extern bool ix86_handle_option (struct gcc_options *opts,
struct gcc_options *opts_set ATTRIBUTE_UNUSED,
const struct cl_decoded_option *decoded,
location_t loc);
/* Functions in i386.c */
extern bool ix86_target_stack_probe (void);
extern bool ix86_can_use_return_insn_p (void);
extern void ix86_setup_frame_addresses (void);
extern HOST_WIDE_INT ix86_initial_elimination_offset (int, int);
extern void ix86_expand_prologue (void);
extern void ix86_maybe_emit_epilogue_vzeroupper (void);
extern void ix86_expand_epilogue (int);
extern void ix86_expand_split_stack_prologue (void);
extern void ix86_output_addr_vec_elt (FILE *, int);
extern void ix86_output_addr_diff_elt (FILE *, int, int);
extern enum calling_abi ix86_cfun_abi (void);
extern enum calling_abi ix86_function_type_abi (const_tree);
#ifdef RTX_CODE
extern int standard_80387_constant_p (rtx);
extern const char *standard_80387_constant_opcode (rtx);
extern rtx standard_80387_constant_rtx (int);
extern int standard_sse_constant_p (rtx);
extern const char *standard_sse_constant_opcode (rtx, rtx);
extern bool symbolic_reference_mentioned_p (rtx);
extern bool extended_reg_mentioned_p (rtx);
extern bool x86_extended_QIreg_mentioned_p (rtx);
extern bool x86_extended_reg_mentioned_p (rtx);
extern bool x86_maybe_negate_const_int (rtx *, enum machine_mode);
extern enum machine_mode ix86_cc_mode (enum rtx_code, rtx, rtx);
extern int avx_vpermilp_parallel (rtx par, enum machine_mode mode);
extern int avx_vperm2f128_parallel (rtx par, enum machine_mode mode);
extern bool ix86_expand_movmem (rtx, rtx, rtx, rtx, rtx, rtx);
extern bool ix86_expand_setmem (rtx, rtx, rtx, rtx, rtx, rtx);
extern bool ix86_expand_strlen (rtx, rtx, rtx, rtx);
extern bool constant_address_p (rtx);
extern bool legitimate_pic_operand_p (rtx);
extern bool legitimate_pic_address_disp_p (rtx);
extern bool ix86_legitimize_reload_address (rtx, enum machine_mode,
int, int, int);
extern void print_reg (rtx, int, FILE*);
extern void ix86_print_operand (FILE *, rtx, int);
extern void split_double_mode (enum machine_mode, rtx[], int, rtx[], rtx[]);
extern const char *output_set_got (rtx, rtx);
extern const char *output_387_binary_op (rtx, rtx*);
extern const char *output_387_reg_move (rtx, rtx*);
extern const char *output_fix_trunc (rtx, rtx*, bool);
extern const char *output_fp_compare (rtx, rtx*, bool, bool);
extern const char *output_adjust_stack_and_probe (rtx);
extern const char *output_probe_stack_range (rtx, rtx);
extern void ix86_expand_clear (rtx);
extern void ix86_expand_move (enum machine_mode, rtx[]);
extern void ix86_expand_vector_move (enum machine_mode, rtx[]);
extern void ix86_expand_vector_move_misalign (enum machine_mode, rtx[]);
extern void ix86_expand_push (enum machine_mode, rtx);
extern rtx ix86_fixup_binary_operands (enum rtx_code,
enum machine_mode, rtx[]);
extern void ix86_fixup_binary_operands_no_copy (enum rtx_code,
enum machine_mode, rtx[]);
extern void ix86_expand_binary_operator (enum rtx_code,
enum machine_mode, rtx[]);
extern void ix86_expand_vector_logical_operator (enum rtx_code,
enum machine_mode, rtx[]);
extern bool ix86_binary_operator_ok (enum rtx_code, enum machine_mode, rtx[]);
extern bool ix86_avoid_lea_for_add (rtx, rtx[]);
extern bool ix86_use_lea_for_mov (rtx, rtx[]);
extern bool ix86_avoid_lea_for_addr (rtx, rtx[]);
extern void ix86_split_lea_for_addr (rtx, rtx[], enum machine_mode);
extern bool ix86_lea_for_add_ok (rtx, rtx[]);
extern bool ix86_vec_interleave_v2df_operator_ok (rtx operands[3], bool high);
extern bool ix86_dep_by_shift_count (const_rtx set_insn, const_rtx use_insn);
extern bool ix86_agi_dependent (rtx set_insn, rtx use_insn);
extern void ix86_expand_unary_operator (enum rtx_code, enum machine_mode,
rtx[]);
extern rtx ix86_build_const_vector (enum machine_mode, bool, rtx);
extern rtx ix86_build_signbit_mask (enum machine_mode, bool, bool);
extern void ix86_split_convert_uns_si_sse (rtx[]);
extern void ix86_expand_convert_uns_didf_sse (rtx, rtx);
extern void ix86_expand_convert_uns_sixf_sse (rtx, rtx);
extern void ix86_expand_convert_uns_sidf_sse (rtx, rtx);
extern void ix86_expand_convert_uns_sisf_sse (rtx, rtx);
extern void ix86_expand_convert_sign_didf_sse (rtx, rtx);
extern void ix86_expand_vector_convert_uns_vsivsf (rtx, rtx);
extern rtx ix86_expand_adjust_ufix_to_sfix_si (rtx, rtx *);
extern enum ix86_fpcmp_strategy ix86_fp_comparison_strategy (enum rtx_code);
extern void ix86_expand_fp_absneg_operator (enum rtx_code, enum machine_mode,
rtx[]);
extern void ix86_expand_copysign (rtx []);
extern void ix86_split_copysign_const (rtx []);
extern void ix86_split_copysign_var (rtx []);
extern bool ix86_unary_operator_ok (enum rtx_code, enum machine_mode, rtx[]);
extern bool ix86_match_ccmode (rtx, enum machine_mode);
extern void ix86_expand_branch (enum rtx_code, rtx, rtx, rtx);
extern void ix86_expand_setcc (rtx, enum rtx_code, rtx, rtx);
extern bool ix86_expand_int_movcc (rtx[]);
extern bool ix86_expand_fp_movcc (rtx[]);
extern bool ix86_expand_fp_vcond (rtx[]);
extern bool ix86_expand_int_vcond (rtx[]);
extern void ix86_expand_vec_perm (rtx[]);
extern bool ix86_expand_vec_perm_const (rtx[]);
extern void ix86_expand_sse_unpack (rtx, rtx, bool, bool);
extern bool ix86_expand_int_addcc (rtx[]);
extern rtx ix86_expand_call (rtx, rtx, rtx, rtx, rtx, bool);
extern void ix86_split_call_vzeroupper (rtx, rtx);
extern void x86_initialize_trampoline (rtx, rtx, rtx);
extern rtx ix86_zero_extend_to_Pmode (rtx);
extern void ix86_split_long_move (rtx[]);
extern void ix86_split_ashl (rtx *, rtx, enum machine_mode);
extern void ix86_split_ashr (rtx *, rtx, enum machine_mode);
extern void ix86_split_lshr (rtx *, rtx, enum machine_mode);
extern rtx ix86_find_base_term (rtx);
extern bool ix86_check_movabs (rtx, int);
extern void ix86_split_idivmod (enum machine_mode, rtx[], bool);
extern rtx assign_386_stack_local (enum machine_mode, enum ix86_stack_slot);
extern int ix86_attr_length_immediate_default (rtx, bool);
extern int ix86_attr_length_address_default (rtx);
extern int ix86_attr_length_vex_default (rtx, bool, bool);
extern enum machine_mode ix86_fp_compare_mode (enum rtx_code);
extern rtx ix86_libcall_value (enum machine_mode);
extern bool ix86_function_arg_regno_p (int);
extern void ix86_asm_output_function_label (FILE *, const char *, tree);
extern rtx ix86_force_to_memory (enum machine_mode, rtx);
extern void ix86_free_from_memory (enum machine_mode);
extern void ix86_call_abi_override (const_tree);
extern int ix86_reg_parm_stack_space (const_tree);
extern void ix86_split_fp_branch (enum rtx_code code, rtx, rtx,
rtx, rtx, rtx, rtx);
extern bool ix86_hard_regno_mode_ok (int, enum machine_mode);
extern bool ix86_modes_tieable_p (enum machine_mode, enum machine_mode);
extern bool ix86_secondary_memory_needed (enum reg_class, enum reg_class,
enum machine_mode, int);
extern bool ix86_cannot_change_mode_class (enum machine_mode,
enum machine_mode, enum reg_class);
extern int ix86_mode_needed (int, rtx);
extern int ix86_mode_after (int, int, rtx);
extern int ix86_mode_entry (int);
extern int ix86_mode_exit (int);
#ifdef HARD_CONST
extern void ix86_emit_mode_set (int, int, HARD_REG_SET);
#endif
extern void x86_order_regs_for_local_alloc (void);
extern void x86_function_profiler (FILE *, int);
extern void x86_emit_floatuns (rtx [2]);
extern void ix86_emit_fp_unordered_jump (rtx);
extern void ix86_emit_i387_log1p (rtx, rtx);
extern void ix86_emit_i387_round (rtx, rtx);
extern void ix86_emit_swdivsf (rtx, rtx, rtx, enum machine_mode);
extern void ix86_emit_swsqrtsf (rtx, rtx, enum machine_mode, bool);
extern enum rtx_code ix86_reverse_condition (enum rtx_code, enum machine_mode);
extern void ix86_expand_lround (rtx, rtx);
extern void ix86_expand_lfloorceil (rtx, rtx, bool);
extern void ix86_expand_rint (rtx, rtx);
extern void ix86_expand_floorceil (rtx, rtx, bool);
extern void ix86_expand_floorceildf_32 (rtx, rtx, bool);
extern void ix86_expand_round_sse4 (rtx, rtx);
extern void ix86_expand_round (rtx, rtx);
extern void ix86_expand_rounddf_32 (rtx, rtx);
extern void ix86_expand_trunc (rtx, rtx);
extern void ix86_expand_truncdf_32 (rtx, rtx);
extern void ix86_expand_vecop_qihi (enum rtx_code, rtx, rtx, rtx);
#ifdef TREE_CODE
extern void init_cumulative_args (CUMULATIVE_ARGS *, tree, rtx, tree, int);
#endif /* TREE_CODE */
#endif /* RTX_CODE */
#ifdef TREE_CODE
extern int ix86_data_alignment (tree, int);
extern unsigned int ix86_local_alignment (tree, enum machine_mode,
unsigned int);
extern unsigned int ix86_minimum_alignment (tree, enum machine_mode,
unsigned int);
extern int ix86_constant_alignment (tree, int);
extern tree ix86_handle_shared_attribute (tree *, tree, tree, int, bool *);
extern tree ix86_handle_selectany_attribute (tree *, tree, tree, int, bool *);
extern int x86_field_alignment (tree, int);
extern tree ix86_valid_target_attribute_tree (tree);
extern unsigned int ix86_get_callcvt (const_tree);
#endif
extern rtx ix86_tls_module_base (void);
extern void ix86_expand_vector_init (bool, rtx, rtx);
extern void ix86_expand_vector_set (bool, rtx, rtx, int);
extern void ix86_expand_vector_extract (bool, rtx, rtx, int);
extern void ix86_expand_reduc (rtx (*)(rtx, rtx, rtx), rtx, rtx);
extern void ix86_expand_vec_extract_even_odd (rtx, rtx, rtx, unsigned);
extern bool ix86_expand_pinsr (rtx *);
extern void ix86_expand_mul_widen_evenodd (rtx, rtx, rtx, bool, bool);
extern void ix86_expand_mul_widen_hilo (rtx, rtx, rtx, bool, bool);
extern void ix86_expand_sse2_mulv4si3 (rtx, rtx, rtx);
extern void ix86_expand_sse2_mulvxdi3 (rtx, rtx, rtx);
/* In i386-c.c */
extern void ix86_target_macros (void);
extern void ix86_register_pragmas (void);
/* In winnt.c */
extern void i386_pe_unique_section (tree, int);
extern void i386_pe_declare_function_type (FILE *, const char *, int);
extern void i386_pe_record_external_function (tree, const char *);
extern void i386_pe_maybe_record_exported_symbol (tree, const char *, int);
extern void i386_pe_encode_section_info (tree, rtx, int);
extern bool i386_pe_binds_local_p (const_tree);
extern const char *i386_pe_strip_name_encoding_full (const char *);
extern bool i386_pe_valid_dllimport_attribute_p (const_tree);
extern unsigned int i386_pe_section_type_flags (tree, const char *, int);
extern void i386_pe_asm_named_section (const char *, unsigned int, tree);
extern void i386_pe_asm_output_aligned_decl_common (FILE *, tree,
const char *,
HOST_WIDE_INT,
HOST_WIDE_INT);
extern void i386_pe_file_end (void);
extern void i386_pe_start_function (FILE *, const char *, tree);
extern void i386_pe_end_function (FILE *, const char *, tree);
extern void i386_pe_assemble_visibility (tree, int);
extern tree i386_pe_mangle_decl_assembler_name (tree, tree);
extern tree i386_pe_mangle_assembler_name (const char *);
extern void i386_pe_seh_init (FILE *);
extern void i386_pe_seh_end_prologue (FILE *);
extern void i386_pe_seh_unwind_emit (FILE *, rtx);
extern void i386_pe_seh_emit_except_personality (rtx);
extern void i386_pe_seh_init_sections (void);
/* In winnt-cxx.c and winnt-stubs.c */
extern void i386_pe_adjust_class_at_definition (tree);
extern bool i386_pe_type_dllimport_p (tree);
extern bool i386_pe_type_dllexport_p (tree);
extern int i386_pe_reloc_rw_mask (void);
extern rtx maybe_get_pool_constant (rtx);
extern char internal_label_prefix[16];
extern int internal_label_prefix_len;
enum ix86_address_seg { SEG_DEFAULT, SEG_FS, SEG_GS };
struct ix86_address
{
rtx base, index, disp;
HOST_WIDE_INT scale;
enum ix86_address_seg seg;
};
extern int ix86_decompose_address (rtx, struct ix86_address *);
extern int memory_address_length (rtx, bool);
extern void x86_output_aligned_bss (FILE *, tree, const char *,
unsigned HOST_WIDE_INT, int);
extern void x86_elf_aligned_common (FILE *, const char *,
unsigned HOST_WIDE_INT, int);
#ifdef RTX_CODE
extern void ix86_fp_comparison_codes (enum rtx_code code, enum rtx_code *,
enum rtx_code *, enum rtx_code *);
extern enum rtx_code ix86_fp_compare_code_to_integer (enum rtx_code);
#endif
extern int asm_preferred_eh_data_format (int, int);
#ifdef HAVE_ATTR_cpu
extern enum attr_cpu ix86_schedule;
#endif
extern const char * ix86_output_call_insn (rtx insn, rtx call_op);
#ifdef RTX_CODE
/* Target data for multipass lookahead scheduling.
Currently used for Core 2/i7 tuning. */
struct ix86_first_cycle_multipass_data_
{
/* The length (in bytes) of ifetch block in this solution. */
int ifetch_block_len;
/* Number of instructions in ifetch block in this solution. */
int ifetch_block_n_insns;
/* Bitmap to remember changes to ready_try for backtracking. */
sbitmap ready_try_change;
/* Size of the bitmap. */
int ready_try_change_size;
};
# define TARGET_SCHED_FIRST_CYCLE_MULTIPASS_DATA_T \
struct ix86_first_cycle_multipass_data_
#endif /* RTX_CODE */

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,55 @@
/* Definitions for Intel 386 running Linux-based GNU systems with ELF format.
Copyright (C) 2012-2013 Free Software Foundation, Inc.
Contributed by Ilya Enkovich.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GCC is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#undef TARGET_OS_CPP_BUILTINS
#define TARGET_OS_CPP_BUILTINS() \
do \
{ \
GNU_USER_TARGET_OS_CPP_BUILTINS(); \
ANDROID_TARGET_OS_CPP_BUILTINS(); \
} \
while (0)
#undef CC1_SPEC
#define CC1_SPEC \
LINUX_OR_ANDROID_CC (GNU_USER_TARGET_CC1_SPEC, \
GNU_USER_TARGET_CC1_SPEC " " ANDROID_CC1_SPEC)
#undef LINK_SPEC
#define LINK_SPEC \
LINUX_OR_ANDROID_LD (GNU_USER_TARGET_LINK_SPEC, \
GNU_USER_TARGET_LINK_SPEC " " ANDROID_LINK_SPEC)
#undef LIB_SPEC
#define LIB_SPEC \
LINUX_OR_ANDROID_LD (GNU_USER_TARGET_LIB_SPEC, \
GNU_USER_TARGET_LIB_SPEC " " ANDROID_LIB_SPEC)
#undef STARTFILE_SPEC
#define STARTFILE_SPEC \
LINUX_OR_ANDROID_LD (GNU_USER_TARGET_STARTFILE_SPEC, \
ANDROID_STARTFILE_SPEC)
#undef ENDFILE_SPEC
#define ENDFILE_SPEC \
LINUX_OR_ANDROID_LD (GNU_USER_TARGET_MATHFILE_SPEC " " \
GNU_USER_TARGET_ENDFILE_SPEC, \
GNU_USER_TARGET_MATHFILE_SPEC " " \
ANDROID_ENDFILE_SPEC)

View File

@ -0,0 +1,32 @@
/* Definitions for AMD x86-64 running Linux-based GNU systems with ELF format.
Copyright (C) 2001-2013 Free Software Foundation, Inc.
Contributed by Jan Hubicka <jh@suse.cz>, based on linux.h.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GCC is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
Under Section 7 of GPL version 3, you are granted additional
permissions described in the GCC Runtime Library Exception, version
3.1, as published by the Free Software Foundation.
You should have received a copy of the GNU General Public License and
a copy of the GCC Runtime Library Exception along with this program;
see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
<http://www.gnu.org/licenses/>. */
#define GNU_USER_LINK_EMULATION32 "elf_i386"
#define GNU_USER_LINK_EMULATION64 "elf_x86_64"
#define GNU_USER_LINK_EMULATIONX32 "elf32_x86_64"
#define GLIBC_DYNAMIC_LINKER32 "/lib/ld-linux.so.2"
#define GLIBC_DYNAMIC_LINKER64 "/lib64/ld-linux-x86-64.so.2"
#define GLIBC_DYNAMIC_LINKERX32 "/libx32/ld-linux-x32.so.2"

View File

@ -0,0 +1,80 @@
/* Definitions for Unix assembler syntax for the Intel 80386.
Copyright (C) 1988-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GCC is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
Under Section 7 of GPL version 3, you are granted additional
permissions described in the GCC Runtime Library Exception, version
3.1, as published by the Free Software Foundation.
You should have received a copy of the GNU General Public License and
a copy of the GCC Runtime Library Exception along with this program;
see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
<http://www.gnu.org/licenses/>. */
/* This file defines the aspects of assembler syntax
that are the same for all the i386 Unix systems
(though they may differ in non-Unix systems). */
/* Define macro used to output shift-double opcodes when the shift
count is in %cl. Some assemblers require %cl as an argument;
some don't. This macro controls what to do: by default, don't
print %cl. */
#define SHIFT_DOUBLE_OMITS_COUNT 1
/* Define the syntax of pseudo-ops, labels and comments. */
/* String containing the assembler's comment-starter.
Note the trailing space is necessary in case the character
that immediately follows the comment is '*'. If this happens
and the space is not there the assembler will interpret this
as the start of a C-like slash-star comment and complain when
there is no terminator. */
#define ASM_COMMENT_START "/ "
/* Output to assembler file text saying following lines
may contain character constants, extra white space, comments, etc. */
#define ASM_APP_ON "/APP\n"
/* Output to assembler file text saying following lines
no longer contain unusual constructs. */
#define ASM_APP_OFF "/NO_APP\n"
/* Output before read-only data. */
#define TEXT_SECTION_ASM_OP "\t.text"
/* Output before writable (initialized) data. */
#define DATA_SECTION_ASM_OP "\t.data"
/* Output before writable (uninitialized) data. */
#define BSS_SECTION_ASM_OP "\t.bss"
/* Globalizing directive for a label. */
#define GLOBAL_ASM_OP "\t.globl\t"
/* By default, target has a 80387, uses IEEE compatible arithmetic,
and returns float values in the 387. */
#undef TARGET_SUBTARGET_DEFAULT
#define TARGET_SUBTARGET_DEFAULT \
(MASK_80387 | MASK_IEEE_FP | MASK_FLOAT_RETURNS)
/* By default, 64-bit mode uses 128-bit long double. */
#undef TARGET_SUBTARGET64_DEFAULT
#define TARGET_SUBTARGET64_DEFAULT \
MASK_128BIT_LONG_DOUBLE

View File

@ -0,0 +1,108 @@
/* OS independent definitions for AMD x86-64.
Copyright (C) 2001-2013 Free Software Foundation, Inc.
Contributed by Bo Thorsen <bo@suse.de>.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GCC is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
Under Section 7 of GPL version 3, you are granted additional
permissions described in the GCC Runtime Library Exception, version
3.1, as published by the Free Software Foundation.
You should have received a copy of the GNU General Public License and
a copy of the GCC Runtime Library Exception along with this program;
see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
<http://www.gnu.org/licenses/>. */
#undef ASM_COMMENT_START
#define ASM_COMMENT_START "#"
#undef DBX_REGISTER_NUMBER
#define DBX_REGISTER_NUMBER(n) \
(TARGET_64BIT ? dbx64_register_map[n] : svr4_dbx_register_map[n])
/* Output assembler code to FILE to call the profiler. */
#define NO_PROFILE_COUNTERS 1
#undef MCOUNT_NAME
#define MCOUNT_NAME "mcount"
#undef SIZE_TYPE
#define SIZE_TYPE (TARGET_LP64 ? "long unsigned int" : "unsigned int")
#undef PTRDIFF_TYPE
#define PTRDIFF_TYPE (TARGET_LP64 ? "long int" : "int")
#undef WCHAR_TYPE
#define WCHAR_TYPE "int"
#undef WCHAR_TYPE_SIZE
#define WCHAR_TYPE_SIZE 32
#undef ASM_SPEC
#define ASM_SPEC "%{m32:--32} %{m64:--64}"
#undef ASM_OUTPUT_ALIGNED_BSS
#define ASM_OUTPUT_ALIGNED_BSS(FILE, DECL, NAME, SIZE, ALIGN) \
x86_output_aligned_bss (FILE, DECL, NAME, SIZE, ALIGN)
#undef ASM_OUTPUT_ALIGNED_COMMON
#define ASM_OUTPUT_ALIGNED_COMMON(FILE, NAME, SIZE, ALIGN) \
x86_elf_aligned_common (FILE, NAME, SIZE, ALIGN);
/* This is used to align code labels according to Intel recommendations. */
#ifdef HAVE_GAS_MAX_SKIP_P2ALIGN
#define ASM_OUTPUT_MAX_SKIP_ALIGN(FILE,LOG,MAX_SKIP) \
do { \
if ((LOG) != 0) { \
if ((MAX_SKIP) == 0) fprintf ((FILE), "\t.p2align %d\n", (LOG)); \
else { \
fprintf ((FILE), "\t.p2align %d,,%d\n", (LOG), (MAX_SKIP)); \
/* Make sure that we have at least 8 byte alignment if > 8 byte \
alignment is preferred. */ \
if ((LOG) > 3 \
&& (1 << (LOG)) > ((MAX_SKIP) + 1) \
&& (MAX_SKIP) >= 7) \
fputs ("\t.p2align 3\n", (FILE)); \
} \
} \
} while (0)
#undef ASM_OUTPUT_MAX_SKIP_PAD
#define ASM_OUTPUT_MAX_SKIP_PAD(FILE, LOG, MAX_SKIP) \
if ((LOG) != 0) \
{ \
if ((MAX_SKIP) == 0) \
fprintf ((FILE), "\t.p2align %d\n", (LOG)); \
else \
fprintf ((FILE), "\t.p2align %d,,%d\n", (LOG), (MAX_SKIP)); \
}
#endif
/* i386 System V Release 4 uses DWARF debugging info.
x86-64 ABI specifies DWARF2. */
#define DWARF2_DEBUGGING_INFO 1
#define DWARF2_UNWIND_INFO 1
#undef PREFERRED_DEBUGGING_TYPE
#define PREFERRED_DEBUGGING_TYPE DWARF2_DEBUG
#undef TARGET_ASM_SELECT_SECTION
#define TARGET_ASM_SELECT_SECTION x86_64_elf_select_section
#undef TARGET_ASM_UNIQUE_SECTION
#define TARGET_ASM_UNIQUE_SECTION x86_64_elf_unique_section
#undef TARGET_SECTION_TYPE_FLAGS
#define TARGET_SECTION_TYPE_FLAGS x86_64_elf_section_type_flags

View File

@ -0,0 +1,40 @@
/* Definitions for ELF systems with .init_array/.fini_array section
support.
Copyright (C) 2011-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it
under the terms of the GNU General Public License as published
by the Free Software Foundation; either version 3, or (at your
option) any later version.
GCC is distributed in the hope that it will be useful, but WITHOUT
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public
License for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifdef HAVE_INITFINI_ARRAY_SUPPORT
#define USE_INITFINI_ARRAY
#undef INIT_SECTION_ASM_OP
#undef FINI_SECTION_ASM_OP
#undef INIT_ARRAY_SECTION_ASM_OP
#define INIT_ARRAY_SECTION_ASM_OP
#undef FINI_ARRAY_SECTION_ASM_OP
#define FINI_ARRAY_SECTION_ASM_OP
/* Use .init_array/.fini_array section for constructors and destructors. */
#undef TARGET_ASM_CONSTRUCTOR
#define TARGET_ASM_CONSTRUCTOR default_elf_init_array_asm_out_constructor
#undef TARGET_ASM_DESTRUCTOR
#define TARGET_ASM_DESTRUCTOR default_elf_fini_array_asm_out_destructor
#endif

View File

@ -0,0 +1,59 @@
/* Configuration file for Linux Android targets.
Copyright (C) 2008-2013 Free Software Foundation, Inc.
Contributed by Doug Kwan (dougkwan@google.com)
Rewritten by CodeSourcery, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it
under the terms of the GNU General Public License as published
by the Free Software Foundation; either version 3, or (at your
option) any later version.
GCC is distributed in the hope that it will be useful, but WITHOUT
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public
License for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#define ANDROID_TARGET_OS_CPP_BUILTINS() \
do { \
if (TARGET_ANDROID) \
builtin_define ("__ANDROID__"); \
} while (0)
#if ANDROID_DEFAULT
# define NOANDROID "mno-android"
#else
# define NOANDROID "!mandroid"
#endif
#define LINUX_OR_ANDROID_CC(LINUX_SPEC, ANDROID_SPEC) \
"%{" NOANDROID "|tno-android-cc:" LINUX_SPEC ";:" ANDROID_SPEC "}"
#define LINUX_OR_ANDROID_LD(LINUX_SPEC, ANDROID_SPEC) \
"%{" NOANDROID "|tno-android-ld:" LINUX_SPEC ";:" ANDROID_SPEC "}"
#define ANDROID_LINK_SPEC \
"%{shared: -Bsymbolic}"
#define ANDROID_CC1_SPEC \
"%{!mglibc:%{!muclibc:%{!mbionic: -mbionic}}} " \
"%{!fno-pic:%{!fno-PIC:%{!fpic:%{!fPIC: -fPIC}}}}"
#define ANDROID_CC1PLUS_SPEC \
"%{!fexceptions:%{!fno-exceptions: -fno-exceptions}} " \
"%{!frtti:%{!fno-rtti: -fno-rtti}}"
#define ANDROID_LIB_SPEC \
"%{!static: -ldl}"
#define ANDROID_STARTFILE_SPEC \
"%{shared: crtbegin_so%O%s;:" \
" %{static: crtbegin_static%O%s;: crtbegin_dynamic%O%s}}"
#define ANDROID_ENDFILE_SPEC \
"%{shared: crtend_so%O%s;: crtend_android%O%s}"

109
src/include/config/linux.h Normal file
View File

@ -0,0 +1,109 @@
/* Definitions for systems using the Linux kernel, with or without
MMU, using ELF at the compiler level but possibly FLT for final
linked executables and shared libraries in some no-MMU cases, and
possibly with a choice of libc implementations.
Copyright (C) 1995-2013 Free Software Foundation, Inc.
Contributed by Eric Youngdale.
Modified for stabs-in-ELF by H.J. Lu (hjl@lucon.org).
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GCC is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
Under Section 7 of GPL version 3, you are granted additional
permissions described in the GCC Runtime Library Exception, version
3.1, as published by the Free Software Foundation.
You should have received a copy of the GNU General Public License and
a copy of the GCC Runtime Library Exception along with this program;
see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
<http://www.gnu.org/licenses/>. */
/* C libraries supported on Linux. */
#ifdef SINGLE_LIBC
#define OPTION_GLIBC (DEFAULT_LIBC == LIBC_GLIBC)
#define OPTION_UCLIBC (DEFAULT_LIBC == LIBC_UCLIBC)
#define OPTION_BIONIC (DEFAULT_LIBC == LIBC_BIONIC)
#else
#define OPTION_GLIBC (linux_libc == LIBC_GLIBC)
#define OPTION_UCLIBC (linux_libc == LIBC_UCLIBC)
#define OPTION_BIONIC (linux_libc == LIBC_BIONIC)
#endif
#define GNU_USER_TARGET_OS_CPP_BUILTINS() \
do { \
if (OPTION_GLIBC) \
builtin_define ("__gnu_linux__"); \
builtin_define_std ("linux"); \
builtin_define_std ("unix"); \
builtin_assert ("system=linux"); \
builtin_assert ("system=unix"); \
builtin_assert ("system=posix"); \
} while (0)
/* Determine which dynamic linker to use depending on whether GLIBC or
uClibc or Bionic is the default C library and whether
-muclibc or -mglibc or -mbionic has been passed to change the default. */
#define CHOOSE_DYNAMIC_LINKER1(LIBC1, LIBC2, LIBC3, LD1, LD2, LD3) \
"%{" LIBC2 ":" LD2 ";:%{" LIBC3 ":" LD3 ";:" LD1 "}}"
#if DEFAULT_LIBC == LIBC_GLIBC
#define CHOOSE_DYNAMIC_LINKER(G, U, B) \
CHOOSE_DYNAMIC_LINKER1 ("mglibc", "muclibc", "mbionic", G, U, B)
#elif DEFAULT_LIBC == LIBC_UCLIBC
#define CHOOSE_DYNAMIC_LINKER(G, U, B) \
CHOOSE_DYNAMIC_LINKER1 ("muclibc", "mglibc", "mbionic", U, G, B)
#elif DEFAULT_LIBC == LIBC_BIONIC
#define CHOOSE_DYNAMIC_LINKER(G, U, B) \
CHOOSE_DYNAMIC_LINKER1 ("mbionic", "mglibc", "muclibc", B, G, U)
#else
#error "Unsupported DEFAULT_LIBC"
#endif /* DEFAULT_LIBC */
/* For most targets the following definitions suffice;
GLIBC_DYNAMIC_LINKER must be defined for each target using them, or
GLIBC_DYNAMIC_LINKER32 and GLIBC_DYNAMIC_LINKER64 for targets
supporting both 32-bit and 64-bit compilation. */
#define UCLIBC_DYNAMIC_LINKER "/lib/ld-uClibc.so.0"
#define UCLIBC_DYNAMIC_LINKER32 "/lib/ld-uClibc.so.0"
#define UCLIBC_DYNAMIC_LINKER64 "/lib/ld64-uClibc.so.0"
#define UCLIBC_DYNAMIC_LINKERX32 "/lib/ldx32-uClibc.so.0"
#define BIONIC_DYNAMIC_LINKER "/system/bin/linker"
#define BIONIC_DYNAMIC_LINKER32 "/system/bin/linker"
#define BIONIC_DYNAMIC_LINKER64 "/system/bin/linker64"
#define BIONIC_DYNAMIC_LINKERX32 "/system/bin/linkerx32"
#define GNU_USER_DYNAMIC_LINKER \
CHOOSE_DYNAMIC_LINKER (GLIBC_DYNAMIC_LINKER, UCLIBC_DYNAMIC_LINKER, \
BIONIC_DYNAMIC_LINKER)
#define GNU_USER_DYNAMIC_LINKER32 \
CHOOSE_DYNAMIC_LINKER (GLIBC_DYNAMIC_LINKER32, UCLIBC_DYNAMIC_LINKER32, \
BIONIC_DYNAMIC_LINKER32)
#define GNU_USER_DYNAMIC_LINKER64 \
CHOOSE_DYNAMIC_LINKER (GLIBC_DYNAMIC_LINKER64, UCLIBC_DYNAMIC_LINKER64, \
BIONIC_DYNAMIC_LINKER64)
#define GNU_USER_DYNAMIC_LINKERX32 \
CHOOSE_DYNAMIC_LINKER (GLIBC_DYNAMIC_LINKERX32, UCLIBC_DYNAMIC_LINKERX32, \
BIONIC_DYNAMIC_LINKERX32)
/* Determine whether the entire c99 runtime
is present in the runtime library. */
#undef TARGET_C99_FUNCTIONS
#define TARGET_C99_FUNCTIONS (OPTION_GLIBC)
/* Whether we have sincos that follows the GNU extension. */
#undef TARGET_HAS_SINCOS
#define TARGET_HAS_SINCOS (OPTION_GLIBC || OPTION_BIONIC)
/* Whether we have Bionic libc runtime */
#undef TARGET_HAS_BIONIC
#define TARGET_HAS_BIONIC (OPTION_BIONIC)

View File

@ -0,0 +1,40 @@
/* Dummy definitions of VxWorks-related macros
Copyright (C) 2007-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
Under Section 7 of GPL version 3, you are granted additional
permissions described in the GCC Runtime Library Exception, version
3.1, as published by the Free Software Foundation.
You should have received a copy of the GNU General Public License and
a copy of the GCC Runtime Library Exception along with this program;
see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
<http://www.gnu.org/licenses/>. */
/* True if we're targeting VxWorks. */
#ifndef TARGET_VXWORKS
#define TARGET_VXWORKS 0
#endif
/* True if generating code for a VxWorks RTP. */
#ifndef TARGET_VXWORKS_RTP
#define TARGET_VXWORKS_RTP false
#endif
/* The symbol that points to an RTP's table of GOTs. */
#define VXWORKS_GOTT_BASE (gcc_unreachable (), "")
/* The symbol that holds the index of the current module's GOT in
VXWORKS_GOTT_BASE. */
#define VXWORKS_GOTT_INDEX (gcc_unreachable (), "")

7
src/include/configargs.h Normal file
View File

@ -0,0 +1,7 @@
/* Generated automatically. */
static const char configuration_arguments[] = "../configure --prefix=/home/zet/bin/gcc-48 --disable-bootstrap --enable-languages=c,c++ --enable-shared --enable-threads=posix --enable-lto --enable-plugin --enable-gold=yes --without-included-gettext --enable-nls --disable-libmudflap --disable-browser-plugin --disable-werror";
static const char thread_model[] = "posix";
static const struct {
const char *name, *value;
} configure_default_options[] = { { "cpu", "generic" }, { "arch", "x86-64" } };

208
src/include/coretypes.h Normal file
View File

@ -0,0 +1,208 @@
/* GCC core type declarations.
Copyright (C) 2002-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
Under Section 7 of GPL version 3, you are granted additional
permissions described in the GCC Runtime Library Exception, version
3.1, as published by the Free Software Foundation.
You should have received a copy of the GNU General Public License and
a copy of the GCC Runtime Library Exception along with this program;
see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
<http://www.gnu.org/licenses/>. */
/* Provide forward declarations of core types which are referred to by
most of the compiler. This allows header files to use these types
(e.g. in function prototypes) without concern for whether the full
definitions are visible. Some other declarations that need to be
universally visible are here, too.
In the context of tconfig.h, most of these have special definitions
which prevent them from being used except in further type
declarations. This is a kludge; the right thing is to avoid
including the "tm.h" header set in the context of tconfig.h, but
we're not there yet. */
#ifndef GCC_CORETYPES_H
#define GCC_CORETYPES_H
#ifndef GTY
#define GTY(x) /* nothing - marker for gengtype */
#endif
#ifndef USED_FOR_TARGET
struct bitmap_head_def;
typedef struct bitmap_head_def *bitmap;
typedef const struct bitmap_head_def *const_bitmap;
struct simple_bitmap_def;
typedef struct simple_bitmap_def *sbitmap;
typedef const struct simple_bitmap_def *const_sbitmap;
struct rtx_def;
typedef struct rtx_def *rtx;
typedef const struct rtx_def *const_rtx;
struct rtvec_def;
typedef struct rtvec_def *rtvec;
typedef const struct rtvec_def *const_rtvec;
union tree_node;
typedef union tree_node *tree;
typedef const union tree_node *const_tree;
union gimple_statement_d;
typedef union gimple_statement_d *gimple;
typedef const union gimple_statement_d *const_gimple;
typedef gimple gimple_seq;
union section;
typedef union section section;
struct gcc_options;
struct cl_target_option;
struct cl_optimization;
struct cl_option;
struct cl_decoded_option;
struct cl_option_handlers;
struct diagnostic_context;
typedef struct diagnostic_context diagnostic_context;
struct pretty_print_info;
typedef struct pretty_print_info pretty_printer;
/* Address space number for named address space support. */
typedef unsigned char addr_space_t;
/* The value of addr_space_t that represents the generic address space. */
#define ADDR_SPACE_GENERIC 0
#define ADDR_SPACE_GENERIC_P(AS) ((AS) == ADDR_SPACE_GENERIC)
/* The major intermediate representations of GCC. */
enum ir_type {
IR_GIMPLE,
IR_RTL_CFGRTL,
IR_RTL_CFGLAYOUT
};
/* Provide forward struct declaration so that we don't have to include
all of cpplib.h whenever a random prototype includes a pointer.
Note that the cpp_reader and cpp_token typedefs remain part of
cpplib.h. */
struct cpp_reader;
struct cpp_token;
/* The thread-local storage model associated with a given VAR_DECL
or SYMBOL_REF. This isn't used much, but both trees and RTL refer
to it, so it's here. */
enum tls_model {
TLS_MODEL_NONE,
TLS_MODEL_EMULATED,
TLS_MODEL_REAL,
TLS_MODEL_GLOBAL_DYNAMIC = TLS_MODEL_REAL,
TLS_MODEL_LOCAL_DYNAMIC,
TLS_MODEL_INITIAL_EXEC,
TLS_MODEL_LOCAL_EXEC
};
/* Types of unwind/exception handling info that can be generated. */
enum unwind_info_type
{
UI_NONE,
UI_SJLJ,
UI_DWARF2,
UI_TARGET,
UI_SEH
};
/* Callgraph node profile representation. */
enum node_frequency {
/* This function most likely won't be executed at all.
(set only when profile feedback is available or via function attribute). */
NODE_FREQUENCY_UNLIKELY_EXECUTED,
/* For functions that are known to be executed once (i.e. constructors, destructors
and main function. */
NODE_FREQUENCY_EXECUTED_ONCE,
/* The default value. */
NODE_FREQUENCY_NORMAL,
/* Optimize this function hard
(set only when profile feedback is available or via function attribute). */
NODE_FREQUENCY_HOT
};
/* Possible initialization status of a variable. When requested
by the user, this information is tracked and recorded in the DWARF
debug information, along with the variable's location. */
enum var_init_status
{
VAR_INIT_STATUS_UNKNOWN,
VAR_INIT_STATUS_UNINITIALIZED,
VAR_INIT_STATUS_INITIALIZED
};
struct edge_def;
typedef struct edge_def *edge;
typedef const struct edge_def *const_edge;
struct basic_block_def;
typedef struct basic_block_def *basic_block;
typedef const struct basic_block_def *const_basic_block;
#define obstack_chunk_alloc ((void *(*) (long)) xmalloc)
#define obstack_chunk_free ((void (*) (void *)) free)
#define OBSTACK_CHUNK_SIZE 0
#define gcc_obstack_init(OBSTACK) \
_obstack_begin ((OBSTACK), OBSTACK_CHUNK_SIZE, 0, \
obstack_chunk_alloc, \
obstack_chunk_free)
/* enum reg_class is target specific, so it should not appear in
target-independent code or interfaces, like the target hook declarations
in target.h. */
typedef int reg_class_t;
#else
struct _dont_use_rtx_here_;
struct _dont_use_rtvec_here_;
union _dont_use_tree_here_;
#define rtx struct _dont_use_rtx_here_ *
#define const_rtx struct _dont_use_rtx_here_ *
#define rtvec struct _dont_use_rtvec_here *
#define const_rtvec struct _dont_use_rtvec_here *
#define tree union _dont_use_tree_here_ *
#define const_tree union _dont_use_tree_here_ *
#endif
/* Memory model types for the __atomic* builtins.
This must match the order in libstdc++-v3/include/bits/atomic_base.h. */
enum memmodel
{
MEMMODEL_RELAXED = 0,
MEMMODEL_CONSUME = 1,
MEMMODEL_ACQUIRE = 2,
MEMMODEL_RELEASE = 3,
MEMMODEL_ACQ_REL = 4,
MEMMODEL_SEQ_CST = 5,
MEMMODEL_LAST = 6
};
/* Suppose that higher bits are target dependant. */
#define MEMMODEL_MASK ((1<<16)-1)
/* Support for user-provided GGC and PCH markers. The first parameter
is a pointer to a pointer, the second a cookie. */
typedef void (*gt_pointer_operator) (void *, void *);
#if !defined (HAVE_UCHAR)
typedef unsigned char uchar;
#endif
#endif /* coretypes.h */

479
src/include/cp/cp-tree.def Normal file
View File

@ -0,0 +1,479 @@
/* This file contains the definitions and documentation for the
additional tree codes used in the GNU C++ compiler (see tree.def
for the standard codes).
Copyright (C) 1987-2013 Free Software Foundation, Inc.
Hacked by Michael Tiemann (tiemann@cygnus.com)
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GCC is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
/* An OFFSET_REF is used in two situations:
1. An expression of the form `A::m' where `A' is a class and `m' is
a non-static member. In this case, operand 0 will be a TYPE
(corresponding to `A') and operand 1 will be a FIELD_DECL,
BASELINK, or TEMPLATE_ID_EXPR (corresponding to `m').
The expression is a pointer-to-member if its address is taken,
but simply denotes a member of the object if its address is not
taken.
This form is only used during the parsing phase; once semantic
analysis has taken place they are eliminated.
2. An expression of the form `x.*p'. In this case, operand 0 will
be an expression corresponding to `x' and operand 1 will be an
expression with pointer-to-member type. */
DEFTREECODE (OFFSET_REF, "offset_ref", tcc_reference, 2)
/* A pointer-to-member constant. For a pointer-to-member constant
`X::Y' The PTRMEM_CST_CLASS is the RECORD_TYPE for `X' and the
PTRMEM_CST_MEMBER is the _DECL for `Y'. */
DEFTREECODE (PTRMEM_CST, "ptrmem_cst", tcc_constant, 0)
/* For NEW_EXPR, operand 0 is the placement list.
Operand 1 is the new-declarator.
Operand 2 is the number of elements in the array.
Operand 3 is the initializer. */
DEFTREECODE (NEW_EXPR, "nw_expr", tcc_expression, 4)
DEFTREECODE (VEC_NEW_EXPR, "vec_nw_expr", tcc_expression, 3)
/* For DELETE_EXPR, operand 0 is the store to be destroyed.
Operand 1 is the value to pass to the destroying function
saying whether the store should be deallocated as well. */
DEFTREECODE (DELETE_EXPR, "dl_expr", tcc_expression, 2)
DEFTREECODE (VEC_DELETE_EXPR, "vec_dl_expr", tcc_expression, 2)
/* Value is reference to particular overloaded class method.
Operand 0 is the class, operand 1 is the field
The COMPLEXITY field holds the class level (usually 0). */
DEFTREECODE (SCOPE_REF, "scope_ref", tcc_reference, 2)
/* When composing an object with a member, this is the result.
Operand 0 is the object. Operand 1 is the member (usually
a dereferenced pointer to member). */
DEFTREECODE (MEMBER_REF, "member_ref", tcc_reference, 2)
/* Type conversion operator in C++. TREE_TYPE is type that this
operator converts to. Operand is expression to be converted. */
DEFTREECODE (TYPE_EXPR, "type_expr", tcc_expression, 1)
/* AGGR_INIT_EXPRs have a variably-sized representation similar to
that of CALL_EXPRs. Operand 0 is an INTEGER_CST node containing the
operand count, operand 1 is the function which performs initialization,
operand 2 is the slot which was allocated for this expression, and
the remaining operands are the arguments to the initialization function. */
DEFTREECODE (AGGR_INIT_EXPR, "aggr_init_expr", tcc_vl_exp, 3)
/* Initialization of an array from another array, expressed at a high level
so that it works with TARGET_EXPR. Operand 0 is the target, operand 1
is the initializer. */
DEFTREECODE (VEC_INIT_EXPR, "vec_init_expr", tcc_expression, 2)
/* A throw expression. operand 0 is the expression, if there was one,
else it is NULL_TREE. */
DEFTREECODE (THROW_EXPR, "throw_expr", tcc_expression, 1)
/* An empty class object. The TREE_TYPE gives the class type. We use
these to avoid actually creating instances of the empty classes. */
DEFTREECODE (EMPTY_CLASS_EXPR, "empty_class_expr", tcc_expression, 0)
/* A reference to a member function or member functions from a base
class. BASELINK_FUNCTIONS gives the FUNCTION_DECL,
TEMPLATE_DECL, OVERLOAD, or TEMPLATE_ID_EXPR corresponding to the
functions. BASELINK_BINFO gives the base from which the functions
come, i.e., the base to which the `this' pointer must be converted
before the functions are called. BASELINK_ACCESS_BINFO gives the
base used to name the functions.
A BASELINK is an expression; the TREE_TYPE of the BASELINK gives
the type of the expression. This type is either a FUNCTION_TYPE,
METHOD_TYPE, or `unknown_type_node' indicating that the function is
overloaded. */
DEFTREECODE (BASELINK, "baselink", tcc_exceptional, 0)
/* Template definition. The following fields have the specified uses,
although there are other macros in cp-tree.h that should be used for
accessing this data.
DECL_ARGUMENTS template parm vector
DECL_TEMPLATE_INFO template text &c
DECL_VINDEX list of instantiations already produced;
only done for functions so far
For class template:
DECL_INITIAL associated templates (methods &c)
DECL_TEMPLATE_RESULT null
For non-class templates:
TREE_TYPE type of object to be constructed
DECL_TEMPLATE_RESULT decl for object to be created
(e.g., FUNCTION_DECL with tmpl parms used)
*/
DEFTREECODE (TEMPLATE_DECL, "template_decl", tcc_declaration, 0)
/* Index into a template parameter list. The TEMPLATE_PARM_IDX gives
the index (from 0) of the parameter, while the TEMPLATE_PARM_LEVEL
gives the level (from 1) of the parameter.
Here's an example:
template <class T> // Index 0, Level 1.
struct S
{
template <class U, // Index 0, Level 2.
class V> // Index 1, Level 2.
void f();
};
The DESCENDANTS will be a chain of TEMPLATE_PARM_INDEXs descended
from this one. The first descendant will have the same IDX, but
its LEVEL will be one less. The TREE_CHAIN field is used to chain
together the descendants. The TEMPLATE_PARM_DECL is the
declaration of this parameter, either a TYPE_DECL or CONST_DECL.
The TEMPLATE_PARM_ORIG_LEVEL is the LEVEL of the most distant
parent, i.e., the LEVEL that the parameter originally had when it
was declared. For example, if we instantiate S<int>, we will have:
struct S<int>
{
template <class U, // Index 0, Level 1, Orig Level 2
class V> // Index 1, Level 1, Orig Level 2
void f();
};
The LEVEL is the level of the parameter when we are worrying about
the types of things; the ORIG_LEVEL is the level when we are
worrying about instantiating things. */
DEFTREECODE (TEMPLATE_PARM_INDEX, "template_parm_index", tcc_exceptional, 0)
/* Index into a template parameter list for template template parameters.
This parameter must be a type. The TYPE_FIELDS value will be a
TEMPLATE_PARM_INDEX.
It is used without template arguments like TT in C<TT>,
TEMPLATE_TEMPLATE_PARM_TEMPLATE_INFO is NULL_TREE
and TYPE_NAME is a TEMPLATE_DECL. */
DEFTREECODE (TEMPLATE_TEMPLATE_PARM, "template_template_parm", tcc_type, 0)
/* The ordering of the following codes is optimized for the checking
macros in tree.h. Changing the order will degrade the speed of the
compiler. TEMPLATE_TYPE_PARM, TYPENAME_TYPE, TYPEOF_TYPE,
BOUND_TEMPLATE_TEMPLATE_PARM. */
/* Index into a template parameter list. This parameter must be a type.
The type.values field will be a TEMPLATE_PARM_INDEX. */
DEFTREECODE (TEMPLATE_TYPE_PARM, "template_type_parm", tcc_type, 0)
/* A type designated by `typename T::t'. TYPE_CONTEXT is `T',
TYPE_NAME is an IDENTIFIER_NODE for `t'. If the type was named via
template-id, TYPENAME_TYPE_FULLNAME will hold the TEMPLATE_ID_EXPR.
TREE_TYPE is always NULL. */
DEFTREECODE (TYPENAME_TYPE, "typename_type", tcc_type, 0)
/* A type designated by `__typeof (expr)'. TYPEOF_TYPE_EXPR is the
expression in question. */
DEFTREECODE (TYPEOF_TYPE, "typeof_type", tcc_type, 0)
/* Like TEMPLATE_TEMPLATE_PARM it is used with bound template arguments
like TT<int>.
In this case, TEMPLATE_TEMPLATE_PARM_TEMPLATE_INFO contains the
template name and its bound arguments. TYPE_NAME is a TYPE_DECL. */
DEFTREECODE (BOUND_TEMPLATE_TEMPLATE_PARM, "bound_template_template_parm",
tcc_type, 0)
/* For template template argument of the form `T::template C'.
TYPE_CONTEXT is `T', the template parameter dependent object.
TYPE_NAME is an IDENTIFIER_NODE for `C', the member class template. */
DEFTREECODE (UNBOUND_CLASS_TEMPLATE, "unbound_class_template", tcc_type, 0)
/* A using declaration. USING_DECL_SCOPE contains the specified
scope. In a member using decl, unless DECL_DEPENDENT_P is true,
USING_DECL_DECLS contains the _DECL or OVERLOAD so named. This is
not an alias, but is later expanded into multiple aliases. */
DEFTREECODE (USING_DECL, "using_decl", tcc_declaration, 0)
/* A using directive. The operand is USING_STMT_NAMESPACE. */
DEFTREECODE (USING_STMT, "using_stmt", tcc_statement, 1)
/* An un-parsed default argument. Holds a vector of input tokens and
a vector of places where the argument was instantiated before
parsing had occurred. */
DEFTREECODE (DEFAULT_ARG, "default_arg", tcc_exceptional, 0)
/* An uninstantiated noexcept-specification. DEFERRED_NOEXCEPT_PATTERN is
the pattern from the template, and DEFERRED_NOEXCEPT_ARGS are the
template arguments to substitute into the pattern when needed. */
DEFTREECODE (DEFERRED_NOEXCEPT, "deferred_noexcept", tcc_exceptional, 0)
/* A template-id, like foo<int>. The first operand is the template.
The second is NULL if there are no explicit arguments, or a
TREE_VEC of arguments. The template will be a FUNCTION_DECL,
TEMPLATE_DECL, or an OVERLOAD. If the template-id refers to a
member template, the template may be an IDENTIFIER_NODE. */
DEFTREECODE (TEMPLATE_ID_EXPR, "template_id_expr", tcc_expression, 2)
/* A list-like node for chaining overloading candidates. TREE_TYPE is
the original name, and the parameter is the FUNCTION_DECL. */
DEFTREECODE (OVERLOAD, "overload", tcc_exceptional, 0)
/* A pseudo-destructor, of the form "OBJECT.~DESTRUCTOR" or
"OBJECT.SCOPE::~DESTRUCTOR. The first operand is the OBJECT. The
second operand (if non-NULL) is the SCOPE. The third operand is
the TYPE node corresponding to the DESTRUCTOR. The type of the
first operand will always be a scalar type.
The type of a PSEUDO_DTOR_EXPR is always "void", even though it can
be used as if it were a zero-argument function. We handle the
function-call case specially, and giving it "void" type prevents it
being used in expressions in ways that are not permitted. */
DEFTREECODE (PSEUDO_DTOR_EXPR, "pseudo_dtor_expr", tcc_expression, 3)
/* A whole bunch of tree codes for the initial, superficial parsing of
templates. */
DEFTREECODE (MODOP_EXPR, "modop_expr", tcc_expression, 3)
DEFTREECODE (CAST_EXPR, "cast_expr", tcc_unary, 1)
DEFTREECODE (REINTERPRET_CAST_EXPR, "reinterpret_cast_expr", tcc_unary, 1)
DEFTREECODE (CONST_CAST_EXPR, "const_cast_expr", tcc_unary, 1)
DEFTREECODE (STATIC_CAST_EXPR, "static_cast_expr", tcc_unary, 1)
DEFTREECODE (DYNAMIC_CAST_EXPR, "dynamic_cast_expr", tcc_unary, 1)
DEFTREECODE (IMPLICIT_CONV_EXPR, "implicit_conv_expr", tcc_unary, 1)
DEFTREECODE (DOTSTAR_EXPR, "dotstar_expr", tcc_expression, 2)
DEFTREECODE (TYPEID_EXPR, "typeid_expr", tcc_expression, 1)
DEFTREECODE (NOEXCEPT_EXPR, "noexcept_expr", tcc_unary, 1)
/* A placeholder for an expression that is not type-dependent, but
does occur in a template. When an expression that is not
type-dependent appears in a larger expression, we must compute the
type of that larger expression. That computation would normally
modify the original expression, which would change the mangling of
that expression if it appeared in a template argument list. In
that situation, we create a NON_DEPENDENT_EXPR to take the place of
the original expression. The expression is the only operand -- it
is only needed for diagnostics. */
DEFTREECODE (NON_DEPENDENT_EXPR, "non_dependent_expr", tcc_expression, 1)
/* CTOR_INITIALIZER is a placeholder in template code for a call to
setup_vtbl_pointer (and appears in all functions, not just ctors). */
DEFTREECODE (CTOR_INITIALIZER, "ctor_initializer", tcc_expression, 1)
DEFTREECODE (TRY_BLOCK, "try_block", tcc_statement, 2)
DEFTREECODE (EH_SPEC_BLOCK, "eh_spec_block", tcc_statement, 2)
/* A HANDLER wraps a catch handler for the HANDLER_TYPE. If this is
CATCH_ALL_TYPE, then the handler catches all types. The declaration of
the catch variable is in HANDLER_PARMS, and the body block in
HANDLER_BODY. */
DEFTREECODE (HANDLER, "handler", tcc_statement, 2)
/* A MUST_NOT_THROW_EXPR wraps an expression that may not
throw, and must call terminate if it does. The second argument
is a condition, used in templates to express noexcept (condition). */
DEFTREECODE (MUST_NOT_THROW_EXPR, "must_not_throw_expr", tcc_expression, 2)
/* A CLEANUP_STMT marks the point at which a declaration is fully
constructed. The CLEANUP_EXPR is run on behalf of CLEANUP_DECL
when CLEANUP_BODY completes. */
DEFTREECODE (CLEANUP_STMT, "cleanup_stmt", tcc_statement, 3)
/* Represents an 'if' statement. The operands are IF_COND,
THEN_CLAUSE, and ELSE_CLAUSE, and the current scope, respectively. */
/* ??? It is currently still necessary to distinguish between IF_STMT
and COND_EXPR for the benefit of templates. */
DEFTREECODE (IF_STMT, "if_stmt", tcc_statement, 4)
/* Used to represent a `for' statement. The operands are
FOR_INIT_STMT, FOR_COND, FOR_EXPR, and FOR_BODY, respectively. */
DEFTREECODE (FOR_STMT, "for_stmt", tcc_statement, 5)
/* Used to represent a range-based `for' statement. The operands are
RANGE_FOR_DECL, RANGE_FOR_EXPR, RANGE_FOR_BODY, and RANGE_FOR_SCOPE,
respectively. Only used in templates. */
DEFTREECODE (RANGE_FOR_STMT, "range_for_stmt", tcc_statement, 4)
/* Used to represent a 'while' statement. The operands are WHILE_COND
and WHILE_BODY, respectively. */
DEFTREECODE (WHILE_STMT, "while_stmt", tcc_statement, 2)
/* Used to represent a 'do' statement. The operands are DO_BODY and
DO_COND, respectively. */
DEFTREECODE (DO_STMT, "do_stmt", tcc_statement, 2)
/* Used to represent a 'break' statement. */
DEFTREECODE (BREAK_STMT, "break_stmt", tcc_statement, 0)
/* Used to represent a 'continue' statement. */
DEFTREECODE (CONTINUE_STMT, "continue_stmt", tcc_statement, 0)
/* Used to represent a 'switch' statement. The operands are
SWITCH_STMT_COND, SWITCH_STMT_BODY, SWITCH_STMT_TYPE, and
SWITCH_STMT_SCOPE, respectively. */
DEFTREECODE (SWITCH_STMT, "switch_stmt", tcc_statement, 4)
/* Used to represent an expression statement. Use `EXPR_STMT_EXPR' to
obtain the expression. */
DEFTREECODE (EXPR_STMT, "expr_stmt", tcc_expression, 1)
DEFTREECODE (TAG_DEFN, "tag_defn", tcc_expression, 0)
/* Represents an 'offsetof' expression during template expansion. */
DEFTREECODE (OFFSETOF_EXPR, "offsetof_expr", tcc_expression, 1)
/* Represents the -> operator during template expansion. */
DEFTREECODE (ARROW_EXPR, "arrow_expr", tcc_expression, 1)
/* Represents an '__alignof__' expression during template
expansion. */
DEFTREECODE (ALIGNOF_EXPR, "alignof_expr", tcc_expression, 1)
/* Represents an Objective-C++ '@encode' expression during template
expansion. */
DEFTREECODE (AT_ENCODE_EXPR, "at_encode_expr", tcc_expression, 1)
/* A STMT_EXPR represents a statement-expression during template
expansion. This is the GCC extension { ( ... ) }. The
STMT_EXPR_STMT is the statement given by the expression. */
DEFTREECODE (STMT_EXPR, "stmt_expr", tcc_expression, 1)
/* Unary plus. Operand 0 is the expression to which the unary plus
is applied. */
DEFTREECODE (UNARY_PLUS_EXPR, "unary_plus_expr", tcc_unary, 1)
/** C++0x extensions. */
/* A static assertion. This is a C++0x extension.
STATIC_ASSERT_CONDITION contains the condition that is being
checked. STATIC_ASSERT_MESSAGE contains the message (a string
literal) to be displayed if the condition fails to hold. */
DEFTREECODE (STATIC_ASSERT, "static_assert", tcc_exceptional, 0)
/* Represents an argument pack of types (or templates). An argument
pack stores zero or more arguments that will be used to instantiate
a parameter pack.
ARGUMENT_PACK_ARGS retrieves the arguments stored in the argument
pack.
Example:
template<typename... Values>
class tuple { ... };
tuple<int, float, double> t;
Values is a (template) parameter pack. When tuple<int, float,
double> is instantiated, the Values parameter pack is instantiated
with the argument pack <int, float, double>. ARGUMENT_PACK_ARGS will
be a TREE_VEC containing int, float, and double. */
DEFTREECODE (TYPE_ARGUMENT_PACK, "type_argument_pack", tcc_type, 0)
/* Represents an argument pack of values, which can be used either for
non-type template arguments or function call arguments.
NONTYPE_ARGUMENT_PACK plays precisely the same role as
TYPE_ARGUMENT_PACK, but will be used for packing non-type template
arguments (e.g., "int... Dimensions") or function arguments ("const
Args&... args"). */
DEFTREECODE (NONTYPE_ARGUMENT_PACK, "nontype_argument_pack", tcc_expression, 1)
/* Represents a type expression that will be expanded into a list of
types when instantiated with one or more argument packs.
PACK_EXPANSION_PATTERN retrieves the expansion pattern. This is
the type or expression that we will substitute into with each
argument in an argument pack.
SET_PACK_EXPANSION_PATTERN sets the expansion pattern.
PACK_EXPANSION_PARAMETER_PACKS contains a TREE_LIST of the parameter
packs that are used in this pack expansion.
Example:
template<typename... Values>
struct tied : tuple<Values&...> {
// ...
};
The derivation from tuple contains a TYPE_PACK_EXPANSION for the
template arguments. Its PACK_EXPANSION_PATTERN is "Values&" and its
PACK_EXPANSION_PARAMETER_PACKS will contain "Values". */
DEFTREECODE (TYPE_PACK_EXPANSION, "type_pack_expansion", tcc_type, 0)
/* Represents an expression that will be expanded into a list of
expressions when instantiated with one or more argument packs.
EXPR_PACK_EXPANSION plays precisely the same role as TYPE_PACK_EXPANSION,
but will be used for expressions. */
DEFTREECODE (EXPR_PACK_EXPANSION, "expr_pack_expansion", tcc_expression, 3)
/* Selects the Ith parameter out of an argument pack. This node will
be used when instantiating pack expansions; see
tsubst_pack_expansion.
ARGUMENT_PACK_SELECT_FROM_PACK contains the *_ARGUMENT_PACK node
from which the argument will be selected.
ARGUMENT_PACK_SELECT_INDEX contains the index into the argument
pack that will be returned by this ARGUMENT_PACK_SELECT node. The
index is a machine integer. */
DEFTREECODE (ARGUMENT_PACK_SELECT, "argument_pack_select", tcc_exceptional, 0)
/** C++ extensions. */
/* Represents a trait expression during template expansion. */
DEFTREECODE (TRAIT_EXPR, "trait_expr", tcc_exceptional, 0)
/* A lambda expression. This is a C++0x extension.
LAMBDA_EXPR_DEFAULT_CAPTURE_MODE is an enum for the default, which may be
none.
LAMBDA_EXPR_CAPTURE_LIST holds the capture-list, including `this'.
LAMBDA_EXPR_THIS_CAPTURE goes straight to the capture of `this', if it exists.
LAMBDA_EXPR_PENDING_PROXIES is a vector of capture proxies which need to
be pushed once scope returns to the lambda.
LAMBDA_EXPR_MUTABLE_P signals whether this lambda was declared mutable.
LAMBDA_EXPR_RETURN_TYPE holds the return type, if it was specified. */
DEFTREECODE (LAMBDA_EXPR, "lambda_expr", tcc_exceptional, 0)
/* The declared type of an expression. This is a C++0x extension.
DECLTYPE_TYPE_EXPR is the expression whose type we are computing.
DECLTYPE_TYPE_ID_EXPR_OR_MEMBER_ACCESS_P states whether the
expression was parsed as an id-expression or a member access
expression. When false, it was parsed as a full expression.
DECLTYPE_FOR_LAMBDA_CAPTURE is set if we want lambda capture semantics.
DECLTYPE_FOR_LAMBDA_RETURN is set if we want lambda return deduction. */
DEFTREECODE (DECLTYPE_TYPE, "decltype_type", tcc_type, 0)
/* A type designated by `__underlying_type (type)'.
UNDERLYING_TYPE_TYPE is the type in question. */
DEFTREECODE (UNDERLYING_TYPE, "underlying_type", tcc_type, 0)
/* A type designated by one of the bases type traits.
BASES_TYPE is the type in question. */
DEFTREECODE (BASES, "bases", tcc_type, 0)
/* Used to represent the template information stored by template
specializations.
The accessors are:
TI_TEMPLATE the template declaration associated to the specialization
TI_ARGS the arguments of the template specialization
TI_TYPEDEFS_NEEDING_ACCESS_CHECKING the vector of typedefs used in
the pattern of the template for which access check is needed at template
instantiation time. */
DEFTREECODE (TEMPLATE_INFO, "template_info", tcc_exceptional, 0)
/*
Local variables:
mode:c
End:
*/

6095
src/include/cp/cp-tree.h Normal file

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,79 @@
/* Interface for the GNU C++ pretty-printer.
Copyright (C) 2003-2013 Free Software Foundation, Inc.
Contributed by Gabriel Dos Reis <gdr@integrable-solutions.net>
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GCC_CXX_PRETTY_PRINT_H
#define GCC_CXX_PRETTY_PRINT_H
#include "c-family/c-pretty-print.h"
#undef pp_c_base
#define pp_c_base(PP) (&(PP)->c_base)
typedef enum
{
/* Ask for a qualified-id. */
pp_cxx_flag_default_argument = 1 << pp_c_flag_last_bit
} cxx_pretty_printer_flags;
typedef struct
{
c_pretty_printer c_base;
/* This is the enclosing scope of the entity being pretty-printed. */
tree enclosing_scope;
} cxx_pretty_printer;
#define pp_cxx_cv_qualifier_seq(PP, T) \
pp_c_type_qualifier_list (pp_c_base (PP), T)
#define pp_cxx_whitespace(PP) pp_c_whitespace (pp_c_base (PP))
#define pp_cxx_left_paren(PP) pp_c_left_paren (pp_c_base (PP))
#define pp_cxx_right_paren(PP) pp_c_right_paren (pp_c_base (PP))
#define pp_cxx_left_brace(PP) pp_c_left_brace (pp_c_base (PP))
#define pp_cxx_right_brace(PP) pp_c_right_brace (pp_c_base (PP))
#define pp_cxx_left_bracket(PP) pp_c_left_bracket (pp_c_base (PP))
#define pp_cxx_right_bracket(PP) pp_c_right_bracket (pp_c_base (PP))
#define pp_cxx_dot(PP) pp_c_dot (pp_c_base (PP))
#define pp_cxx_ampersand(PP) pp_c_ampersand (pp_c_base (PP))
#define pp_cxx_star(PP) pp_c_star (pp_c_base (PP))
#define pp_cxx_arrow(PP) pp_c_arrow (pp_c_base (PP))
#define pp_cxx_semicolon(PP) pp_c_semicolon (pp_c_base (PP))
#define pp_cxx_complement(PP) pp_c_complement (pp_c_base (PP))
#define pp_cxx_ws_string(PP, I) pp_c_ws_string (pp_c_base (PP), I)
#define pp_cxx_identifier(PP, I) pp_c_identifier (pp_c_base (PP), I)
#define pp_cxx_tree_identifier(PP, T) \
pp_c_tree_identifier (pp_c_base (PP), T)
void pp_cxx_pretty_printer_init (cxx_pretty_printer *);
void pp_cxx_begin_template_argument_list (cxx_pretty_printer *);
void pp_cxx_end_template_argument_list (cxx_pretty_printer *);
void pp_cxx_colon_colon (cxx_pretty_printer *);
void pp_cxx_separate_with (cxx_pretty_printer *, int);
void pp_cxx_declaration (cxx_pretty_printer *, tree);
void pp_cxx_canonical_template_parameter (cxx_pretty_printer *, tree);
void pp_cxx_trait_expression (cxx_pretty_printer *, tree);
void pp_cxx_va_arg_expression (cxx_pretty_printer *, tree);
void pp_cxx_offsetof_expression (cxx_pretty_printer *, tree);
void pp_cxx_userdef_literal (cxx_pretty_printer *, tree);
#endif /* GCC_CXX_PRETTY_PRINT_H */

View File

@ -0,0 +1,369 @@
/* Declarations for C++ name lookup routines.
Copyright (C) 2003-2013 Free Software Foundation, Inc.
Contributed by Gabriel Dos Reis <gdr@integrable-solutions.net>
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GCC is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GCC_CP_NAME_LOOKUP_H
#define GCC_CP_NAME_LOOKUP_H
#include "c-family/c-common.h"
/* The type of dictionary used to map names to types declared at
a given scope. */
typedef struct binding_table_s *binding_table;
typedef struct binding_entry_s *binding_entry;
/* The type of a routine repeatedly called by binding_table_foreach. */
typedef void (*bt_foreach_proc) (binding_entry, void *);
struct GTY(()) binding_entry_s {
binding_entry chain;
tree name;
tree type;
};
/* These macros indicate the initial chains count for binding_table. */
#define SCOPE_DEFAULT_HT_SIZE (1 << 3)
#define CLASS_SCOPE_HT_SIZE (1 << 3)
#define NAMESPACE_ORDINARY_HT_SIZE (1 << 5)
#define NAMESPACE_STD_HT_SIZE (1 << 8)
#define GLOBAL_SCOPE_HT_SIZE (1 << 8)
extern void binding_table_foreach (binding_table, bt_foreach_proc, void *);
extern binding_entry binding_table_find (binding_table, tree);
/* Datatype that represents binding established by a declaration between
a name and a C++ entity. */
typedef struct cxx_binding cxx_binding;
/* The datatype used to implement C++ scope. */
typedef struct cp_binding_level cp_binding_level;
/* Nonzero if this binding is for a local scope, as opposed to a class
or namespace scope. */
#define LOCAL_BINDING_P(NODE) ((NODE)->is_local)
/* True if NODE->value is from a base class of the class which is
currently being defined. */
#define INHERITED_VALUE_BINDING_P(NODE) ((NODE)->value_is_inherited)
struct GTY(()) cxx_binding {
/* Link to chain together various bindings for this name. */
cxx_binding *previous;
/* The non-type entity this name is bound to. */
tree value;
/* The type entity this name is bound to. */
tree type;
/* The scope at which this binding was made. */
cp_binding_level *scope;
unsigned value_is_inherited : 1;
unsigned is_local : 1;
};
/* Datatype used to temporarily save C++ bindings (for implicit
instantiations purposes and like). Implemented in decl.c. */
typedef struct GTY(()) cxx_saved_binding {
/* The name of the current binding. */
tree identifier;
/* The binding we're saving. */
cxx_binding *binding;
tree real_type_value;
} cxx_saved_binding;
extern tree identifier_type_value (tree);
extern void set_identifier_type_value (tree, tree);
extern void pop_binding (tree, tree);
extern tree constructor_name (tree);
extern bool constructor_name_p (tree, tree);
/* The kinds of scopes we recognize. */
typedef enum scope_kind {
sk_block = 0, /* An ordinary block scope. This enumerator must
have the value zero because "cp_binding_level"
is initialized by using "memset" to set the
contents to zero, and the default scope kind
is "sk_block". */
sk_cleanup, /* A scope for (pseudo-)scope for cleanup. It is
pseudo in that it is transparent to name lookup
activities. */
sk_try, /* A try-block. */
sk_catch, /* A catch-block. */
sk_for, /* The scope of the variable declared in a
for-init-statement. */
sk_cond, /* The scope of the variable declared in the condition
of an if or switch statement. */
sk_function_parms, /* The scope containing function parameters. */
sk_class, /* The scope containing the members of a class. */
sk_scoped_enum, /* The scope containing the enumertors of a C++0x
scoped enumeration. */
sk_namespace, /* The scope containing the members of a
namespace, including the global scope. */
sk_template_parms, /* A scope for template parameters. */
sk_template_spec, /* Like sk_template_parms, but for an explicit
specialization. Since, by definition, an
explicit specialization is introduced by
"template <>", this scope is always empty. */
sk_omp /* An OpenMP structured block. */
} scope_kind;
/* The scope where the class/struct/union/enum tag applies. */
typedef enum tag_scope {
ts_current = 0, /* Current scope only. This is for the
class-key identifier;
case mentioned in [basic.lookup.elab]/2,
or the class/enum definition
class-key identifier { ... }; */
ts_global = 1, /* All scopes. This is the 3.4.1
[basic.lookup.unqual] lookup mentioned
in [basic.lookup.elab]/2. */
ts_within_enclosing_non_class = 2, /* Search within enclosing non-class
only, for friend class lookup
according to [namespace.memdef]/3
and [class.friend]/9. */
ts_lambda = 3 /* Declaring a lambda closure. */
} tag_scope;
typedef struct GTY(()) cp_class_binding {
cxx_binding *base;
/* The bound name. */
tree identifier;
} cp_class_binding;
typedef struct GTY(()) cp_label_binding {
/* The bound LABEL_DECL. */
tree label;
/* The previous IDENTIFIER_LABEL_VALUE. */
tree prev_value;
} cp_label_binding;
/* For each binding contour we allocate a binding_level structure
which records the names defined in that contour.
Contours include:
0) the global one
1) one for each function definition,
where internal declarations of the parameters appear.
2) one for each compound statement,
to record its declarations.
The current meaning of a name can be found by searching the levels
from the current one out to the global one.
Off to the side, may be the class_binding_level. This exists only
to catch class-local declarations. It is otherwise nonexistent.
Also there may be binding levels that catch cleanups that must be
run when exceptions occur. Thus, to see whether a name is bound in
the current scope, it is not enough to look in the
CURRENT_BINDING_LEVEL. You should use lookup_name_current_level
instead. */
/* Note that the information in the `names' component of the global contour
is duplicated in the IDENTIFIER_GLOBAL_VALUEs of all identifiers. */
struct GTY(()) cp_binding_level {
/* A chain of _DECL nodes for all variables, constants, functions,
and typedef types. These are in the reverse of the order
supplied. There may be OVERLOADs on this list, too, but they
are wrapped in TREE_LISTs; the TREE_VALUE is the OVERLOAD. */
tree names;
/* A chain of NAMESPACE_DECL nodes. */
tree namespaces;
/* An array of static functions and variables (for namespaces only) */
vec<tree, va_gc> *static_decls;
/* A list of USING_DECL nodes. */
tree usings;
/* A list of used namespaces. PURPOSE is the namespace,
VALUE the common ancestor with this binding_level's namespace. */
tree using_directives;
/* For the binding level corresponding to a class, the entities
declared in the class or its base classes. */
vec<cp_class_binding, va_gc> *class_shadowed;
/* Similar to class_shadowed, but for IDENTIFIER_TYPE_VALUE, and
is used for all binding levels. The TREE_PURPOSE is the name of
the entity, the TREE_TYPE is the associated type. In addition
the TREE_VALUE is the IDENTIFIER_TYPE_VALUE before we entered
the class. */
tree type_shadowed;
/* Similar to class_shadowed, but for IDENTIFIER_LABEL_VALUE, and
used for all binding levels. */
vec<cp_label_binding, va_gc> *shadowed_labels;
/* For each level (except not the global one),
a chain of BLOCK nodes for all the levels
that were entered and exited one level down. */
tree blocks;
/* The entity (namespace, class, function) the scope of which this
binding contour corresponds to. Otherwise NULL. */
tree this_entity;
/* The binding level which this one is contained in (inherits from). */
cp_binding_level *level_chain;
/* List of VAR_DECLS saved from a previous for statement.
These would be dead in ISO-conforming code, but might
be referenced in ARM-era code. */
vec<tree, va_gc> *dead_vars_from_for;
/* STATEMENT_LIST for statements in this binding contour.
Only used at present for SK_CLEANUP temporary bindings. */
tree statement_list;
/* Binding depth at which this level began. */
int binding_depth;
/* The kind of scope that this object represents. However, a
SK_TEMPLATE_SPEC scope is represented with KIND set to
SK_TEMPLATE_PARMS and EXPLICIT_SPEC_P set to true. */
ENUM_BITFIELD (scope_kind) kind : 4;
/* True if this scope is an SK_TEMPLATE_SPEC scope. This field is
only valid if KIND == SK_TEMPLATE_PARMS. */
BOOL_BITFIELD explicit_spec_p : 1;
/* true means make a BLOCK for this level regardless of all else. */
unsigned keep : 1;
/* Nonzero if this level can safely have additional
cleanup-needing variables added to it. */
unsigned more_cleanups_ok : 1;
unsigned have_cleanups : 1;
/* 24 bits left to fill a 32-bit word. */
};
/* The binding level currently in effect. */
#define current_binding_level \
(*(cfun && cp_function_chain && cp_function_chain->bindings \
? &cp_function_chain->bindings \
: &scope_chain->bindings))
/* The binding level of the current class, if any. */
#define class_binding_level scope_chain->class_bindings
/* The tree node representing the global scope. */
extern GTY(()) tree global_namespace;
extern GTY(()) tree global_scope_name;
/* Indicates that there is a type value in some namespace, although
that is not necessarily in scope at the moment. */
extern GTY(()) tree global_type_node;
/* True if SCOPE designates the global scope binding contour. */
#define global_scope_p(SCOPE) \
((SCOPE) == NAMESPACE_LEVEL (global_namespace))
extern cp_binding_level *leave_scope (void);
extern bool kept_level_p (void);
extern bool global_bindings_p (void);
extern bool toplevel_bindings_p (void);
extern bool namespace_bindings_p (void);
extern bool local_bindings_p (void);
extern bool template_parm_scope_p (void);
extern scope_kind innermost_scope_kind (void);
extern cp_binding_level *begin_scope (scope_kind, tree);
extern void print_binding_stack (void);
extern void push_to_top_level (void);
extern void pop_from_top_level (void);
extern void pop_everything (void);
extern void keep_next_level (bool);
extern bool is_ancestor (tree, tree);
extern tree push_scope (tree);
extern void pop_scope (tree);
extern tree push_inner_scope (tree);
extern void pop_inner_scope (tree, tree);
extern void push_binding_level (cp_binding_level *);
extern void push_namespace (tree);
extern void pop_namespace (void);
extern void push_nested_namespace (tree);
extern void pop_nested_namespace (tree);
extern bool handle_namespace_attrs (tree, tree);
extern void pushlevel_class (void);
extern void poplevel_class (void);
extern tree pushdecl_with_scope (tree, cp_binding_level *, bool);
extern tree lookup_name_prefer_type (tree, int);
extern tree lookup_name_real (tree, int, int, bool, int, int);
extern tree lookup_type_scope (tree, tag_scope);
extern tree namespace_binding (tree, tree);
extern void set_namespace_binding (tree, tree, tree);
extern bool hidden_name_p (tree);
extern tree remove_hidden_names (tree);
extern tree lookup_qualified_name (tree, tree, bool, bool);
extern tree lookup_name_nonclass (tree);
extern tree lookup_name_innermost_nonclass_level (tree);
extern bool is_local_extern (tree);
extern tree lookup_function_nonclass (tree, vec<tree, va_gc> *, bool);
extern void push_local_binding (tree, tree, int);
extern bool pushdecl_class_level (tree);
extern tree pushdecl_namespace_level (tree, bool);
extern bool push_class_level_binding (tree, tree);
extern tree getdecls (void);
extern int function_parm_depth (void);
extern tree cp_namespace_decls (tree);
extern void set_decl_namespace (tree, tree, bool);
extern void push_decl_namespace (tree);
extern void pop_decl_namespace (void);
extern void do_namespace_alias (tree, tree);
extern void do_toplevel_using_decl (tree, tree, tree);
extern void do_local_using_decl (tree, tree, tree);
extern tree do_class_using_decl (tree, tree);
extern void do_using_directive (tree);
extern tree lookup_arg_dependent (tree, tree, vec<tree, va_gc> *, bool);
extern bool is_associated_namespace (tree, tree);
extern void parse_using_directive (tree, tree);
extern tree innermost_non_namespace_value (tree);
extern cxx_binding *outer_binding (tree, cxx_binding *, bool);
extern void cp_emit_debug_info_for_using (tree, tree);
/* Set *DECL to the (non-hidden) declaration for ID at global scope,
if present and return true; otherwise return false. */
static inline bool
get_global_value_if_present (tree id, tree *decl)
{
tree global_value = namespace_binding (id, global_namespace);
if (global_value)
*decl = global_value;
return global_value != NULL;
}
/* True is the binding of IDENTIFIER at global scope names a type. */
static inline bool
is_typename_at_global_scope (tree id)
{
tree global_value = namespace_binding (id, global_namespace);
return global_value && TREE_CODE (global_value) == TYPE_DECL;
}
#endif /* GCC_CP_NAME_LOOKUP_H */

71
src/include/cppdefault.h Normal file
View File

@ -0,0 +1,71 @@
/* CPP Library.
Copyright (C) 1986-2013 Free Software Foundation, Inc.
Contributed by Per Bothner, 1994-95.
Based on CCCP program by Paul Rubin, June 1986
Adapted to ANSI C, Richard Stallman, Jan 1987
This program is free software; you can redistribute it and/or modify it
under the terms of the GNU General Public License as published by the
Free Software Foundation; either version 3, or (at your option) any
later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GCC_CPPDEFAULT_H
#define GCC_CPPDEFAULT_H
/* This is the default list of directories to search for include files.
It may be overridden by the various -I and -ixxx options.
#include "file" looks in the same directory as the current file,
then this list.
#include <file> just looks in this list.
All these directories are treated as `system' include directories
(they are not subject to pedantic warnings in some cases). */
struct default_include
{
const char *const fname; /* The name of the directory. */
const char *const component; /* The component containing the directory
(see update_path in prefix.c) */
const char cplusplus; /* Only look here if we're compiling C++. */
const char cxx_aware; /* Includes in this directory don't need to
be wrapped in extern "C" when compiling
C++. */
const char add_sysroot; /* FNAME should be prefixed by
cpp_SYSROOT. */
const char multilib; /* FNAME should have appended
- the multilib path specified with -imultilib
when set to 1,
- the multiarch path specified with
-imultiarch, when set to 2. */
};
extern const struct default_include cpp_include_defaults[];
extern const char cpp_GCC_INCLUDE_DIR[];
extern const size_t cpp_GCC_INCLUDE_DIR_len;
/* The configure-time prefix, i.e., the value supplied as the argument
to --prefix=. */
extern const char cpp_PREFIX[];
/* The length of the configure-time prefix. */
extern const size_t cpp_PREFIX_len;
/* The configure-time execution prefix. This is typically the lib/gcc
subdirectory of cpp_PREFIX. */
extern const char cpp_EXEC_PREFIX[];
/* The run-time execution prefix. This is typically the lib/gcc
subdirectory of the actual installation. */
extern const char *gcc_exec_prefix;
/* Return true if the toolchain is relocated. */
bool cpp_relocated (void);
#endif /* ! GCC_CPPDEFAULT_H */

1059
src/include/cpplib.h Normal file

File diff suppressed because it is too large Load Diff

195
src/include/debug.h Normal file
View File

@ -0,0 +1,195 @@
/* Debug hooks for GCC.
Copyright (C) 2001-2013 Free Software Foundation, Inc.
This program is free software; you can redistribute it and/or modify it
under the terms of the GNU General Public License as published by the
Free Software Foundation; either version 3, or (at your option) any
later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GCC_DEBUG_H
#define GCC_DEBUG_H
/* This structure contains hooks for the debug information output
functions, accessed through the global instance debug_hooks set in
toplev.c according to command line options. */
struct gcc_debug_hooks
{
/* Initialize debug output. MAIN_FILENAME is the name of the main
input file. */
void (* init) (const char *main_filename);
/* Output debug symbols. */
void (* finish) (const char *main_filename);
/* Called from cgraph_optimize before starting to assemble
functions/variables/toplevel asms. */
void (* assembly_start) (void);
/* Macro defined on line LINE with name and expansion TEXT. */
void (* define) (unsigned int line, const char *text);
/* MACRO undefined on line LINE. */
void (* undef) (unsigned int line, const char *macro);
/* Record the beginning of a new source file FILE from LINE number
in the previous one. */
void (* start_source_file) (unsigned int line, const char *file);
/* Record the resumption of a source file. LINE is the line number
in the source file we are returning to. */
void (* end_source_file) (unsigned int line);
/* Record the beginning of block N, counting from 1 and not
including the function-scope block, at LINE. */
void (* begin_block) (unsigned int line, unsigned int n);
/* Record the end of a block. Arguments as for begin_block. */
void (* end_block) (unsigned int line, unsigned int n);
/* Returns nonzero if it is appropriate not to emit any debugging
information for BLOCK, because it doesn't contain any
instructions. This may not be the case for blocks containing
nested functions, since we may actually call such a function even
though the BLOCK information is messed up. Defaults to true. */
bool (* ignore_block) (const_tree);
/* Record a source file location at (FILE, LINE, DISCRIMINATOR). */
void (* source_line) (unsigned int line, const char *file,
int discriminator, bool is_stmt);
/* Called at start of prologue code. LINE is the first line in the
function. */
void (* begin_prologue) (unsigned int line, const char *file);
/* Called at end of prologue code. LINE is the first line in the
function. */
void (* end_prologue) (unsigned int line, const char *file);
/* Called at beginning of epilogue code. */
void (* begin_epilogue) (unsigned int line, const char *file);
/* Record end of epilogue code. */
void (* end_epilogue) (unsigned int line, const char *file);
/* Called at start of function DECL, before it is declared. */
void (* begin_function) (tree decl);
/* Record end of function. LINE is highest line number in function. */
void (* end_function) (unsigned int line);
/* Debug information for a function DECL. This might include the
function name (a symbol), its parameters, and the block that
makes up the function's body, and the local variables of the
function. */
void (* function_decl) (tree decl);
/* Debug information for a global DECL. Called from toplev.c after
compilation proper has finished. */
void (* global_decl) (tree decl);
/* Debug information for a type DECL. Called from toplev.c after
compilation proper, also from various language front ends to
record built-in types. The second argument is properly a
boolean, which indicates whether or not the type is a "local"
type as determined by the language. (It's not a boolean for
legacy reasons.) */
void (* type_decl) (tree decl, int local);
/* Debug information for imported modules and declarations. */
void (* imported_module_or_decl) (tree decl, tree name,
tree context, bool child);
/* DECL is an inline function, whose body is present, but which is
not being output at this point. */
void (* deferred_inline_function) (tree decl);
/* DECL is an inline function which is about to be emitted out of
line. The hook is useful to, e.g., emit abstract debug info for
the inline before it gets mangled by optimization. */
void (* outlining_inline_function) (tree decl);
/* Called from final_scan_insn for any CODE_LABEL insn whose
LABEL_NAME is non-null. */
void (* label) (rtx);
/* Called after the start and before the end of writing a PCH file.
The parameter is 0 if after the start, 1 if before the end. */
void (* handle_pch) (unsigned int);
/* Called from final_scan_insn for any NOTE_INSN_VAR_LOCATION note. */
void (* var_location) (rtx);
/* Called from final_scan_insn if there is a switch between hot and cold
text sections. */
void (* switch_text_section) (void);
/* Called from grokdeclarator. Replaces the anonymous name with the
type name. */
void (* set_name) (tree, tree);
/* This is 1 if the debug writer wants to see start and end commands for the
main source files, and 0 otherwise. */
int start_end_main_source_file;
/* The type of symtab field used by these debug hooks. This is one
of the TYPE_SYMTAB_IS_xxx values defined in tree.h. */
int tree_type_symtab_field;
};
extern const struct gcc_debug_hooks *debug_hooks;
/* The do-nothing hooks. */
extern void debug_nothing_void (void);
extern void debug_nothing_charstar (const char *);
extern void debug_nothing_int_charstar (unsigned int, const char *);
extern void debug_nothing_int_charstar_int_bool (unsigned int, const char *,
int, bool);
extern void debug_nothing_int (unsigned int);
extern void debug_nothing_int_int (unsigned int, unsigned int);
extern void debug_nothing_tree (tree);
extern void debug_nothing_tree_tree (tree, tree);
extern void debug_nothing_tree_int (tree, int);
extern void debug_nothing_tree_tree_tree_bool (tree, tree, tree, bool);
extern bool debug_true_const_tree (const_tree);
extern void debug_nothing_rtx (rtx);
extern void debug_nothing_rtx_rtx (rtx, rtx);
/* Hooks for various debug formats. */
extern const struct gcc_debug_hooks do_nothing_debug_hooks;
extern const struct gcc_debug_hooks dbx_debug_hooks;
extern const struct gcc_debug_hooks sdb_debug_hooks;
extern const struct gcc_debug_hooks xcoff_debug_hooks;
extern const struct gcc_debug_hooks dwarf2_debug_hooks;
extern const struct gcc_debug_hooks vmsdbg_debug_hooks;
/* Dwarf2 frame information. */
extern void dwarf2out_begin_prologue (unsigned int, const char *);
extern void dwarf2out_vms_end_prologue (unsigned int, const char *);
extern void dwarf2out_vms_begin_epilogue (unsigned int, const char *);
extern void dwarf2out_end_epilogue (unsigned int, const char *);
extern void dwarf2out_frame_finish (void);
/* Decide whether we want to emit frame unwind information for the current
translation unit. */
extern bool dwarf2out_do_frame (void);
extern bool dwarf2out_do_cfi_asm (void);
extern void dwarf2out_switch_text_section (void);
const char *remap_debug_filename (const char *);
void add_debug_prefix_map (const char *);
/* For -fdump-go-spec. */
extern const struct gcc_debug_hooks *
dump_go_spec_init (const char *, const struct gcc_debug_hooks *);
#endif /* !GCC_DEBUG_H */

1409
src/include/defaults.h Normal file

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,89 @@
/* Declarations of core diagnostic functionality for code that does
not need to deal with diagnostic contexts or diagnostic info
structures.
Copyright (C) 1998-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GCC_DIAGNOSTIC_CORE_H
#define GCC_DIAGNOSTIC_CORE_H
#include "input.h"
#include "bversion.h"
/* Constants used to discriminate diagnostics. */
typedef enum
{
#define DEFINE_DIAGNOSTIC_KIND(K, msgid) K,
#include "diagnostic.def"
#undef DEFINE_DIAGNOSTIC_KIND
DK_LAST_DIAGNOSTIC_KIND,
/* This is used for tagging pragma pops in the diagnostic
classification history chain. */
DK_POP
} diagnostic_t;
extern const char *progname;
extern const char *trim_filename (const char *);
/* If we haven't already defined a front-end-specific diagnostics
style, use the generic one. */
#ifndef GCC_DIAG_STYLE
#define GCC_DIAG_STYLE __gcc_tdiag__
#endif
/* None of these functions are suitable for ATTRIBUTE_PRINTF, because
each language front end can extend them with its own set of format
specifiers. We must use custom format checks. */
#if (ENABLE_CHECKING && GCC_VERSION >= 4001) || GCC_VERSION == BUILDING_GCC_VERSION
#define ATTRIBUTE_GCC_DIAG(m, n) __attribute__ ((__format__ (GCC_DIAG_STYLE, m, n))) ATTRIBUTE_NONNULL(m)
#else
#define ATTRIBUTE_GCC_DIAG(m, n) ATTRIBUTE_NONNULL(m)
#endif
extern void internal_error (const char *, ...) ATTRIBUTE_GCC_DIAG(1,2)
ATTRIBUTE_NORETURN;
/* Pass one of the OPT_W* from options.h as the first parameter. */
extern bool warning (int, const char *, ...) ATTRIBUTE_GCC_DIAG(2,3);
extern bool warning_at (location_t, int, const char *, ...)
ATTRIBUTE_GCC_DIAG(3,4);
extern void error (const char *, ...) ATTRIBUTE_GCC_DIAG(1,2);
extern void error_n (location_t, int, const char *, const char *, ...)
ATTRIBUTE_GCC_DIAG(3,5) ATTRIBUTE_GCC_DIAG(4,5);
extern void error_at (location_t, const char *, ...) ATTRIBUTE_GCC_DIAG(2,3);
extern void fatal_error (const char *, ...) ATTRIBUTE_GCC_DIAG(1,2)
ATTRIBUTE_NORETURN;
/* Pass one of the OPT_W* from options.h as the second parameter. */
extern bool pedwarn (location_t, int, const char *, ...)
ATTRIBUTE_GCC_DIAG(3,4);
extern bool permerror (location_t, const char *, ...) ATTRIBUTE_GCC_DIAG(2,3);
extern void sorry (const char *, ...) ATTRIBUTE_GCC_DIAG(1,2);
extern void inform (location_t, const char *, ...) ATTRIBUTE_GCC_DIAG(2,3);
extern void inform_n (location_t, int, const char *, const char *, ...)
ATTRIBUTE_GCC_DIAG(3,5) ATTRIBUTE_GCC_DIAG(4,5);
extern void verbatim (const char *, ...) ATTRIBUTE_GCC_DIAG(1,2);
extern bool emit_diagnostic (diagnostic_t, location_t, int,
const char *, ...) ATTRIBUTE_GCC_DIAG(4,5);
extern bool seen_error (void);
#ifdef BUFSIZ
/* N.B. Unlike all the others, fnotice is just gettext+fprintf, and
therefore it can have ATTRIBUTE_PRINTF. */
extern void fnotice (FILE *, const char *, ...)
ATTRIBUTE_PRINTF_2;
#endif
#endif /* ! GCC_DIAGNOSTIC_CORE_H */

View File

@ -0,0 +1,45 @@
/* Copyright (C) 2001-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
/* DK_UNSPECIFIED must be first so it has a value of zero. We never
assign this kind to an actual diagnostic, we only use this in
variables that can hold a kind, to mean they have yet to have a
kind specified. I.e. they're uninitialized. Within the diagnostic
machinery, this kind also means "don't change the existing kind",
meaning "no change is specified". */
DEFINE_DIAGNOSTIC_KIND (DK_UNSPECIFIED, "")
/* If a diagnostic is set to DK_IGNORED, it won't get reported at all.
This is used by the diagnostic machinery when it wants to disable a
diagnostic without disabling the option which causes it. */
DEFINE_DIAGNOSTIC_KIND (DK_IGNORED, "")
/* The remainder are real diagnostic types. */
DEFINE_DIAGNOSTIC_KIND (DK_FATAL, "fatal error: ")
DEFINE_DIAGNOSTIC_KIND (DK_ICE, "internal compiler error: ")
DEFINE_DIAGNOSTIC_KIND (DK_ERROR, "error: ")
DEFINE_DIAGNOSTIC_KIND (DK_SORRY, "sorry, unimplemented: ")
DEFINE_DIAGNOSTIC_KIND (DK_WARNING, "warning: ")
DEFINE_DIAGNOSTIC_KIND (DK_ANACHRONISM, "anachronism: ")
DEFINE_DIAGNOSTIC_KIND (DK_NOTE, "note: ")
DEFINE_DIAGNOSTIC_KIND (DK_DEBUG, "debug: ")
/* These two would be re-classified as DK_WARNING or DK_ERROR, so the
prefix does not matter. */
DEFINE_DIAGNOSTIC_KIND (DK_PEDWARN, "pedwarn: ")
DEFINE_DIAGNOSTIC_KIND (DK_PERMERROR, "permerror: ")

296
src/include/diagnostic.h Normal file
View File

@ -0,0 +1,296 @@
/* Various declarations for language-independent diagnostics subroutines.
Copyright (C) 2000-2013 Free Software Foundation, Inc.
Contributed by Gabriel Dos Reis <gdr@codesourcery.com>
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GCC_DIAGNOSTIC_H
#define GCC_DIAGNOSTIC_H
#include "pretty-print.h"
#include "diagnostic-core.h"
/* A diagnostic is described by the MESSAGE to send, the FILE and LINE of
its context and its KIND (ice, error, warning, note, ...) See complete
list in diagnostic.def. */
typedef struct diagnostic_info
{
text_info message;
location_t location;
unsigned int override_column;
/* Auxiliary data for client. */
void *x_data;
/* The kind of diagnostic it is about. */
diagnostic_t kind;
/* Which OPT_* directly controls this diagnostic. */
int option_index;
} diagnostic_info;
/* Each time a diagnostic's classification is changed with a pragma,
we record the change and the location of the change in an array of
these structs. */
typedef struct diagnostic_classification_change_t
{
location_t location;
int option;
diagnostic_t kind;
} diagnostic_classification_change_t;
/* Forward declarations. */
typedef void (*diagnostic_starter_fn) (diagnostic_context *,
diagnostic_info *);
typedef diagnostic_starter_fn diagnostic_finalizer_fn;
/* This data structure bundles altogether any information relevant to
the context of a diagnostic message. */
struct diagnostic_context
{
/* Where most of the diagnostic formatting work is done. */
pretty_printer *printer;
/* The number of times we have issued diagnostics. */
int diagnostic_count[DK_LAST_DIAGNOSTIC_KIND];
/* True if we should display the "warnings are being tread as error"
message, usually displayed once per compiler run. */
bool some_warnings_are_errors;
/* True if it has been requested that warnings be treated as errors. */
bool warning_as_error_requested;
/* The number of option indexes that can be passed to warning() et
al. */
int n_opts;
/* For each option index that can be passed to warning() et al
(OPT_* from options.h when using this code with the core GCC
options), this array may contain a new kind that the diagnostic
should be changed to before reporting, or DK_UNSPECIFIED to leave
it as the reported kind, or DK_IGNORED to not report it at
all. */
diagnostic_t *classify_diagnostic;
/* History of all changes to the classifications above. This list
is stored in location-order, so we can search it, either
binary-wise or end-to-front, to find the most recent
classification for a given diagnostic, given the location of the
diagnostic. */
diagnostic_classification_change_t *classification_history;
/* The size of the above array. */
int n_classification_history;
/* For pragma push/pop. */
int *push_list;
int n_push;
/* True if we should print the source line with a caret indicating
the location. */
bool show_caret;
/* Maximum width of the source line printed. */
int caret_max_width;
/* True if we should print the command line option which controls
each diagnostic, if known. */
bool show_option_requested;
/* True if we should raise a SIGABRT on errors. */
bool abort_on_error;
/* True if we should show the column number on diagnostics. */
bool show_column;
/* True if pedwarns are errors. */
bool pedantic_errors;
/* True if permerrors are warnings. */
bool permissive;
/* The index of the option to associate with turning permerrors into
warnings. */
int opt_permissive;
/* True if errors are fatal. */
bool fatal_errors;
/* True if all warnings should be disabled. */
bool dc_inhibit_warnings;
/* True if warnings should be given in system headers. */
bool dc_warn_system_headers;
/* Maximum number of errors to report. */
unsigned int max_errors;
/* This function is called before any message is printed out. It is
responsible for preparing message prefix and such. For example, it
might say:
In file included from "/usr/local/include/curses.h:5:
from "/home/gdr/src/nifty_printer.h:56:
...
*/
diagnostic_starter_fn begin_diagnostic;
/* This function is called after the diagnostic message is printed. */
diagnostic_finalizer_fn end_diagnostic;
/* Client hook to report an internal error. */
void (*internal_error) (diagnostic_context *, const char *, va_list *);
/* Client hook to say whether the option controlling a diagnostic is
enabled. Returns nonzero if enabled, zero if disabled. */
int (*option_enabled) (int, void *);
/* Client information to pass as second argument to
option_enabled. */
void *option_state;
/* Client hook to return the name of an option that controls a
diagnostic. Returns malloced memory. The first diagnostic_t
argument is the kind of diagnostic before any reclassification
(of warnings as errors, etc.); the second is the kind after any
reclassification. May return NULL if no name is to be printed.
May be passed 0 as well as the index of a particular option. */
char *(*option_name) (diagnostic_context *, int, diagnostic_t, diagnostic_t);
/* Auxiliary data for client. */
void *x_data;
/* Used to detect that the last caret was printed at the same location. */
location_t last_location;
/* Used to detect when the input file stack has changed since last
described. */
const struct line_map *last_module;
int lock;
bool inhibit_notes_p;
};
static inline void
diagnostic_inhibit_notes (diagnostic_context * context)
{
context->inhibit_notes_p = true;
}
/* Client supplied function to announce a diagnostic. */
#define diagnostic_starter(DC) (DC)->begin_diagnostic
/* Client supplied function called after a diagnostic message is
displayed. */
#define diagnostic_finalizer(DC) (DC)->end_diagnostic
/* Extension hooks for client. */
#define diagnostic_context_auxiliary_data(DC) (DC)->x_data
#define diagnostic_info_auxiliary_data(DI) (DI)->x_data
/* Same as pp_format_decoder. Works on 'diagnostic_context *'. */
#define diagnostic_format_decoder(DC) ((DC)->printer->format_decoder)
/* Same as output_prefixing_rule. Works on 'diagnostic_context *'. */
#define diagnostic_prefixing_rule(DC) ((DC)->printer->wrapping.rule)
/* Maximum characters per line in automatic line wrapping mode.
Zero means don't wrap lines. */
#define diagnostic_line_cutoff(DC) ((DC)->printer->wrapping.line_cutoff)
#define diagnostic_flush_buffer(DC) pp_base_flush ((DC)->printer)
/* True if the last module or file in which a diagnostic was reported is
different from the current one. */
#define diagnostic_last_module_changed(DC, MAP) \
((DC)->last_module != MAP)
/* Remember the current module or file as being the last one in which we
report a diagnostic. */
#define diagnostic_set_last_module(DC, MAP) \
(DC)->last_module = MAP
/* Raise SIGABRT on any diagnostic of severity DK_ERROR or higher. */
#define diagnostic_abort_on_error(DC) \
(DC)->abort_on_error = true
/* This diagnostic_context is used by front-ends that directly output
diagnostic messages without going through `error', `warning',
and similar functions. */
extern diagnostic_context *global_dc;
/* The total count of a KIND of diagnostics emitted so far. */
#define diagnostic_kind_count(DC, DK) (DC)->diagnostic_count[(int) (DK)]
/* The number of errors that have been issued so far. Ideally, these
would take a diagnostic_context as an argument. */
#define errorcount diagnostic_kind_count (global_dc, DK_ERROR)
/* Similarly, but for warnings. */
#define warningcount diagnostic_kind_count (global_dc, DK_WARNING)
/* Similarly, but for sorrys. */
#define sorrycount diagnostic_kind_count (global_dc, DK_SORRY)
/* Returns nonzero if warnings should be emitted. */
#define diagnostic_report_warnings_p(DC, LOC) \
(!(DC)->dc_inhibit_warnings \
&& !(in_system_header_at (LOC) && !(DC)->dc_warn_system_headers))
#define report_diagnostic(D) diagnostic_report_diagnostic (global_dc, D)
/* Override the column number to be used for reporting a
diagnostic. */
#define diagnostic_override_column(DI, COL) (DI)->override_column = (COL)
/* Override the option index to be used for reporting a
diagnostic. */
#define diagnostic_override_option_index(DI, OPTIDX) \
((DI)->option_index = (OPTIDX))
/* Diagnostic related functions. */
extern void diagnostic_initialize (diagnostic_context *, int);
extern void diagnostic_finish (diagnostic_context *);
extern void diagnostic_report_current_module (diagnostic_context *, location_t);
extern void diagnostic_show_locus (diagnostic_context *, const diagnostic_info *);
/* Force diagnostics controlled by OPTIDX to be kind KIND. */
extern diagnostic_t diagnostic_classify_diagnostic (diagnostic_context *,
int /* optidx */,
diagnostic_t /* kind */,
location_t);
extern void diagnostic_push_diagnostics (diagnostic_context *, location_t);
extern void diagnostic_pop_diagnostics (diagnostic_context *, location_t);
extern bool diagnostic_report_diagnostic (diagnostic_context *,
diagnostic_info *);
#ifdef ATTRIBUTE_GCC_DIAG
extern void diagnostic_set_info (diagnostic_info *, const char *, va_list *,
location_t, diagnostic_t) ATTRIBUTE_GCC_DIAG(2,0);
extern void diagnostic_set_info_translated (diagnostic_info *, const char *,
va_list *, location_t,
diagnostic_t)
ATTRIBUTE_GCC_DIAG(2,0);
extern void diagnostic_append_note (diagnostic_context *, location_t,
const char *, ...) ATTRIBUTE_GCC_DIAG(3,4);
#endif
extern char *diagnostic_build_prefix (diagnostic_context *, const diagnostic_info *);
void default_diagnostic_starter (diagnostic_context *, diagnostic_info *);
void default_diagnostic_finalizer (diagnostic_context *, diagnostic_info *);
void diagnostic_set_caret_max_width (diagnostic_context *context, int value);
/* Pure text formatting support functions. */
extern char *file_name_as_prefix (const char *);
#endif /* ! GCC_DIAGNOSTIC_H */

457
src/include/double-int.h Normal file
View File

@ -0,0 +1,457 @@
/* Operations with long integers.
Copyright (C) 2006-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it
under the terms of the GNU General Public License as published by the
Free Software Foundation; either version 3, or (at your option) any
later version.
GCC is distributed in the hope that it will be useful, but WITHOUT
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef DOUBLE_INT_H
#define DOUBLE_INT_H
/* A large integer is currently represented as a pair of HOST_WIDE_INTs.
It therefore represents a number with precision of
2 * HOST_BITS_PER_WIDE_INT bits (it is however possible that the
internal representation will change, if numbers with greater precision
are needed, so the users should not rely on it). The representation does
not contain any information about signedness of the represented value, so
it can be used to represent both signed and unsigned numbers. For
operations where the results depend on signedness (division, comparisons),
it must be specified separately. For each such operation, there are three
versions of the function -- double_int_op, that takes an extra UNS argument
giving the signedness of the values, and double_int_sop and double_int_uop
that stand for its specializations for signed and unsigned values.
You may also represent with numbers in smaller precision using double_int.
You however need to use double_int_ext (that fills in the bits of the
number over the prescribed precision with zeros or with the sign bit) before
operations that do not perform arithmetics modulo 2^precision (comparisons,
division), and possibly before storing the results, if you want to keep
them in some canonical form). In general, the signedness of double_int_ext
should match the signedness of the operation.
??? The components of double_int differ in signedness mostly for
historical reasons (they replace an older structure used to represent
numbers with precision higher than HOST_WIDE_INT). It might be less
confusing to have them both signed or both unsigned. */
struct double_int
{
/* Normally, we would define constructors to create instances.
Two things prevent us from doing so.
First, defining a constructor makes the class non-POD in C++03,
and we certainly want double_int to be a POD.
Second, the GCC conding conventions prefer explicit conversion,
and explicit conversion operators are not available until C++11. */
static double_int from_uhwi (unsigned HOST_WIDE_INT cst);
static double_int from_shwi (HOST_WIDE_INT cst);
static double_int from_pair (HOST_WIDE_INT high, unsigned HOST_WIDE_INT low);
/* Construct from a fuffer of length LEN. BUFFER will be read according
to byte endianess and word endianess. */
static double_int from_buffer (const unsigned char *buffer, int len);
/* No copy assignment operator or destructor to keep the type a POD. */
/* There are some special value-creation static member functions. */
static double_int mask (unsigned prec);
static double_int max_value (unsigned int prec, bool uns);
static double_int min_value (unsigned int prec, bool uns);
/* The following functions are mutating operations. */
double_int &operator ++ (); // prefix
double_int &operator -- (); // prefix
double_int &operator *= (double_int);
double_int &operator += (double_int);
double_int &operator -= (double_int);
double_int &operator &= (double_int);
double_int &operator ^= (double_int);
double_int &operator |= (double_int);
/* The following functions are non-mutating operations. */
/* Conversion functions. */
HOST_WIDE_INT to_shwi () const;
unsigned HOST_WIDE_INT to_uhwi () const;
/* Conversion query functions. */
bool fits_uhwi () const;
bool fits_shwi () const;
bool fits_hwi (bool uns) const;
/* Attribute query functions. */
int trailing_zeros () const;
int popcount () const;
/* Arithmetic query operations. */
bool multiple_of (double_int, bool, double_int *) const;
/* Arithmetic operation functions. */
/* The following operations perform arithmetics modulo 2^precision, so you
do not need to call .ext between them, even if you are representing
numbers with precision less than HOST_BITS_PER_DOUBLE_INT bits. */
double_int set_bit (unsigned) const;
double_int mul_with_sign (double_int, bool unsigned_p, bool *overflow) const;
double_int wide_mul_with_sign (double_int, bool unsigned_p,
double_int *higher, bool *overflow) const;
double_int add_with_sign (double_int, bool unsigned_p, bool *overflow) const;
double_int sub_with_overflow (double_int, bool *overflow) const;
double_int neg_with_overflow (bool *overflow) const;
double_int operator * (double_int) const;
double_int operator + (double_int) const;
double_int operator - (double_int) const;
double_int operator - () const;
double_int operator ~ () const;
double_int operator & (double_int) const;
double_int operator | (double_int) const;
double_int operator ^ (double_int) const;
double_int and_not (double_int) const;
double_int lshift (HOST_WIDE_INT count, unsigned int prec, bool arith) const;
double_int rshift (HOST_WIDE_INT count, unsigned int prec, bool arith) const;
double_int alshift (HOST_WIDE_INT count, unsigned int prec) const;
double_int arshift (HOST_WIDE_INT count, unsigned int prec) const;
double_int llshift (HOST_WIDE_INT count, unsigned int prec) const;
double_int lrshift (HOST_WIDE_INT count, unsigned int prec) const;
double_int lrotate (HOST_WIDE_INT count, unsigned int prec) const;
double_int rrotate (HOST_WIDE_INT count, unsigned int prec) const;
/* You must ensure that double_int::ext is called on the operands
of the following operations, if the precision of the numbers
is less than HOST_BITS_PER_DOUBLE_INT bits. */
double_int div (double_int, bool, unsigned) const;
double_int sdiv (double_int, unsigned) const;
double_int udiv (double_int, unsigned) const;
double_int mod (double_int, bool, unsigned) const;
double_int smod (double_int, unsigned) const;
double_int umod (double_int, unsigned) const;
double_int divmod_with_overflow (double_int, bool, unsigned,
double_int *, bool *) const;
double_int divmod (double_int, bool, unsigned, double_int *) const;
double_int sdivmod (double_int, unsigned, double_int *) const;
double_int udivmod (double_int, unsigned, double_int *) const;
/* Precision control functions. */
double_int ext (unsigned prec, bool uns) const;
double_int zext (unsigned prec) const;
double_int sext (unsigned prec) const;
/* Comparative functions. */
bool is_zero () const;
bool is_one () const;
bool is_minus_one () const;
bool is_negative () const;
int cmp (double_int b, bool uns) const;
int ucmp (double_int b) const;
int scmp (double_int b) const;
bool ult (double_int b) const;
bool ule (double_int b) const;
bool ugt (double_int b) const;
bool slt (double_int b) const;
bool sle (double_int b) const;
bool sgt (double_int b) const;
double_int max (double_int b, bool uns);
double_int smax (double_int b);
double_int umax (double_int b);
double_int min (double_int b, bool uns);
double_int smin (double_int b);
double_int umin (double_int b);
bool operator == (double_int cst2) const;
bool operator != (double_int cst2) const;
/* Please migrate away from using these member variables publically. */
unsigned HOST_WIDE_INT low;
HOST_WIDE_INT high;
};
#define HOST_BITS_PER_DOUBLE_INT (2 * HOST_BITS_PER_WIDE_INT)
/* Constructors and conversions. */
/* Constructs double_int from integer CST. The bits over the precision of
HOST_WIDE_INT are filled with the sign bit. */
inline double_int
double_int::from_shwi (HOST_WIDE_INT cst)
{
double_int r;
r.low = (unsigned HOST_WIDE_INT) cst;
r.high = cst < 0 ? -1 : 0;
return r;
}
/* Some useful constants. */
/* FIXME(crowl): Maybe remove after converting callers?
The problem is that a named constant would not be as optimizable,
while the functional syntax is more verbose. */
#define double_int_minus_one (double_int::from_shwi (-1))
#define double_int_zero (double_int::from_shwi (0))
#define double_int_one (double_int::from_shwi (1))
#define double_int_two (double_int::from_shwi (2))
#define double_int_ten (double_int::from_shwi (10))
/* Constructs double_int from unsigned integer CST. The bits over the
precision of HOST_WIDE_INT are filled with zeros. */
inline double_int
double_int::from_uhwi (unsigned HOST_WIDE_INT cst)
{
double_int r;
r.low = cst;
r.high = 0;
return r;
}
inline double_int
double_int::from_pair (HOST_WIDE_INT high, unsigned HOST_WIDE_INT low)
{
double_int r;
r.low = low;
r.high = high;
return r;
}
inline double_int &
double_int::operator ++ ()
{
*this += double_int_one;
return *this;
}
inline double_int &
double_int::operator -- ()
{
*this -= double_int_one;
return *this;
}
inline double_int &
double_int::operator *= (double_int b)
{
*this = *this * b;
return *this;
}
inline double_int &
double_int::operator += (double_int b)
{
*this = *this + b;
return *this;
}
inline double_int &
double_int::operator -= (double_int b)
{
*this = *this - b;
return *this;
}
inline double_int &
double_int::operator &= (double_int b)
{
*this = *this & b;
return *this;
}
inline double_int &
double_int::operator ^= (double_int b)
{
*this = *this ^ b;
return *this;
}
inline double_int &
double_int::operator |= (double_int b)
{
*this = *this | b;
return *this;
}
/* Returns value of CST as a signed number. CST must satisfy
double_int::fits_signed. */
inline HOST_WIDE_INT
double_int::to_shwi () const
{
return (HOST_WIDE_INT) low;
}
/* Returns value of CST as an unsigned number. CST must satisfy
double_int::fits_unsigned. */
inline unsigned HOST_WIDE_INT
double_int::to_uhwi () const
{
return low;
}
/* Returns true if CST fits in unsigned HOST_WIDE_INT. */
inline bool
double_int::fits_uhwi () const
{
return high == 0;
}
/* Logical operations. */
/* Returns ~A. */
inline double_int
double_int::operator ~ () const
{
double_int result;
result.low = ~low;
result.high = ~high;
return result;
}
/* Returns A | B. */
inline double_int
double_int::operator | (double_int b) const
{
double_int result;
result.low = low | b.low;
result.high = high | b.high;
return result;
}
/* Returns A & B. */
inline double_int
double_int::operator & (double_int b) const
{
double_int result;
result.low = low & b.low;
result.high = high & b.high;
return result;
}
/* Returns A & ~B. */
inline double_int
double_int::and_not (double_int b) const
{
double_int result;
result.low = low & ~b.low;
result.high = high & ~b.high;
return result;
}
/* Returns A ^ B. */
inline double_int
double_int::operator ^ (double_int b) const
{
double_int result;
result.low = low ^ b.low;
result.high = high ^ b.high;
return result;
}
void dump_double_int (FILE *, double_int, bool);
#define ALL_ONES (~((unsigned HOST_WIDE_INT) 0))
/* The operands of the following comparison functions must be processed
with double_int_ext, if their precision is less than
HOST_BITS_PER_DOUBLE_INT bits. */
/* Returns true if CST is zero. */
inline bool
double_int::is_zero () const
{
return low == 0 && high == 0;
}
/* Returns true if CST is one. */
inline bool
double_int::is_one () const
{
return low == 1 && high == 0;
}
/* Returns true if CST is minus one. */
inline bool
double_int::is_minus_one () const
{
return low == ALL_ONES && high == -1;
}
/* Returns true if CST is negative. */
inline bool
double_int::is_negative () const
{
return high < 0;
}
/* Returns true if CST1 == CST2. */
inline bool
double_int::operator == (double_int cst2) const
{
return low == cst2.low && high == cst2.high;
}
/* Returns true if CST1 != CST2. */
inline bool
double_int::operator != (double_int cst2) const
{
return low != cst2.low || high != cst2.high;
}
/* Return number of set bits of CST. */
inline int
double_int::popcount () const
{
return popcount_hwi (high) + popcount_hwi (low);
}
#ifndef GENERATOR_FILE
/* Conversion to and from GMP integer representations. */
void mpz_set_double_int (mpz_t, double_int, bool);
double_int mpz_get_double_int (const_tree, mpz_t, bool);
#endif
#endif /* DOUBLE_INT_H */

166
src/include/dumpfile.h Normal file
View File

@ -0,0 +1,166 @@
/* Definitions for the shared dumpfile.
Copyright (C) 2004-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GCC is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GCC_DUMPFILE_H
#define GCC_DUMPFILE_H 1
#include "line-map.h"
/* Different tree dump places. When you add new tree dump places,
extend the DUMP_FILES array in dumpfile.c. */
enum tree_dump_index
{
TDI_none, /* No dump */
TDI_cgraph, /* dump function call graph. */
TDI_tu, /* dump the whole translation unit. */
TDI_class, /* dump class hierarchy. */
TDI_original, /* dump each function before optimizing it */
TDI_generic, /* dump each function after genericizing it */
TDI_nested, /* dump each function after unnesting it */
TDI_tree_all, /* enable all the GENERIC/GIMPLE dumps. */
TDI_rtl_all, /* enable all the RTL dumps. */
TDI_ipa_all, /* enable all the IPA dumps. */
TDI_end
};
/* Bit masks to control dumping. Not all values are applicable to all
dumps. Add new ones at the end. When you define new values, extend
the DUMP_OPTIONS array in dumpfile.c. The TDF_* flags coexist with
MSG_* flags (for -fopt-info) and the bit values must be chosen to
allow that. */
#define TDF_ADDRESS (1 << 0) /* dump node addresses */
#define TDF_SLIM (1 << 1) /* don't go wild following links */
#define TDF_RAW (1 << 2) /* don't unparse the function */
#define TDF_DETAILS (1 << 3) /* show more detailed info about
each pass */
#define TDF_STATS (1 << 4) /* dump various statistics about
each pass */
#define TDF_BLOCKS (1 << 5) /* display basic block boundaries */
#define TDF_VOPS (1 << 6) /* display virtual operands */
#define TDF_LINENO (1 << 7) /* display statement line numbers */
#define TDF_UID (1 << 8) /* display decl UIDs */
#define TDF_TREE (1 << 9) /* is a tree dump */
#define TDF_RTL (1 << 10) /* is a RTL dump */
#define TDF_IPA (1 << 11) /* is an IPA dump */
#define TDF_STMTADDR (1 << 12) /* Address of stmt. */
#define TDF_GRAPH (1 << 13) /* a graph dump is being emitted */
#define TDF_MEMSYMS (1 << 14) /* display memory symbols in expr.
Implies TDF_VOPS. */
#define TDF_DIAGNOSTIC (1 << 15) /* A dump to be put in a diagnostic
message. */
#define TDF_VERBOSE (1 << 16) /* A dump that uses the full tree
dumper to print stmts. */
#define TDF_RHS_ONLY (1 << 17) /* a flag to only print the RHS of
a gimple stmt. */
#define TDF_ASMNAME (1 << 18) /* display asm names of decls */
#define TDF_EH (1 << 19) /* display EH region number
holding this gimple statement. */
#define TDF_NOUID (1 << 20) /* omit UIDs from dumps. */
#define TDF_ALIAS (1 << 21) /* display alias information */
#define TDF_ENUMERATE_LOCALS (1 << 22) /* Enumerate locals by uid. */
#define TDF_CSELIB (1 << 23) /* Dump cselib details. */
#define TDF_SCEV (1 << 24) /* Dump SCEV details. */
#define TDF_COMMENT (1 << 25) /* Dump lines with prefix ";;" */
#define MSG_OPTIMIZED_LOCATIONS (1 << 26) /* -fopt-info optimized sources */
#define MSG_MISSED_OPTIMIZATION (1 << 27) /* missed opportunities */
#define MSG_NOTE (1 << 28) /* general optimization info */
#define MSG_ALL (MSG_OPTIMIZED_LOCATIONS | MSG_MISSED_OPTIMIZATION \
| MSG_NOTE)
/* Flags to control high-level -fopt-info dumps. Usually these flags
define a group of passes. An optimization pass can be part of
multiple groups. */
#define OPTGROUP_NONE (0)
#define OPTGROUP_IPA (1 << 1) /* IPA optimization passes */
#define OPTGROUP_LOOP (1 << 2) /* Loop optimization passes */
#define OPTGROUP_INLINE (1 << 3) /* Inlining passes */
#define OPTGROUP_VEC (1 << 4) /* Vectorization passes */
#define OPTGROUP_ALL (OPTGROUP_IPA | OPTGROUP_LOOP | OPTGROUP_INLINE \
| OPTGROUP_VEC)
/* Define a tree dump switch. */
struct dump_file_info
{
const char *suffix; /* suffix to give output file. */
const char *swtch; /* command line dump switch */
const char *glob; /* command line glob */
const char *pfilename; /* filename for the pass-specific stream */
const char *alt_filename; /* filename for the -fopt-info stream */
FILE *pstream; /* pass-specific dump stream */
FILE *alt_stream; /* -fopt-info stream */
int pflags; /* dump flags */
int optgroup_flags; /* optgroup flags for -fopt-info */
int alt_flags; /* flags for opt-info */
int pstate; /* state of pass-specific stream */
int alt_state; /* state of the -fopt-info stream */
int num; /* dump file number */
};
/* In dumpfile.c */
extern char *get_dump_file_name (int);
extern int dump_initialized_p (int);
extern FILE *dump_begin (int, int *);
extern void dump_end (int, FILE *);
extern int dump_start (int, int *);
extern void dump_finish (int);
extern void dump_node (const_tree, int, FILE *);
extern int dump_switch_p (const char *);
extern int opt_info_switch_p (const char *);
extern const char *dump_flag_name (int);
extern void dump_printf (int, const char *, ...) ATTRIBUTE_PRINTF_2;
extern void dump_printf_loc (int, source_location,
const char *, ...) ATTRIBUTE_PRINTF_3;
extern void dump_basic_block (int, basic_block, int);
extern void dump_generic_expr_loc (int, source_location, int, tree);
extern void dump_generic_expr (int, int, tree);
extern void dump_gimple_stmt_loc (int, source_location, int, gimple, int);
extern void dump_gimple_stmt (int, int, gimple, int);
extern void print_combine_total_stats (void);
extern unsigned int dump_register (const char *, const char *, const char *,
int, int);
extern bool enable_rtl_dump_file (void);
/* In combine.c */
extern void dump_combine_total_stats (FILE *);
/* In cfghooks.c */
extern void dump_bb (FILE *, basic_block, int, int);
/* Global variables used to communicate with passes. */
extern FILE *dump_file;
extern FILE *alt_dump_file;
extern int dump_flags;
extern const char *dump_file_name;
/* Return the dump_file_info for the given phase. */
extern struct dump_file_info *get_dump_file_info (int);
/* Return true if any of the dumps is enabled, false otherwise. */
static inline bool
dump_enabled_p (void)
{
return (dump_file || alt_dump_file);
}
#endif /* GCC_DUMPFILE_H */

119
src/include/emit-rtl.h Normal file
View File

@ -0,0 +1,119 @@
/* Exported functions from emit-rtl.c
Copyright (C) 2004-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GCC_EMIT_RTL_H
#define GCC_EMIT_RTL_H
/* Return whether two MEM_ATTRs are equal. */
bool mem_attrs_eq_p (const struct mem_attrs *, const struct mem_attrs *);
/* Set the alias set of MEM to SET. */
extern void set_mem_alias_set (rtx, alias_set_type);
/* Set the alignment of MEM to ALIGN bits. */
extern void set_mem_align (rtx, unsigned int);
/* Set the address space of MEM to ADDRSPACE. */
extern void set_mem_addr_space (rtx, addr_space_t);
/* Set the expr for MEM to EXPR. */
extern void set_mem_expr (rtx, tree);
/* Set the offset for MEM to OFFSET. */
extern void set_mem_offset (rtx, HOST_WIDE_INT);
/* Clear the offset recorded for MEM. */
extern void clear_mem_offset (rtx);
/* Set the size for MEM to SIZE. */
extern void set_mem_size (rtx, HOST_WIDE_INT);
/* Clear the size recorded for MEM. */
extern void clear_mem_size (rtx);
/* Set the attributes for MEM appropriate for a spill slot. */
extern void set_mem_attrs_for_spill (rtx);
extern tree get_spill_slot_decl (bool);
/* Return a memory reference like MEMREF, but with its address changed to
ADDR. The caller is asserting that the actual piece of memory pointed
to is the same, just the form of the address is being changed, such as
by putting something into a register. */
extern rtx replace_equiv_address (rtx, rtx);
/* Likewise, but the reference is not required to be valid. */
extern rtx replace_equiv_address_nv (rtx, rtx);
extern rtx gen_blockage (void);
extern rtvec gen_rtvec (int, ...);
extern rtx copy_insn_1 (rtx);
extern rtx copy_insn (rtx);
extern rtx copy_delay_slot_insn (rtx);
extern rtx gen_int_mode (HOST_WIDE_INT, enum machine_mode);
extern rtx emit_copy_of_insn_after (rtx, rtx);
extern void set_reg_attrs_from_value (rtx, rtx);
extern void set_reg_attrs_for_parm (rtx, rtx);
extern void set_reg_attrs_for_decl_rtl (tree t, rtx x);
extern void adjust_reg_mode (rtx, enum machine_mode);
extern int mem_expr_equal_p (const_tree, const_tree);
extern bool need_atomic_barrier_p (enum memmodel, bool);
/* Return the first insn of the current sequence or current function. */
static inline rtx
get_insns (void)
{
return crtl->emit.x_first_insn;
}
/* Specify a new insn as the first in the chain. */
static inline void
set_first_insn (rtx insn)
{
gcc_checking_assert (!insn || !PREV_INSN (insn));
crtl->emit.x_first_insn = insn;
}
/* Return the last insn emitted in current sequence or current function. */
static inline rtx
get_last_insn (void)
{
return crtl->emit.x_last_insn;
}
/* Specify a new insn as the last in the chain. */
static inline void
set_last_insn (rtx insn)
{
gcc_checking_assert (!insn || !NEXT_INSN (insn));
crtl->emit.x_last_insn = insn;
}
/* Return a number larger than any instruction's uid in this function. */
static inline int
get_max_uid (void)
{
return crtl->emit.x_cur_insn_uid;
}
#endif /* GCC_EMIT_RTL_H */

335
src/include/except.h Normal file
View File

@ -0,0 +1,335 @@
/* Exception Handling interface routines.
Copyright (C) 1996-2013 Free Software Foundation, Inc.
Contributed by Mike Stump <mrs@cygnus.com>.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
/* No include guards here, but define an include file marker anyway, so
that the compiler can keep track of where this file is included. This
is e.g. used to avoid including this file in front-end specific files. */
#ifndef GCC_EXCEPT_H
# define GCC_EXCEPT_H
#endif
#include "hashtab.h"
struct function;
struct eh_region_d;
struct pointer_map_t;
/* The type of an exception region. */
enum eh_region_type
{
/* CLEANUP regions implement e.g. destructors run when exiting a block.
They can be generated from both GIMPLE_TRY_FINALLY and GIMPLE_TRY_CATCH
nodes. It is expected by the runtime that cleanup regions will *not*
resume normal program flow, but will continue propagation of the
exception. */
ERT_CLEANUP,
/* TRY regions implement catching an exception. The list of types associated
with the attached catch handlers is examined in order by the runtime and
control is transferred to the appropriate handler. Note that a NULL type
list is a catch-all handler, and that it will catch *all* exceptions
including those originating from a different language. */
ERT_TRY,
/* ALLOWED_EXCEPTIONS regions implement exception filtering, e.g. the
throw(type-list) specification that can be added to C++ functions.
The runtime examines the thrown exception vs the type list, and if
the exception does not match, transfers control to the handler. The
normal handler for C++ calls __cxa_call_unexpected. */
ERT_ALLOWED_EXCEPTIONS,
/* MUST_NOT_THROW regions prevent all exceptions from propagating. This
region type is used in C++ to surround destructors being run inside a
CLEANUP region. This differs from an ALLOWED_EXCEPTIONS region with
an empty type list in that the runtime is prepared to terminate the
program directly. We only generate code for MUST_NOT_THROW regions
along control paths that are already handling an exception within the
current function. */
ERT_MUST_NOT_THROW
};
/* A landing pad for a given exception region. Any transfer of control
from the EH runtime to the function happens at a landing pad. */
struct GTY(()) eh_landing_pad_d
{
/* The linked list of all landing pads associated with the region. */
struct eh_landing_pad_d *next_lp;
/* The region with which this landing pad is associated. */
struct eh_region_d *region;
/* At the gimple level, the location to which control will be transferred
for this landing pad. There can be both EH and normal edges into the
block containing the post-landing-pad label. */
tree post_landing_pad;
/* At the rtl level, the location to which the runtime will transfer
control. This differs from the post-landing-pad in that the target's
EXCEPTION_RECEIVER pattern will be expanded here, as well as other
bookkeeping specific to exceptions. There must not be normal edges
into the block containing the landing-pad label. */
rtx landing_pad;
/* The index of this landing pad within fun->eh->lp_array. */
int index;
};
/* A catch handler associated with an ERT_TRY region. */
struct GTY(()) eh_catch_d
{
/* The double-linked list of all catch handlers for the region. */
struct eh_catch_d *next_catch;
struct eh_catch_d *prev_catch;
/* A TREE_LIST of runtime type objects that this catch handler
will catch, or NULL if all exceptions are caught. */
tree type_list;
/* A TREE_LIST of INTEGER_CSTs that correspond to the type_list entries,
having been mapped by assign_filter_values. These integers are to be
compared against the __builtin_eh_filter value. */
tree filter_list;
/* The code that should be executed if this catch handler matches the
thrown exception. This label is only maintained until
pass_lower_eh_dispatch, at which point it is cleared. */
tree label;
};
/* Describes one exception region. */
struct GTY(()) eh_region_d
{
/* The immediately surrounding region. */
struct eh_region_d *outer;
/* The list of immediately contained regions. */
struct eh_region_d *inner;
struct eh_region_d *next_peer;
/* The index of this region within fun->eh->region_array. */
int index;
/* Each region does exactly one thing. */
enum eh_region_type type;
/* Holds the action to perform based on the preceding type. */
union eh_region_u {
struct eh_region_u_try {
/* The double-linked list of all catch handlers for this region. */
struct eh_catch_d *first_catch;
struct eh_catch_d *last_catch;
} GTY ((tag ("ERT_TRY"))) eh_try;
struct eh_region_u_allowed {
/* A TREE_LIST of runtime type objects allowed to pass. */
tree type_list;
/* The code that should be executed if the thrown exception does
not match the type list. This label is only maintained until
pass_lower_eh_dispatch, at which point it is cleared. */
tree label;
/* The integer that will be passed by the runtime to signal that
we should execute the code at LABEL. This integer is assigned
by assign_filter_values and is to be compared against the
__builtin_eh_filter value. */
int filter;
} GTY ((tag ("ERT_ALLOWED_EXCEPTIONS"))) allowed;
struct eh_region_u_must_not_throw {
/* A function decl to be invoked if this region is actually reachable
from within the function, rather than implementable from the runtime.
The normal way for this to happen is for there to be a CLEANUP region
contained within this MUST_NOT_THROW region. Note that if the
runtime handles the MUST_NOT_THROW region, we have no control over
what termination function is called; it will be decided by the
personality function in effect for this CIE. */
tree failure_decl;
/* The location assigned to the call of FAILURE_DECL, if expanded. */
location_t failure_loc;
} GTY ((tag ("ERT_MUST_NOT_THROW"))) must_not_throw;
} GTY ((desc ("%0.type"))) u;
/* The list of landing pads associated with this region. */
struct eh_landing_pad_d *landing_pads;
/* EXC_PTR and FILTER values copied from the runtime for this region.
Each region gets its own psuedos so that if there are nested exceptions
we do not overwrite the values of the first exception. */
rtx exc_ptr_reg, filter_reg;
/* True if this region should use __cxa_end_cleanup instead
of _Unwind_Resume. */
bool use_cxa_end_cleanup;
};
typedef struct eh_landing_pad_d *eh_landing_pad;
typedef struct eh_catch_d *eh_catch;
typedef struct eh_region_d *eh_region;
/* The exception status for each function. */
struct GTY(()) eh_status
{
/* The tree of all regions for this function. */
eh_region region_tree;
/* The same information as an indexable array. */
vec<eh_region, va_gc> *region_array;
/* The landing pads as an indexable array. */
vec<eh_landing_pad, va_gc> *lp_array;
/* At the gimple level, a mapping from gimple statement to landing pad
or must-not-throw region. See record_stmt_eh_region. */
htab_t GTY((param_is (struct throw_stmt_node))) throw_stmt_table;
/* All of the runtime type data used by the function. These objects
are emitted to the lang-specific-data-area for the function. */
vec<tree, va_gc> *ttype_data;
/* The table of all action chains. These encode the eh_region tree in
a compact form for use by the runtime, and is also emitted to the
lang-specific-data-area. Note that the ARM EABI uses a different
format for the encoding than all other ports. */
union eh_status_u {
vec<tree, va_gc> *GTY((tag ("1"))) arm_eabi;
vec<uchar, va_gc> *GTY((tag ("0"))) other;
} GTY ((desc ("targetm.arm_eabi_unwinder"))) ehspec_data;
};
/* Invokes CALLBACK for every exception handler label. Only used by old
loop hackery; should not be used by new code. */
extern void for_each_eh_label (void (*) (rtx));
extern void init_eh_for_function (void);
extern void remove_eh_landing_pad (eh_landing_pad);
extern void remove_eh_handler (eh_region);
extern void remove_unreachable_eh_regions (sbitmap);
extern bool current_function_has_exception_handlers (void);
extern void output_function_exception_table (const char *);
extern rtx expand_builtin_eh_pointer (tree);
extern rtx expand_builtin_eh_filter (tree);
extern rtx expand_builtin_eh_copy_values (tree);
extern void expand_builtin_unwind_init (void);
extern rtx expand_builtin_eh_return_data_regno (tree);
extern rtx expand_builtin_extract_return_addr (tree);
extern void expand_builtin_init_dwarf_reg_sizes (tree);
extern rtx expand_builtin_frob_return_addr (tree);
extern rtx expand_builtin_dwarf_sp_column (void);
extern void expand_builtin_eh_return (tree, tree);
extern void expand_eh_return (void);
extern rtx expand_builtin_extend_pointer (tree);
extern void expand_dw2_landing_pad_for_region (eh_region);
typedef tree (*duplicate_eh_regions_map) (tree, void *);
extern struct pointer_map_t *duplicate_eh_regions
(struct function *, eh_region, int, duplicate_eh_regions_map, void *);
extern void sjlj_emit_function_exit_after (rtx);
extern eh_region gen_eh_region_cleanup (eh_region);
extern eh_region gen_eh_region_try (eh_region);
extern eh_region gen_eh_region_allowed (eh_region, tree);
extern eh_region gen_eh_region_must_not_throw (eh_region);
extern eh_catch gen_eh_region_catch (eh_region, tree);
extern eh_landing_pad gen_eh_landing_pad (eh_region);
extern eh_region get_eh_region_from_number_fn (struct function *, int);
extern eh_region get_eh_region_from_number (int);
extern eh_landing_pad get_eh_landing_pad_from_number_fn (struct function*,int);
extern eh_landing_pad get_eh_landing_pad_from_number (int);
extern eh_region get_eh_region_from_lp_number_fn (struct function *, int);
extern eh_region get_eh_region_from_lp_number (int);
extern eh_region eh_region_outermost (struct function *, eh_region, eh_region);
extern void make_reg_eh_region_note (rtx insn, int ecf_flags, int lp_nr);
extern void make_reg_eh_region_note_nothrow_nononlocal (rtx);
extern void verify_eh_tree (struct function *);
extern void dump_eh_tree (FILE *, struct function *);
void debug_eh_tree (struct function *);
extern void add_type_for_runtime (tree);
extern tree lookup_type_for_runtime (tree);
extern void assign_filter_values (void);
extern eh_region get_eh_region_from_rtx (const_rtx);
extern eh_landing_pad get_eh_landing_pad_from_rtx (const_rtx);
extern void finish_eh_generation (void);
struct GTY(()) throw_stmt_node {
gimple stmt;
int lp_nr;
};
extern struct htab *get_eh_throw_stmt_table (struct function *);
extern void set_eh_throw_stmt_table (struct function *, struct htab *);
enum eh_personality_kind {
eh_personality_none,
eh_personality_any,
eh_personality_lang
};
extern enum eh_personality_kind
function_needs_eh_personality (struct function *);
/* Pre-order iteration within the eh_region tree. */
static inline eh_region
ehr_next (eh_region r, eh_region start)
{
if (r->inner)
r = r->inner;
else if (r->next_peer && r != start)
r = r->next_peer;
else
{
do
{
r = r->outer;
if (r == start)
return NULL;
}
while (r->next_peer == NULL);
r = r->next_peer;
}
return r;
}
#define FOR_ALL_EH_REGION_AT(R, START) \
for ((R) = (START); (R) != NULL; (R) = ehr_next (R, START))
#define FOR_ALL_EH_REGION_FN(R, FN) \
for ((R) = (FN)->eh->region_tree; (R) != NULL; (R) = ehr_next (R, NULL))
#define FOR_ALL_EH_REGION(R) FOR_ALL_EH_REGION_FN (R, cfun)

97
src/include/filenames.h Normal file
View File

@ -0,0 +1,97 @@
/* Macros for taking apart, interpreting and processing file names.
These are here because some non-Posix (a.k.a. DOSish) systems have
drive letter brain-damage at the beginning of an absolute file name,
use forward- and back-slash in path names interchangeably, and
some of them have case-insensitive file names.
Copyright 2000, 2001, 2007, 2010 Free Software Foundation, Inc.
This file is part of BFD, the Binary File Descriptor library.
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA 02110-1301, USA. */
#ifndef FILENAMES_H
#define FILENAMES_H
#include "hashtab.h" /* for hashval_t */
#ifdef __cplusplus
extern "C" {
#endif
#if defined(__MSDOS__) || defined(_WIN32) || defined(__OS2__) || defined (__CYGWIN__)
# ifndef HAVE_DOS_BASED_FILE_SYSTEM
# define HAVE_DOS_BASED_FILE_SYSTEM 1
# endif
# ifndef HAVE_CASE_INSENSITIVE_FILE_SYSTEM
# define HAVE_CASE_INSENSITIVE_FILE_SYSTEM 1
# endif
# define HAS_DRIVE_SPEC(f) HAS_DOS_DRIVE_SPEC (f)
# define IS_DIR_SEPARATOR(c) IS_DOS_DIR_SEPARATOR (c)
# define IS_ABSOLUTE_PATH(f) IS_DOS_ABSOLUTE_PATH (f)
#else /* not DOSish */
# if defined(__APPLE__)
# ifndef HAVE_CASE_INSENSITIVE_FILE_SYSTEM
# define HAVE_CASE_INSENSITIVE_FILE_SYSTEM 1
# endif
# endif /* __APPLE__ */
# define HAS_DRIVE_SPEC(f) (0)
# define IS_DIR_SEPARATOR(c) IS_UNIX_DIR_SEPARATOR (c)
# define IS_ABSOLUTE_PATH(f) IS_UNIX_ABSOLUTE_PATH (f)
#endif
#define IS_DIR_SEPARATOR_1(dos_based, c) \
(((c) == '/') \
|| (((c) == '\\') && (dos_based)))
#define HAS_DRIVE_SPEC_1(dos_based, f) \
((f)[0] && ((f)[1] == ':') && (dos_based))
/* Remove the drive spec from F, assuming HAS_DRIVE_SPEC (f).
The result is a pointer to the remainder of F. */
#define STRIP_DRIVE_SPEC(f) ((f) + 2)
#define IS_DOS_DIR_SEPARATOR(c) IS_DIR_SEPARATOR_1 (1, c)
#define IS_DOS_ABSOLUTE_PATH(f) IS_ABSOLUTE_PATH_1 (1, f)
#define HAS_DOS_DRIVE_SPEC(f) HAS_DRIVE_SPEC_1 (1, f)
#define IS_UNIX_DIR_SEPARATOR(c) IS_DIR_SEPARATOR_1 (0, c)
#define IS_UNIX_ABSOLUTE_PATH(f) IS_ABSOLUTE_PATH_1 (0, f)
/* Note that when DOS_BASED is true, IS_ABSOLUTE_PATH accepts d:foo as
well, although it is only semi-absolute. This is because the users
of IS_ABSOLUTE_PATH want to know whether to prepend the current
working directory to a file name, which should not be done with a
name like d:foo. */
#define IS_ABSOLUTE_PATH_1(dos_based, f) \
(IS_DIR_SEPARATOR_1 (dos_based, (f)[0]) \
|| HAS_DRIVE_SPEC_1 (dos_based, f))
extern int filename_cmp (const char *s1, const char *s2);
#define FILENAME_CMP(s1, s2) filename_cmp(s1, s2)
extern int filename_ncmp (const char *s1, const char *s2,
size_t n);
extern hashval_t filename_hash (const void *s);
extern int filename_eq (const void *s1, const void *s2);
#ifdef __cplusplus
}
#endif
#endif /* FILENAMES_H */

116
src/include/fixed-value.h Normal file
View File

@ -0,0 +1,116 @@
/* Fixed-point arithmetic support.
Copyright (C) 2006-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GCC_FIXED_VALUE_H
#define GCC_FIXED_VALUE_H
#include "machmode.h"
#include "real.h"
#include "double-int.h"
struct GTY(()) fixed_value
{
double_int data; /* Store data up to 2 wide integers. */
enum machine_mode mode; /* Use machine mode to know IBIT and FBIT. */
};
#define FIXED_VALUE_TYPE struct fixed_value
#define MAX_FCONST0 18 /* For storing 18 fixed-point zeros per
fract, ufract, accum, and uaccum modes . */
#define MAX_FCONST1 8 /* For storing 8 fixed-point ones per accum
and uaccum modes. */
/* Constant fixed-point values 0 and 1. */
extern FIXED_VALUE_TYPE fconst0[MAX_FCONST0];
extern FIXED_VALUE_TYPE fconst1[MAX_FCONST1];
/* Macros to access fconst0 and fconst1 via machine modes. */
#define FCONST0(mode) fconst0[mode - QQmode]
#define FCONST1(mode) fconst1[mode - HAmode]
/* Return a CONST_FIXED with value R and mode M. */
#define CONST_FIXED_FROM_FIXED_VALUE(r, m) \
const_fixed_from_fixed_value (r, m)
extern rtx const_fixed_from_fixed_value (FIXED_VALUE_TYPE, enum machine_mode);
/* Construct a FIXED_VALUE from a bit payload and machine mode MODE.
The bits in PAYLOAD are sign-extended/zero-extended according to MODE. */
extern FIXED_VALUE_TYPE fixed_from_double_int (double_int,
enum machine_mode);
/* Return a CONST_FIXED from a bit payload and machine mode MODE.
The bits in PAYLOAD are sign-extended/zero-extended according to MODE. */
static inline rtx
const_fixed_from_double_int (double_int payload,
enum machine_mode mode)
{
return
const_fixed_from_fixed_value (fixed_from_double_int (payload, mode),
mode);
}
/* Initialize from a decimal or hexadecimal string. */
extern void fixed_from_string (FIXED_VALUE_TYPE *, const char *,
enum machine_mode);
/* In tree.c: wrap up a FIXED_VALUE_TYPE in a tree node. */
extern tree build_fixed (tree, FIXED_VALUE_TYPE);
/* Extend or truncate to a new mode. */
extern bool fixed_convert (FIXED_VALUE_TYPE *, enum machine_mode,
const FIXED_VALUE_TYPE *, bool);
/* Convert to a fixed-point mode from an integer. */
extern bool fixed_convert_from_int (FIXED_VALUE_TYPE *, enum machine_mode,
double_int, bool, bool);
/* Convert to a fixed-point mode from a real. */
extern bool fixed_convert_from_real (FIXED_VALUE_TYPE *, enum machine_mode,
const REAL_VALUE_TYPE *, bool);
/* Convert to a real mode from a fixed-point. */
extern void real_convert_from_fixed (REAL_VALUE_TYPE *, enum machine_mode,
const FIXED_VALUE_TYPE *);
/* Compare two fixed-point objects for bitwise identity. */
extern bool fixed_identical (const FIXED_VALUE_TYPE *, const FIXED_VALUE_TYPE *);
/* Calculate a hash value. */
extern unsigned int fixed_hash (const FIXED_VALUE_TYPE *);
#define FIXED_VALUES_IDENTICAL(x, y) fixed_identical (&(x), &(y))
/* Determine whether a fixed-point value X is negative. */
#define FIXED_VALUE_NEGATIVE(x) fixed_isneg (&(x))
/* Render F as a decimal floating point constant. */
extern void fixed_to_decimal (char *str, const FIXED_VALUE_TYPE *, size_t);
/* Binary or unary arithmetic on tree_code. */
extern bool fixed_arithmetic (FIXED_VALUE_TYPE *, int, const FIXED_VALUE_TYPE *,
const FIXED_VALUE_TYPE *, bool);
/* Compare fixed-point values by tree_code. */
extern bool fixed_compare (int, const FIXED_VALUE_TYPE *,
const FIXED_VALUE_TYPE *);
/* Determine whether a fixed-point value X is negative. */
extern bool fixed_isneg (const FIXED_VALUE_TYPE *);
#endif /* GCC_FIXED_VALUE_H */

194
src/include/flag-types.h Normal file
View File

@ -0,0 +1,194 @@
/* Compilation switch flag type definitions for GCC.
Copyright (C) 1987-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GCC_FLAG_TYPES_H
#define GCC_FLAG_TYPES_H
enum debug_info_type
{
NO_DEBUG, /* Write no debug info. */
DBX_DEBUG, /* Write BSD .stabs for DBX (using dbxout.c). */
SDB_DEBUG, /* Write COFF for (old) SDB (using sdbout.c). */
DWARF2_DEBUG, /* Write Dwarf v2 debug info (using dwarf2out.c). */
XCOFF_DEBUG, /* Write IBM/Xcoff debug info (using dbxout.c). */
VMS_DEBUG, /* Write VMS debug info (using vmsdbgout.c). */
VMS_AND_DWARF2_DEBUG /* Write VMS debug info (using vmsdbgout.c).
and DWARF v2 debug info (using dwarf2out.c). */
};
enum debug_info_levels
{
DINFO_LEVEL_NONE, /* Write no debugging info. */
DINFO_LEVEL_TERSE, /* Write minimal info to support tracebacks only. */
DINFO_LEVEL_NORMAL, /* Write info for all declarations (and line table). */
DINFO_LEVEL_VERBOSE /* Write normal info plus #define/#undef info. */
};
/* A major contribution to object and executable size is debug
information size. A major contribution to debug information
size is struct descriptions replicated in several object files.
The following function determines whether or not debug information
should be generated for a given struct. The indirect parameter
indicates that the struct is being handled indirectly, via
a pointer. See opts.c for the implementation. */
enum debug_info_usage
{
DINFO_USAGE_DFN, /* A struct definition. */
DINFO_USAGE_DIR_USE, /* A direct use, such as the type of a variable. */
DINFO_USAGE_IND_USE, /* An indirect use, such as through a pointer. */
DINFO_USAGE_NUM_ENUMS /* The number of enumerators. */
};
/* A major contribution to object and executable size is debug
information size. A major contribution to debug information size
is struct descriptions replicated in several object files. The
following flags attempt to reduce this information. The basic
idea is to not emit struct debugging information in the current
compilation unit when that information will be generated by
another compilation unit.
Debug information for a struct defined in the current source
file should be generated in the object file. Likewise the
debug information for a struct defined in a header should be
generated in the object file of the corresponding source file.
Both of these case are handled when the base name of the file of
the struct definition matches the base name of the source file
of the current compilation unit. This matching emits minimal
struct debugging information.
The base file name matching rule above will fail to emit debug
information for structs defined in system headers. So a second
category of files includes system headers in addition to files
with matching bases.
The remaining types of files are library headers and application
headers. We cannot currently distinguish these two types. */
enum debug_struct_file
{
DINFO_STRUCT_FILE_NONE, /* Debug no structs. */
DINFO_STRUCT_FILE_BASE, /* Debug structs defined in files with the
same base name as the compilation unit. */
DINFO_STRUCT_FILE_SYS, /* Also debug structs defined in system
header files. */
DINFO_STRUCT_FILE_ANY /* Debug structs defined in all files. */
};
/* Enumerate visibility settings. This is deliberately ordered from most
to least visibility. */
#ifndef SYMBOL_VISIBILITY_DEFINED
#define SYMBOL_VISIBILITY_DEFINED
enum symbol_visibility
{
VISIBILITY_DEFAULT,
VISIBILITY_PROTECTED,
VISIBILITY_HIDDEN,
VISIBILITY_INTERNAL
};
#endif
/* The stack reuse level. */
enum stack_reuse_level
{
SR_NONE,
SR_NAMED_VARS,
SR_ALL
};
/* The algorithm used for the integrated register allocator (IRA). */
enum ira_algorithm
{
IRA_ALGORITHM_CB,
IRA_ALGORITHM_PRIORITY
};
/* The regions used for the integrated register allocator (IRA). */
enum ira_region
{
IRA_REGION_ONE,
IRA_REGION_ALL,
IRA_REGION_MIXED,
/* This value means that there were no options -fira-region on the
command line and that we should choose a value depending on the
used -O option. */
IRA_REGION_AUTODETECT
};
/* The options for excess precision. */
enum excess_precision
{
EXCESS_PRECISION_DEFAULT,
EXCESS_PRECISION_FAST,
EXCESS_PRECISION_STANDARD
};
/* Type of stack check. */
enum stack_check_type
{
/* Do not check the stack. */
NO_STACK_CHECK = 0,
/* Check the stack generically, i.e. assume no specific support
from the target configuration files. */
GENERIC_STACK_CHECK,
/* Check the stack and rely on the target configuration files to
check the static frame of functions, i.e. use the generic
mechanism only for dynamic stack allocations. */
STATIC_BUILTIN_STACK_CHECK,
/* Check the stack and entirely rely on the target configuration
files, i.e. do not use the generic mechanism at all. */
FULL_BUILTIN_STACK_CHECK
};
/* Names for the different levels of -Wstrict-overflow=N. The numeric
values here correspond to N. */
enum warn_strict_overflow_code
{
/* Overflow warning that should be issued with -Wall: a questionable
construct that is easy to avoid even when using macros. Example:
folding (x + CONSTANT > x) to 1. */
WARN_STRICT_OVERFLOW_ALL = 1,
/* Overflow warning about folding a comparison to a constant because
of undefined signed overflow, other than cases covered by
WARN_STRICT_OVERFLOW_ALL. Example: folding (abs (x) >= 0) to 1
(this is false when x == INT_MIN). */
WARN_STRICT_OVERFLOW_CONDITIONAL = 2,
/* Overflow warning about changes to comparisons other than folding
them to a constant. Example: folding (x + 1 > 1) to (x > 0). */
WARN_STRICT_OVERFLOW_COMPARISON = 3,
/* Overflow warnings not covered by the above cases. Example:
folding ((x * 10) / 5) to (x * 2). */
WARN_STRICT_OVERFLOW_MISC = 4,
/* Overflow warnings about reducing magnitude of constants in
comparison. Example: folding (x + 2 > y) to (x + 1 >= y). */
WARN_STRICT_OVERFLOW_MAGNITUDE = 5
};
/* Floating-point contraction mode. */
enum fp_contract_mode {
FP_CONTRACT_OFF = 0,
FP_CONTRACT_ON = 1,
FP_CONTRACT_FAST = 2
};
#endif /* ! GCC_FLAG_TYPES_H */

101
src/include/flags.h Normal file
View File

@ -0,0 +1,101 @@
/* Compilation switch flag definitions for GCC.
Copyright (C) 1987-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GCC_FLAGS_H
#define GCC_FLAGS_H
#include "flag-types.h"
#include "options.h"
#if !defined(IN_LIBGCC2) && !defined(IN_TARGET_LIBS) && !defined(IN_RTS)
/* Names of debug_info_type, for error messages. */
extern const char *const debug_type_names[];
extern void strip_off_ending (char *, int);
extern int base_of_path (const char *path, const char **base_out);
/* Return true iff flags are set as if -ffast-math. */
extern bool fast_math_flags_set_p (const struct gcc_options *);
extern bool fast_math_flags_struct_set_p (struct cl_optimization *);
/* Now the symbols that are set with `-f' switches. */
/* True if printing into -fdump-final-insns= dump. */
extern bool final_insns_dump_p;
/* Other basic status info about current function. */
/* Target-dependent global state. */
struct target_flag_state {
/* Values of the -falign-* flags: how much to align labels in code.
0 means `use default', 1 means `don't align'.
For each variable, there is an _log variant which is the power
of two not less than the variable, for .align output. */
int x_align_loops_log;
int x_align_loops_max_skip;
int x_align_jumps_log;
int x_align_jumps_max_skip;
int x_align_labels_log;
int x_align_labels_max_skip;
int x_align_functions_log;
/* The excess precision currently in effect. */
enum excess_precision x_flag_excess_precision;
};
extern struct target_flag_state default_target_flag_state;
#if SWITCHABLE_TARGET
extern struct target_flag_state *this_target_flag_state;
#else
#define this_target_flag_state (&default_target_flag_state)
#endif
#define align_loops_log \
(this_target_flag_state->x_align_loops_log)
#define align_loops_max_skip \
(this_target_flag_state->x_align_loops_max_skip)
#define align_jumps_log \
(this_target_flag_state->x_align_jumps_log)
#define align_jumps_max_skip \
(this_target_flag_state->x_align_jumps_max_skip)
#define align_labels_log \
(this_target_flag_state->x_align_labels_log)
#define align_labels_max_skip \
(this_target_flag_state->x_align_labels_max_skip)
#define align_functions_log \
(this_target_flag_state->x_align_functions_log)
#define flag_excess_precision \
(this_target_flag_state->x_flag_excess_precision)
/* Returns TRUE if generated code should match ABI version N or
greater is in use. */
#define abi_version_at_least(N) \
(flag_abi_version == 0 || flag_abi_version >= (N))
/* Whether to emit an overflow warning whose code is C. */
#define issue_strict_overflow_warning(c) (warn_strict_overflow >= (int) (c))
#endif
#endif /* ! GCC_FLAGS_H */

782
src/include/function.h Normal file
View File

@ -0,0 +1,782 @@
/* Structure for saving state for a nested function.
Copyright (C) 1989-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GCC_FUNCTION_H
#define GCC_FUNCTION_H
#include "hashtab.h"
#include "vec.h"
#include "machmode.h"
#include "tm.h" /* For CUMULATIVE_ARGS. */
#include "hard-reg-set.h" /* For HARD_REG_SET in struct rtl_data. */
#include "input.h" /* For location_t. */
/* Stack of pending (incomplete) sequences saved by `start_sequence'.
Each element describes one pending sequence.
The main insn-chain is saved in the last element of the chain,
unless the chain is empty. */
struct GTY(()) sequence_stack {
/* First and last insns in the chain of the saved sequence. */
rtx first;
rtx last;
struct sequence_stack *next;
};
struct GTY(()) emit_status {
/* This is reset to LAST_VIRTUAL_REGISTER + 1 at the start of each function.
After rtl generation, it is 1 plus the largest register number used. */
int x_reg_rtx_no;
/* Lowest label number in current function. */
int x_first_label_num;
/* The ends of the doubly-linked chain of rtl for the current function.
Both are reset to null at the start of rtl generation for the function.
start_sequence saves both of these on `sequence_stack' and then starts
a new, nested sequence of insns. */
rtx x_first_insn;
rtx x_last_insn;
/* Stack of pending (incomplete) sequences saved by `start_sequence'.
Each element describes one pending sequence.
The main insn-chain is saved in the last element of the chain,
unless the chain is empty. */
struct sequence_stack *sequence_stack;
/* INSN_UID for next insn emitted.
Reset to 1 for each function compiled. */
int x_cur_insn_uid;
/* INSN_UID for next debug insn emitted. Only used if
--param min-nondebug-insn-uid=<value> is given with nonzero value. */
int x_cur_debug_insn_uid;
/* The length of the regno_pointer_align, regno_decl, and x_regno_reg_rtx
vectors. Since these vectors are needed during the expansion phase when
the total number of registers in the function is not yet known, the
vectors are copied and made bigger when necessary. */
int regno_pointer_align_length;
/* Indexed by pseudo register number, if nonzero gives the known alignment
for that pseudo (if REG_POINTER is set in x_regno_reg_rtx).
Allocated in parallel with x_regno_reg_rtx. */
unsigned char * GTY((skip)) regno_pointer_align;
};
/* Indexed by register number, gives an rtx for that register (and only
that register). For pseudo registers, it is the unique rtx for
that pseudo. For hard registers, it is an rtx of the mode specified
by reg_raw_mode.
FIXME: We could put it into emit_status struct, but gengtype is not
able to deal with length attribute nested in top level structures. */
extern GTY ((length ("crtl->emit.x_reg_rtx_no"))) rtx * regno_reg_rtx;
/* For backward compatibility... eventually these should all go away. */
#define reg_rtx_no (crtl->emit.x_reg_rtx_no)
#define seq_stack (crtl->emit.sequence_stack)
#define REGNO_POINTER_ALIGN(REGNO) (crtl->emit.regno_pointer_align[REGNO])
struct GTY(()) expr_status {
/* Number of units that we should eventually pop off the stack.
These are the arguments to function calls that have already returned. */
int x_pending_stack_adjust;
/* Under some ABIs, it is the caller's responsibility to pop arguments
pushed for function calls. A naive implementation would simply pop
the arguments immediately after each call. However, if several
function calls are made in a row, it is typically cheaper to pop
all the arguments after all of the calls are complete since a
single pop instruction can be used. Therefore, GCC attempts to
defer popping the arguments until absolutely necessary. (For
example, at the end of a conditional, the arguments must be popped,
since code outside the conditional won't know whether or not the
arguments need to be popped.)
When INHIBIT_DEFER_POP is nonzero, however, the compiler does not
attempt to defer pops. Instead, the stack is popped immediately
after each call. Rather then setting this variable directly, use
NO_DEFER_POP and OK_DEFER_POP. */
int x_inhibit_defer_pop;
/* If PREFERRED_STACK_BOUNDARY and PUSH_ROUNDING are defined, the stack
boundary can be momentarily unaligned while pushing the arguments.
Record the delta since last aligned boundary here in order to get
stack alignment in the nested function calls working right. */
int x_stack_pointer_delta;
/* Nonzero means __builtin_saveregs has already been done in this function.
The value is the pseudoreg containing the value __builtin_saveregs
returned. */
rtx x_saveregs_value;
/* Similarly for __builtin_apply_args. */
rtx x_apply_args_value;
/* List of labels that must never be deleted. */
rtx x_forced_labels;
};
typedef struct call_site_record_d *call_site_record;
/* RTL representation of exception handling. */
struct GTY(()) rtl_eh {
rtx ehr_stackadj;
rtx ehr_handler;
rtx ehr_label;
rtx sjlj_fc;
rtx sjlj_exit_after;
vec<uchar, va_gc> *action_record_data;
vec<call_site_record, va_gc> *call_site_record_v[2];
};
#define pending_stack_adjust (crtl->expr.x_pending_stack_adjust)
#define inhibit_defer_pop (crtl->expr.x_inhibit_defer_pop)
#define saveregs_value (crtl->expr.x_saveregs_value)
#define apply_args_value (crtl->expr.x_apply_args_value)
#define forced_labels (crtl->expr.x_forced_labels)
#define stack_pointer_delta (crtl->expr.x_stack_pointer_delta)
struct gimple_df;
struct temp_slot;
typedef struct temp_slot *temp_slot_p;
struct call_site_record_d;
struct dw_fde_struct;
struct ipa_opt_pass_d;
typedef struct ipa_opt_pass_d *ipa_opt_pass;
struct GTY(()) varasm_status {
/* If we're using a per-function constant pool, this is it. */
struct rtx_constant_pool *pool;
/* Number of tree-constants deferred during the expansion of this
function. */
unsigned int deferred_constants;
};
/* Information mainlined about RTL representation of incoming arguments. */
struct GTY(()) incoming_args {
/* Number of bytes of args popped by function being compiled on its return.
Zero if no bytes are to be popped.
May affect compilation of return insn or of function epilogue. */
int pops_args;
/* If function's args have a fixed size, this is that size, in bytes.
Otherwise, it is -1.
May affect compilation of return insn or of function epilogue. */
int size;
/* # bytes the prologue should push and pretend that the caller pushed them.
The prologue must do this, but only if parms can be passed in
registers. */
int pretend_args_size;
/* This is the offset from the arg pointer to the place where the first
anonymous arg can be found, if there is one. */
rtx arg_offset_rtx;
/* Quantities of various kinds of registers
used for the current function's args. */
CUMULATIVE_ARGS info;
/* The arg pointer hard register, or the pseudo into which it was copied. */
rtx internal_arg_pointer;
};
/* Data for function partitioning. */
struct GTY(()) function_subsections {
/* Assembly labels for the hot and cold text sections, to
be used by debugger functions for determining the size of text
sections. */
const char *hot_section_label;
const char *cold_section_label;
const char *hot_section_end_label;
const char *cold_section_end_label;
};
/* Describe an empty area of space in the stack frame. These can be chained
into a list; this is used to keep track of space wasted for alignment
reasons. */
struct GTY(()) frame_space
{
struct frame_space *next;
HOST_WIDE_INT start;
HOST_WIDE_INT length;
};
/* Datastructures maintained for currently processed function in RTL form. */
struct GTY(()) rtl_data {
struct expr_status expr;
struct emit_status emit;
struct varasm_status varasm;
struct incoming_args args;
struct function_subsections subsections;
struct rtl_eh eh;
/* For function.c */
/* # of bytes of outgoing arguments. If ACCUMULATE_OUTGOING_ARGS is
defined, the needed space is pushed by the prologue. */
int outgoing_args_size;
/* If nonzero, an RTL expression for the location at which the current
function returns its result. If the current function returns its
result in a register, current_function_return_rtx will always be
the hard register containing the result. */
rtx return_rtx;
/* Vector of initial-value pairs. Each pair consists of a pseudo
register of approprite mode that stores the initial value a hard
register REGNO, and that hard register itself. */
/* ??? This could be a VEC but there is currently no way to define an
opaque VEC type. */
struct initial_value_struct *hard_reg_initial_vals;
/* A variable living at the top of the frame that holds a known value.
Used for detecting stack clobbers. */
tree stack_protect_guard;
/* List (chain of EXPR_LIST) of labels heading the current handlers for
nonlocal gotos. */
rtx x_nonlocal_goto_handler_labels;
/* Label that will go on function epilogue.
Jumping to this label serves as a "return" instruction
on machines which require execution of the epilogue on all returns. */
rtx x_return_label;
/* Label that will go on the end of function epilogue.
Jumping to this label serves as a "naked return" instruction
on machines which require execution of the epilogue on all returns. */
rtx x_naked_return_label;
/* List (chain of EXPR_LISTs) of all stack slots in this function.
Made for the sake of unshare_all_rtl. */
rtx x_stack_slot_list;
/* List of empty areas in the stack frame. */
struct frame_space *frame_space_list;
/* Place after which to insert the tail_recursion_label if we need one. */
rtx x_stack_check_probe_note;
/* Location at which to save the argument pointer if it will need to be
referenced. There are two cases where this is done: if nonlocal gotos
exist, or if vars stored at an offset from the argument pointer will be
needed by inner routines. */
rtx x_arg_pointer_save_area;
/* Dynamic Realign Argument Pointer used for realigning stack. */
rtx drap_reg;
/* Offset to end of allocated area of stack frame.
If stack grows down, this is the address of the last stack slot allocated.
If stack grows up, this is the address for the next slot. */
HOST_WIDE_INT x_frame_offset;
/* Insn after which register parms and SAVE_EXPRs are born, if nonopt. */
rtx x_parm_birth_insn;
/* List of all used temporaries allocated, by level. */
vec<temp_slot_p, va_gc> *x_used_temp_slots;
/* List of available temp slots. */
struct temp_slot *x_avail_temp_slots;
/* Current nesting level for temporaries. */
int x_temp_slot_level;
/* The largest alignment needed on the stack, including requirement
for outgoing stack alignment. */
unsigned int stack_alignment_needed;
/* Preferred alignment of the end of stack frame, which is preferred
to call other functions. */
unsigned int preferred_stack_boundary;
/* The minimum alignment of parameter stack. */
unsigned int parm_stack_boundary;
/* The largest alignment of slot allocated on the stack. */
unsigned int max_used_stack_slot_alignment;
/* The stack alignment estimated before reload, with consideration of
following factors:
1. Alignment of local stack variables (max_used_stack_slot_alignment)
2. Alignment requirement to call other functions
(preferred_stack_boundary)
3. Alignment of non-local stack variables but might be spilled in
local stack. */
unsigned int stack_alignment_estimated;
/* For reorg. */
/* Nonzero if function being compiled called builtin_return_addr or
builtin_frame_address with nonzero count. */
bool accesses_prior_frames;
/* Nonzero if the function calls __builtin_eh_return. */
bool calls_eh_return;
/* Nonzero if function saves all registers, e.g. if it has a nonlocal
label that can reach the exit block via non-exceptional paths. */
bool saves_all_registers;
/* Nonzero if function being compiled has nonlocal gotos to parent
function. */
bool has_nonlocal_goto;
/* Nonzero if function being compiled has an asm statement. */
bool has_asm_statement;
/* This bit is used by the exception handling logic. It is set if all
calls (if any) are sibling calls. Such functions do not have to
have EH tables generated, as they cannot throw. A call to such a
function, however, should be treated as throwing if any of its callees
can throw. */
bool all_throwers_are_sibcalls;
/* Nonzero if stack limit checking should be enabled in the current
function. */
bool limit_stack;
/* Nonzero if profiling code should be generated. */
bool profile;
/* Nonzero if the current function uses the constant pool. */
bool uses_const_pool;
/* Nonzero if the current function uses pic_offset_table_rtx. */
bool uses_pic_offset_table;
/* Nonzero if the current function needs an lsda for exception handling. */
bool uses_eh_lsda;
/* Set when the tail call has been produced. */
bool tail_call_emit;
/* Nonzero if code to initialize arg_pointer_save_area has been emitted. */
bool arg_pointer_save_area_init;
/* Nonzero if current function must be given a frame pointer.
Set in reload1.c or lra-eliminations.c if anything is allocated
on the stack there. */
bool frame_pointer_needed;
/* When set, expand should optimize for speed. */
bool maybe_hot_insn_p;
/* Nonzero if function stack realignment is needed. This flag may be
set twice: before and after reload. It is set before reload wrt
stack alignment estimation before reload. It will be changed after
reload if by then criteria of stack realignment is different.
The value set after reload is the accurate one and is finalized. */
bool stack_realign_needed;
/* Nonzero if function stack realignment is tried. This flag is set
only once before reload. It affects register elimination. This
is used to generate DWARF debug info for stack variables. */
bool stack_realign_tried;
/* Nonzero if function being compiled needs dynamic realigned
argument pointer (drap) if stack needs realigning. */
bool need_drap;
/* Nonzero if function stack realignment estimation is done, namely
stack_realign_needed flag has been set before reload wrt estimated
stack alignment info. */
bool stack_realign_processed;
/* Nonzero if function stack realignment has been finalized, namely
stack_realign_needed flag has been set and finalized after reload. */
bool stack_realign_finalized;
/* True if dbr_schedule has already been called for this function. */
bool dbr_scheduled_p;
/* True if current function can not throw. Unlike
TREE_NOTHROW (current_function_decl) it is set even for overwritable
function where currently compiled version of it is nothrow. */
bool nothrow;
/* True if we performed shrink-wrapping for the current function. */
bool shrink_wrapped;
/* Nonzero if function being compiled doesn't modify the stack pointer
(ignoring the prologue and epilogue). This is only valid after
pass_stack_ptr_mod has run. */
bool sp_is_unchanging;
/* Nonzero if function being compiled doesn't contain any calls
(ignoring the prologue and epilogue). This is set prior to
local register allocation and is valid for the remaining
compiler passes. */
bool is_leaf;
/* Nonzero if the function being compiled is a leaf function which only
uses leaf registers. This is valid after reload (specifically after
sched2) and is useful only if the port defines LEAF_REGISTERS. */
bool uses_only_leaf_regs;
/* Like regs_ever_live, but 1 if a reg is set or clobbered from an
asm. Unlike regs_ever_live, elements of this array corresponding
to eliminable regs (like the frame pointer) are set if an asm
sets them. */
HARD_REG_SET asm_clobbers;
};
#define return_label (crtl->x_return_label)
#define naked_return_label (crtl->x_naked_return_label)
#define stack_slot_list (crtl->x_stack_slot_list)
#define parm_birth_insn (crtl->x_parm_birth_insn)
#define frame_offset (crtl->x_frame_offset)
#define stack_check_probe_note (crtl->x_stack_check_probe_note)
#define arg_pointer_save_area (crtl->x_arg_pointer_save_area)
#define used_temp_slots (crtl->x_used_temp_slots)
#define avail_temp_slots (crtl->x_avail_temp_slots)
#define temp_slot_level (crtl->x_temp_slot_level)
#define nonlocal_goto_handler_labels (crtl->x_nonlocal_goto_handler_labels)
#define frame_pointer_needed (crtl->frame_pointer_needed)
#define stack_realign_fp (crtl->stack_realign_needed && !crtl->need_drap)
#define stack_realign_drap (crtl->stack_realign_needed && crtl->need_drap)
extern GTY(()) struct rtl_data x_rtl;
/* Accessor to RTL datastructures. We keep them statically allocated now since
we never keep multiple functions. For threaded compiler we might however
want to do differently. */
#define crtl (&x_rtl)
struct GTY(()) stack_usage
{
/* # of bytes of static stack space allocated by the function. */
HOST_WIDE_INT static_stack_size;
/* # of bytes of dynamic stack space allocated by the function. This is
meaningful only if has_unbounded_dynamic_stack_size is zero. */
HOST_WIDE_INT dynamic_stack_size;
/* # of bytes of space pushed onto the stack after the prologue. If
!ACCUMULATE_OUTGOING_ARGS, it contains the outgoing arguments. */
int pushed_stack_size;
/* Nonzero if the amount of stack space allocated dynamically cannot
be bounded at compile-time. */
unsigned int has_unbounded_dynamic_stack_size : 1;
};
#define current_function_static_stack_size (cfun->su->static_stack_size)
#define current_function_dynamic_stack_size (cfun->su->dynamic_stack_size)
#define current_function_pushed_stack_size (cfun->su->pushed_stack_size)
#define current_function_has_unbounded_dynamic_stack_size \
(cfun->su->has_unbounded_dynamic_stack_size)
#define current_function_allocates_dynamic_stack_space \
(current_function_dynamic_stack_size != 0 \
|| current_function_has_unbounded_dynamic_stack_size)
/* This structure can save all the important global and static variables
describing the status of the current function. */
struct GTY(()) function {
struct eh_status *eh;
/* The control flow graph for this function. */
struct control_flow_graph *cfg;
/* GIMPLE body for this function. */
gimple_seq gimple_body;
/* SSA and dataflow information. */
struct gimple_df *gimple_df;
/* The loops in this function. */
struct loops *x_current_loops;
/* The stack usage of this function. */
struct stack_usage *su;
/* Value histograms attached to particular statements. */
htab_t GTY((skip)) value_histograms;
/* For function.c. */
/* Points to the FUNCTION_DECL of this function. */
tree decl;
/* A PARM_DECL that should contain the static chain for this function.
It will be initialized at the beginning of the function. */
tree static_chain_decl;
/* An expression that contains the non-local goto save area. The first
word is the saved frame pointer and the second is the saved stack
pointer. */
tree nonlocal_goto_save_area;
/* Vector of function local variables, functions, types and constants. */
vec<tree, va_gc> *local_decls;
/* For md files. */
/* tm.h can use this to store whatever it likes. */
struct machine_function * GTY ((maybe_undef)) machine;
/* Language-specific code can use this to store whatever it likes. */
struct language_function * language;
/* Used types hash table. */
htab_t GTY ((param_is (union tree_node))) used_types_hash;
/* Dwarf2 Frame Description Entry, containing the Call Frame Instructions
used for unwinding. Only set when either dwarf2 unwinding or dwarf2
debugging is enabled. */
struct dw_fde_struct *fde;
/* Last statement uid. */
int last_stmt_uid;
/* Function sequence number for profiling, debugging, etc. */
int funcdef_no;
/* Line number of the start of the function for debugging purposes. */
location_t function_start_locus;
/* Line number of the end of the function. */
location_t function_end_locus;
/* Properties used by the pass manager. */
unsigned int curr_properties;
unsigned int last_verified;
/* Non-null if the function does something that would prevent it from
being copied; this applies to both versioning and inlining. Set to
a string describing the reason for failure. */
const char * GTY((skip)) cannot_be_copied_reason;
/* Collected bit flags. */
/* Number of units of general registers that need saving in stdarg
function. What unit is depends on the backend, either it is number
of bytes, or it can be number of registers. */
unsigned int va_list_gpr_size : 8;
/* Number of units of floating point registers that need saving in stdarg
function. */
unsigned int va_list_fpr_size : 8;
/* Nonzero if function being compiled can call setjmp. */
unsigned int calls_setjmp : 1;
/* Nonzero if function being compiled can call alloca,
either as a subroutine or builtin. */
unsigned int calls_alloca : 1;
/* Nonzero if function being compiled receives nonlocal gotos
from nested functions. */
unsigned int has_nonlocal_label : 1;
/* Nonzero if we've set cannot_be_copied_reason. I.e. if
(cannot_be_copied_set && !cannot_be_copied_reason), the function
can in fact be copied. */
unsigned int cannot_be_copied_set : 1;
/* Nonzero if current function uses stdarg.h or equivalent. */
unsigned int stdarg : 1;
unsigned int after_inlining : 1;
unsigned int always_inline_functions_inlined : 1;
/* Nonzero if function being compiled can throw synchronous non-call
exceptions. */
unsigned int can_throw_non_call_exceptions : 1;
/* Nonzero if instructions that may throw exceptions but don't otherwise
contribute to the execution of the program can be deleted. */
unsigned int can_delete_dead_exceptions : 1;
/* Fields below this point are not set for abstract functions; see
allocate_struct_function. */
/* Nonzero if function being compiled needs to be given an address
where the value should be stored. */
unsigned int returns_struct : 1;
/* Nonzero if function being compiled needs to
return the address of where it has put a structure value. */
unsigned int returns_pcc_struct : 1;
/* Nonzero if this function has local DECL_HARD_REGISTER variables.
In this case code motion has to be done more carefully. */
unsigned int has_local_explicit_reg_vars : 1;
/* Nonzero if the current function is a thunk, i.e., a lightweight
function implemented by the output_mi_thunk hook) that just
adjusts one of its arguments and forwards to another
function. */
unsigned int is_thunk : 1;
};
/* Add the decl D to the local_decls list of FUN. */
static inline void
add_local_decl (struct function *fun, tree d)
{
vec_safe_push (fun->local_decls, d);
}
#define FOR_EACH_LOCAL_DECL(FUN, I, D) \
FOR_EACH_VEC_SAFE_ELT_REVERSE ((FUN)->local_decls, I, D)
/* If va_list_[gf]pr_size is set to this, it means we don't know how
many units need to be saved. */
#define VA_LIST_MAX_GPR_SIZE 255
#define VA_LIST_MAX_FPR_SIZE 255
/* The function currently being compiled. */
extern GTY(()) struct function *cfun;
/* In order to ensure that cfun is not set directly, we redefine it so
that it is not an lvalue. Rather than assign to cfun, use
push_cfun or set_cfun. */
#define cfun (cfun + 0)
/* Nonzero if we've already converted virtual regs to hard regs. */
extern int virtuals_instantiated;
/* Nonzero if at least one trampoline has been created. */
extern int trampolines_created;
struct GTY(()) types_used_by_vars_entry {
tree type;
tree var_decl;
};
/* Hash table making the relationship between a global variable
and the types it references in its initializer. The key of the
entry is a referenced type, and the value is the DECL of the global
variable. types_use_by_vars_do_hash and types_used_by_vars_eq below are
the hash and equality functions to use for this hash table. */
extern GTY((param_is (struct types_used_by_vars_entry))) htab_t
types_used_by_vars_hash;
hashval_t types_used_by_vars_do_hash (const void*);
int types_used_by_vars_eq (const void *, const void *);
void types_used_by_var_decl_insert (tree type, tree var_decl);
/* During parsing of a global variable, this vector contains the types
referenced by the global variable. */
extern GTY(()) vec<tree, va_gc> *types_used_by_cur_var_decl;
/* cfun shouldn't be set directly; use one of these functions instead. */
extern void set_cfun (struct function *new_cfun);
extern void push_cfun (struct function *new_cfun);
extern void pop_cfun (void);
extern void instantiate_decl_rtl (rtx x);
/* For backward compatibility... eventually these should all go away. */
#define current_function_funcdef_no (cfun->funcdef_no)
#define current_loops (cfun->x_current_loops)
#define dom_computed (cfun->cfg->x_dom_computed)
#define n_bbs_in_dom_tree (cfun->cfg->x_n_bbs_in_dom_tree)
#define VALUE_HISTOGRAMS(fun) (fun)->value_histograms
/* Identify BLOCKs referenced by more than one NOTE_INSN_BLOCK_{BEG,END},
and create duplicate blocks. */
extern void reorder_blocks (void);
/* Set BLOCK_NUMBER for all the blocks in FN. */
extern void number_blocks (tree);
extern void clear_block_marks (tree);
extern tree blocks_nreverse (tree);
extern tree block_chainon (tree, tree);
/* Return size needed for stack frame based on slots so far allocated.
This size counts from zero. It is not rounded to STACK_BOUNDARY;
the caller may have to do that. */
extern HOST_WIDE_INT get_frame_size (void);
/* Issue an error message and return TRUE if frame OFFSET overflows in
the signed target pointer arithmetics for function FUNC. Otherwise
return FALSE. */
extern bool frame_offset_overflow (HOST_WIDE_INT, tree);
/* A pointer to a function to create target specific, per-function
data structures. */
extern struct machine_function * (*init_machine_status) (void);
/* Save and restore status information for a nested function. */
extern void free_after_parsing (struct function *);
extern void free_after_compilation (struct function *);
extern void init_varasm_status (void);
#ifdef RTX_CODE
extern void diddle_return_value (void (*)(rtx, void*), void*);
extern void clobber_return_register (void);
#endif
extern rtx get_arg_pointer_save_area (void);
/* Returns the name of the current function. */
extern const char *fndecl_name (tree);
extern const char *function_name (struct function *);
extern const char *current_function_name (void);
extern void do_warn_unused_parameter (tree);
extern bool pass_by_reference (CUMULATIVE_ARGS *, enum machine_mode,
tree, bool);
extern bool reference_callee_copied (CUMULATIVE_ARGS *, enum machine_mode,
tree, bool);
extern void used_types_insert (tree);
extern int get_next_funcdef_no (void);
extern int get_last_funcdef_no (void);
#ifdef HAVE_simple_return
extern bool requires_stack_frame_p (rtx, HARD_REG_SET, HARD_REG_SET);
#endif
extern rtx get_hard_reg_initial_val (enum machine_mode, unsigned int);
extern rtx has_hard_reg_initial_val (enum machine_mode, unsigned int);
extern rtx get_hard_reg_initial_reg (rtx);
extern bool initial_value_entry (int i, rtx *, rtx *);
/* Called from gimple_expand_cfg. */
extern unsigned int emit_initial_value_sets (void);
/* In predict.c */
extern bool optimize_function_for_size_p (struct function *);
extern bool optimize_function_for_speed_p (struct function *);
#endif /* GCC_FUNCTION_H */

166
src/include/gcc-plugin.h Normal file
View File

@ -0,0 +1,166 @@
/* Public header file for plugins to include.
Copyright (C) 2009-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GCC is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GCC_PLUGIN_H
#define GCC_PLUGIN_H
#ifndef IN_GCC
#define IN_GCC
#endif
#include "config.h"
#include "system.h"
#include "coretypes.h"
#include "highlev-plugin-common.h"
#include "hashtab.h"
/* Event names. */
enum plugin_event
{
# define DEFEVENT(NAME) NAME,
# include "plugin.def"
# undef DEFEVENT
PLUGIN_EVENT_FIRST_DYNAMIC
};
/* All globals declared here have C linkage to reduce link compatibility
issues with implementation language choice and mangling. */
#ifdef __cplusplus
extern "C" {
#endif
extern const char **plugin_event_name;
struct plugin_argument
{
char *key; /* key of the argument. */
char *value; /* value is optional and can be NULL. */
};
/* Additional information about the plugin. Used by --help and --version. */
struct plugin_info
{
const char *version;
const char *help;
};
/* Represents the gcc version. Used to avoid using an incompatible plugin. */
struct plugin_gcc_version
{
const char *basever;
const char *datestamp;
const char *devphase;
const char *revision;
const char *configuration_arguments;
};
/* Object that keeps track of the plugin name and its arguments. */
struct plugin_name_args
{
char *base_name; /* Short name of the plugin (filename without
.so suffix). */
const char *full_name; /* Path to the plugin as specified with
-fplugin=. */
int argc; /* Number of arguments specified with
-fplugin-arg-... */
struct plugin_argument *argv; /* Array of ARGC key-value pairs. */
const char *version; /* Version string provided by plugin. */
const char *help; /* Help string provided by plugin. */
};
/* The default version check. Compares every field in VERSION. */
extern bool plugin_default_version_check (struct plugin_gcc_version *,
struct plugin_gcc_version *);
/* Function type for the plugin initialization routine. Each plugin module
should define this as an externally-visible function with name
"plugin_init."
PLUGIN_INFO - plugin invocation information.
VERSION - the plugin_gcc_version symbol of GCC.
Returns 0 if initialization finishes successfully. */
typedef int (*plugin_init_func) (struct plugin_name_args *plugin_info,
struct plugin_gcc_version *version);
/* Declaration for "plugin_init" function so that it doesn't need to be
duplicated in every plugin. */
extern int plugin_init (struct plugin_name_args *plugin_info,
struct plugin_gcc_version *version);
/* Function type for a plugin callback routine.
GCC_DATA - event-specific data provided by GCC
USER_DATA - plugin-specific data provided by the plugin */
typedef void (*plugin_callback_func) (void *gcc_data, void *user_data);
/* Called from the plugin's initialization code. Register a single callback.
This function can be called multiple times.
PLUGIN_NAME - display name for this plugin
EVENT - which event the callback is for
CALLBACK - the callback to be called at the event
USER_DATA - plugin-provided data.
*/
/* Number of event ids / names registered so far. */
extern int get_event_last (void);
int get_named_event_id (const char *name, enum insert_option insert);
/* This is also called without a callback routine for the
PLUGIN_PASS_MANAGER_SETUP, PLUGIN_INFO, PLUGIN_REGISTER_GGC_ROOTS and
PLUGIN_REGISTER_GGC_CACHES pseudo-events, with a specific user_data.
*/
extern void register_callback (const char *plugin_name,
int event,
plugin_callback_func callback,
void *user_data);
extern int unregister_callback (const char *plugin_name, int event);
/* Retrieve the plugin directory name, as returned by the
-fprint-file-name=plugin argument to the gcc program, which is the
-iplugindir program argument to cc1. */
extern const char* default_plugin_dir_name (void);
#ifdef __cplusplus
}
#endif
/* In case the C++ compiler does name mangling for globals, declare
plugin_is_GPL_compatible extern "C" so that a later definition
in a plugin file will have this linkage. */
#ifdef __cplusplus
extern "C" {
#endif
extern int plugin_is_GPL_compatible;
#ifdef __cplusplus
}
#endif
#endif /* GCC_PLUGIN_H */

1219
src/include/genrtl.h Normal file

File diff suppressed because it is too large Load Diff

279
src/include/ggc.h Normal file
View File

@ -0,0 +1,279 @@
/* Garbage collection for the GNU compiler.
Copyright (C) 1998-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GCC_GGC_H
#define GCC_GGC_H
#include "statistics.h"
/* Symbols are marked with `ggc' for `gcc gc' so as not to interfere with
an external gc library that might be linked in. */
/* Constants for general use. */
extern const char empty_string[]; /* empty string */
/* Internal functions and data structures used by the GTY
machinery, including the generated gt*.[hc] files. */
#include "gtype-desc.h"
/* One of these applies its third parameter (with cookie in the fourth
parameter) to each pointer in the object pointed to by the first
parameter, using the second parameter. */
typedef void (*gt_note_pointers) (void *, void *, gt_pointer_operator,
void *);
/* One of these is called before objects are re-ordered in memory.
The first parameter is the original object, the second is the
subobject that has had its pointers reordered, the third parameter
can compute the new values of a pointer when given the cookie in
the fourth parameter. */
typedef void (*gt_handle_reorder) (void *, void *, gt_pointer_operator,
void *);
/* Used by the gt_pch_n_* routines. Register an object in the hash table. */
extern int gt_pch_note_object (void *, void *, gt_note_pointers);
/* Used by the gt_pch_n_* routines. Register that an object has a reorder
function. */
extern void gt_pch_note_reorder (void *, void *, gt_handle_reorder);
/* Mark the object in the first parameter and anything it points to. */
typedef void (*gt_pointer_walker) (void *);
/* Structures for the easy way to mark roots.
In an array, terminated by having base == NULL. */
struct ggc_root_tab {
void *base;
size_t nelt;
size_t stride;
gt_pointer_walker cb;
gt_pointer_walker pchw;
};
#define LAST_GGC_ROOT_TAB { NULL, 0, 0, NULL, NULL }
/* Pointers to arrays of ggc_root_tab, terminated by NULL. */
extern const struct ggc_root_tab * const gt_ggc_rtab[];
extern const struct ggc_root_tab * const gt_ggc_deletable_rtab[];
extern const struct ggc_root_tab * const gt_pch_cache_rtab[];
extern const struct ggc_root_tab * const gt_pch_scalar_rtab[];
/* Structure for hash table cache marking. */
struct htab;
struct ggc_cache_tab {
struct htab * *base;
size_t nelt;
size_t stride;
gt_pointer_walker cb;
gt_pointer_walker pchw;
int (*marked_p) (const void *);
};
#define LAST_GGC_CACHE_TAB { NULL, 0, 0, NULL, NULL, NULL }
/* Pointers to arrays of ggc_cache_tab, terminated by NULL. */
extern const struct ggc_cache_tab * const gt_ggc_cache_rtab[];
/* If EXPR is not NULL and previously unmarked, mark it and evaluate
to true. Otherwise evaluate to false. */
#define ggc_test_and_set_mark(EXPR) \
((EXPR) != NULL && ((void *) (EXPR)) != (void *) 1 && ! ggc_set_mark (EXPR))
#define ggc_mark(EXPR) \
do { \
const void *const a__ = (EXPR); \
if (a__ != NULL && a__ != (void *) 1) \
ggc_set_mark (a__); \
} while (0)
/* Actually set the mark on a particular region of memory, but don't
follow pointers. This function is called by ggc_mark_*. It
returns zero if the object was not previously marked; nonzero if
the object was already marked, or if, for any other reason,
pointers in this data structure should not be traversed. */
extern int ggc_set_mark (const void *);
/* Return 1 if P has been marked, zero otherwise.
P must have been allocated by the GC allocator; it mustn't point to
static objects, stack variables, or memory allocated with malloc. */
extern int ggc_marked_p (const void *);
/* PCH and GGC handling for strings, mostly trivial. */
extern void gt_pch_n_S (const void *);
extern void gt_ggc_m_S (const void *);
/* End of GTY machinery API. */
/* Initialize the string pool. */
extern void init_stringpool (void);
/* Initialize the garbage collector. */
extern void init_ggc (void);
/* When true, identifier nodes are considered as GC roots. When
false, identifier nodes are treated like any other GC-allocated
object, and the identifier hash table is treated as a weak
hash. */
extern bool ggc_protect_identifiers;
/* Write out all GCed objects to F. */
extern void gt_pch_save (FILE *f);
/* Allocation. */
/* The internal primitive. */
extern void *ggc_internal_alloc_stat (size_t MEM_STAT_DECL)
ATTRIBUTE_MALLOC;
extern size_t ggc_round_alloc_size (size_t requested_size);
#define ggc_internal_alloc(s) ggc_internal_alloc_stat (s MEM_STAT_INFO)
/* Allocates cleared memory. */
extern void *ggc_internal_cleared_alloc_stat (size_t MEM_STAT_DECL)
ATTRIBUTE_MALLOC;
/* Resize a block. */
extern void *ggc_realloc_stat (void *, size_t MEM_STAT_DECL);
/* Free a block. To be used when known for certain it's not reachable. */
extern void ggc_free (void *);
extern void dump_ggc_loc_statistics (bool);
/* Reallocators. */
#define GGC_RESIZEVEC(T, P, N) \
((T *) ggc_realloc_stat ((P), (N) * sizeof (T) MEM_STAT_INFO))
#define GGC_RESIZEVAR(T, P, N) \
((T *) ggc_realloc_stat ((P), (N) MEM_STAT_INFO))
static inline void *
ggc_internal_vec_alloc_stat (size_t s, size_t c MEM_STAT_DECL)
{
return ggc_internal_alloc_stat (c * s PASS_MEM_STAT);
}
static inline void *
ggc_internal_cleared_vec_alloc_stat (size_t s, size_t c MEM_STAT_DECL)
{
return ggc_internal_cleared_alloc_stat (c * s PASS_MEM_STAT);
}
#define ggc_internal_cleared_vec_alloc(s, c) \
(ggc_internal_cleared_vec_alloc_stat ((s), (c) MEM_STAT_INFO))
static inline void *
ggc_alloc_atomic_stat (size_t s MEM_STAT_DECL)
{
return ggc_internal_alloc_stat (s PASS_MEM_STAT);
}
#define ggc_alloc_atomic(S) (ggc_alloc_atomic_stat ((S) MEM_STAT_INFO))
#define ggc_alloc_cleared_atomic(S) \
(ggc_internal_cleared_alloc_stat ((S) MEM_STAT_INFO))
extern void *ggc_cleared_alloc_htab_ignore_args (size_t, size_t)
ATTRIBUTE_MALLOC;
extern void *ggc_cleared_alloc_ptr_array_two_args (size_t, size_t)
ATTRIBUTE_MALLOC;
#define htab_create_ggc(SIZE, HASH, EQ, DEL) \
htab_create_typed_alloc (SIZE, HASH, EQ, DEL, \
ggc_cleared_alloc_htab_ignore_args, \
ggc_cleared_alloc_ptr_array_two_args, \
ggc_free)
#define splay_tree_new_ggc(COMPARE, ALLOC_TREE, ALLOC_NODE) \
splay_tree_new_typed_alloc (COMPARE, NULL, NULL, &ALLOC_TREE, &ALLOC_NODE, \
&ggc_splay_dont_free, NULL)
extern void *ggc_splay_alloc (int, void *)
ATTRIBUTE_MALLOC;
extern void ggc_splay_dont_free (void *, void *);
/* Allocate a gc-able string, and fill it with LENGTH bytes from CONTENTS.
If LENGTH is -1, then CONTENTS is assumed to be a
null-terminated string and the memory sized accordingly. */
extern const char *ggc_alloc_string_stat (const char *contents, int length
MEM_STAT_DECL);
#define ggc_alloc_string(c, l) ggc_alloc_string_stat (c, l MEM_STAT_INFO)
/* Make a copy of S, in GC-able memory. */
#define ggc_strdup(S) ggc_alloc_string_stat ((S), -1 MEM_STAT_INFO)
/* Invoke the collector. Garbage collection occurs only when this
function is called, not during allocations. */
extern void ggc_collect (void);
/* Register an additional root table. This can be useful for some
plugins. Does nothing if the passed pointer is NULL. */
extern void ggc_register_root_tab (const struct ggc_root_tab *);
/* Register an additional cache table. This can be useful for some
plugins. Does nothing if the passed pointer is NULL. */
extern void ggc_register_cache_tab (const struct ggc_cache_tab *);
/* Read objects previously saved with gt_pch_save from F. */
extern void gt_pch_restore (FILE *f);
/* Statistics. */
/* Print allocation statistics. */
extern void ggc_print_statistics (void);
extern void stringpool_statistics (void);
/* Heuristics. */
extern void init_ggc_heuristics (void);
#define ggc_alloc_rtvec_sized(NELT) \
ggc_alloc_rtvec_def (sizeof (struct rtvec_def) \
+ ((NELT) - 1) * sizeof (rtx)) \
/* Memory statistics passing versions of some allocators. Too few of them to
make gengtype produce them, so just define the needed ones here. */
static inline struct rtx_def *
ggc_alloc_rtx_def_stat (size_t s MEM_STAT_DECL)
{
return (struct rtx_def *) ggc_internal_alloc_stat (s PASS_MEM_STAT);
}
static inline union tree_node *
ggc_alloc_tree_node_stat (size_t s MEM_STAT_DECL)
{
return (union tree_node *) ggc_internal_alloc_stat (s PASS_MEM_STAT);
}
static inline union tree_node *
ggc_alloc_cleared_tree_node_stat (size_t s MEM_STAT_DECL)
{
return (union tree_node *) ggc_internal_cleared_alloc_stat (s PASS_MEM_STAT);
}
static inline union gimple_statement_d *
ggc_alloc_cleared_gimple_statement_d_stat (size_t s MEM_STAT_DECL)
{
return (union gimple_statement_d *)
ggc_internal_cleared_alloc_stat (s PASS_MEM_STAT);
}
#endif

View File

@ -0,0 +1,36 @@
/* Various declarations for pretty formatting of GIMPLE statements and
expressions.
Copyright (C) 2000-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GCC_GIMPLE_PRETTY_PRINT_H
#define GCC_GIMPLE_PRETTY_PRINT_H
#include "pretty-print.h"
#include "tree-pretty-print.h"
/* In gimple-pretty-print.c */
extern void debug_gimple_stmt (gimple);
extern void debug_gimple_seq (gimple_seq);
extern void print_gimple_seq (FILE *, gimple_seq, int, int);
extern void print_gimple_stmt (FILE *, gimple, int, int);
extern void print_gimple_expr (FILE *, gimple, int, int);
extern void pp_gimple_stmt_1 (pretty_printer *, gimple, int, int);
extern void gimple_dump_bb_for_graph (pretty_printer *, basic_block);
#endif /* ! GCC_GIMPLE_PRETTY_PRINT_H */

364
src/include/gimple.def Normal file
View File

@ -0,0 +1,364 @@
/* This file contains the definitions of the GIMPLE IR tuples used in GCC.
Copyright (C) 2007-2013 Free Software Foundation, Inc.
Contributed by Aldy Hernandez <aldyh@redhat.com>
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
/* The format of this file is
DEFGSCODE(GIMPLE_symbol, printable name, GSS_symbol). */
/* Error marker. This is used in similar ways as ERROR_MARK in tree.def. */
DEFGSCODE(GIMPLE_ERROR_MARK, "gimple_error_mark", GSS_BASE)
/* IMPORTANT. Do not rearrange the codes between GIMPLE_COND and
GIMPLE_RETURN. The ordering is exposed by gimple_has_ops calls.
These are all the GIMPLE statements with register operands. */
/* GIMPLE_COND <COND_CODE, OP1, OP2, TRUE_LABEL, FALSE_LABEL>
represents the conditional jump:
if (OP1 COND_CODE OP2) goto TRUE_LABEL else goto FALSE_LABEL
COND_CODE is the tree code used as the comparison predicate. It
must be of class tcc_comparison.
OP1 and OP2 are the operands used in the comparison. They must be
accepted by is_gimple_operand.
TRUE_LABEL and FALSE_LABEL are the LABEL_DECL nodes used as the
jump target for the comparison. */
DEFGSCODE(GIMPLE_COND, "gimple_cond", GSS_WITH_OPS)
/* GIMPLE_DEBUG represents a debug statement. */
DEFGSCODE(GIMPLE_DEBUG, "gimple_debug", GSS_WITH_OPS)
/* GIMPLE_GOTO <TARGET> represents unconditional jumps.
TARGET is a LABEL_DECL or an expression node for computed GOTOs. */
DEFGSCODE(GIMPLE_GOTO, "gimple_goto", GSS_WITH_OPS)
/* GIMPLE_LABEL <LABEL> represents label statements. LABEL is a
LABEL_DECL representing a jump target. */
DEFGSCODE(GIMPLE_LABEL, "gimple_label", GSS_WITH_OPS)
/* GIMPLE_SWITCH <INDEX, DEFAULT_LAB, LAB1, ..., LABN> represents the
multiway branch:
switch (INDEX)
{
case LAB1: ...; break;
...
case LABN: ...; break;
default: ...
}
INDEX is the variable evaluated to decide which label to jump to.
DEFAULT_LAB, LAB1 ... LABN are the tree nodes representing case labels.
They must be CASE_LABEL_EXPR nodes. */
DEFGSCODE(GIMPLE_SWITCH, "gimple_switch", GSS_WITH_OPS)
/* IMPORTANT.
Do not rearrange the codes between GIMPLE_ASSIGN and GIMPLE_RETURN.
It's exposed by GIMPLE_RANGE_CHECK calls. These are all the GIMPLE
statements with memory and register operands. */
/* GIMPLE_ASSIGN <SUBCODE, LHS, RHS1[, RHS2]> represents the assignment
statement
LHS = RHS1 SUBCODE RHS2.
SUBCODE is the tree code for the expression computed by the RHS of the
assignment. It must be one of the tree codes accepted by
get_gimple_rhs_class. If LHS is not a gimple register according to
is_gimple_reg, SUBCODE must be of class GIMPLE_SINGLE_RHS.
LHS is the operand on the LHS of the assignment. It must be a tree node
accepted by is_gimple_lvalue.
RHS1 is the first operand on the RHS of the assignment. It must always be
present. It must be a tree node accepted by is_gimple_val.
RHS2 is the second operand on the RHS of the assignment. It must be a tree
node accepted by is_gimple_val. This argument exists only if SUBCODE is
of class GIMPLE_BINARY_RHS. */
DEFGSCODE(GIMPLE_ASSIGN, "gimple_assign", GSS_WITH_MEM_OPS)
/* GIMPLE_ASM <STRING, I1, ..., IN, O1, ... OM, C1, ..., CP>
represents inline assembly statements.
STRING is the string containing the assembly statements.
I1 ... IN are the N input operands.
O1 ... OM are the M output operands.
C1 ... CP are the P clobber operands.
L1 ... LQ are the Q label operands. */
DEFGSCODE(GIMPLE_ASM, "gimple_asm", GSS_ASM)
/* GIMPLE_CALL <FN, LHS, ARG1, ..., ARGN[, CHAIN]> represents function
calls.
FN is the callee. It must be accepted by is_gimple_call_addr.
LHS is the operand where the return value from FN is stored. It may
be NULL.
ARG1 ... ARGN are the arguments. They must all be accepted by
is_gimple_operand.
CHAIN is the optional static chain link for nested functions. */
DEFGSCODE(GIMPLE_CALL, "gimple_call", GSS_CALL)
/* GIMPLE_TRANSACTION <BODY, LABEL> represents __transaction_atomic and
__transaction_relaxed blocks.
BODY is the sequence of statements inside the transaction.
LABEL is a label for the statement immediately following the
transaction. This is before RETURN so that it has MEM_OPS,
so that it can clobber global memory. */
DEFGSCODE(GIMPLE_TRANSACTION, "gimple_transaction", GSS_TRANSACTION)
/* GIMPLE_RETURN <RETVAL> represents return statements.
RETVAL is the value to return or NULL. If a value is returned it
must be accepted by is_gimple_operand. */
DEFGSCODE(GIMPLE_RETURN, "gimple_return", GSS_WITH_MEM_OPS)
/* GIMPLE_BIND <VARS, BLOCK, BODY> represents a lexical scope.
VARS is the set of variables declared in that scope.
BLOCK is the symbol binding block used for debug information.
BODY is the sequence of statements in the scope. */
DEFGSCODE(GIMPLE_BIND, "gimple_bind", GSS_BIND)
/* GIMPLE_CATCH <TYPES, HANDLER> represents a typed exception handler.
TYPES is the type (or list of types) handled. HANDLER is the
sequence of statements that handle these types. */
DEFGSCODE(GIMPLE_CATCH, "gimple_catch", GSS_CATCH)
/* GIMPLE_EH_FILTER <TYPES, FAILURE> represents an exception
specification. TYPES is a list of allowed types and FAILURE is the
sequence of statements to execute on failure. */
DEFGSCODE(GIMPLE_EH_FILTER, "gimple_eh_filter", GSS_EH_FILTER)
/* GIMPLE_EH_MUST_NOT_THROW <DECL> represents an exception barrier.
DECL is a noreturn function decl taking no arguments that will
be invoked if an exception propagates to this point. */
DEFGSCODE(GIMPLE_EH_MUST_NOT_THROW, "gimple_eh_must_not_throw", GSS_EH_MNT)
/* GIMPLE_EH_ELSE <N_BODY, E_BODY> must be the sole contents of
a GIMPLE_TRY_FINALLY node. For all normal exits from the try block,
N_BODY is run; for all exception exits from the try block,
E_BODY is run. */
DEFGSCODE(GIMPLE_EH_ELSE, "gimple_eh_else", GSS_EH_ELSE)
/* GIMPLE_RESX resumes execution after an exception. */
DEFGSCODE(GIMPLE_RESX, "gimple_resx", GSS_EH_CTRL)
/* GIMPLE_EH_DISPATCH demultiplexes an exception edge based on
the FILTER argument. */
DEFGSCODE(GIMPLE_EH_DISPATCH, "gimple_eh_dispatch", GSS_EH_CTRL)
/* GIMPLE_PHI <RESULT, ARG1, ..., ARGN> represents the PHI node
RESULT = PHI <ARG1, ..., ARGN>
RESULT is the SSA name created by this PHI node.
ARG1 ... ARGN are the arguments to the PHI node. N must be
exactly the same as the number of incoming edges to the basic block
holding the PHI node. Every argument is either an SSA name or a
tree node of class tcc_constant. */
DEFGSCODE(GIMPLE_PHI, "gimple_phi", GSS_PHI)
/* GIMPLE_TRY <TRY_KIND, EVAL, CLEANUP>
represents a try/catch or a try/finally statement.
TRY_KIND is either GIMPLE_TRY_CATCH or GIMPLE_TRY_FINALLY.
EVAL is the sequence of statements to execute on entry to GIMPLE_TRY.
CLEANUP is the sequence of statements to execute according to
TRY_KIND. If TRY_KIND is GIMPLE_TRY_CATCH, CLEANUP is only exected
if an exception is thrown during execution of EVAL. If TRY_KIND is
GIMPLE_TRY_FINALLY, CLEANUP is always executed after executing EVAL
(regardless of whether EVAL finished normally, or jumped out or an
exception was thrown). */
DEFGSCODE(GIMPLE_TRY, "gimple_try", GSS_TRY)
/* GIMPLE_NOP represents the "do nothing" statement. */
DEFGSCODE(GIMPLE_NOP, "gimple_nop", GSS_BASE)
/* IMPORTANT.
Do not rearrange any of the GIMPLE_OMP_* codes. This ordering is
exposed by the range check in gimple_omp_subcode(). */
/* Tuples used for lowering of OMP_ATOMIC. Although the form of the OMP_ATOMIC
expression is very simple (just in form mem op= expr), various implicit
conversions may cause the expression to become more complex, so that it does
not fit the gimple grammar very well. To overcome this problem, OMP_ATOMIC
is rewritten as a sequence of two codes in gimplification:
GIMPLE_OMP_LOAD (tmp, mem)
val = some computations involving tmp;
GIMPLE_OMP_STORE (val). */
DEFGSCODE(GIMPLE_OMP_ATOMIC_LOAD, "gimple_omp_atomic_load",
GSS_OMP_ATOMIC_LOAD)
DEFGSCODE(GIMPLE_OMP_ATOMIC_STORE, "gimple_omp_atomic_store",
GSS_OMP_ATOMIC_STORE)
/* GIMPLE_OMP_CONTINUE marks the location of the loop or sections
iteration in partially lowered OpenMP code. */
DEFGSCODE(GIMPLE_OMP_CONTINUE, "gimple_omp_continue", GSS_OMP_CONTINUE)
/* GIMPLE_OMP_CRITICAL <NAME, BODY> represents
#pragma omp critical [name]
NAME is the name given to the critical section.
BODY is the sequence of statements that are inside the critical section. */
DEFGSCODE(GIMPLE_OMP_CRITICAL, "gimple_omp_critical", GSS_OMP_CRITICAL)
/* GIMPLE_OMP_FOR <BODY, CLAUSES, INDEX, INITIAL, FINAL, COND, INCR, PRE_BODY>
represents
PRE_BODY
#pragma omp for [clause1 ... clauseN]
for (INDEX = INITIAL; INDEX COND FINAL; INDEX {+=,-=} INCR)
BODY
BODY is the loop body.
CLAUSES is the list of clauses.
INDEX must be an integer or pointer variable, which is implicitly thread
private. It must be accepted by is_gimple_operand.
INITIAL is the initial value given to INDEX. It must be
accepted by is_gimple_operand.
FINAL is the final value that INDEX should take. It must
be accepted by is_gimple_operand.
COND is the condition code for the controlling predicate. It must
be one of { <, >, <=, >= }
INCR is the loop index increment. It must be tree node of type
tcc_constant.
PRE_BODY is a landing pad filled by the gimplifier with things from
INIT, COND, and INCR that are technically part of the OMP_FOR
structured block, but are evaluated before the loop body begins.
INITIAL, FINAL and INCR are required to be loop invariant integer
expressions that are evaluated without any synchronization.
The evaluation order, frequency of evaluation and side-effects are
unspecified by the standard. */
DEFGSCODE(GIMPLE_OMP_FOR, "gimple_omp_for", GSS_OMP_FOR)
/* GIMPLE_OMP_MASTER <BODY> represents #pragma omp master.
BODY is the sequence of statements to execute in the master section. */
DEFGSCODE(GIMPLE_OMP_MASTER, "gimple_omp_master", GSS_OMP)
/* GIMPLE_OMP_ORDERED <BODY> represents #pragma omp ordered.
BODY is the sequence of statements to execute in the ordered section. */
DEFGSCODE(GIMPLE_OMP_ORDERED, "gimple_omp_ordered", GSS_OMP)
/* GIMPLE_OMP_PARALLEL <BODY, CLAUSES, CHILD_FN, DATA_ARG> represents
#pragma omp parallel [CLAUSES]
BODY
BODY is a the sequence of statements to be executed by all threads.
CLAUSES is a TREE_LIST node with all the clauses.
CHILD_FN is set when outlining the body of the parallel region.
All the statements in BODY are moved into this newly created
function when converting OMP constructs into low-GIMPLE.
DATA_ARG is a local variable in the parent function containing data
to be shared with CHILD_FN. This is used to implement all the data
sharing clauses. */
DEFGSCODE(GIMPLE_OMP_PARALLEL, "gimple_omp_parallel", GSS_OMP_PARALLEL)
/* GIMPLE_OMP_TASK <BODY, CLAUSES, CHILD_FN, DATA_ARG, COPY_FN,
ARG_SIZE, ARG_ALIGN> represents
#pragma omp task [CLAUSES]
BODY
BODY is a the sequence of statements to be executed by all threads.
CLAUSES is a TREE_LIST node with all the clauses.
CHILD_FN is set when outlining the body of the explicit task region.
All the statements in BODY are moved into this newly created
function when converting OMP constructs into low-GIMPLE.
DATA_ARG is a local variable in the parent function containing data
to be shared with CHILD_FN. This is used to implement all the data
sharing clauses.
COPY_FN is set when outlining the firstprivate var initialization.
All the needed statements are emitted into the newly created
function, or when only memcpy is needed, it is NULL.
ARG_SIZE and ARG_ALIGN are the size and alignment of the incoming
data area allocated by GOMP_task and passed to CHILD_FN. */
DEFGSCODE(GIMPLE_OMP_TASK, "gimple_omp_task", GSS_OMP_TASK)
/* OMP_RETURN marks the end of an OpenMP directive. */
DEFGSCODE(GIMPLE_OMP_RETURN, "gimple_omp_return", GSS_BASE)
/* OMP_SECTION <BODY> represents #pragma omp section.
BODY is the sequence of statements in the section body. */
DEFGSCODE(GIMPLE_OMP_SECTION, "gimple_omp_section", GSS_OMP)
/* OMP_SECTIONS <BODY, CLAUSES, CONTROL> represents #pragma omp sections.
BODY is the sequence of statements in the sections body.
CLAUSES is a TREE_LIST node holding the list of associated clauses.
CONTROL is a VAR_DECL used for deciding which of the sections
to execute. */
DEFGSCODE(GIMPLE_OMP_SECTIONS, "gimple_omp_sections", GSS_OMP_SECTIONS)
/* GIMPLE_OMP_SECTIONS_SWITCH is a marker placed immediately after
OMP_SECTIONS. It represents the GIMPLE_SWITCH used to decide which
branch is taken. */
DEFGSCODE(GIMPLE_OMP_SECTIONS_SWITCH, "gimple_omp_sections_switch", GSS_BASE)
/* GIMPLE_OMP_SINGLE <BODY, CLAUSES> represents #pragma omp single
BODY is the sequence of statements inside the single section.
CLAUSES is a TREE_LIST node holding the associated clauses. */
DEFGSCODE(GIMPLE_OMP_SINGLE, "gimple_omp_single", GSS_OMP_SINGLE)
/* GIMPLE_PREDICT <PREDICT, OUTCOME> specifies a hint for branch prediction.
PREDICT is one of the predictors from predict.def.
OUTCOME is NOT_TAKEN or TAKEN. */
DEFGSCODE(GIMPLE_PREDICT, "gimple_predict", GSS_BASE)
/* This node represents a cleanup expression. It is ONLY USED INTERNALLY
by the gimplifier as a placeholder for cleanups, and its uses will be
cleaned up by the time gimplification is done.
This tuple should not exist outside of the gimplifier proper. */
DEFGSCODE(GIMPLE_WITH_CLEANUP_EXPR, "gimple_with_cleanup_expr", GSS_WCE)

5350
src/include/gimple.h Normal file

File diff suppressed because it is too large Load Diff

53
src/include/gsstruct.def Normal file
View File

@ -0,0 +1,53 @@
/* This file contains the definitions for the gimple IR structure
enumeration used in GCC.
Copyright (C) 2007-2013 Free Software Foundation, Inc.
Contributed by Aldy Hernandez <aldyh@redhat.com>
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
/* The format of this file is
DEFGSSTRUCT(GSS enumeration value, structure name, has-tree-operands).
Each enum value should correspond with a single member of the union
gimple_statement_d. */
DEFGSSTRUCT(GSS_BASE, gimple_statement_base, false)
DEFGSSTRUCT(GSS_WITH_OPS, gimple_statement_with_ops, true)
DEFGSSTRUCT(GSS_WITH_MEM_OPS_BASE, gimple_statement_with_memory_ops_base, false)
DEFGSSTRUCT(GSS_WITH_MEM_OPS, gimple_statement_with_memory_ops, true)
DEFGSSTRUCT(GSS_CALL, gimple_statement_call, true)
DEFGSSTRUCT(GSS_ASM, gimple_statement_asm, true)
DEFGSSTRUCT(GSS_BIND, gimple_statement_bind, false)
DEFGSSTRUCT(GSS_PHI, gimple_statement_phi, false)
DEFGSSTRUCT(GSS_TRY, gimple_statement_try, false)
DEFGSSTRUCT(GSS_CATCH, gimple_statement_catch, false)
DEFGSSTRUCT(GSS_EH_FILTER, gimple_statement_eh_filter, false)
DEFGSSTRUCT(GSS_EH_MNT, gimple_statement_eh_mnt, false)
DEFGSSTRUCT(GSS_EH_CTRL, gimple_statement_eh_ctrl, false)
DEFGSSTRUCT(GSS_EH_ELSE, gimple_statement_eh_else, false)
DEFGSSTRUCT(GSS_WCE, gimple_statement_wce, false)
DEFGSSTRUCT(GSS_OMP, gimple_statement_omp, false)
DEFGSSTRUCT(GSS_OMP_CRITICAL, gimple_statement_omp_critical, false)
DEFGSSTRUCT(GSS_OMP_FOR, gimple_statement_omp_for, false)
DEFGSSTRUCT(GSS_OMP_PARALLEL, gimple_statement_omp_parallel, false)
DEFGSSTRUCT(GSS_OMP_TASK, gimple_statement_omp_task, false)
DEFGSSTRUCT(GSS_OMP_SECTIONS, gimple_statement_omp_sections, false)
DEFGSSTRUCT(GSS_OMP_SINGLE, gimple_statement_omp_single, false)
DEFGSSTRUCT(GSS_OMP_CONTINUE, gimple_statement_omp_continue, false)
DEFGSSTRUCT(GSS_OMP_ATOMIC_LOAD, gimple_statement_omp_atomic_load, false)
DEFGSSTRUCT(GSS_OMP_ATOMIC_STORE, gimple_statement_omp_atomic_store, false)
DEFGSSTRUCT(GSS_TRANSACTION, gimple_statement_transaction, false)

View File

@ -0,0 +1,208 @@
DEF_TM_BUILTIN (BUILT_IN_TM_START, "_ITM_beginTransaction",
BT_FN_UINT32_UINT32_VAR, ATTR_TM_NOTHROW_RT_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_COMMIT, "_ITM_commitTransaction",
BT_FN_VOID, ATTR_TM_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_COMMIT_EH, "_ITM_commitTransactionEH",
BT_FN_VOID_PTR, ATTR_TM_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_ABORT, "_ITM_abortTransaction",
BT_FN_VOID_INT, ATTR_TM_NORETURN_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_IRREVOCABLE, "_ITM_changeTransactionMode",
BT_FN_VOID_INT, ATTR_TM_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_MEMCPY, "_ITM_memcpyRtWt",
BT_FN_VOID_PTR_CONST_PTR_SIZE, ATTR_TM_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_MEMMOVE, "_ITM_memmoveRtWt",
BT_FN_VOID_PTR_CONST_PTR_SIZE, ATTR_TM_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_MEMSET, "_ITM_memsetW",
BT_FN_VOID_PTR_INT_SIZE, ATTR_TM_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_GETTMCLONE_IRR, "_ITM_getTMCloneOrIrrevocable",
BT_FN_PTR_PTR, ATTR_TM_CONST_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_GETTMCLONE_SAFE, "_ITM_getTMCloneSafe",
BT_FN_PTR_PTR, ATTR_TM_CONST_NOTHROW_LIST)
/* Memory allocation builtins. */
DEF_TM_BUILTIN (BUILT_IN_TM_MALLOC, "_ITM_malloc",
BT_FN_PTR_SIZE, ATTR_TMPURE_MALLOC_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_CALLOC, "_ITM_calloc",
BT_FN_PTR_SIZE_SIZE, ATTR_TMPURE_MALLOC_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_FREE, "_ITM_free",
BT_FN_VOID_PTR, ATTR_TMPURE_NOTHROW_LIST)
/* Logging builtins. */
DEF_TM_BUILTIN (BUILT_IN_TM_LOG_1, "_ITM_LU1",
BT_FN_VOID_VPTR, ATTR_TM_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOG_2, "_ITM_LU2",
BT_FN_VOID_VPTR, ATTR_TM_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOG_4, "_ITM_LU4",
BT_FN_VOID_VPTR, ATTR_TM_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOG_8, "_ITM_LU8",
BT_FN_VOID_VPTR, ATTR_TM_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOG_FLOAT, "_ITM_LF",
BT_FN_VOID_VPTR, ATTR_TM_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOG_DOUBLE, "_ITM_LD",
BT_FN_VOID_VPTR, ATTR_TM_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOG_LDOUBLE, "_ITM_LE",
BT_FN_VOID_VPTR, ATTR_TM_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOG, "_ITM_LB",
BT_FN_VOID_VPTR_SIZE, ATTR_TM_TMPURE_NOTHROW_LIST)
/* These stubs should get defined in the backend if applicable. */
DEF_BUILTIN_STUB (BUILT_IN_TM_LOG_M64, "__builtin__ITM_LM64")
DEF_BUILTIN_STUB (BUILT_IN_TM_LOG_M128, "__builtin__ITM_LM128")
DEF_BUILTIN_STUB (BUILT_IN_TM_LOG_M256, "__builtin__ITM_LM256")
/* Writes.
Note: The writes must follow the following order: STORE, WAR, WAW.
The TM optimizations depend on this order.
BUILT_IN_TM_STORE_1 must be the first builtin.
BUILTIN_TM_LOAD_STORE_P depends on this. */
DEF_TM_BUILTIN (BUILT_IN_TM_STORE_1, "_ITM_WU1",
BT_FN_VOID_VPTR_I1, ATTR_TM_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_STORE_WAR_1, "_ITM_WaRU1",
BT_FN_VOID_VPTR_I1, ATTR_TM_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_STORE_WAW_1, "_ITM_WaWU1",
BT_FN_VOID_VPTR_I1, ATTR_TM_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_STORE_2, "_ITM_WU2",
BT_FN_VOID_VPTR_I2, ATTR_TM_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_STORE_WAR_2, "_ITM_WaRU2",
BT_FN_VOID_VPTR_I2, ATTR_TM_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_STORE_WAW_2, "_ITM_WaWU2",
BT_FN_VOID_VPTR_I2, ATTR_TM_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_STORE_4, "_ITM_WU4",
BT_FN_VOID_VPTR_I4, ATTR_TM_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_STORE_WAR_4, "_ITM_WaRU4",
BT_FN_VOID_VPTR_I4, ATTR_TM_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_STORE_WAW_4, "_ITM_WaWU4",
BT_FN_VOID_VPTR_I4, ATTR_TM_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_STORE_8, "_ITM_WU8",
BT_FN_VOID_VPTR_I8, ATTR_TM_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_STORE_WAR_8, "_ITM_WaRU8",
BT_FN_VOID_VPTR_I8, ATTR_TM_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_STORE_WAW_8, "_ITM_WaWU8",
BT_FN_VOID_VPTR_I8, ATTR_TM_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_STORE_FLOAT, "_ITM_WF",
BT_FN_VOID_VPTR_FLOAT, ATTR_TM_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_STORE_WAR_FLOAT, "_ITM_WaRF",
BT_FN_VOID_VPTR_FLOAT, ATTR_TM_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_STORE_WAW_FLOAT, "_ITM_WaWF",
BT_FN_VOID_VPTR_FLOAT, ATTR_TM_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_STORE_DOUBLE, "_ITM_WD",
BT_FN_VOID_VPTR_DOUBLE, ATTR_TM_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_STORE_WAR_DOUBLE, "_ITM_WaRD",
BT_FN_VOID_VPTR_DOUBLE, ATTR_TM_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_STORE_WAW_DOUBLE, "_ITM_WaWD",
BT_FN_VOID_VPTR_DOUBLE, ATTR_TM_NOTHROW_LIST)
/* These stubs should get defined in the backend if applicable. */
DEF_BUILTIN_STUB (BUILT_IN_TM_STORE_M64, "__builtin__ITM_WM64")
DEF_BUILTIN_STUB (BUILT_IN_TM_STORE_WAR_M64, "__builtin__ITM_WaRM64")
DEF_BUILTIN_STUB (BUILT_IN_TM_STORE_WAW_M64, "__builtin__ITM_WaWM64")
DEF_BUILTIN_STUB (BUILT_IN_TM_STORE_M128, "__builtin__ITM_WM128")
DEF_BUILTIN_STUB (BUILT_IN_TM_STORE_WAR_M128, "__builtin__ITM_WaRM128")
DEF_BUILTIN_STUB (BUILT_IN_TM_STORE_WAW_M128, "__builtin__ITM_WaWM128")
DEF_BUILTIN_STUB (BUILT_IN_TM_STORE_M256, "__builtin__ITM_WM256")
DEF_BUILTIN_STUB (BUILT_IN_TM_STORE_WAR_M256, "__builtin__ITM_WaRM256")
DEF_BUILTIN_STUB (BUILT_IN_TM_STORE_WAW_M256, "__builtin__ITM_WaWM256")
DEF_TM_BUILTIN (BUILT_IN_TM_STORE_LDOUBLE, "_ITM_WE",
BT_FN_VOID_VPTR_LDOUBLE, ATTR_TM_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_STORE_WAR_LDOUBLE, "_ITM_WaRE",
BT_FN_VOID_VPTR_LDOUBLE, ATTR_TM_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_STORE_WAW_LDOUBLE, "_ITM_WaWE",
BT_FN_VOID_VPTR_LDOUBLE, ATTR_TM_NOTHROW_LIST)
/* Note: BUILT_IN_TM_STORE_WAW_LDOUBLE must be the last TM store.
BUILTIN_TM_STORE_P depends on this. */
/* Reads.
Note: The reads must follow the following order: LOAD, RAR, RAW, RFW.
The TM optimizations depend on this order. */
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_1, "_ITM_RU1",
BT_FN_I1_VPTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_RAR_1, "_ITM_RaRU1",
BT_FN_I1_VPTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_RAW_1, "_ITM_RaWU1",
BT_FN_I1_VPTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_RFW_1, "_ITM_RfWU1",
BT_FN_I1_VPTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_2, "_ITM_RU2",
BT_FN_I2_VPTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_RAR_2, "_ITM_RaRU2",
BT_FN_I2_VPTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_RAW_2, "_ITM_RaWU2",
BT_FN_I2_VPTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_RFW_2, "_ITM_RfWU2",
BT_FN_I2_VPTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_4, "_ITM_RU4",
BT_FN_I4_VPTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_RAR_4, "_ITM_RaRU4",
BT_FN_I4_VPTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_RAW_4, "_ITM_RaWU4",
BT_FN_I4_VPTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_RFW_4, "_ITM_RfWU4",
BT_FN_I4_VPTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_8, "_ITM_RU8",
BT_FN_I8_VPTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_RAR_8, "_ITM_RaRU8",
BT_FN_I8_VPTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_RAW_8, "_ITM_RaWU8",
BT_FN_I8_VPTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_RFW_8, "_ITM_RfWU8",
BT_FN_I8_VPTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_FLOAT, "_ITM_RF",
BT_FN_FLOAT_VPTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_RAR_FLOAT, "_ITM_RaRF",
BT_FN_FLOAT_VPTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_RAW_FLOAT, "_ITM_RaWF",
BT_FN_FLOAT_VPTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_RFW_FLOAT, "_ITM_RfWF",
BT_FN_FLOAT_VPTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_DOUBLE, "_ITM_RD",
BT_FN_DOUBLE_CONST_DOUBLE_PTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_RAR_DOUBLE, "_ITM_RaRD",
BT_FN_DOUBLE_CONST_DOUBLE_PTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_RAW_DOUBLE, "_ITM_RaWD",
BT_FN_DOUBLE_CONST_DOUBLE_PTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_RFW_DOUBLE, "_ITM_RfWD",
BT_FN_DOUBLE_CONST_DOUBLE_PTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
/* These stubs should get defined in the backend if applicable. */
DEF_BUILTIN_STUB (BUILT_IN_TM_LOAD_M64, "__builtin__ITM_RM64")
DEF_BUILTIN_STUB (BUILT_IN_TM_LOAD_RAR_M64, "__builtin__ITM_RaRM64")
DEF_BUILTIN_STUB (BUILT_IN_TM_LOAD_RAW_M64, "__builtin__ITM_RaRM64")
DEF_BUILTIN_STUB (BUILT_IN_TM_LOAD_RFW_M64, "__builtin__ITM_RfWM64")
DEF_BUILTIN_STUB (BUILT_IN_TM_LOAD_M128, "__builtin__ITM_RM128")
DEF_BUILTIN_STUB (BUILT_IN_TM_LOAD_RAR_M128, "__builtin__ITM_RaRM128")
DEF_BUILTIN_STUB (BUILT_IN_TM_LOAD_RAW_M128, "__builtin__ITM_RaRM128")
DEF_BUILTIN_STUB (BUILT_IN_TM_LOAD_RFW_M128, "__builtin__ITM_RfWM128")
DEF_BUILTIN_STUB (BUILT_IN_TM_LOAD_M256, "__builtin__ITM_RM256")
DEF_BUILTIN_STUB (BUILT_IN_TM_LOAD_RAR_M256, "__builtin__ITM_RaRM256")
DEF_BUILTIN_STUB (BUILT_IN_TM_LOAD_RAW_M256, "__builtin__ITM_RaRM256")
DEF_BUILTIN_STUB (BUILT_IN_TM_LOAD_RFW_M256, "__builtin__ITM_RfWM256")
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_LDOUBLE, "_ITM_RE",
BT_FN_LDOUBLE_VPTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_RAR_LDOUBLE, "_ITM_RaRE",
BT_FN_LDOUBLE_VPTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_RAW_LDOUBLE, "_ITM_RaWE",
BT_FN_LDOUBLE_VPTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
DEF_TM_BUILTIN (BUILT_IN_TM_LOAD_RFW_LDOUBLE, "_ITM_RfWE",
BT_FN_LDOUBLE_VPTR, ATTR_TM_PURE_TMPURE_NOTHROW_LIST)
/* Note: BUILT_IN_TM_LOAD_RFW_LDOUBLE must be the last TM load as well
as the last builtin. BUILTIN_TM_LOAD_STORE_P and BUILTIN_TM_LOAD_P
depend on this. */

5079
src/include/gtype-desc.h Normal file

File diff suppressed because it is too large Load Diff

724
src/include/hard-reg-set.h Normal file
View File

@ -0,0 +1,724 @@
/* Sets (bit vectors) of hard registers, and operations on them.
Copyright (C) 1987-2013 Free Software Foundation, Inc.
This file is part of GCC
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GCC_HARD_REG_SET_H
#define GCC_HARD_REG_SET_H
/* Define the type of a set of hard registers. */
/* HARD_REG_ELT_TYPE is a typedef of the unsigned integral type which
will be used for hard reg sets, either alone or in an array.
If HARD_REG_SET is a macro, its definition is HARD_REG_ELT_TYPE,
and it has enough bits to represent all the target machine's hard
registers. Otherwise, it is a typedef for a suitably sized array
of HARD_REG_ELT_TYPEs. HARD_REG_SET_LONGS is defined as how many.
Note that lots of code assumes that the first part of a regset is
the same format as a HARD_REG_SET. To help make sure this is true,
we only try the widest fast integer mode (HOST_WIDEST_FAST_INT)
instead of all the smaller types. This approach loses only if
there are very few registers and then only in the few cases where
we have an array of HARD_REG_SETs, so it needn't be as complex as
it used to be. */
typedef unsigned HOST_WIDEST_FAST_INT HARD_REG_ELT_TYPE;
#if FIRST_PSEUDO_REGISTER <= HOST_BITS_PER_WIDEST_FAST_INT
#define HARD_REG_SET HARD_REG_ELT_TYPE
#else
#define HARD_REG_SET_LONGS \
((FIRST_PSEUDO_REGISTER + HOST_BITS_PER_WIDEST_FAST_INT - 1) \
/ HOST_BITS_PER_WIDEST_FAST_INT)
typedef HARD_REG_ELT_TYPE HARD_REG_SET[HARD_REG_SET_LONGS];
#endif
/* HARD_REG_SET wrapped into a structure, to make it possible to
use HARD_REG_SET even in APIs that should not include
hard-reg-set.h. */
struct hard_reg_set_container
{
HARD_REG_SET set;
};
/* HARD_CONST is used to cast a constant to the appropriate type
for use with a HARD_REG_SET. */
#define HARD_CONST(X) ((HARD_REG_ELT_TYPE) (X))
/* Define macros SET_HARD_REG_BIT, CLEAR_HARD_REG_BIT and TEST_HARD_REG_BIT
to set, clear or test one bit in a hard reg set of type HARD_REG_SET.
All three take two arguments: the set and the register number.
In the case where sets are arrays of longs, the first argument
is actually a pointer to a long.
Define two macros for initializing a set:
CLEAR_HARD_REG_SET and SET_HARD_REG_SET.
These take just one argument.
Also define macros for copying hard reg sets:
COPY_HARD_REG_SET and COMPL_HARD_REG_SET.
These take two arguments TO and FROM; they read from FROM
and store into TO. COMPL_HARD_REG_SET complements each bit.
Also define macros for combining hard reg sets:
IOR_HARD_REG_SET and AND_HARD_REG_SET.
These take two arguments TO and FROM; they read from FROM
and combine bitwise into TO. Define also two variants
IOR_COMPL_HARD_REG_SET and AND_COMPL_HARD_REG_SET
which use the complement of the set FROM.
Also define:
hard_reg_set_subset_p (X, Y), which returns true if X is a subset of Y.
hard_reg_set_equal_p (X, Y), which returns true if X and Y are equal.
hard_reg_set_intersect_p (X, Y), which returns true if X and Y intersect.
hard_reg_set_empty_p (X), which returns true if X is empty. */
#define UHOST_BITS_PER_WIDE_INT ((unsigned) HOST_BITS_PER_WIDEST_FAST_INT)
#ifdef HARD_REG_SET
#define SET_HARD_REG_BIT(SET, BIT) \
((SET) |= HARD_CONST (1) << (BIT))
#define CLEAR_HARD_REG_BIT(SET, BIT) \
((SET) &= ~(HARD_CONST (1) << (BIT)))
#define TEST_HARD_REG_BIT(SET, BIT) \
(!!((SET) & (HARD_CONST (1) << (BIT))))
#define CLEAR_HARD_REG_SET(TO) ((TO) = HARD_CONST (0))
#define SET_HARD_REG_SET(TO) ((TO) = ~ HARD_CONST (0))
#define COPY_HARD_REG_SET(TO, FROM) ((TO) = (FROM))
#define COMPL_HARD_REG_SET(TO, FROM) ((TO) = ~(FROM))
#define IOR_HARD_REG_SET(TO, FROM) ((TO) |= (FROM))
#define IOR_COMPL_HARD_REG_SET(TO, FROM) ((TO) |= ~ (FROM))
#define AND_HARD_REG_SET(TO, FROM) ((TO) &= (FROM))
#define AND_COMPL_HARD_REG_SET(TO, FROM) ((TO) &= ~ (FROM))
static inline bool
hard_reg_set_subset_p (const HARD_REG_SET x, const HARD_REG_SET y)
{
return (x & ~y) == HARD_CONST (0);
}
static inline bool
hard_reg_set_equal_p (const HARD_REG_SET x, const HARD_REG_SET y)
{
return x == y;
}
static inline bool
hard_reg_set_intersect_p (const HARD_REG_SET x, const HARD_REG_SET y)
{
return (x & y) != HARD_CONST (0);
}
static inline bool
hard_reg_set_empty_p (const HARD_REG_SET x)
{
return x == HARD_CONST (0);
}
#else
#define SET_HARD_REG_BIT(SET, BIT) \
((SET)[(BIT) / UHOST_BITS_PER_WIDE_INT] \
|= HARD_CONST (1) << ((BIT) % UHOST_BITS_PER_WIDE_INT))
#define CLEAR_HARD_REG_BIT(SET, BIT) \
((SET)[(BIT) / UHOST_BITS_PER_WIDE_INT] \
&= ~(HARD_CONST (1) << ((BIT) % UHOST_BITS_PER_WIDE_INT)))
#define TEST_HARD_REG_BIT(SET, BIT) \
(!!((SET)[(BIT) / UHOST_BITS_PER_WIDE_INT] \
& (HARD_CONST (1) << ((BIT) % UHOST_BITS_PER_WIDE_INT))))
#if FIRST_PSEUDO_REGISTER <= 2*HOST_BITS_PER_WIDEST_FAST_INT
#define CLEAR_HARD_REG_SET(TO) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO); \
scan_tp_[0] = 0; \
scan_tp_[1] = 0; } while (0)
#define SET_HARD_REG_SET(TO) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO); \
scan_tp_[0] = -1; \
scan_tp_[1] = -1; } while (0)
#define COPY_HARD_REG_SET(TO, FROM) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO), *scan_fp_ = (FROM); \
scan_tp_[0] = scan_fp_[0]; \
scan_tp_[1] = scan_fp_[1]; } while (0)
#define COMPL_HARD_REG_SET(TO, FROM) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO), *scan_fp_ = (FROM); \
scan_tp_[0] = ~ scan_fp_[0]; \
scan_tp_[1] = ~ scan_fp_[1]; } while (0)
#define AND_HARD_REG_SET(TO, FROM) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO), *scan_fp_ = (FROM); \
scan_tp_[0] &= scan_fp_[0]; \
scan_tp_[1] &= scan_fp_[1]; } while (0)
#define AND_COMPL_HARD_REG_SET(TO, FROM) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO), *scan_fp_ = (FROM); \
scan_tp_[0] &= ~ scan_fp_[0]; \
scan_tp_[1] &= ~ scan_fp_[1]; } while (0)
#define IOR_HARD_REG_SET(TO, FROM) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO), *scan_fp_ = (FROM); \
scan_tp_[0] |= scan_fp_[0]; \
scan_tp_[1] |= scan_fp_[1]; } while (0)
#define IOR_COMPL_HARD_REG_SET(TO, FROM) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO), *scan_fp_ = (FROM); \
scan_tp_[0] |= ~ scan_fp_[0]; \
scan_tp_[1] |= ~ scan_fp_[1]; } while (0)
static inline bool
hard_reg_set_subset_p (const HARD_REG_SET x, const HARD_REG_SET y)
{
return (x[0] & ~y[0]) == 0 && (x[1] & ~y[1]) == 0;
}
static inline bool
hard_reg_set_equal_p (const HARD_REG_SET x, const HARD_REG_SET y)
{
return x[0] == y[0] && x[1] == y[1];
}
static inline bool
hard_reg_set_intersect_p (const HARD_REG_SET x, const HARD_REG_SET y)
{
return (x[0] & y[0]) != 0 || (x[1] & y[1]) != 0;
}
static inline bool
hard_reg_set_empty_p (const HARD_REG_SET x)
{
return x[0] == 0 && x[1] == 0;
}
#else
#if FIRST_PSEUDO_REGISTER <= 3*HOST_BITS_PER_WIDEST_FAST_INT
#define CLEAR_HARD_REG_SET(TO) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO); \
scan_tp_[0] = 0; \
scan_tp_[1] = 0; \
scan_tp_[2] = 0; } while (0)
#define SET_HARD_REG_SET(TO) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO); \
scan_tp_[0] = -1; \
scan_tp_[1] = -1; \
scan_tp_[2] = -1; } while (0)
#define COPY_HARD_REG_SET(TO, FROM) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO), *scan_fp_ = (FROM); \
scan_tp_[0] = scan_fp_[0]; \
scan_tp_[1] = scan_fp_[1]; \
scan_tp_[2] = scan_fp_[2]; } while (0)
#define COMPL_HARD_REG_SET(TO, FROM) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO), *scan_fp_ = (FROM); \
scan_tp_[0] = ~ scan_fp_[0]; \
scan_tp_[1] = ~ scan_fp_[1]; \
scan_tp_[2] = ~ scan_fp_[2]; } while (0)
#define AND_HARD_REG_SET(TO, FROM) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO), *scan_fp_ = (FROM); \
scan_tp_[0] &= scan_fp_[0]; \
scan_tp_[1] &= scan_fp_[1]; \
scan_tp_[2] &= scan_fp_[2]; } while (0)
#define AND_COMPL_HARD_REG_SET(TO, FROM) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO), *scan_fp_ = (FROM); \
scan_tp_[0] &= ~ scan_fp_[0]; \
scan_tp_[1] &= ~ scan_fp_[1]; \
scan_tp_[2] &= ~ scan_fp_[2]; } while (0)
#define IOR_HARD_REG_SET(TO, FROM) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO), *scan_fp_ = (FROM); \
scan_tp_[0] |= scan_fp_[0]; \
scan_tp_[1] |= scan_fp_[1]; \
scan_tp_[2] |= scan_fp_[2]; } while (0)
#define IOR_COMPL_HARD_REG_SET(TO, FROM) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO), *scan_fp_ = (FROM); \
scan_tp_[0] |= ~ scan_fp_[0]; \
scan_tp_[1] |= ~ scan_fp_[1]; \
scan_tp_[2] |= ~ scan_fp_[2]; } while (0)
static inline bool
hard_reg_set_subset_p (const HARD_REG_SET x, const HARD_REG_SET y)
{
return ((x[0] & ~y[0]) == 0
&& (x[1] & ~y[1]) == 0
&& (x[2] & ~y[2]) == 0);
}
static inline bool
hard_reg_set_equal_p (const HARD_REG_SET x, const HARD_REG_SET y)
{
return x[0] == y[0] && x[1] == y[1] && x[2] == y[2];
}
static inline bool
hard_reg_set_intersect_p (const HARD_REG_SET x, const HARD_REG_SET y)
{
return ((x[0] & y[0]) != 0
|| (x[1] & y[1]) != 0
|| (x[2] & y[2]) != 0);
}
static inline bool
hard_reg_set_empty_p (const HARD_REG_SET x)
{
return x[0] == 0 && x[1] == 0 && x[2] == 0;
}
#else
#if FIRST_PSEUDO_REGISTER <= 4*HOST_BITS_PER_WIDEST_FAST_INT
#define CLEAR_HARD_REG_SET(TO) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO); \
scan_tp_[0] = 0; \
scan_tp_[1] = 0; \
scan_tp_[2] = 0; \
scan_tp_[3] = 0; } while (0)
#define SET_HARD_REG_SET(TO) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO); \
scan_tp_[0] = -1; \
scan_tp_[1] = -1; \
scan_tp_[2] = -1; \
scan_tp_[3] = -1; } while (0)
#define COPY_HARD_REG_SET(TO, FROM) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO), *scan_fp_ = (FROM); \
scan_tp_[0] = scan_fp_[0]; \
scan_tp_[1] = scan_fp_[1]; \
scan_tp_[2] = scan_fp_[2]; \
scan_tp_[3] = scan_fp_[3]; } while (0)
#define COMPL_HARD_REG_SET(TO, FROM) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO), *scan_fp_ = (FROM); \
scan_tp_[0] = ~ scan_fp_[0]; \
scan_tp_[1] = ~ scan_fp_[1]; \
scan_tp_[2] = ~ scan_fp_[2]; \
scan_tp_[3] = ~ scan_fp_[3]; } while (0)
#define AND_HARD_REG_SET(TO, FROM) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO), *scan_fp_ = (FROM); \
scan_tp_[0] &= scan_fp_[0]; \
scan_tp_[1] &= scan_fp_[1]; \
scan_tp_[2] &= scan_fp_[2]; \
scan_tp_[3] &= scan_fp_[3]; } while (0)
#define AND_COMPL_HARD_REG_SET(TO, FROM) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO), *scan_fp_ = (FROM); \
scan_tp_[0] &= ~ scan_fp_[0]; \
scan_tp_[1] &= ~ scan_fp_[1]; \
scan_tp_[2] &= ~ scan_fp_[2]; \
scan_tp_[3] &= ~ scan_fp_[3]; } while (0)
#define IOR_HARD_REG_SET(TO, FROM) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO), *scan_fp_ = (FROM); \
scan_tp_[0] |= scan_fp_[0]; \
scan_tp_[1] |= scan_fp_[1]; \
scan_tp_[2] |= scan_fp_[2]; \
scan_tp_[3] |= scan_fp_[3]; } while (0)
#define IOR_COMPL_HARD_REG_SET(TO, FROM) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO), *scan_fp_ = (FROM); \
scan_tp_[0] |= ~ scan_fp_[0]; \
scan_tp_[1] |= ~ scan_fp_[1]; \
scan_tp_[2] |= ~ scan_fp_[2]; \
scan_tp_[3] |= ~ scan_fp_[3]; } while (0)
static inline bool
hard_reg_set_subset_p (const HARD_REG_SET x, const HARD_REG_SET y)
{
return ((x[0] & ~y[0]) == 0
&& (x[1] & ~y[1]) == 0
&& (x[2] & ~y[2]) == 0
&& (x[3] & ~y[3]) == 0);
}
static inline bool
hard_reg_set_equal_p (const HARD_REG_SET x, const HARD_REG_SET y)
{
return x[0] == y[0] && x[1] == y[1] && x[2] == y[2] && x[3] == y[3];
}
static inline bool
hard_reg_set_intersect_p (const HARD_REG_SET x, const HARD_REG_SET y)
{
return ((x[0] & y[0]) != 0
|| (x[1] & y[1]) != 0
|| (x[2] & y[2]) != 0
|| (x[3] & y[3]) != 0);
}
static inline bool
hard_reg_set_empty_p (const HARD_REG_SET x)
{
return x[0] == 0 && x[1] == 0 && x[2] == 0 && x[3] == 0;
}
#else /* FIRST_PSEUDO_REGISTER > 4*HOST_BITS_PER_WIDEST_FAST_INT */
#define CLEAR_HARD_REG_SET(TO) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO); \
int i; \
for (i = 0; i < HARD_REG_SET_LONGS; i++) \
*scan_tp_++ = 0; } while (0)
#define SET_HARD_REG_SET(TO) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO); \
int i; \
for (i = 0; i < HARD_REG_SET_LONGS; i++) \
*scan_tp_++ = -1; } while (0)
#define COPY_HARD_REG_SET(TO, FROM) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO), *scan_fp_ = (FROM); \
int i; \
for (i = 0; i < HARD_REG_SET_LONGS; i++) \
*scan_tp_++ = *scan_fp_++; } while (0)
#define COMPL_HARD_REG_SET(TO, FROM) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO), *scan_fp_ = (FROM); \
int i; \
for (i = 0; i < HARD_REG_SET_LONGS; i++) \
*scan_tp_++ = ~ *scan_fp_++; } while (0)
#define AND_HARD_REG_SET(TO, FROM) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO), *scan_fp_ = (FROM); \
int i; \
for (i = 0; i < HARD_REG_SET_LONGS; i++) \
*scan_tp_++ &= *scan_fp_++; } while (0)
#define AND_COMPL_HARD_REG_SET(TO, FROM) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO), *scan_fp_ = (FROM); \
int i; \
for (i = 0; i < HARD_REG_SET_LONGS; i++) \
*scan_tp_++ &= ~ *scan_fp_++; } while (0)
#define IOR_HARD_REG_SET(TO, FROM) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO), *scan_fp_ = (FROM); \
int i; \
for (i = 0; i < HARD_REG_SET_LONGS; i++) \
*scan_tp_++ |= *scan_fp_++; } while (0)
#define IOR_COMPL_HARD_REG_SET(TO, FROM) \
do { HARD_REG_ELT_TYPE *scan_tp_ = (TO), *scan_fp_ = (FROM); \
int i; \
for (i = 0; i < HARD_REG_SET_LONGS; i++) \
*scan_tp_++ |= ~ *scan_fp_++; } while (0)
static inline bool
hard_reg_set_subset_p (const HARD_REG_SET x, const HARD_REG_SET y)
{
int i;
for (i = 0; i < HARD_REG_SET_LONGS; i++)
if ((x[i] & ~y[i]) != 0)
return false;
return true;
}
static inline bool
hard_reg_set_equal_p (const HARD_REG_SET x, const HARD_REG_SET y)
{
int i;
for (i = 0; i < HARD_REG_SET_LONGS; i++)
if (x[i] != y[i])
return false;
return true;
}
static inline bool
hard_reg_set_intersect_p (const HARD_REG_SET x, const HARD_REG_SET y)
{
int i;
for (i = 0; i < HARD_REG_SET_LONGS; i++)
if ((x[i] & y[i]) != 0)
return true;
return false;
}
static inline bool
hard_reg_set_empty_p (const HARD_REG_SET x)
{
int i;
for (i = 0; i < HARD_REG_SET_LONGS; i++)
if (x[i] != 0)
return false;
return true;
}
#endif
#endif
#endif
#endif
/* Iterator for hard register sets. */
typedef struct
{
/* Pointer to the current element. */
HARD_REG_ELT_TYPE *pelt;
/* The length of the set. */
unsigned short length;
/* Word within the current element. */
unsigned short word_no;
/* Contents of the actually processed word. When finding next bit
it is shifted right, so that the actual bit is always the least
significant bit of ACTUAL. */
HARD_REG_ELT_TYPE bits;
} hard_reg_set_iterator;
#define HARD_REG_ELT_BITS UHOST_BITS_PER_WIDE_INT
/* The implementation of the iterator functions is fully analogous to
the bitmap iterators. */
static inline void
hard_reg_set_iter_init (hard_reg_set_iterator *iter, HARD_REG_SET set,
unsigned min, unsigned *regno)
{
#ifdef HARD_REG_SET_LONGS
iter->pelt = set;
iter->length = HARD_REG_SET_LONGS;
#else
iter->pelt = &set;
iter->length = 1;
#endif
iter->word_no = min / HARD_REG_ELT_BITS;
if (iter->word_no < iter->length)
{
iter->bits = iter->pelt[iter->word_no];
iter->bits >>= min % HARD_REG_ELT_BITS;
/* This is required for correct search of the next bit. */
min += !iter->bits;
}
*regno = min;
}
static inline bool
hard_reg_set_iter_set (hard_reg_set_iterator *iter, unsigned *regno)
{
while (1)
{
/* Return false when we're advanced past the end of the set. */
if (iter->word_no >= iter->length)
return false;
if (iter->bits)
{
/* Find the correct bit and return it. */
while (!(iter->bits & 1))
{
iter->bits >>= 1;
*regno += 1;
}
return (*regno < FIRST_PSEUDO_REGISTER);
}
/* Round to the beginning of the next word. */
*regno = (*regno + HARD_REG_ELT_BITS - 1);
*regno -= *regno % HARD_REG_ELT_BITS;
/* Find the next non-zero word. */
while (++iter->word_no < iter->length)
{
iter->bits = iter->pelt[iter->word_no];
if (iter->bits)
break;
*regno += HARD_REG_ELT_BITS;
}
}
}
static inline void
hard_reg_set_iter_next (hard_reg_set_iterator *iter, unsigned *regno)
{
iter->bits >>= 1;
*regno += 1;
}
#define EXECUTE_IF_SET_IN_HARD_REG_SET(SET, MIN, REGNUM, ITER) \
for (hard_reg_set_iter_init (&(ITER), (SET), (MIN), &(REGNUM)); \
hard_reg_set_iter_set (&(ITER), &(REGNUM)); \
hard_reg_set_iter_next (&(ITER), &(REGNUM)))
/* Define some standard sets of registers. */
/* Indexed by hard register number, contains 1 for registers
that are being used for global register decls.
These must be exempt from ordinary flow analysis
and are also considered fixed. */
extern char global_regs[FIRST_PSEUDO_REGISTER];
struct target_hard_regs {
/* The set of registers that actually exist on the current target. */
HARD_REG_SET x_accessible_reg_set;
/* The set of registers that should be considered to be register
operands. It is a subset of x_accessible_reg_set. */
HARD_REG_SET x_operand_reg_set;
/* Indexed by hard register number, contains 1 for registers
that are fixed use (stack pointer, pc, frame pointer, etc.;.
These are the registers that cannot be used to allocate
a pseudo reg whose life does not cross calls. */
char x_fixed_regs[FIRST_PSEUDO_REGISTER];
/* The same info as a HARD_REG_SET. */
HARD_REG_SET x_fixed_reg_set;
/* Indexed by hard register number, contains 1 for registers
that are fixed use or are clobbered by function calls.
These are the registers that cannot be used to allocate
a pseudo reg whose life crosses calls. */
char x_call_used_regs[FIRST_PSEUDO_REGISTER];
char x_call_really_used_regs[FIRST_PSEUDO_REGISTER];
/* The same info as a HARD_REG_SET. */
HARD_REG_SET x_call_used_reg_set;
/* Contains registers that are fixed use -- i.e. in fixed_reg_set -- or
a function value return register or TARGET_STRUCT_VALUE_RTX or
STATIC_CHAIN_REGNUM. These are the registers that cannot hold quantities
across calls even if we are willing to save and restore them. */
HARD_REG_SET x_call_fixed_reg_set;
/* Contains 1 for registers that are set or clobbered by calls. */
/* ??? Ideally, this would be just call_used_regs plus global_regs, but
for someone's bright idea to have call_used_regs strictly include
fixed_regs. Which leaves us guessing as to the set of fixed_regs
that are actually preserved. We know for sure that those associated
with the local stack frame are safe, but scant others. */
HARD_REG_SET x_regs_invalidated_by_call;
/* Call used hard registers which can not be saved because there is no
insn for this. */
HARD_REG_SET x_no_caller_save_reg_set;
/* Table of register numbers in the order in which to try to use them. */
int x_reg_alloc_order[FIRST_PSEUDO_REGISTER];
/* The inverse of reg_alloc_order. */
int x_inv_reg_alloc_order[FIRST_PSEUDO_REGISTER];
/* For each reg class, a HARD_REG_SET saying which registers are in it. */
HARD_REG_SET x_reg_class_contents[N_REG_CLASSES];
/* For each reg class, a boolean saying whether the class contains only
fixed registers. */
bool x_class_only_fixed_regs[N_REG_CLASSES];
/* For each reg class, number of regs it contains. */
unsigned int x_reg_class_size[N_REG_CLASSES];
/* For each reg class, table listing all the classes contained in it. */
enum reg_class x_reg_class_subclasses[N_REG_CLASSES][N_REG_CLASSES];
/* For each pair of reg classes,
a largest reg class contained in their union. */
enum reg_class x_reg_class_subunion[N_REG_CLASSES][N_REG_CLASSES];
/* For each pair of reg classes,
the smallest reg class that contains their union. */
enum reg_class x_reg_class_superunion[N_REG_CLASSES][N_REG_CLASSES];
/* Vector indexed by hardware reg giving its name. */
const char *x_reg_names[FIRST_PSEUDO_REGISTER];
};
extern struct target_hard_regs default_target_hard_regs;
#if SWITCHABLE_TARGET
extern struct target_hard_regs *this_target_hard_regs;
#else
#define this_target_hard_regs (&default_target_hard_regs)
#endif
#define accessible_reg_set \
(this_target_hard_regs->x_accessible_reg_set)
#define operand_reg_set \
(this_target_hard_regs->x_operand_reg_set)
#define fixed_regs \
(this_target_hard_regs->x_fixed_regs)
#define fixed_reg_set \
(this_target_hard_regs->x_fixed_reg_set)
#define call_used_regs \
(this_target_hard_regs->x_call_used_regs)
#define call_really_used_regs \
(this_target_hard_regs->x_call_really_used_regs)
#define call_used_reg_set \
(this_target_hard_regs->x_call_used_reg_set)
#define call_fixed_reg_set \
(this_target_hard_regs->x_call_fixed_reg_set)
#define regs_invalidated_by_call \
(this_target_hard_regs->x_regs_invalidated_by_call)
#define no_caller_save_reg_set \
(this_target_hard_regs->x_no_caller_save_reg_set)
#define reg_alloc_order \
(this_target_hard_regs->x_reg_alloc_order)
#define inv_reg_alloc_order \
(this_target_hard_regs->x_inv_reg_alloc_order)
#define reg_class_contents \
(this_target_hard_regs->x_reg_class_contents)
#define class_only_fixed_regs \
(this_target_hard_regs->x_class_only_fixed_regs)
#define reg_class_size \
(this_target_hard_regs->x_reg_class_size)
#define reg_class_subclasses \
(this_target_hard_regs->x_reg_class_subclasses)
#define reg_class_subunion \
(this_target_hard_regs->x_reg_class_subunion)
#define reg_class_superunion \
(this_target_hard_regs->x_reg_class_superunion)
#define reg_names \
(this_target_hard_regs->x_reg_names)
/* Vector indexed by reg class giving its name. */
extern const char * reg_class_names[];
/* Given a hard REGN a FROM mode and a TO mode, return nonzero if
REGN cannot change modes between the specified modes. */
#define REG_CANNOT_CHANGE_MODE_P(REGN, FROM, TO) \
CANNOT_CHANGE_MODE_CLASS (FROM, TO, REGNO_REG_CLASS (REGN))
#endif /* ! GCC_HARD_REG_SET_H */

209
src/include/hashtab.h Normal file
View File

@ -0,0 +1,209 @@
/* An expandable hash tables datatype.
Copyright (C) 1999, 2000, 2002, 2003, 2004, 2005, 2009, 2010
Free Software Foundation, Inc.
Contributed by Vladimir Makarov (vmakarov@cygnus.com).
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA 02110-1301, USA. */
/* This package implements basic hash table functionality. It is possible
to search for an entry, create an entry and destroy an entry.
Elements in the table are generic pointers.
The size of the table is not fixed; if the occupancy of the table
grows too high the hash table will be expanded.
The abstract data implementation is based on generalized Algorithm D
from Knuth's book "The art of computer programming". Hash table is
expanded by creation of new hash table and transferring elements from
the old table to the new table. */
#ifndef __HASHTAB_H__
#define __HASHTAB_H__
#ifdef __cplusplus
extern "C" {
#endif /* __cplusplus */
#include "ansidecl.h"
#ifndef GTY
#define GTY(X)
#endif
/* The type for a hash code. */
typedef unsigned int hashval_t;
/* Callback function pointer types. */
/* Calculate hash of a table entry. */
typedef hashval_t (*htab_hash) (const void *);
/* Compare a table entry with a possible entry. The entry already in
the table always comes first, so the second element can be of a
different type (but in this case htab_find and htab_find_slot
cannot be used; instead the variants that accept a hash value
must be used). */
typedef int (*htab_eq) (const void *, const void *);
/* Cleanup function called whenever a live element is removed from
the hash table. */
typedef void (*htab_del) (void *);
/* Function called by htab_traverse for each live element. The first
arg is the slot of the element (which can be passed to htab_clear_slot
if desired), the second arg is the auxiliary pointer handed to
htab_traverse. Return 1 to continue scan, 0 to stop. */
typedef int (*htab_trav) (void **, void *);
/* Memory-allocation function, with the same functionality as calloc().
Iff it returns NULL, the hash table implementation will pass an error
code back to the user, so if your code doesn't handle errors,
best if you use xcalloc instead. */
typedef void *(*htab_alloc) (size_t, size_t);
/* We also need a free() routine. */
typedef void (*htab_free) (void *);
/* Memory allocation and deallocation; variants which take an extra
argument. */
typedef void *(*htab_alloc_with_arg) (void *, size_t, size_t);
typedef void (*htab_free_with_arg) (void *, void *);
/* This macro defines reserved value for empty table entry. */
#define HTAB_EMPTY_ENTRY ((PTR) 0)
/* This macro defines reserved value for table entry which contained
a deleted element. */
#define HTAB_DELETED_ENTRY ((PTR) 1)
/* Hash tables are of the following type. The structure
(implementation) of this type is not needed for using the hash
tables. All work with hash table should be executed only through
functions mentioned below. The size of this structure is subject to
change. */
struct GTY(()) htab {
/* Pointer to hash function. */
htab_hash hash_f;
/* Pointer to comparison function. */
htab_eq eq_f;
/* Pointer to cleanup function. */
htab_del del_f;
/* Table itself. */
void ** GTY ((use_param, length ("%h.size"))) entries;
/* Current size (in entries) of the hash table. */
size_t size;
/* Current number of elements including also deleted elements. */
size_t n_elements;
/* Current number of deleted elements in the table. */
size_t n_deleted;
/* The following member is used for debugging. Its value is number
of all calls of `htab_find_slot' for the hash table. */
unsigned int searches;
/* The following member is used for debugging. Its value is number
of collisions fixed for time of work with the hash table. */
unsigned int collisions;
/* Pointers to allocate/free functions. */
htab_alloc alloc_f;
htab_free free_f;
/* Alternate allocate/free functions, which take an extra argument. */
void * GTY((skip)) alloc_arg;
htab_alloc_with_arg alloc_with_arg_f;
htab_free_with_arg free_with_arg_f;
/* Current size (in entries) of the hash table, as an index into the
table of primes. */
unsigned int size_prime_index;
};
typedef struct htab *htab_t;
/* An enum saying whether we insert into the hash table or not. */
enum insert_option {NO_INSERT, INSERT};
/* The prototypes of the package functions. */
extern htab_t htab_create_alloc (size_t, htab_hash,
htab_eq, htab_del,
htab_alloc, htab_free);
extern htab_t htab_create_alloc_ex (size_t, htab_hash,
htab_eq, htab_del,
void *, htab_alloc_with_arg,
htab_free_with_arg);
extern htab_t htab_create_typed_alloc (size_t, htab_hash, htab_eq, htab_del,
htab_alloc, htab_alloc, htab_free);
/* Backward-compatibility functions. */
extern htab_t htab_create (size_t, htab_hash, htab_eq, htab_del);
extern htab_t htab_try_create (size_t, htab_hash, htab_eq, htab_del);
extern void htab_set_functions_ex (htab_t, htab_hash,
htab_eq, htab_del,
void *, htab_alloc_with_arg,
htab_free_with_arg);
extern void htab_delete (htab_t);
extern void htab_empty (htab_t);
extern void * htab_find (htab_t, const void *);
extern void ** htab_find_slot (htab_t, const void *, enum insert_option);
extern void * htab_find_with_hash (htab_t, const void *, hashval_t);
extern void ** htab_find_slot_with_hash (htab_t, const void *,
hashval_t, enum insert_option);
extern void htab_clear_slot (htab_t, void **);
extern void htab_remove_elt (htab_t, void *);
extern void htab_remove_elt_with_hash (htab_t, void *, hashval_t);
extern void htab_traverse (htab_t, htab_trav, void *);
extern void htab_traverse_noresize (htab_t, htab_trav, void *);
extern size_t htab_size (htab_t);
extern size_t htab_elements (htab_t);
extern double htab_collisions (htab_t);
/* A hash function for pointers. */
extern htab_hash htab_hash_pointer;
/* An equality function for pointers. */
extern htab_eq htab_eq_pointer;
/* A hash function for null-terminated strings. */
extern hashval_t htab_hash_string (const void *);
/* An iterative hash function for arbitrary data. */
extern hashval_t iterative_hash (const void *, size_t, hashval_t);
/* Shorthand for hashing something with an intrinsic size. */
#define iterative_hash_object(OB,INIT) iterative_hash (&OB, sizeof (OB), INIT)
#ifdef __cplusplus
}
#endif /* __cplusplus */
#endif /* __HASHTAB_H */

View File

@ -0,0 +1,33 @@
/* Interface for high-level plugins in GCC - Parts common between GCC,
ICI and high-level plugins.
Copyright (C) 2009-2013 Free Software Foundation, Inc.
Contributed by INRIA.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef HIGHLEV_PLUGIN_COMMON_H
#define HIGHLEV_PLUGIN_COMMON_H
/* Return codes for invoke_plugin_callbacks / call_plugin_event . */
#define PLUGEVT_SUCCESS 0
#define PLUGEVT_NO_EVENTS 1
#define PLUGEVT_NO_SUCH_EVENT 2
#define PLUGEVT_NO_CALLBACK 3
#endif /* HIGHLEV_PLUGIN_COMMON_H */

279
src/include/hwint.h Normal file
View File

@ -0,0 +1,279 @@
/* HOST_WIDE_INT definitions for the GNU compiler.
Copyright (C) 1998-2013 Free Software Foundation, Inc.
This file is part of GCC.
Provide definitions for macros which depend on HOST_BITS_PER_INT
and HOST_BITS_PER_LONG. */
#ifndef GCC_HWINT_H
#define GCC_HWINT_H
/* This describes the machine the compiler is hosted on. */
#define HOST_BITS_PER_CHAR CHAR_BIT
#define HOST_BITS_PER_SHORT (CHAR_BIT * SIZEOF_SHORT)
#define HOST_BITS_PER_INT (CHAR_BIT * SIZEOF_INT)
#define HOST_BITS_PER_LONG (CHAR_BIT * SIZEOF_LONG)
/* The string that should be inserted into a printf style format to
indicate a "long" operand. */
#ifndef HOST_LONG_FORMAT
#define HOST_LONG_FORMAT "l"
#endif
/* The string that should be inserted into a printf style format to
indicate a "long long" operand. */
#ifndef HOST_LONG_LONG_FORMAT
#define HOST_LONG_LONG_FORMAT "ll"
#endif
/* If HAVE_LONG_LONG and SIZEOF_LONG_LONG aren't defined, but
GCC_VERSION >= 3000, assume this is the second or later stage of a
bootstrap, we do have long long, and it's 64 bits. (This is
required by C99; we do have some ports that violate that assumption
but they're all cross-compile-only.) Just in case, force a
constraint violation if that assumption is incorrect. */
#if !defined HAVE_LONG_LONG
# if GCC_VERSION >= 3000
# define HAVE_LONG_LONG 1
# define SIZEOF_LONG_LONG 8
extern char sizeof_long_long_must_be_8[sizeof(long long) == 8 ? 1 : -1];
# endif
#endif
#ifdef HAVE_LONG_LONG
# define HOST_BITS_PER_LONGLONG (CHAR_BIT * SIZEOF_LONG_LONG)
#endif
#ifdef HAVE___INT64
# define HOST_BITS_PER___INT64 (CHAR_BIT * SIZEOF___INT64)
#endif
/* Set HOST_WIDE_INT. This should be the widest efficient host
integer type. It can be 32 or 64 bits, except that if we are
targeting a machine with 64-bit size_t then it has to be 64 bits.
With a sane ABI, 'long' is the largest efficient host integer type.
Thus, we use that unless we have to use 'long long' or '__int64'
because we're targeting a 64-bit machine from a 32-bit host. */
#if HOST_BITS_PER_LONG >= 64 || !defined NEED_64BIT_HOST_WIDE_INT
# define HOST_BITS_PER_WIDE_INT HOST_BITS_PER_LONG
# define HOST_WIDE_INT long
# define HOST_WIDE_INT_C(X) X ## L
#else
# if HOST_BITS_PER_LONGLONG >= 64
# define HOST_BITS_PER_WIDE_INT HOST_BITS_PER_LONGLONG
# define HOST_WIDE_INT long long
# define HOST_WIDE_INT_C(X) X ## LL
# else
# if HOST_BITS_PER___INT64 >= 64
# define HOST_BITS_PER_WIDE_INT HOST_BITS_PER___INT64
# define HOST_WIDE_INT __int64
# define HOST_WIDE_INT_C(X) X ## i64
# else
#error "Unable to find a suitable type for HOST_WIDE_INT"
# endif
# endif
#endif
#define HOST_WIDE_INT_1 HOST_WIDE_INT_C(1)
/* This is a magic identifier which allows GCC to figure out the type
of HOST_WIDE_INT for %wd specifier checks. You must issue this
typedef before using the __asm_fprintf__ format attribute. */
typedef HOST_WIDE_INT __gcc_host_wide_int__;
/* Various printf format strings for HOST_WIDE_INT. */
#if HOST_BITS_PER_WIDE_INT == HOST_BITS_PER_LONG
# define HOST_WIDE_INT_PRINT HOST_LONG_FORMAT
# define HOST_WIDE_INT_PRINT_C "L"
/* 'long' might be 32 or 64 bits, and the number of leading zeroes
must be tweaked accordingly. */
# if HOST_BITS_PER_WIDE_INT == 64
# define HOST_WIDE_INT_PRINT_DOUBLE_HEX \
"0x%" HOST_LONG_FORMAT "x%016" HOST_LONG_FORMAT "x"
# else
# define HOST_WIDE_INT_PRINT_DOUBLE_HEX \
"0x%" HOST_LONG_FORMAT "x%08" HOST_LONG_FORMAT "x"
# endif
#else
# define HOST_WIDE_INT_PRINT HOST_LONG_LONG_FORMAT
# define HOST_WIDE_INT_PRINT_C "LL"
/* We can assume that 'long long' is at least 64 bits. */
# define HOST_WIDE_INT_PRINT_DOUBLE_HEX \
"0x%" HOST_LONG_LONG_FORMAT "x%016" HOST_LONG_LONG_FORMAT "x"
#endif /* HOST_BITS_PER_WIDE_INT == HOST_BITS_PER_LONG */
#define HOST_WIDE_INT_PRINT_DEC "%" HOST_WIDE_INT_PRINT "d"
#define HOST_WIDE_INT_PRINT_DEC_C HOST_WIDE_INT_PRINT_DEC HOST_WIDE_INT_PRINT_C
#define HOST_WIDE_INT_PRINT_UNSIGNED "%" HOST_WIDE_INT_PRINT "u"
#define HOST_WIDE_INT_PRINT_HEX "%#" HOST_WIDE_INT_PRINT "x"
#define HOST_WIDE_INT_PRINT_HEX_PURE "%" HOST_WIDE_INT_PRINT "x"
/* Set HOST_WIDEST_INT. This is a 64-bit type unless the compiler
in use has no 64-bit type at all; in that case it's 32 bits. */
#if HOST_BITS_PER_WIDE_INT >= 64 \
|| (HOST_BITS_PER_LONGLONG < 64 && HOST_BITS_PER___INT64 < 64)
# define HOST_WIDEST_INT HOST_WIDE_INT
# define HOST_BITS_PER_WIDEST_INT HOST_BITS_PER_WIDE_INT
# define HOST_WIDEST_INT_PRINT HOST_WIDE_INT_PRINT
# define HOST_WIDEST_INT_PRINT_DEC HOST_WIDE_INT_PRINT_DEC
# define HOST_WIDEST_INT_PRINT_DEC_C HOST_WIDE_INT_PRINT_DEC_C
# define HOST_WIDEST_INT_PRINT_UNSIGNED HOST_WIDE_INT_PRINT_UNSIGNED
# define HOST_WIDEST_INT_PRINT_HEX HOST_WIDE_INT_PRINT_HEX
# define HOST_WIDEST_INT_PRINT_DOUBLE_HEX HOST_WIDE_INT_PRINT_DOUBLE_HEX
# define HOST_WIDEST_INT_C(X) HOST_WIDE_INT(X)
#else
# if HOST_BITS_PER_LONGLONG >= 64
# define HOST_BITS_PER_WIDEST_INT HOST_BITS_PER_LONGLONG
# define HOST_WIDEST_INT long long
# define HOST_WIDEST_INT_C(X) X ## LL
# else
# if HOST_BITS_PER___INT64 >= 64
# define HOST_BITS_PER_WIDEST_INT HOST_BITS_PER___INT64
# define HOST_WIDEST_INT __int64
# define HOST_WIDEST_INT_C(X) X ## i64
# else
#error "This line should be impossible to reach"
# endif
# endif
# define HOST_WIDEST_INT_PRINT HOST_LONG_LONG_FORMAT
# define HOST_WIDEST_INT_PRINT_DEC "%" HOST_LONG_LONG_FORMAT "d"
# define HOST_WIDEST_INT_PRINT_DEC_C "%" HOST_LONG_LONG_FORMAT "dLL"
# define HOST_WIDEST_INT_PRINT_UNSIGNED "%" HOST_LONG_LONG_FORMAT "u"
# define HOST_WIDEST_INT_PRINT_HEX "%#" HOST_LONG_LONG_FORMAT "x"
# define HOST_WIDEST_INT_PRINT_DOUBLE_HEX \
"0x%" HOST_LONG_LONG_FORMAT "x%016" HOST_LONG_LONG_FORMAT "x"
#endif
/* Define HOST_WIDEST_FAST_INT to the widest integer type supported
efficiently in hardware. (That is, the widest integer type that fits
in a hardware register.) Normally this is "long" but on some hosts it
should be "long long" or "__int64". This is no convenient way to
autodetect this, so such systems must set a flag in config.host; see there
for details. */
#ifdef USE_LONG_LONG_FOR_WIDEST_FAST_INT
# ifdef HAVE_LONG_LONG
# define HOST_WIDEST_FAST_INT long long
# define HOST_BITS_PER_WIDEST_FAST_INT HOST_BITS_PER_LONGLONG
# elif defined (HAVE___INT64)
# define HOST_WIDEST_FAST_INT __int64
# define HOST_BITS_PER_WIDEST_FAST_INT HOST_BITS_PER___INT64
# else
# error "Your host said it wanted to use long long or __int64 but neither"
# error "exist"
# endif
#else
# define HOST_WIDEST_FAST_INT long
# define HOST_BITS_PER_WIDEST_FAST_INT HOST_BITS_PER_LONG
#endif
/* Inline functions operating on HOST_WIDE_INT. */
#if GCC_VERSION < 3004
extern int clz_hwi (unsigned HOST_WIDE_INT x);
extern int ctz_hwi (unsigned HOST_WIDE_INT x);
extern int ffs_hwi (unsigned HOST_WIDE_INT x);
/* Return the number of set bits in X. */
extern int popcount_hwi (unsigned HOST_WIDE_INT x);
/* Return log2, or -1 if not exact. */
extern int exact_log2 (unsigned HOST_WIDE_INT);
/* Return floor of log2, with -1 for zero. */
extern int floor_log2 (unsigned HOST_WIDE_INT);
/* Return the smallest n such that 2**n >= X. */
extern int ceil_log2 (unsigned HOST_WIDE_INT);
#else /* GCC_VERSION >= 3004 */
/* For convenience, define 0 -> word_size. */
static inline int
clz_hwi (unsigned HOST_WIDE_INT x)
{
if (x == 0)
return HOST_BITS_PER_WIDE_INT;
# if HOST_BITS_PER_WIDE_INT == HOST_BITS_PER_LONG
return __builtin_clzl (x);
# elif HOST_BITS_PER_WIDE_INT == HOST_BITS_PER_LONGLONG
return __builtin_clzll (x);
# else
return __builtin_clz (x);
# endif
}
static inline int
ctz_hwi (unsigned HOST_WIDE_INT x)
{
if (x == 0)
return HOST_BITS_PER_WIDE_INT;
# if HOST_BITS_PER_WIDE_INT == HOST_BITS_PER_LONG
return __builtin_ctzl (x);
# elif HOST_BITS_PER_WIDE_INT == HOST_BITS_PER_LONGLONG
return __builtin_ctzll (x);
# else
return __builtin_ctz (x);
# endif
}
static inline int
ffs_hwi (unsigned HOST_WIDE_INT x)
{
# if HOST_BITS_PER_WIDE_INT == HOST_BITS_PER_LONG
return __builtin_ffsl (x);
# elif HOST_BITS_PER_WIDE_INT == HOST_BITS_PER_LONGLONG
return __builtin_ffsll (x);
# else
return __builtin_ffs (x);
# endif
}
static inline int
popcount_hwi (unsigned HOST_WIDE_INT x)
{
# if HOST_BITS_PER_WIDE_INT == HOST_BITS_PER_LONG
return __builtin_popcountl (x);
# elif HOST_BITS_PER_WIDE_INT == HOST_BITS_PER_LONGLONG
return __builtin_popcountll (x);
# else
return __builtin_popcount (x);
# endif
}
static inline int
floor_log2 (unsigned HOST_WIDE_INT x)
{
return HOST_BITS_PER_WIDE_INT - 1 - clz_hwi (x);
}
static inline int
ceil_log2 (unsigned HOST_WIDE_INT x)
{
return floor_log2 (x - 1) + 1;
}
static inline int
exact_log2 (unsigned HOST_WIDE_INT x)
{
return x == (x & -x) && x ? ctz_hwi (x) : -1;
}
#endif /* GCC_VERSION >= 3004 */
#define HOST_WIDE_INT_MIN (HOST_WIDE_INT) \
((unsigned HOST_WIDE_INT) 1 << (HOST_BITS_PER_WIDE_INT - 1))
#define HOST_WIDE_INT_MAX (~(HOST_WIDE_INT_MIN))
extern HOST_WIDE_INT abs_hwi (HOST_WIDE_INT);
extern unsigned HOST_WIDE_INT absu_hwi (HOST_WIDE_INT);
extern HOST_WIDE_INT gcd (HOST_WIDE_INT, HOST_WIDE_INT);
extern HOST_WIDE_INT pos_mul_hwi (HOST_WIDE_INT, HOST_WIDE_INT);
extern HOST_WIDE_INT mul_hwi (HOST_WIDE_INT, HOST_WIDE_INT);
extern HOST_WIDE_INT least_common_multiple (HOST_WIDE_INT, HOST_WIDE_INT);
#endif /* ! GCC_HWINT_H */

34
src/include/incpath.h Normal file
View File

@ -0,0 +1,34 @@
/* Set up combined include path for the preprocessor.
Copyright (C) 2003-2013 Free Software Foundation, Inc.
This program is free software; you can redistribute it and/or modify it
under the terms of the GNU General Public License as published by the
Free Software Foundation; either version 3, or (at your option) any
later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
extern void split_quote_chain (void);
extern void add_path (char *, int, int, bool);
extern void register_include_chains (cpp_reader *, const char *,
const char *, const char *,
int, int, int);
extern void add_cpp_dir_path (struct cpp_dir *, int);
extern struct cpp_dir *get_added_cpp_dirs (int);
struct target_c_incpath_s {
/* Do extra includes processing. STDINC is false iff -nostdinc was given. */
void (*extra_pre_includes) (const char *, const char *, int);
void (*extra_includes) (const char *, const char *, int);
};
extern struct target_c_incpath_s target_c_incpath;
enum { QUOTE = 0, BRACKET, SYSTEM, AFTER };

67
src/include/input.h Normal file
View File

@ -0,0 +1,67 @@
/* Declarations for variables relating to reading the source file.
Used by parsers, lexical analyzers, and error message routines.
Copyright (C) 1993-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GCC_INPUT_H
#define GCC_INPUT_H
#include "line-map.h"
extern GTY(()) struct line_maps *line_table;
/* A value which will never be used to represent a real location. */
#define UNKNOWN_LOCATION ((source_location) 0)
/* The location for declarations in "<built-in>" */
#define BUILTINS_LOCATION ((source_location) 1)
/* line-map.c reserves RESERVED_LOCATION_COUNT to the user. Ensure
both UNKNOWN_LOCATION and BUILTINS_LOCATION fit into that. */
extern char builtins_location_check[(BUILTINS_LOCATION
< RESERVED_LOCATION_COUNT) ? 1 : -1];
extern expanded_location expand_location (source_location);
extern const char * location_get_source_line(expanded_location xloc);
extern expanded_location expand_location_to_spelling_point (source_location);
extern source_location expansion_point_location_if_in_system_header (source_location);
/* Historically GCC used location_t, while cpp used source_location.
This could be removed but it hardly seems worth the effort. */
typedef source_location location_t;
extern location_t input_location;
#define LOCATION_FILE(LOC) ((expand_location (LOC)).file)
#define LOCATION_LINE(LOC) ((expand_location (LOC)).line)
#define LOCATION_COLUMN(LOC)((expand_location (LOC)).column)
#define LOCATION_LOCUS(LOC) \
((IS_ADHOC_LOC(LOC)) ? get_location_from_adhoc_loc (line_table, LOC) : (LOC))
#define LOCATION_BLOCK(LOC) \
((tree) ((IS_ADHOC_LOC (LOC)) ? get_data_from_adhoc_loc (line_table, (LOC)) \
: NULL))
#define input_line LOCATION_LINE (input_location)
#define input_filename LOCATION_FILE (input_location)
#define in_system_header_at(LOC) \
((linemap_location_in_system_header_p (line_table, LOC)))
#define in_system_header (in_system_header_at (input_location))
void dump_line_table_statistics (void);
#endif

View File

@ -0,0 +1,279 @@
/* Generated automatically by the program `genconstants'
from the machine description file `md'. */
#ifndef GCC_INSN_CONSTANTS_H
#define GCC_INSN_CONSTANTS_H
#define XMM9_REG 46
#define R13_REG 42
#define XMM14_REG 51
#define ROUND_CEIL 0x2
#define PCOM_TRUE 1
#define PPERM_SRC 0x00
#define PPERM_ZERO 0x80
#define MM7_REG 36
#define XMM6_REG 27
#define ST3_REG 11
#define R10_REG 39
#define XMM11_REG 48
#define FLAGS_REG 17
#define ST1_REG 9
#define MM4_REG 33
#define COM_FALSE_P 3
#define XMM3_REG 24
#define ST0_REG 8
#define COM_FALSE_S 2
#define SP_REG 7
#define AX_REG 0
#define ROUND_NO_EXC 0x8
#define R8_REG 37
#define XMM0_REG 21
#define XMM8_REG 45
#define ST5_REG 13
#define R12_REG 41
#define R9_REG 38
#define ROUND_MXCSR 0x4
#define PCOM_FALSE 0
#define FPSR_REG 18
#define PPERM_INVERT 0x20
#define MM6_REG 35
#define MM1_REG 30
#define PPERM_SRC1 0x00
#define PPERM_SRC2 0x10
#define XMM5_REG 26
#define ST2_REG 10
#define XMM10_REG 47
#define ROUND_TRUNC 0x3
#define DI_REG 5
#define DX_REG 1
#define MM3_REG 32
#define XMM12_REG 49
#define COM_TRUE_P 5
#define XMM4_REG 25
#define COM_TRUE_S 4
#define ROUND_FLOOR 0x1
#define ST6_REG 14
#define ST7_REG 15
#define R14_REG 43
#define XMM15_REG 52
#define R15_REG 44
#define XMM13_REG 50
#define PPERM_SIGN 0xc0
#define MM0_REG 29
#define BP_REG 6
#define BX_REG 3
#define XMM7_REG 28
#define ST4_REG 12
#define PPERM_INV_SIGN 0xe0
#define R11_REG 40
#define PPERM_REV_INV 0x60
#define MM5_REG 34
#define PPERM_REVERSE 0x40
#define CX_REG 2
#define SI_REG 4
#define XMM2_REG 23
#define PPERM_ONES 0xa0
#define MM2_REG 31
#define XMM1_REG 22
#define FPCR_REG 19
enum unspec {
UNSPEC_GOT = 0,
UNSPEC_GOTOFF = 1,
UNSPEC_GOTPCREL = 2,
UNSPEC_GOTTPOFF = 3,
UNSPEC_TPOFF = 4,
UNSPEC_NTPOFF = 5,
UNSPEC_DTPOFF = 6,
UNSPEC_GOTNTPOFF = 7,
UNSPEC_INDNTPOFF = 8,
UNSPEC_PLTOFF = 9,
UNSPEC_MACHOPIC_OFFSET = 10,
UNSPEC_PCREL = 11,
UNSPEC_STACK_ALLOC = 12,
UNSPEC_SET_GOT = 13,
UNSPEC_SET_RIP = 14,
UNSPEC_SET_GOT_OFFSET = 15,
UNSPEC_MEMORY_BLOCKAGE = 16,
UNSPEC_STACK_CHECK = 17,
UNSPEC_TP = 18,
UNSPEC_TLS_GD = 19,
UNSPEC_TLS_LD_BASE = 20,
UNSPEC_TLSDESC = 21,
UNSPEC_TLS_IE_SUN = 22,
UNSPEC_SCAS = 23,
UNSPEC_FNSTSW = 24,
UNSPEC_SAHF = 25,
UNSPEC_PARITY = 26,
UNSPEC_FSTCW = 27,
UNSPEC_ADD_CARRY = 28,
UNSPEC_FLDCW = 29,
UNSPEC_REP = 30,
UNSPEC_LD_MPIC = 31,
UNSPEC_TRUNC_NOOP = 32,
UNSPEC_DIV_ALREADY_SPLIT = 33,
UNSPEC_MS_TO_SYSV_CALL = 34,
UNSPEC_PAUSE = 35,
UNSPEC_LEA_ADDR = 36,
UNSPEC_XBEGIN_ABORT = 37,
UNSPEC_STOS = 38,
UNSPEC_FIX_NOTRUNC = 39,
UNSPEC_MASKMOV = 40,
UNSPEC_MOVMSK = 41,
UNSPEC_RCP = 42,
UNSPEC_RSQRT = 43,
UNSPEC_PSADBW = 44,
UNSPEC_COPYSIGN = 45,
UNSPEC_IEEE_MIN = 46,
UNSPEC_IEEE_MAX = 47,
UNSPEC_SIN = 48,
UNSPEC_COS = 49,
UNSPEC_FPATAN = 50,
UNSPEC_FYL2X = 51,
UNSPEC_FYL2XP1 = 52,
UNSPEC_FRNDINT = 53,
UNSPEC_FIST = 54,
UNSPEC_F2XM1 = 55,
UNSPEC_TAN = 56,
UNSPEC_FXAM = 57,
UNSPEC_FRNDINT_FLOOR = 58,
UNSPEC_FRNDINT_CEIL = 59,
UNSPEC_FRNDINT_TRUNC = 60,
UNSPEC_FRNDINT_MASK_PM = 61,
UNSPEC_FIST_FLOOR = 62,
UNSPEC_FIST_CEIL = 63,
UNSPEC_SINCOS_COS = 64,
UNSPEC_SINCOS_SIN = 65,
UNSPEC_XTRACT_FRACT = 66,
UNSPEC_XTRACT_EXP = 67,
UNSPEC_FSCALE_FRACT = 68,
UNSPEC_FSCALE_EXP = 69,
UNSPEC_FPREM_F = 70,
UNSPEC_FPREM_U = 71,
UNSPEC_FPREM1_F = 72,
UNSPEC_FPREM1_U = 73,
UNSPEC_C2_FLAG = 74,
UNSPEC_FXAM_MEM = 75,
UNSPEC_SP_SET = 76,
UNSPEC_SP_TEST = 77,
UNSPEC_SP_TLS_SET = 78,
UNSPEC_SP_TLS_TEST = 79,
UNSPEC_ROUND = 80,
UNSPEC_CRC32 = 81,
UNSPEC_BEXTR = 82,
UNSPEC_PDEP = 83,
UNSPEC_PEXT = 84,
UNSPEC_MOVNTQ = 85,
UNSPEC_PFRCP = 86,
UNSPEC_PFRCPIT1 = 87,
UNSPEC_PFRCPIT2 = 88,
UNSPEC_PFRSQRT = 89,
UNSPEC_PFRSQIT1 = 90,
UNSPEC_MOVNT = 91,
UNSPEC_LOADU = 92,
UNSPEC_STOREU = 93,
UNSPEC_LDDQU = 94,
UNSPEC_PSHUFB = 95,
UNSPEC_PSIGN = 96,
UNSPEC_PALIGNR = 97,
UNSPEC_EXTRQI = 98,
UNSPEC_EXTRQ = 99,
UNSPEC_INSERTQI = 100,
UNSPEC_INSERTQ = 101,
UNSPEC_BLENDV = 102,
UNSPEC_INSERTPS = 103,
UNSPEC_DP = 104,
UNSPEC_MOVNTDQA = 105,
UNSPEC_MPSADBW = 106,
UNSPEC_PHMINPOSUW = 107,
UNSPEC_PTEST = 108,
UNSPEC_PCMPESTR = 109,
UNSPEC_PCMPISTR = 110,
UNSPEC_FMADDSUB = 111,
UNSPEC_XOP_UNSIGNED_CMP = 112,
UNSPEC_XOP_TRUEFALSE = 113,
UNSPEC_XOP_PERMUTE = 114,
UNSPEC_FRCZ = 115,
UNSPEC_AESENC = 116,
UNSPEC_AESENCLAST = 117,
UNSPEC_AESDEC = 118,
UNSPEC_AESDECLAST = 119,
UNSPEC_AESIMC = 120,
UNSPEC_AESKEYGENASSIST = 121,
UNSPEC_PCLMUL = 122,
UNSPEC_PCMP = 123,
UNSPEC_VPERMIL = 124,
UNSPEC_VPERMIL2 = 125,
UNSPEC_VPERMIL2F128 = 126,
UNSPEC_CAST = 127,
UNSPEC_VTESTP = 128,
UNSPEC_VCVTPH2PS = 129,
UNSPEC_VCVTPS2PH = 130,
UNSPEC_VPERMVAR = 131,
UNSPEC_VPERMTI = 132,
UNSPEC_GATHER = 133,
UNSPEC_VSIBADDR = 134,
UNSPEC_LFENCE = 135,
UNSPEC_SFENCE = 136,
UNSPEC_MFENCE = 137,
UNSPEC_MOVA = 138,
UNSPEC_LDA = 139,
UNSPEC_STA = 140
};
#define NUM_UNSPEC_VALUES 141
extern const char *const unspec_strings[];
enum unspecv {
UNSPECV_BLOCKAGE = 0,
UNSPECV_STACK_PROBE = 1,
UNSPECV_PROBE_STACK_RANGE = 2,
UNSPECV_ALIGN = 3,
UNSPECV_PROLOGUE_USE = 4,
UNSPECV_SPLIT_STACK_RETURN = 5,
UNSPECV_CLD = 6,
UNSPECV_NOPS = 7,
UNSPECV_RDTSC = 8,
UNSPECV_RDTSCP = 9,
UNSPECV_RDPMC = 10,
UNSPECV_LLWP_INTRINSIC = 11,
UNSPECV_SLWP_INTRINSIC = 12,
UNSPECV_LWPVAL_INTRINSIC = 13,
UNSPECV_LWPINS_INTRINSIC = 14,
UNSPECV_RDFSBASE = 15,
UNSPECV_RDGSBASE = 16,
UNSPECV_WRFSBASE = 17,
UNSPECV_WRGSBASE = 18,
UNSPECV_FXSAVE = 19,
UNSPECV_FXRSTOR = 20,
UNSPECV_FXSAVE64 = 21,
UNSPECV_FXRSTOR64 = 22,
UNSPECV_XSAVE = 23,
UNSPECV_XRSTOR = 24,
UNSPECV_XSAVE64 = 25,
UNSPECV_XRSTOR64 = 26,
UNSPECV_XSAVEOPT = 27,
UNSPECV_XSAVEOPT64 = 28,
UNSPECV_RDRAND = 29,
UNSPECV_RDSEED = 30,
UNSPECV_XBEGIN = 31,
UNSPECV_XEND = 32,
UNSPECV_XABORT = 33,
UNSPECV_XTEST = 34,
UNSPECV_NLGR = 35,
UNSPECV_EMMS = 36,
UNSPECV_FEMMS = 37,
UNSPECV_LDMXCSR = 38,
UNSPECV_STMXCSR = 39,
UNSPECV_CLFLUSH = 40,
UNSPECV_MONITOR = 41,
UNSPECV_MWAIT = 42,
UNSPECV_VZEROALL = 43,
UNSPECV_VZEROUPPER = 44,
UNSPECV_CMPXCHG = 45,
UNSPECV_XCHG = 46,
UNSPECV_LOCK = 47
};
#define NUM_UNSPECV_VALUES 48
extern const char *const unspecv_strings[];
#endif /* GCC_INSN_CONSTANTS_H */

4966
src/include/insn-flags.h Normal file

File diff suppressed because it is too large Load Diff

160
src/include/insn-modes.h Normal file
View File

@ -0,0 +1,160 @@
/* Generated automatically from machmode.def and config/i386/i386-modes.def
by genmodes. */
#ifndef GCC_INSN_MODES_H
#define GCC_INSN_MODES_H
enum machine_mode
{
VOIDmode, /* machmode.def:172 */
BLKmode, /* machmode.def:176 */
CCmode, /* machmode.def:204 */
CCGCmode, /* config/i386/i386-modes.def:61 */
CCGOCmode, /* config/i386/i386-modes.def:62 */
CCNOmode, /* config/i386/i386-modes.def:63 */
CCAmode, /* config/i386/i386-modes.def:64 */
CCCmode, /* config/i386/i386-modes.def:65 */
CCOmode, /* config/i386/i386-modes.def:66 */
CCSmode, /* config/i386/i386-modes.def:67 */
CCZmode, /* config/i386/i386-modes.def:68 */
CCFPmode, /* config/i386/i386-modes.def:69 */
CCFPUmode, /* config/i386/i386-modes.def:70 */
BImode, /* machmode.def:179 */
QImode, /* machmode.def:184 */
HImode, /* machmode.def:185 */
SImode, /* machmode.def:186 */
DImode, /* machmode.def:187 */
TImode, /* machmode.def:188 */
OImode, /* config/i386/i386-modes.def:88 */
QQmode, /* machmode.def:207 */
HQmode, /* machmode.def:208 */
SQmode, /* machmode.def:209 */
DQmode, /* machmode.def:210 */
TQmode, /* machmode.def:211 */
UQQmode, /* machmode.def:213 */
UHQmode, /* machmode.def:214 */
USQmode, /* machmode.def:215 */
UDQmode, /* machmode.def:216 */
UTQmode, /* machmode.def:217 */
HAmode, /* machmode.def:219 */
SAmode, /* machmode.def:220 */
DAmode, /* machmode.def:221 */
TAmode, /* machmode.def:222 */
UHAmode, /* machmode.def:224 */
USAmode, /* machmode.def:225 */
UDAmode, /* machmode.def:226 */
UTAmode, /* machmode.def:227 */
SFmode, /* machmode.def:199 */
DFmode, /* machmode.def:200 */
XFmode, /* config/i386/i386-modes.def:24 */
TFmode, /* config/i386/i386-modes.def:25 */
SDmode, /* machmode.def:239 */
DDmode, /* machmode.def:240 */
TDmode, /* machmode.def:241 */
CQImode, /* machmode.def:235 */
CHImode, /* machmode.def:235 */
CSImode, /* machmode.def:235 */
CDImode, /* machmode.def:235 */
CTImode, /* machmode.def:235 */
COImode, /* machmode.def:235 */
SCmode, /* machmode.def:236 */
DCmode, /* machmode.def:236 */
XCmode, /* machmode.def:236 */
TCmode, /* machmode.def:236 */
V2QImode, /* config/i386/i386-modes.def:86 */
V4QImode, /* config/i386/i386-modes.def:74 */
V2HImode, /* config/i386/i386-modes.def:74 */
V1SImode, /* config/i386/i386-modes.def:85 */
V8QImode, /* config/i386/i386-modes.def:75 */
V4HImode, /* config/i386/i386-modes.def:75 */
V2SImode, /* config/i386/i386-modes.def:75 */
V1DImode, /* config/i386/i386-modes.def:84 */
V16QImode, /* config/i386/i386-modes.def:76 */
V8HImode, /* config/i386/i386-modes.def:76 */
V4SImode, /* config/i386/i386-modes.def:76 */
V2DImode, /* config/i386/i386-modes.def:76 */
V1TImode, /* config/i386/i386-modes.def:83 */
V32QImode, /* config/i386/i386-modes.def:77 */
V16HImode, /* config/i386/i386-modes.def:77 */
V8SImode, /* config/i386/i386-modes.def:77 */
V4DImode, /* config/i386/i386-modes.def:77 */
V2TImode, /* config/i386/i386-modes.def:77 */
V64QImode, /* config/i386/i386-modes.def:78 */
V32HImode, /* config/i386/i386-modes.def:78 */
V16SImode, /* config/i386/i386-modes.def:78 */
V8DImode, /* config/i386/i386-modes.def:78 */
V4TImode, /* config/i386/i386-modes.def:78 */
V2SFmode, /* config/i386/i386-modes.def:79 */
V4SFmode, /* config/i386/i386-modes.def:80 */
V2DFmode, /* config/i386/i386-modes.def:80 */
V8SFmode, /* config/i386/i386-modes.def:81 */
V4DFmode, /* config/i386/i386-modes.def:81 */
V2TFmode, /* config/i386/i386-modes.def:81 */
V16SFmode, /* config/i386/i386-modes.def:82 */
V8DFmode, /* config/i386/i386-modes.def:82 */
V4TFmode, /* config/i386/i386-modes.def:82 */
MAX_MACHINE_MODE,
MIN_MODE_RANDOM = VOIDmode,
MAX_MODE_RANDOM = BLKmode,
MIN_MODE_CC = CCmode,
MAX_MODE_CC = CCFPUmode,
MIN_MODE_INT = QImode,
MAX_MODE_INT = OImode,
MIN_MODE_PARTIAL_INT = VOIDmode,
MAX_MODE_PARTIAL_INT = VOIDmode,
MIN_MODE_FRACT = QQmode,
MAX_MODE_FRACT = TQmode,
MIN_MODE_UFRACT = UQQmode,
MAX_MODE_UFRACT = UTQmode,
MIN_MODE_ACCUM = HAmode,
MAX_MODE_ACCUM = TAmode,
MIN_MODE_UACCUM = UHAmode,
MAX_MODE_UACCUM = UTAmode,
MIN_MODE_FLOAT = SFmode,
MAX_MODE_FLOAT = TFmode,
MIN_MODE_DECIMAL_FLOAT = SDmode,
MAX_MODE_DECIMAL_FLOAT = TDmode,
MIN_MODE_COMPLEX_INT = CQImode,
MAX_MODE_COMPLEX_INT = COImode,
MIN_MODE_COMPLEX_FLOAT = SCmode,
MAX_MODE_COMPLEX_FLOAT = TCmode,
MIN_MODE_VECTOR_INT = V2QImode,
MAX_MODE_VECTOR_INT = V4TImode,
MIN_MODE_VECTOR_FRACT = VOIDmode,
MAX_MODE_VECTOR_FRACT = VOIDmode,
MIN_MODE_VECTOR_UFRACT = VOIDmode,
MAX_MODE_VECTOR_UFRACT = VOIDmode,
MIN_MODE_VECTOR_ACCUM = VOIDmode,
MAX_MODE_VECTOR_ACCUM = VOIDmode,
MIN_MODE_VECTOR_UACCUM = VOIDmode,
MAX_MODE_VECTOR_UACCUM = VOIDmode,
MIN_MODE_VECTOR_FLOAT = V2SFmode,
MAX_MODE_VECTOR_FLOAT = V4TFmode,
NUM_MACHINE_MODES = MAX_MACHINE_MODE
};
#define CONST_MODE_SIZE
#define CONST_MODE_BASE_ALIGN
#define CONST_MODE_IBIT const
#define CONST_MODE_FBIT const
#endif /* insn-modes.h */

View File

@ -0,0 +1,90 @@
/* Insn note definitions.
Copyright (C) 2004-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
/* This file defines all the codes that may appear in the
NOTE_LINE_NUMBER field of a NOTE insn for kinds of notes that are
not line numbers. Source files define DEF_INSN_NOTE appropriately
before including this file.
We are slowly removing the concept of insn-chain notes from the
compiler. Adding new codes to this file is STRONGLY DISCOURAGED.
If you think you need one, look for other ways to express what you
mean, such as register notes or bits in the basic-block structure. */
/* Shorthand. */
#define INSN_NOTE(NAME) DEF_INSN_NOTE (NOTE_INSN_##NAME)
/* This note is used to get rid of an insn when it isn't safe to patch
the insn out of the chain. */
INSN_NOTE (DELETED)
/* Generated in place of user-declared labels when they are deleted. */
INSN_NOTE (DELETED_LABEL)
/* Similarly, but for labels that have been present in debug stmts
earlier and thus will only appear with -g. These must use different
label namespace. */
INSN_NOTE (DELETED_DEBUG_LABEL)
/* These are used to mark the beginning and end of a lexical block.
See NOTE_BLOCK and reorder_blocks. */
INSN_NOTE (BLOCK_BEG)
INSN_NOTE (BLOCK_END)
/* This note indicates the start of the real body of the function,
i.e. the point just after all of the parms have been moved into
their homes, etc. */
INSN_NOTE (FUNCTION_BEG)
/* This marks the point immediately after the last prologue insn. */
INSN_NOTE (PROLOGUE_END)
/* This marks the point immediately prior to the first epilogue insn. */
INSN_NOTE (EPILOGUE_BEG)
/* These note where exception handling regions begin and end.
Uses NOTE_EH_HANDLER to identify the region in question. */
INSN_NOTE (EH_REGION_BEG)
INSN_NOTE (EH_REGION_END)
/* The location of a variable. */
INSN_NOTE (VAR_LOCATION)
/* The values passed to callee. */
INSN_NOTE (CALL_ARG_LOCATION)
/* Record the struct for the following basic block. Uses
NOTE_BASIC_BLOCK. FIXME: Redundant with the basic block pointer
now included in every insn. NOTE: If there's no CFG anymore, in other words,
if BLOCK_FOR_INSN () == NULL, NOTE_BASIC_BLOCK cannot be considered reliable
anymore. */
INSN_NOTE (BASIC_BLOCK)
/* Mark the inflection point in the instruction stream where we switch
between hot and cold text sections. */
INSN_NOTE (SWITCH_TEXT_SECTIONS)
/* When emitting dwarf2 frame information, contains a directive that
should be emitted. */
INSN_NOTE (CFI)
/* When emitting dwarf2 frame information, contains the number of a debug
label that should be emitted. */
INSN_NOTE (CFI_LABEL)
#undef INSN_NOTE

View File

@ -0,0 +1,42 @@
/* Internal functions.
Copyright (C) 2011-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
/* This file specifies a list of internal "functions". These functions
differ from built-in functions in that they have no linkage and cannot
be called directly by the user. They represent operations that are only
synthesised by GCC itself.
Internal functions are used instead of tree codes if the operation
and its operands are more naturally represented as a GIMPLE_CALL
than a GIMPLE_ASSIGN.
Each entry in this file has the form:
DEF_INTERNAL_FN (NAME, FLAGS)
where NAME is the name of the function and FLAGS is a set of
ECF_* flags. Each entry must have a corresponding expander
of the form:
void expand_NAME (gimple stmt)
where STMT is the statement that performs the call. */
DEF_INTERNAL_FN (LOAD_LANES, ECF_CONST | ECF_LEAF)
DEF_INTERNAL_FN (STORE_LANES, ECF_CONST | ECF_LEAF)

53
src/include/internal-fn.h Normal file
View File

@ -0,0 +1,53 @@
/* Internal functions.
Copyright (C) 2011-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GCC_INTERNAL_FN_H
#define GCC_INTERNAL_FN_H
enum internal_fn {
#define DEF_INTERNAL_FN(CODE, FLAGS) IFN_##CODE,
#include "internal-fn.def"
#undef DEF_INTERNAL_FN
IFN_LAST
};
/* Return the name of internal function FN. The name is only meaningful
for dumps; it has no linkage. */
extern const char *const internal_fn_name_array[];
static inline const char *
internal_fn_name (enum internal_fn fn)
{
return internal_fn_name_array[(int) fn];
}
/* Return the ECF_* flags for function FN. */
extern const int internal_fn_flags_array[];
static inline int
internal_fn_flags (enum internal_fn fn)
{
return internal_fn_flags_array[(int) fn];
}
extern void expand_internal_call (gimple);
#endif

69
src/include/intl.h Normal file
View File

@ -0,0 +1,69 @@
/* intl.h - internationalization
Copyright (C) 1998-2013 Free Software Foundation, Inc.
GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GCC is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GCC_INTL_H
#define GCC_INTL_H
#ifdef HAVE_LOCALE_H
# include <locale.h>
#endif
#ifndef HAVE_SETLOCALE
# define setlocale(category, locale) (locale)
#endif
#ifdef ENABLE_NLS
#include <libintl.h>
extern void gcc_init_libintl (void);
extern size_t gcc_gettext_width (const char *);
#else
/* Stubs. */
# undef textdomain
# define textdomain(domain) (domain)
# undef bindtextdomain
# define bindtextdomain(domain, directory) (domain)
# undef gettext
# define gettext(msgid) (msgid)
# define ngettext(singular,plural,n) fake_ngettext(singular,plural,n)
# define gcc_init_libintl() /* nothing */
# define gcc_gettext_width(s) strlen(s)
extern const char *fake_ngettext(const char *singular,const char *plural,
unsigned long int n);
#endif
#ifndef _
# define _(msgid) gettext (msgid)
#endif
#ifndef N_
# define N_(msgid) msgid
#endif
#ifndef G_
# define G_(gmsgid) gmsgid
#endif
extern char *get_spaces (const char *);
extern const char *open_quote;
extern const char *close_quote;
extern const char *locale_encoding;
extern bool locale_utf8;
#endif /* intl.h */

619
src/include/ipa-prop.h Normal file
View File

@ -0,0 +1,619 @@
/* Interprocedural analyses.
Copyright (C) 2005-2013 Free Software Foundation, Inc.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef IPA_PROP_H
#define IPA_PROP_H
#include "tree.h"
#include "vec.h"
#include "cgraph.h"
#include "gimple.h"
#include "alloc-pool.h"
/* The following definitions and interfaces are used by
interprocedural analyses or parameters. */
/* ipa-prop.c stuff (ipa-cp, indirect inlining): */
/* A jump function for a callsite represents the values passed as actual
arguments of the callsite. They were originally proposed in a paper called
"Interprocedural Constant Propagation", by David Callahan, Keith D Cooper,
Ken Kennedy, Linda Torczon in Comp86, pg 152-161. There are three main
types of values :
Pass-through - the caller's formal parameter is passed as an actual
argument, possibly one simple operation performed on it.
Constant - a constant (is_gimple_ip_invariant)is passed as an actual
argument.
Unknown - neither of the above.
IPA_JF_ANCESTOR is a special pass-through jump function, which means that
the result is an address of a part of the object pointed to by the formal
parameter to which the function refers. It is mainly intended to represent
getting addresses of of ancestor fields in C++
(e.g. &this_1(D)->D.1766.D.1756). Note that if the original pointer is
NULL, ancestor jump function must behave like a simple pass-through.
Other pass-through functions can either simply pass on an unchanged formal
parameter or can apply one simple binary operation to it (such jump
functions are called polynomial).
IPA_JF_KNOWN_TYPE is a special type of an "unknown" function that applies
only to pointer parameters. It means that even though we cannot prove that
the passed value is an interprocedural constant, we still know the exact
type of the containing object which may be valuable for devirtualization.
Jump functions are computed in ipa-prop.c by function
update_call_notes_after_inlining. Some information can be lost and jump
functions degraded accordingly when inlining, see
update_call_notes_after_inlining in the same file. */
enum jump_func_type
{
IPA_JF_UNKNOWN = 0, /* newly allocated and zeroed jump functions default */
IPA_JF_KNOWN_TYPE, /* represented by field known_type */
IPA_JF_CONST, /* represented by field costant */
IPA_JF_PASS_THROUGH, /* represented by field pass_through */
IPA_JF_ANCESTOR /* represented by field ancestor */
};
/* Structure holding data required to describe a known type jump function. */
struct GTY(()) ipa_known_type_data
{
/* Offset of the component of the base_type being described. */
HOST_WIDE_INT offset;
/* Type of the whole object. */
tree base_type;
/* Type of the component of the object that is being described. */
tree component_type;
};
/* Structure holding data required to describe a pass-through jump function. */
struct GTY(()) ipa_pass_through_data
{
/* If an operation is to be performed on the original parameter, this is the
second (constant) operand. */
tree operand;
/* Number of the caller's formal parameter being passed. */
int formal_id;
/* Operation that is performed on the argument before it is passed on.
NOP_EXPR means no operation. Otherwise oper must be a simple binary
arithmetic operation where the caller's parameter is the first operand and
operand field from this structure is the second one. */
enum tree_code operation;
/* When the passed value is a pointer, it is set to true only when we are
certain that no write to the object it points to has occurred since the
caller functions started execution, except for changes noted in the
aggregate part of the jump function (see description of
ipa_agg_jump_function). The flag is used only when the operation is
NOP_EXPR. */
bool agg_preserved;
};
/* Structure holding data required to describe an ancestor pass-through
jump function. */
struct GTY(()) ipa_ancestor_jf_data
{
/* Offset of the field representing the ancestor. */
HOST_WIDE_INT offset;
/* Type of the result. */
tree type;
/* Number of the caller's formal parameter being passed. */
int formal_id;
/* Flag with the same meaning like agg_preserve in ipa_pass_through_data. */
bool agg_preserved;
};
/* An element in an aggegate part of a jump function describing a known value
at a given offset. When it is part of a pass-through jump function with
agg_preserved set or an ancestor jump function with agg_preserved set, all
unlisted positions are assumed to be preserved but the value can be a type
node, which means that the particular piece (starting at offset and having
the size of the type) is clobbered with an unknown value. When
agg_preserved is false or the type of the containing jump function is
different, all unlisted parts are assumed to be unknown and all values must
fullfill is_gimple_ip_invariant. */
typedef struct GTY(()) ipa_agg_jf_item
{
/* The offset at which the known value is located within the aggregate. */
HOST_WIDE_INT offset;
/* The known constant or type if this is a clobber. */
tree value;
} ipa_agg_jf_item_t;
/* Aggregate jump function - i.e. description of contents of aggregates passed
either by reference or value. */
struct GTY(()) ipa_agg_jump_function
{
/* Description of the individual items. */
vec<ipa_agg_jf_item_t, va_gc> *items;
/* True if the data was passed by reference (as opposed to by value). */
bool by_ref;
};
typedef struct ipa_agg_jump_function *ipa_agg_jump_function_p;
typedef struct ipa_agg_jump_function ipa_agg_jump_function_t;
/* A jump function for a callsite represents the values passed as actual
arguments of the callsite. See enum jump_func_type for the various
types of jump functions supported. */
typedef struct GTY (()) ipa_jump_func
{
/* Aggregate contants description. See struct ipa_agg_jump_function and its
description. */
struct ipa_agg_jump_function agg;
enum jump_func_type type;
/* Represents a value of a jump function. pass_through is used only in jump
function context. constant represents the actual constant in constant jump
functions and member_cst holds constant c++ member functions. */
union jump_func_value
{
struct ipa_known_type_data GTY ((tag ("IPA_JF_KNOWN_TYPE"))) known_type;
tree GTY ((tag ("IPA_JF_CONST"))) constant;
struct ipa_pass_through_data GTY ((tag ("IPA_JF_PASS_THROUGH"))) pass_through;
struct ipa_ancestor_jf_data GTY ((tag ("IPA_JF_ANCESTOR"))) ancestor;
} GTY ((desc ("%1.type"))) value;
} ipa_jump_func_t;
/* Return the offset of the component that is decribed by a known type jump
function JFUNC. */
static inline HOST_WIDE_INT
ipa_get_jf_known_type_offset (struct ipa_jump_func *jfunc)
{
gcc_checking_assert (jfunc->type == IPA_JF_KNOWN_TYPE);
return jfunc->value.known_type.offset;
}
/* Return the base type of a known type jump function JFUNC. */
static inline tree
ipa_get_jf_known_type_base_type (struct ipa_jump_func *jfunc)
{
gcc_checking_assert (jfunc->type == IPA_JF_KNOWN_TYPE);
return jfunc->value.known_type.base_type;
}
/* Return the component type of a known type jump function JFUNC. */
static inline tree
ipa_get_jf_known_type_component_type (struct ipa_jump_func *jfunc)
{
gcc_checking_assert (jfunc->type == IPA_JF_KNOWN_TYPE);
return jfunc->value.known_type.component_type;
}
/* Return the constant stored in a constant jump functin JFUNC. */
static inline tree
ipa_get_jf_constant (struct ipa_jump_func *jfunc)
{
gcc_checking_assert (jfunc->type == IPA_JF_CONST);
return jfunc->value.constant;
}
/* Return the operand of a pass through jmp function JFUNC. */
static inline tree
ipa_get_jf_pass_through_operand (struct ipa_jump_func *jfunc)
{
gcc_checking_assert (jfunc->type == IPA_JF_PASS_THROUGH);
return jfunc->value.pass_through.operand;
}
/* Return the number of the caller's formal parameter that a pass through jump
function JFUNC refers to. */
static inline int
ipa_get_jf_pass_through_formal_id (struct ipa_jump_func *jfunc)
{
gcc_checking_assert (jfunc->type == IPA_JF_PASS_THROUGH);
return jfunc->value.pass_through.formal_id;
}
/* Return operation of a pass through jump function JFUNC. */
static inline enum tree_code
ipa_get_jf_pass_through_operation (struct ipa_jump_func *jfunc)
{
gcc_checking_assert (jfunc->type == IPA_JF_PASS_THROUGH);
return jfunc->value.pass_through.operation;
}
/* Return the agg_preserved flag of a pass through jump functin JFUNC. */
static inline bool
ipa_get_jf_pass_through_agg_preserved (struct ipa_jump_func *jfunc)
{
gcc_checking_assert (jfunc->type == IPA_JF_PASS_THROUGH);
return jfunc->value.pass_through.agg_preserved;
}
/* Return the offset of an ancestor jump function JFUNC. */
static inline HOST_WIDE_INT
ipa_get_jf_ancestor_offset (struct ipa_jump_func *jfunc)
{
gcc_checking_assert (jfunc->type == IPA_JF_ANCESTOR);
return jfunc->value.ancestor.offset;
}
/* Return the result type of an ancestor jump function JFUNC. */
static inline tree
ipa_get_jf_ancestor_type (struct ipa_jump_func *jfunc)
{
gcc_checking_assert (jfunc->type == IPA_JF_ANCESTOR);
return jfunc->value.ancestor.type;
}
/* Return the number of the caller's formal parameter that an ancestor jump
function JFUNC refers to. */
static inline int
ipa_get_jf_ancestor_formal_id (struct ipa_jump_func *jfunc)
{
gcc_checking_assert (jfunc->type == IPA_JF_ANCESTOR);
return jfunc->value.ancestor.formal_id;
}
/* Return the agg_preserved flag of an ancestor jump functin JFUNC. */
static inline bool
ipa_get_jf_ancestor_agg_preserved (struct ipa_jump_func *jfunc)
{
gcc_checking_assert (jfunc->type == IPA_JF_ANCESTOR);
return jfunc->value.ancestor.agg_preserved;
}
/* Summary describing a single formal parameter. */
struct ipa_param_descriptor
{
/* PARAM_DECL of this parameter. */
tree decl;
/* The parameter is used. */
unsigned used : 1;
};
typedef struct ipa_param_descriptor ipa_param_descriptor_t;
struct ipcp_lattice;
/* ipa_node_params stores information related to formal parameters of functions
and some other information for interprocedural passes that operate on
parameters (such as ipa-cp). */
struct ipa_node_params
{
/* Information about individual formal parameters that are gathered when
summaries are generated. */
vec<ipa_param_descriptor_t> descriptors;
/* Pointer to an array of structures describing individual formal
parameters. */
struct ipcp_param_lattices *lattices;
/* Only for versioned nodes this field would not be NULL,
it points to the node that IPA cp cloned from. */
struct cgraph_node *ipcp_orig_node;
/* If this node is an ipa-cp clone, these are the known values that describe
what it has been specialized for. */
vec<tree> known_vals;
/* Whether the param uses analysis has already been performed. */
unsigned uses_analysis_done : 1;
/* Whether the function is enqueued in ipa-cp propagation stack. */
unsigned node_enqueued : 1;
/* Whether we should create a specialized version based on values that are
known to be constant in all contexts. */
unsigned do_clone_for_all_contexts : 1;
/* Set if this is an IPA-CP clone for all contexts. */
unsigned is_all_contexts_clone : 1;
/* Node has been completely replaced by clones and will be removed after
ipa-cp is finished. */
unsigned node_dead : 1;
};
/* ipa_node_params access functions. Please use these to access fields that
are or will be shared among various passes. */
/* Return the number of formal parameters. */
static inline int
ipa_get_param_count (struct ipa_node_params *info)
{
return info->descriptors.length ();
}
/* Return the declaration of Ith formal parameter of the function corresponding
to INFO. Note there is no setter function as this array is built just once
using ipa_initialize_node_params. */
static inline tree
ipa_get_param (struct ipa_node_params *info, int i)
{
return info->descriptors[i].decl;
}
/* Set the used flag corresponding to the Ith formal parameter of the function
associated with INFO to VAL. */
static inline void
ipa_set_param_used (struct ipa_node_params *info, int i, bool val)
{
info->descriptors[i].used = val;
}
/* Return the used flag corresponding to the Ith formal parameter of the
function associated with INFO. */
static inline bool
ipa_is_param_used (struct ipa_node_params *info, int i)
{
return info->descriptors[i].used;
}
/* Information about replacements done in aggregates for a given node (each
node has its linked list). */
struct GTY(()) ipa_agg_replacement_value
{
/* Next item in the linked list. */
struct ipa_agg_replacement_value *next;
/* Offset within the aggregate. */
HOST_WIDE_INT offset;
/* The constant value. */
tree value;
/* The paramter index. */
int index;
/* Whether the value was passed by reference. */
bool by_ref;
};
typedef struct ipa_agg_replacement_value *ipa_agg_replacement_value_p;
void ipa_set_node_agg_value_chain (struct cgraph_node *node,
struct ipa_agg_replacement_value *aggvals);
/* ipa_edge_args stores information related to a callsite and particularly its
arguments. It can be accessed by the IPA_EDGE_REF macro. */
typedef struct GTY(()) ipa_edge_args
{
/* Vector of the callsite's jump function of each parameter. */
vec<ipa_jump_func_t, va_gc> *jump_functions;
} ipa_edge_args_t;
/* ipa_edge_args access functions. Please use these to access fields that
are or will be shared among various passes. */
/* Return the number of actual arguments. */
static inline int
ipa_get_cs_argument_count (struct ipa_edge_args *args)
{
return vec_safe_length (args->jump_functions);
}
/* Returns a pointer to the jump function for the ith argument. Please note
there is no setter function as jump functions are all set up in
ipa_compute_jump_functions. */
static inline struct ipa_jump_func *
ipa_get_ith_jump_func (struct ipa_edge_args *args, int i)
{
return &(*args->jump_functions)[i];
}
/* Vectors need to have typedefs of structures. */
typedef struct ipa_node_params ipa_node_params_t;
/* Types of vectors holding the infos. */
/* Vector where the parameter infos are actually stored. */
extern vec<ipa_node_params_t> ipa_node_params_vector;
/* Vector of known aggregate values in cloned nodes. */
extern GTY(()) vec<ipa_agg_replacement_value_p, va_gc> *ipa_node_agg_replacements;
/* Vector where the parameter infos are actually stored. */
extern GTY(()) vec<ipa_edge_args_t, va_gc> *ipa_edge_args_vector;
/* Return the associated parameter/argument info corresponding to the given
node/edge. */
#define IPA_NODE_REF(NODE) (&ipa_node_params_vector[(NODE)->uid])
#define IPA_EDGE_REF(EDGE) (&(*ipa_edge_args_vector)[(EDGE)->uid])
/* This macro checks validity of index returned by
ipa_get_param_decl_index function. */
#define IS_VALID_JUMP_FUNC_INDEX(I) ((I) != -1)
/* Creating and freeing ipa_node_params and ipa_edge_args. */
void ipa_create_all_node_params (void);
void ipa_create_all_edge_args (void);
void ipa_free_edge_args_substructures (struct ipa_edge_args *);
void ipa_free_node_params_substructures (struct ipa_node_params *);
void ipa_free_all_node_params (void);
void ipa_free_all_edge_args (void);
void ipa_free_all_structures_after_ipa_cp (void);
void ipa_free_all_structures_after_iinln (void);
void ipa_register_cgraph_hooks (void);
/* This function ensures the array of node param infos is big enough to
accommodate a structure for all nodes and reallocates it if not. */
static inline void
ipa_check_create_node_params (void)
{
if (!ipa_node_params_vector.exists ())
ipa_node_params_vector.create (cgraph_max_uid);
if (ipa_node_params_vector.length () <= (unsigned) cgraph_max_uid)
ipa_node_params_vector.safe_grow_cleared (cgraph_max_uid + 1);
}
/* This function ensures the array of edge arguments infos is big enough to
accommodate a structure for all edges and reallocates it if not. */
static inline void
ipa_check_create_edge_args (void)
{
if (vec_safe_length (ipa_edge_args_vector) <= (unsigned) cgraph_edge_max_uid)
vec_safe_grow_cleared (ipa_edge_args_vector, cgraph_edge_max_uid + 1);
}
/* Returns true if the array of edge infos is large enough to accommodate an
info for EDGE. The main purpose of this function is that debug dumping
function can check info availability without causing reallocations. */
static inline bool
ipa_edge_args_info_available_for_edge_p (struct cgraph_edge *edge)
{
return ((unsigned) edge->uid < vec_safe_length (ipa_edge_args_vector));
}
/* Return the aggregate replacements for NODE, if there are any. */
static inline struct ipa_agg_replacement_value *
ipa_get_agg_replacements_for_node (struct cgraph_node *node)
{
if ((unsigned) node->uid >= vec_safe_length (ipa_node_agg_replacements))
return NULL;
return (*ipa_node_agg_replacements)[node->uid];
}
/* Function formal parameters related computations. */
void ipa_initialize_node_params (struct cgraph_node *node);
bool ipa_propagate_indirect_call_infos (struct cgraph_edge *cs,
vec<cgraph_edge_p> *new_edges);
/* Indirect edge and binfo processing. */
tree ipa_get_indirect_edge_target (struct cgraph_edge *ie,
vec<tree> ,
vec<tree> ,
vec<ipa_agg_jump_function_p> );
struct cgraph_edge *ipa_make_edge_direct_to_target (struct cgraph_edge *, tree);
/* Functions related to both. */
void ipa_analyze_node (struct cgraph_node *);
/* Aggregate jump function related functions. */
tree ipa_find_agg_cst_for_param (struct ipa_agg_jump_function *, HOST_WIDE_INT,
bool);
bool ipa_load_from_parm_agg (struct ipa_node_params *, gimple, tree, int *,
HOST_WIDE_INT *, bool *);
/* Debugging interface. */
void ipa_print_node_params (FILE *, struct cgraph_node *node);
void ipa_print_all_params (FILE *);
void ipa_print_node_jump_functions (FILE *f, struct cgraph_node *node);
void ipa_print_all_jump_functions (FILE * f);
void ipcp_verify_propagated_values (void);
extern alloc_pool ipcp_values_pool;
extern alloc_pool ipcp_sources_pool;
extern alloc_pool ipcp_agg_lattice_pool;
/* Structure to describe transformations of formal parameters and actual
arguments. Each instance describes one new parameter and they are meant to
be stored in a vector. Additionally, most users will probably want to store
adjustments about parameters that are being removed altogether so that SSA
names belonging to them can be replaced by SSA names of an artificial
variable. */
struct ipa_parm_adjustment
{
/* The original PARM_DECL itself, helpful for processing of the body of the
function itself. Intended for traversing function bodies.
ipa_modify_formal_parameters, ipa_modify_call_arguments and
ipa_combine_adjustments ignore this and use base_index.
ipa_modify_formal_parameters actually sets this. */
tree base;
/* Type of the new parameter. However, if by_ref is true, the real type will
be a pointer to this type. */
tree type;
/* Alias refrerence type to be used in MEM_REFs when adjusting caller
arguments. */
tree alias_ptr_type;
/* The new declaration when creating/replacing a parameter. Created by
ipa_modify_formal_parameters, useful for functions modifying the body
accordingly. */
tree reduction;
/* New declaration of a substitute variable that we may use to replace all
non-default-def ssa names when a parm decl is going away. */
tree new_ssa_base;
/* If non-NULL and the original parameter is to be removed (copy_param below
is NULL), this is going to be its nonlocalized vars value. */
tree nonlocal_value;
/* Offset into the original parameter (for the cases when the new parameter
is a component of an original one). */
HOST_WIDE_INT offset;
/* Zero based index of the original parameter this one is based on. (ATM
there is no way to insert a new parameter out of the blue because there is
no need but if it arises the code can be easily exteded to do so.) */
int base_index;
/* This new parameter is an unmodified parameter at index base_index. */
unsigned copy_param : 1;
/* This adjustment describes a parameter that is about to be removed
completely. Most users will probably need to book keep those so that they
don't leave behinfd any non default def ssa names belonging to them. */
unsigned remove_param : 1;
/* The parameter is to be passed by reference. */
unsigned by_ref : 1;
};
typedef struct ipa_parm_adjustment ipa_parm_adjustment_t;
typedef vec<ipa_parm_adjustment_t> ipa_parm_adjustment_vec;
vec<tree> ipa_get_vector_of_formal_parms (tree fndecl);
void ipa_modify_formal_parameters (tree fndecl, ipa_parm_adjustment_vec,
const char *);
void ipa_modify_call_arguments (struct cgraph_edge *, gimple,
ipa_parm_adjustment_vec);
ipa_parm_adjustment_vec ipa_combine_adjustments (ipa_parm_adjustment_vec,
ipa_parm_adjustment_vec);
void ipa_dump_param_adjustments (FILE *, ipa_parm_adjustment_vec, tree);
void ipa_dump_agg_replacement_values (FILE *f,
struct ipa_agg_replacement_value *av);
void ipa_prop_write_jump_functions (void);
void ipa_prop_read_jump_functions (void);
void ipa_prop_write_all_agg_replacement (void);
void ipa_prop_read_all_agg_replacement (void);
void ipa_update_after_lto_read (void);
int ipa_get_param_decl_index (struct ipa_node_params *, tree);
tree ipa_value_from_jfunc (struct ipa_node_params *info,
struct ipa_jump_func *jfunc);
unsigned int ipcp_transform_function (struct cgraph_node *node);
/* From tree-sra.c: */
tree build_ref_for_offset (location_t, tree, HOST_WIDE_INT, tree,
gimple_stmt_iterator *, bool);
#endif /* IPA_PROP_H */

View File

@ -0,0 +1,108 @@
/* IPA reference lists.
Copyright (C) 2010-2013 Free Software Foundation, Inc.
Contributed by Jan Hubicka
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
/* Return callgraph node REF is referring. */
static inline struct cgraph_node *
ipa_ref_node (struct ipa_ref *ref)
{
return cgraph (ref->referred);
}
/* Return varpool node REF is referring. */
static inline struct varpool_node *
ipa_ref_varpool_node (struct ipa_ref *ref)
{
return varpool (ref->referred);
}
/* Return cgraph node REF is in. */
static inline struct cgraph_node *
ipa_ref_referring_node (struct ipa_ref *ref)
{
return cgraph (ref->referring);
}
/* Return varpool node REF is in. */
static inline struct varpool_node *
ipa_ref_referring_varpool_node (struct ipa_ref *ref)
{
return varpool (ref->referring);
}
/* Return reference list REF is in. */
static inline struct ipa_ref_list *
ipa_ref_referring_ref_list (struct ipa_ref *ref)
{
return &ref->referring->symbol.ref_list;
}
/* Return reference list REF is in. */
static inline struct ipa_ref_list *
ipa_ref_referred_ref_list (struct ipa_ref *ref)
{
return &ref->referred->symbol.ref_list;
}
/* Return first reference in LIST or NULL if empty. */
static inline struct ipa_ref *
ipa_ref_list_first_reference (struct ipa_ref_list *list)
{
if (!vec_safe_length (list->references))
return NULL;
return &(*list->references)[0];
}
/* Return first referring ref in LIST or NULL if empty. */
static inline struct ipa_ref *
ipa_ref_list_first_referring (struct ipa_ref_list *list)
{
if (!list->referring.length ())
return NULL;
return list->referring[0];
}
/* Clear reference list. */
static inline void
ipa_empty_ref_list (struct ipa_ref_list *list)
{
list->referring.create (0);
list->references = NULL;
}
/* Clear reference list. */
static inline unsigned int
ipa_ref_list_nreferences (struct ipa_ref_list *list)
{
return vec_safe_length (list->references);
}
#define ipa_ref_list_reference_iterate(L,I,P) \
vec_safe_iterate ((L)->references, (I), &(P))
#define ipa_ref_list_referring_iterate(L,I,P) \
(L)->referring.iterate ((I), &(P))

73
src/include/ipa-ref.h Normal file
View File

@ -0,0 +1,73 @@
/* IPA reference lists.
Copyright (C) 2010-2013 Free Software Foundation, Inc.
Contributed by Jan Hubicka
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
struct cgraph_node;
struct varpool_node;
union symtab_node_def;
typedef union symtab_node_def *symtab_node;
typedef const union symtab_node_def *const_symtab_node;
/* How the reference is done. */
enum GTY(()) ipa_ref_use
{
IPA_REF_LOAD,
IPA_REF_STORE,
IPA_REF_ADDR,
IPA_REF_ALIAS
};
/* Record of reference in callgraph or varpool. */
struct GTY(()) ipa_ref
{
symtab_node referring;
symtab_node referred;
gimple stmt;
unsigned int referred_index;
ENUM_BITFIELD (ipa_ref_use) use:2;
};
typedef struct ipa_ref ipa_ref_t;
typedef struct ipa_ref *ipa_ref_ptr;
/* List of references. This is stored in both callgraph and varpool nodes. */
struct GTY(()) ipa_ref_list
{
/* Store actual references in references vector. */
vec<ipa_ref_t, va_gc> *references;
/* Referring is vector of pointers to references. It must not live in GGC space
or GGC will try to mark middle of references vectors. */
vec<ipa_ref_ptr> GTY((skip)) referring;
};
struct ipa_ref * ipa_record_reference (symtab_node,
symtab_node,
enum ipa_ref_use, gimple);
void ipa_remove_reference (struct ipa_ref *);
void ipa_remove_all_references (struct ipa_ref_list *);
void ipa_remove_all_referring (struct ipa_ref_list *);
void ipa_dump_references (FILE *, struct ipa_ref_list *);
void ipa_dump_referring (FILE *, struct ipa_ref_list *);
void ipa_clone_references (symtab_node, struct ipa_ref_list *);
void ipa_clone_referring (symtab_node, struct ipa_ref_list *);
bool ipa_ref_cannot_lead_to_return (struct ipa_ref *);
bool ipa_ref_has_aliases_p (struct ipa_ref_list *);

Some files were not shown because too many files have changed in this diff Show More