I'm applying this patch to my maint tree tonight as it does resolve
the issue for now. What surprised me was the file that we were
crashing out on wasn't even the file we wanted to get the blame
data for. :-\--8>--
From: Linus Torvalds <torvalds@linux-foundation.org>
Subject: [PATCH] git-blame shouldn't crash if run in an unmerged treeIf we are in the middle of resolving a merge conflict there may be
one or more files whose entries in the index represent an unmerged
state (index entries in the higher-order stages).Attempting to run git-blame on any file in such a working directory
resulted in "fatal: internal error: ce_mode is 0" as we use the magic
marker for an unmerged entry is 0 (set up by things like diff-lib.c's
do_diff_cache() and builtin-read-tree.c's read_tree_unmerged())
and the ce_match_stat_basic() function gets upset about this.I'm not entirely sure that the whole "ce_mode = 0" case is a good
idea to begin with, and maybe the right thing to do is to remove
that horrid freakish special case, but removing the internal error
seems to be the simplest fix for now.Linus
[sp: Thanks to Björn Steinbrink for the test case]
Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
---
read-cache.c | 2 +
t/t8004-blame.sh | 73 ++++++++++++++++++++++++++++++++++++++++++++++++++++++
2 files changed, 75 insertions(+), 0 deletions(-)
create mode 100755 t/t8004-blame.shdiff --git a/read-cache.c b/read-cache.c
index 536f4d0..928e8fa 100644
--- a/read-cache.c
+++ b/read-cache.c
@@ -149,6 +149,8 @@ static int ce_match_stat_basic(struct cache_entry *ce, struct stat *st)
else if (ce_compare_gitlink(ce))
changed |= DATA_CHANGED;
return changed;
+ case 0: /* Special case: unmerged file in index */
+ return MODE_CHANGED | DATA_CHANGED | TYPE_CHANGED;
default:
die("internal error: ce_mode is %o", ntohl(ce->ce_mode));
}
diff --git a/t/t8004-blame.sh b/t/t8004-blame.sh
new file mode 100755
index 0000000...
Please feel free to add a Signed-off-by: there. I guess I didn't add it in
the original email, because I wasn't sure if I'd have the energy to see if
I could just remove the clearing of "ce_mode". I never did.That whole "ce->ce_mode = 0" thing is really hacky, and we use it for two
totally different things ("git read-tree" uses it for "delete this entry",
and reading the index uses it when you ask for only merged entries). Bad
form, and not very logical.Linus
-
The first merge moved some code from file1 (which doesn't exist in the
branch anymore) into file2, so I guess the code move detection comes
into play here.Actually, in the original case that crashed here, I was curious about
some lines in file2 which looked like they had been automatically merged
from file1, so I tried to use git blame with file2 to see if that really
happened (I didn't expect git to be even able to follow code moves while
merging). Unfortunately, I didn't get such a test case yet, which might
indicate that I've only imagined that merge, and thinking about it, I
think that file2 wasn't marked as modified in "git status". Hm, I'll try
to find that merge conflict again and try that again.-
Nope, didn't succeed in reproducing what I probably just pretend to have
seen.Björn
-
| Andrew Morton | -mm merge plans for 2.6.23 |
| Greg Kroah-Hartman | [PATCH 005/196] Chinese: add translation of SubmittingDrivers |
| david | Re: Dual-Licensing Linux Kernel with GPL V2 and GPL V3 |
| Roland Dreier | Re: Integration of SCST in the mainstream Linux kernel |
git: | |
| Gerrit Renker | [PATCH 15/37] dccp: Set per-connection CCIDs via socket options |
| David Miller | Re: [PATCH] pkt_sched: Destroy gen estimators under rtnl_lock(). |
| David Miller | [GIT]: Networking |
| Jan Kara | Re: [BUG] New Kernel Bugs |
