path: root/update-cache.c
diff options
authorJunio C Hamano <>2005-05-08 07:05:18 (GMT)
committerJunio C Hamano <>2005-05-08 07:05:18 (GMT)
commit4c5abf428203524aac7ec094da692e5b89782127 (patch)
tree5bd89fe05bd53351e5d32641bc03a221fbafaf3c /update-cache.c
parent192268c197c0f143989662f648b1d900014e7d89 (diff)
Allow removal of "path" when "path/file" exists.
When we used to have "path" as a file or a symlink, but now we have "path/file" (or in general, have "path" as a directory), we would want to remove "path" before adding "path/file". The logic in add_file_to_cache() only runs lstat() and does not detect this case and fails to allow removing it in this case. In the opposite case of having "path/file" in the index and having "path" on the filesystem as a file or a symlink we do allow removal of "path/file", so to be symmetric we should allow it as well, without forcing the user to say --force-remove. Signed-off-by: Junio C Hamano <>
Diffstat (limited to 'update-cache.c')
1 files changed, 12 insertions, 3 deletions
diff --git a/update-cache.c b/update-cache.c
index 1e4e62c..69b1afe 100644
--- a/update-cache.c
+++ b/update-cache.c
@@ -53,14 +53,23 @@ static void fill_stat_cache_info(struct cache_entry *ce, struct stat *st)
static int add_file_to_cache(char *path)
- int size, namelen, option;
+ int size, namelen, option, status;
struct cache_entry *ce;
struct stat st;
int fd;
char *target;
- if (lstat(path, &st) < 0) {
- if (errno == ENOENT || errno == ENOTDIR) {
+ status = lstat(path, &st);
+ if (status < 0 || S_ISDIR(st.st_mode)) {
+ /* When we used to have "path" and now we want to add
+ * "path/file", we need a way to remove "path" before
+ * being able to add "path/file". However,
+ * "git-update-cache --remove path" would not work.
+ * --force-remove can be used but this is more user
+ * friendly, especially since we can do the opposite
+ * case just fine without --force-remove.
+ */
+ if (status == 0 || (errno == ENOENT || errno == ENOTDIR)) {
if (allow_remove)
return remove_file_from_cache(path);