summaryrefslogtreecommitdiff
path: root/src/file.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/file.c')
-rw-r--r--src/file.c17
1 files changed, 15 insertions, 2 deletions
diff --git a/src/file.c b/src/file.c
index 9828d283..f8e4fb91 100644
--- a/src/file.c
+++ b/src/file.c
@@ -60,6 +60,14 @@ file_hash_cmp (const void *x, const void *y)
static struct hash_table files;
+/* We can't free files we take out of the hash table, because they are still
+ likely pointed to in various places. The check_renamed() will be used if
+ we come across these, to find the new correct file. This is mainly to
+ prevent leak checkers from complaining. */
+static struct file **rehashed_files = NULL;
+static size_t rehashed_files_len = 0;
+#define REHASHED_FILES_INCR 5
+
/* Whether or not .SECONDARY with no prerequisites was given. */
static int all_secondary = 0;
@@ -217,8 +225,7 @@ rehash_file (struct file *from_file, const char *to_hname)
/* Find the end of the renamed list for the "from" file. */
file_key.hname = from_file->hname;
- while (from_file->renamed != 0)
- from_file = from_file->renamed;
+ check_renamed (from_file);
if (file_hash_cmp (from_file, &file_key))
/* hname changed unexpectedly!! */
abort ();
@@ -331,6 +338,12 @@ rehash_file (struct file *from_file, const char *to_hname)
to_file->builtin = 0;
from_file->renamed = to_file;
+
+ if (rehashed_files_len % REHASHED_FILES_INCR == 0)
+ rehashed_files = xrealloc (rehashed_files,
+ sizeof (struct file *) * (rehashed_files_len + REHASHED_FILES_INCR));
+
+ rehashed_files[rehashed_files_len++] = from_file;
}
/* Rename FILE to NAME. This is not as simple as resetting