From: "Phillip Wood via GitGitGadget" <gitgitgadget@gmail.com>
To: git@vger.kernel.org
Cc: Philippe Blain <levraiphilippeblain@gmail.com>,
Denton Liu <liu.denton@gmail.com>,
Johannes Schindelin <Johannes.Schindelin@gmx.de>,
Phillip Wood <phillip.wood123@gmail.com>,
Elijah Newren <newren@gmail.com>,
Junio C Hamano <gitster@pobox.com>,
Jonathan Tan <jonathantanmy@google.com>,
Phillip Wood <phillip.wood@dunelm.org.uk>,
Phillip Wood <phillip.wood@dunelm.org.uk>
Subject: [PATCH v3 4/8] rebase: store orig_head as a commit
Date: Thu, 13 Oct 2022 08:42:40 +0000 [thread overview]
Message-ID: <dc056b13ed5c62729f97bd2cedbe769c531f4bc4.1665650564.git.gitgitgadget@gmail.com> (raw)
In-Reply-To: <pull.1323.v3.git.1665650564.gitgitgadget@gmail.com>
From: Phillip Wood <phillip.wood@dunelm.org.uk>
Using a struct commit rather than a struct oid to hold orig_head means
that we error out straight away if the branch being rebased does not
point to a commit. It also simplifies the code that handles finding
the merge base and fork point as it no longer has to convert from an
oid to a commit.
To avoid changing the behavior of "git rebase <upstream> <branch>" we
keep the existing call to read_ref() and use lookup_commit_reference()
on the oid returned by that rather than calling
lookup_commit_reference_by_name() which applies the ref dwim rules to
its argument. lookup_commit_reference() will dereference tag objects
but we do not expect the branch being rebased to be pointing to a tag
object.
Helped-by: Junio C Hamano <gitster@pobox.com>
Signed-off-by: Phillip Wood <phillip.wood@dunelm.org.uk>
---
builtin/rebase.c | 67 ++++++++++++++++++++++--------------------------
1 file changed, 31 insertions(+), 36 deletions(-)
diff --git a/builtin/rebase.c b/builtin/rebase.c
index 76f83a42f49..7e6ce374c59 100644
--- a/builtin/rebase.c
+++ b/builtin/rebase.c
@@ -68,7 +68,7 @@ struct rebase_options {
const char *upstream_name;
const char *upstream_arg;
char *head_name;
- struct object_id orig_head;
+ struct commit *orig_head;
struct commit *onto;
const char *onto_name;
const char *revisions;
@@ -261,13 +261,13 @@ static int do_interactive_rebase(struct rebase_options *opts, unsigned flags)
struct replay_opts replay = get_replay_opts(opts);
struct string_list commands = STRING_LIST_INIT_DUP;
- if (get_revision_ranges(opts->upstream, opts->onto, &opts->orig_head,
+ if (get_revision_ranges(opts->upstream, opts->onto, &opts->orig_head->object.oid,
&revisions, &shortrevisions))
return -1;
if (init_basic_state(&replay,
opts->head_name ? opts->head_name : "detached HEAD",
- opts->onto, &opts->orig_head)) {
+ opts->onto, &opts->orig_head->object.oid)) {
free(revisions);
free(shortrevisions);
@@ -298,9 +298,8 @@ static int do_interactive_rebase(struct rebase_options *opts, unsigned flags)
split_exec_commands(opts->cmd, &commands);
ret = complete_action(the_repository, &replay, flags,
shortrevisions, opts->onto_name, opts->onto,
- &opts->orig_head, &commands, opts->autosquash,
- opts->update_refs,
- &todo_list);
+ &opts->orig_head->object.oid, &commands,
+ opts->autosquash, opts->update_refs, &todo_list);
}
string_list_clear(&commands, 0);
@@ -448,7 +447,8 @@ static int read_basic_state(struct rebase_options *opts)
} else if (!read_oneliner(&buf, state_dir_path("head", opts),
READ_ONELINER_WARN_MISSING))
return -1;
- if (get_oid_hex(buf.buf, &opts->orig_head))
+ if (get_oid_hex(buf.buf, &oid) ||
+ !(opts->orig_head = lookup_commit_reference(the_repository, &oid)))
return error(_("invalid orig-head: '%s'"), buf.buf);
if (file_exists(state_dir_path("quiet", opts)))
@@ -517,7 +517,7 @@ static int rebase_write_basic_state(struct rebase_options *opts)
write_file(state_dir_path("onto", opts), "%s",
opts->onto ? oid_to_hex(&opts->onto->object.oid) : "");
write_file(state_dir_path("orig-head", opts), "%s",
- oid_to_hex(&opts->orig_head));
+ oid_to_hex(&opts->orig_head->object.oid));
if (!(opts->flags & REBASE_NO_QUIET))
write_file(state_dir_path("quiet", opts), "%s", "");
if (opts->flags & REBASE_VERBOSE)
@@ -646,7 +646,7 @@ static int run_am(struct rebase_options *opts)
/* this is now equivalent to !opts->upstream */
&opts->onto->object.oid :
&opts->upstream->object.oid),
- oid_to_hex(&opts->orig_head));
+ oid_to_hex(&opts->orig_head->object.oid));
rebased_patches = xstrdup(git_path("rebased-patches"));
format_patch.out = open(rebased_patches,
@@ -680,7 +680,7 @@ static int run_am(struct rebase_options *opts)
free(rebased_patches);
strvec_clear(&am.args);
- ropts.oid = &opts->orig_head;
+ ropts.oid = &opts->orig_head->object.oid;
ropts.branch = opts->head_name;
ropts.default_reflog_action = DEFAULT_REFLOG_ACTION;
reset_head(the_repository, &ropts);
@@ -833,7 +833,7 @@ static int checkout_up_to_date(struct rebase_options *options)
strbuf_addf(&buf, "%s: checkout %s",
getenv(GIT_REFLOG_ACTION_ENVIRONMENT),
options->switch_to);
- ropts.oid = &options->orig_head;
+ ropts.oid = &options->orig_head->object.oid;
ropts.branch = options->head_name;
ropts.flags = RESET_HEAD_RUN_POST_CHECKOUT_HOOK;
if (!ropts.branch)
@@ -866,15 +866,11 @@ static int is_linear_history(struct commit *from, struct commit *to)
static int can_fast_forward(struct commit *onto, struct commit *upstream,
struct commit *restrict_revision,
- struct object_id *head_oid, struct object_id *merge_base)
+ struct commit *head, struct object_id *merge_base)
{
- struct commit *head = lookup_commit(the_repository, head_oid);
struct commit_list *merge_bases = NULL;
int res = 0;
- if (!head)
- goto done;
-
merge_bases = get_merge_bases(onto, head);
if (!merge_bases || merge_bases->next) {
oidcpy(merge_base, null_oid());
@@ -1312,13 +1308,13 @@ int cmd_rebase(int argc, const char **argv, const char *prefix)
if (read_basic_state(&options))
exit(1);
- ropts.oid = &options.orig_head;
+ ropts.oid = &options.orig_head->object.oid;
ropts.branch = options.head_name;
ropts.flags = RESET_HEAD_HARD;
ropts.default_reflog_action = DEFAULT_REFLOG_ACTION;
if (reset_head(the_repository, &ropts) < 0)
die(_("could not move back to %s"),
- oid_to_hex(&options.orig_head));
+ oid_to_hex(&options.orig_head->object.oid));
remove_branch_state(the_repository, 0);
ret = finish_rebase(&options);
goto cleanup;
@@ -1604,25 +1600,27 @@ int cmd_rebase(int argc, const char **argv, const char *prefix)
*/
if (argc == 1) {
/* Is it "rebase other branchname" or "rebase other commit"? */
+ struct object_id branch_oid;
branch_name = argv[0];
options.switch_to = argv[0];
/* Is it a local branch? */
strbuf_reset(&buf);
strbuf_addf(&buf, "refs/heads/%s", branch_name);
- if (!read_ref(buf.buf, &options.orig_head)) {
+ if (!read_ref(buf.buf, &branch_oid)) {
die_if_checked_out(buf.buf, 1);
options.head_name = xstrdup(buf.buf);
+ options.orig_head =
+ lookup_commit_reference(the_repository,
+ &branch_oid);
/* If not is it a valid ref (branch or commit)? */
} else {
- struct commit *commit =
+ options.orig_head =
lookup_commit_reference_by_name(branch_name);
- if (!commit)
- die(_("no such branch/commit '%s'"),
- branch_name);
- oidcpy(&options.orig_head, &commit->object.oid);
options.head_name = NULL;
}
+ if (!options.orig_head)
+ die(_("no such branch/commit '%s'"), branch_name);
} else if (argc == 0) {
/* Do not need to switch branches, we are already on it. */
options.head_name =
@@ -1639,8 +1637,9 @@ int cmd_rebase(int argc, const char **argv, const char *prefix)
FREE_AND_NULL(options.head_name);
branch_name = "HEAD";
}
- if (get_oid("HEAD", &options.orig_head))
- die(_("Could not resolve HEAD to a revision"));
+ options.orig_head = lookup_commit_reference_by_name("HEAD");
+ if (!options.orig_head)
+ die(_("Could not resolve HEAD to a commit"));
} else
BUG("unexpected number of arguments left to parse");
@@ -1672,13 +1671,9 @@ int cmd_rebase(int argc, const char **argv, const char *prefix)
options.onto_name);
}
- if (options.fork_point > 0) {
- struct commit *head =
- lookup_commit_reference(the_repository,
- &options.orig_head);
+ if (options.fork_point > 0)
options.restrict_revision =
- get_fork_point(options.upstream_name, head);
- }
+ get_fork_point(options.upstream_name, options.orig_head);
if (repo_read_index(the_repository) < 0)
die(_("could not read index"));
@@ -1708,7 +1703,7 @@ int cmd_rebase(int argc, const char **argv, const char *prefix)
* call it before checking allow_preemptive_ff.
*/
if (can_fast_forward(options.onto, options.upstream, options.restrict_revision,
- &options.orig_head, &merge_base) &&
+ options.orig_head, &merge_base) &&
allow_preemptive_ff) {
int flag;
@@ -1785,7 +1780,7 @@ int cmd_rebase(int argc, const char **argv, const char *prefix)
strbuf_addf(&msg, "%s: checkout %s",
getenv(GIT_REFLOG_ACTION_ENVIRONMENT), options.onto_name);
ropts.oid = &options.onto->object.oid;
- ropts.orig_head = &options.orig_head,
+ ropts.orig_head = &options.orig_head->object.oid,
ropts.flags = RESET_HEAD_DETACH | RESET_ORIG_HEAD |
RESET_HEAD_RUN_POST_CHECKOUT_HOOK;
ropts.head_msg = msg.buf;
@@ -1799,7 +1794,7 @@ int cmd_rebase(int argc, const char **argv, const char *prefix)
* we just fast-forwarded.
*/
strbuf_reset(&msg);
- if (oideq(&merge_base, &options.orig_head)) {
+ if (oideq(&merge_base, &options.orig_head->object.oid)) {
printf(_("Fast-forwarded %s to %s.\n"),
branch_name, options.onto_name);
strbuf_addf(&msg, "rebase finished: %s onto %s",
@@ -1820,7 +1815,7 @@ int cmd_rebase(int argc, const char **argv, const char *prefix)
(options.restrict_revision ?
oid_to_hex(&options.restrict_revision->object.oid) :
oid_to_hex(&options.upstream->object.oid)),
- oid_to_hex(&options.orig_head));
+ oid_to_hex(&options.orig_head->object.oid));
options.revisions = revisions.buf;
--
gitgitgadget
next prev parent reply other threads:[~2022-10-13 8:43 UTC|newest]
Thread overview: 82+ messages / expand[flat|nested] mbox.gz Atom feed top
2022-08-15 15:11 [PATCH 0/5] rebase --keep-base: imply --reapply-cherry-picks and --no-fork-point Phillip Wood via GitGitGadget
2022-08-15 15:11 ` [PATCH 1/5] t3416: set $EDITOR in subshell Phillip Wood via GitGitGadget
2022-08-15 16:53 ` Junio C Hamano
2022-08-16 13:53 ` Phillip Wood
2022-08-24 22:28 ` Jonathan Tan
2022-08-30 15:12 ` Phillip Wood
2022-08-15 15:11 ` [PATCH 2/5] rebase: store orig_head as a commit Phillip Wood via GitGitGadget
2022-08-15 16:58 ` Junio C Hamano
2022-08-16 9:11 ` Johannes Schindelin
2022-08-18 7:01 ` Elijah Newren
2022-08-15 15:11 ` [PATCH 3/5] rebase: factor out merge_base calculation Phillip Wood via GitGitGadget
2022-08-15 17:22 ` Junio C Hamano
2022-08-16 9:15 ` Johannes Schindelin
2022-08-16 15:00 ` Junio C Hamano
2022-08-16 13:50 ` Phillip Wood
2022-08-16 15:03 ` Junio C Hamano
2022-08-18 7:11 ` Elijah Newren
2022-08-24 22:02 ` Jonathan Tan
2022-08-30 15:03 ` Phillip Wood
2022-08-15 15:11 ` [PATCH 4/5] rebase --keep-base: imply --reapply-cherry-picks Phillip Wood via GitGitGadget
2022-08-15 20:58 ` Junio C Hamano
2022-08-24 22:09 ` Jonathan Tan
2022-08-30 15:09 ` Phillip Wood
2022-08-25 0:29 ` Philippe Blain
2022-09-05 13:54 ` Phillip Wood
2022-08-15 15:11 ` [PATCH 5/5] rebase --keep-base: imply --no-fork-point Phillip Wood via GitGitGadget
2022-08-15 21:07 ` Junio C Hamano
2022-08-24 22:18 ` Jonathan Tan
2022-09-05 13:51 ` Phillip Wood
2022-08-16 9:23 ` [PATCH 0/5] rebase --keep-base: imply --reapply-cherry-picks and --no-fork-point Johannes Schindelin
2022-08-24 22:27 ` Jonathan Tan
2022-09-07 14:37 ` [PATCH v2 0/7] " Phillip Wood via GitGitGadget
2022-09-07 14:37 ` [PATCH v2 1/7] t3416: tighten two tests Phillip Wood via GitGitGadget
2022-09-07 18:12 ` Junio C Hamano
2022-09-07 14:37 ` [PATCH v2 2/7] t3416: set $EDITOR in subshell Phillip Wood via GitGitGadget
2022-09-07 18:12 ` Junio C Hamano
2022-09-07 14:37 ` [PATCH v2 3/7] rebase: store orig_head as a commit Phillip Wood via GitGitGadget
2022-09-07 18:12 ` Junio C Hamano
2022-09-08 13:19 ` Phillip Wood
2022-09-07 14:37 ` [PATCH v2 4/7] rebase: rename merge_base to branch_base Phillip Wood via GitGitGadget
2022-09-07 18:12 ` Junio C Hamano
2022-09-07 14:37 ` [PATCH v2 5/7] rebase: factor out branch_base calculation Phillip Wood via GitGitGadget
2022-09-07 18:12 ` Junio C Hamano
2022-09-07 14:37 ` [PATCH v2 6/7] rebase --keep-base: imply --reapply-cherry-picks Phillip Wood via GitGitGadget
2022-09-07 14:37 ` [PATCH v2 7/7] rebase --keep-base: imply --no-fork-point Phillip Wood via GitGitGadget
2022-09-08 2:44 ` Denton Liu
2022-09-08 13:21 ` Phillip Wood
2022-10-13 8:42 ` [PATCH v3 0/8] rebase --keep-base: imply --reapply-cherry-picks and --no-fork-point Phillip Wood via GitGitGadget
2022-10-13 8:42 ` [PATCH v3 1/8] t3416: tighten two tests Phillip Wood via GitGitGadget
2022-10-13 8:42 ` [PATCH v3 2/8] t3416: set $EDITOR in subshell Phillip Wood via GitGitGadget
2022-10-13 8:42 ` [PATCH v3 3/8] rebase: be stricter when reading state files containing oids Phillip Wood via GitGitGadget
2022-10-13 16:34 ` Junio C Hamano
2022-10-13 19:10 ` Ævar Arnfjörð Bjarmason
2022-10-13 20:13 ` Junio C Hamano
2022-10-13 8:42 ` Phillip Wood via GitGitGadget [this message]
2022-10-13 16:34 ` [PATCH v3 4/8] rebase: store orig_head as a commit Junio C Hamano
2022-10-13 20:49 ` Phillip Wood
2022-10-13 23:25 ` Junio C Hamano
2022-10-13 8:42 ` [PATCH v3 5/8] rebase: rename merge_base to branch_base Phillip Wood via GitGitGadget
2022-10-13 19:16 ` Ævar Arnfjörð Bjarmason
2022-10-17 9:49 ` Phillip Wood
2022-10-17 11:27 ` Ævar Arnfjörð Bjarmason
2022-10-17 13:13 ` Phillip Wood
2022-10-17 16:19 ` Ævar Arnfjörð Bjarmason
2022-10-19 15:35 ` Phillip Wood
2022-10-13 8:42 ` [PATCH v3 6/8] rebase: factor out branch_base calculation Phillip Wood via GitGitGadget
2022-10-13 19:21 ` Ævar Arnfjörð Bjarmason
2022-10-17 9:39 ` Phillip Wood
2022-10-17 11:23 ` Ævar Arnfjörð Bjarmason
2022-10-13 8:42 ` [PATCH v3 7/8] rebase --keep-base: imply --reapply-cherry-picks Phillip Wood via GitGitGadget
2022-10-13 8:42 ` [PATCH v3 8/8] rebase --keep-base: imply --no-fork-point Phillip Wood via GitGitGadget
2022-10-17 13:17 ` [PATCH v4 0/8] rebase --keep-base: imply --reapply-cherry-picks and --no-fork-point Phillip Wood via GitGitGadget
2022-10-17 13:17 ` [PATCH v4 1/8] t3416: tighten two tests Phillip Wood via GitGitGadget
2022-10-17 13:17 ` [PATCH v4 2/8] t3416: set $EDITOR in subshell Phillip Wood via GitGitGadget
2022-10-17 13:17 ` [PATCH v4 3/8] rebase: be stricter when reading state files containing oids Phillip Wood via GitGitGadget
2022-10-17 18:51 ` Junio C Hamano
2022-10-19 15:32 ` Phillip Wood
2022-10-17 13:17 ` [PATCH v4 4/8] rebase: store orig_head as a commit Phillip Wood via GitGitGadget
2022-10-17 13:17 ` [PATCH v4 5/8] rebase: rename merge_base to branch_base Phillip Wood via GitGitGadget
2022-10-17 13:17 ` [PATCH v4 6/8] rebase: factor out branch_base calculation Phillip Wood via GitGitGadget
2022-10-17 13:17 ` [PATCH v4 7/8] rebase --keep-base: imply --reapply-cherry-picks Phillip Wood via GitGitGadget
2022-10-17 13:17 ` [PATCH v4 8/8] rebase --keep-base: imply --no-fork-point Phillip Wood via GitGitGadget
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=dc056b13ed5c62729f97bd2cedbe769c531f4bc4.1665650564.git.gitgitgadget@gmail.com \
--to=gitgitgadget@gmail.com \
--cc=Johannes.Schindelin@gmx.de \
--cc=git@vger.kernel.org \
--cc=gitster@pobox.com \
--cc=jonathantanmy@google.com \
--cc=levraiphilippeblain@gmail.com \
--cc=liu.denton@gmail.com \
--cc=newren@gmail.com \
--cc=phillip.wood123@gmail.com \
--cc=phillip.wood@dunelm.org.uk \
/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).