{"thread":{"id":"50790","subject":"[PATCH 00/20] nd/diff-parseopt the last part","startedAt":"2019-03-20T11:47:15Z","lastAt":"2019-05-01T18:47:01Z","messageCount":52,"participants":["Nguyễn Thái Ngọc Duy","Martin Ågren","Ævar Arnfjörð Bjarmason","Duy Nguyen","Johannes Schindelin","Jeff King"],"isPatch":true,"patchVersion":1,"patchTotal":20},"messages":[{"id":"371979","messageId":"20190320114703.18659-1-pclouds@gmail.com","threadId":"50790","inReplyTo":null,"subject":"[PATCH 00/20] nd/diff-parseopt the last part","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-20T11:46:43Z","receivedAt":"2019-03-20T11:47:15Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Gotta keep pumping until everything is out! This is the last part to\nfinish converting diff.c to use parse_options().\n\nThe two commands 'range-diff' and 'diff --no-index' are also updated\nto do parse_options() directly, which is the end game (i.e. the end of\ndiff_opt_parse(), but that can't happen until revision.c is\nconverted).\n\nThe next step could be collect complaints about how noisy 'git\nrange-diff -h' and 'git diff --no-index -h' is and start trimming\nunused options. revision.c conversion will happen in parallel.\n\nNguyễn Thái Ngọc Duy (20):\n  diff-parseopt: convert --ws-error-highlight\n  diff-parseopt: convert --ita-[in]visible-in-index\n  diff-parseopt: convert -z\n  diff-parseopt: convert -l\n  diff-parseopt: convert -S|-G\n  diff-parseopt: convert --pickaxe-all|--pickaxe-regex\n  diff-parseopt: convert -O\n  diff-parseopt: convert --find-object\n  diff-parseopt: convert --diff-filter\n  diff-parseopt: convert --[no-]abbrev\n  diff-parseopt: convert --[src|dst]-prefix\n  diff-parseopt: convert --line-prefix\n  diff-parseopt: convert --no-prefix\n  diff-parseopt: convert --inter-hunk-context\n  diff-parseopt: convert --[no-]color-moved\n  diff-parseopt: convert --color-moved-ws\n  diff.c: allow --no-color-moved-ws\n  range-diff: use parse_options() instead of diff_opt_parse()\n  diff --no-index: use parse_options() instead of diff_opt_parse()\n  am: avoid diff_opt_parse()\n\n builtin/am.c             |   4 +-\n builtin/diff.c           |  21 +--\n builtin/range-diff.c     |  26 +--\n diff-no-index.c          |  49 +++---\n diff.c                   | 337 +++++++++++++++++++--------------------\n diff.h                   |   5 +-\n parse-options-cb.c       |   4 +-\n parse-options.h          |   6 +-\n t/t4053-diff-no-index.sh |   3 +-\n 9 files changed, 219 insertions(+), 236 deletions(-)\n\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"371980","messageId":"20190320114703.18659-2-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190320114703.18659-1-pclouds@gmail.com","subject":"[PATCH 01/20] diff-parseopt: convert --ws-error-highlight","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-20T11:46:44Z","receivedAt":"2019-03-20T11:47:20Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"mark one more string for translation while at there.\n\nSigned-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 22 ++++++++++++----------\n 1 file changed, 12 insertions(+), 10 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex ce118bb326..8fdcdcc8ff 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -4801,17 +4801,18 @@ static void enable_patch_output(int *fmt)\n \t*fmt |= DIFF_FORMAT_PATCH;\n }\n \n-static int parse_ws_error_highlight_opt(struct diff_options *opt, const char *arg)\n+static int diff_opt_ws_error_highlight(const struct option *option,\n+\t\t\t\t       const char *arg, int unset)\n {\n+\tstruct diff_options *opt = option->value;\n \tint val = parse_ws_error_highlight(arg);\n \n-\tif (val < 0) {\n-\t\terror(\"unknown value after ws-error-highlight=%.*s\",\n-\t\t      -1 - val, arg);\n-\t\treturn 0;\n-\t}\n+\tBUG_ON_OPT_NEG(unset);\n+\tif (val < 0)\n+\t\treturn error(_(\"unknown value after ws-error-highlight=%.*s\"),\n+\t\t\t     -1 - val, arg);\n \topt->ws_error_highlight = val;\n-\treturn 1;\n+\treturn 0;\n }\n \n static int parse_objfind_opt(struct diff_options *opt, const char *arg)\n@@ -5234,6 +5235,9 @@ static void prep_parse_options(struct diff_options *options)\n \t\t\t N_(\"show full pre- and post-image object names on the \\\"index\\\" lines\")),\n \t\tOPT_COLOR_FLAG(0, \"color\", &options->use_color,\n \t\t\t       N_(\"show colored diff\")),\n+\t\tOPT_CALLBACK_F(0, \"ws-error-highlight\", options, N_(\"<kind>\"),\n+\t\t\t       N_(\"highlight whitespaces errors in the context, old or new lines in the diff\"),\n+\t\t\t       PARSE_OPT_NONEG, diff_opt_ws_error_highlight),\n \t\tOPT_CALLBACK_F(0, \"output-indicator-new\",\n \t\t\t       &options->output_indicators[OUTPUT_INDICATOR_NEW],\n \t\t\t       N_(\"<char>\"),\n@@ -5397,9 +5401,7 @@ int diff_opt_parse(struct diff_options *options,\n \t\tif (cm & COLOR_MOVED_WS_ERROR)\n \t\t\treturn -1;\n \t\toptions->color_moved_ws_handling = cm;\n-\t} else if (skip_prefix(arg, \"--ws-error-highlight=\", &arg))\n-\t\treturn parse_ws_error_highlight_opt(options, arg);\n-\telse if (!strcmp(arg, \"--ita-invisible-in-index\"))\n+\t} else if (!strcmp(arg, \"--ita-invisible-in-index\"))\n \t\toptions->ita_invisible_in_index = 1;\n \telse if (!strcmp(arg, \"--ita-visible-in-index\"))\n \t\toptions->ita_invisible_in_index = 0;\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"371981","messageId":"20190320114703.18659-3-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190320114703.18659-1-pclouds@gmail.com","subject":"[PATCH 02/20] diff-parseopt: convert --ita-[in]visible-in-index","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-20T11:46:45Z","receivedAt":"2019-03-20T11:47:25Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 11 +++++++----\n 1 file changed, 7 insertions(+), 4 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex 8fdcdcc8ff..3eace63172 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -5352,6 +5352,12 @@ static void prep_parse_options(struct diff_options *options)\n \t\t\t       N_(\"specify how differences in submodules are shown\"),\n \t\t\t       PARSE_OPT_NONEG | PARSE_OPT_OPTARG,\n \t\t\t       diff_opt_submodule),\n+\t\tOPT_SET_INT_F(0, \"ita-invisible-in-index\", &options->ita_invisible_in_index,\n+\t\t\t      N_(\"hide 'git add -N' entries from the index\"),\n+\t\t\t      1, PARSE_OPT_NONEG),\n+\t\tOPT_SET_INT_F(0, \"ita-visible-in-index\", &options->ita_invisible_in_index,\n+\t\t\t      N_(\"treat 'git add -N' entries as real in the index\"),\n+\t\t\t      0, PARSE_OPT_NONEG),\n \t\t{ OPTION_CALLBACK, 0, \"output\", options, N_(\"<file>\"),\n \t\t  N_(\"Output to a specific file\"),\n \t\t  PARSE_OPT_NONEG, NULL, 0, diff_opt_output },\n@@ -5401,10 +5407,7 @@ int diff_opt_parse(struct diff_options *options,\n \t\tif (cm & COLOR_MOVED_WS_ERROR)\n \t\t\treturn -1;\n \t\toptions->color_moved_ws_handling = cm;\n-\t} else if (!strcmp(arg, \"--ita-invisible-in-index\"))\n-\t\toptions->ita_invisible_in_index = 1;\n-\telse if (!strcmp(arg, \"--ita-visible-in-index\"))\n-\t\toptions->ita_invisible_in_index = 0;\n+\t}\n \n \t/* misc options */\n \telse if (!strcmp(arg, \"-z\"))\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"371982","messageId":"20190320114703.18659-4-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190320114703.18659-1-pclouds@gmail.com","subject":"[PATCH 03/20] diff-parseopt: convert -z","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-20T11:46:46Z","receivedAt":"2019-03-20T11:47:29Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 5 +++--\n 1 file changed, 3 insertions(+), 2 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex 3eace63172..f290dfe6be 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -5238,6 +5238,9 @@ static void prep_parse_options(struct diff_options *options)\n \t\tOPT_CALLBACK_F(0, \"ws-error-highlight\", options, N_(\"<kind>\"),\n \t\t\t       N_(\"highlight whitespaces errors in the context, old or new lines in the diff\"),\n \t\t\t       PARSE_OPT_NONEG, diff_opt_ws_error_highlight),\n+\t\tOPT_SET_INT('z', NULL, &options->line_termination,\n+\t\t\t    N_(\"do not munge pathnames and use NULs as output field terminators in --raw or --numstat\"),\n+\t\t\t    0),\n \t\tOPT_CALLBACK_F(0, \"output-indicator-new\",\n \t\t\t       &options->output_indicators[OUTPUT_INDICATOR_NEW],\n \t\t\t       N_(\"<char>\"),\n@@ -5410,8 +5413,6 @@ int diff_opt_parse(struct diff_options *options,\n \t}\n \n \t/* misc options */\n-\telse if (!strcmp(arg, \"-z\"))\n-\t\toptions->line_termination = 0;\n \telse if ((argcount = short_opt('l', av, &optarg))) {\n \t\toptions->rename_limit = strtoul(optarg, NULL, 10);\n \t\treturn argcount;\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"371983","messageId":"20190320114703.18659-5-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190320114703.18659-1-pclouds@gmail.com","subject":"[PATCH 04/20] diff-parseopt: convert -l","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-20T11:46:47Z","receivedAt":"2019-03-20T11:47:34Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 6 ++----\n 1 file changed, 2 insertions(+), 4 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex f290dfe6be..a2abc7e5b0 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -5283,6 +5283,8 @@ static void prep_parse_options(struct diff_options *options)\n \t\tOPT_CALLBACK_F(0, \"follow\", options, NULL,\n \t\t\t       N_(\"continue listing the history of a file beyond renames\"),\n \t\t\t       PARSE_OPT_NOARG, diff_opt_follow),\n+\t\tOPT_INTEGER('l', NULL, &options->rename_limit,\n+\t\t\t    N_(\"prevent rename/copy detection if the number of rename/copy targets exceeds given limit\")),\n \n \t\tOPT_GROUP(N_(\"Diff algorithm options\")),\n \t\tOPT_BIT(0, \"minimal\", &options->xdl_opts,\n@@ -5413,10 +5415,6 @@ int diff_opt_parse(struct diff_options *options,\n \t}\n \n \t/* misc options */\n-\telse if ((argcount = short_opt('l', av, &optarg))) {\n-\t\toptions->rename_limit = strtoul(optarg, NULL, 10);\n-\t\treturn argcount;\n-\t}\n \telse if ((argcount = short_opt('S', av, &optarg))) {\n \t\toptions->pickaxe = optarg;\n \t\toptions->pickaxe_opts |= DIFF_PICKAXE_KIND_S;\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"371984","messageId":"20190320114703.18659-6-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190320114703.18659-1-pclouds@gmail.com","subject":"[PATCH 05/20] diff-parseopt: convert -S|-G","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-20T11:46:48Z","receivedAt":"2019-03-20T11:47:39Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 37 ++++++++++++++++++++++++++++---------\n 1 file changed, 28 insertions(+), 9 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex a2abc7e5b0..e198129353 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -5056,6 +5056,28 @@ static int diff_opt_patience(const struct option *opt,\n \treturn 0;\n }\n \n+static int diff_opt_pickaxe_regex(const struct option *opt,\n+\t\t\t\t  const char *arg, int unset)\n+{\n+\tstruct diff_options *options = opt->value;\n+\n+\tBUG_ON_OPT_NEG(unset);\n+\toptions->pickaxe = arg;\n+\toptions->pickaxe_opts |= DIFF_PICKAXE_KIND_G;\n+\treturn 0;\n+}\n+\n+static int diff_opt_pickaxe_string(const struct option *opt,\n+\t\t\t\t   const char *arg, int unset)\n+{\n+\tstruct diff_options *options = opt->value;\n+\n+\tBUG_ON_OPT_NEG(unset);\n+\toptions->pickaxe = arg;\n+\toptions->pickaxe_opts |= DIFF_PICKAXE_KIND_S;\n+\treturn 0;\n+}\n+\n static int diff_opt_relative(const struct option *opt,\n \t\t\t     const char *arg, int unset)\n {\n@@ -5363,6 +5385,12 @@ static void prep_parse_options(struct diff_options *options)\n \t\tOPT_SET_INT_F(0, \"ita-visible-in-index\", &options->ita_invisible_in_index,\n \t\t\t      N_(\"treat 'git add -N' entries as real in the index\"),\n \t\t\t      0, PARSE_OPT_NONEG),\n+\t\tOPT_CALLBACK_F('S', NULL, options, N_(\"<string>\"),\n+\t\t\t       N_(\"look for differences that change the number of occurrences of the specified string\"),\n+\t\t\t       0, diff_opt_pickaxe_string),\n+\t\tOPT_CALLBACK_F('G', NULL, options, N_(\"<regex>\"),\n+\t\t\t       N_(\"look for differences that change the number of occurrences of the specified regex\"),\n+\t\t\t       0, diff_opt_pickaxe_regex),\n \t\t{ OPTION_CALLBACK, 0, \"output\", options, N_(\"<file>\"),\n \t\t  N_(\"Output to a specific file\"),\n \t\t  PARSE_OPT_NONEG, NULL, 0, diff_opt_output },\n@@ -5415,15 +5443,6 @@ int diff_opt_parse(struct diff_options *options,\n \t}\n \n \t/* misc options */\n-\telse if ((argcount = short_opt('S', av, &optarg))) {\n-\t\toptions->pickaxe = optarg;\n-\t\toptions->pickaxe_opts |= DIFF_PICKAXE_KIND_S;\n-\t\treturn argcount;\n-\t} else if ((argcount = short_opt('G', av, &optarg))) {\n-\t\toptions->pickaxe = optarg;\n-\t\toptions->pickaxe_opts |= DIFF_PICKAXE_KIND_G;\n-\t\treturn argcount;\n-\t}\n \telse if (!strcmp(arg, \"--pickaxe-all\"))\n \t\toptions->pickaxe_opts |= DIFF_PICKAXE_ALL;\n \telse if (!strcmp(arg, \"--pickaxe-regex\"))\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"371985","messageId":"20190320114703.18659-7-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190320114703.18659-1-pclouds@gmail.com","subject":"[PATCH 06/20] diff-parseopt: convert --pickaxe-all|--pickaxe-regex","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-20T11:46:49Z","receivedAt":"2019-03-20T11:47:44Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 10 ++++++----\n 1 file changed, 6 insertions(+), 4 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex e198129353..639b166c79 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -5391,6 +5391,12 @@ static void prep_parse_options(struct diff_options *options)\n \t\tOPT_CALLBACK_F('G', NULL, options, N_(\"<regex>\"),\n \t\t\t       N_(\"look for differences that change the number of occurrences of the specified regex\"),\n \t\t\t       0, diff_opt_pickaxe_regex),\n+\t\tOPT_BIT_F(0, \"pickaxe-all\", &options->pickaxe_opts,\n+\t\t\t  N_(\"show all changes in the changeset with -S or -G\"),\n+\t\t\t  DIFF_PICKAXE_ALL, PARSE_OPT_NONEG),\n+\t\tOPT_BIT_F(0, \"pickaxe-regex\", &options->pickaxe_opts,\n+\t\t\t  N_(\"treat <string> in -S as extended POSIX regular expression\"),\n+\t\t\t  DIFF_PICKAXE_REGEX, PARSE_OPT_NONEG),\n \t\t{ OPTION_CALLBACK, 0, \"output\", options, N_(\"<file>\"),\n \t\t  N_(\"Output to a specific file\"),\n \t\t  PARSE_OPT_NONEG, NULL, 0, diff_opt_output },\n@@ -5443,10 +5449,6 @@ int diff_opt_parse(struct diff_options *options,\n \t}\n \n \t/* misc options */\n-\telse if (!strcmp(arg, \"--pickaxe-all\"))\n-\t\toptions->pickaxe_opts |= DIFF_PICKAXE_ALL;\n-\telse if (!strcmp(arg, \"--pickaxe-regex\"))\n-\t\toptions->pickaxe_opts |= DIFF_PICKAXE_REGEX;\n \telse if ((argcount = short_opt('O', av, &optarg))) {\n \t\toptions->orderfile = prefix_filename(prefix, optarg);\n \t\treturn argcount;\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"371986","messageId":"20190320114703.18659-8-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190320114703.18659-1-pclouds@gmail.com","subject":"[PATCH 07/20] diff-parseopt: convert -O","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-20T11:46:50Z","receivedAt":"2019-03-20T11:47:48Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 23 +++--------------------\n 1 file changed, 3 insertions(+), 20 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex 639b166c79..21c7a6b1a1 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -4617,22 +4617,6 @@ static int opt_arg(const char *arg, int arg_short, const char *arg_long, int *va\n \treturn 1;\n }\n \n-static inline int short_opt(char opt, const char **argv,\n-\t\t\t    const char **optarg)\n-{\n-\tconst char *arg = argv[0];\n-\tif (arg[0] != '-' || arg[1] != opt)\n-\t\treturn 0;\n-\tif (arg[2] != '\\0') {\n-\t\t*optarg = arg + 2;\n-\t\treturn 1;\n-\t}\n-\tif (!argv[1])\n-\t\tdie(\"Option '%c' requires a value\", opt);\n-\t*optarg = argv[1];\n-\treturn 2;\n-}\n-\n int parse_long_opt(const char *opt, const char **argv,\n \t\t   const char **optarg)\n {\n@@ -5397,6 +5381,8 @@ static void prep_parse_options(struct diff_options *options)\n \t\tOPT_BIT_F(0, \"pickaxe-regex\", &options->pickaxe_opts,\n \t\t\t  N_(\"treat <string> in -S as extended POSIX regular expression\"),\n \t\t\t  DIFF_PICKAXE_REGEX, PARSE_OPT_NONEG),\n+\t\tOPT_FILENAME('O', NULL, &options->orderfile,\n+\t\t\t     N_(\"override diff.orderFile configuration variable\")),\n \t\t{ OPTION_CALLBACK, 0, \"output\", options, N_(\"<file>\"),\n \t\t  N_(\"Output to a specific file\"),\n \t\t  PARSE_OPT_NONEG, NULL, 0, diff_opt_output },\n@@ -5449,10 +5435,7 @@ int diff_opt_parse(struct diff_options *options,\n \t}\n \n \t/* misc options */\n-\telse if ((argcount = short_opt('O', av, &optarg))) {\n-\t\toptions->orderfile = prefix_filename(prefix, optarg);\n-\t\treturn argcount;\n-\t} else if (skip_prefix(arg, \"--find-object=\", &arg))\n+\telse if (skip_prefix(arg, \"--find-object=\", &arg))\n \t\treturn parse_objfind_opt(options, arg);\n \telse if ((argcount = parse_long_opt(\"diff-filter\", av, &optarg))) {\n \t\tint offending = parse_diff_filter_opt(optarg, options);\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"371987","messageId":"20190320114703.18659-9-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190320114703.18659-1-pclouds@gmail.com","subject":"[PATCH 08/20] diff-parseopt: convert --find-object","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-20T11:46:51Z","receivedAt":"2019-03-20T11:47:52Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"while at it, mark one more string for translation.\n\nSigned-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 14 +++++++++-----\n 1 file changed, 9 insertions(+), 5 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex 21c7a6b1a1..694f32148c 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -4799,12 +4799,15 @@ static int diff_opt_ws_error_highlight(const struct option *option,\n \treturn 0;\n }\n \n-static int parse_objfind_opt(struct diff_options *opt, const char *arg)\n+static int diff_opt_find_object(const struct option *option,\n+\t\t\t\tconst char *arg, int unset)\n {\n+\tstruct diff_options *opt = option->value;\n \tstruct object_id oid;\n \n+\tBUG_ON_OPT_NEG(unset);\n \tif (get_oid(arg, &oid))\n-\t\treturn error(\"unable to resolve '%s'\", arg);\n+\t\treturn error(_(\"unable to resolve '%s'\"), arg);\n \n \tif (!opt->objfind)\n \t\topt->objfind = xcalloc(1, sizeof(*opt->objfind));\n@@ -4813,7 +4816,7 @@ static int parse_objfind_opt(struct diff_options *opt, const char *arg)\n \topt->flags.recursive = 1;\n \topt->flags.tree_in_recursive = 1;\n \toidset_insert(opt->objfind, &oid);\n-\treturn 1;\n+\treturn 0;\n }\n \n static int diff_opt_anchored(const struct option *opt,\n@@ -5383,6 +5386,9 @@ static void prep_parse_options(struct diff_options *options)\n \t\t\t  DIFF_PICKAXE_REGEX, PARSE_OPT_NONEG),\n \t\tOPT_FILENAME('O', NULL, &options->orderfile,\n \t\t\t     N_(\"override diff.orderFile configuration variable\")),\n+\t\tOPT_CALLBACK_F(0, \"find-object\", options, N_(\"<object-id>\"),\n+\t\t\t       N_(\"look for differences that change the number of occurrences of the specified object\"),\n+\t\t\t       PARSE_OPT_NONEG, diff_opt_find_object),\n \t\t{ OPTION_CALLBACK, 0, \"output\", options, N_(\"<file>\"),\n \t\t  N_(\"Output to a specific file\"),\n \t\t  PARSE_OPT_NONEG, NULL, 0, diff_opt_output },\n@@ -5435,8 +5441,6 @@ int diff_opt_parse(struct diff_options *options,\n \t}\n \n \t/* misc options */\n-\telse if (skip_prefix(arg, \"--find-object=\", &arg))\n-\t\treturn parse_objfind_opt(options, arg);\n \telse if ((argcount = parse_long_opt(\"diff-filter\", av, &optarg))) {\n \t\tint offending = parse_diff_filter_opt(optarg, options);\n \t\tif (offending)\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"371988","messageId":"20190320114703.18659-10-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190320114703.18659-1-pclouds@gmail.com","subject":"[PATCH 09/20] diff-parseopt: convert --diff-filter","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-20T11:46:52Z","receivedAt":"2019-03-20T11:47:57Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"while at it, mark one more string for translation\n\nSigned-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 18 +++++++++---------\n 1 file changed, 9 insertions(+), 9 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex 694f32148c..6e84af1cce 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -4736,10 +4736,13 @@ static unsigned filter_bit_tst(char status, const struct diff_options *opt)\n \treturn opt->filter & filter_bit[(int) status];\n }\n \n-static int parse_diff_filter_opt(const char *optarg, struct diff_options *opt)\n+static int diff_opt_diff_filter(const struct option *option,\n+\t\t\t\tconst char *optarg, int unset)\n {\n+\tstruct diff_options *opt = option->value;\n \tint i, optch;\n \n+\tBUG_ON_OPT_NEG(unset);\n \tprepare_filter_bits();\n \n \t/*\n@@ -4770,7 +4773,8 @@ static int parse_diff_filter_opt(const char *optarg, struct diff_options *opt)\n \n \t\tbit = (0 <= optch && optch <= 'Z') ? filter_bit[optch] : 0;\n \t\tif (!bit)\n-\t\t\treturn optarg[i];\n+\t\t\treturn error(_(\"unknown change class '%c' in --diff-filter=%s\"),\n+\t\t\t\t     optarg[i], optarg);\n \t\tif (negate)\n \t\t\topt->filter &= ~bit;\n \t\telse\n@@ -5389,6 +5393,9 @@ static void prep_parse_options(struct diff_options *options)\n \t\tOPT_CALLBACK_F(0, \"find-object\", options, N_(\"<object-id>\"),\n \t\t\t       N_(\"look for differences that change the number of occurrences of the specified object\"),\n \t\t\t       PARSE_OPT_NONEG, diff_opt_find_object),\n+\t\tOPT_CALLBACK_F(0, \"diff-filter\", options, N_(\"[(A|C|D|M|R|T|U|X|B)...[*]]\"),\n+\t\t\t       N_(\"select files by diff type\"),\n+\t\t\t       PARSE_OPT_NONEG, diff_opt_diff_filter),\n \t\t{ OPTION_CALLBACK, 0, \"output\", options, N_(\"<file>\"),\n \t\t  N_(\"Output to a specific file\"),\n \t\t  PARSE_OPT_NONEG, NULL, 0, diff_opt_output },\n@@ -5441,13 +5448,6 @@ int diff_opt_parse(struct diff_options *options,\n \t}\n \n \t/* misc options */\n-\telse if ((argcount = parse_long_opt(\"diff-filter\", av, &optarg))) {\n-\t\tint offending = parse_diff_filter_opt(optarg, options);\n-\t\tif (offending)\n-\t\t\tdie(\"unknown change class '%c' in --diff-filter=%s\",\n-\t\t\t    offending, optarg);\n-\t\treturn argcount;\n-\t}\n \telse if (!strcmp(arg, \"--no-abbrev\"))\n \t\toptions->abbrev = 0;\n \telse if (!strcmp(arg, \"--abbrev\"))\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"371989","messageId":"20190320114703.18659-11-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190320114703.18659-1-pclouds@gmail.com","subject":"[PATCH 10/20] diff-parseopt: convert --[no-]abbrev","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-20T11:46:53Z","receivedAt":"2019-03-20T11:48:02Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"OPT__ABBREV() has the same behavior as the deleted code with one\ndifference: it does check for valid number and error out if not. And the\n'40' change is self explanatory.\n\nSigned-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c             | 12 +-----------\n parse-options-cb.c |  4 ++--\n 2 files changed, 3 insertions(+), 13 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex 6e84af1cce..30baf21021 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -5254,6 +5254,7 @@ static void prep_parse_options(struct diff_options *options)\n \t\tOPT_SET_INT('z', NULL, &options->line_termination,\n \t\t\t    N_(\"do not munge pathnames and use NULs as output field terminators in --raw or --numstat\"),\n \t\t\t    0),\n+\t\tOPT__ABBREV(&options->abbrev),\n \t\tOPT_CALLBACK_F(0, \"output-indicator-new\",\n \t\t\t       &options->output_indicators[OUTPUT_INDICATOR_NEW],\n \t\t\t       N_(\"<char>\"),\n@@ -5448,17 +5449,6 @@ int diff_opt_parse(struct diff_options *options,\n \t}\n \n \t/* misc options */\n-\telse if (!strcmp(arg, \"--no-abbrev\"))\n-\t\toptions->abbrev = 0;\n-\telse if (!strcmp(arg, \"--abbrev\"))\n-\t\toptions->abbrev = DEFAULT_ABBREV;\n-\telse if (skip_prefix(arg, \"--abbrev=\", &arg)) {\n-\t\toptions->abbrev = strtoul(arg, NULL, 10);\n-\t\tif (options->abbrev < MINIMUM_ABBREV)\n-\t\t\toptions->abbrev = MINIMUM_ABBREV;\n-\t\telse if (the_hash_algo->hexsz < options->abbrev)\n-\t\t\toptions->abbrev = the_hash_algo->hexsz;\n-\t}\n \telse if ((argcount = parse_long_opt(\"src-prefix\", av, &optarg))) {\n \t\toptions->a_prefix = optarg;\n \t\treturn argcount;\ndiff --git a/parse-options-cb.c b/parse-options-cb.c\nindex 2733393546..6e2e8d6273 100644\n--- a/parse-options-cb.c\n+++ b/parse-options-cb.c\n@@ -22,8 +22,8 @@ int parse_opt_abbrev_cb(const struct option *opt, const char *arg, int unset)\n \t\t\t\t     opt->long_name);\n \t\tif (v && v < MINIMUM_ABBREV)\n \t\t\tv = MINIMUM_ABBREV;\n-\t\telse if (v > 40)\n-\t\t\tv = 40;\n+\t\telse if (v > the_hash_algo->hexsz)\n+\t\t\tv = the_hash_algo->hexsz;\n \t}\n \t*(int *)(opt->value) = v;\n \treturn 0;\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"371990","messageId":"20190320114703.18659-12-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190320114703.18659-1-pclouds@gmail.com","subject":"[PATCH 11/20] diff-parseopt: convert --[src|dst]-prefix","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-20T11:46:54Z","receivedAt":"2019-03-20T11:48:06Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c          | 14 ++++++--------\n parse-options.h |  3 ++-\n 2 files changed, 8 insertions(+), 9 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex 30baf21021..2d34dc878e 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -5255,6 +5255,12 @@ static void prep_parse_options(struct diff_options *options)\n \t\t\t    N_(\"do not munge pathnames and use NULs as output field terminators in --raw or --numstat\"),\n \t\t\t    0),\n \t\tOPT__ABBREV(&options->abbrev),\n+\t\tOPT_STRING_F(0, \"src-prefix\", &options->a_prefix, N_(\"<prefix>\"),\n+\t\t\t     N_(\"show the given source prefix instead of \\\"a/\\\"\"),\n+\t\t\t     PARSE_OPT_NONEG),\n+\t\tOPT_STRING_F(0, \"dst-prefix\", &options->b_prefix, N_(\"<prefix>\"),\n+\t\t\t     N_(\"show the given source prefix instead of \\\"b/\\\"\"),\n+\t\t\t     PARSE_OPT_NONEG),\n \t\tOPT_CALLBACK_F(0, \"output-indicator-new\",\n \t\t\t       &options->output_indicators[OUTPUT_INDICATOR_NEW],\n \t\t\t       N_(\"<char>\"),\n@@ -5449,20 +5455,12 @@ int diff_opt_parse(struct diff_options *options,\n \t}\n \n \t/* misc options */\n-\telse if ((argcount = parse_long_opt(\"src-prefix\", av, &optarg))) {\n-\t\toptions->a_prefix = optarg;\n-\t\treturn argcount;\n-\t}\n \telse if ((argcount = parse_long_opt(\"line-prefix\", av, &optarg))) {\n \t\toptions->line_prefix = optarg;\n \t\toptions->line_prefix_length = strlen(options->line_prefix);\n \t\tgraph_setup_line_prefix(options);\n \t\treturn argcount;\n \t}\n-\telse if ((argcount = parse_long_opt(\"dst-prefix\", av, &optarg))) {\n-\t\toptions->b_prefix = optarg;\n-\t\treturn argcount;\n-\t}\n \telse if (!strcmp(arg, \"--no-prefix\"))\n \t\toptions->a_prefix = options->b_prefix = \"\";\n \telse if (opt_arg(arg, '\\0', \"inter-hunk-context\",\ndiff --git a/parse-options.h b/parse-options.h\nindex 7d83e2971d..c95cbe26f0 100644\n--- a/parse-options.h\n+++ b/parse-options.h\n@@ -136,6 +136,7 @@ struct option {\n #define OPT_BOOL_F(s, l, v, h, f)   OPT_SET_INT_F(s, l, v, h, 1, f)\n #define OPT_CALLBACK_F(s, l, v, a, h, f, cb)\t\t\t\\\n \t{ OPTION_CALLBACK, (s), (l), (v), (a), (h), (f), (cb) }\n+#define OPT_STRING_F(s, l, v, a, h, f)   { OPTION_STRING,  (s), (l), (v), (a), (h), (f) }\n \n #define OPT_END()                   { OPTION_END }\n #define OPT_ARGUMENT(l, h)          { OPTION_ARGUMENT, 0, (l), NULL, NULL, \\\n@@ -157,7 +158,7 @@ struct option {\n #define OPT_INTEGER(s, l, v, h)     { OPTION_INTEGER, (s), (l), (v), N_(\"n\"), (h) }\n #define OPT_MAGNITUDE(s, l, v, h)   { OPTION_MAGNITUDE, (s), (l), (v), \\\n \t\t\t\t      N_(\"n\"), (h), PARSE_OPT_NONEG }\n-#define OPT_STRING(s, l, v, a, h)   { OPTION_STRING,  (s), (l), (v), (a), (h) }\n+#define OPT_STRING(s, l, v, a, h)   OPT_STRING_F(s, l, v, a, h, 0)\n #define OPT_STRING_LIST(s, l, v, a, h) \\\n \t\t\t\t    { OPTION_CALLBACK, (s), (l), (v), (a), \\\n \t\t\t\t      (h), 0, &parse_opt_string_list }\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"371991","messageId":"20190320114703.18659-13-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190320114703.18659-1-pclouds@gmail.com","subject":"[PATCH 12/20] diff-parseopt: convert --line-prefix","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-20T11:46:55Z","receivedAt":"2019-03-20T11:48:11Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 23 +++++++++++++++--------\n 1 file changed, 15 insertions(+), 8 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex 2d34dc878e..4ab5b3c06a 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -5010,6 +5010,18 @@ static int diff_opt_ignore_submodules(const struct option *opt,\n \treturn 0;\n }\n \n+static int diff_opt_line_prefix(const struct option *opt,\n+\t\t\t\tconst char *optarg, int unset)\n+{\n+\tstruct diff_options *options = opt->value;\n+\n+\tBUG_ON_OPT_NEG(unset);\n+\toptions->line_prefix = optarg;\n+\toptions->line_prefix_length = strlen(options->line_prefix);\n+\tgraph_setup_line_prefix(options);\n+\treturn 0;\n+}\n+\n static enum parse_opt_result diff_opt_output(struct parse_opt_ctx_t *ctx,\n \t\t\t\t\t     const struct option *opt,\n \t\t\t\t\t     const char *arg, int unset)\n@@ -5261,6 +5273,9 @@ static void prep_parse_options(struct diff_options *options)\n \t\tOPT_STRING_F(0, \"dst-prefix\", &options->b_prefix, N_(\"<prefix>\"),\n \t\t\t     N_(\"show the given source prefix instead of \\\"b/\\\"\"),\n \t\t\t     PARSE_OPT_NONEG),\n+\t\tOPT_CALLBACK_F(0, \"line-prefix\", options, N_(\"<prefix>\"),\n+\t\t\t       N_(\"prepend an additional prefix to every line of output\"),\n+\t\t\t       PARSE_OPT_NONEG, diff_opt_line_prefix),\n \t\tOPT_CALLBACK_F(0, \"output-indicator-new\",\n \t\t\t       &options->output_indicators[OUTPUT_INDICATOR_NEW],\n \t\t\t       N_(\"<char>\"),\n@@ -5418,8 +5433,6 @@ int diff_opt_parse(struct diff_options *options,\n \t\t   const char **av, int ac, const char *prefix)\n {\n \tconst char *arg = av[0];\n-\tconst char *optarg;\n-\tint argcount;\n \n \tif (!prefix)\n \t\tprefix = \"\";\n@@ -5455,12 +5468,6 @@ int diff_opt_parse(struct diff_options *options,\n \t}\n \n \t/* misc options */\n-\telse if ((argcount = parse_long_opt(\"line-prefix\", av, &optarg))) {\n-\t\toptions->line_prefix = optarg;\n-\t\toptions->line_prefix_length = strlen(options->line_prefix);\n-\t\tgraph_setup_line_prefix(options);\n-\t\treturn argcount;\n-\t}\n \telse if (!strcmp(arg, \"--no-prefix\"))\n \t\toptions->a_prefix = options->b_prefix = \"\";\n \telse if (opt_arg(arg, '\\0', \"inter-hunk-context\",\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"371992","messageId":"20190320114703.18659-14-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190320114703.18659-1-pclouds@gmail.com","subject":"[PATCH 13/20] diff-parseopt: convert --no-prefix","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-20T11:46:56Z","receivedAt":"2019-03-20T11:48:16Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 17 +++++++++++++++--\n 1 file changed, 15 insertions(+), 2 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex 4ab5b3c06a..045fdbb882 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -5022,6 +5022,18 @@ static int diff_opt_line_prefix(const struct option *opt,\n \treturn 0;\n }\n \n+static int diff_opt_no_prefix(const struct option *opt,\n+\t\t\t      const char *optarg, int unset)\n+{\n+\tstruct diff_options *options = opt->value;\n+\n+\tBUG_ON_OPT_NEG(unset);\n+\tBUG_ON_OPT_ARG(optarg);\n+\toptions->a_prefix = \"\";\n+\toptions->b_prefix = \"\";\n+\treturn 0;\n+}\n+\n static enum parse_opt_result diff_opt_output(struct parse_opt_ctx_t *ctx,\n \t\t\t\t\t     const struct option *opt,\n \t\t\t\t\t     const char *arg, int unset)\n@@ -5276,6 +5288,9 @@ static void prep_parse_options(struct diff_options *options)\n \t\tOPT_CALLBACK_F(0, \"line-prefix\", options, N_(\"<prefix>\"),\n \t\t\t       N_(\"prepend an additional prefix to every line of output\"),\n \t\t\t       PARSE_OPT_NONEG, diff_opt_line_prefix),\n+\t\tOPT_CALLBACK_F(0, \"no-prefix\", options, NULL,\n+\t\t\t       N_(\"no not show any source or destination prefix\"),\n+\t\t\t       PARSE_OPT_NONEG | PARSE_OPT_NOARG, diff_opt_no_prefix),\n \t\tOPT_CALLBACK_F(0, \"output-indicator-new\",\n \t\t\t       &options->output_indicators[OUTPUT_INDICATOR_NEW],\n \t\t\t       N_(\"<char>\"),\n@@ -5468,8 +5483,6 @@ int diff_opt_parse(struct diff_options *options,\n \t}\n \n \t/* misc options */\n-\telse if (!strcmp(arg, \"--no-prefix\"))\n-\t\toptions->a_prefix = options->b_prefix = \"\";\n \telse if (opt_arg(arg, '\\0', \"inter-hunk-context\",\n \t\t\t &options->interhunkcontext))\n \t\t;\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"371993","messageId":"20190320114703.18659-15-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190320114703.18659-1-pclouds@gmail.com","subject":"[PATCH 14/20] diff-parseopt: convert --inter-hunk-context","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-20T11:46:57Z","receivedAt":"2019-03-20T11:48:20Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c          | 50 +++----------------------------------------------\n parse-options.h |  3 ++-\n 2 files changed, 5 insertions(+), 48 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex 045fdbb882..e2f515a7da 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -4573,50 +4573,6 @@ void diff_setup_done(struct diff_options *options)\n \tFREE_AND_NULL(options->parseopts);\n }\n \n-static int opt_arg(const char *arg, int arg_short, const char *arg_long, int *val)\n-{\n-\tchar c, *eq;\n-\tint len;\n-\n-\tif (*arg != '-')\n-\t\treturn 0;\n-\tc = *++arg;\n-\tif (!c)\n-\t\treturn 0;\n-\tif (c == arg_short) {\n-\t\tc = *++arg;\n-\t\tif (!c)\n-\t\t\treturn 1;\n-\t\tif (val && isdigit(c)) {\n-\t\t\tchar *end;\n-\t\t\tint n = strtoul(arg, &end, 10);\n-\t\t\tif (*end)\n-\t\t\t\treturn 0;\n-\t\t\t*val = n;\n-\t\t\treturn 1;\n-\t\t}\n-\t\treturn 0;\n-\t}\n-\tif (c != '-')\n-\t\treturn 0;\n-\targ++;\n-\teq = strchrnul(arg, '=');\n-\tlen = eq - arg;\n-\tif (!len || strncmp(arg, arg_long, len))\n-\t\treturn 0;\n-\tif (*eq) {\n-\t\tint n;\n-\t\tchar *end;\n-\t\tif (!isdigit(*++eq))\n-\t\t\treturn 0;\n-\t\tn = strtoul(eq, &end, 10);\n-\t\tif (*end)\n-\t\t\treturn 0;\n-\t\t*val = n;\n-\t}\n-\treturn 1;\n-}\n-\n int parse_long_opt(const char *opt, const char **argv,\n \t\t   const char **optarg)\n {\n@@ -5291,6 +5247,9 @@ static void prep_parse_options(struct diff_options *options)\n \t\tOPT_CALLBACK_F(0, \"no-prefix\", options, NULL,\n \t\t\t       N_(\"no not show any source or destination prefix\"),\n \t\t\t       PARSE_OPT_NONEG | PARSE_OPT_NOARG, diff_opt_no_prefix),\n+\t\tOPT_INTEGER_F(0, \"inter-hunk-context\", &options->interhunkcontext,\n+\t\t\t      N_(\"show context between diff hunks up to the specified number of lines\"),\n+\t\t\t      PARSE_OPT_NONEG),\n \t\tOPT_CALLBACK_F(0, \"output-indicator-new\",\n \t\t\t       &options->output_indicators[OUTPUT_INDICATOR_NEW],\n \t\t\t       N_(\"<char>\"),\n@@ -5483,9 +5442,6 @@ int diff_opt_parse(struct diff_options *options,\n \t}\n \n \t/* misc options */\n-\telse if (opt_arg(arg, '\\0', \"inter-hunk-context\",\n-\t\t\t &options->interhunkcontext))\n-\t\t;\n \telse\n \t\treturn 0;\n \treturn 1;\ndiff --git a/parse-options.h b/parse-options.h\nindex c95cbe26f0..cca64d04cb 100644\n--- a/parse-options.h\n+++ b/parse-options.h\n@@ -137,6 +137,7 @@ struct option {\n #define OPT_CALLBACK_F(s, l, v, a, h, f, cb)\t\t\t\\\n \t{ OPTION_CALLBACK, (s), (l), (v), (a), (h), (f), (cb) }\n #define OPT_STRING_F(s, l, v, a, h, f)   { OPTION_STRING,  (s), (l), (v), (a), (h), (f) }\n+#define OPT_INTEGER_F(s, l, v, h, f)     { OPTION_INTEGER, (s), (l), (v), N_(\"n\"), (h), (f) }\n \n #define OPT_END()                   { OPTION_END }\n #define OPT_ARGUMENT(l, h)          { OPTION_ARGUMENT, 0, (l), NULL, NULL, \\\n@@ -155,7 +156,7 @@ struct option {\n \t\t\t\t      (h), PARSE_OPT_NOARG | PARSE_OPT_HIDDEN, NULL, 1}\n #define OPT_CMDMODE(s, l, v, h, i)  { OPTION_CMDMODE, (s), (l), (v), NULL, \\\n \t\t\t\t      (h), PARSE_OPT_NOARG|PARSE_OPT_NONEG, NULL, (i) }\n-#define OPT_INTEGER(s, l, v, h)     { OPTION_INTEGER, (s), (l), (v), N_(\"n\"), (h) }\n+#define OPT_INTEGER(s, l, v, h)     OPT_INTEGER_F(s, l, v, h, 0)\n #define OPT_MAGNITUDE(s, l, v, h)   { OPTION_MAGNITUDE, (s), (l), (v), \\\n \t\t\t\t      N_(\"n\"), (h), PARSE_OPT_NONEG }\n #define OPT_STRING(s, l, v, a, h)   OPT_STRING_F(s, l, v, a, h, 0)\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"371994","messageId":"20190320114703.18659-16-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190320114703.18659-1-pclouds@gmail.com","subject":"[PATCH 15/20] diff-parseopt: convert --[no-]color-moved","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-20T11:46:58Z","receivedAt":"2019-03-20T11:48:24Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"mark one more string for translation while at there\n\nSigned-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 38 +++++++++++++++++++++++++-------------\n 1 file changed, 25 insertions(+), 13 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex e2f515a7da..df4303de4e 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -4841,6 +4841,27 @@ static int diff_opt_char(const struct option *opt,\n \treturn 0;\n }\n \n+static int diff_opt_color_moved(const struct option *opt,\n+\t\t\t\tconst char *arg, int unset)\n+{\n+\tstruct diff_options *options = opt->value;\n+\n+\tif (unset) {\n+\t\toptions->color_moved = COLOR_MOVED_NO;\n+\t} else if (!arg) {\n+\t\tif (diff_color_moved_default)\n+\t\t\toptions->color_moved = diff_color_moved_default;\n+\t\tif (options->color_moved == COLOR_MOVED_NO)\n+\t\t\toptions->color_moved = COLOR_MOVED_DEFAULT;\n+\t} else {\n+\t\tint cm = parse_color_moved(arg);\n+\t\tif (cm < 0)\n+\t\t\treturn error(_(\"bad --color-moved argument: %s\"), arg);\n+\t\toptions->color_moved = cm;\n+\t}\n+\treturn 0;\n+}\n+\n static int diff_opt_color_words(const struct option *opt,\n \t\t\t\tconst char *arg, int unset)\n {\n@@ -5339,6 +5360,9 @@ static void prep_parse_options(struct diff_options *options)\n \t\tOPT_CALLBACK_F(0, \"color-words\", options, N_(\"<regex>\"),\n \t\t\t       N_(\"equivalent to --word-diff=color --word-diff-regex=<regex>\"),\n \t\t\t       PARSE_OPT_NONEG | PARSE_OPT_OPTARG, diff_opt_color_words),\n+\t\tOPT_CALLBACK_F(0, \"color-moved\", options, N_(\"<mode>\"),\n+\t\t\t       N_(\"move lines of code are colored differently\"),\n+\t\t\t       PARSE_OPT_OPTARG, diff_opt_color_moved),\n \n \t\tOPT_GROUP(N_(\"Diff other options\")),\n \t\tOPT_CALLBACK_F(0, \"relative\", options, N_(\"<prefix>\"),\n@@ -5422,19 +5446,7 @@ int diff_opt_parse(struct diff_options *options,\n \t\treturn ac;\n \n \t/* flags options */\n-\tif (!strcmp(arg, \"--color-moved\")) {\n-\t\tif (diff_color_moved_default)\n-\t\t\toptions->color_moved = diff_color_moved_default;\n-\t\tif (options->color_moved == COLOR_MOVED_NO)\n-\t\t\toptions->color_moved = COLOR_MOVED_DEFAULT;\n-\t} else if (!strcmp(arg, \"--no-color-moved\"))\n-\t\toptions->color_moved = COLOR_MOVED_NO;\n-\telse if (skip_prefix(arg, \"--color-moved=\", &arg)) {\n-\t\tint cm = parse_color_moved(arg);\n-\t\tif (cm < 0)\n-\t\t\treturn error(\"bad --color-moved argument: %s\", arg);\n-\t\toptions->color_moved = cm;\n-\t} else if (skip_prefix(arg, \"--color-moved-ws=\", &arg)) {\n+\tif (skip_prefix(arg, \"--color-moved-ws=\", &arg)) {\n \t\tunsigned cm = parse_color_moved_ws(arg);\n \t\tif (cm & COLOR_MOVED_WS_ERROR)\n \t\t\treturn -1;\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"371995","messageId":"20190320114703.18659-17-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190320114703.18659-1-pclouds@gmail.com","subject":"[PATCH 16/20] diff-parseopt: convert --color-moved-ws","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-20T11:46:59Z","receivedAt":"2019-03-20T11:48:29Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 35 ++++++++++++++++++-----------------\n 1 file changed, 18 insertions(+), 17 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex df4303de4e..8f79d3f002 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -4862,6 +4862,20 @@ static int diff_opt_color_moved(const struct option *opt,\n \treturn 0;\n }\n \n+static int diff_opt_color_moved_ws(const struct option *opt,\n+\t\t\t\t   const char *arg, int unset)\n+{\n+\tstruct diff_options *options = opt->value;\n+\tunsigned cm;\n+\n+\tBUG_ON_OPT_NEG(unset);\n+\tcm = parse_color_moved_ws(arg);\n+\tif (cm & COLOR_MOVED_WS_ERROR)\n+\t\treturn error(_(\"invalid mode '%s' in --color-moved-ws\"), arg);\n+\toptions->color_moved_ws_handling = cm;\n+\treturn 0;\n+}\n+\n static int diff_opt_color_words(const struct option *opt,\n \t\t\t\tconst char *arg, int unset)\n {\n@@ -5363,6 +5377,9 @@ static void prep_parse_options(struct diff_options *options)\n \t\tOPT_CALLBACK_F(0, \"color-moved\", options, N_(\"<mode>\"),\n \t\t\t       N_(\"move lines of code are colored differently\"),\n \t\t\t       PARSE_OPT_OPTARG, diff_opt_color_moved),\n+\t\tOPT_CALLBACK_F(0, \"color-moved-ws\", options, N_(\"<mode>\"),\n+\t\t\t       N_(\"how white spaces are ignored in --color-moved\"),\n+\t\t\t       PARSE_OPT_NONEG, diff_opt_color_moved_ws),\n \n \t\tOPT_GROUP(N_(\"Diff other options\")),\n \t\tOPT_CALLBACK_F(0, \"relative\", options, N_(\"<prefix>\"),\n@@ -5430,8 +5447,6 @@ static void prep_parse_options(struct diff_options *options)\n int diff_opt_parse(struct diff_options *options,\n \t\t   const char **av, int ac, const char *prefix)\n {\n-\tconst char *arg = av[0];\n-\n \tif (!prefix)\n \t\tprefix = \"\";\n \n@@ -5442,21 +5457,7 @@ int diff_opt_parse(struct diff_options *options,\n \t\t\t   PARSE_OPT_ONE_SHOT |\n \t\t\t   PARSE_OPT_STOP_AT_NON_OPTION);\n \n-\tif (ac)\n-\t\treturn ac;\n-\n-\t/* flags options */\n-\tif (skip_prefix(arg, \"--color-moved-ws=\", &arg)) {\n-\t\tunsigned cm = parse_color_moved_ws(arg);\n-\t\tif (cm & COLOR_MOVED_WS_ERROR)\n-\t\t\treturn -1;\n-\t\toptions->color_moved_ws_handling = cm;\n-\t}\n-\n-\t/* misc options */\n-\telse\n-\t\treturn 0;\n-\treturn 1;\n+\treturn ac;\n }\n \n int parse_rename_score(const char **cp_p)\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"371996","messageId":"20190320114703.18659-18-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190320114703.18659-1-pclouds@gmail.com","subject":"[PATCH 17/20] diff.c: allow --no-color-moved-ws","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-20T11:47:00Z","receivedAt":"2019-03-20T11:48:34Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"This option is added in commit b73bcbac4a (diff: allow\n--no-color-moved-ws - 2018-11-23) in pw/diff-color-moved-ws-fix. To ease\nmerge conflict resolution, re-implement the option handling here so that\nthe conflict could be resolved by taking this side of change.\n\nSigned-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 8 ++++++--\n 1 file changed, 6 insertions(+), 2 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex 8f79d3f002..6ce59d0621 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -4868,7 +4868,11 @@ static int diff_opt_color_moved_ws(const struct option *opt,\n \tstruct diff_options *options = opt->value;\n \tunsigned cm;\n \n-\tBUG_ON_OPT_NEG(unset);\n+\tif (unset) {\n+\t\toptions->color_moved_ws_handling = 0;\n+\t\treturn 0;\n+\t}\n+\n \tcm = parse_color_moved_ws(arg);\n \tif (cm & COLOR_MOVED_WS_ERROR)\n \t\treturn error(_(\"invalid mode '%s' in --color-moved-ws\"), arg);\n@@ -5379,7 +5383,7 @@ static void prep_parse_options(struct diff_options *options)\n \t\t\t       PARSE_OPT_OPTARG, diff_opt_color_moved),\n \t\tOPT_CALLBACK_F(0, \"color-moved-ws\", options, N_(\"<mode>\"),\n \t\t\t       N_(\"how white spaces are ignored in --color-moved\"),\n-\t\t\t       PARSE_OPT_NONEG, diff_opt_color_moved_ws),\n+\t\t\t       0, diff_opt_color_moved_ws),\n \n \t\tOPT_GROUP(N_(\"Diff other options\")),\n \t\tOPT_CALLBACK_F(0, \"relative\", options, N_(\"<prefix>\"),\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"371997","messageId":"20190320114703.18659-19-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190320114703.18659-1-pclouds@gmail.com","subject":"[PATCH 18/20] range-diff: use parse_options() instead of diff_opt_parse()","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-20T11:47:01Z","receivedAt":"2019-03-20T11:48:39Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Diff's internal option parsing is now done with 'struct option', which\nmakes it possible to combine all diff options to range-diff and parse\neverything all at once. Parsing code becomes simpler, and we get a\nlooong 'git range-diff -h'\n\nSigned-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n builtin/range-diff.c | 26 ++++++--------------------\n 1 file changed, 6 insertions(+), 20 deletions(-)\n\ndiff --git a/builtin/range-diff.c b/builtin/range-diff.c\nindex f01a0be851..784bd19321 100644\n--- a/builtin/range-diff.c\n+++ b/builtin/range-diff.c\n@@ -16,42 +16,27 @@ int cmd_range_diff(int argc, const char **argv, const char *prefix)\n \tint creation_factor = RANGE_DIFF_CREATION_FACTOR_DEFAULT;\n \tstruct diff_options diffopt = { NULL };\n \tint simple_color = -1;\n-\tstruct option options[] = {\n+\tstruct option range_diff_options[] = {\n \t\tOPT_INTEGER(0, \"creation-factor\", &creation_factor,\n \t\t\t    N_(\"Percentage by which creation is weighted\")),\n \t\tOPT_BOOL(0, \"no-dual-color\", &simple_color,\n \t\t\t    N_(\"use simple diff colors\")),\n \t\tOPT_END()\n \t};\n-\tint i, j, res = 0;\n+\tstruct option *options;\n+\tint res = 0;\n \tstruct strbuf range1 = STRBUF_INIT, range2 = STRBUF_INIT;\n \n \tgit_config(git_diff_ui_config, NULL);\n \n \trepo_diff_setup(the_repository, &diffopt);\n \n+\toptions = parse_options_concat(range_diff_options, diffopt.parseopts);\n \targc = parse_options(argc, argv, NULL, options,\n-\t\t\t     builtin_range_diff_usage, PARSE_OPT_KEEP_UNKNOWN |\n-\t\t\t     PARSE_OPT_KEEP_DASHDASH | PARSE_OPT_KEEP_ARGV0);\n-\n-\tfor (i = j = 1; i < argc && strcmp(\"--\", argv[i]); ) {\n-\t\tint c = diff_opt_parse(&diffopt, argv + i, argc - i, prefix);\n+\t\t\t     builtin_range_diff_usage, 0);\n \n-\t\tif (!c)\n-\t\t\targv[j++] = argv[i++];\n-\t\telse\n-\t\t\ti += c;\n-\t}\n-\twhile (i < argc)\n-\t\targv[j++] = argv[i++];\n-\targc = j;\n \tdiff_setup_done(&diffopt);\n \n-\t/* Make sure that there are no unparsed options */\n-\targc = parse_options(argc, argv, NULL,\n-\t\t\t     options + ARRAY_SIZE(options) - 1, /* OPT_END */\n-\t\t\t     builtin_range_diff_usage, 0);\n-\n \t/* force color when --dual-color was used */\n \tif (!simple_color)\n \t\tdiffopt.use_color = 1;\n@@ -90,6 +75,7 @@ int cmd_range_diff(int argc, const char **argv, const char *prefix)\n \t\terror(_(\"need two commit ranges\"));\n \t\tusage_with_options(builtin_range_diff_usage, options);\n \t}\n+\tFREE_AND_NULL(options);\n \n \tres = show_range_diff(range1.buf, range2.buf, creation_factor,\n \t\t\t      simple_color < 1, &diffopt);\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"371998","messageId":"20190320114703.18659-20-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190320114703.18659-1-pclouds@gmail.com","subject":"[PATCH 19/20] diff --no-index: use parse_options() instead of diff_opt_parse()","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-20T11:47:02Z","receivedAt":"2019-03-20T11:48:44Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"While at there, move exit() back to the caller. It's easier to see the\nflow that way than burying it in diff-no-index.c\n\nSigned-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n builtin/diff.c           | 21 +++--------------\n diff-no-index.c          | 49 ++++++++++++++++++++++++----------------\n diff.h                   |  3 ++-\n t/t4053-diff-no-index.sh |  3 +--\n 4 files changed, 35 insertions(+), 41 deletions(-)\n\ndiff --git a/builtin/diff.c b/builtin/diff.c\nindex f0393bba23..52dc3e136f 100644\n--- a/builtin/diff.c\n+++ b/builtin/diff.c\n@@ -320,26 +320,11 @@ int cmd_diff(int argc, const char **argv, const char *prefix)\n \n \trepo_init_revisions(the_repository, &rev, prefix);\n \n-\tif (no_index && argc != i + 2) {\n-\t\tif (no_index == DIFF_NO_INDEX_IMPLICIT) {\n-\t\t\t/*\n-\t\t\t * There was no --no-index and there were not two\n-\t\t\t * paths. It is possible that the user intended\n-\t\t\t * to do an inside-repository operation.\n-\t\t\t */\n-\t\t\tfprintf(stderr, \"Not a git repository\\n\");\n-\t\t\tfprintf(stderr,\n-\t\t\t\t\"To compare two paths outside a working tree:\\n\");\n-\t\t}\n-\t\t/* Give the usage message for non-repository usage and exit. */\n-\t\tusagef(\"git diff %s <path> <path>\",\n-\t\t       no_index == DIFF_NO_INDEX_EXPLICIT ?\n-\t\t       \"--no-index\" : \"[--no-index]\");\n-\n-\t}\n \tif (no_index)\n \t\t/* If this is a no-index diff, just run it and exit there. */\n-\t\tdiff_no_index(the_repository, &rev, argc, argv);\n+\t\texit(diff_no_index(the_repository, &rev,\n+\t\t\t\t   no_index == DIFF_NO_INDEX_IMPLICIT,\n+\t\t\t\t   argc, argv));\n \n \t/* Otherwise, we are doing the usual \"git\" diff */\n \trev.diffopt.skip_stat_unmatch = !!diff_auto_refresh_index;\ndiff --git a/diff-no-index.c b/diff-no-index.c\nindex 9414e922d1..a879f45862 100644\n--- a/diff-no-index.c\n+++ b/diff-no-index.c\n@@ -14,6 +14,7 @@\n #include \"revision.h\"\n #include \"log-tree.h\"\n #include \"builtin.h\"\n+#include \"parse-options.h\"\n #include \"string-list.h\"\n #include \"dir.h\"\n \n@@ -233,35 +234,43 @@ static void fixup_paths(const char **path, struct strbuf *replacement)\n \t}\n }\n \n-void diff_no_index(struct repository *r,\n-\t\t   struct rev_info *revs,\n-\t\t   int argc, const char **argv)\n+static const char * const diff_no_index_usage[] = {\n+\tN_(\"git diff --no-index [<options>] <path> <path>\"),\n+\tNULL\n+};\n+\n+int diff_no_index(struct repository *r,\n+\t\t  struct rev_info *revs,\n+\t\t  int implicit_no_index,\n+\t\t  int argc, const char **argv)\n {\n-\tint i;\n+\tint i, no_index;\n \tconst char *paths[2];\n \tstruct strbuf replacement = STRBUF_INIT;\n \tconst char *prefix = revs->prefix;\n+\tstruct option no_index_options[] = {\n+\t\tOPT_BOOL_F(0, \"no-index\", &no_index, \"\",\n+\t\t\t   PARSE_OPT_NONEG | PARSE_OPT_HIDDEN),\n+\t\tOPT_END(),\n+\t};\n+\tstruct option *options;\n \n \t/*\n \t * FIXME: --no-index should not look at index and we should be\n \t * able to pass NULL repo. Maybe later.\n \t */\n \trepo_diff_setup(r, &revs->diffopt);\n-\tfor (i = 1; i < argc - 2; ) {\n-\t\tint j;\n-\t\tif (!strcmp(argv[i], \"--no-index\"))\n-\t\t\ti++;\n-\t\telse if (!strcmp(argv[i], \"--\"))\n-\t\t\ti++;\n-\t\telse {\n-\t\t\tj = diff_opt_parse(&revs->diffopt, argv + i, argc - i,\n-\t\t\t\t\t   revs->prefix);\n-\t\t\tif (j <= 0)\n-\t\t\t\tdie(\"invalid diff option/value: %s\", argv[i]);\n-\t\t\ti += j;\n-\t\t}\n+\toptions = parse_options_concat(no_index_options,\n+\t\t\t\t       revs->diffopt.parseopts);\n+\targc = parse_options(argc, argv, revs->prefix, options,\n+\t\t\t     diff_no_index_usage, 0);\n+\tif (argc != 2) {\n+\t\tif (implicit_no_index)\n+\t\t\twarning(_(\"Not a git repository. Use --no-index to \"\n+\t\t\t\t  \"compare two paths outside a working tree\"));\n+\t\tusage_with_options(diff_no_index_usage, options);\n \t}\n-\n+\tFREE_AND_NULL(options);\n \tfor (i = 0; i < 2; i++) {\n \t\tconst char *p = argv[argc - 2 + i];\n \t\tif (!strcmp(p, \"-\"))\n@@ -293,7 +302,7 @@ void diff_no_index(struct repository *r,\n \trevs->diffopt.flags.exit_with_status = 1;\n \n \tif (queue_diff(&revs->diffopt, paths[0], paths[1]))\n-\t\texit(1);\n+\t\treturn 1;\n \tdiff_set_mnemonic_prefix(&revs->diffopt, \"1/\", \"2/\");\n \tdiffcore_std(&revs->diffopt);\n \tdiff_flush(&revs->diffopt);\n@@ -304,5 +313,5 @@ void diff_no_index(struct repository *r,\n \t * The return code for --no-index imitates diff(1):\n \t * 0 = no changes, 1 = changes, else error\n \t */\n-\texit(diff_result_code(&revs->diffopt, 0));\n+\treturn diff_result_code(&revs->diffopt, 0);\n }\ndiff --git a/diff.h b/diff.h\nindex d9ad73f0e1..03c6afda22 100644\n--- a/diff.h\n+++ b/diff.h\n@@ -437,7 +437,8 @@ int diff_flush_patch_id(struct diff_options *, struct object_id *, int);\n \n int diff_result_code(struct diff_options *, int);\n \n-void diff_no_index(struct repository *, struct rev_info *, int, const char **);\n+int diff_no_index(struct repository *, struct rev_info *,\n+\t\t  int implicit_no_index, int, const char **);\n \n int index_differs_from(struct repository *r, const char *def,\n \t\t       const struct diff_flags *flags,\ndiff --git a/t/t4053-diff-no-index.sh b/t/t4053-diff-no-index.sh\nindex 6e0dd6f9e5..fb25cdb789 100755\n--- a/t/t4053-diff-no-index.sh\n+++ b/t/t4053-diff-no-index.sh\n@@ -50,8 +50,7 @@ test_expect_success 'git diff --no-index executed outside repo gives correct err\n \t\texport GIT_CEILING_DIRECTORIES &&\n \t\tcd non/git &&\n \t\ttest_must_fail git diff --no-index a 2>actual.err &&\n-\t\techo \"usage: git diff --no-index <path> <path>\" >expect.err &&\n-\t\ttest_cmp expect.err actual.err\n+\t\ttest_i18ngrep \"usage: git diff --no-index\" actual.err\n \t)\n '\n \n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"371999","messageId":"20190320114703.18659-21-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190320114703.18659-1-pclouds@gmail.com","subject":"[PATCH 20/20] am: avoid diff_opt_parse()","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-20T11:47:03Z","receivedAt":"2019-03-20T11:48:48Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"diff_opt_parse() is a heavy hammer to just set diff filter. But it's\nthe only way because of the diff_status_letters[] mapping. Add a new\nAPI to set diff filter and use it in git-am. diff_opt_parse()'s only\nremaining call site in revision.c will be gone soon and having it here\njust because of git-am does not make sense.\n\nSigned-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n builtin/am.c | 4 ++--\n diff.c       | 6 ++++++\n diff.h       | 2 ++\n 3 files changed, 10 insertions(+), 2 deletions(-)\n\ndiff --git a/builtin/am.c b/builtin/am.c\nindex 95370313b6..0cbf285459 100644\n--- a/builtin/am.c\n+++ b/builtin/am.c\n@@ -1515,11 +1515,11 @@ static int fall_back_threeway(const struct am_state *state, const char *index_pa\n \t\t * review them with extra care to spot mismerges.\n \t\t */\n \t\tstruct rev_info rev_info;\n-\t\tconst char *diff_filter_str = \"--diff-filter=AM\";\n \n \t\trepo_init_revisions(the_repository, &rev_info, NULL);\n \t\trev_info.diffopt.output_format = DIFF_FORMAT_NAME_STATUS;\n-\t\tdiff_opt_parse(&rev_info.diffopt, &diff_filter_str, 1, rev_info.prefix);\n+\t\trev_info.diffopt.filter |= diff_filter_bit('A');\n+\t\trev_info.diffopt.filter |= diff_filter_bit('M');\n \t\tadd_pending_oid(&rev_info, \"HEAD\", &our_tree, 0);\n \t\tdiff_setup_done(&rev_info.diffopt);\n \t\trun_diff_index(&rev_info, 1);\ndiff --git a/diff.c b/diff.c\nindex 6ce59d0621..b94befd494 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -4692,6 +4692,12 @@ static unsigned filter_bit_tst(char status, const struct diff_options *opt)\n \treturn opt->filter & filter_bit[(int) status];\n }\n \n+unsigned diff_filter_bit(char status)\n+{\n+\tprepare_filter_bits();\n+\treturn filter_bit[(int) status];\n+}\n+\n static int diff_opt_diff_filter(const struct option *option,\n \t\t\t\tconst char *optarg, int unset)\n {\ndiff --git a/diff.h b/diff.h\nindex 03c6afda22..f88482705c 100644\n--- a/diff.h\n+++ b/diff.h\n@@ -233,6 +233,8 @@ struct diff_options {\n \tstruct option *parseopts;\n };\n \n+unsigned diff_filter_bit(char status);\n+\n void diff_emit_submodule_del(struct diff_options *o, const char *line);\n void diff_emit_submodule_add(struct diff_options *o, const char *line);\n void diff_emit_submodule_untracked(struct diff_options *o, const char *path);\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"372020","messageId":"CAN0heSp+QAXe1uMO=VC8bp09UC6S-BH=0RwkVMdDBhZC-dEbPA@mail.gmail.com","threadId":"50790","inReplyTo":"20190320114703.18659-2-pclouds@gmail.com","subject":"Re: [PATCH 01/20] diff-parseopt: convert --ws-error-highlight","fromName":"Martin Ågren","fromEmail":"martin.agren@gmail.com","sentAt":"2019-03-20T20:19:47Z","receivedAt":"2019-03-20T20:20:04Z","isPatch":true,"sender":{"key":"martin.agren@gmail.com","avatar":null},"body":"On Wed, 20 Mar 2019 at 12:59, Nguyễn Thái Ngọc Duy <pclouds@gmail.com> wrote:\n>\n> mark one more string for translation while at there.\n\ns/^m/M/\n\n> +               OPT_CALLBACK_F(0, \"ws-error-highlight\", options, N_(\"<kind>\"),\n> +                              N_(\"highlight whitespaces errors in the context, old or new lines in the diff\"),\n> +                              PARSE_OPT_NONEG, diff_opt_ws_error_highlight),\n\ns/whitespaces/whitespace/\n\nI tripped on the comma, somehow, and part of the explanation why is\nperhaps because this gives (a few of) the possible values, but that's\nnot really indicated. Maybe wrap them in 'quotes', but maybe this text\nis already getting too long. Feel free to completely ignore this.\n\n\nMartin\n"},{"id":"372022","messageId":"CAN0heSoyOqMeJeBJ7HWRzOW3WABCSGfqV8CoEVMM37h+T10g5w@mail.gmail.com","threadId":"50790","inReplyTo":"20190320114703.18659-8-pclouds@gmail.com","subject":"Re: [PATCH 07/20] diff-parseopt: convert -O","fromName":"Martin Ågren","fromEmail":"martin.agren@gmail.com","sentAt":"2019-03-20T20:26:33Z","receivedAt":"2019-03-20T20:26:47Z","isPatch":true,"sender":{"key":"martin.agren@gmail.com","avatar":null},"body":"On Wed, 20 Mar 2019 at 12:48, Nguyễn Thái Ngọc Duy <pclouds@gmail.com> wrote:\n> +               OPT_FILENAME('O', NULL, &options->orderfile,\n> +                            N_(\"override diff.orderFile configuration variable\")),\n\nThis doesn't really tell me *why* I would want to provide -O. Or put\nanother way, there are lots of --foo-bar for overriding some baz.fooBar\nconfig item, but they're not described like this. The primary purpose of\n--foo-bar, at least to me, would be to solve some actual problem, like\n\"fooing the bar\", whatever that means.\n\nGleaning at the manpage, an alternative would be \"control the order in\nwhich files appear in the output\", but maybe you avoided that\ndeliberately? \"provide an orderfile\"?\n\n\nMartin\n"},{"id":"372023","messageId":"CAN0heSonEy5z_2ebwQfr35Y-y4n8j-WX2=LdT6Lu3zi7YMhJBg@mail.gmail.com","threadId":"50790","inReplyTo":"20190320114703.18659-14-pclouds@gmail.com","subject":"Re: [PATCH 13/20] diff-parseopt: convert --no-prefix","fromName":"Martin Ågren","fromEmail":"martin.agren@gmail.com","sentAt":"2019-03-20T20:30:54Z","receivedAt":"2019-03-20T20:31:09Z","isPatch":true,"sender":{"key":"martin.agren@gmail.com","avatar":null},"body":"On Wed, 20 Mar 2019 at 12:50, Nguyễn Thái Ngọc Duy <pclouds@gmail.com> wrote:\n> +               OPT_CALLBACK_F(0, \"no-prefix\", options, NULL,\n> +                              N_(\"no not show any source or destination prefix\"),\n> +                              PARSE_OPT_NONEG | PARSE_OPT_NOARG, diff_opt_no_prefix),\n\ns/no not/do not/\n"},{"id":"372033","messageId":"87zhppcfsq.fsf@evledraar.gmail.com","threadId":"50790","inReplyTo":"20190320114703.18659-11-pclouds@gmail.com","subject":"Re: [PATCH 10/20] diff-parseopt: convert --[no-]abbrev","fromName":"Ævar Arnfjörð Bjarmason","fromEmail":"avarab@gmail.com","sentAt":"2019-03-20T23:00:21Z","receivedAt":"2019-03-20T23:00:26Z","isPatch":true,"sender":{"key":"avarab@gmail.com","avatar":"https://avatars.githubusercontent.com/u/45301?v=4"},"body":"\nOn Wed, Mar 20 2019, Nguyễn Thái Ngọc Duy wrote:\n\n> [...]And the '40' change is self explanatory.\n\nLet me make an attempt at being dense anyway...\n\n> -\t\telse if (v > 40)\n> -\t\t\tv = 40;\n> +\t\telse if (v > the_hash_algo->hexsz)\n> +\t\t\tv = the_hash_algo->hexsz;\n>  \t}\n\nThis is obviously not a regression, it's a hardcoded 40 *now*. So we\nshould take this patch.\n\nBut in general, I wonder how this is going to work once we get a few\nsteps further into the SHA-256 migration. I.e. here we're still parsing\nthe command-line, and the_hash_algo might be initialized early to SHA-1.\n\nSo if I set --abbrev=45 it'll be trimmed to --abbrev=40 by this code.\n\nBut then shortly afterwards we pass my SHA-256 object down to some\nmachinery, and will then want to abbreviate it.\n\nIsn't that part of the code something we're going to want to support\nlooking up objects in either hash, even if we initially started out with\nSHA-1 in the_hash_algo? So we'll be over-abbreviating a SHA-256 object.\n\nLeaving aside the sillyness of wanting to abbreviate *anything* to 45\ncharacters, I wonder how those sorts of chicken & egg hash scenarios\nwill go involving the_hash_algo.\n"},{"id":"372041","messageId":"CACsJy8CuTX5Yh_80cLuQViNRF8fH_PcMSv0w_OYAt2EB_WfrQw@mail.gmail.com","threadId":"50790","inReplyTo":"87zhppcfsq.fsf@evledraar.gmail.com","subject":"Re: [PATCH 10/20] diff-parseopt: convert --[no-]abbrev","fromName":"Duy Nguyen","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-21T00:35:25Z","receivedAt":"2019-03-21T00:35:54Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"On Thu, Mar 21, 2019 at 6:00 AM Ævar Arnfjörð Bjarmason\n<avarab@gmail.com> wrote:\n>\n>\n> On Wed, Mar 20 2019, Nguyễn Thái Ngọc Duy wrote:\n>\n> > [...]And the '40' change is self explanatory.\n>\n> Let me make an attempt at being dense anyway...\n>\n> > -             else if (v > 40)\n> > -                     v = 40;\n> > +             else if (v > the_hash_algo->hexsz)\n> > +                     v = the_hash_algo->hexsz;\n> >       }\n>\n> This is obviously not a regression, it's a hardcoded 40 *now*. So we\n> should take this patch.\n>\n> But in general, I wonder how this is going to work once we get a few\n> steps further into the SHA-256 migration. I.e. here we're still parsing\n> the command-line, and the_hash_algo might be initialized early to SHA-1.\n\nThat would be wrong. the_hash_algo must be properly initialized by the\ntime any command parsing is done (except maybe \"git <options> <cmd>\").\nWhile parse_options() most of the time is just a dumb \"set this\nvariable, set that variable\", it often can have callbacks to do more\ncomplicated stuff and we can't just go with \"pre-initialized to SHA-1\"\nassumption. That's as bad as \"assume $CWD is worktree\" until worktree\nis discovered.\n\nThere is a corner case though. If some command takes hash algo as an\noption (e.g. git hash-object should work without a repo) then yes we\nmight have a problem since the_hash_algo might not be initialized yet,\ndepending on option order.\n\n> So if I set --abbrev=45 it'll be trimmed to --abbrev=40 by this code.\n>\n> But then shortly afterwards we pass my SHA-256 object down to some\n> machinery, and will then want to abbreviate it.\n>\n> Isn't that part of the code something we're going to want to support\n> looking up objects in either hash, even if we initially started out with\n> SHA-1 in the_hash_algo? So we'll be over-abbreviating a SHA-256 object.\n>\n> Leaving aside the sillyness of wanting to abbreviate *anything* to 45\n> characters, I wonder how those sorts of chicken & egg hash scenarios\n> will go involving the_hash_algo.\n-- \nDuy\n"},{"id":"372325","messageId":"20190324082014.2041-1-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190320114703.18659-1-pclouds@gmail.com","subject":"[PATCH v2 00/20] nd/diff-parseopt the last part","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-24T08:19:54Z","receivedAt":"2019-03-24T08:21:14Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"v2 fixes some help text and commit messages. No major changes.\n\nNguyễn Thái Ngọc Duy (20):\n  diff-parseopt: convert --ws-error-highlight\n  diff-parseopt: convert --ita-[in]visible-in-index\n  diff-parseopt: convert -z\n  diff-parseopt: convert -l\n  diff-parseopt: convert -S|-G\n  diff-parseopt: convert --pickaxe-all|--pickaxe-regex\n  diff-parseopt: convert -O\n  diff-parseopt: convert --find-object\n  diff-parseopt: convert --diff-filter\n  diff-parseopt: convert --[no-]abbrev\n  diff-parseopt: convert --[src|dst]-prefix\n  diff-parseopt: convert --line-prefix\n  diff-parseopt: convert --no-prefix\n  diff-parseopt: convert --inter-hunk-context\n  diff-parseopt: convert --[no-]color-moved\n  diff-parseopt: convert --color-moved-ws\n  diff.c: allow --no-color-moved-ws\n  range-diff: use parse_options() instead of diff_opt_parse()\n  diff --no-index: use parse_options() instead of diff_opt_parse()\n  am: avoid diff_opt_parse()\n\n builtin/am.c             |   4 +-\n builtin/diff.c           |  21 +--\n builtin/range-diff.c     |  26 +--\n diff-no-index.c          |  49 +++---\n diff.c                   | 337 +++++++++++++++++++--------------------\n diff.h                   |   5 +-\n parse-options-cb.c       |   4 +-\n parse-options.h          |   6 +-\n t/t4053-diff-no-index.sh |   3 +-\n 9 files changed, 219 insertions(+), 236 deletions(-)\n\nRange-diff dựa trên v1:\n 1:  676bba9a4c !  1:  ed9901217e diff-parseopt: convert --ws-error-highlight\n    @@ -2,7 +2,7 @@\n     \n         diff-parseopt: convert --ws-error-highlight\n     \n    -    mark one more string for translation while at there.\n    +    Mark one more string for translation while at there.\n     \n      diff --git a/diff.c b/diff.c\n      --- a/diff.c\n    @@ -38,7 +38,7 @@\n      \t\tOPT_COLOR_FLAG(0, \"color\", &options->use_color,\n      \t\t\t       N_(\"show colored diff\")),\n     +\t\tOPT_CALLBACK_F(0, \"ws-error-highlight\", options, N_(\"<kind>\"),\n    -+\t\t\t       N_(\"highlight whitespaces errors in the context, old or new lines in the diff\"),\n    ++\t\t\t       N_(\"highlight whitespace errors in the 'context', 'old' or 'new' lines in the diff\"),\n     +\t\t\t       PARSE_OPT_NONEG, diff_opt_ws_error_highlight),\n      \t\tOPT_CALLBACK_F(0, \"output-indicator-new\",\n      \t\t\t       &options->output_indicators[OUTPUT_INDICATOR_NEW],\n 2:  94fb8a961b =  2:  3ad3991675 diff-parseopt: convert --ita-[in]visible-in-index\n 3:  7b2c38485f !  3:  ea21fa9e03 diff-parseopt: convert -z\n    @@ -7,7 +7,7 @@\n      +++ b/diff.c\n     @@\n      \t\tOPT_CALLBACK_F(0, \"ws-error-highlight\", options, N_(\"<kind>\"),\n    - \t\t\t       N_(\"highlight whitespaces errors in the context, old or new lines in the diff\"),\n    + \t\t\t       N_(\"highlight whitespace errors in the 'context', 'old' or 'new' lines in the diff\"),\n      \t\t\t       PARSE_OPT_NONEG, diff_opt_ws_error_highlight),\n     +\t\tOPT_SET_INT('z', NULL, &options->line_termination,\n     +\t\t\t    N_(\"do not munge pathnames and use NULs as output field terminators in --raw or --numstat\"),\n 4:  470c29dfb6 =  4:  02b7116f53 diff-parseopt: convert -l\n 5:  f950b910dd =  5:  2d43346824 diff-parseopt: convert -S|-G\n 6:  a3d8dfbb9e =  6:  357b691470 diff-parseopt: convert --pickaxe-all|--pickaxe-regex\n 7:  209794414b !  7:  adc09e748e diff-parseopt: convert -O\n    @@ -33,7 +33,7 @@\n      \t\t\t  N_(\"treat <string> in -S as extended POSIX regular expression\"),\n      \t\t\t  DIFF_PICKAXE_REGEX, PARSE_OPT_NONEG),\n     +\t\tOPT_FILENAME('O', NULL, &options->orderfile,\n    -+\t\t\t     N_(\"override diff.orderFile configuration variable\")),\n    ++\t\t\t     N_(\"control the order in which files appear in the output\")),\n      \t\t{ OPTION_CALLBACK, 0, \"output\", options, N_(\"<file>\"),\n      \t\t  N_(\"Output to a specific file\"),\n      \t\t  PARSE_OPT_NONEG, NULL, 0, diff_opt_output },\n 8:  11730d9a4a !  8:  ca34bbd042 diff-parseopt: convert --find-object\n    @@ -2,7 +2,7 @@\n     \n         diff-parseopt: convert --find-object\n     \n    -    while at it, mark one more string for translation.\n    +    While at it, mark one more string for translation.\n     \n      diff --git a/diff.c b/diff.c\n      --- a/diff.c\n    @@ -37,7 +37,7 @@\n     @@\n      \t\t\t  DIFF_PICKAXE_REGEX, PARSE_OPT_NONEG),\n      \t\tOPT_FILENAME('O', NULL, &options->orderfile,\n    - \t\t\t     N_(\"override diff.orderFile configuration variable\")),\n    + \t\t\t     N_(\"control the order in which files appear in the output\")),\n     +\t\tOPT_CALLBACK_F(0, \"find-object\", options, N_(\"<object-id>\"),\n     +\t\t\t       N_(\"look for differences that change the number of occurrences of the specified object\"),\n     +\t\t\t       PARSE_OPT_NONEG, diff_opt_find_object),\n 9:  a70f80ffa5 !  9:  6a735031e0 diff-parseopt: convert --diff-filter\n    @@ -2,7 +2,7 @@\n     \n         diff-parseopt: convert --diff-filter\n     \n    -    while at it, mark one more string for translation\n    +    While at it, mark one more string for translation\n     \n      diff --git a/diff.c b/diff.c\n      --- a/diff.c\n10:  95f2d0e3b0 = 10:  646a5844f0 diff-parseopt: convert --[no-]abbrev\n11:  58bbccd2df = 11:  20e050397a diff-parseopt: convert --[src|dst]-prefix\n12:  4454256a15 = 12:  ae0d85b620 diff-parseopt: convert --line-prefix\n13:  1b882aaeb1 ! 13:  288d4fd648 diff-parseopt: convert --no-prefix\n    @@ -29,7 +29,7 @@\n      \t\t\t       N_(\"prepend an additional prefix to every line of output\"),\n      \t\t\t       PARSE_OPT_NONEG, diff_opt_line_prefix),\n     +\t\tOPT_CALLBACK_F(0, \"no-prefix\", options, NULL,\n    -+\t\t\t       N_(\"no not show any source or destination prefix\"),\n    ++\t\t\t       N_(\"do not show any source or destination prefix\"),\n     +\t\t\t       PARSE_OPT_NONEG | PARSE_OPT_NOARG, diff_opt_no_prefix),\n      \t\tOPT_CALLBACK_F(0, \"output-indicator-new\",\n      \t\t\t       &options->output_indicators[OUTPUT_INDICATOR_NEW],\n14:  3b1b06c51b ! 14:  753173f724 diff-parseopt: convert --inter-hunk-context\n    @@ -58,7 +58,7 @@\n      {\n     @@\n      \t\tOPT_CALLBACK_F(0, \"no-prefix\", options, NULL,\n    - \t\t\t       N_(\"no not show any source or destination prefix\"),\n    + \t\t\t       N_(\"do not show any source or destination prefix\"),\n      \t\t\t       PARSE_OPT_NONEG | PARSE_OPT_NOARG, diff_opt_no_prefix),\n     +\t\tOPT_INTEGER_F(0, \"inter-hunk-context\", &options->interhunkcontext,\n     +\t\t\t      N_(\"show context between diff hunks up to the specified number of lines\"),\n15:  afc89eb973 ! 15:  51cb7b3beb diff-parseopt: convert --[no-]color-moved\n    @@ -2,7 +2,7 @@\n     \n         diff-parseopt: convert --[no-]color-moved\n     \n    -    mark one more string for translation while at there\n    +    Mark one more string for translation while at there\n     \n      diff --git a/diff.c b/diff.c\n      --- a/diff.c\n16:  34a2457af1 = 16:  c1a0faa93b diff-parseopt: convert --color-moved-ws\n17:  cc882ae588 = 17:  1e99596a25 diff.c: allow --no-color-moved-ws\n18:  60ea27b58d = 18:  d7272ff0c9 range-diff: use parse_options() instead of diff_opt_parse()\n19:  96e72eb330 = 19:  09c98fb8fd diff --no-index: use parse_options() instead of diff_opt_parse()\n20:  d7273eff56 = 20:  59dbe880bc am: avoid diff_opt_parse()\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"372326","messageId":"20190324082014.2041-2-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190324082014.2041-1-pclouds@gmail.com","subject":"[PATCH v2 01/20] diff-parseopt: convert --ws-error-highlight","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-24T08:19:55Z","receivedAt":"2019-03-24T08:21:19Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Mark one more string for translation while at there.\n\nSigned-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 22 ++++++++++++----------\n 1 file changed, 12 insertions(+), 10 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex ce118bb326..7bfdf08137 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -4801,17 +4801,18 @@ static void enable_patch_output(int *fmt)\n \t*fmt |= DIFF_FORMAT_PATCH;\n }\n \n-static int parse_ws_error_highlight_opt(struct diff_options *opt, const char *arg)\n+static int diff_opt_ws_error_highlight(const struct option *option,\n+\t\t\t\t       const char *arg, int unset)\n {\n+\tstruct diff_options *opt = option->value;\n \tint val = parse_ws_error_highlight(arg);\n \n-\tif (val < 0) {\n-\t\terror(\"unknown value after ws-error-highlight=%.*s\",\n-\t\t      -1 - val, arg);\n-\t\treturn 0;\n-\t}\n+\tBUG_ON_OPT_NEG(unset);\n+\tif (val < 0)\n+\t\treturn error(_(\"unknown value after ws-error-highlight=%.*s\"),\n+\t\t\t     -1 - val, arg);\n \topt->ws_error_highlight = val;\n-\treturn 1;\n+\treturn 0;\n }\n \n static int parse_objfind_opt(struct diff_options *opt, const char *arg)\n@@ -5234,6 +5235,9 @@ static void prep_parse_options(struct diff_options *options)\n \t\t\t N_(\"show full pre- and post-image object names on the \\\"index\\\" lines\")),\n \t\tOPT_COLOR_FLAG(0, \"color\", &options->use_color,\n \t\t\t       N_(\"show colored diff\")),\n+\t\tOPT_CALLBACK_F(0, \"ws-error-highlight\", options, N_(\"<kind>\"),\n+\t\t\t       N_(\"highlight whitespace errors in the 'context', 'old' or 'new' lines in the diff\"),\n+\t\t\t       PARSE_OPT_NONEG, diff_opt_ws_error_highlight),\n \t\tOPT_CALLBACK_F(0, \"output-indicator-new\",\n \t\t\t       &options->output_indicators[OUTPUT_INDICATOR_NEW],\n \t\t\t       N_(\"<char>\"),\n@@ -5397,9 +5401,7 @@ int diff_opt_parse(struct diff_options *options,\n \t\tif (cm & COLOR_MOVED_WS_ERROR)\n \t\t\treturn -1;\n \t\toptions->color_moved_ws_handling = cm;\n-\t} else if (skip_prefix(arg, \"--ws-error-highlight=\", &arg))\n-\t\treturn parse_ws_error_highlight_opt(options, arg);\n-\telse if (!strcmp(arg, \"--ita-invisible-in-index\"))\n+\t} else if (!strcmp(arg, \"--ita-invisible-in-index\"))\n \t\toptions->ita_invisible_in_index = 1;\n \telse if (!strcmp(arg, \"--ita-visible-in-index\"))\n \t\toptions->ita_invisible_in_index = 0;\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"372327","messageId":"20190324082014.2041-3-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190324082014.2041-1-pclouds@gmail.com","subject":"[PATCH v2 02/20] diff-parseopt: convert --ita-[in]visible-in-index","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-24T08:19:56Z","receivedAt":"2019-03-24T08:21:24Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 11 +++++++----\n 1 file changed, 7 insertions(+), 4 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex 7bfdf08137..8255db6966 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -5352,6 +5352,12 @@ static void prep_parse_options(struct diff_options *options)\n \t\t\t       N_(\"specify how differences in submodules are shown\"),\n \t\t\t       PARSE_OPT_NONEG | PARSE_OPT_OPTARG,\n \t\t\t       diff_opt_submodule),\n+\t\tOPT_SET_INT_F(0, \"ita-invisible-in-index\", &options->ita_invisible_in_index,\n+\t\t\t      N_(\"hide 'git add -N' entries from the index\"),\n+\t\t\t      1, PARSE_OPT_NONEG),\n+\t\tOPT_SET_INT_F(0, \"ita-visible-in-index\", &options->ita_invisible_in_index,\n+\t\t\t      N_(\"treat 'git add -N' entries as real in the index\"),\n+\t\t\t      0, PARSE_OPT_NONEG),\n \t\t{ OPTION_CALLBACK, 0, \"output\", options, N_(\"<file>\"),\n \t\t  N_(\"Output to a specific file\"),\n \t\t  PARSE_OPT_NONEG, NULL, 0, diff_opt_output },\n@@ -5401,10 +5407,7 @@ int diff_opt_parse(struct diff_options *options,\n \t\tif (cm & COLOR_MOVED_WS_ERROR)\n \t\t\treturn -1;\n \t\toptions->color_moved_ws_handling = cm;\n-\t} else if (!strcmp(arg, \"--ita-invisible-in-index\"))\n-\t\toptions->ita_invisible_in_index = 1;\n-\telse if (!strcmp(arg, \"--ita-visible-in-index\"))\n-\t\toptions->ita_invisible_in_index = 0;\n+\t}\n \n \t/* misc options */\n \telse if (!strcmp(arg, \"-z\"))\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"372328","messageId":"20190324082014.2041-4-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190324082014.2041-1-pclouds@gmail.com","subject":"[PATCH v2 03/20] diff-parseopt: convert -z","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-24T08:19:57Z","receivedAt":"2019-03-24T08:21:29Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 5 +++--\n 1 file changed, 3 insertions(+), 2 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex 8255db6966..2b1d015553 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -5238,6 +5238,9 @@ static void prep_parse_options(struct diff_options *options)\n \t\tOPT_CALLBACK_F(0, \"ws-error-highlight\", options, N_(\"<kind>\"),\n \t\t\t       N_(\"highlight whitespace errors in the 'context', 'old' or 'new' lines in the diff\"),\n \t\t\t       PARSE_OPT_NONEG, diff_opt_ws_error_highlight),\n+\t\tOPT_SET_INT('z', NULL, &options->line_termination,\n+\t\t\t    N_(\"do not munge pathnames and use NULs as output field terminators in --raw or --numstat\"),\n+\t\t\t    0),\n \t\tOPT_CALLBACK_F(0, \"output-indicator-new\",\n \t\t\t       &options->output_indicators[OUTPUT_INDICATOR_NEW],\n \t\t\t       N_(\"<char>\"),\n@@ -5410,8 +5413,6 @@ int diff_opt_parse(struct diff_options *options,\n \t}\n \n \t/* misc options */\n-\telse if (!strcmp(arg, \"-z\"))\n-\t\toptions->line_termination = 0;\n \telse if ((argcount = short_opt('l', av, &optarg))) {\n \t\toptions->rename_limit = strtoul(optarg, NULL, 10);\n \t\treturn argcount;\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"372329","messageId":"20190324082014.2041-5-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190324082014.2041-1-pclouds@gmail.com","subject":"[PATCH v2 04/20] diff-parseopt: convert -l","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-24T08:19:58Z","receivedAt":"2019-03-24T08:21:34Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 6 ++----\n 1 file changed, 2 insertions(+), 4 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex 2b1d015553..6b19c97499 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -5283,6 +5283,8 @@ static void prep_parse_options(struct diff_options *options)\n \t\tOPT_CALLBACK_F(0, \"follow\", options, NULL,\n \t\t\t       N_(\"continue listing the history of a file beyond renames\"),\n \t\t\t       PARSE_OPT_NOARG, diff_opt_follow),\n+\t\tOPT_INTEGER('l', NULL, &options->rename_limit,\n+\t\t\t    N_(\"prevent rename/copy detection if the number of rename/copy targets exceeds given limit\")),\n \n \t\tOPT_GROUP(N_(\"Diff algorithm options\")),\n \t\tOPT_BIT(0, \"minimal\", &options->xdl_opts,\n@@ -5413,10 +5415,6 @@ int diff_opt_parse(struct diff_options *options,\n \t}\n \n \t/* misc options */\n-\telse if ((argcount = short_opt('l', av, &optarg))) {\n-\t\toptions->rename_limit = strtoul(optarg, NULL, 10);\n-\t\treturn argcount;\n-\t}\n \telse if ((argcount = short_opt('S', av, &optarg))) {\n \t\toptions->pickaxe = optarg;\n \t\toptions->pickaxe_opts |= DIFF_PICKAXE_KIND_S;\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"372330","messageId":"20190324082014.2041-6-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190324082014.2041-1-pclouds@gmail.com","subject":"[PATCH v2 05/20] diff-parseopt: convert -S|-G","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-24T08:19:59Z","receivedAt":"2019-03-24T08:21:40Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 37 ++++++++++++++++++++++++++++---------\n 1 file changed, 28 insertions(+), 9 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex 6b19c97499..8f01fbc2c1 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -5056,6 +5056,28 @@ static int diff_opt_patience(const struct option *opt,\n \treturn 0;\n }\n \n+static int diff_opt_pickaxe_regex(const struct option *opt,\n+\t\t\t\t  const char *arg, int unset)\n+{\n+\tstruct diff_options *options = opt->value;\n+\n+\tBUG_ON_OPT_NEG(unset);\n+\toptions->pickaxe = arg;\n+\toptions->pickaxe_opts |= DIFF_PICKAXE_KIND_G;\n+\treturn 0;\n+}\n+\n+static int diff_opt_pickaxe_string(const struct option *opt,\n+\t\t\t\t   const char *arg, int unset)\n+{\n+\tstruct diff_options *options = opt->value;\n+\n+\tBUG_ON_OPT_NEG(unset);\n+\toptions->pickaxe = arg;\n+\toptions->pickaxe_opts |= DIFF_PICKAXE_KIND_S;\n+\treturn 0;\n+}\n+\n static int diff_opt_relative(const struct option *opt,\n \t\t\t     const char *arg, int unset)\n {\n@@ -5363,6 +5385,12 @@ static void prep_parse_options(struct diff_options *options)\n \t\tOPT_SET_INT_F(0, \"ita-visible-in-index\", &options->ita_invisible_in_index,\n \t\t\t      N_(\"treat 'git add -N' entries as real in the index\"),\n \t\t\t      0, PARSE_OPT_NONEG),\n+\t\tOPT_CALLBACK_F('S', NULL, options, N_(\"<string>\"),\n+\t\t\t       N_(\"look for differences that change the number of occurrences of the specified string\"),\n+\t\t\t       0, diff_opt_pickaxe_string),\n+\t\tOPT_CALLBACK_F('G', NULL, options, N_(\"<regex>\"),\n+\t\t\t       N_(\"look for differences that change the number of occurrences of the specified regex\"),\n+\t\t\t       0, diff_opt_pickaxe_regex),\n \t\t{ OPTION_CALLBACK, 0, \"output\", options, N_(\"<file>\"),\n \t\t  N_(\"Output to a specific file\"),\n \t\t  PARSE_OPT_NONEG, NULL, 0, diff_opt_output },\n@@ -5415,15 +5443,6 @@ int diff_opt_parse(struct diff_options *options,\n \t}\n \n \t/* misc options */\n-\telse if ((argcount = short_opt('S', av, &optarg))) {\n-\t\toptions->pickaxe = optarg;\n-\t\toptions->pickaxe_opts |= DIFF_PICKAXE_KIND_S;\n-\t\treturn argcount;\n-\t} else if ((argcount = short_opt('G', av, &optarg))) {\n-\t\toptions->pickaxe = optarg;\n-\t\toptions->pickaxe_opts |= DIFF_PICKAXE_KIND_G;\n-\t\treturn argcount;\n-\t}\n \telse if (!strcmp(arg, \"--pickaxe-all\"))\n \t\toptions->pickaxe_opts |= DIFF_PICKAXE_ALL;\n \telse if (!strcmp(arg, \"--pickaxe-regex\"))\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"372331","messageId":"20190324082014.2041-7-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190324082014.2041-1-pclouds@gmail.com","subject":"[PATCH v2 06/20] diff-parseopt: convert --pickaxe-all|--pickaxe-regex","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-24T08:20:00Z","receivedAt":"2019-03-24T08:21:45Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 10 ++++++----\n 1 file changed, 6 insertions(+), 4 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex 8f01fbc2c1..699f8605d0 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -5391,6 +5391,12 @@ static void prep_parse_options(struct diff_options *options)\n \t\tOPT_CALLBACK_F('G', NULL, options, N_(\"<regex>\"),\n \t\t\t       N_(\"look for differences that change the number of occurrences of the specified regex\"),\n \t\t\t       0, diff_opt_pickaxe_regex),\n+\t\tOPT_BIT_F(0, \"pickaxe-all\", &options->pickaxe_opts,\n+\t\t\t  N_(\"show all changes in the changeset with -S or -G\"),\n+\t\t\t  DIFF_PICKAXE_ALL, PARSE_OPT_NONEG),\n+\t\tOPT_BIT_F(0, \"pickaxe-regex\", &options->pickaxe_opts,\n+\t\t\t  N_(\"treat <string> in -S as extended POSIX regular expression\"),\n+\t\t\t  DIFF_PICKAXE_REGEX, PARSE_OPT_NONEG),\n \t\t{ OPTION_CALLBACK, 0, \"output\", options, N_(\"<file>\"),\n \t\t  N_(\"Output to a specific file\"),\n \t\t  PARSE_OPT_NONEG, NULL, 0, diff_opt_output },\n@@ -5443,10 +5449,6 @@ int diff_opt_parse(struct diff_options *options,\n \t}\n \n \t/* misc options */\n-\telse if (!strcmp(arg, \"--pickaxe-all\"))\n-\t\toptions->pickaxe_opts |= DIFF_PICKAXE_ALL;\n-\telse if (!strcmp(arg, \"--pickaxe-regex\"))\n-\t\toptions->pickaxe_opts |= DIFF_PICKAXE_REGEX;\n \telse if ((argcount = short_opt('O', av, &optarg))) {\n \t\toptions->orderfile = prefix_filename(prefix, optarg);\n \t\treturn argcount;\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"372332","messageId":"20190324082014.2041-8-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190324082014.2041-1-pclouds@gmail.com","subject":"[PATCH v2 07/20] diff-parseopt: convert -O","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-24T08:20:01Z","receivedAt":"2019-03-24T08:21:50Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 23 +++--------------------\n 1 file changed, 3 insertions(+), 20 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex 699f8605d0..849620aea5 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -4617,22 +4617,6 @@ static int opt_arg(const char *arg, int arg_short, const char *arg_long, int *va\n \treturn 1;\n }\n \n-static inline int short_opt(char opt, const char **argv,\n-\t\t\t    const char **optarg)\n-{\n-\tconst char *arg = argv[0];\n-\tif (arg[0] != '-' || arg[1] != opt)\n-\t\treturn 0;\n-\tif (arg[2] != '\\0') {\n-\t\t*optarg = arg + 2;\n-\t\treturn 1;\n-\t}\n-\tif (!argv[1])\n-\t\tdie(\"Option '%c' requires a value\", opt);\n-\t*optarg = argv[1];\n-\treturn 2;\n-}\n-\n int parse_long_opt(const char *opt, const char **argv,\n \t\t   const char **optarg)\n {\n@@ -5397,6 +5381,8 @@ static void prep_parse_options(struct diff_options *options)\n \t\tOPT_BIT_F(0, \"pickaxe-regex\", &options->pickaxe_opts,\n \t\t\t  N_(\"treat <string> in -S as extended POSIX regular expression\"),\n \t\t\t  DIFF_PICKAXE_REGEX, PARSE_OPT_NONEG),\n+\t\tOPT_FILENAME('O', NULL, &options->orderfile,\n+\t\t\t     N_(\"control the order in which files appear in the output\")),\n \t\t{ OPTION_CALLBACK, 0, \"output\", options, N_(\"<file>\"),\n \t\t  N_(\"Output to a specific file\"),\n \t\t  PARSE_OPT_NONEG, NULL, 0, diff_opt_output },\n@@ -5449,10 +5435,7 @@ int diff_opt_parse(struct diff_options *options,\n \t}\n \n \t/* misc options */\n-\telse if ((argcount = short_opt('O', av, &optarg))) {\n-\t\toptions->orderfile = prefix_filename(prefix, optarg);\n-\t\treturn argcount;\n-\t} else if (skip_prefix(arg, \"--find-object=\", &arg))\n+\telse if (skip_prefix(arg, \"--find-object=\", &arg))\n \t\treturn parse_objfind_opt(options, arg);\n \telse if ((argcount = parse_long_opt(\"diff-filter\", av, &optarg))) {\n \t\tint offending = parse_diff_filter_opt(optarg, options);\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"372333","messageId":"20190324082014.2041-9-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190324082014.2041-1-pclouds@gmail.com","subject":"[PATCH v2 08/20] diff-parseopt: convert --find-object","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-24T08:20:02Z","receivedAt":"2019-03-24T08:21:56Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"While at it, mark one more string for translation.\n\nSigned-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 14 +++++++++-----\n 1 file changed, 9 insertions(+), 5 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex 849620aea5..99871d2546 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -4799,12 +4799,15 @@ static int diff_opt_ws_error_highlight(const struct option *option,\n \treturn 0;\n }\n \n-static int parse_objfind_opt(struct diff_options *opt, const char *arg)\n+static int diff_opt_find_object(const struct option *option,\n+\t\t\t\tconst char *arg, int unset)\n {\n+\tstruct diff_options *opt = option->value;\n \tstruct object_id oid;\n \n+\tBUG_ON_OPT_NEG(unset);\n \tif (get_oid(arg, &oid))\n-\t\treturn error(\"unable to resolve '%s'\", arg);\n+\t\treturn error(_(\"unable to resolve '%s'\"), arg);\n \n \tif (!opt->objfind)\n \t\topt->objfind = xcalloc(1, sizeof(*opt->objfind));\n@@ -4813,7 +4816,7 @@ static int parse_objfind_opt(struct diff_options *opt, const char *arg)\n \topt->flags.recursive = 1;\n \topt->flags.tree_in_recursive = 1;\n \toidset_insert(opt->objfind, &oid);\n-\treturn 1;\n+\treturn 0;\n }\n \n static int diff_opt_anchored(const struct option *opt,\n@@ -5383,6 +5386,9 @@ static void prep_parse_options(struct diff_options *options)\n \t\t\t  DIFF_PICKAXE_REGEX, PARSE_OPT_NONEG),\n \t\tOPT_FILENAME('O', NULL, &options->orderfile,\n \t\t\t     N_(\"control the order in which files appear in the output\")),\n+\t\tOPT_CALLBACK_F(0, \"find-object\", options, N_(\"<object-id>\"),\n+\t\t\t       N_(\"look for differences that change the number of occurrences of the specified object\"),\n+\t\t\t       PARSE_OPT_NONEG, diff_opt_find_object),\n \t\t{ OPTION_CALLBACK, 0, \"output\", options, N_(\"<file>\"),\n \t\t  N_(\"Output to a specific file\"),\n \t\t  PARSE_OPT_NONEG, NULL, 0, diff_opt_output },\n@@ -5435,8 +5441,6 @@ int diff_opt_parse(struct diff_options *options,\n \t}\n \n \t/* misc options */\n-\telse if (skip_prefix(arg, \"--find-object=\", &arg))\n-\t\treturn parse_objfind_opt(options, arg);\n \telse if ((argcount = parse_long_opt(\"diff-filter\", av, &optarg))) {\n \t\tint offending = parse_diff_filter_opt(optarg, options);\n \t\tif (offending)\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"372334","messageId":"20190324082014.2041-10-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190324082014.2041-1-pclouds@gmail.com","subject":"[PATCH v2 09/20] diff-parseopt: convert --diff-filter","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-24T08:20:03Z","receivedAt":"2019-03-24T08:22:01Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"While at it, mark one more string for translation\n\nSigned-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 18 +++++++++---------\n 1 file changed, 9 insertions(+), 9 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex 99871d2546..47146c33f5 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -4736,10 +4736,13 @@ static unsigned filter_bit_tst(char status, const struct diff_options *opt)\n \treturn opt->filter & filter_bit[(int) status];\n }\n \n-static int parse_diff_filter_opt(const char *optarg, struct diff_options *opt)\n+static int diff_opt_diff_filter(const struct option *option,\n+\t\t\t\tconst char *optarg, int unset)\n {\n+\tstruct diff_options *opt = option->value;\n \tint i, optch;\n \n+\tBUG_ON_OPT_NEG(unset);\n \tprepare_filter_bits();\n \n \t/*\n@@ -4770,7 +4773,8 @@ static int parse_diff_filter_opt(const char *optarg, struct diff_options *opt)\n \n \t\tbit = (0 <= optch && optch <= 'Z') ? filter_bit[optch] : 0;\n \t\tif (!bit)\n-\t\t\treturn optarg[i];\n+\t\t\treturn error(_(\"unknown change class '%c' in --diff-filter=%s\"),\n+\t\t\t\t     optarg[i], optarg);\n \t\tif (negate)\n \t\t\topt->filter &= ~bit;\n \t\telse\n@@ -5389,6 +5393,9 @@ static void prep_parse_options(struct diff_options *options)\n \t\tOPT_CALLBACK_F(0, \"find-object\", options, N_(\"<object-id>\"),\n \t\t\t       N_(\"look for differences that change the number of occurrences of the specified object\"),\n \t\t\t       PARSE_OPT_NONEG, diff_opt_find_object),\n+\t\tOPT_CALLBACK_F(0, \"diff-filter\", options, N_(\"[(A|C|D|M|R|T|U|X|B)...[*]]\"),\n+\t\t\t       N_(\"select files by diff type\"),\n+\t\t\t       PARSE_OPT_NONEG, diff_opt_diff_filter),\n \t\t{ OPTION_CALLBACK, 0, \"output\", options, N_(\"<file>\"),\n \t\t  N_(\"Output to a specific file\"),\n \t\t  PARSE_OPT_NONEG, NULL, 0, diff_opt_output },\n@@ -5441,13 +5448,6 @@ int diff_opt_parse(struct diff_options *options,\n \t}\n \n \t/* misc options */\n-\telse if ((argcount = parse_long_opt(\"diff-filter\", av, &optarg))) {\n-\t\tint offending = parse_diff_filter_opt(optarg, options);\n-\t\tif (offending)\n-\t\t\tdie(\"unknown change class '%c' in --diff-filter=%s\",\n-\t\t\t    offending, optarg);\n-\t\treturn argcount;\n-\t}\n \telse if (!strcmp(arg, \"--no-abbrev\"))\n \t\toptions->abbrev = 0;\n \telse if (!strcmp(arg, \"--abbrev\"))\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"372335","messageId":"20190324082014.2041-11-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190324082014.2041-1-pclouds@gmail.com","subject":"[PATCH v2 10/20] diff-parseopt: convert --[no-]abbrev","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-24T08:20:04Z","receivedAt":"2019-03-24T08:22:06Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"OPT__ABBREV() has the same behavior as the deleted code with one\ndifference: it does check for valid number and error out if not. And the\n'40' change is self explanatory.\n\nSigned-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c             | 12 +-----------\n parse-options-cb.c |  4 ++--\n 2 files changed, 3 insertions(+), 13 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex 47146c33f5..8d387280a4 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -5254,6 +5254,7 @@ static void prep_parse_options(struct diff_options *options)\n \t\tOPT_SET_INT('z', NULL, &options->line_termination,\n \t\t\t    N_(\"do not munge pathnames and use NULs as output field terminators in --raw or --numstat\"),\n \t\t\t    0),\n+\t\tOPT__ABBREV(&options->abbrev),\n \t\tOPT_CALLBACK_F(0, \"output-indicator-new\",\n \t\t\t       &options->output_indicators[OUTPUT_INDICATOR_NEW],\n \t\t\t       N_(\"<char>\"),\n@@ -5448,17 +5449,6 @@ int diff_opt_parse(struct diff_options *options,\n \t}\n \n \t/* misc options */\n-\telse if (!strcmp(arg, \"--no-abbrev\"))\n-\t\toptions->abbrev = 0;\n-\telse if (!strcmp(arg, \"--abbrev\"))\n-\t\toptions->abbrev = DEFAULT_ABBREV;\n-\telse if (skip_prefix(arg, \"--abbrev=\", &arg)) {\n-\t\toptions->abbrev = strtoul(arg, NULL, 10);\n-\t\tif (options->abbrev < MINIMUM_ABBREV)\n-\t\t\toptions->abbrev = MINIMUM_ABBREV;\n-\t\telse if (the_hash_algo->hexsz < options->abbrev)\n-\t\t\toptions->abbrev = the_hash_algo->hexsz;\n-\t}\n \telse if ((argcount = parse_long_opt(\"src-prefix\", av, &optarg))) {\n \t\toptions->a_prefix = optarg;\n \t\treturn argcount;\ndiff --git a/parse-options-cb.c b/parse-options-cb.c\nindex 2733393546..6e2e8d6273 100644\n--- a/parse-options-cb.c\n+++ b/parse-options-cb.c\n@@ -22,8 +22,8 @@ int parse_opt_abbrev_cb(const struct option *opt, const char *arg, int unset)\n \t\t\t\t     opt->long_name);\n \t\tif (v && v < MINIMUM_ABBREV)\n \t\t\tv = MINIMUM_ABBREV;\n-\t\telse if (v > 40)\n-\t\t\tv = 40;\n+\t\telse if (v > the_hash_algo->hexsz)\n+\t\t\tv = the_hash_algo->hexsz;\n \t}\n \t*(int *)(opt->value) = v;\n \treturn 0;\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"372336","messageId":"20190324082014.2041-12-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190324082014.2041-1-pclouds@gmail.com","subject":"[PATCH v2 11/20] diff-parseopt: convert --[src|dst]-prefix","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-24T08:20:05Z","receivedAt":"2019-03-24T08:22:11Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c          | 14 ++++++--------\n parse-options.h |  3 ++-\n 2 files changed, 8 insertions(+), 9 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex 8d387280a4..574fc511ff 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -5255,6 +5255,12 @@ static void prep_parse_options(struct diff_options *options)\n \t\t\t    N_(\"do not munge pathnames and use NULs as output field terminators in --raw or --numstat\"),\n \t\t\t    0),\n \t\tOPT__ABBREV(&options->abbrev),\n+\t\tOPT_STRING_F(0, \"src-prefix\", &options->a_prefix, N_(\"<prefix>\"),\n+\t\t\t     N_(\"show the given source prefix instead of \\\"a/\\\"\"),\n+\t\t\t     PARSE_OPT_NONEG),\n+\t\tOPT_STRING_F(0, \"dst-prefix\", &options->b_prefix, N_(\"<prefix>\"),\n+\t\t\t     N_(\"show the given source prefix instead of \\\"b/\\\"\"),\n+\t\t\t     PARSE_OPT_NONEG),\n \t\tOPT_CALLBACK_F(0, \"output-indicator-new\",\n \t\t\t       &options->output_indicators[OUTPUT_INDICATOR_NEW],\n \t\t\t       N_(\"<char>\"),\n@@ -5449,20 +5455,12 @@ int diff_opt_parse(struct diff_options *options,\n \t}\n \n \t/* misc options */\n-\telse if ((argcount = parse_long_opt(\"src-prefix\", av, &optarg))) {\n-\t\toptions->a_prefix = optarg;\n-\t\treturn argcount;\n-\t}\n \telse if ((argcount = parse_long_opt(\"line-prefix\", av, &optarg))) {\n \t\toptions->line_prefix = optarg;\n \t\toptions->line_prefix_length = strlen(options->line_prefix);\n \t\tgraph_setup_line_prefix(options);\n \t\treturn argcount;\n \t}\n-\telse if ((argcount = parse_long_opt(\"dst-prefix\", av, &optarg))) {\n-\t\toptions->b_prefix = optarg;\n-\t\treturn argcount;\n-\t}\n \telse if (!strcmp(arg, \"--no-prefix\"))\n \t\toptions->a_prefix = options->b_prefix = \"\";\n \telse if (opt_arg(arg, '\\0', \"inter-hunk-context\",\ndiff --git a/parse-options.h b/parse-options.h\nindex 7d83e2971d..c95cbe26f0 100644\n--- a/parse-options.h\n+++ b/parse-options.h\n@@ -136,6 +136,7 @@ struct option {\n #define OPT_BOOL_F(s, l, v, h, f)   OPT_SET_INT_F(s, l, v, h, 1, f)\n #define OPT_CALLBACK_F(s, l, v, a, h, f, cb)\t\t\t\\\n \t{ OPTION_CALLBACK, (s), (l), (v), (a), (h), (f), (cb) }\n+#define OPT_STRING_F(s, l, v, a, h, f)   { OPTION_STRING,  (s), (l), (v), (a), (h), (f) }\n \n #define OPT_END()                   { OPTION_END }\n #define OPT_ARGUMENT(l, h)          { OPTION_ARGUMENT, 0, (l), NULL, NULL, \\\n@@ -157,7 +158,7 @@ struct option {\n #define OPT_INTEGER(s, l, v, h)     { OPTION_INTEGER, (s), (l), (v), N_(\"n\"), (h) }\n #define OPT_MAGNITUDE(s, l, v, h)   { OPTION_MAGNITUDE, (s), (l), (v), \\\n \t\t\t\t      N_(\"n\"), (h), PARSE_OPT_NONEG }\n-#define OPT_STRING(s, l, v, a, h)   { OPTION_STRING,  (s), (l), (v), (a), (h) }\n+#define OPT_STRING(s, l, v, a, h)   OPT_STRING_F(s, l, v, a, h, 0)\n #define OPT_STRING_LIST(s, l, v, a, h) \\\n \t\t\t\t    { OPTION_CALLBACK, (s), (l), (v), (a), \\\n \t\t\t\t      (h), 0, &parse_opt_string_list }\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"372337","messageId":"20190324082014.2041-13-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190324082014.2041-1-pclouds@gmail.com","subject":"[PATCH v2 12/20] diff-parseopt: convert --line-prefix","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-24T08:20:06Z","receivedAt":"2019-03-24T08:22:16Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 23 +++++++++++++++--------\n 1 file changed, 15 insertions(+), 8 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex 574fc511ff..e1675a32ec 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -5010,6 +5010,18 @@ static int diff_opt_ignore_submodules(const struct option *opt,\n \treturn 0;\n }\n \n+static int diff_opt_line_prefix(const struct option *opt,\n+\t\t\t\tconst char *optarg, int unset)\n+{\n+\tstruct diff_options *options = opt->value;\n+\n+\tBUG_ON_OPT_NEG(unset);\n+\toptions->line_prefix = optarg;\n+\toptions->line_prefix_length = strlen(options->line_prefix);\n+\tgraph_setup_line_prefix(options);\n+\treturn 0;\n+}\n+\n static enum parse_opt_result diff_opt_output(struct parse_opt_ctx_t *ctx,\n \t\t\t\t\t     const struct option *opt,\n \t\t\t\t\t     const char *arg, int unset)\n@@ -5261,6 +5273,9 @@ static void prep_parse_options(struct diff_options *options)\n \t\tOPT_STRING_F(0, \"dst-prefix\", &options->b_prefix, N_(\"<prefix>\"),\n \t\t\t     N_(\"show the given source prefix instead of \\\"b/\\\"\"),\n \t\t\t     PARSE_OPT_NONEG),\n+\t\tOPT_CALLBACK_F(0, \"line-prefix\", options, N_(\"<prefix>\"),\n+\t\t\t       N_(\"prepend an additional prefix to every line of output\"),\n+\t\t\t       PARSE_OPT_NONEG, diff_opt_line_prefix),\n \t\tOPT_CALLBACK_F(0, \"output-indicator-new\",\n \t\t\t       &options->output_indicators[OUTPUT_INDICATOR_NEW],\n \t\t\t       N_(\"<char>\"),\n@@ -5418,8 +5433,6 @@ int diff_opt_parse(struct diff_options *options,\n \t\t   const char **av, int ac, const char *prefix)\n {\n \tconst char *arg = av[0];\n-\tconst char *optarg;\n-\tint argcount;\n \n \tif (!prefix)\n \t\tprefix = \"\";\n@@ -5455,12 +5468,6 @@ int diff_opt_parse(struct diff_options *options,\n \t}\n \n \t/* misc options */\n-\telse if ((argcount = parse_long_opt(\"line-prefix\", av, &optarg))) {\n-\t\toptions->line_prefix = optarg;\n-\t\toptions->line_prefix_length = strlen(options->line_prefix);\n-\t\tgraph_setup_line_prefix(options);\n-\t\treturn argcount;\n-\t}\n \telse if (!strcmp(arg, \"--no-prefix\"))\n \t\toptions->a_prefix = options->b_prefix = \"\";\n \telse if (opt_arg(arg, '\\0', \"inter-hunk-context\",\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"372338","messageId":"20190324082014.2041-14-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190324082014.2041-1-pclouds@gmail.com","subject":"[PATCH v2 13/20] diff-parseopt: convert --no-prefix","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-24T08:20:07Z","receivedAt":"2019-03-24T08:22:22Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 17 +++++++++++++++--\n 1 file changed, 15 insertions(+), 2 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex e1675a32ec..6029f8de2d 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -5022,6 +5022,18 @@ static int diff_opt_line_prefix(const struct option *opt,\n \treturn 0;\n }\n \n+static int diff_opt_no_prefix(const struct option *opt,\n+\t\t\t      const char *optarg, int unset)\n+{\n+\tstruct diff_options *options = opt->value;\n+\n+\tBUG_ON_OPT_NEG(unset);\n+\tBUG_ON_OPT_ARG(optarg);\n+\toptions->a_prefix = \"\";\n+\toptions->b_prefix = \"\";\n+\treturn 0;\n+}\n+\n static enum parse_opt_result diff_opt_output(struct parse_opt_ctx_t *ctx,\n \t\t\t\t\t     const struct option *opt,\n \t\t\t\t\t     const char *arg, int unset)\n@@ -5276,6 +5288,9 @@ static void prep_parse_options(struct diff_options *options)\n \t\tOPT_CALLBACK_F(0, \"line-prefix\", options, N_(\"<prefix>\"),\n \t\t\t       N_(\"prepend an additional prefix to every line of output\"),\n \t\t\t       PARSE_OPT_NONEG, diff_opt_line_prefix),\n+\t\tOPT_CALLBACK_F(0, \"no-prefix\", options, NULL,\n+\t\t\t       N_(\"do not show any source or destination prefix\"),\n+\t\t\t       PARSE_OPT_NONEG | PARSE_OPT_NOARG, diff_opt_no_prefix),\n \t\tOPT_CALLBACK_F(0, \"output-indicator-new\",\n \t\t\t       &options->output_indicators[OUTPUT_INDICATOR_NEW],\n \t\t\t       N_(\"<char>\"),\n@@ -5468,8 +5483,6 @@ int diff_opt_parse(struct diff_options *options,\n \t}\n \n \t/* misc options */\n-\telse if (!strcmp(arg, \"--no-prefix\"))\n-\t\toptions->a_prefix = options->b_prefix = \"\";\n \telse if (opt_arg(arg, '\\0', \"inter-hunk-context\",\n \t\t\t &options->interhunkcontext))\n \t\t;\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"372339","messageId":"20190324082014.2041-15-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190324082014.2041-1-pclouds@gmail.com","subject":"[PATCH v2 14/20] diff-parseopt: convert --inter-hunk-context","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-24T08:20:08Z","receivedAt":"2019-03-24T08:22:27Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c          | 50 +++----------------------------------------------\n parse-options.h |  3 ++-\n 2 files changed, 5 insertions(+), 48 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex 6029f8de2d..8b65b03c0d 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -4573,50 +4573,6 @@ void diff_setup_done(struct diff_options *options)\n \tFREE_AND_NULL(options->parseopts);\n }\n \n-static int opt_arg(const char *arg, int arg_short, const char *arg_long, int *val)\n-{\n-\tchar c, *eq;\n-\tint len;\n-\n-\tif (*arg != '-')\n-\t\treturn 0;\n-\tc = *++arg;\n-\tif (!c)\n-\t\treturn 0;\n-\tif (c == arg_short) {\n-\t\tc = *++arg;\n-\t\tif (!c)\n-\t\t\treturn 1;\n-\t\tif (val && isdigit(c)) {\n-\t\t\tchar *end;\n-\t\t\tint n = strtoul(arg, &end, 10);\n-\t\t\tif (*end)\n-\t\t\t\treturn 0;\n-\t\t\t*val = n;\n-\t\t\treturn 1;\n-\t\t}\n-\t\treturn 0;\n-\t}\n-\tif (c != '-')\n-\t\treturn 0;\n-\targ++;\n-\teq = strchrnul(arg, '=');\n-\tlen = eq - arg;\n-\tif (!len || strncmp(arg, arg_long, len))\n-\t\treturn 0;\n-\tif (*eq) {\n-\t\tint n;\n-\t\tchar *end;\n-\t\tif (!isdigit(*++eq))\n-\t\t\treturn 0;\n-\t\tn = strtoul(eq, &end, 10);\n-\t\tif (*end)\n-\t\t\treturn 0;\n-\t\t*val = n;\n-\t}\n-\treturn 1;\n-}\n-\n int parse_long_opt(const char *opt, const char **argv,\n \t\t   const char **optarg)\n {\n@@ -5291,6 +5247,9 @@ static void prep_parse_options(struct diff_options *options)\n \t\tOPT_CALLBACK_F(0, \"no-prefix\", options, NULL,\n \t\t\t       N_(\"do not show any source or destination prefix\"),\n \t\t\t       PARSE_OPT_NONEG | PARSE_OPT_NOARG, diff_opt_no_prefix),\n+\t\tOPT_INTEGER_F(0, \"inter-hunk-context\", &options->interhunkcontext,\n+\t\t\t      N_(\"show context between diff hunks up to the specified number of lines\"),\n+\t\t\t      PARSE_OPT_NONEG),\n \t\tOPT_CALLBACK_F(0, \"output-indicator-new\",\n \t\t\t       &options->output_indicators[OUTPUT_INDICATOR_NEW],\n \t\t\t       N_(\"<char>\"),\n@@ -5483,9 +5442,6 @@ int diff_opt_parse(struct diff_options *options,\n \t}\n \n \t/* misc options */\n-\telse if (opt_arg(arg, '\\0', \"inter-hunk-context\",\n-\t\t\t &options->interhunkcontext))\n-\t\t;\n \telse\n \t\treturn 0;\n \treturn 1;\ndiff --git a/parse-options.h b/parse-options.h\nindex c95cbe26f0..cca64d04cb 100644\n--- a/parse-options.h\n+++ b/parse-options.h\n@@ -137,6 +137,7 @@ struct option {\n #define OPT_CALLBACK_F(s, l, v, a, h, f, cb)\t\t\t\\\n \t{ OPTION_CALLBACK, (s), (l), (v), (a), (h), (f), (cb) }\n #define OPT_STRING_F(s, l, v, a, h, f)   { OPTION_STRING,  (s), (l), (v), (a), (h), (f) }\n+#define OPT_INTEGER_F(s, l, v, h, f)     { OPTION_INTEGER, (s), (l), (v), N_(\"n\"), (h), (f) }\n \n #define OPT_END()                   { OPTION_END }\n #define OPT_ARGUMENT(l, h)          { OPTION_ARGUMENT, 0, (l), NULL, NULL, \\\n@@ -155,7 +156,7 @@ struct option {\n \t\t\t\t      (h), PARSE_OPT_NOARG | PARSE_OPT_HIDDEN, NULL, 1}\n #define OPT_CMDMODE(s, l, v, h, i)  { OPTION_CMDMODE, (s), (l), (v), NULL, \\\n \t\t\t\t      (h), PARSE_OPT_NOARG|PARSE_OPT_NONEG, NULL, (i) }\n-#define OPT_INTEGER(s, l, v, h)     { OPTION_INTEGER, (s), (l), (v), N_(\"n\"), (h) }\n+#define OPT_INTEGER(s, l, v, h)     OPT_INTEGER_F(s, l, v, h, 0)\n #define OPT_MAGNITUDE(s, l, v, h)   { OPTION_MAGNITUDE, (s), (l), (v), \\\n \t\t\t\t      N_(\"n\"), (h), PARSE_OPT_NONEG }\n #define OPT_STRING(s, l, v, a, h)   OPT_STRING_F(s, l, v, a, h, 0)\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"372340","messageId":"20190324082014.2041-16-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190324082014.2041-1-pclouds@gmail.com","subject":"[PATCH v2 15/20] diff-parseopt: convert --[no-]color-moved","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-24T08:20:09Z","receivedAt":"2019-03-24T08:22:32Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Mark one more string for translation while at there\n\nSigned-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 38 +++++++++++++++++++++++++-------------\n 1 file changed, 25 insertions(+), 13 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex 8b65b03c0d..de6c09e95a 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -4841,6 +4841,27 @@ static int diff_opt_char(const struct option *opt,\n \treturn 0;\n }\n \n+static int diff_opt_color_moved(const struct option *opt,\n+\t\t\t\tconst char *arg, int unset)\n+{\n+\tstruct diff_options *options = opt->value;\n+\n+\tif (unset) {\n+\t\toptions->color_moved = COLOR_MOVED_NO;\n+\t} else if (!arg) {\n+\t\tif (diff_color_moved_default)\n+\t\t\toptions->color_moved = diff_color_moved_default;\n+\t\tif (options->color_moved == COLOR_MOVED_NO)\n+\t\t\toptions->color_moved = COLOR_MOVED_DEFAULT;\n+\t} else {\n+\t\tint cm = parse_color_moved(arg);\n+\t\tif (cm < 0)\n+\t\t\treturn error(_(\"bad --color-moved argument: %s\"), arg);\n+\t\toptions->color_moved = cm;\n+\t}\n+\treturn 0;\n+}\n+\n static int diff_opt_color_words(const struct option *opt,\n \t\t\t\tconst char *arg, int unset)\n {\n@@ -5339,6 +5360,9 @@ static void prep_parse_options(struct diff_options *options)\n \t\tOPT_CALLBACK_F(0, \"color-words\", options, N_(\"<regex>\"),\n \t\t\t       N_(\"equivalent to --word-diff=color --word-diff-regex=<regex>\"),\n \t\t\t       PARSE_OPT_NONEG | PARSE_OPT_OPTARG, diff_opt_color_words),\n+\t\tOPT_CALLBACK_F(0, \"color-moved\", options, N_(\"<mode>\"),\n+\t\t\t       N_(\"move lines of code are colored differently\"),\n+\t\t\t       PARSE_OPT_OPTARG, diff_opt_color_moved),\n \n \t\tOPT_GROUP(N_(\"Diff other options\")),\n \t\tOPT_CALLBACK_F(0, \"relative\", options, N_(\"<prefix>\"),\n@@ -5422,19 +5446,7 @@ int diff_opt_parse(struct diff_options *options,\n \t\treturn ac;\n \n \t/* flags options */\n-\tif (!strcmp(arg, \"--color-moved\")) {\n-\t\tif (diff_color_moved_default)\n-\t\t\toptions->color_moved = diff_color_moved_default;\n-\t\tif (options->color_moved == COLOR_MOVED_NO)\n-\t\t\toptions->color_moved = COLOR_MOVED_DEFAULT;\n-\t} else if (!strcmp(arg, \"--no-color-moved\"))\n-\t\toptions->color_moved = COLOR_MOVED_NO;\n-\telse if (skip_prefix(arg, \"--color-moved=\", &arg)) {\n-\t\tint cm = parse_color_moved(arg);\n-\t\tif (cm < 0)\n-\t\t\treturn error(\"bad --color-moved argument: %s\", arg);\n-\t\toptions->color_moved = cm;\n-\t} else if (skip_prefix(arg, \"--color-moved-ws=\", &arg)) {\n+\tif (skip_prefix(arg, \"--color-moved-ws=\", &arg)) {\n \t\tunsigned cm = parse_color_moved_ws(arg);\n \t\tif (cm & COLOR_MOVED_WS_ERROR)\n \t\t\treturn -1;\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"372341","messageId":"20190324082014.2041-17-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190324082014.2041-1-pclouds@gmail.com","subject":"[PATCH v2 16/20] diff-parseopt: convert --color-moved-ws","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-24T08:20:10Z","receivedAt":"2019-03-24T08:22:37Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 35 ++++++++++++++++++-----------------\n 1 file changed, 18 insertions(+), 17 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex de6c09e95a..1a24bbfb69 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -4862,6 +4862,20 @@ static int diff_opt_color_moved(const struct option *opt,\n \treturn 0;\n }\n \n+static int diff_opt_color_moved_ws(const struct option *opt,\n+\t\t\t\t   const char *arg, int unset)\n+{\n+\tstruct diff_options *options = opt->value;\n+\tunsigned cm;\n+\n+\tBUG_ON_OPT_NEG(unset);\n+\tcm = parse_color_moved_ws(arg);\n+\tif (cm & COLOR_MOVED_WS_ERROR)\n+\t\treturn error(_(\"invalid mode '%s' in --color-moved-ws\"), arg);\n+\toptions->color_moved_ws_handling = cm;\n+\treturn 0;\n+}\n+\n static int diff_opt_color_words(const struct option *opt,\n \t\t\t\tconst char *arg, int unset)\n {\n@@ -5363,6 +5377,9 @@ static void prep_parse_options(struct diff_options *options)\n \t\tOPT_CALLBACK_F(0, \"color-moved\", options, N_(\"<mode>\"),\n \t\t\t       N_(\"move lines of code are colored differently\"),\n \t\t\t       PARSE_OPT_OPTARG, diff_opt_color_moved),\n+\t\tOPT_CALLBACK_F(0, \"color-moved-ws\", options, N_(\"<mode>\"),\n+\t\t\t       N_(\"how white spaces are ignored in --color-moved\"),\n+\t\t\t       PARSE_OPT_NONEG, diff_opt_color_moved_ws),\n \n \t\tOPT_GROUP(N_(\"Diff other options\")),\n \t\tOPT_CALLBACK_F(0, \"relative\", options, N_(\"<prefix>\"),\n@@ -5430,8 +5447,6 @@ static void prep_parse_options(struct diff_options *options)\n int diff_opt_parse(struct diff_options *options,\n \t\t   const char **av, int ac, const char *prefix)\n {\n-\tconst char *arg = av[0];\n-\n \tif (!prefix)\n \t\tprefix = \"\";\n \n@@ -5442,21 +5457,7 @@ int diff_opt_parse(struct diff_options *options,\n \t\t\t   PARSE_OPT_ONE_SHOT |\n \t\t\t   PARSE_OPT_STOP_AT_NON_OPTION);\n \n-\tif (ac)\n-\t\treturn ac;\n-\n-\t/* flags options */\n-\tif (skip_prefix(arg, \"--color-moved-ws=\", &arg)) {\n-\t\tunsigned cm = parse_color_moved_ws(arg);\n-\t\tif (cm & COLOR_MOVED_WS_ERROR)\n-\t\t\treturn -1;\n-\t\toptions->color_moved_ws_handling = cm;\n-\t}\n-\n-\t/* misc options */\n-\telse\n-\t\treturn 0;\n-\treturn 1;\n+\treturn ac;\n }\n \n int parse_rename_score(const char **cp_p)\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"372342","messageId":"20190324082014.2041-18-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190324082014.2041-1-pclouds@gmail.com","subject":"[PATCH v2 17/20] diff.c: allow --no-color-moved-ws","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-24T08:20:11Z","receivedAt":"2019-03-24T08:22:42Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"This option is added in commit b73bcbac4a (diff: allow\n--no-color-moved-ws - 2018-11-23) in pw/diff-color-moved-ws-fix. To ease\nmerge conflict resolution, re-implement the option handling here so that\nthe conflict could be resolved by taking this side of change.\n\nSigned-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n diff.c | 8 ++++++--\n 1 file changed, 6 insertions(+), 2 deletions(-)\n\ndiff --git a/diff.c b/diff.c\nindex 1a24bbfb69..8b770cd396 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -4868,7 +4868,11 @@ static int diff_opt_color_moved_ws(const struct option *opt,\n \tstruct diff_options *options = opt->value;\n \tunsigned cm;\n \n-\tBUG_ON_OPT_NEG(unset);\n+\tif (unset) {\n+\t\toptions->color_moved_ws_handling = 0;\n+\t\treturn 0;\n+\t}\n+\n \tcm = parse_color_moved_ws(arg);\n \tif (cm & COLOR_MOVED_WS_ERROR)\n \t\treturn error(_(\"invalid mode '%s' in --color-moved-ws\"), arg);\n@@ -5379,7 +5383,7 @@ static void prep_parse_options(struct diff_options *options)\n \t\t\t       PARSE_OPT_OPTARG, diff_opt_color_moved),\n \t\tOPT_CALLBACK_F(0, \"color-moved-ws\", options, N_(\"<mode>\"),\n \t\t\t       N_(\"how white spaces are ignored in --color-moved\"),\n-\t\t\t       PARSE_OPT_NONEG, diff_opt_color_moved_ws),\n+\t\t\t       0, diff_opt_color_moved_ws),\n \n \t\tOPT_GROUP(N_(\"Diff other options\")),\n \t\tOPT_CALLBACK_F(0, \"relative\", options, N_(\"<prefix>\"),\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"372343","messageId":"20190324082014.2041-19-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190324082014.2041-1-pclouds@gmail.com","subject":"[PATCH v2 18/20] range-diff: use parse_options() instead of diff_opt_parse()","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-24T08:20:12Z","receivedAt":"2019-03-24T08:22:47Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Diff's internal option parsing is now done with 'struct option', which\nmakes it possible to combine all diff options to range-diff and parse\neverything all at once. Parsing code becomes simpler, and we get a\nlooong 'git range-diff -h'\n\nSigned-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n builtin/range-diff.c | 26 ++++++--------------------\n 1 file changed, 6 insertions(+), 20 deletions(-)\n\ndiff --git a/builtin/range-diff.c b/builtin/range-diff.c\nindex f01a0be851..784bd19321 100644\n--- a/builtin/range-diff.c\n+++ b/builtin/range-diff.c\n@@ -16,42 +16,27 @@ int cmd_range_diff(int argc, const char **argv, const char *prefix)\n \tint creation_factor = RANGE_DIFF_CREATION_FACTOR_DEFAULT;\n \tstruct diff_options diffopt = { NULL };\n \tint simple_color = -1;\n-\tstruct option options[] = {\n+\tstruct option range_diff_options[] = {\n \t\tOPT_INTEGER(0, \"creation-factor\", &creation_factor,\n \t\t\t    N_(\"Percentage by which creation is weighted\")),\n \t\tOPT_BOOL(0, \"no-dual-color\", &simple_color,\n \t\t\t    N_(\"use simple diff colors\")),\n \t\tOPT_END()\n \t};\n-\tint i, j, res = 0;\n+\tstruct option *options;\n+\tint res = 0;\n \tstruct strbuf range1 = STRBUF_INIT, range2 = STRBUF_INIT;\n \n \tgit_config(git_diff_ui_config, NULL);\n \n \trepo_diff_setup(the_repository, &diffopt);\n \n+\toptions = parse_options_concat(range_diff_options, diffopt.parseopts);\n \targc = parse_options(argc, argv, NULL, options,\n-\t\t\t     builtin_range_diff_usage, PARSE_OPT_KEEP_UNKNOWN |\n-\t\t\t     PARSE_OPT_KEEP_DASHDASH | PARSE_OPT_KEEP_ARGV0);\n-\n-\tfor (i = j = 1; i < argc && strcmp(\"--\", argv[i]); ) {\n-\t\tint c = diff_opt_parse(&diffopt, argv + i, argc - i, prefix);\n+\t\t\t     builtin_range_diff_usage, 0);\n \n-\t\tif (!c)\n-\t\t\targv[j++] = argv[i++];\n-\t\telse\n-\t\t\ti += c;\n-\t}\n-\twhile (i < argc)\n-\t\targv[j++] = argv[i++];\n-\targc = j;\n \tdiff_setup_done(&diffopt);\n \n-\t/* Make sure that there are no unparsed options */\n-\targc = parse_options(argc, argv, NULL,\n-\t\t\t     options + ARRAY_SIZE(options) - 1, /* OPT_END */\n-\t\t\t     builtin_range_diff_usage, 0);\n-\n \t/* force color when --dual-color was used */\n \tif (!simple_color)\n \t\tdiffopt.use_color = 1;\n@@ -90,6 +75,7 @@ int cmd_range_diff(int argc, const char **argv, const char *prefix)\n \t\terror(_(\"need two commit ranges\"));\n \t\tusage_with_options(builtin_range_diff_usage, options);\n \t}\n+\tFREE_AND_NULL(options);\n \n \tres = show_range_diff(range1.buf, range2.buf, creation_factor,\n \t\t\t      simple_color < 1, &diffopt);\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"372344","messageId":"20190324082014.2041-20-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190324082014.2041-1-pclouds@gmail.com","subject":"[PATCH v2 19/20] diff --no-index: use parse_options() instead of diff_opt_parse()","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-24T08:20:13Z","receivedAt":"2019-03-24T08:22:52Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"While at there, move exit() back to the caller. It's easier to see the\nflow that way than burying it in diff-no-index.c\n\nSigned-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n builtin/diff.c           | 21 +++--------------\n diff-no-index.c          | 49 ++++++++++++++++++++++++----------------\n diff.h                   |  3 ++-\n t/t4053-diff-no-index.sh |  3 +--\n 4 files changed, 35 insertions(+), 41 deletions(-)\n\ndiff --git a/builtin/diff.c b/builtin/diff.c\nindex f0393bba23..52dc3e136f 100644\n--- a/builtin/diff.c\n+++ b/builtin/diff.c\n@@ -320,26 +320,11 @@ int cmd_diff(int argc, const char **argv, const char *prefix)\n \n \trepo_init_revisions(the_repository, &rev, prefix);\n \n-\tif (no_index && argc != i + 2) {\n-\t\tif (no_index == DIFF_NO_INDEX_IMPLICIT) {\n-\t\t\t/*\n-\t\t\t * There was no --no-index and there were not two\n-\t\t\t * paths. It is possible that the user intended\n-\t\t\t * to do an inside-repository operation.\n-\t\t\t */\n-\t\t\tfprintf(stderr, \"Not a git repository\\n\");\n-\t\t\tfprintf(stderr,\n-\t\t\t\t\"To compare two paths outside a working tree:\\n\");\n-\t\t}\n-\t\t/* Give the usage message for non-repository usage and exit. */\n-\t\tusagef(\"git diff %s <path> <path>\",\n-\t\t       no_index == DIFF_NO_INDEX_EXPLICIT ?\n-\t\t       \"--no-index\" : \"[--no-index]\");\n-\n-\t}\n \tif (no_index)\n \t\t/* If this is a no-index diff, just run it and exit there. */\n-\t\tdiff_no_index(the_repository, &rev, argc, argv);\n+\t\texit(diff_no_index(the_repository, &rev,\n+\t\t\t\t   no_index == DIFF_NO_INDEX_IMPLICIT,\n+\t\t\t\t   argc, argv));\n \n \t/* Otherwise, we are doing the usual \"git\" diff */\n \trev.diffopt.skip_stat_unmatch = !!diff_auto_refresh_index;\ndiff --git a/diff-no-index.c b/diff-no-index.c\nindex 9414e922d1..a879f45862 100644\n--- a/diff-no-index.c\n+++ b/diff-no-index.c\n@@ -14,6 +14,7 @@\n #include \"revision.h\"\n #include \"log-tree.h\"\n #include \"builtin.h\"\n+#include \"parse-options.h\"\n #include \"string-list.h\"\n #include \"dir.h\"\n \n@@ -233,35 +234,43 @@ static void fixup_paths(const char **path, struct strbuf *replacement)\n \t}\n }\n \n-void diff_no_index(struct repository *r,\n-\t\t   struct rev_info *revs,\n-\t\t   int argc, const char **argv)\n+static const char * const diff_no_index_usage[] = {\n+\tN_(\"git diff --no-index [<options>] <path> <path>\"),\n+\tNULL\n+};\n+\n+int diff_no_index(struct repository *r,\n+\t\t  struct rev_info *revs,\n+\t\t  int implicit_no_index,\n+\t\t  int argc, const char **argv)\n {\n-\tint i;\n+\tint i, no_index;\n \tconst char *paths[2];\n \tstruct strbuf replacement = STRBUF_INIT;\n \tconst char *prefix = revs->prefix;\n+\tstruct option no_index_options[] = {\n+\t\tOPT_BOOL_F(0, \"no-index\", &no_index, \"\",\n+\t\t\t   PARSE_OPT_NONEG | PARSE_OPT_HIDDEN),\n+\t\tOPT_END(),\n+\t};\n+\tstruct option *options;\n \n \t/*\n \t * FIXME: --no-index should not look at index and we should be\n \t * able to pass NULL repo. Maybe later.\n \t */\n \trepo_diff_setup(r, &revs->diffopt);\n-\tfor (i = 1; i < argc - 2; ) {\n-\t\tint j;\n-\t\tif (!strcmp(argv[i], \"--no-index\"))\n-\t\t\ti++;\n-\t\telse if (!strcmp(argv[i], \"--\"))\n-\t\t\ti++;\n-\t\telse {\n-\t\t\tj = diff_opt_parse(&revs->diffopt, argv + i, argc - i,\n-\t\t\t\t\t   revs->prefix);\n-\t\t\tif (j <= 0)\n-\t\t\t\tdie(\"invalid diff option/value: %s\", argv[i]);\n-\t\t\ti += j;\n-\t\t}\n+\toptions = parse_options_concat(no_index_options,\n+\t\t\t\t       revs->diffopt.parseopts);\n+\targc = parse_options(argc, argv, revs->prefix, options,\n+\t\t\t     diff_no_index_usage, 0);\n+\tif (argc != 2) {\n+\t\tif (implicit_no_index)\n+\t\t\twarning(_(\"Not a git repository. Use --no-index to \"\n+\t\t\t\t  \"compare two paths outside a working tree\"));\n+\t\tusage_with_options(diff_no_index_usage, options);\n \t}\n-\n+\tFREE_AND_NULL(options);\n \tfor (i = 0; i < 2; i++) {\n \t\tconst char *p = argv[argc - 2 + i];\n \t\tif (!strcmp(p, \"-\"))\n@@ -293,7 +302,7 @@ void diff_no_index(struct repository *r,\n \trevs->diffopt.flags.exit_with_status = 1;\n \n \tif (queue_diff(&revs->diffopt, paths[0], paths[1]))\n-\t\texit(1);\n+\t\treturn 1;\n \tdiff_set_mnemonic_prefix(&revs->diffopt, \"1/\", \"2/\");\n \tdiffcore_std(&revs->diffopt);\n \tdiff_flush(&revs->diffopt);\n@@ -304,5 +313,5 @@ void diff_no_index(struct repository *r,\n \t * The return code for --no-index imitates diff(1):\n \t * 0 = no changes, 1 = changes, else error\n \t */\n-\texit(diff_result_code(&revs->diffopt, 0));\n+\treturn diff_result_code(&revs->diffopt, 0);\n }\ndiff --git a/diff.h b/diff.h\nindex d9ad73f0e1..03c6afda22 100644\n--- a/diff.h\n+++ b/diff.h\n@@ -437,7 +437,8 @@ int diff_flush_patch_id(struct diff_options *, struct object_id *, int);\n \n int diff_result_code(struct diff_options *, int);\n \n-void diff_no_index(struct repository *, struct rev_info *, int, const char **);\n+int diff_no_index(struct repository *, struct rev_info *,\n+\t\t  int implicit_no_index, int, const char **);\n \n int index_differs_from(struct repository *r, const char *def,\n \t\t       const struct diff_flags *flags,\ndiff --git a/t/t4053-diff-no-index.sh b/t/t4053-diff-no-index.sh\nindex 6e0dd6f9e5..fb25cdb789 100755\n--- a/t/t4053-diff-no-index.sh\n+++ b/t/t4053-diff-no-index.sh\n@@ -50,8 +50,7 @@ test_expect_success 'git diff --no-index executed outside repo gives correct err\n \t\texport GIT_CEILING_DIRECTORIES &&\n \t\tcd non/git &&\n \t\ttest_must_fail git diff --no-index a 2>actual.err &&\n-\t\techo \"usage: git diff --no-index <path> <path>\" >expect.err &&\n-\t\ttest_cmp expect.err actual.err\n+\t\ttest_i18ngrep \"usage: git diff --no-index\" actual.err\n \t)\n '\n \n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"372345","messageId":"20190324082014.2041-21-pclouds@gmail.com","threadId":"50790","inReplyTo":"20190324082014.2041-1-pclouds@gmail.com","subject":"[PATCH v2 20/20] am: avoid diff_opt_parse()","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2019-03-24T08:20:14Z","receivedAt":"2019-03-24T08:22:57Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"diff_opt_parse() is a heavy hammer to just set diff filter. But it's\nthe only way because of the diff_status_letters[] mapping. Add a new\nAPI to set diff filter and use it in git-am. diff_opt_parse()'s only\nremaining call site in revision.c will be gone soon and having it here\njust because of git-am does not make sense.\n\nSigned-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n builtin/am.c | 4 ++--\n diff.c       | 6 ++++++\n diff.h       | 2 ++\n 3 files changed, 10 insertions(+), 2 deletions(-)\n\ndiff --git a/builtin/am.c b/builtin/am.c\nindex 95370313b6..0cbf285459 100644\n--- a/builtin/am.c\n+++ b/builtin/am.c\n@@ -1515,11 +1515,11 @@ static int fall_back_threeway(const struct am_state *state, const char *index_pa\n \t\t * review them with extra care to spot mismerges.\n \t\t */\n \t\tstruct rev_info rev_info;\n-\t\tconst char *diff_filter_str = \"--diff-filter=AM\";\n \n \t\trepo_init_revisions(the_repository, &rev_info, NULL);\n \t\trev_info.diffopt.output_format = DIFF_FORMAT_NAME_STATUS;\n-\t\tdiff_opt_parse(&rev_info.diffopt, &diff_filter_str, 1, rev_info.prefix);\n+\t\trev_info.diffopt.filter |= diff_filter_bit('A');\n+\t\trev_info.diffopt.filter |= diff_filter_bit('M');\n \t\tadd_pending_oid(&rev_info, \"HEAD\", &our_tree, 0);\n \t\tdiff_setup_done(&rev_info.diffopt);\n \t\trun_diff_index(&rev_info, 1);\ndiff --git a/diff.c b/diff.c\nindex 8b770cd396..11f26285c3 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -4692,6 +4692,12 @@ static unsigned filter_bit_tst(char status, const struct diff_options *opt)\n \treturn opt->filter & filter_bit[(int) status];\n }\n \n+unsigned diff_filter_bit(char status)\n+{\n+\tprepare_filter_bits();\n+\treturn filter_bit[(int) status];\n+}\n+\n static int diff_opt_diff_filter(const struct option *option,\n \t\t\t\tconst char *optarg, int unset)\n {\ndiff --git a/diff.h b/diff.h\nindex 03c6afda22..f88482705c 100644\n--- a/diff.h\n+++ b/diff.h\n@@ -233,6 +233,8 @@ struct diff_options {\n \tstruct option *parseopts;\n };\n \n+unsigned diff_filter_bit(char status);\n+\n void diff_emit_submodule_del(struct diff_options *o, const char *line);\n void diff_emit_submodule_add(struct diff_options *o, const char *line);\n void diff_emit_submodule_untracked(struct diff_options *o, const char *path);\n-- \n2.21.0.548.gd3c7d92dc2\n\n"},{"id":"374689","messageId":"nycvar.QRO.7.76.6.1904292055300.45@tvgsbejvaqbjf.bet","threadId":"50790","inReplyTo":"20190324082014.2041-20-pclouds@gmail.com","subject":"Re: [PATCH v2 19/20] diff --no-index: use parse_options() instead of diff_opt_parse()","fromName":"Johannes Schindelin","fromEmail":"johannes.schindelin@gmx.de","sentAt":"2019-04-30T01:02:28Z","receivedAt":"2019-04-30T01:02:35Z","isPatch":true,"sender":{"key":"johannes.schindelin@gmx.de","avatar":"https://avatars.githubusercontent.com/u/127790?v=4"},"body":"Hi Duy,\n\nOn Sun, 24 Mar 2019, Nguyễn Thái Ngọc Duy wrote:\n\n> While at there, move exit() back to the caller. It's easier to see the\n> flow that way than burying it in diff-no-index.c\n\nI just noticed that this commit message is missing more than just a\ntrailing period. It does not explain the change of behavior: previously,\n`GIT_EXTERNAL_DIFF=heya git diff --no-index a b` would silently ignore the\nexternal diff, it would have required an explicit `--ext-diff` to pick it\nup.\n\nAfter this change, it is necessary to pass `--no-ext-diff` to reinstate\nthe original behavior.\n\nWhile this might seem like a desirable change, it is a\nbackwards-incompatible change and would do with a *lot* more of a message\nto users whose scripts now potentially break.\n\nCiao,\nJohannes\n"},{"id":"374692","messageId":"CACsJy8CUNVWqWff05Lg2xjnOj3L2T7RvVbZh+RZPjvFokvT_-A@mail.gmail.com","threadId":"50790","inReplyTo":"nycvar.QRO.7.76.6.1904292055300.45@tvgsbejvaqbjf.bet","subject":"Re: [PATCH v2 19/20] diff --no-index: use parse_options() instead of diff_opt_parse()","fromName":"Duy Nguyen","fromEmail":"pclouds@gmail.com","sentAt":"2019-04-30T04:53:21Z","receivedAt":"2019-04-30T04:53:50Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"On Tue, Apr 30, 2019 at 8:02 AM Johannes Schindelin\n<Johannes.Schindelin@gmx.de> wrote:\n>\n> Hi Duy,\n>\n> On Sun, 24 Mar 2019, Nguyễn Thái Ngọc Duy wrote:\n>\n> > While at there, move exit() back to the caller. It's easier to see the\n> > flow that way than burying it in diff-no-index.c\n>\n> I just noticed that this commit message is missing more than just a\n> trailing period. It does not explain the change of behavior: previously,\n> `GIT_EXTERNAL_DIFF=heya git diff --no-index a b` would silently ignore the\n> external diff, it would have required an explicit `--ext-diff` to pick it\n> up.\n\nBecause I was not aware of the behavior change.\n-- \nDuy\n"},{"id":"374722","messageId":"nycvar.QRO.7.76.6.1904301811110.45@tvgsbejvaqbjf.bet","threadId":"50790","inReplyTo":"CACsJy8CUNVWqWff05Lg2xjnOj3L2T7RvVbZh+RZPjvFokvT_-A@mail.gmail.com","subject":"Re: [PATCH v2 19/20] diff --no-index: use parse_options() instead of diff_opt_parse()","fromName":"Johannes Schindelin","fromEmail":"johannes.schindelin@gmx.de","sentAt":"2019-04-30T22:12:32Z","receivedAt":"2019-04-30T22:12:42Z","isPatch":true,"sender":{"key":"johannes.schindelin@gmx.de","avatar":"https://avatars.githubusercontent.com/u/127790?v=4"},"body":"Hi Duy,\n\nOn Tue, 30 Apr 2019, Duy Nguyen wrote:\n\n> On Tue, Apr 30, 2019 at 8:02 AM Johannes Schindelin\n> <Johannes.Schindelin@gmx.de> wrote:\n> >\n> > Hi Duy,\n> >\n> > On Sun, 24 Mar 2019, Nguyễn Thái Ngọc Duy wrote:\n> >\n> > > While at there, move exit() back to the caller. It's easier to see the\n> > > flow that way than burying it in diff-no-index.c\n> >\n> > I just noticed that this commit message is missing more than just a\n> > trailing period. It does not explain the change of behavior: previously,\n> > `GIT_EXTERNAL_DIFF=heya git diff --no-index a b` would silently ignore the\n> > external diff, it would have required an explicit `--ext-diff` to pick it\n> > up.\n>\n> Because I was not aware of the behavior change.\n\nWell, your patch removes an early return in favor of a later return that\nallows plenty of diff options to be configured in a different way than\nbefore.\n\nSo while it is obvious (and understandable) that you were not aware of\nthis behavior change, the real question is what we should do about this,\nnow that this patch is already in `master` and on its way into v2.22.0.\n\nCiao,\nJohannes\n"},{"id":"374741","messageId":"CACsJy8AGf81=_BTd6+idnBcHPB2AAj=dciJn6r_rCB8TJ1hvug@mail.gmail.com","threadId":"50790","inReplyTo":"nycvar.QRO.7.76.6.1904301811110.45@tvgsbejvaqbjf.bet","subject":"Re: [PATCH v2 19/20] diff --no-index: use parse_options() instead of diff_opt_parse()","fromName":"Duy Nguyen","fromEmail":"pclouds@gmail.com","sentAt":"2019-05-01T09:53:44Z","receivedAt":"2019-05-01T09:54:12Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"On Wed, May 1, 2019 at 5:12 AM Johannes Schindelin\n<Johannes.Schindelin@gmx.de> wrote:>\n> Hi Duy,\n>\n> On Tue, 30 Apr 2019, Duy Nguyen wrote:\n>\n> > On Tue, Apr 30, 2019 at 8:02 AM Johannes Schindelin\n> > <Johannes.Schindelin@gmx.de> wrote:\n> > >\n> > > Hi Duy,\n> > >\n> > > On Sun, 24 Mar 2019, Nguyễn Thái Ngọc Duy wrote:\n> > >\n> > > > While at there, move exit() back to the caller. It's easier to see the\n> > > > flow that way than burying it in diff-no-index.c\n> > >\n> > > I just noticed that this commit message is missing more than just a\n> > > trailing period. It does not explain the change of behavior: previously,\n> > > `GIT_EXTERNAL_DIFF=heya git diff --no-index a b` would silently ignore the\n> > > external diff, it would have required an explicit `--ext-diff` to pick it\n> > > up.\n> >\n> > Because I was not aware of the behavior change.\n>\n> Well, your patch removes an early return in favor of a later return that\n> allows plenty of diff options to be configured in a different way than\n> before.\n\nNo (and I was terse because I did not have time to look more into it).\nThe code flow is the same, the number of option parsing is the same.\nEven post option processing is the same.\n\nBisecting points to 287ab28bfa (diff: reuse diff setup for --no-index\ncase, 2019-02-16). From the description (i.e. \"miss out some settings\nlike --ext-diff...\") the behavior change seems delibrate. Adding Jeff\nfor clarification/\n\n> So while it is obvious\n\nI probably have problem understanding. The \"commit message is missing\"\nseems to imply I knew about this but chose not to mention it.\n\n> (and understandable) that you were not aware of\n> this behavior change, the real question is what we should do about this,\n> now that this patch is already in `master` and on its way into v2.22.0.\n>\n> Ciao,\n> Johannes\n\n\n\n-- \nDuy\n"},{"id":"374779","messageId":"20190501184658.GH4109@sigill.intra.peff.net","threadId":"50790","inReplyTo":"CACsJy8AGf81=_BTd6+idnBcHPB2AAj=dciJn6r_rCB8TJ1hvug@mail.gmail.com","subject":"Re: [PATCH v2 19/20] diff --no-index: use parse_options() instead of diff_opt_parse()","fromName":"Jeff King","fromEmail":"peff@peff.net","sentAt":"2019-05-01T18:46:58Z","receivedAt":"2019-05-01T18:47:01Z","isPatch":true,"sender":{"key":"peff@peff.net","avatar":"https://avatars.githubusercontent.com/u/45925?v=4"},"body":"On Wed, May 01, 2019 at 04:53:44PM +0700, Duy Nguyen wrote:\n\n> > > > I just noticed that this commit message is missing more than just a\n> > > > trailing period. It does not explain the change of behavior: previously,\n> > > > `GIT_EXTERNAL_DIFF=heya git diff --no-index a b` would silently ignore the\n> > > > external diff, it would have required an explicit `--ext-diff` to pick it\n> > > > up.\n> [...]\n> Bisecting points to 287ab28bfa (diff: reuse diff setup for --no-index\n> case, 2019-02-16). From the description (i.e. \"miss out some settings\n> like --ext-diff...\") the behavior change seems delibrate. Adding Jeff\n> for clarification/\n\nYeah, that was the purpose of that change: whether in no-index mode or\nnot, git-diff should behave consistently.\n\n-Peff\n"}]}