* [PATCH/RFC 0/2] Bug fixes regarding diff and "git add -N" @ 2015-03-09 14:14 Nguyễn Thái Ngọc Duy 2015-03-09 14:14 ` [PATCH 1/2] diff --cached: do not report i-t-a entries as "new" Nguyễn Thái Ngọc Duy ` (2 more replies) 0 siblings, 3 replies; 18+ messages in thread From: Nguyễn Thái Ngọc Duy @ 2015-03-09 14:14 UTC (permalink / raw) To: git; +Cc: Nguyễn Thái Ngọc Duy The first one attempts to fix "git status" reporting intent-to-add files as "changes to be committed". The "new file" report is now moved to "git diff-files" aka "changes not staged for commit" instead. I just want to check if I'm going on the right direction as core diff machinery is not really my area. I know these patches break t2203 and t4011 but from a quick glance, the tests simply rely on the old behavior, not real breakages. Nguyễn Thái Ngọc Duy (2): diff --cached: do not report i-t-a entries as "new" diff-files: mark i-t-a paths as "new" builtin/add.c | 1 + diff-lib.c | 7 +++++++ 2 files changed, 8 insertions(+) -- 2.3.0.rc1.137.g477eb31 ^ permalink raw reply [flat|nested] 18+ messages in thread
* [PATCH 1/2] diff --cached: do not report i-t-a entries as "new" 2015-03-09 14:14 [PATCH/RFC 0/2] Bug fixes regarding diff and "git add -N" Nguyễn Thái Ngọc Duy @ 2015-03-09 14:14 ` Nguyễn Thái Ngọc Duy 2015-03-15 6:55 ` Junio C Hamano 2015-03-16 13:56 ` [PATCH v2] diff-lib.c: adjust position of i-t-a entries in diff Nguyễn Thái Ngọc Duy 2015-03-09 14:14 ` [PATCH 2/2] diff-files: mark i-t-a paths as "new" Nguyễn Thái Ngọc Duy 2015-03-09 15:45 ` [PATCH] t2203,t4011: adjust to changed intent-to-add treatment Michael J Gruber 2 siblings, 2 replies; 18+ messages in thread From: Nguyễn Thái Ngọc Duy @ 2015-03-09 14:14 UTC (permalink / raw) To: git; +Cc: Nguyễn Thái Ngọc Duy Paths marked by "git add -N" are simply a reminder to the user that these files should be staged. If the user does not stage any of them, "git commit" will not record them. Align the behavior of "diff --cached" and "git commit". The most prominent result of this patch is "git status" no longer reports i-t-a paths as "Changes to be committed". Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com> --- diff-lib.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/diff-lib.c b/diff-lib.c index a85c497..db0e6f8 100644 --- a/diff-lib.c +++ b/diff-lib.c @@ -400,6 +400,8 @@ static void do_oneway_diff(struct unpack_trees_options *o, * Something added to the tree? */ if (!tree) { + if (idx && (idx->ce_flags & CE_INTENT_TO_ADD)) + return; show_new_file(revs, idx, cached, match_missing); return; } -- 2.3.0.rc1.137.g477eb31 ^ permalink raw reply related [flat|nested] 18+ messages in thread
* Re: [PATCH 1/2] diff --cached: do not report i-t-a entries as "new" 2015-03-09 14:14 ` [PATCH 1/2] diff --cached: do not report i-t-a entries as "new" Nguyễn Thái Ngọc Duy @ 2015-03-15 6:55 ` Junio C Hamano 2015-03-16 13:56 ` [PATCH v2] diff-lib.c: adjust position of i-t-a entries in diff Nguyễn Thái Ngọc Duy 1 sibling, 0 replies; 18+ messages in thread From: Junio C Hamano @ 2015-03-15 6:55 UTC (permalink / raw) To: Nguyễn Thái Ngọc Duy; +Cc: git Nguyễn Thái Ngọc Duy <pclouds@gmail.com> writes: > Paths marked by "git add -N" are simply a reminder to the user that > these files should be staged. If the user does not stage any of them, > "git commit" will not record them. > > Align the behavior of "diff --cached" and "git commit". The most > prominent result of this patch is "git status" no longer reports i-t-a > paths as "Changes to be committed". > > Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com> > --- > diff-lib.c | 2 ++ > 1 file changed, 2 insertions(+) > > diff --git a/diff-lib.c b/diff-lib.c > index a85c497..db0e6f8 100644 > --- a/diff-lib.c > +++ b/diff-lib.c > @@ -400,6 +400,8 @@ static void do_oneway_diff(struct unpack_trees_options *o, > * Something added to the tree? > */ > if (!tree) { > + if (idx && (idx->ce_flags & CE_INTENT_TO_ADD)) > + return; > show_new_file(revs, idx, cached, match_missing); > return; > } This hunk by itself feels like it is going in the right direction. The HEAD does not have it, and even though there is idx, it merely is an i-t-a entry. Don't you need to special case the call to show_modified() at the end of this function as well, though? idx is i-t-a, and tree has a concrete object. Should it appear as if the path already exists in the index, or should we pretend as if idx is not yet there? For example, after this sequence: $ git init $ >void $ git add void $ git commit -m void $ git rm --cached void $ git add -N void HEAD has "void" with an empty blob, the index has i-t-a. I am not sure if we should say something about path "void" when asked: $ git diff --cached Perhaps something like this to cover that case? /* * Something removed from the tree? */ - if (!idx) { + if (!idx || (ix->ce_flags & CE_INTENT_TO_ADD)) { diff_index_show_file(revs, "-", tree, tree->sha1, 1, tree->ce_mode, 0); return; } ^ permalink raw reply [flat|nested] 18+ messages in thread
* [PATCH v2] diff-lib.c: adjust position of i-t-a entries in diff 2015-03-09 14:14 ` [PATCH 1/2] diff --cached: do not report i-t-a entries as "new" Nguyễn Thái Ngọc Duy 2015-03-15 6:55 ` Junio C Hamano @ 2015-03-16 13:56 ` Nguyễn Thái Ngọc Duy 2015-03-16 15:15 ` Michael J Gruber 1 sibling, 1 reply; 18+ messages in thread From: Nguyễn Thái Ngọc Duy @ 2015-03-16 13:56 UTC (permalink / raw) To: git; +Cc: Junio C Hamano, Michael J Gruber, Nguyễn Thái Ngọc Duy Entries added by "git add -N" are reminder for the user so that they don't forget to add them before committing. These entries appear in the index even though they are not real. Their presence in the index leads to a confusing "git status" like this: On branch master Changes to be committed: new file: foo Changes not staged for commit: modified: foo If you do a "git commit", "foo" will not be included even though "status" reports it as "to be committed". This patch changes the output to become On branch master Changes not staged for commit: new file: foo no changes added to commit The two hunks in diff-lib.c adjust "diff-index" and "diff-files" so that i-t-a entries appear as new files in diff-files and nothing in diff-index. Due to this change, diff-files may start to report "new files" for the first time. "add -u" needs to be told about this or it will die in denial, screaming "new files can't exist! Reality is wrong." Luckily, it's the only one among run_diff_files() callers that needs fixing. The test "cache-tree invalidates i-t-a paths" is marked failure because I don't think removing "--cached" from "git diff" is the right fix. This test relies on "diff --cached" behavior but the behavior now has changed. We may need to revisit this test at some point in future. Helped-by: Michael J Gruber <git@drmicha.warpmail.net> Helped-by: Junio C Hamano <gitster@pobox.com> Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com> --- builtin/add.c | 1 + diff-lib.c | 12 ++++++++++++ t/t2203-add-intent.sh | 21 ++++++++++++++++++--- t/t4011-diff-symlink.sh | 10 ++++++---- 4 files changed, 37 insertions(+), 7 deletions(-) diff --git a/builtin/add.c b/builtin/add.c index 3390933..ee370b0 100644 --- a/builtin/add.c +++ b/builtin/add.c @@ -63,6 +63,7 @@ static void update_callback(struct diff_queue_struct *q, switch (fix_unmerged_status(p, data)) { default: die(_("unexpected diff status %c"), p->status); + case DIFF_STATUS_ADDED: case DIFF_STATUS_MODIFIED: case DIFF_STATUS_TYPE_CHANGED: if (add_file_to_index(&the_index, path, data->flags)) { diff --git a/diff-lib.c b/diff-lib.c index a85c497..714501a 100644 --- a/diff-lib.c +++ b/diff-lib.c @@ -212,6 +212,11 @@ int run_diff_files(struct rev_info *revs, unsigned int option) ce->sha1, !is_null_sha1(ce->sha1), ce->name, 0); continue; + } else if (ce->ce_flags & CE_INTENT_TO_ADD) { + diff_addremove(&revs->diffopt, '+', ce->ce_mode, + EMPTY_BLOB_SHA1_BIN, 0, + ce->name, 0); + continue; } changed = match_stat_with_submodule(&revs->diffopt, ce, &st, @@ -376,6 +381,13 @@ static void do_oneway_diff(struct unpack_trees_options *o, struct rev_info *revs = o->unpack_data; int match_missing, cached; + /* i-t-a entries do not actually exist in the index */ + if (idx && (idx->ce_flags & CE_INTENT_TO_ADD)) { + idx = NULL; + if (!tree) + return; /* nothing to diff.. */ + } + /* if the entry is not checked out, don't examine work tree */ cached = o->index_only || (idx && ((idx->ce_flags & CE_VALID) || ce_skip_worktree(idx))); diff --git a/t/t2203-add-intent.sh b/t/t2203-add-intent.sh index 2a4a749..42827b8 100755 --- a/t/t2203-add-intent.sh +++ b/t/t2203-add-intent.sh @@ -5,10 +5,24 @@ test_description='Intent to add' . ./test-lib.sh test_expect_success 'intent to add' ' + test_commit 1 && + git rm 1.t && + echo hello >1.t && echo hello >file && echo hello >elif && git add -N file && - git add elif + git add elif && + git add -N 1.t +' + +test_expect_success 'git status' ' + git status --porcelain | grep -v actual >actual && + cat >expect <<-\EOF && + DA 1.t + A elif + A file + EOF + test_cmp expect actual ' test_expect_success 'check result of "add -N"' ' @@ -43,7 +57,8 @@ test_expect_success 'i-t-a entry is simply ignored' ' git add -N nitfol && git commit -m second && test $(git ls-tree HEAD -- nitfol | wc -l) = 0 && - test $(git diff --name-only HEAD -- nitfol | wc -l) = 1 + test $(git diff --name-only HEAD -- nitfol | wc -l) = 0 && + test $(git diff --name-only -- nitfol | wc -l) = 1 ' test_expect_success 'can commit with an unrelated i-t-a entry in index' ' @@ -62,7 +77,7 @@ test_expect_success 'can "commit -a" with an i-t-a entry' ' git commit -a -m all ' -test_expect_success 'cache-tree invalidates i-t-a paths' ' +test_expect_failure 'cache-tree invalidates i-t-a paths' ' git reset --hard && mkdir dir && : >dir/foo && diff --git a/t/t4011-diff-symlink.sh b/t/t4011-diff-symlink.sh index 13e7f62..7452fce 100755 --- a/t/t4011-diff-symlink.sh +++ b/t/t4011-diff-symlink.sh @@ -139,11 +139,13 @@ test_expect_success SYMLINKS 'setup symlinks with attributes' ' test_expect_success SYMLINKS 'symlinks do not respect userdiff config by path' ' cat >expect <<-\EOF && diff --git a/file.bin b/file.bin - index e69de29..d95f3ad 100644 - Binary files a/file.bin and b/file.bin differ + new file mode 100644 + index 0000000..d95f3ad + Binary files /dev/null and b/file.bin differ diff --git a/link.bin b/link.bin - index e69de29..dce41ec 120000 - --- a/link.bin + new file mode 120000 + index 0000000..dce41ec + --- /dev/null +++ b/link.bin @@ -0,0 +1 @@ +file.bin -- 2.3.0.rc1.137.g477eb31 ^ permalink raw reply related [flat|nested] 18+ messages in thread
* Re: [PATCH v2] diff-lib.c: adjust position of i-t-a entries in diff 2015-03-16 13:56 ` [PATCH v2] diff-lib.c: adjust position of i-t-a entries in diff Nguyễn Thái Ngọc Duy @ 2015-03-16 15:15 ` Michael J Gruber 2015-03-16 16:05 ` Junio C Hamano 0 siblings, 1 reply; 18+ messages in thread From: Michael J Gruber @ 2015-03-16 15:15 UTC (permalink / raw) To: Nguyễn Thái Ngọc Duy, git; +Cc: Junio C Hamano Nguyễn Thái Ngọc Duy venit, vidit, dixit 16.03.2015 14:56: > Entries added by "git add -N" are reminder for the user so that they > don't forget to add them before committing. These entries appear in > the index even though they are not real. Their presence in the index > leads to a confusing "git status" like this: > > On branch master > Changes to be committed: > new file: foo > > Changes not staged for commit: > modified: foo > > If you do a "git commit", "foo" will not be included even though > "status" reports it as "to be committed". This patch changes the > output to become > > On branch master > Changes not staged for commit: > new file: foo > > no changes added to commit > > The two hunks in diff-lib.c adjust "diff-index" and "diff-files" so > that i-t-a entries appear as new files in diff-files and nothing in > diff-index. > > Due to this change, diff-files may start to report "new files" for the > first time. "add -u" needs to be told about this or it will die in > denial, screaming "new files can't exist! Reality is wrong." Luckily, > it's the only one among run_diff_files() callers that needs fixing. > > The test "cache-tree invalidates i-t-a paths" is marked failure > because I don't think removing "--cached" from "git diff" is the right > fix. This test relies on "diff --cached" behavior but the behavior now > has changed. We may need to revisit this test at some point in future. I can't quite follow that reasoning. If the test describes expected behavior which the patch breaks, then we should not apply the patch. If the patch changes behavior in an expected way, then we should change the test to match. > Helped-by: Michael J Gruber <git@drmicha.warpmail.net> > Helped-by: Junio C Hamano <gitster@pobox.com> > Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com> > --- > builtin/add.c | 1 + > diff-lib.c | 12 ++++++++++++ > t/t2203-add-intent.sh | 21 ++++++++++++++++++--- > t/t4011-diff-symlink.sh | 10 ++++++---- > 4 files changed, 37 insertions(+), 7 deletions(-) > > diff --git a/builtin/add.c b/builtin/add.c > index 3390933..ee370b0 100644 > --- a/builtin/add.c > +++ b/builtin/add.c > @@ -63,6 +63,7 @@ static void update_callback(struct diff_queue_struct *q, > switch (fix_unmerged_status(p, data)) { > default: > die(_("unexpected diff status %c"), p->status); > + case DIFF_STATUS_ADDED: > case DIFF_STATUS_MODIFIED: > case DIFF_STATUS_TYPE_CHANGED: > if (add_file_to_index(&the_index, path, data->flags)) { > diff --git a/diff-lib.c b/diff-lib.c > index a85c497..714501a 100644 > --- a/diff-lib.c > +++ b/diff-lib.c > @@ -212,6 +212,11 @@ int run_diff_files(struct rev_info *revs, unsigned int option) > ce->sha1, !is_null_sha1(ce->sha1), > ce->name, 0); > continue; > + } else if (ce->ce_flags & CE_INTENT_TO_ADD) { > + diff_addremove(&revs->diffopt, '+', ce->ce_mode, > + EMPTY_BLOB_SHA1_BIN, 0, > + ce->name, 0); > + continue; > } > > changed = match_stat_with_submodule(&revs->diffopt, ce, &st, > @@ -376,6 +381,13 @@ static void do_oneway_diff(struct unpack_trees_options *o, > struct rev_info *revs = o->unpack_data; > int match_missing, cached; > > + /* i-t-a entries do not actually exist in the index */ > + if (idx && (idx->ce_flags & CE_INTENT_TO_ADD)) { > + idx = NULL; > + if (!tree) > + return; /* nothing to diff.. */ > + } > + > /* if the entry is not checked out, don't examine work tree */ > cached = o->index_only || > (idx && ((idx->ce_flags & CE_VALID) || ce_skip_worktree(idx))); > diff --git a/t/t2203-add-intent.sh b/t/t2203-add-intent.sh > index 2a4a749..42827b8 100755 > --- a/t/t2203-add-intent.sh > +++ b/t/t2203-add-intent.sh > @@ -5,10 +5,24 @@ test_description='Intent to add' > . ./test-lib.sh > > test_expect_success 'intent to add' ' > + test_commit 1 && > + git rm 1.t && > + echo hello >1.t && > echo hello >file && > echo hello >elif && > git add -N file && > - git add elif > + git add elif && > + git add -N 1.t > +' > + > +test_expect_success 'git status' ' > + git status --porcelain | grep -v actual >actual && > + cat >expect <<-\EOF && > + DA 1.t > + A elif > + A file > + EOF > + test_cmp expect actual > ' > > test_expect_success 'check result of "add -N"' ' > @@ -43,7 +57,8 @@ test_expect_success 'i-t-a entry is simply ignored' ' > git add -N nitfol && > git commit -m second && > test $(git ls-tree HEAD -- nitfol | wc -l) = 0 && > - test $(git diff --name-only HEAD -- nitfol | wc -l) = 1 > + test $(git diff --name-only HEAD -- nitfol | wc -l) = 0 && > + test $(git diff --name-only -- nitfol | wc -l) = 1 > ' > > test_expect_success 'can commit with an unrelated i-t-a entry in index' ' > @@ -62,7 +77,7 @@ test_expect_success 'can "commit -a" with an i-t-a entry' ' > git commit -a -m all > ' > > -test_expect_success 'cache-tree invalidates i-t-a paths' ' > +test_expect_failure 'cache-tree invalidates i-t-a paths' ' > git reset --hard && > mkdir dir && > : >dir/foo && > diff --git a/t/t4011-diff-symlink.sh b/t/t4011-diff-symlink.sh > index 13e7f62..7452fce 100755 > --- a/t/t4011-diff-symlink.sh > +++ b/t/t4011-diff-symlink.sh > @@ -139,11 +139,13 @@ test_expect_success SYMLINKS 'setup symlinks with attributes' ' > test_expect_success SYMLINKS 'symlinks do not respect userdiff config by path' ' > cat >expect <<-\EOF && > diff --git a/file.bin b/file.bin > - index e69de29..d95f3ad 100644 > - Binary files a/file.bin and b/file.bin differ > + new file mode 100644 > + index 0000000..d95f3ad > + Binary files /dev/null and b/file.bin differ > diff --git a/link.bin b/link.bin > - index e69de29..dce41ec 120000 > - --- a/link.bin > + new file mode 120000 > + index 0000000..dce41ec > + --- /dev/null > +++ b/link.bin > @@ -0,0 +1 @@ > +file.bin > ^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [PATCH v2] diff-lib.c: adjust position of i-t-a entries in diff 2015-03-16 15:15 ` Michael J Gruber @ 2015-03-16 16:05 ` Junio C Hamano 2015-03-17 14:07 ` Duy Nguyen 0 siblings, 1 reply; 18+ messages in thread From: Junio C Hamano @ 2015-03-16 16:05 UTC (permalink / raw) To: Michael J Gruber; +Cc: Nguyễn Thái Ngọc Duy, git Michael J Gruber <git@drmicha.warpmail.net> writes: > Nguyễn Thái Ngọc Duy venit, vidit, dixit 16.03.2015 14:56: > >> The test "cache-tree invalidates i-t-a paths" is marked failure >> because I don't think removing "--cached" from "git diff" is the right >> fix. This test relies on "diff --cached" behavior but the behavior now >> has changed. We may need to revisit this test at some point in future. > > I can't quite follow that reasoning. If the test describes expected > behavior which the patch breaks, then we should not apply the patch. If > the patch changes behavior in an expected way, then we should change the > test to match. The offending one came from eec3e7e4 (cache-tree: invalidate i-t-a paths after generating trees, 2012-12-16), which was a fix to an earlier bug where a cache-tree written out of an index with i-t-a entries had incorrect information and still claimed it is fully valid after write-tree rebuilt it. The test probably should add another path without i-t-a bit, run the same "diff --cached" with updated expectation before write-tre, and run the "diff --cached" again to make sure it produces a result that match the updated expectation. ^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [PATCH v2] diff-lib.c: adjust position of i-t-a entries in diff 2015-03-16 16:05 ` Junio C Hamano @ 2015-03-17 14:07 ` Duy Nguyen 2015-03-17 17:57 ` Junio C Hamano 0 siblings, 1 reply; 18+ messages in thread From: Duy Nguyen @ 2015-03-17 14:07 UTC (permalink / raw) To: Junio C Hamano; +Cc: Michael J Gruber, git On Mon, Mar 16, 2015 at 09:05:45AM -0700, Junio C Hamano wrote: > The offending one came from eec3e7e4 (cache-tree: invalidate i-t-a > paths after generating trees, 2012-12-16), which was a fix to an > earlier bug where a cache-tree written out of an index with i-t-a > entries had incorrect information and still claimed it is fully > valid after write-tree rebuilt it. The test probably should add > another path without i-t-a bit, run the same "diff --cached" with > updated expectation before write-tre, and run the "diff --cached" > again to make sure it produces a result that match the updated > expectation. Would adding another non-i-t-a entry help? Before this patch "diff --cached" after write-tree shows the i-t-a entry only when eec3e7e4 is applied. But with this patch we don't show i-t-a entry any more, before or after write-tree, eec3e7e4 makes no visible difference. We could even revert eec3e7e4 and the outcome of "diff --cached" would be the same because we just sort of move the "invalidation" part from cache-tree to do_oneway_diff(). Not invalidating would speed up "diff --cached" when i-t-a entries are present. Still it may be a good idea to invalidate i-t-a paths to be on the safe side. Perhaps a patch like this to resurrect the test? -- 8< -- Subject: t2203: enable 'cache-tree invalidates i-t-a paths' test This test is disabled in the previous patch because the "diff --cached" expectation is the same, with or without eec3e7e4 [1] where this test is added. But it still is a good idea to invalidate i-t-a paths because the index does _not_ match the cached-tree exactly. "diff --cached" may not care, but other operations might. Update the test to catch this invalidation instead. [1] cache-tree: invalidate i-t-a paths after generating trees, 2012-12-16 Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com> diff --git a/t/t2203-add-intent.sh b/t/t2203-add-intent.sh index 42827b8..1a6c814 100755 --- a/t/t2203-add-intent.sh +++ b/t/t2203-add-intent.sh @@ -77,7 +77,7 @@ test_expect_success 'can "commit -a" with an i-t-a entry' ' git commit -a -m all ' -test_expect_failure 'cache-tree invalidates i-t-a paths' ' +test_expect_success 'cache-tree invalidates i-t-a paths' ' git reset --hard && mkdir dir && : >dir/foo && @@ -86,14 +86,14 @@ test_expect_failure 'cache-tree invalidates i-t-a paths' ' : >dir/bar && git add -N dir/bar && - git diff --cached --name-only >actual && - echo dir/bar >expect && - test_cmp expect actual && - git write-tree >/dev/null && - - git diff --cached --name-only >actual && - echo dir/bar >expect && + test-dump-cache-tree >actual && + cat >expect <<-\EOF && + invalid (1 subtrees) + invalid #(ref) (1 subtrees) + invalid dir/ (0 subtrees) + invalid #(ref) dir/ (0 subtrees) + EOF test_cmp expect actual ' -- 8< -- ^ permalink raw reply related [flat|nested] 18+ messages in thread
* Re: [PATCH v2] diff-lib.c: adjust position of i-t-a entries in diff 2015-03-17 14:07 ` Duy Nguyen @ 2015-03-17 17:57 ` Junio C Hamano 2015-03-18 12:47 ` Duy Nguyen 0 siblings, 1 reply; 18+ messages in thread From: Junio C Hamano @ 2015-03-17 17:57 UTC (permalink / raw) To: Duy Nguyen; +Cc: Michael J Gruber, git Duy Nguyen <pclouds@gmail.com> writes: > On Mon, Mar 16, 2015 at 09:05:45AM -0700, Junio C Hamano wrote: >> The offending one came from eec3e7e4 (cache-tree: invalidate i-t-a >> paths after generating trees, 2012-12-16), which was a fix to an >> earlier bug where a cache-tree written out of an index with i-t-a >> entries had incorrect information and still claimed it is fully >> valid after write-tree rebuilt it. The test probably should add >> another path without i-t-a bit, run the same "diff --cached" with >> updated expectation before write-tre, and run the "diff --cached" >> again to make sure it produces a result that match the updated >> expectation. > > Would adding another non-i-t-a entry help? Before this patch > "diff --cached" after write-tree shows the i-t-a entry only when > eec3e7e4 is applied. But with this patch we don't show i-t-a entry any > more, before or after write-tree, eec3e7e4 makes no visible difference. > > We could even revert eec3e7e4 and the outcome of "diff --cached" would > be the same because we just sort of move the "invalidation" part from > cache-tree to do_oneway_diff(). Not invalidating would speed up "diff > --cached" when i-t-a entries are present. Still it may be a good idea > to invalidate i-t-a paths to be on the safe side. Perhaps a patch like > this to resurrect the test? My unerstanding of what eec3e7e4 (cache-tree: invalidate i-t-a paths after generating trees, 2012-12-16) fixed was that in this sequence: - You prepare an index. - You write-tree out of the index, which involves: - updating the cache-tree to match the shape of the resulting from writing the index out. - create tree objects matching all levels of the cache-tree as needed on disk. - report the top-level tree object name - run "diff-index --cached", which can and will take advantage of the fact that everything in a subtree below a known-to-be-valid cache-tree entry does not have to be checked one-by-one. If a cache-tree says "everything under D/ in the index would hash to tree object T" and the HEAD has tree object T at D/, then the diff machinery will bypass the entire section in the index under D/, which is a valid optimization. However, when there is an i-t-a entry, we excluded that entry from the tree object computation, its presence did not contribute to the tree object name, but still marked the cache-tree entries that contain it as valid by mistake. This old bug was what the commit fixed, so an invocation of "diff --cached" after a write-tree, even if the index contains an i-t-a entry, will not see cache-tree entries that are marked valid when they are not. Instead, "diff --cached" will bypass the optimization and makes comparison one-by-one for the index entries. So reverting the fix obviously is not the right thing to do. If the tests show different results from two invocations of "diff --cached" with your patch applied, there is something that is broken by your patch, because the index and the HEAD does not change across write-tree in that test. If on the other hand the tests show the same result from these two "diff --cached" and the result is different from what the test expects, that means your patch changed the world order, i.e. an i-t-a entry used to be treated as if it were adding an empty blob to the index but it is now treated as non-existent, then that is a good thing and the only thing we need to update is what the test expects. I am guessing that instead of expecting dir/bar to be shown, it now should expect no output? Does adding an non-i-t-a entry help? It does not hurt, and it makes the test uses a non-empty output, making its effect more visible, which may or may not count as helping. ^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [PATCH v2] diff-lib.c: adjust position of i-t-a entries in diff 2015-03-17 17:57 ` Junio C Hamano @ 2015-03-18 12:47 ` Duy Nguyen 2015-03-18 20:30 ` Junio C Hamano 0 siblings, 1 reply; 18+ messages in thread From: Duy Nguyen @ 2015-03-18 12:47 UTC (permalink / raw) To: Junio C Hamano; +Cc: Michael J Gruber, Git Mailing List On Wed, Mar 18, 2015 at 12:57 AM, Junio C Hamano <gitster@pobox.com> wrote: > Duy Nguyen <pclouds@gmail.com> writes: > >> On Mon, Mar 16, 2015 at 09:05:45AM -0700, Junio C Hamano wrote: >>> The offending one came from eec3e7e4 (cache-tree: invalidate i-t-a >>> paths after generating trees, 2012-12-16), which was a fix to an >>> earlier bug where a cache-tree written out of an index with i-t-a >>> entries had incorrect information and still claimed it is fully >>> valid after write-tree rebuilt it. The test probably should add >>> another path without i-t-a bit, run the same "diff --cached" with >>> updated expectation before write-tre, and run the "diff --cached" >>> again to make sure it produces a result that match the updated >>> expectation. >> >> Would adding another non-i-t-a entry help? Before this patch >> "diff --cached" after write-tree shows the i-t-a entry only when >> eec3e7e4 is applied. But with this patch we don't show i-t-a entry any >> more, before or after write-tree, eec3e7e4 makes no visible difference. >> >> We could even revert eec3e7e4 and the outcome of "diff --cached" would >> be the same because we just sort of move the "invalidation" part from >> cache-tree to do_oneway_diff(). Not invalidating would speed up "diff >> --cached" when i-t-a entries are present. Still it may be a good idea >> to invalidate i-t-a paths to be on the safe side. Perhaps a patch like >> this to resurrect the test? > > My unerstanding of what eec3e7e4 (cache-tree: invalidate i-t-a paths > after generating trees, 2012-12-16) fixed was that in this sequence: > > ... > > So reverting the fix obviously is not the right thing to do. If the > tests show different results from two invocations of "diff --cached" > with your patch applied, there is something that is broken by your > patch, because the index and the HEAD does not change across > write-tree in that test. Right. I missed this but I think this is a less important test because I added a new test to make sure "diff --cached" ("git status" to be exact) outputs the right thing when i-t-a entries are present. > If on the other hand the tests show the same result from these two > "diff --cached" and the result is different from what the test > expects, that means your patch changed the world order, i.e. an > i-t-a entry used to be treated as if it were adding an empty blob to > the index but it is now treated as non-existent, then that is a good > thing and the only thing we need to update is what the test expects. > I am guessing that instead of expecting dir/bar to be shown, it now > should expect no output? Yes, no output. > Does adding an non-i-t-a entry help? It does not hurt, and it makes > the test uses a non-empty output, making its effect more visible, > which may or may not count as helping. But still, if I revert the change in cache-tree.c and force write-tree to produce valid cache-tree when i-t-a entries are present, this test still passes incorrectly. This is why I changed the test. -- Duy ^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [PATCH v2] diff-lib.c: adjust position of i-t-a entries in diff 2015-03-18 12:47 ` Duy Nguyen @ 2015-03-18 20:30 ` Junio C Hamano 2015-03-19 6:00 ` Junio C Hamano 2015-03-23 20:52 ` Junio C Hamano 0 siblings, 2 replies; 18+ messages in thread From: Junio C Hamano @ 2015-03-18 20:30 UTC (permalink / raw) To: Duy Nguyen; +Cc: Michael J Gruber, Git Mailing List Duy Nguyen <pclouds@gmail.com> writes: > Right. I missed this but I think this is a less important test > because I added a new test to make sure "diff --cached" ("git > status" to be exact) outputs the right thing when i-t-a entries > are present. OK. >> If on the other hand the tests show the same result from these two >> "diff --cached" and the result is different from what the test >> expects, that means your patch changed the world order, i.e. an >> i-t-a entry used to be treated as if it were adding an empty blob to >> the index but it is now treated as non-existent, then that is a good >> thing and the only thing we need to update is what the test expects. >> I am guessing that instead of expecting dir/bar to be shown, it now >> should expect no output? > > Yes, no output. Good, as that means your changes did not break things, right? > But still, if I revert the change in cache-tree.c and force write-tree > to produce valid cache-tree when i-t-a entries are present, this test > still passes incorrectly. This is worrysome. Doesn't that suggest that the diff-cache optimization is disabled and cache-tree that is marked as valid (because you "revert" the fix) is not looked at? That is the only explanation that makes sense to me---you write out a tree omitting i-t-a entries in the index and update the index without your earlier fix eec3e7e4 (cache-tree: invalidate i-t-a paths after generating trees, 2012-12-16), i.e. marking the cache-tree entries valid. A later invocation of diff-cache *should* trust that validity and just say "the tree and the index match" without even digging into the individual entries, at which point you should see a bogus result. If that is the case, it would be a performance regression, which may be already there before your patches or something your patches may have introduced. Ah, wait. I suspect that it all cancels out. * You "add -N dir/bar". You write-tree. The tree is written as if dir/bar is not there. cache-tree is updated and it is marked as valid (because you deliberately broke the earlier fix you made at eec3e7e4). * You run "diff-cache". It walks the HEAD and the cache-tree and finds that HEAD:dir and the cache-tree entry for "dir" records the same tree object name, and the cache-tree entry is marked "valid". Hence you declare "no differences". But for the updated definition of "diff-cache", there indeed is no difference. The HEAD and the index matches, because dir/bar does not yet exist. OK, so I think I can see how the result could work without invalidating the cache-tree entry that contains i-t-a entries. It might be even the right thing to do in general. We can view that invalidation a workaround to achieve the old behaviour of diff-cache, which used to report that dir/ are different between HEAD and index. We can even argue that it is the right thing to mark the cache-tree entry for dir/ as valid, no matter how many i-t-a entries are in there, as long as writing out the tree for dir/ out of index results in the same tree as the tree that is stored as HEAD:dir/. And from that viewpoint, keeping the earlier fix (invalidation code) when these patches are applied _is_ introducing a performance bug. Now, as you mentioned, there _may_ be codepaths that uses the same definition of "what's in the index" as what diff-cache used to take before your patches, and they may be broken by removing the invalidation. If we find such codepaths, we should treat their old behaviour as buggy and fix them, instead of reintroducing the invalidation and keep their current behaviour, as the new world order is "i-t-a entries in the index does not yet exist." Thanks for straightening my confusion out. ^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [PATCH v2] diff-lib.c: adjust position of i-t-a entries in diff 2015-03-18 20:30 ` Junio C Hamano @ 2015-03-19 6:00 ` Junio C Hamano 2015-03-24 1:15 ` Duy Nguyen 2015-03-23 20:52 ` Junio C Hamano 1 sibling, 1 reply; 18+ messages in thread From: Junio C Hamano @ 2015-03-19 6:00 UTC (permalink / raw) To: Duy Nguyen; +Cc: Michael J Gruber, Git Mailing List Junio C Hamano <gitster@pobox.com> writes: > Ah, wait. > > I suspect that it all cancels out. > ... > Now, as you mentioned, there _may_ be codepaths that uses the same > definition of "what's in the index" as what diff-cache used to take > before your patches, and they may be broken by removing the > invalidation. If we find such codepaths, we should treat their old > behaviour as buggy and fix them, instead of reintroducing the > invalidation and keep their current behaviour, as the new world > order is "i-t-a entries in the index does not yet exist." One potential negative consequence of the new world order I can immediately think of is this. In many operations, we try to be lenient to changes in the working tree as long as the index is clean. "read-tree -m" is the most visible one, where we require that the index and HEAD matches while allowing changes to working tree paths as long as they do not interfere with the paths that are involved in the merge. We need to make sure that the path dir/bar added by "add -N dir/bar", which in the new world order does not count as "index is not clean and there is a difference from HEAD", (1) does not interfere with the mergy operation that wants to touch dir (which _could_ even be expected to be a file) or dir/bar, and (2) is not lost because the mergy operation wants to touch dir or dir/bar, for example. ^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [PATCH v2] diff-lib.c: adjust position of i-t-a entries in diff 2015-03-19 6:00 ` Junio C Hamano @ 2015-03-24 1:15 ` Duy Nguyen 2015-03-24 17:00 ` Junio C Hamano 0 siblings, 1 reply; 18+ messages in thread From: Duy Nguyen @ 2015-03-24 1:15 UTC (permalink / raw) To: Junio C Hamano; +Cc: Michael J Gruber, Git Mailing List On Thu, Mar 19, 2015 at 1:00 PM, Junio C Hamano <gitster@pobox.com> wrote: > Junio C Hamano <gitster@pobox.com> writes: > >> Ah, wait. >> >> I suspect that it all cancels out. >> ... >> Now, as you mentioned, there _may_ be codepaths that uses the same >> definition of "what's in the index" as what diff-cache used to take >> before your patches, and they may be broken by removing the >> invalidation. If we find such codepaths, we should treat their old >> behaviour as buggy and fix them, instead of reintroducing the >> invalidation and keep their current behaviour, as the new world >> order is "i-t-a entries in the index does not yet exist." > > One potential negative consequence of the new world order I can > immediately think of is this. In many operations, we try to be > lenient to changes in the working tree as long as the index is > clean. "read-tree -m" is the most visible one, where we require > that the index and HEAD matches while allowing changes to working > tree paths as long as they do not interfere with the paths that are > involved in the merge. We need to make sure that the path dir/bar > added by "add -N dir/bar", which in the new world order does not > count as "index is not clean and there is a difference from HEAD", > (1) does not interfere with the mergy operation that wants to touch > dir (which _could_ even be expected to be a file) or dir/bar, and > (2) is not lost because the mergy operation wants to touch dir or > dir/bar, for example. "read-tree -m" does not invoke diff, does it? If I went with my previous approach (modifying unpack-trees to ignore i-t-a entries) then this could be a problem, but because unpack-trees is untouched, merge operations should not be impacted by this patch. Even if some other command does "diff --cached" first to abort early, if "diff --cached" fails to report "HEAD and index are different" as you described, I would expect unpack-trees to be able to deal with it anyway. PS. Sorry for the late response, busy fighting the evil last weekend. I blame Steam on Linux. -- Duy ^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [PATCH v2] diff-lib.c: adjust position of i-t-a entries in diff 2015-03-24 1:15 ` Duy Nguyen @ 2015-03-24 17:00 ` Junio C Hamano 0 siblings, 0 replies; 18+ messages in thread From: Junio C Hamano @ 2015-03-24 17:00 UTC (permalink / raw) To: Duy Nguyen; +Cc: Michael J Gruber, Git Mailing List Duy Nguyen <pclouds@gmail.com> writes: > "read-tree -m" does not invoke diff, does it? If I went with my > previous approach (modifying unpack-trees to ignore i-t-a entries) > then this could be a problem, but because unpack-trees is untouched, > merge operations should not be impacted by this patch. Theoretically yes, but not quite. I wouldn't be surprised if an enterprising soul saw an optimization opportunity in the "read-tree -m A B" codepath. When it finds that a tree in A and a valid cache-tree entry that corresponds to the tree matches, it could blow away all index entries covered by the cache-tree entry and replace them with B, either (1) unconditionally when "-u" is not given; or (2) as long as the working tree matches the index inside that directory when running with "-u". And such an optimization used to be a valid thing to do in the old world; but (1) will break in the new world, if we drop that invalidation---the i-t-a entries will be discarded from the index. As i-t-a is not a norm but an abberration, I'd rather keep the pessimizing invalidation to keep the door open for such an optimization for a more common case, and there may be other cases in which our correctness around i-t-a depends on. ^ permalink raw reply [flat|nested] 18+ messages in thread
* Re: [PATCH v2] diff-lib.c: adjust position of i-t-a entries in diff 2015-03-18 20:30 ` Junio C Hamano 2015-03-19 6:00 ` Junio C Hamano @ 2015-03-23 20:52 ` Junio C Hamano 1 sibling, 0 replies; 18+ messages in thread From: Junio C Hamano @ 2015-03-23 20:52 UTC (permalink / raw) To: Duy Nguyen; +Cc: Michael J Gruber, Git Mailing List Junio C Hamano <gitster@pobox.com> writes: > Ah, wait. > > I suspect that it all cancels out. > ... > OK, so I think I can see how the result could work without > invalidating the cache-tree entry that contains i-t-a entries. > > It might be even the right thing to do in general. We can view that > invalidation a workaround to achieve the old behaviour of diff-cache, > which used to report that dir/ are different between HEAD and index. So, we somehow left this hanging for a week without progress. Here is the version I am going to queue. Thanks. -- >8 -- From: Nguyễn Thái Ngọc Duy <pclouds@gmail.com> Date: Mon, 16 Mar 2015 20:56:46 +0700 Subject: [PATCH] diff-lib.c: adjust position of i-t-a entries in diff Entries added by "git add -N" are reminder for the user so that they don't forget to add them before committing. These entries appear in the index even though they are not real. Their presence in the index leads to a confusing "git status" like this: On branch master Changes to be committed: new file: foo Changes not staged for commit: modified: foo If you do a "git commit", "foo" will not be included even though "status" reports it as "to be committed". This patch changes the output to become On branch master Changes not staged for commit: new file: foo no changes added to commit The two hunks in diff-lib.c adjust "diff-index" and "diff-files" so that i-t-a entries appear as new files in diff-files and nothing in diff-index. Due to this change, diff-files may start to report "new files" for the first time. "add -u" needs to be told about this or it will die in denial, screaming "new files can't exist! Reality is wrong." Luckily, it's the only one among run_diff_files() callers that needs fixing. Now in the new world order, a hierarchy in the index that contain i-t-a paths is written out as a tree object as if these i-t-a entries do not exist, and comparing the index with such a tree object that would result from writing out the hierarchy will result in no difference. Update a test in t2203 that expected the i-t-a entries to appear as "added to the index" in the comparison to instead expect no output. An earlier change eec3e7e4 (cache-tree: invalidate i-t-a paths after generating trees, 2012-12-16) becomes an unnecessary pessimization in the new world order---a cache-tree in the index that corresponds to a hierarchy with i-t-a paths can now be marked as valid and record the object name of the tree that results from writing a tree object out of that hierarchy, as it will compare equal to that tree. Reverting the commit is left for the future, though, as it is purely a performance issue and no longer affects correctness. Helped-by: Michael J Gruber <git@drmicha.warpmail.net> Helped-by: Junio C Hamano <gitster@pobox.com> Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com> Signed-off-by: Junio C Hamano <gitster@pobox.com> --- builtin/add.c | 1 + diff-lib.c | 12 ++++++++++++ t/t2203-add-intent.sh | 23 +++++++++++++++++++---- t/t4011-diff-symlink.sh | 10 ++++++---- 4 files changed, 38 insertions(+), 8 deletions(-) diff --git a/builtin/add.c b/builtin/add.c index 3390933..ee370b0 100644 --- a/builtin/add.c +++ b/builtin/add.c @@ -63,6 +63,7 @@ static void update_callback(struct diff_queue_struct *q, switch (fix_unmerged_status(p, data)) { default: die(_("unexpected diff status %c"), p->status); + case DIFF_STATUS_ADDED: case DIFF_STATUS_MODIFIED: case DIFF_STATUS_TYPE_CHANGED: if (add_file_to_index(&the_index, path, data->flags)) { diff --git a/diff-lib.c b/diff-lib.c index a85c497..714501a 100644 --- a/diff-lib.c +++ b/diff-lib.c @@ -212,6 +212,11 @@ int run_diff_files(struct rev_info *revs, unsigned int option) ce->sha1, !is_null_sha1(ce->sha1), ce->name, 0); continue; + } else if (ce->ce_flags & CE_INTENT_TO_ADD) { + diff_addremove(&revs->diffopt, '+', ce->ce_mode, + EMPTY_BLOB_SHA1_BIN, 0, + ce->name, 0); + continue; } changed = match_stat_with_submodule(&revs->diffopt, ce, &st, @@ -376,6 +381,13 @@ static void do_oneway_diff(struct unpack_trees_options *o, struct rev_info *revs = o->unpack_data; int match_missing, cached; + /* i-t-a entries do not actually exist in the index */ + if (idx && (idx->ce_flags & CE_INTENT_TO_ADD)) { + idx = NULL; + if (!tree) + return; /* nothing to diff.. */ + } + /* if the entry is not checked out, don't examine work tree */ cached = o->index_only || (idx && ((idx->ce_flags & CE_VALID) || ce_skip_worktree(idx))); diff --git a/t/t2203-add-intent.sh b/t/t2203-add-intent.sh index 2a4a749..7c641bf 100755 --- a/t/t2203-add-intent.sh +++ b/t/t2203-add-intent.sh @@ -5,10 +5,24 @@ test_description='Intent to add' . ./test-lib.sh test_expect_success 'intent to add' ' + test_commit 1 && + git rm 1.t && + echo hello >1.t && echo hello >file && echo hello >elif && git add -N file && - git add elif + git add elif && + git add -N 1.t +' + +test_expect_success 'git status' ' + git status --porcelain | grep -v actual >actual && + cat >expect <<-\EOF && + DA 1.t + A elif + A file + EOF + test_cmp expect actual ' test_expect_success 'check result of "add -N"' ' @@ -43,7 +57,8 @@ test_expect_success 'i-t-a entry is simply ignored' ' git add -N nitfol && git commit -m second && test $(git ls-tree HEAD -- nitfol | wc -l) = 0 && - test $(git diff --name-only HEAD -- nitfol | wc -l) = 1 + test $(git diff --name-only HEAD -- nitfol | wc -l) = 0 && + test $(git diff --name-only -- nitfol | wc -l) = 1 ' test_expect_success 'can commit with an unrelated i-t-a entry in index' ' @@ -72,13 +87,13 @@ test_expect_success 'cache-tree invalidates i-t-a paths' ' : >dir/bar && git add -N dir/bar && git diff --cached --name-only >actual && - echo dir/bar >expect && + >expect && test_cmp expect actual && git write-tree >/dev/null && git diff --cached --name-only >actual && - echo dir/bar >expect && + >expect && test_cmp expect actual ' diff --git a/t/t4011-diff-symlink.sh b/t/t4011-diff-symlink.sh index 13e7f62..7452fce 100755 --- a/t/t4011-diff-symlink.sh +++ b/t/t4011-diff-symlink.sh @@ -139,11 +139,13 @@ test_expect_success SYMLINKS 'setup symlinks with attributes' ' test_expect_success SYMLINKS 'symlinks do not respect userdiff config by path' ' cat >expect <<-\EOF && diff --git a/file.bin b/file.bin - index e69de29..d95f3ad 100644 - Binary files a/file.bin and b/file.bin differ + new file mode 100644 + index 0000000..d95f3ad + Binary files /dev/null and b/file.bin differ diff --git a/link.bin b/link.bin - index e69de29..dce41ec 120000 - --- a/link.bin + new file mode 120000 + index 0000000..dce41ec + --- /dev/null +++ b/link.bin @@ -0,0 +1 @@ +file.bin -- 2.3.4-437-g9384a34 ^ permalink raw reply related [flat|nested] 18+ messages in thread
* [PATCH 2/2] diff-files: mark i-t-a paths as "new" 2015-03-09 14:14 [PATCH/RFC 0/2] Bug fixes regarding diff and "git add -N" Nguyễn Thái Ngọc Duy 2015-03-09 14:14 ` [PATCH 1/2] diff --cached: do not report i-t-a entries as "new" Nguyễn Thái Ngọc Duy @ 2015-03-09 14:14 ` Nguyễn Thái Ngọc Duy 2015-03-15 7:05 ` Junio C Hamano 2015-03-09 15:45 ` [PATCH] t2203,t4011: adjust to changed intent-to-add treatment Michael J Gruber 2 siblings, 1 reply; 18+ messages in thread From: Nguyễn Thái Ngọc Duy @ 2015-03-09 14:14 UTC (permalink / raw) To: git; +Cc: Nguyễn Thái Ngọc Duy Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com> --- builtin/add.c | 1 + diff-lib.c | 5 +++++ 2 files changed, 6 insertions(+) diff --git a/builtin/add.c b/builtin/add.c index 3390933..ee370b0 100644 --- a/builtin/add.c +++ b/builtin/add.c @@ -63,6 +63,7 @@ static void update_callback(struct diff_queue_struct *q, switch (fix_unmerged_status(p, data)) { default: die(_("unexpected diff status %c"), p->status); + case DIFF_STATUS_ADDED: case DIFF_STATUS_MODIFIED: case DIFF_STATUS_TYPE_CHANGED: if (add_file_to_index(&the_index, path, data->flags)) { diff --git a/diff-lib.c b/diff-lib.c index db0e6f8..5f1afa4 100644 --- a/diff-lib.c +++ b/diff-lib.c @@ -212,6 +212,11 @@ int run_diff_files(struct rev_info *revs, unsigned int option) ce->sha1, !is_null_sha1(ce->sha1), ce->name, 0); continue; + } else if (ce->ce_flags & CE_INTENT_TO_ADD) { + diff_addremove(&revs->diffopt, '+', ce->ce_mode, + EMPTY_BLOB_SHA1_BIN, 0, + ce->name, 0); + continue; } changed = match_stat_with_submodule(&revs->diffopt, ce, &st, -- 2.3.0.rc1.137.g477eb31 ^ permalink raw reply related [flat|nested] 18+ messages in thread
* Re: [PATCH 2/2] diff-files: mark i-t-a paths as "new" 2015-03-09 14:14 ` [PATCH 2/2] diff-files: mark i-t-a paths as "new" Nguyễn Thái Ngọc Duy @ 2015-03-15 7:05 ` Junio C Hamano 0 siblings, 0 replies; 18+ messages in thread From: Junio C Hamano @ 2015-03-15 7:05 UTC (permalink / raw) To: Nguyễn Thái Ngọc Duy; +Cc: git Nguyễn Thái Ngọc Duy <pclouds@gmail.com> writes: > Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com> > --- > builtin/add.c | 1 + > diff-lib.c | 5 +++++ > 2 files changed, 6 insertions(+) > > diff --git a/builtin/add.c b/builtin/add.c > index 3390933..ee370b0 100644 > --- a/builtin/add.c > +++ b/builtin/add.c > @@ -63,6 +63,7 @@ static void update_callback(struct diff_queue_struct *q, > switch (fix_unmerged_status(p, data)) { > default: > die(_("unexpected diff status %c"), p->status); > + case DIFF_STATUS_ADDED: > case DIFF_STATUS_MODIFIED: > case DIFF_STATUS_TYPE_CHANGED: > if (add_file_to_index(&the_index, path, data->flags)) { Is this related to making "diff-files" show an i-t-a as "new", or something else? Ahh, "added" would have never appeared in diff-files output (because by definition comparing index and working tree for only paths known to the index would never produce "add"), and the point of this series is to use that status to signal that the path is marked as i-t-a. And an i-t-a path is "not yet exist in the index, known to the system, and exists in the working tree", so catching that new case here and calling add_file_to_index() would cause such a path to be truly added to the index (this is "add -u" codepath, right?). Makes sense. > diff --git a/diff-lib.c b/diff-lib.c > index db0e6f8..5f1afa4 100644 > --- a/diff-lib.c > +++ b/diff-lib.c > @@ -212,6 +212,11 @@ int run_diff_files(struct rev_info *revs, unsigned int option) > ce->sha1, !is_null_sha1(ce->sha1), > ce->name, 0); > continue; > + } else if (ce->ce_flags & CE_INTENT_TO_ADD) { > + diff_addremove(&revs->diffopt, '+', ce->ce_mode, > + EMPTY_BLOB_SHA1_BIN, 0, > + ce->name, 0); > + continue; > } > > changed = match_stat_with_submodule(&revs->diffopt, ce, &st, And this makes sense, of course. The way "add -N" entries appear in "git status" has been disturbing for quite a while to me, too. Thanks for starting to look into it. ^ permalink raw reply [flat|nested] 18+ messages in thread
* [PATCH] t2203,t4011: adjust to changed intent-to-add treatment 2015-03-09 14:14 [PATCH/RFC 0/2] Bug fixes regarding diff and "git add -N" Nguyễn Thái Ngọc Duy 2015-03-09 14:14 ` [PATCH 1/2] diff --cached: do not report i-t-a entries as "new" Nguyễn Thái Ngọc Duy 2015-03-09 14:14 ` [PATCH 2/2] diff-files: mark i-t-a paths as "new" Nguyễn Thái Ngọc Duy @ 2015-03-09 15:45 ` Michael J Gruber 2015-03-15 7:07 ` Junio C Hamano 2 siblings, 1 reply; 18+ messages in thread From: Michael J Gruber @ 2015-03-09 15:45 UTC (permalink / raw) To: git; +Cc: Nguyễn Thái Ngọc Duy Signed-off-by: Michael J Gruber <git@drmicha.warpmail.net> --- For the record, the tests would need to change like this, and it makes a lot of sense. After the change, "i-t-a" is not a "change staged in the index" any more - and in fact in never was, as "git commit" shows. t/t2203-add-intent.sh | 7 ++++--- t/t4011-diff-symlink.sh | 10 ++++++---- 2 files changed, 10 insertions(+), 7 deletions(-) diff --git a/t/t2203-add-intent.sh b/t/t2203-add-intent.sh index 2a4a749..1a9b3c4 100755 --- a/t/t2203-add-intent.sh +++ b/t/t2203-add-intent.sh @@ -43,7 +43,8 @@ test_expect_success 'i-t-a entry is simply ignored' ' git add -N nitfol && git commit -m second && test $(git ls-tree HEAD -- nitfol | wc -l) = 0 && - test $(git diff --name-only HEAD -- nitfol | wc -l) = 1 + test $(git diff --name-only HEAD -- nitfol | wc -l) = 0 && + test $(git diff --name-only -- nitfol | wc -l) = 1 ' test_expect_success 'can commit with an unrelated i-t-a entry in index' ' @@ -71,13 +72,13 @@ test_expect_success 'cache-tree invalidates i-t-a paths' ' : >dir/bar && git add -N dir/bar && - git diff --cached --name-only >actual && + git diff --name-only >actual && echo dir/bar >expect && test_cmp expect actual && git write-tree >/dev/null && - git diff --cached --name-only >actual && + git diff --name-only >actual && echo dir/bar >expect && test_cmp expect actual ' diff --git a/t/t4011-diff-symlink.sh b/t/t4011-diff-symlink.sh index 13e7f62..7452fce 100755 --- a/t/t4011-diff-symlink.sh +++ b/t/t4011-diff-symlink.sh @@ -139,11 +139,13 @@ test_expect_success SYMLINKS 'setup symlinks with attributes' ' test_expect_success SYMLINKS 'symlinks do not respect userdiff config by path' ' cat >expect <<-\EOF && diff --git a/file.bin b/file.bin - index e69de29..d95f3ad 100644 - Binary files a/file.bin and b/file.bin differ + new file mode 100644 + index 0000000..d95f3ad + Binary files /dev/null and b/file.bin differ diff --git a/link.bin b/link.bin - index e69de29..dce41ec 120000 - --- a/link.bin + new file mode 120000 + index 0000000..dce41ec + --- /dev/null +++ b/link.bin @@ -0,0 +1 @@ +file.bin -- 2.3.1.303.g5174db1 ^ permalink raw reply related [flat|nested] 18+ messages in thread
* Re: [PATCH] t2203,t4011: adjust to changed intent-to-add treatment 2015-03-09 15:45 ` [PATCH] t2203,t4011: adjust to changed intent-to-add treatment Michael J Gruber @ 2015-03-15 7:07 ` Junio C Hamano 0 siblings, 0 replies; 18+ messages in thread From: Junio C Hamano @ 2015-03-15 7:07 UTC (permalink / raw) To: Michael J Gruber; +Cc: git, Nguyễn Thái Ngọc Duy Michael J Gruber <git@drmicha.warpmail.net> writes: > Signed-off-by: Michael J Gruber <git@drmicha.warpmail.net> > --- > For the record, the tests would need to change like this, and it makes > a lot of sense. After the change, "i-t-a" is not a "change staged in > the index" any more - and in fact in never was, as "git commit" shows. Perhaps another follow-up patch can illustrate how these entries should show "git status", both in the longform and -s output? > > t/t2203-add-intent.sh | 7 ++++--- > t/t4011-diff-symlink.sh | 10 ++++++---- > 2 files changed, 10 insertions(+), 7 deletions(-) > > diff --git a/t/t2203-add-intent.sh b/t/t2203-add-intent.sh > index 2a4a749..1a9b3c4 100755 > --- a/t/t2203-add-intent.sh > +++ b/t/t2203-add-intent.sh > @@ -43,7 +43,8 @@ test_expect_success 'i-t-a entry is simply ignored' ' > git add -N nitfol && > git commit -m second && > test $(git ls-tree HEAD -- nitfol | wc -l) = 0 && > - test $(git diff --name-only HEAD -- nitfol | wc -l) = 1 > + test $(git diff --name-only HEAD -- nitfol | wc -l) = 0 && > + test $(git diff --name-only -- nitfol | wc -l) = 1 > ' > > test_expect_success 'can commit with an unrelated i-t-a entry in index' ' > @@ -71,13 +72,13 @@ test_expect_success 'cache-tree invalidates i-t-a paths' ' > > : >dir/bar && > git add -N dir/bar && > - git diff --cached --name-only >actual && > + git diff --name-only >actual && > echo dir/bar >expect && > test_cmp expect actual && > > git write-tree >/dev/null && > > - git diff --cached --name-only >actual && > + git diff --name-only >actual && > echo dir/bar >expect && > test_cmp expect actual > ' > diff --git a/t/t4011-diff-symlink.sh b/t/t4011-diff-symlink.sh > index 13e7f62..7452fce 100755 > --- a/t/t4011-diff-symlink.sh > +++ b/t/t4011-diff-symlink.sh > @@ -139,11 +139,13 @@ test_expect_success SYMLINKS 'setup symlinks with attributes' ' > test_expect_success SYMLINKS 'symlinks do not respect userdiff config by path' ' > cat >expect <<-\EOF && > diff --git a/file.bin b/file.bin > - index e69de29..d95f3ad 100644 > - Binary files a/file.bin and b/file.bin differ > + new file mode 100644 > + index 0000000..d95f3ad > + Binary files /dev/null and b/file.bin differ > diff --git a/link.bin b/link.bin > - index e69de29..dce41ec 120000 > - --- a/link.bin > + new file mode 120000 > + index 0000000..dce41ec > + --- /dev/null > +++ b/link.bin > @@ -0,0 +1 @@ > +file.bin ^ permalink raw reply [flat|nested] 18+ messages in thread
end of thread, other threads:[~2015-03-24 17:51 UTC | newest] Thread overview: 18+ messages (download: mbox.gz follow: Atom feed -- links below jump to the message on this page -- 2015-03-09 14:14 [PATCH/RFC 0/2] Bug fixes regarding diff and "git add -N" Nguyễn Thái Ngọc Duy 2015-03-09 14:14 ` [PATCH 1/2] diff --cached: do not report i-t-a entries as "new" Nguyễn Thái Ngọc Duy 2015-03-15 6:55 ` Junio C Hamano 2015-03-16 13:56 ` [PATCH v2] diff-lib.c: adjust position of i-t-a entries in diff Nguyễn Thái Ngọc Duy 2015-03-16 15:15 ` Michael J Gruber 2015-03-16 16:05 ` Junio C Hamano 2015-03-17 14:07 ` Duy Nguyen 2015-03-17 17:57 ` Junio C Hamano 2015-03-18 12:47 ` Duy Nguyen 2015-03-18 20:30 ` Junio C Hamano 2015-03-19 6:00 ` Junio C Hamano 2015-03-24 1:15 ` Duy Nguyen 2015-03-24 17:00 ` Junio C Hamano 2015-03-23 20:52 ` Junio C Hamano 2015-03-09 14:14 ` [PATCH 2/2] diff-files: mark i-t-a paths as "new" Nguyễn Thái Ngọc Duy 2015-03-15 7:05 ` Junio C Hamano 2015-03-09 15:45 ` [PATCH] t2203,t4011: adjust to changed intent-to-add treatment Michael J Gruber 2015-03-15 7:07 ` Junio C Hamano
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox; as well as URLs for NNTP newsgroup(s).