Commit 6d9901e7 by Zdenek Dvorak Committed by Zdenek Dvorak

Makefile.in (rtl-profile.o, [...]): Add GCC_H dependency.

	* Makefile.in (rtl-profile.o, value-prof.o): Add GCC_H dependency.
	* common.opt (fspeculative-prefetching): New.
	* flags.h (flag_speculative_prefetching_set): Declare.
	* gcov-io.c (gcov_write_counter, gcov_read_counter): Allow negative
	values.
	* opts.c (flag_sepculative_prefetching_set): New variable.
	(common_handle_option): Handle -fspeculative-prefetching.
	* passes.c (rest_of_compilation): Ditto.
	* profile.c (instrument_values, compute_value_histograms, branch_prob):
	Use vectors instead of arrays.
	* toplev.c (process_options): Handle -fspeculative-prefetching.
	* rtl-profile.c: Include ggc.h.
	(rtl_gen_interval_profiler, rtl_gen_pow2_profiler,
	rtl_gen_one_value_profiler_no_edge_manipulation,
	rtl_gen_one_value_profiler, rtl_gen_const_delta_profiler): Type of
	argument changed.
	* tree-profile.c (tree_gen_interval_profiler, tree_gen_pow2_profiler,
	tree_gen_one_value_profiler, tree_gen_const_delta_profiler): Type of
	argument changed.
	* value-prof.c: Include ggc.h.
	(NOPREFETCH_RANGE_MIN, NOPREFETCH_RANGE_MAX): New
	macros.
	(insn_prefetch_values_to_profile, find_mem_reference_1,
	find_mem_reference_2, find_mem_reference, gen_speculative_prefetch,
	speculative_prefetching_transform): New.
	(value_profile_transformations): Call speculative_prefetching_transform.
	(insn_values_to_profile): Call insn_prefetch_values_to_profile.
	(insn_divmod_values_to_profile, rtl_find_values_to_profile,
	tree_find_values_to_profile, find_values to profile): Use vectors
	instead of arrays.
	(free_profiled_values): Removed.
	* value-prof.h (struct histogram_value): Renamed to
	struct histogram_value_t.
	(histogram_value, histogram_values): New types.
	(find_values_to_profile): Declaration changed.
	(free_profiled_values): Removed.
	(struct profile_hooks): Type of argument of the hooks changed to
	histogram_value.
	* doc/invoke.texi (-fspeculative-prefetching): Document.

From-SVN: r86930
parent d7fe1183
2004-09-01 Zdenek Dvorak <rakdver@atrey.karlin.mff.cuni.cz> 2004-09-01 Zdenek Dvorak <rakdver@atrey.karlin.mff.cuni.cz>
* Makefile.in (rtl-profile.o, value-prof.o): Add GCC_H dependency.
* common.opt (fspeculative-prefetching): New.
* flags.h (flag_speculative_prefetching_set): Declare.
* gcov-io.c (gcov_write_counter, gcov_read_counter): Allow negative
values.
* opts.c (flag_sepculative_prefetching_set): New variable.
(common_handle_option): Handle -fspeculative-prefetching.
* passes.c (rest_of_compilation): Ditto.
* profile.c (instrument_values, compute_value_histograms, branch_prob):
Use vectors instead of arrays.
* toplev.c (process_options): Handle -fspeculative-prefetching.
* rtl-profile.c: Include ggc.h.
(rtl_gen_interval_profiler, rtl_gen_pow2_profiler,
rtl_gen_one_value_profiler_no_edge_manipulation,
rtl_gen_one_value_profiler, rtl_gen_const_delta_profiler): Type of
argument changed.
* tree-profile.c (tree_gen_interval_profiler, tree_gen_pow2_profiler,
tree_gen_one_value_profiler, tree_gen_const_delta_profiler): Type of
argument changed.
* value-prof.c: Include ggc.h.
(NOPREFETCH_RANGE_MIN, NOPREFETCH_RANGE_MAX): New
macros.
(insn_prefetch_values_to_profile, find_mem_reference_1,
find_mem_reference_2, find_mem_reference, gen_speculative_prefetch,
speculative_prefetching_transform): New.
(value_profile_transformations): Call speculative_prefetching_transform.
(insn_values_to_profile): Call insn_prefetch_values_to_profile.
(insn_divmod_values_to_profile, rtl_find_values_to_profile,
tree_find_values_to_profile, find_values to profile): Use vectors
instead of arrays.
(free_profiled_values): Removed.
* value-prof.h (struct histogram_value): Renamed to
struct histogram_value_t.
(histogram_value, histogram_values): New types.
(find_values_to_profile): Declaration changed.
(free_profiled_values): Removed.
(struct profile_hooks): Type of argument of the hooks changed to
histogram_value.
* doc/invoke.texi (-fspeculative-prefetching): Document.
2004-09-01 Zdenek Dvorak <rakdver@atrey.karlin.mff.cuni.cz>
PR rtl-optimization/16408 PR rtl-optimization/16408
* gcse.c (replace_store_insn): Fix LIBCALL/RETVAL notes. * gcse.c (replace_store_insn): Fix LIBCALL/RETVAL notes.
......
...@@ -1959,10 +1959,10 @@ tree-profile.o : tree-profile.c $(CONFIG_H) $(SYSTEM_H) coretypes.h \ ...@@ -1959,10 +1959,10 @@ tree-profile.o : tree-profile.c $(CONFIG_H) $(SYSTEM_H) coretypes.h \
tree-pass.h $(TREE_FLOW_H) $(TIMEVAR_H) tree-pass.h $(TREE_FLOW_H) $(TIMEVAR_H)
rtl-profile.o : tree-profile.c $(CONFIG_H) $(SYSTEM_H) coretypes.h \ rtl-profile.o : tree-profile.c $(CONFIG_H) $(SYSTEM_H) coretypes.h \
$(TM_H) $(RTL_H) $(TREE_H) $(FLAGS_H) output.h $(REGS_H) $(EXPR_H) function.h \ $(TM_H) $(RTL_H) $(TREE_H) $(FLAGS_H) output.h $(REGS_H) $(EXPR_H) function.h \
toplev.h $(BASIC_BLOCK_H) $(COVERAGE_H) $(TREE_FLOW_H) value-prof.h toplev.h $(BASIC_BLOCK_H) $(COVERAGE_H) $(TREE_FLOW_H) value-prof.h $(GGC_H)
value-prof.o : value-prof.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(RTL_H) \ value-prof.o : value-prof.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(RTL_H) \
$(BASIC_BLOCK_H) hard-reg-set.h value-prof.h $(EXPR_H) output.h $(FLAGS_H) \ $(BASIC_BLOCK_H) hard-reg-set.h value-prof.h $(EXPR_H) output.h $(FLAGS_H) \
$(RECOG_H) insn-config.h $(OPTABS_H) $(REGS_H) $(RECOG_H) insn-config.h $(OPTABS_H) $(REGS_H) $(GGC_H)
loop.o : loop.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(RTL_H) $(FLAGS_H) $(LOOP_H) \ loop.o : loop.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(RTL_H) $(FLAGS_H) $(LOOP_H) \
insn-config.h $(REGS_H) hard-reg-set.h $(RECOG_H) $(EXPR_H) \ insn-config.h $(REGS_H) hard-reg-set.h $(RECOG_H) $(EXPR_H) \
real.h $(PREDICT_H) $(BASIC_BLOCK_H) function.h $(CFGLOOP_H) \ real.h $(PREDICT_H) $(BASIC_BLOCK_H) function.h $(CFGLOOP_H) \
......
...@@ -752,6 +752,10 @@ fsingle-precision-constant ...@@ -752,6 +752,10 @@ fsingle-precision-constant
Common Report Var(flag_single_precision_constant) Common Report Var(flag_single_precision_constant)
Convert floating point constants to single precision constants Convert floating point constants to single precision constants
fspeculative-prefetching
Common Report Var(flag_speculative_prefetching)
Use value profiling for speculative prefetching
; Emit code to probe the stack, to help detect stack overflow; also ; Emit code to probe the stack, to help detect stack overflow; also
; may cause large objects to be allocated dynamically. ; may cause large objects to be allocated dynamically.
fstack-check fstack-check
......
...@@ -311,7 +311,7 @@ Objective-C and Objective-C++ Dialects}. ...@@ -311,7 +311,7 @@ Objective-C and Objective-C++ Dialects}.
-fsched-stalled-insns=@var{n} -sched-stalled-insns-dep=@var{n} @gol -fsched-stalled-insns=@var{n} -sched-stalled-insns-dep=@var{n} @gol
-fsched2-use-superblocks @gol -fsched2-use-superblocks @gol
-fsched2-use-traces -freschedule-modulo-scheduled-loops @gol -fsched2-use-traces -freschedule-modulo-scheduled-loops @gol
-fsignaling-nans -fsingle-precision-constant @gol -fsignaling-nans -fsingle-precision-constant -fspeculative-prefetching @gol
-fstrength-reduce -fstrict-aliasing -ftracer -fthread-jumps @gol -fstrength-reduce -fstrict-aliasing -ftracer -fthread-jumps @gol
-funroll-all-loops -funroll-loops -fpeel-loops @gol -funroll-all-loops -funroll-loops -fpeel-loops @gol
-funswitch-loops -fold-unroll-loops -fold-unroll-all-loops @gol -funswitch-loops -fold-unroll-loops -fold-unroll-all-loops @gol
...@@ -5011,6 +5011,21 @@ and actually performs the optimizations based on them. ...@@ -5011,6 +5011,21 @@ and actually performs the optimizations based on them.
Currently the optimizations include specialization of division operation Currently the optimizations include specialization of division operation
using the knowledge about the value of the denominator. using the knowledge about the value of the denominator.
@item -fspeculative-prefetching
@opindex fspeculative-prefetching
If combined with @option{-fprofile-arcs}, it instructs the compiler to add
a code to gather information about addresses of memory references in the
program.
With @option{-fbranch-probabilities}, it reads back the data gathered
and issues prefetch instructions according to them. In addition to the opportunities
noticed by @option{-fprefetch-loop-arrays}, it also notices more complicated
memory access patterns -- for example accesses to the data stored in linked
list whose elements are usually allocated sequentially.
In order to prevent issuing double prefetches, usage of
@option{-fspeculative-prefetching} implies @option{-fno-prefetch-loop-arrays}.
Enabled with @option{-fprofile-generate} and @option{-fprofile-use}. Enabled with @option{-fprofile-generate} and @option{-fprofile-use}.
@item -frename-registers @item -frename-registers
......
...@@ -257,6 +257,10 @@ extern int flag_remove_unreachable_functions; ...@@ -257,6 +257,10 @@ extern int flag_remove_unreachable_functions;
/* Nonzero if we should track variables. */ /* Nonzero if we should track variables. */
extern int flag_var_tracking; extern int flag_var_tracking;
/* True if flag_speculative_prefetching was set by user. Used to suppress
warning message in case flag was set by -fprofile-{generate,use}. */
extern bool flag_speculative_prefetching_set;
/* A string that's used when a random name is required. NULL means /* A string that's used when a random name is required. NULL means
to make it really random. */ to make it really random. */
......
...@@ -268,9 +268,6 @@ gcov_write_counter (gcov_type value) ...@@ -268,9 +268,6 @@ gcov_write_counter (gcov_type value)
buffer[1] = (gcov_unsigned_t) (value >> 32); buffer[1] = (gcov_unsigned_t) (value >> 32);
else else
buffer[1] = 0; buffer[1] = 0;
if (value < 0)
gcov_var.error = -1;
} }
#endif /* IN_LIBGCOV */ #endif /* IN_LIBGCOV */
...@@ -453,9 +450,7 @@ gcov_read_counter (void) ...@@ -453,9 +450,7 @@ gcov_read_counter (void)
value |= ((gcov_type) from_file (buffer[1])) << 32; value |= ((gcov_type) from_file (buffer[1])) << 32;
else if (buffer[1]) else if (buffer[1])
gcov_var.error = -1; gcov_var.error = -1;
if (value < 0)
gcov_var.error = -1;
return value; return value;
} }
......
...@@ -93,6 +93,7 @@ static const char undocumented_msg[] = N_("This switch lacks documentation"); ...@@ -93,6 +93,7 @@ static const char undocumented_msg[] = N_("This switch lacks documentation");
static bool profile_arc_flag_set, flag_profile_values_set; static bool profile_arc_flag_set, flag_profile_values_set;
static bool flag_unroll_loops_set, flag_tracer_set; static bool flag_unroll_loops_set, flag_tracer_set;
static bool flag_value_profile_transformations_set; static bool flag_value_profile_transformations_set;
bool flag_speculative_prefetching_set;
static bool flag_peel_loops_set, flag_branch_probabilities_set; static bool flag_peel_loops_set, flag_branch_probabilities_set;
/* Input file names. */ /* Input file names. */
...@@ -830,6 +831,10 @@ common_handle_option (size_t scode, const char *arg, int value) ...@@ -830,6 +831,10 @@ common_handle_option (size_t scode, const char *arg, int value)
flag_tracer = value; flag_tracer = value;
if (!flag_value_profile_transformations_set) if (!flag_value_profile_transformations_set)
flag_value_profile_transformations = value; flag_value_profile_transformations = value;
#ifdef HAVE_prefetch
if (!flag_speculative_prefetching_set)
flag_speculative_prefetching = value;
#endif
break; break;
case OPT_fprofile_generate: case OPT_fprofile_generate:
...@@ -839,6 +844,10 @@ common_handle_option (size_t scode, const char *arg, int value) ...@@ -839,6 +844,10 @@ common_handle_option (size_t scode, const char *arg, int value)
flag_profile_values = value; flag_profile_values = value;
if (!flag_value_profile_transformations_set) if (!flag_value_profile_transformations_set)
flag_value_profile_transformations = value; flag_value_profile_transformations = value;
#ifdef HAVE_prefetch
if (!flag_speculative_prefetching_set)
flag_speculative_prefetching = value;
#endif
break; break;
case OPT_fprofile_values: case OPT_fprofile_values:
...@@ -861,7 +870,11 @@ common_handle_option (size_t scode, const char *arg, int value) ...@@ -861,7 +870,11 @@ common_handle_option (size_t scode, const char *arg, int value)
break; break;
case OPT_fvpt: case OPT_fvpt:
flag_value_profile_transformations_set = value; flag_value_profile_transformations_set = true;
break;
case OPT_fspeculative_prefetching:
flag_speculative_prefetching_set = true;
break; break;
case OPT_frandom_seed: case OPT_frandom_seed:
......
...@@ -1820,7 +1820,8 @@ rest_of_compilation (void) ...@@ -1820,7 +1820,8 @@ rest_of_compilation (void)
if (flag_branch_probabilities if (flag_branch_probabilities
&& flag_profile_values && flag_profile_values
&& flag_value_profile_transformations) && (flag_value_profile_transformations
|| flag_speculative_prefetching))
rest_of_handle_value_profile_transformations (); rest_of_handle_value_profile_transformations ();
/* Remove the death notes created for vpt. */ /* Remove the death notes created for vpt. */
......
...@@ -119,9 +119,9 @@ static int total_num_branches; ...@@ -119,9 +119,9 @@ static int total_num_branches;
/* Forward declarations. */ /* Forward declarations. */
static void find_spanning_tree (struct edge_list *); static void find_spanning_tree (struct edge_list *);
static unsigned instrument_edges (struct edge_list *); static unsigned instrument_edges (struct edge_list *);
static void instrument_values (unsigned, struct histogram_value *); static void instrument_values (histogram_values);
static void compute_branch_probabilities (void); static void compute_branch_probabilities (void);
static void compute_value_histograms (unsigned, struct histogram_value *); static void compute_value_histograms (histogram_values);
static gcov_type * get_exec_counts (void); static gcov_type * get_exec_counts (void);
static basic_block find_group (basic_block); static basic_block find_group (basic_block);
static void union_groups (basic_block, basic_block); static void union_groups (basic_block, basic_block);
...@@ -166,17 +166,18 @@ instrument_edges (struct edge_list *el) ...@@ -166,17 +166,18 @@ instrument_edges (struct edge_list *el)
return num_instr_edges; return num_instr_edges;
} }
/* Add code to measure histograms list of VALUES of length N_VALUES. */ /* Add code to measure histograms for values in list VALUES. */
static void static void
instrument_values (unsigned n_values, struct histogram_value *values) instrument_values (histogram_values values)
{ {
unsigned i, t; unsigned i, t;
/* Emit code to generate the histograms before the insns. */ /* Emit code to generate the histograms before the insns. */
for (i = 0; i < n_values; i++) for (i = 0; i < VEC_length (histogram_value, values); i++)
{ {
switch (values[i].type) histogram_value hist = VEC_index (histogram_value, values, i);
switch (hist->type)
{ {
case HIST_TYPE_INTERVAL: case HIST_TYPE_INTERVAL:
t = GCOV_COUNTER_V_INTERVAL; t = GCOV_COUNTER_V_INTERVAL;
...@@ -197,25 +198,25 @@ instrument_values (unsigned n_values, struct histogram_value *values) ...@@ -197,25 +198,25 @@ instrument_values (unsigned n_values, struct histogram_value *values)
default: default:
abort (); abort ();
} }
if (!coverage_counter_alloc (t, values[i].n_counters)) if (!coverage_counter_alloc (t, hist->n_counters))
continue; continue;
switch (values[i].type) switch (hist->type)
{ {
case HIST_TYPE_INTERVAL: case HIST_TYPE_INTERVAL:
(profile_hooks->gen_interval_profiler) (values + i, t, 0); (profile_hooks->gen_interval_profiler) (hist, t, 0);
break; break;
case HIST_TYPE_POW2: case HIST_TYPE_POW2:
(profile_hooks->gen_pow2_profiler) (values + i, t, 0); (profile_hooks->gen_pow2_profiler) (hist, t, 0);
break; break;
case HIST_TYPE_SINGLE_VALUE: case HIST_TYPE_SINGLE_VALUE:
(profile_hooks->gen_one_value_profiler) (values + i, t, 0); (profile_hooks->gen_one_value_profiler) (hist, t, 0);
break; break;
case HIST_TYPE_CONST_DELTA: case HIST_TYPE_CONST_DELTA:
(profile_hooks->gen_const_delta_profiler) (values + i, t, 0); (profile_hooks->gen_const_delta_profiler) (hist, t, 0);
break; break;
default: default:
...@@ -613,22 +614,27 @@ compute_branch_probabilities (void) ...@@ -613,22 +614,27 @@ compute_branch_probabilities (void)
free_aux_for_blocks (); free_aux_for_blocks ();
} }
/* Load value histograms for N_VALUES values whose description is stored /* Load value histograms values whose description is stored in VALUES array
in VALUES array from .da file. */ from .da file. */
static void static void
compute_value_histograms (unsigned n_values, struct histogram_value *values) compute_value_histograms (histogram_values values)
{ {
unsigned i, j, t, any; unsigned i, j, t, any;
unsigned n_histogram_counters[GCOV_N_VALUE_COUNTERS]; unsigned n_histogram_counters[GCOV_N_VALUE_COUNTERS];
gcov_type *histogram_counts[GCOV_N_VALUE_COUNTERS]; gcov_type *histogram_counts[GCOV_N_VALUE_COUNTERS];
gcov_type *act_count[GCOV_N_VALUE_COUNTERS]; gcov_type *act_count[GCOV_N_VALUE_COUNTERS];
gcov_type *aact_count; gcov_type *aact_count;
histogram_value hist;
for (t = 0; t < GCOV_N_VALUE_COUNTERS; t++) for (t = 0; t < GCOV_N_VALUE_COUNTERS; t++)
n_histogram_counters[t] = 0; n_histogram_counters[t] = 0;
for (i = 0; i < n_values; i++) for (i = 0; i < VEC_length (histogram_value, values); i++)
n_histogram_counters[(int) (values[i].type)] += values[i].n_counters; {
hist = VEC_index (histogram_value, values, i);
n_histogram_counters[(int) hist->type] += hist->n_counters;
}
any = 0; any = 0;
for (t = 0; t < GCOV_N_VALUE_COUNTERS; t++) for (t = 0; t < GCOV_N_VALUE_COUNTERS; t++)
...@@ -649,25 +655,27 @@ compute_value_histograms (unsigned n_values, struct histogram_value *values) ...@@ -649,25 +655,27 @@ compute_value_histograms (unsigned n_values, struct histogram_value *values)
if (!any) if (!any)
return; return;
for (i = 0; i < n_values; i++) for (i = 0; i < VEC_length (histogram_value, values); i++)
{ {
rtx hist_list = NULL_RTX; rtx hist_list = NULL_RTX;
t = (int) (values[i].type);
hist = VEC_index (histogram_value, values, i);
t = (int) hist->type;
/* FIXME: make this work for trees. */ /* FIXME: make this work for trees. */
if (!ir_type ()) if (!ir_type ())
{ {
aact_count = act_count[t]; aact_count = act_count[t];
act_count[t] += values[i].n_counters; act_count[t] += hist->n_counters;
for (j = values[i].n_counters; j > 0; j--) for (j = hist->n_counters; j > 0; j--)
hist_list = alloc_EXPR_LIST (0, GEN_INT (aact_count[j - 1]), hist_list = alloc_EXPR_LIST (0, GEN_INT (aact_count[j - 1]),
hist_list); hist_list);
hist_list = alloc_EXPR_LIST (0, hist_list = alloc_EXPR_LIST (0,
copy_rtx ((rtx)values[i].value), hist_list); copy_rtx ((rtx) hist->value), hist_list);
hist_list = alloc_EXPR_LIST (0, GEN_INT (values[i].type), hist_list); hist_list = alloc_EXPR_LIST (0, GEN_INT (hist->type), hist_list);
REG_NOTES ((rtx)values[i].insn) = REG_NOTES ((rtx) hist->insn) =
alloc_EXPR_LIST (REG_VALUE_PROFILE, hist_list, alloc_EXPR_LIST (REG_VALUE_PROFILE, hist_list,
REG_NOTES ((rtx)values[i].insn)); REG_NOTES ((rtx) hist->insn));
} }
} }
...@@ -700,8 +708,7 @@ branch_prob (void) ...@@ -700,8 +708,7 @@ branch_prob (void)
unsigned num_edges, ignored_edges; unsigned num_edges, ignored_edges;
unsigned num_instrumented; unsigned num_instrumented;
struct edge_list *el; struct edge_list *el;
unsigned n_values = 0; histogram_values values = NULL;
struct histogram_value *values = NULL;
total_num_times_called++; total_num_times_called++;
...@@ -960,13 +967,13 @@ branch_prob (void) ...@@ -960,13 +967,13 @@ branch_prob (void)
#undef BB_TO_GCOV_INDEX #undef BB_TO_GCOV_INDEX
if (flag_profile_values) if (flag_profile_values)
find_values_to_profile (&n_values, &values); find_values_to_profile (&values);
if (flag_branch_probabilities) if (flag_branch_probabilities)
{ {
compute_branch_probabilities (); compute_branch_probabilities ();
if (flag_profile_values) if (flag_profile_values)
compute_value_histograms (n_values, values); compute_value_histograms (values);
} }
remove_fake_edges (); remove_fake_edges ();
...@@ -981,7 +988,7 @@ branch_prob (void) ...@@ -981,7 +988,7 @@ branch_prob (void)
abort (); abort ();
if (flag_profile_values) if (flag_profile_values)
instrument_values (n_values, values); instrument_values (values);
/* Commit changes done by instrumentation. */ /* Commit changes done by instrumentation. */
if (ir_type ()) if (ir_type ())
......
...@@ -62,6 +62,7 @@ Software Foundation, 59 Temple Place - Suite 330, Boston, MA ...@@ -62,6 +62,7 @@ Software Foundation, 59 Temple Place - Suite 330, Boston, MA
#include "coverage.h" #include "coverage.h"
#include "value-prof.h" #include "value-prof.h"
#include "tree.h" #include "tree.h"
#include "ggc.h"
/* Output instructions as RTL to increment the edge execution count. */ /* Output instructions as RTL to increment the edge execution count. */
...@@ -93,8 +94,7 @@ rtl_gen_edge_profiler (int edgeno, edge e) ...@@ -93,8 +94,7 @@ rtl_gen_edge_profiler (int edgeno, edge e)
section for counters, BASE is offset of the counter position. */ section for counters, BASE is offset of the counter position. */
static void static void
rtl_gen_interval_profiler (struct histogram_value *value, unsigned tag, rtl_gen_interval_profiler (histogram_value value, unsigned tag, unsigned base)
unsigned base)
{ {
unsigned gcov_size = tree_low_cst (TYPE_SIZE (GCOV_TYPE_NODE), 1); unsigned gcov_size = tree_low_cst (TYPE_SIZE (GCOV_TYPE_NODE), 1);
enum machine_mode mode = mode_for_size (gcov_size, MODE_INT, 0); enum machine_mode mode = mode_for_size (gcov_size, MODE_INT, 0);
...@@ -196,8 +196,7 @@ rtl_gen_interval_profiler (struct histogram_value *value, unsigned tag, ...@@ -196,8 +196,7 @@ rtl_gen_interval_profiler (struct histogram_value *value, unsigned tag,
section for counters, BASE is offset of the counter position. */ section for counters, BASE is offset of the counter position. */
static void static void
rtl_gen_pow2_profiler (struct histogram_value *value, unsigned tag, rtl_gen_pow2_profiler (histogram_value value, unsigned tag, unsigned base)
unsigned base)
{ {
unsigned gcov_size = tree_low_cst (TYPE_SIZE (GCOV_TYPE_NODE), 1); unsigned gcov_size = tree_low_cst (TYPE_SIZE (GCOV_TYPE_NODE), 1);
enum machine_mode mode = mode_for_size (gcov_size, MODE_INT, 0); enum machine_mode mode = mode_for_size (gcov_size, MODE_INT, 0);
...@@ -272,8 +271,8 @@ rtl_gen_pow2_profiler (struct histogram_value *value, unsigned tag, ...@@ -272,8 +271,8 @@ rtl_gen_pow2_profiler (struct histogram_value *value, unsigned tag,
section for counters, BASE is offset of the counter position. */ section for counters, BASE is offset of the counter position. */
static rtx static rtx
rtl_gen_one_value_profiler_no_edge_manipulation (struct histogram_value *value, rtl_gen_one_value_profiler_no_edge_manipulation (histogram_value value,
unsigned tag, unsigned base) unsigned tag, unsigned base)
{ {
unsigned gcov_size = tree_low_cst (TYPE_SIZE (GCOV_TYPE_NODE), 1); unsigned gcov_size = tree_low_cst (TYPE_SIZE (GCOV_TYPE_NODE), 1);
enum machine_mode mode = mode_for_size (gcov_size, MODE_INT, 0); enum machine_mode mode = mode_for_size (gcov_size, MODE_INT, 0);
...@@ -351,8 +350,7 @@ rtl_gen_one_value_profiler_no_edge_manipulation (struct histogram_value *value, ...@@ -351,8 +350,7 @@ rtl_gen_one_value_profiler_no_edge_manipulation (struct histogram_value *value,
section for counters, BASE is offset of the counter position. */ section for counters, BASE is offset of the counter position. */
static void static void
rtl_gen_one_value_profiler (struct histogram_value *value, unsigned tag, rtl_gen_one_value_profiler (histogram_value value, unsigned tag, unsigned base)
unsigned base)
{ {
edge e = split_block (BLOCK_FOR_INSN ((rtx)value->insn), edge e = split_block (BLOCK_FOR_INSN ((rtx)value->insn),
PREV_INSN ((rtx)value->insn)); PREV_INSN ((rtx)value->insn));
...@@ -368,10 +366,9 @@ rtl_gen_one_value_profiler (struct histogram_value *value, unsigned tag, ...@@ -368,10 +366,9 @@ rtl_gen_one_value_profiler (struct histogram_value *value, unsigned tag,
section for counters, BASE is offset of the counter position. */ section for counters, BASE is offset of the counter position. */
static void static void
rtl_gen_const_delta_profiler (struct histogram_value *value, unsigned tag, rtl_gen_const_delta_profiler (histogram_value value, unsigned tag, unsigned base)
unsigned base)
{ {
struct histogram_value one_value_delta; histogram_value one_value_delta;
unsigned gcov_size = tree_low_cst (TYPE_SIZE (GCOV_TYPE_NODE), 1); unsigned gcov_size = tree_low_cst (TYPE_SIZE (GCOV_TYPE_NODE), 1);
enum machine_mode mode = mode_for_size (gcov_size, MODE_INT, 0); enum machine_mode mode = mode_for_size (gcov_size, MODE_INT, 0);
rtx stored_value_ref, stored_value, tmp, uval; rtx stored_value_ref, stored_value, tmp, uval;
...@@ -393,13 +390,14 @@ rtl_gen_const_delta_profiler (struct histogram_value *value, unsigned tag, ...@@ -393,13 +390,14 @@ rtl_gen_const_delta_profiler (struct histogram_value *value, unsigned tag,
copy_rtx (uval), copy_rtx (stored_value), copy_rtx (uval), copy_rtx (stored_value),
NULL_RTX, 0, OPTAB_WIDEN); NULL_RTX, 0, OPTAB_WIDEN);
one_value_delta.value = tmp; one_value_delta = ggc_alloc (sizeof (*one_value_delta));
one_value_delta.mode = mode; one_value_delta->value = tmp;
one_value_delta.seq = NULL_RTX; one_value_delta->mode = mode;
one_value_delta.insn = value->insn; one_value_delta->seq = NULL_RTX;
one_value_delta.type = HIST_TYPE_SINGLE_VALUE; one_value_delta->insn = value->insn;
emit_insn (rtl_gen_one_value_profiler_no_edge_manipulation (&one_value_delta, one_value_delta->type = HIST_TYPE_SINGLE_VALUE;
tag, base + 1)); emit_insn (rtl_gen_one_value_profiler_no_edge_manipulation (one_value_delta,
tag, base + 1));
emit_move_insn (copy_rtx (stored_value), uval); emit_move_insn (copy_rtx (stored_value), uval);
sequence = get_insns (); sequence = get_insns ();
end_sequence (); end_sequence ();
......
...@@ -1730,6 +1730,17 @@ process_options (void) ...@@ -1730,6 +1730,17 @@ process_options (void)
if (flag_value_profile_transformations) if (flag_value_profile_transformations)
flag_profile_values = 1; flag_profile_values = 1;
/* Speculative prefetching implies the value profiling. We also switch off
the prefetching in the loop optimizer, so that we do not emit double
prefetches. TODO -- we should teach these two to cooperate; the loop
based prefetching may sometimes do a better job, especially in connection
with reuse analysis. */
if (flag_speculative_prefetching)
{
flag_profile_values = 1;
flag_prefetch_loop_arrays = 0;
}
/* Warn about options that are not supported on this machine. */ /* Warn about options that are not supported on this machine. */
#ifndef INSN_SCHEDULING #ifndef INSN_SCHEDULING
if (flag_schedule_insns || flag_schedule_insns_after_reload) if (flag_schedule_insns || flag_schedule_insns_after_reload)
...@@ -1898,12 +1909,24 @@ process_options (void) ...@@ -1898,12 +1909,24 @@ process_options (void)
warning ("-fprefetch-loop-arrays not supported for this target"); warning ("-fprefetch-loop-arrays not supported for this target");
flag_prefetch_loop_arrays = 0; flag_prefetch_loop_arrays = 0;
} }
if (flag_speculative_prefetching)
{
if (flag_speculative_prefetching_set)
WARNIng ("-fspeculative-prefetching not supported for this target");
flag_speculative_prefetching = 0;
}
#else #else
if (flag_prefetch_loop_arrays && !HAVE_prefetch) if (flag_prefetch_loop_arrays && !HAVE_prefetch)
{ {
warning ("-fprefetch-loop-arrays not supported for this target (try -march switches)"); warning ("-fprefetch-loop-arrays not supported for this target (try -march switches)");
flag_prefetch_loop_arrays = 0; flag_prefetch_loop_arrays = 0;
} }
if (flag_speculative_prefetching && !HAVE_prefetch)
{
if (flag_speculative_prefetching_set)
warning ("-fspeculative-prefetching not supported for this target (try -march switches)");
flag_speculative_prefetching = 0;
}
#endif #endif
/* This combination of options isn't handled for i386 targets and doesn't /* This combination of options isn't handled for i386 targets and doesn't
......
...@@ -94,7 +94,7 @@ tree_gen_edge_profiler (int edgeno, edge e) ...@@ -94,7 +94,7 @@ tree_gen_edge_profiler (int edgeno, edge e)
tag of the section for counters, BASE is offset of the counter position. */ tag of the section for counters, BASE is offset of the counter position. */
static void static void
tree_gen_interval_profiler (struct histogram_value *value ATTRIBUTE_UNUSED, tree_gen_interval_profiler (histogram_value value ATTRIBUTE_UNUSED,
unsigned tag ATTRIBUTE_UNUSED, unsigned tag ATTRIBUTE_UNUSED,
unsigned base ATTRIBUTE_UNUSED) unsigned base ATTRIBUTE_UNUSED)
{ {
...@@ -107,7 +107,7 @@ tree_gen_interval_profiler (struct histogram_value *value ATTRIBUTE_UNUSED, ...@@ -107,7 +107,7 @@ tree_gen_interval_profiler (struct histogram_value *value ATTRIBUTE_UNUSED,
of the section for counters, BASE is offset of the counter position. */ of the section for counters, BASE is offset of the counter position. */
static void static void
tree_gen_pow2_profiler (struct histogram_value *value ATTRIBUTE_UNUSED, tree_gen_pow2_profiler (histogram_value value ATTRIBUTE_UNUSED,
unsigned tag ATTRIBUTE_UNUSED, unsigned tag ATTRIBUTE_UNUSED,
unsigned base ATTRIBUTE_UNUSED) unsigned base ATTRIBUTE_UNUSED)
{ {
...@@ -120,7 +120,7 @@ tree_gen_pow2_profiler (struct histogram_value *value ATTRIBUTE_UNUSED, ...@@ -120,7 +120,7 @@ tree_gen_pow2_profiler (struct histogram_value *value ATTRIBUTE_UNUSED,
section for counters, BASE is offset of the counter position. */ section for counters, BASE is offset of the counter position. */
static void static void
tree_gen_one_value_profiler (struct histogram_value *value ATTRIBUTE_UNUSED, tree_gen_one_value_profiler (histogram_value value ATTRIBUTE_UNUSED,
unsigned tag ATTRIBUTE_UNUSED, unsigned tag ATTRIBUTE_UNUSED,
unsigned base ATTRIBUTE_UNUSED) unsigned base ATTRIBUTE_UNUSED)
{ {
...@@ -134,7 +134,7 @@ tree_gen_one_value_profiler (struct histogram_value *value ATTRIBUTE_UNUSED, ...@@ -134,7 +134,7 @@ tree_gen_one_value_profiler (struct histogram_value *value ATTRIBUTE_UNUSED,
section for counters, BASE is offset of the counter position. */ section for counters, BASE is offset of the counter position. */
static void static void
tree_gen_const_delta_profiler (struct histogram_value *value ATTRIBUTE_UNUSED, tree_gen_const_delta_profiler (histogram_value value ATTRIBUTE_UNUSED,
unsigned tag ATTRIBUTE_UNUSED, unsigned tag ATTRIBUTE_UNUSED,
unsigned base ATTRIBUTE_UNUSED) unsigned base ATTRIBUTE_UNUSED)
{ {
......
...@@ -39,14 +39,15 @@ enum hist_type ...@@ -39,14 +39,15 @@ enum hist_type
/* The value to measure. */ /* The value to measure. */
/* The void *'s are either rtx or tree, depending on which IR is in use. */ /* The void *'s are either rtx or tree, depending on which IR is in use. */
struct histogram_value struct histogram_value_t GTY(())
{ {
void * value; /* The value to profile. */ PTR GTY ((skip (""))) value; /* The value to profile. */
enum machine_mode mode; /* And its mode. */ enum machine_mode mode; /* And its mode. */
void * seq; /* Insns required to count the profiled value. */ PTR GTY ((skip (""))) seq; /* Insns required to count the
void * insn; /* Insn before that to measure. */ profiled value. */
enum hist_type type; /* Type of information to measure. */ PTR GTY ((skip (""))) insn; /* Insn before that to measure. */
unsigned n_counters; /* Number of required counters. */ enum hist_type type; /* Type of information to measure. */
unsigned n_counters; /* Number of required counters. */
union union
{ {
struct struct
...@@ -63,13 +64,18 @@ struct histogram_value ...@@ -63,13 +64,18 @@ struct histogram_value
} hdata; /* Profiled information specific data. */ } hdata; /* Profiled information specific data. */
}; };
typedef struct histogram_value_t *histogram_value;
DEF_VEC_P(histogram_value);
typedef VEC(histogram_value) *histogram_values;
/* Hooks registration. */ /* Hooks registration. */
extern void rtl_register_value_prof_hooks (void); extern void rtl_register_value_prof_hooks (void);
extern void tree_register_value_prof_hooks (void); extern void tree_register_value_prof_hooks (void);
/* IR-independent entry points. */ /* IR-independent entry points. */
extern void find_values_to_profile (unsigned *, struct histogram_value **); extern void find_values_to_profile (histogram_values *);
extern void free_profiled_values (unsigned, struct histogram_value *);
extern bool value_profile_transformations (void); extern bool value_profile_transformations (void);
/* External declarations for edge-based profiling. */ /* External declarations for edge-based profiling. */
...@@ -78,18 +84,17 @@ struct profile_hooks { ...@@ -78,18 +84,17 @@ struct profile_hooks {
void (*gen_edge_profiler) (int, edge); void (*gen_edge_profiler) (int, edge);
/* Insert code to increment the interval histogram counter. */ /* Insert code to increment the interval histogram counter. */
void (*gen_interval_profiler) (struct histogram_value *, unsigned, unsigned); void (*gen_interval_profiler) (histogram_value, unsigned, unsigned);
/* Insert code to increment the power of two histogram counter. */ /* Insert code to increment the power of two histogram counter. */
void (*gen_pow2_profiler) (struct histogram_value *, unsigned, unsigned); void (*gen_pow2_profiler) (histogram_value, unsigned, unsigned);
/* Insert code to find the most common value. */ /* Insert code to find the most common value. */
void (*gen_one_value_profiler) (struct histogram_value *, unsigned, unsigned); void (*gen_one_value_profiler) (histogram_value, unsigned, unsigned);
/* Insert code to find the most common value of a difference between two /* Insert code to find the most common value of a difference between two
evaluations of an expression. */ evaluations of an expression. */
void (*gen_const_delta_profiler) (struct histogram_value *, unsigned, void (*gen_const_delta_profiler) (histogram_value, unsigned, unsigned);
unsigned);
FILE * (*profile_dump_file) (void); FILE * (*profile_dump_file) (void);
}; };
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment