From: Greg Price <price@ksplice.com>
To: Junio C Hamano <gitster@pobox.com>
Cc: Johannes Sixt <j.sixt@viscovery.net>,
git@vger.kernel.org, Stephen Haberman <stephen@exigencecorp.com>
Subject: Re: [PATCH] Fix rebase -p --onto
Date: Fri, 17 Jul 2009 12:33:50 -0400 [thread overview]
Message-ID: <20090717163350.GK7878@vinegar-pot.mit.edu> (raw)
In-Reply-To: <7vk52767el.fsf@alter.siamese.dyndns.org>
On Fri, Jul 17, 2009 at 01:27:46AM -0700, Junio C Hamano wrote:
> Hmm, if the original history were
>
> .---X---o---o---o---M
> \ /
> x---x---x---x---x
>
> Y
>
> and the rebase is about moving history leading to M since X on top of Y,
> I would actually have agreed that this
>
> .---X---o---o---o---M
> \ /
> x---x---x---x---x
> \
> Y---o'--o'--o'--M'
>
> would be the right thing to do (IOW, I would agree with you).
Yes, I agree.
> Can the current code distinguish the two cases?
Yes. Stephen's commit acc8559 already limits $TODO to the descendants
of the merge-bases of HEAD and UPSTREAM, which captures the
distinction here. When we rebase from X, the merge-base is X, so only
that branch moves. When we rebase from the base of both branches,
both branches should move.
I've added a test demonstrating this case to a revised version of the
patch, below.
Greg
>From dcab1103e14394364c15136823269416f8c56e97 Mon Sep 17 00:00:00 2001
From: Greg Price <price@ksplice.com>
Date: Thu, 16 Jul 2009 12:48:40 -0400
Subject: [PATCH] Fix rebase -p --onto
In a rebase with --onto, the correct test for whether we can skip
rewriting a commit is if it is already on top of $ONTO, not $UPSTREAM.
Without --onto, this distinction does not exist and the behavior does
not change.
In the situation
X---o---o---o---M
\ /
x---x---x---x
Y
if we try to move the branches merged at M from their base on X to be
based on Y, so as to get
X
Y---o'--o'--o'--M'
\ /
x'--x'--x'--x'
then we fail. The command `git rebase -p --onto Y X M` moves only the
first-parent chain, like so:
X
\
x---x---x---x
\
Y---o'--o'--o'--M'
because it mistakenly drops the other branch(es) x---x---x---x from
the TODO file. This tests and fixes this behavior.
Signed-off-by: Greg Price <price@ksplice.com>
---
git-rebase--interactive.sh | 2 +-
t/t3414-rebase-preserve-onto.sh | 80 +++++++++++++++++++++++++++++++++++++++
2 files changed, 81 insertions(+), 1 deletions(-)
create mode 100755 t/t3414-rebase-preserve-onto.sh
diff --git a/git-rebase--interactive.sh b/git-rebase--interactive.sh
index f96d887..23ded48 100755
--- a/git-rebase--interactive.sh
+++ b/git-rebase--interactive.sh
@@ -703,7 +703,7 @@ first and then run 'git rebase --continue' again."
preserve=t
for p in $(git rev-list --parents -1 $sha1 | cut -d' ' -s -f2-)
do
- if test -f "$REWRITTEN"/$p -a \( $p != $UPSTREAM -o $sha1 = $first_after_upstream \)
+ if test -f "$REWRITTEN"/$p -a \( $p != $ONTO -o $sha1 = $first_after_upstream \)
then
preserve=f
fi
diff --git a/t/t3414-rebase-preserve-onto.sh b/t/t3414-rebase-preserve-onto.sh
new file mode 100755
index 0000000..80019ee
--- /dev/null
+++ b/t/t3414-rebase-preserve-onto.sh
@@ -0,0 +1,80 @@
+#!/bin/sh
+#
+# Copyright (c) 2009 Greg Price
+#
+
+test_description='git rebase -p should respect --onto
+
+In a rebase with --onto, we should rewrite all the commits that
+aren'"'"'t on top of $ONTO, even if they are on top of $UPSTREAM.
+'
+. ./test-lib.sh
+
+. ../lib-rebase.sh
+
+# Set up branches like this:
+# A1---B1---E1---F1---G1
+# \ \ /
+# \ \--C1---D1--/
+# H1
+
+test_expect_success 'setup' '
+ test_commit A1 &&
+ test_commit B1 &&
+ test_commit C1 &&
+ test_commit D1 &&
+ git reset --hard B1 &&
+ test_commit E1 &&
+ test_commit F1 &&
+ test_merge G1 D1 &&
+ git reset --hard A1 &&
+ test_commit H1
+'
+
+# Now rebase merge G1 from both branches' base B1, both should move:
+# A1---B1---E1---F1---G1
+# \ \ /
+# \ \--C1---D1--/
+# \
+# H1---E2---F2---G2
+# \ /
+# \--C2---D2--/
+
+test_expect_success 'rebase from B1 onto H1' '
+ git checkout G1 &&
+ git rebase -p --onto H1 B1 &&
+ test "$(git rev-parse HEAD^1^1^1)" = "$(git rev-parse H1)" &&
+ test "$(git rev-parse HEAD^2^1^1)" = "$(git rev-parse H1)"
+'
+
+# On the other hand if rebase from E1 which is within one branch,
+# then the other branch stays:
+# A1---B1---E1---F1---G1
+# \ \ /
+# \ \--C1---D1--/
+# \ \
+# H1-----F3-----G3
+
+test_expect_success 'rebase from E1 onto H1' '
+ git checkout G1 &&
+ git rebase -p --onto H1 E1 &&
+ test "$(git rev-parse HEAD^1^1)" = "$(git rev-parse H1)" &&
+ test "$(git rev-parse HEAD^2)" = "$(git rev-parse D1)"
+'
+
+# And the same if we rebase from a commit in the second-parent branch.
+# A1---B1---E1---F1----G1
+# \ \ \ /
+# \ \--C1---D1-\-/
+# \ \
+# H1------D3------G4
+
+test_expect_success 'rebase from C1 onto H1' '
+ git checkout G1 &&
+ git rev-list --first-parent --pretty=oneline C1..G1 &&
+ git rebase -p --onto H1 C1 &&
+ test "$(git rev-parse HEAD^2^1)" = "$(git rev-parse H1)" &&
+ test "$(git rev-parse HEAD^1)" = "$(git rev-parse F1)"
+'
+
+test_done
--
1.6.3.1.499.ge7b8da
prev parent reply other threads:[~2009-07-17 16:34 UTC|newest]
Thread overview: 9+ messages / expand[flat|nested] mbox.gz Atom feed top
2009-07-16 23:00 [PATCH] Fix rebase -p --onto Greg Price
2009-07-17 6:38 ` Johannes Sixt
2009-07-17 8:27 ` Junio C Hamano
2009-07-17 8:40 ` Johannes Sixt
2009-07-17 8:47 ` Johannes Sixt
2009-07-17 16:48 ` Greg Price
2009-07-17 18:32 ` Johannes Schindelin
2009-07-17 19:00 ` Greg Price
2009-07-17 16:33 ` Greg Price [this message]
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20090717163350.GK7878@vinegar-pot.mit.edu \
--to=price@ksplice.com \
--cc=git@vger.kernel.org \
--cc=gitster@pobox.com \
--cc=j.sixt@viscovery.net \
--cc=stephen@exigencecorp.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
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).