{"thread":{"id":"38824","subject":"[PATCH] [RFC] Add a new config. option for skipping merges in git-log","startedAt":"2015-03-16T14:23:13Z","lastAt":"2015-03-16T21:58:34Z","messageCount":8,"participants":["Koosha Khajehmoogahi","Junio C Hamano"],"isPatch":true,"patchVersion":1,"patchTotal":null},"messages":[{"id":"257785","messageId":"5506E751.8010506@posteo.de","threadId":"38824","inReplyTo":null,"subject":"[PATCH] [RFC] Add a new config. option for skipping merges in git-log","fromName":"Koosha Khajehmoogahi","fromEmail":"koosha@posteo.de","sentAt":"2015-03-16T14:23:13Z","receivedAt":"2015-03-16T14:23:13Z","isPatch":true,"sender":{"key":"koosha@posteo.de","avatar":null},"body":"\nThis patch adds a 'showmerges' config. option for git-log.\nThis option determines whether the log should contain merge\ncommits or not. In essence, if this option is set to false,\ngit-log will be run as 'git-log --no-merges'.\n\nTo force git-log to show merges even if 'log.showmerges' is\nset, we use --include-merges command line option.\n\nSigned-off-by: Koosha Khajehmoogahi <koosha@posteo.de>\n---\n Documentation/config.txt | 3 +++\n builtin/log.c            | 9 +++++++++\n revision.c               | 2 ++\n revision.h               | 1 +\n 4 files changed, 15 insertions(+)\n\n\n\nPlease help me with this patch. It seems that my --include-merges\ncommand-line option does not have have any effect on the behavior\nof git-log. I don't know why the value of force_show_merges is\nalways 0!\n\ndiff --git a/Documentation/config.txt b/Documentation/config.txt\nindex 1530255..7775b8c 100644\n--- a/Documentation/config.txt\n+++ b/Documentation/config.txt\n@@ -1735,6 +1735,9 @@ log.showroot::\n \tTools like linkgit:git-log[1] or linkgit:git-whatchanged[1], which\n \tnormally hide the root commit will now show it. True by default.\n \n+log.showmerges::\n+\tIf true, merges will be shown in the log list. True by default.\n+\n log.mailmap::\n \tIf true, makes linkgit:git-log[1], linkgit:git-show[1], and\n \tlinkgit:git-whatchanged[1] assume `--use-mailmap`.\ndiff --git a/builtin/log.c b/builtin/log.c\nindex dd8f3fc..867bcf2 100644\n--- a/builtin/log.c\n+++ b/builtin/log.c\n@@ -31,6 +31,7 @@ static const char *default_date_mode = NULL;\n \n static int default_abbrev_commit;\n static int default_show_root = 1;\n+static int default_max_parents = -1;\n static int decoration_style;\n static int decoration_given;\n static int use_mailmap_config;\n@@ -108,6 +109,8 @@ static void cmd_log_init_defaults(struct rev_info *rev)\n \trev->diffopt.stat_graph_width = -1; /* respect statGraphWidth config */\n \trev->abbrev_commit = default_abbrev_commit;\n \trev->show_root_diff = default_show_root;\n+\tif (rev->force_show_merges == 0)\n+\t\trev->max_parents = default_max_parents;\n \trev->subject_prefix = fmt_patch_subject_prefix;\n \tDIFF_OPT_SET(&rev->diffopt, ALLOW_TEXTCONV);\n \n@@ -390,6 +393,12 @@ static int git_log_config(const char *var, const char *value, void *cb)\n \t\tdefault_show_root = git_config_bool(var, value);\n \t\treturn 0;\n \t}\n+\n+\tif (!strcmp(var, \"log.showmerges\")) {\n+\t\tdefault_max_parents = git_config_bool(var, value) ? -1 : 1;\n+\t\treturn 0;\n+\t}\n+\n \tif (skip_prefix(var, \"color.decorate.\", &slot_name))\n \t\treturn parse_decorate_color_config(var, slot_name, value);\n \tif (!strcmp(var, \"log.mailmap\")) {\ndiff --git a/revision.c b/revision.c\nindex 66520c6..e7073b8 100644\n--- a/revision.c\n+++ b/revision.c\n@@ -1804,6 +1804,8 @@ static int handle_revision_opt(struct rev_info *revs, int argc, const char **arg\n \t\trevs->min_parents = 2;\n \t} else if (!strcmp(arg, \"--no-merges\")) {\n \t\trevs->max_parents = 1;\n+\t} else if (!strcmp(arg, \"--include-merges\")) {\n+\t\trevs->force_show_merges = 1;\n \t} else if (starts_with(arg, \"--min-parents=\")) {\n \t\trevs->min_parents = atoi(arg+14);\n \t} else if (starts_with(arg, \"--no-min-parents\")) {\ndiff --git a/revision.h b/revision.h\nindex 0ea8b4e..f496472 100644\n--- a/revision.h\n+++ b/revision.h\n@@ -145,6 +145,7 @@ struct rev_info {\n \tunsigned int\ttrack_linear:1,\n \t\t\ttrack_first_time:1,\n \t\t\tlinear:1;\n+\tunsigned int force_show_merges:1;\n \n \tenum date_mode date_mode;\n \n-- \n1.9.1\n"},{"id":"257790","messageId":"5506F652.7050700@posteo.de","threadId":"38824","inReplyTo":"5506E751.8010506@posteo.de","subject":"[PATCH] [RFC] Add a new config. option for skipping merges in git-log","fromName":"Koosha Khajehmoogahi","fromEmail":"koosha@posteo.de","sentAt":"2015-03-16T15:27:14Z","receivedAt":"2015-03-16T15:27:14Z","isPatch":true,"sender":{"key":"koosha@posteo.de","avatar":null},"body":"\nThis patch adds a 'showmerges' config. option for git-log.\nThis option determines whether the log should contain merge\ncommits or not. In essence, if this option is set to false,\ngit-log will be run as 'git-log --no-merges'.\n\nTo force git-log to show merges even if 'log.showmerges' is\nset, we use --include-merges command line option.\n\nSigned-off-by: Koosha Khajehmoogahi <koosha@posteo.de>\n---\n Documentation/config.txt | 3 +++\n builtin/log.c            | 9 +++++++++\n revision.c               | 2 ++\n revision.h               | 1 +\n 4 files changed, 15 insertions(+)\n\nThis is the second time I send this patch as it seems it didn't\nget delivered even after one hour!\n\nPlease help me with this patch. It seems that my --include-merges\ncommand-line option does not have have any effect on the behavior\nof git-log. I don't know why the value of force_show_merges is\nalways 0!\n\ndiff --git a/Documentation/config.txt b/Documentation/config.txt\nindex 1530255..7775b8c 100644\n--- a/Documentation/config.txt\n+++ b/Documentation/config.txt\n@@ -1735,6 +1735,9 @@ log.showroot::\n \tTools like linkgit:git-log[1] or linkgit:git-whatchanged[1], which\n \tnormally hide the root commit will now show it. True by default.\n \n+log.showmerges::\n+\tIf true, merges will be shown in the log list. True by default.\n+\n log.mailmap::\n \tIf true, makes linkgit:git-log[1], linkgit:git-show[1], and\n \tlinkgit:git-whatchanged[1] assume `--use-mailmap`.\ndiff --git a/builtin/log.c b/builtin/log.c\nindex dd8f3fc..867bcf2 100644\n--- a/builtin/log.c\n+++ b/builtin/log.c\n@@ -31,6 +31,7 @@ static const char *default_date_mode = NULL;\n \n static int default_abbrev_commit;\n static int default_show_root = 1;\n+static int default_max_parents = -1;\n static int decoration_style;\n static int decoration_given;\n static int use_mailmap_config;\n@@ -108,6 +109,8 @@ static void cmd_log_init_defaults(struct rev_info *rev)\n \trev->diffopt.stat_graph_width = -1; /* respect statGraphWidth config */\n \trev->abbrev_commit = default_abbrev_commit;\n \trev->show_root_diff = default_show_root;\n+\tif (rev->force_show_merges == 0)\n+\t\trev->max_parents = default_max_parents;\n \trev->subject_prefix = fmt_patch_subject_prefix;\n \tDIFF_OPT_SET(&rev->diffopt, ALLOW_TEXTCONV);\n \n@@ -390,6 +393,12 @@ static int git_log_config(const char *var, const char *value, void *cb)\n \t\tdefault_show_root = git_config_bool(var, value);\n \t\treturn 0;\n \t}\n+\n+\tif (!strcmp(var, \"log.showmerges\")) {\n+\t\tdefault_max_parents = git_config_bool(var, value) ? -1 : 1;\n+\t\treturn 0;\n+\t}\n+\n \tif (skip_prefix(var, \"color.decorate.\", &slot_name))\n \t\treturn parse_decorate_color_config(var, slot_name, value);\n \tif (!strcmp(var, \"log.mailmap\")) {\ndiff --git a/revision.c b/revision.c\nindex 66520c6..e7073b8 100644\n--- a/revision.c\n+++ b/revision.c\n@@ -1804,6 +1804,8 @@ static int handle_revision_opt(struct rev_info *revs, int argc, const char **arg\n \t\trevs->min_parents = 2;\n \t} else if (!strcmp(arg, \"--no-merges\")) {\n \t\trevs->max_parents = 1;\n+\t} else if (!strcmp(arg, \"--include-merges\")) {\n+\t\trevs->force_show_merges = 1;\n \t} else if (starts_with(arg, \"--min-parents=\")) {\n \t\trevs->min_parents = atoi(arg+14);\n \t} else if (starts_with(arg, \"--no-min-parents\")) {\ndiff --git a/revision.h b/revision.h\nindex 0ea8b4e..f496472 100644\n--- a/revision.h\n+++ b/revision.h\n@@ -145,6 +145,7 @@ struct rev_info {\n \tunsigned int\ttrack_linear:1,\n \t\t\ttrack_first_time:1,\n \t\t\tlinear:1;\n+\tunsigned int force_show_merges:1;\n \n \tenum date_mode date_mode;\n \n-- \n1.9.1\n"},{"id":"257793","messageId":"5506FF19.1050307@gmail.com","threadId":"38824","inReplyTo":"5506F652.7050700@posteo.de","subject":"[PATCH] [RFC] Add a new config. option for skipping merges in git-log","fromName":"Koosha Khajehmoogahi","fromEmail":"koosha.khajeh@gmail.com","sentAt":"2015-03-16T16:04:41Z","receivedAt":"2015-03-16T16:04:41Z","isPatch":true,"sender":{"key":"koosha.khajeh@gmail.com","avatar":"https://gravatar.com/avatar/f19f87f411bad2d1f9f84c0c73c4c97cfffebd9871a77f374ab3cad0af9ee764?d=mp&s=160"},"body":"This patch adds a 'showmerges' config. option for git-log.\nThis option determines whether the log should contain merge\ncommits or not. In essence, if this option is set to false,\ngit-log will be run as 'git-log --no-merges'.\n\nTo force git-log to show merges even if 'log.showmerges' is\nset, we use --include-merges command line option.\n\nSigned-off-by: Koosha Khajehmoogahi <koosha.khajeh@gmail.com>\n---\n Documentation/config.txt | 3 +++\n builtin/log.c            | 9 +++++++++\n revision.c               | 2 ++\n revision.h               | 1 +\n 4 files changed, 15 insertions(+)\n\nThis is the third time I send this patch as it seems it didn't\nget delivered even after one hour!\n\nPlease help me with this patch. It seems that my --include-merges\ncommand-line option does not have have any effect on the behavior\nof git-log. I don't know why the value of force_show_merges is\nalways 0!\n\ndiff --git a/Documentation/config.txt b/Documentation/config.txt\nindex 1530255..7775b8c 100644\n--- a/Documentation/config.txt\n+++ b/Documentation/config.txt\n@@ -1735,6 +1735,9 @@ log.showroot::\n \tTools like linkgit:git-log[1] or linkgit:git-whatchanged[1], which\n \tnormally hide the root commit will now show it. True by default.\n \n+log.showmerges::\n+\tIf true, merges will be shown in the log list. True by default.\n+\n log.mailmap::\n \tIf true, makes linkgit:git-log[1], linkgit:git-show[1], and\n \tlinkgit:git-whatchanged[1] assume `--use-mailmap`.\ndiff --git a/builtin/log.c b/builtin/log.c\nindex dd8f3fc..867bcf2 100644\n--- a/builtin/log.c\n+++ b/builtin/log.c\n@@ -31,6 +31,7 @@ static const char *default_date_mode = NULL;\n \n static int default_abbrev_commit;\n static int default_show_root = 1;\n+static int default_max_parents = -1;\n static int decoration_style;\n static int decoration_given;\n static int use_mailmap_config;\n@@ -108,6 +109,8 @@ static void cmd_log_init_defaults(struct rev_info *rev)\n \trev->diffopt.stat_graph_width = -1; /* respect statGraphWidth config */\n \trev->abbrev_commit = default_abbrev_commit;\n \trev->show_root_diff = default_show_root;\n+\tif (rev->force_show_merges == 0)\n+\t\trev->max_parents = default_max_parents;\n \trev->subject_prefix = fmt_patch_subject_prefix;\n \tDIFF_OPT_SET(&rev->diffopt, ALLOW_TEXTCONV);\n \n@@ -390,6 +393,12 @@ static int git_log_config(const char *var, const char *value, void *cb)\n \t\tdefault_show_root = git_config_bool(var, value);\n \t\treturn 0;\n \t}\n+\n+\tif (!strcmp(var, \"log.showmerges\")) {\n+\t\tdefault_max_parents = git_config_bool(var, value) ? -1 : 1;\n+\t\treturn 0;\n+\t}\n+\n \tif (skip_prefix(var, \"color.decorate.\", &slot_name))\n \t\treturn parse_decorate_color_config(var, slot_name, value);\n \tif (!strcmp(var, \"log.mailmap\")) {\ndiff --git a/revision.c b/revision.c\nindex 66520c6..e7073b8 100644\n--- a/revision.c\n+++ b/revision.c\n@@ -1804,6 +1804,8 @@ static int handle_revision_opt(struct rev_info *revs, int argc, const char **arg\n \t\trevs->min_parents = 2;\n \t} else if (!strcmp(arg, \"--no-merges\")) {\n \t\trevs->max_parents = 1;\n+\t} else if (!strcmp(arg, \"--include-merges\")) {\n+\t\trevs->force_show_merges = 1;\n \t} else if (starts_with(arg, \"--min-parents=\")) {\n \t\trevs->min_parents = atoi(arg+14);\n \t} else if (starts_with(arg, \"--no-min-parents\")) {\ndiff --git a/revision.h b/revision.h\nindex 0ea8b4e..f496472 100644\n--- a/revision.h\n+++ b/revision.h\n@@ -145,6 +145,7 @@ struct rev_info {\n \tunsigned int\ttrack_linear:1,\n \t\t\ttrack_first_time:1,\n \t\t\tlinear:1;\n+\tunsigned int force_show_merges:1;\n \n \tenum date_mode date_mode;\n \n-- \n1.9.1\n"},{"id":"257806","messageId":"xmqqpp88rfq0.fsf@gitster.dls.corp.google.com","threadId":"38824","inReplyTo":"5506E751.8010506@posteo.de","subject":"Re: [PATCH] [RFC] Add a new config. option for skipping merges in git-log","fromName":"Junio C Hamano","fromEmail":"gitster@pobox.com","sentAt":"2015-03-16T17:53:43Z","receivedAt":"2015-03-16T17:53:43Z","isPatch":true,"sender":{"key":"gitster@pobox.com","avatar":"https://avatars.githubusercontent.com/u/54884?v=4"},"body":"Koosha Khajehmoogahi <koosha@posteo.de> writes:\n\n> This patch adds a 'showmerges' config. option for git-log.\n> This option determines whether the log should contain merge\n> commits or not. In essence, if this option is set to false,\n> git-log will be run as 'git-log --no-merges'.\n>\n> To force git-log to show merges even if 'log.showmerges' is\n> set, we use --include-merges command line option.\n\nYuck.\n\nI agree that there is currently no way to revert the setting that is\ntouched by --merges and --no-merges back to the default, but I think\nthe right way to fix that is by streamlining these two options,\ninstead of piling yet another kludge --include-merges on top.\n\nWhen we think about possible \"canned\" selection modes:\n\n (do we show merge commits?) * (do we show non-merge commits?)\n\nwe have four combinations.  Answering the above two questions with\nNo/No would end up showing nothing, which is meaningless, so that\nleaves us three choices (of course, the user could choose to futz\ndirectly with min/max-parents to select only Octopus merges, but\nthat is a more advanced/exotic usage).\n\nWouldn't it make more sense to spell which selection mode the user\nwants with:\n\n\tgit log --merges=<selection-mode>\n\nby naming the three meaningful selection modes with short and sweet\nnames?  Perhaps\n\n    default? show? both? -- show both merge commits and non-merge commits\n    only -- show only merge commits\n    skip -- show only non-merge commits\n\nor something?\n\nNow, as I always say, I am not great at naming things, so do not\ntake these names as the final suggestion, but I think you got the\nidea.\n\nOf course, then the traditional \"--merges\" option can be kept as a\nshort-hand for \"--merges=only\", and \"--no-merges\" would become a\nshort-hand for \"--merges=skip\".\n\nOnce we have done that streamlining of the command line options, it\nwill naturally follow that \"log.merges = show | only | skip\" would\nbe a useful configuration option.\n\nI doubt we need an extra bit in rev_info to implement such a syntax\nsugar.\n\n> diff --git a/revision.h b/revision.h\n> index 0ea8b4e..f496472 100644\n> --- a/revision.h\n> +++ b/revision.h\n> @@ -145,6 +145,7 @@ struct rev_info {\n>  \tunsigned int\ttrack_linear:1,\n>  \t\t\ttrack_first_time:1,\n>  \t\t\tlinear:1;\n> +\tunsigned int force_show_merges:1;\n>  \n>  \tenum date_mode date_mode;\n"},{"id":"257815","messageId":"5507301B.2060401@posteo.de","threadId":"38824","inReplyTo":"xmqqpp88rfq0.fsf@gitster.dls.corp.google.com","subject":"Re: [PATCH] [RFC] Add a new config. option for skipping merges in git-log","fromName":"Koosha Khajehmoogahi","fromEmail":"koosha@posteo.de","sentAt":"2015-03-16T19:33:47Z","receivedAt":"2015-03-16T19:33:47Z","isPatch":true,"sender":{"key":"koosha@posteo.de","avatar":null},"body":"\nOn 03/16/2015 06:53 PM, Junio C Hamano wrote:\n> Koosha Khajehmoogahi <koosha@posteo.de> writes:\n> \n>> This patch adds a 'showmerges' config. option for git-log.\n>> This option determines whether the log should contain merge\n>> commits or not. In essence, if this option is set to false,\n>> git-log will be run as 'git-log --no-merges'.\n>>\n>> To force git-log to show merges even if 'log.showmerges' is\n>> set, we use --include-merges command line option.\n> \n> Yuck.\n> \n> I agree that there is currently no way to revert the setting that is\n> touched by --merges and --no-merges back to the default, but I think\n> the right way to fix that is by streamlining these two options,\n> instead of piling yet another kludge --include-merges on top.\n> \n> When we think about possible \"canned\" selection modes:\n> \n>  (do we show merge commits?) * (do we show non-merge commits?)\n> \n> we have four combinations.  Answering the above two questions with\n> No/No would end up showing nothing, which is meaningless, so that\n> leaves us three choices (of course, the user could choose to futz\n> directly with min/max-parents to select only Octopus merges, but\n> that is a more advanced/exotic usage).\n> \n> Wouldn't it make more sense to spell which selection mode the user\n> wants with:\n> \n> \tgit log --merges=<selection-mode>\n> \n> by naming the three meaningful selection modes with short and sweet\n> names?  Perhaps\n> \n>     default? show? both? -- show both merge commits and non-merge commits\n>     only -- show only merge commits\n>     skip -- show only non-merge commits\n> \n> or something?\n> \n> Now, as I always say, I am not great at naming things, so do not\n> take these names as the final suggestion, but I think you got the\n> idea.\n> \n> Of course, then the traditional \"--merges\" option can be kept as a\n> short-hand for \"--merges=only\", and \"--no-merges\" would become a\n> short-hand for \"--merges=skip\".\n> \n> Once we have done that streamlining of the command line options, it\n> will naturally follow that \"log.merges = show | only | skip\" would\n> be a useful configuration option.\n> \n> I doubt we need an extra bit in rev_info to implement such a syntax\n> sugar.\n> \n>> diff --git a/revision.h b/revision.h\n>> index 0ea8b4e..f496472 100644\n>> --- a/revision.h\n>> +++ b/revision.h\n>> @@ -145,6 +145,7 @@ struct rev_info {\n>>  \tunsigned int\ttrack_linear:1,\n>>  \t\t\ttrack_first_time:1,\n>>  \t\t\tlinear:1;\n>> +\tunsigned int force_show_merges:1;\n>>  \n>>  \tenum date_mode date_mode;\n\nThanks for your suggestions. The \"extra bit\" in rev_info is used when\nwe need to compare user's command-line input to his configuration. Since\ncommand-line input is processed in revision.c but config. options are read\nin builtin/log.c, we need a way to pass the value to builtin/log.c. How\nwould you do that without this extra bit?\n\n-- \nKoosha\n"},{"id":"257818","messageId":"xmqqy4mwpsyn.fsf@gitster.dls.corp.google.com","threadId":"38824","inReplyTo":"5507301B.2060401@posteo.de","subject":"Re: [PATCH] [RFC] Add a new config. option for skipping merges in git-log","fromName":"Junio C Hamano","fromEmail":"gitster@pobox.com","sentAt":"2015-03-16T20:50:40Z","receivedAt":"2015-03-16T20:50:40Z","isPatch":true,"sender":{"key":"gitster@pobox.com","avatar":"https://avatars.githubusercontent.com/u/54884?v=4"},"body":"Koosha Khajehmoogahi <koosha@posteo.de> writes:\n\n> Thanks for your suggestions. The \"extra bit\" in rev_info is used when\n> we need to compare user's command-line input to his configuration. Since\n> command-line input is processed in revision.c but config. options are read\n> in builtin/log.c, we need a way to pass the value to builtin/log.c. How\n> would you do that without this extra bit?\n\nThe command line overrides the config, no?  If you set up what the\ncommand line defaults to from the config, let the command line\nparser do whatever it wants to do, and do nothing else after the\ncommand line parser returns, wouldn't that be sufficient?\n\nPuzzled...\n"},{"id":"257819","messageId":"55074440.90709@posteo.de","threadId":"38824","inReplyTo":"xmqqy4mwpsyn.fsf@gitster.dls.corp.google.com","subject":"Re: [PATCH] [RFC] Add a new config. option for skipping merges in git-log","fromName":"Koosha Khajehmoogahi","fromEmail":"koosha@posteo.de","sentAt":"2015-03-16T20:59:44Z","receivedAt":"2015-03-16T20:59:44Z","isPatch":true,"sender":{"key":"koosha@posteo.de","avatar":null},"body":"\n\nOn 03/16/2015 09:50 PM, Junio C Hamano wrote:\n> The command line overrides the config, no?  If you set up what the\n> command line defaults to from the config, let the command line\n> parser do whatever it wants to do, and do nothing else after the\n> command line parser returns, wouldn't that be sufficient?\n> \n> Puzzled...\n> \n\nYes, the command line overrides the config. But, the config and command\nline parameters are parsed in two different files. The question is how\nyou would read the config in revision.c while parsing the command line\nwhen there is no function in revision.c for that?\n\nSorry if I look baffled.\n-- \nKoosha\n"},{"id":"257821","messageId":"xmqqlhiwppth.fsf@gitster.dls.corp.google.com","threadId":"38824","inReplyTo":"55074440.90709@posteo.de","subject":"Re: [PATCH] [RFC] Add a new config. option for skipping merges in git-log","fromName":"Junio C Hamano","fromEmail":"gitster@pobox.com","sentAt":"2015-03-16T21:58:34Z","receivedAt":"2015-03-16T21:58:34Z","isPatch":true,"sender":{"key":"gitster@pobox.com","avatar":"https://avatars.githubusercontent.com/u/54884?v=4"},"body":"Koosha Khajehmoogahi <koosha@posteo.de> writes:\n\n> On 03/16/2015 09:50 PM, Junio C Hamano wrote:\n>> The command line overrides the config, no?  If you set up what the\n>> command line defaults to from the config, let the command line\n>> parser do whatever it wants to do, and do nothing else after the\n>> command line parser returns, wouldn't that be sufficient?\n>> \n>> Puzzled...\n>> \n>\n> Yes, the command line overrides the config. But, the config and command\n> line parameters are parsed in two different files. The question is how\n> you would read the config in revision.c while parsing the command line\n> when there is no function in revision.c for that?\n\nWhat I had in mind was along the line of the attached diff.\n\nIf I were doing this new feature, it would be in two-patch series,\nwhose first patch [1/2] would be just the revision.[ch] to give\nthese three \"canned\" selection options (we obviously need to update\nthe documentation and also add tests to make sure the new option\nbehaves sensibly when used alone, and in conjunction with existing\n\"--merges\" and \"--no-merges\" options).  The second patch [2/2] would\nteach git_log_config() to read the new configuration value and keep\nit in a file-scope static variable in builtin/log.c, and then call\nparse_merges_opt() with that value in the codepath somewhere after\ninit_revisions() is called on &rev and before setup_revisions() is\ncalled.\n\nNote that the addition I made to cmd_log() below is for illustration\npurposes only; I have no strong opinion on whether it is at the\nright place in the codepath (it is one place that is \"between\ninit_revisions() and setup_revisions()\", but it may not be the best\nsuch place).  The call may want to be made a lot later in the\ncodepath, possibly inside cmd_log_init() instead of cmd_log(), for\nexample.  The choice depends on how widely you would want this new\nconfiguration be honored, which I didn't think too deeply.  The\nquestions you would need to answer before deciding where is the best\nplace to make the call include:\n\n - Should \"git whatchanged\" also pay attention to it?\n - What about \"git show\"?\n\netc.\n\n\n builtin/log.c |  5 +++++\n revision.c    | 20 ++++++++++++++++++++\n revision.h    |  2 ++\n 3 files changed, 27 insertions(+)\n\ndiff --git a/builtin/log.c b/builtin/log.c\nindex dd8f3fc..11a191d 100644\n--- a/builtin/log.c\n+++ b/builtin/log.c\n@@ -36,6 +36,7 @@ static int decoration_given;\n static int use_mailmap_config;\n static const char *fmt_patch_subject_prefix = \"PATCH\";\n static const char *fmt_pretty;\n+static const char *log_merges;\n \n static const char * const builtin_log_usage[] = {\n \tN_(\"git log [<options>] [<revision range>] [[--] <path>...]\"),\n@@ -397,6 +398,8 @@ static int git_log_config(const char *var, const char *value, void *cb)\n \t\treturn 0;\n \t}\n \n+\tif (!strcmp(var, \"log.merges\"))\n+\t\treturn git_config_string(&log_merges, var, value);\n \tif (grep_config(var, value, cb) < 0)\n \t\treturn -1;\n \tif (git_gpg_config(var, value, cb) < 0)\n@@ -628,6 +631,8 @@ int cmd_log(int argc, const char **argv, const char *prefix)\n \n \tinit_revisions(&rev, prefix);\n \trev.always_show_header = 1;\n+\tif (log_merges && parse_merges_opt(&rev, log_merges))\n+\t\tdie(\"unknown config value for log.merges: %s\", log_merges);\n \tmemset(&opt, 0, sizeof(opt));\n \topt.def = \"HEAD\";\n \topt.revarg_opt = REVARG_COMMITTISH;\ndiff --git a/revision.c b/revision.c\nindex dbee26b..2fa37b0 100644\n--- a/revision.c\n+++ b/revision.c\n@@ -1678,6 +1678,23 @@ static void add_message_grep(struct rev_info *revs, const char *pattern)\n \tadd_grep(revs, pattern, GREP_PATTERN_BODY);\n }\n \n+int parse_merges_opt(struct rev_info *revs, const char *param)\n+{\n+\tif (!strcmp(param, \"both\")) {\n+\t\trevs->min_parents = 0;\n+\t\trevs->max_parents = -1;\n+\t} else if (!strcmp(param, \"only\")) {\n+\t\trevs->min_parents = 2;\n+\t\trevs->max_parents = -1;\n+\t} else if (!strcmp(param, \"skip\")) {\n+\t\trevs->min_parents = 0;\n+\t\trevs->max_parents = 1;\n+\t} else {\n+\t\treturn -1;\n+\t}\n+\treturn 0;\n+}\n+\n static int handle_revision_opt(struct rev_info *revs, int argc, const char **argv,\n \t\t\t       int *unkc, const char **unkv)\n {\n@@ -1812,6 +1829,9 @@ static int handle_revision_opt(struct rev_info *revs, int argc, const char **arg\n \t\trevs->max_parents = atoi(arg+14);\n \t} else if (starts_with(arg, \"--no-max-parents\")) {\n \t\trevs->max_parents = -1;\n+\t} else if (starts_with(arg, \"--merges=\")) {\n+\t\tif (parse_merges_opt(revs, arg + 9))\n+\t\t\tdie(\"unknown option: %s\", arg);\n \t} else if (!strcmp(arg, \"--boundary\")) {\n \t\trevs->boundary = 1;\n \t} else if (!strcmp(arg, \"--left-right\")) {\ndiff --git a/revision.h b/revision.h\nindex 0ea8b4e..640589c 100644\n--- a/revision.h\n+++ b/revision.h\n@@ -240,6 +240,8 @@ extern int setup_revisions(int argc, const char **argv, struct rev_info *revs,\n extern void parse_revision_opt(struct rev_info *revs, struct parse_opt_ctx_t *ctx,\n \t\t\t       const struct option *options,\n \t\t\t       const char * const usagestr[]);\n+extern int parse_merges_opt(struct rev_info *, const char *);\n+\n #define REVARG_CANNOT_BE_FILENAME 01\n #define REVARG_COMMITTISH 02\n extern int handle_revision_arg(const char *arg, struct rev_info *revs,\n"}]}