{
if (!EDGE_INFO (e)->ignore)
{
- if (e->count < 0)
- return true;
+ if (e->count < 0
+ && (!(e->flags & EDGE_FAKE)
+ || !block_ends_with_call_p (e->src)))
+ {
+ if (dump_file)
+ {
+ fprintf (dump_file,
+ "Edge %i->%i is inconsistent, count"HOST_WIDEST_INT_PRINT_DEC,
+ e->src->index, e->dest->index, e->count);
+ dump_bb (e->src, dump_file, 0);
+ dump_bb (e->dest, dump_file, 0);
+ }
+ return true;
+ }
}
}
return false;
is_inconsistent (void)
{
basic_block bb;
+ bool inconsistent = false;
FOR_EACH_BB (bb)
{
- if (is_edge_inconsistent (bb->preds))
- return true;
- if (is_edge_inconsistent (bb->succs))
- return true;
- if ( bb->count != sum_edge_counts (bb->preds)
- || (bb->count != sum_edge_counts (bb->succs) &&
- !(find_edge (bb, EXIT_BLOCK_PTR) != NULL &&
- block_ends_with_call_p (bb))))
- return true;
+ inconsistent |= is_edge_inconsistent (bb->preds);
+ if (!dump_file && inconsistent)
+ return true;
+ inconsistent |= is_edge_inconsistent (bb->succs);
+ if (!dump_file && inconsistent)
+ return true;
+ if (bb->count < 0)
+ {
+ if (dump_file)
+ {
+ fprintf (dump_file, "BB %i count is negative "
+ HOST_WIDEST_INT_PRINT_DEC,
+ bb->index,
+ bb->count);
+ dump_bb (bb, dump_file, 0);
+ }
+ inconsistent = true;
+ }
+ if (bb->count != sum_edge_counts (bb->preds))
+ {
+ if (dump_file)
+ {
+ fprintf (dump_file, "BB %i count does not match sum of incomming edges "
+ HOST_WIDEST_INT_PRINT_DEC" should be " HOST_WIDEST_INT_PRINT_DEC,
+ bb->index,
+ bb->count,
+ sum_edge_counts (bb->preds));
+ dump_bb (bb, dump_file, 0);
+ }
+ inconsistent = true;
+ }
+ if (bb->count != sum_edge_counts (bb->succs) &&
+ ! (find_edge (bb, EXIT_BLOCK_PTR) != NULL && block_ends_with_call_p (bb)))
+ {
+ if (dump_file)
+ {
+ fprintf (dump_file, "BB %i count does not match sum of outgoing edges "
+ HOST_WIDEST_INT_PRINT_DEC" should be " HOST_WIDEST_INT_PRINT_DEC,
+ bb->index,
+ bb->count,
+ sum_edge_counts (bb->succs));
+ dump_bb (bb, dump_file, 0);
+ }
+ inconsistent = true;
+ }
+ if (!dump_file && inconsistent)
+ return true;
}
- return false;
+ return inconsistent;
}
/* Set each basic block count to the sum of its outgoing edge counts */
int inconsistent = 0;
/* Very simple sanity checks so we catch bugs in our profiling code. */
- if (profile_info)
+ if (!profile_info)
+ return;
+ if (profile_info->run_max * profile_info->runs < profile_info->sum_max)
{
- if (profile_info->run_max * profile_info->runs < profile_info->sum_max)
- {
- error ("corrupted profile info: run_max * runs < sum_max");
- exec_counts = NULL;
- }
+ error ("corrupted profile info: run_max * runs < sum_max");
+ exec_counts = NULL;
+ }
- if (profile_info->sum_all < profile_info->sum_max)
- {
- error ("corrupted profile info: sum_all is smaller than sum_max");
- exec_counts = NULL;
- }
+ if (profile_info->sum_all < profile_info->sum_max)
+ {
+ error ("corrupted profile info: sum_all is smaller than sum_max");
+ exec_counts = NULL;
}
/* Attach extra info block to each bb. */
}
}
counts_to_freqs ();
+ profile_status = PROFILE_READ;
if (dump_file)
{
&& (LOCATION_FILE (e->goto_locus)
!= LOCATION_FILE (gimple_location (last))
|| (LOCATION_LINE (e->goto_locus)
- != LOCATION_LINE (gimple_location (last)))))
+ != LOCATION_LINE (gimple_location (last)))))
{
basic_block new_bb = split_edge (e);
- single_succ_edge (new_bb)->goto_locus = e->goto_locus;
+ edge ne = single_succ_edge (new_bb);
+ ne->goto_locus = e->goto_locus;
+ ne->goto_block = e->goto_block;
}
if ((e->flags & (EDGE_ABNORMAL | EDGE_ABNORMAL_CALL))
&& e->dest != EXIT_BLOCK_PTR)
VEC_free (histogram_value, heap, values);
free_edge_list (el);
- if (flag_branch_probabilities && profile_info)
- profile_status = PROFILE_READ;
coverage_end_function ();
}
\f