Re: [PATCH v3 3/9] t6111: new TREESAME test set

2013-05-07 Thread Junio C Hamano
Kevin Bracey ke...@bracey.fi writes:

 On 06/05/2013 23:36, Junio C Hamano wrote:
 Kevin Bracey ke...@bracey.fi writes:

 +#,---E--.   *H--. * marks !TREESAME parent 
 paths
 +#   /\ / \*
 +# *A--*B---D--*F-*G-K-*L-*M
 +#   \ /*   \   /
 +#`-C-'  `-*I-*J
 +#
 +# A creates file, B and F change it.
 +# Odd merge G takes the old version from B.
 +# I changes it, but J reverts it.
 +# H and L both change it, and M merges those changes.
 + ...
 ...
 +check_outcome failure 'M L H' G..M -- file # includes J I
 +check_outcome failure 'M L H' G..M --parents -- file # includes J I
 I am not sure if it should be a failure or your expectation is wrong.
 G is outside the graph, so as far as the remainder of the graph is concerned,
 J is the sole remaining parent of K and I and J did change the path in 
 question.

 What makes you think I and J should be excluded in these cases?

 Because it's the simplest answer to the question what happened in
 M since G, which is what G..M is supposed to mean. ...
 
 This all comes about because the formal graph definition doesn't
 match the user interface. The question B..C currently generates
 a graph of all commits in C since B, and the connections between
 those commits. It turns out to be problematic that the graph
 doesn't include the connection to B itself. It would be fine if
 only worrying about nodes in the graph. But it's not fine when you
 start doing graph operations that care about edge connections to
 parents.

OK, that makes sense.

 ...
 What I'm effectively doing is extending the graph to actually
 include the unshown bottom. I think it just makes more sense.

Yup, and this is a good summary.


 ... I assume you mean:

 That is, -a-p F..M makes F the sole remaining parent of G and G does 
 change the
 path from F so it should be shown, while -a-p E..M makes E the sole parent 
 of G,
 and G does not change the path from E, so it should not be shown.

Yes.

 Which is the way the logic works - we treat F and E as
 interesting/priority parents when they're specified as a bottom in
 each case. Without doing that, G would have 2 differing and
 equally (un)important parents in each case, and thus would be
 shown in both cases.

 In this case, the same logic says that G is treated as an
 interesting parent of K because it is the specified bottom. Which
 then enables the default following to follow that path direct to
 G, rather than having to go down the IJ path (which leads to G
 anyway).

OK.
--
To unsubscribe from this list: send the line unsubscribe git in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH v3 3/9] t6111: new TREESAME test set

2013-05-06 Thread Junio C Hamano
Kevin Bracey ke...@bracey.fi writes:

 Some side branching and odd merging to illustrate various flaws in
 revision list scans, particularly when limiting the list.

 Many expected failures, which will be gone by the end of the history
 traversal refinements series.

 Signed-off-by: Kevin Bracey ke...@bracey.fi
 ---
  t/t6111-rev-list-treesame.sh | 180 
 +++
  1 file changed, 180 insertions(+)
  create mode 100755 t/t6111-rev-list-treesame.sh

 diff --git a/t/t6111-rev-list-treesame.sh b/t/t6111-rev-list-treesame.sh
 new file mode 100755
 index 000..602c02d
 --- /dev/null
 +++ b/t/t6111-rev-list-treesame.sh
 @@ -0,0 +1,180 @@
 +#!/bin/sh
 +#
 +#,---E--.   *H--. * marks !TREESAME parent paths
 +#   /\ / \*
 +# *A--*B---D--*F-*G-K-*L-*M
 +#   \ /*   \   /
 +#`-C-'  `-*I-*J
 +#
 +# A creates file, B and F change it.
 +# Odd merge G takes the old version from B.
 +# I changes it, but J reverts it.
 +# H and L both change it, and M merges those changes.

... and because J is a revert of I, K ends up merging the same and
being the same with both G and J.

 +test_description='TREESAME and limiting'
 +
 +. ./test-lib.sh
 +
 +note () {
 + git tag $1
 +}
 +
 +unnote () {
 + git name-rev --tags --stdin | sed -e s|$_x40 (tags/\([^)]*\)) |\1 |g
 +}
 +
 +test_expect_success setup '
 + test_commit Initial file file Hi there A 
 + git branch other-branch 
 +
 + test_commit file=Hello file Hello B 
 + git branch third-branch 
 +
 + git checkout other-branch 
 + test_commit Added other other Hello C 
 +
 + git checkout master 
 + test_merge D other-branch 
 +
 + git checkout third-branch 
 + test_commit Third file third Nothing E 
 +
 + git checkout master 
 + test_commit file=Blah file Blah F 
 +
 + test_tick  git merge --no-commit third-branch 
 + git checkout third-branch file 
 + git commit 
 + note G 
 + git branch fiddler-branch 
 +
 + git checkout -b part2-branch 
 + test_commit file=Part 2 file Part 2 H 
 +
 + git checkout fiddler-branch 
 + test_commit Bad commit file Silly I 
 +
 + test_tick  git revert I  note J 
 +
 + git checkout master 
 + test_tick  git merge --no-ff fiddler-branch 
 + note K
 +
 + test_commit file=Part 1 file Part 1 L 
 +
 + test_tick  test_must_fail git merge part2-branch 
 + test_commit M file Parts 1+2
 +'
 +
 +FMT='tformat:%P  %H | %s'
 +
 +# could we soup this up to optionally check parents? So (BA)C would check
 +# that C is shown and has parents B A.

Sounds like a good thing to do, especially given that some of the
earlier issues you brought up triggered only when --parents is not
used, so...

Perhaps something like the attached.

 +check_outcome () {
 + outcome=$1
 + shift
 + for c in $1
 + do
 + echo $c
 + done expect 

Maybe

printf %s\n $1 expect

is more fashionable these days?

 +# Odd merge G drops a change in F. Important that G is listed in all
 +# except the most basic list. Achieving this means normal merge D will also 
 be
 +# shown in normal full-history, as we can't distinguish unless we do a
 +# simplification pass. After simplification, D is dropped but G remains.
 +check_result 'M L K J I H G F E D C B A'

I'll read the expectation and comment on them in a separate message.

 t/t6111-rev-list-treesame.sh | 30 +-
 1 file changed, 21 insertions(+), 9 deletions(-)

diff --git a/t/t6111-rev-list-treesame.sh b/t/t6111-rev-list-treesame.sh
index 602c02d..f4c9cac 100755
--- a/t/t6111-rev-list-treesame.sh
+++ b/t/t6111-rev-list-treesame.sh
@@ -20,7 +20,7 @@ note () {
 }
 
 unnote () {
-   git name-rev --tags --stdin | sed -e s|$_x40 (tags/\([^)]*\)) |\1 |g
+   git name-rev --tags --stdin | sed -e s|$_x40 (tags/\([^)]*\))\([   
]\)|\1\2|g
 }
 
 test_expect_success setup '
@@ -66,23 +66,34 @@ test_expect_success setup '
test_commit M file Parts 1+2
 '
 
-FMT='tformat:%P%H | %s'
-
 # could we soup this up to optionally check parents? So (BA)C would check
 # that C is shown and has parents B A.
 check_outcome () {
outcome=$1
shift
-   for c in $1
-   do
-   echo $c
-   done expect 
-   shift 
+
+   case $1 in
+   *(*)
+   FMT=%P %H | %s
+   munge_actual=
+   s/^\([^ ]*\)\([^ ]*\) .*/(\1)\2/
+   s/ //g
+   s/()//
+   
+   ;;
+   *)
+   FMT=%H | %s
+   munge_actual=s/^\([^ ]*\) .*/\1/
+   ;;
+   esac 
+   printf %s\n $1 expect 
+   shift
+
param=$* 
test_expect_$outcome log $param '
git log --format=$FMT $param |
unnote actual 
-   sed -e s/^.*   \([^ ]*\) .*/\1/ 

Re: [PATCH v3 3/9] t6111: new TREESAME test set

2013-05-06 Thread Junio C Hamano
Kevin Bracey ke...@bracey.fi writes:

 +#,---E--.   *H--. * marks !TREESAME parent paths
 +#   /\ / \*
 +# *A--*B---D--*F-*G-K-*L-*M
 +#   \ /*   \   /
 +#`-C-'  `-*I-*J
 +#
 +# A creates file, B and F change it.
 +# Odd merge G takes the old version from B.
 +# I changes it, but J reverts it.
 +# H and L both change it, and M merges those changes.
 + ...
 +# Odd merge G drops a change in F. Important that G is listed in all
 +# except the most basic list. Achieving this means normal merge D will also 
 be
 +# shown in normal full-history, as we can't distinguish unless we do a
 +# simplification pass. After simplification, D is dropped but G remains.
 +check_result 'M L K J I H G F E D C B A'

OK.

 +check_result 'M H L K J I G E F D C B A' --topo-order

OK.

 +check_result 'M L H B A' -- file

OK.

 +check_result 'M L H B A' --parents -- file

OK.

 +check_outcome failure 'M L J I H G F D B A' --full-history -- file # drops G

This breaks the promise that full history at least gives a connected
graph.

 +check_result 'M L K J I H G F D B A' --full-history --parents -- file

And it is saved by --parents; the (parents)commit notation may
make it easier to read the above two tests.

 +check_outcome failure 'M H L J I G F B A' --simplify-merges -- file # drops G

The hsitory simplify merges gives ought to be a full history that
keeps any commit that locally touches the specified path, so keeping
I and J even though they do not contribute to the end result is
correct.  The path in question is the same between G and B, but
again, F should be shown because it should be in the full history.

Even though E simplifies down to B, making G a merge between B and F
(the former is an ancestor of the latter), G is kept, because...?

Because the path at B and F are different?

I have to wonder what should happen if D makes path different from B,
and then F makes path the same as B.  B and F should still be kept.

So because the path at B and F are different is not the reason why
we keep G.  How do we decide why G must be kept?

 +check_result 'M L K G F D B A' --first-parent
 +check_result 'M L G F B A' --first-parent -- file

OK.

 +# Check that odd merge G remains shown when F is the bottom.

I did not have a chance to say this when you responded in the
previous round with that bottom thing before you sent this new
round, but I am not sure if it is a good idea to pay special
attention to the bottom-ness.  Very often, instead of running git
log -- path and stopping when seeing enough by killing the pager,
people run git log HEAD~200.. -- path to pick recent enough
commits, but the number 200 is very much arbitrary.

 +check_result 'M L K J I H G E' F..M

OK.

 +check_result 'M H L K J I G E' F..M --topo-order

OK.  But a note about style: options should come before revision
ranges.

 +check_result 'M L H' F..M -- file

OK.  It is still one possible history to explain what we have in the
path at the end.

 +check_result 'M L H' F..M --parents -- file # L+H's parents rewritten to B, 
 so more useful than it may seem

OK.

 +check_outcome failure 'M L J I H G' F..M --full-history -- file # drops G

G is same as E which is in the graph (F and B are the boundaries of
the history, and F is no special than B in that regard).  You want
to show a merge that is different from at least one parent (as
opposed to showing only when it is different from all parents), so
you want to show G.  OK.

 +check_result 'M L K J I H G' F..M --full-history --parents -- file

OK.

It almost makes me suspect that the --full-history option should
flip revs-rewrite_parents on (but not revs-print_parents, unless
the --parents option asks us to) when the option is parsed.

 +check_outcome failure 'M H L J I G' F..M --simplify-merges -- file # drops G

The same as the --full-history without --parents before.

 +check_result 'M L K J I H G' F..M --ancestry-path
 +check_outcome failure 'M L J I H G' F..M --ancestry-path -- file # drops G

With --ancestry-path, what G does relative to E becomes irrelevant,
because E is not in the F..M graph.  G changes path relative to its
remaining parent F, so it should be shown.  OK.

 +check_result 'M L K J I H G' F..M --ancestry-path --parents -- file

OK.  Again this makes me suspect --ancestry-path should flip
revs-rewrite_parents on.

 +check_result 'M H L J I G' F..M --ancestry-path --simplify-merges -- file

 +check_result 'M L K G' F..M --first-parent
 +check_result 'M L G' F..M --first-parent -- file
 +
 +# Note that G is pruned when E is the bottom, even if it's the same commit 
 list
 +# If we want history since E, then we're quite happy to ignore G that took E.
 +check_result 'M L K J I H G' E..M --ancestry-path

OK.

 +check_result 'M L J I H' E..M --ancestry-path -- file

Because F is outside our graph with --ancestry-path, G does not
bring anything new to path relative to its remaining parent E and
should not be shown.