Honza
Index: lto-streamer-in.c
===================================================================
--- lto-streamer-in.c (revision 209047)
+++ lto-streamer-in.c (working copy)
@@ -145,21 +145,49 @@ canon_file_name (const char *string)
}
+/* location_cache is used at LTO read in to avoid too many duplicates
in
+ the linemap tables. */
+
+#define LOCATION_CACHE_SIZE 524287
+struct location_cache_entry
+{
+ const char *file;
+ int line;
+ int col;
+ location_t location;
+};
+static struct location_cache_entry *location_cache;
+
+/* Return hash of FILE/LINE/COL. */
+
+int
+location_cache_hash (const char *file, int line, int col)
+{
+ return iterative_hash_hashval_t ((size_t)file,
+ iterative_hash_hashval_t (line, col))
% LOCATION_CACHE_SIZE;
+}
+
+
/* Read a location bitpack from input block IB. */
location_t
lto_input_location (struct bitpack_d *bp, struct data_in *data_in)
{
- static const char *current_file;
- static int current_line;
+ static const char *current_file, *last_file;
+ static int current_line, last_line;
static int current_col;
bool file_change, line_change, column_change;
unsigned len;
- bool prev_file = current_file != NULL;
+ bool prev_file = last_file != NULL;
+ int hash;
+ const char *cfile;
if (bp_unpack_value (bp, 1))
return UNKNOWN_LOCATION;
+ if (!location_cache)
+ location_cache = XCNEWVEC (struct location_cache_entry,
LOCATION_CACHE_SIZE);
+
file_change = bp_unpack_value (bp, 1);
line_change = bp_unpack_value (bp, 1);
column_change = bp_unpack_value (bp, 1);
@@ -175,18 +203,32 @@ lto_input_location (struct bitpack_d *bp
if (column_change)
current_col = bp_unpack_var_len_unsigned (bp);
+ cfile = current_file;
+ hash = location_cache_hash (cfile, current_line, current_col);
- if (file_change)
+ if (location_cache[hash].file == cfile
+ && location_cache[hash].line == current_line
+ && location_cache[hash].col == current_col + 1)
+ return location_cache[hash].location;
+ location_cache[hash].file = cfile;
+ location_cache[hash].line = current_line;
+ location_cache[hash].col = current_col + 1;
+
+ if (current_file != last_file)
{
if (prev_file)
linemap_add (line_table, LC_LEAVE, false, NULL, 0);
linemap_add (line_table, LC_ENTER, false, current_file,
current_line);
}
- else if (line_change)
+ else if (current_line != last_line)
linemap_line_start (line_table, current_line, current_col);
- return linemap_position_for_column (line_table, current_col);
+ location_cache[hash].location
+ = linemap_position_for_column (line_table, current_col);
+ last_file = current_file;
+ last_line = current_line;
+ return location_cache[hash].location;
}
@@ -981,6 +1023,27 @@ input_function (tree fn_decl, struct dat
}
bsi = gsi_start_bb (bb);
while (!gsi_end_p (bsi))
+ {
+ gimple stmt = gsi_stmt (bsi);
+ /* If we're recompiling LTO objects with debug stmts but
+ we're not supposed to have debug stmts, remove them now.
+ We can't remove them earlier because this would cause uid
+ mismatches in fixups, but we can do it at this point, as
+ long as debug stmts don't require fixups. */
+ if (!MAY_HAVE_DEBUG_STMTS && is_gimple_debug (stmt))
+ {
+ gimple_stmt_iterator gsi = bsi;
+ gsi_next (&bsi);
+ gsi_remove (&gsi, true);
+ }
+ else
+ {
+ gsi_next (&bsi);
+ stmts[gimple_uid (stmt)] = stmt;
+ }
+ }
+ bsi = gsi_start_bb (bb);
+ while (!gsi_end_p (bsi))
{
gimple stmt = gsi_stmt (bsi);
/* If we're recompiling LTO objects with debug stmts but