threads / discuss / 25991

[WIP/RFH] format-patch: Allow diffs for first-parent history

Subject: [WIP/RFH] format-patch: Allow diffs for first-parent history

## tl;dr

2 messages between Dec 8, 2010 and Dec 8, 2010.

replies: 1people: 2as markdown or json

Michael J Gruber· Dec 8, 2010, 10:18 UTC · lore

Introduce a new option "--first-parent" to format-patch which allows to export the "main development" line as a series of patches, where merge commits are represented by their diff against the first parent.

This is useful for keeping development steps and history in side branches and exporting the cleaned up main line for upstream ("mergy rebase").

Signed-off-by: Michael J Gruber <git@drmicha.warpmail.net>
---
This does not work yet! Work In Progress/Request For Help

"git log -p -m --first-parent" does exactly what I want to achieve, since the parent rewriting done by "--first-parent" makes "-p -m" output the diff to the first parent only.

The attached patch teaches format-patch not to ignore merges (on "--first-parent"), but I failed to track how "diff-tree" sets options based on "-m" and how to do that for "format-patch". I am sure someone here can help me!

 builtin/log.c |    6 +++++-
 1 files changed, 5 insertions(+), 1 deletions(-)
diff --git a/builtin/log.c b/builtin/log.c
index 4191d9c..34d01d3 100644
--- a/builtin/log.c
+++ b/builtin/log.c
@@ -983,6 +983,7 @@ int cmd_format_patch(int argc, const char **argv, const char *prefix)
 	int cover_letter = 0;
 	int boundary_count = 0;
 	int no_binary_diff = 0;
+	int first_parent = 0;
 	struct commit *origin = NULL, *head = NULL;
 	const char *in_reply_to = NULL;
 	struct patch_ids ids;
@@ -1023,6 +1024,8 @@ int cmd_format_patch(int argc, const char **argv, const char *prefix)
 		{ OPTION_BOOLEAN, 'p', "no-stat", &use_patch_format, NULL,
 		  "show patch format instead of default (patch + stat)",
 		  PARSE_OPT_NONEG | PARSE_OPT_NOARG },
+		OPT_BOOLEAN(0, "first-parent", &first_parent,
+			    "follow first parents"),
 		OPT_GROUP("Messaging"),
 		{ OPTION_CALLBACK, 0, "add-header", NULL, "header",
 			    "add email header", 0, header_callback },
@@ -1055,7 +1058,8 @@ int cmd_format_patch(int argc, const char **argv, const char *prefix)
 	rev.commit_format = CMIT_FMT_EMAIL;
 	rev.verbose_header = 1;
 	rev.diff = 1;
-	rev.no_merges = 1;
+	rev.no_merges = !first_parent;
+	rev.first_parent_only = first_parent;
 	DIFF_OPT_SET(&rev.diffopt, RECURSIVE);
 	rev.subject_prefix = fmt_patch_subject_prefix;
 	memset(&s_r_opt, 0, sizeof(s_r_opt));
-- 
1.7.3.2.660.g7cc83
Jonathan Nieder· Dec 8, 2010, 10:52 UTC · re: Michael J Gruber · lore

Re: [WIP/RFH] format-patch: Allow diffs for first-parent history

Michael J Gruber wrote:
> The attached patch teaches format-patch not to ignore merges (on
> "--first-parent"), but I failed to track how "diff-tree" sets options
> based on "-m"
With hindsight, here's a search result:
 $ git grep -e argv -- builtin/diff-tree.c
 int cmd_diff_tree(int argc, const char **argv, const char *prefix)
         argc = setup_revisions(argc, argv, opt, &s_r_opt);
                 const char *arg = *++argv;

So it's setup_revisions, in revision.c, which clears revs->ignore_merges when -m is detected.

Maybe it should clear revs->no_merges while at it? I can't see any other meaningful meaning for

	git alias.lg "log --no-merges"
	git lg -m HEAD~2..HEAD
or
	git format-patch -m --first-parent HEAD~2..HEAD

Meanwhile I would also be happy to see --first-parent imply -m, though that might be more controversial since -p -c --first-parent and -p --cc --first-parent are also meaningful.

← back to recent threads