Skip to content

Commit c6e7393

Browse files
committed
Merge branch 'sb/show-branch-parse-options'
* sb/show-branch-parse-options: show-branch: migrate to parse-options API parse-options: add PARSE_OPT_LITERAL_ARGHELP for complicated argh's Conflicts: parse-options.h
2 parents 919cc4d + 5734365 commit c6e7393

File tree

3 files changed

+84
-71
lines changed

3 files changed

+84
-71
lines changed

builtin-show-branch.c

Lines changed: 63 additions & 62 deletions
Original file line numberDiff line numberDiff line change
@@ -3,11 +3,13 @@
33
#include "refs.h"
44
#include "builtin.h"
55
#include "color.h"
6+
#include "parse-options.h"
67

7-
static const char show_branch_usage[] =
8-
"git show-branch [--sparse] [--current] [--all] [--remotes] [--topo-order] [--more=count | --list | --independent | --merge-base ] [--topics] [<refs>...] | --reflog[=n[,b]] <branch>";
9-
static const char show_branch_usage_reflog[] =
10-
"--reflog is incompatible with --all, --remotes, --independent or --merge-base";
8+
static const char* show_branch_usage[] = {
9+
"git show-branch [--sparse] [--current] [--all] [--remotes] [--topo-order] [--more=count | --list | --independent | --merge-base] [--topics] [--color] [<refs>...]",
10+
"--reflog[=n[,b]] [--list] [--color] <branch>",
11+
NULL
12+
};
1113

1214
static int showbranch_use_color = -1;
1315
static char column_colors[][COLOR_MAXLEN] = {
@@ -601,18 +603,25 @@ static int omit_in_dense(struct commit *commit, struct commit **rev, int n)
601603
return 0;
602604
}
603605

604-
static void parse_reflog_param(const char *arg, int *cnt, const char **base)
606+
static int reflog = 0;
607+
608+
static int parse_reflog_param(const struct option *opt, const char *arg,
609+
int unset)
605610
{
606611
char *ep;
607-
*cnt = strtoul(arg, &ep, 10);
612+
const char **base = (const char **)opt->value;
613+
if (!arg)
614+
arg = "";
615+
reflog = strtoul(arg, &ep, 10);
608616
if (*ep == ',')
609617
*base = ep + 1;
610618
else if (*ep)
611-
die("unrecognized reflog param '%s'", arg);
619+
return error("unrecognized reflog param '%s'", arg);
612620
else
613621
*base = NULL;
614-
if (*cnt <= 0)
615-
*cnt = DEFAULT_REFLOG;
622+
if (reflog <= 0)
623+
reflog = DEFAULT_REFLOG;
624+
return 0;
616625
}
617626

618627
int cmd_show_branch(int ac, const char **av, const char *prefix)
@@ -638,8 +647,44 @@ int cmd_show_branch(int ac, const char **av, const char *prefix)
638647
int head_at = -1;
639648
int topics = 0;
640649
int dense = 1;
641-
int reflog = 0;
642650
const char *reflog_base = NULL;
651+
struct option builtin_show_branch_options[] = {
652+
OPT_BOOLEAN('a', "all", &all_heads,
653+
"show remote-tracking and local branches"),
654+
OPT_BOOLEAN('r', "remotes", &all_remotes,
655+
"show remote-tracking branches"),
656+
OPT_BOOLEAN(0, "color", &showbranch_use_color,
657+
"color '*!+-' corresponding to the branch"),
658+
{ OPTION_INTEGER, 0, "more", &extra, "n",
659+
"show <n> more commits after the common ancestor",
660+
PARSE_OPT_OPTARG | PARSE_OPT_LASTARG_DEFAULT,
661+
NULL, (intptr_t)1 },
662+
OPT_SET_INT(0, "list", &extra, "synonym to more=-1", -1),
663+
OPT_BOOLEAN(0, "no-name", &no_name, "suppress naming strings"),
664+
OPT_BOOLEAN(0, "current", &with_current_branch,
665+
"include the current branch"),
666+
OPT_BOOLEAN(0, "sha1-name", &sha1_name,
667+
"name commits with their object names"),
668+
OPT_BOOLEAN(0, "merge-base", &merge_base,
669+
"act like git merge-base -a"),
670+
OPT_BOOLEAN(0, "independent", &independent,
671+
"show refs unreachable from any other ref"),
672+
OPT_BOOLEAN(0, "topo-order", &lifo,
673+
"show commits in topological order"),
674+
OPT_BOOLEAN(0, "topics", &topics,
675+
"show only commits not on the first branch"),
676+
OPT_SET_INT(0, "sparse", &dense,
677+
"show merges reachable from only one tip", 0),
678+
OPT_SET_INT(0, "date-order", &lifo,
679+
"show commits where no parent comes before its "
680+
"children", 0),
681+
{ OPTION_CALLBACK, 'g', "reflog", &reflog_base, "<n>[,<base>]",
682+
"show <n> most recent ref-log entries starting at "
683+
"base",
684+
PARSE_OPT_OPTARG | PARSE_OPT_LITERAL_ARGHELP,
685+
parse_reflog_param },
686+
OPT_END()
687+
};
643688

644689
git_config(git_show_branch_config, NULL);
645690

@@ -652,71 +697,27 @@ int cmd_show_branch(int ac, const char **av, const char *prefix)
652697
av = default_arg - 1; /* ick; we would not address av[0] */
653698
}
654699

655-
while (1 < ac && av[1][0] == '-') {
656-
const char *arg = av[1];
657-
if (!strcmp(arg, "--")) {
658-
ac--; av++;
659-
break;
660-
}
661-
else if (!strcmp(arg, "--all") || !strcmp(arg, "-a"))
662-
all_heads = all_remotes = 1;
663-
else if (!strcmp(arg, "--remotes") || !strcmp(arg, "-r"))
664-
all_remotes = 1;
665-
else if (!strcmp(arg, "--more"))
666-
extra = 1;
667-
else if (!strcmp(arg, "--list"))
668-
extra = -1;
669-
else if (!strcmp(arg, "--no-name"))
670-
no_name = 1;
671-
else if (!strcmp(arg, "--current"))
672-
with_current_branch = 1;
673-
else if (!strcmp(arg, "--sha1-name"))
674-
sha1_name = 1;
675-
else if (!prefixcmp(arg, "--more="))
676-
extra = atoi(arg + 7);
677-
else if (!strcmp(arg, "--merge-base"))
678-
merge_base = 1;
679-
else if (!strcmp(arg, "--independent"))
680-
independent = 1;
681-
else if (!strcmp(arg, "--topo-order"))
682-
lifo = 1;
683-
else if (!strcmp(arg, "--topics"))
684-
topics = 1;
685-
else if (!strcmp(arg, "--sparse"))
686-
dense = 0;
687-
else if (!strcmp(arg, "--date-order"))
688-
lifo = 0;
689-
else if (!strcmp(arg, "--reflog") || !strcmp(arg, "-g")) {
690-
reflog = DEFAULT_REFLOG;
691-
}
692-
else if (!prefixcmp(arg, "--reflog="))
693-
parse_reflog_param(arg + 9, &reflog, &reflog_base);
694-
else if (!prefixcmp(arg, "-g="))
695-
parse_reflog_param(arg + 3, &reflog, &reflog_base);
696-
else if (!strcmp(arg, "--color"))
697-
showbranch_use_color = 1;
698-
else if (!strcmp(arg, "--no-color"))
699-
showbranch_use_color = 0;
700-
else
701-
usage(show_branch_usage);
702-
ac--; av++;
703-
}
704-
ac--; av++;
700+
ac = parse_options(ac, av, builtin_show_branch_options,
701+
show_branch_usage, PARSE_OPT_STOP_AT_NON_OPTION);
702+
if (all_heads)
703+
all_remotes = 1;
705704

706705
if (extra || reflog) {
707706
/* "listing" mode is incompatible with
708707
* independent nor merge-base modes.
709708
*/
710709
if (independent || merge_base)
711-
usage(show_branch_usage);
710+
usage_with_options(show_branch_usage,
711+
builtin_show_branch_options);
712712
if (reflog && ((0 < extra) || all_heads || all_remotes))
713713
/*
714714
* Asking for --more in reflog mode does not
715715
* make sense. --list is Ok.
716716
*
717717
* Also --all and --remotes do not make sense either.
718718
*/
719-
usage(show_branch_usage_reflog);
719+
die("--reflog is incompatible with --all, --remotes, "
720+
"--independent or --merge-base");
720721
}
721722

722723
/* If nothing is specified, show all branches by default */

parse-options.c

Lines changed: 17 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -412,6 +412,20 @@ int parse_options(int argc, const char **argv, const struct option *options,
412412
return parse_options_end(&ctx);
413413
}
414414

415+
static int usage_argh(const struct option *opts)
416+
{
417+
const char *s;
418+
int literal = opts->flags & PARSE_OPT_LITERAL_ARGHELP;
419+
if (opts->flags & PARSE_OPT_OPTARG)
420+
if (opts->long_name)
421+
s = literal ? "[=%s]" : "[=<%s>]";
422+
else
423+
s = literal ? "[%s]" : "[<%s>]";
424+
else
425+
s = literal ? " %s" : " <%s>";
426+
return fprintf(stderr, s, opts->argh);
427+
}
428+
415429
#define USAGE_OPTS_WIDTH 24
416430
#define USAGE_GAP 2
417431

@@ -478,15 +492,9 @@ int usage_with_options_internal(const char * const *usagestr,
478492
break;
479493
/* FALLTHROUGH */
480494
case OPTION_STRING:
481-
if (opts->argh) {
482-
if (opts->flags & PARSE_OPT_OPTARG)
483-
if (opts->long_name)
484-
pos += fprintf(stderr, "[=<%s>]", opts->argh);
485-
else
486-
pos += fprintf(stderr, "[<%s>]", opts->argh);
487-
else
488-
pos += fprintf(stderr, " <%s>", opts->argh);
489-
} else {
495+
if (opts->argh)
496+
pos += usage_argh(opts);
497+
else {
490498
if (opts->flags & PARSE_OPT_OPTARG)
491499
if (opts->long_name)
492500
pos += fprintf(stderr, "[=...]");

parse-options.h

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,7 @@ enum parse_opt_option_flags {
3434
PARSE_OPT_HIDDEN = 8,
3535
PARSE_OPT_LASTARG_DEFAULT = 16,
3636
PARSE_OPT_NODASH = 32,
37+
PARSE_OPT_LITERAL_ARGHELP = 64,
3738
};
3839

3940
struct option;
@@ -72,6 +73,9 @@ typedef int parse_opt_cb(const struct option *, const char *arg, int unset);
7273
* PARSE_OPT_LASTARG_DEFAULT: if no argument is given, the default value
7374
* is used.
7475
* PARSE_OPT_NODASH: this option doesn't start with a dash.
76+
* PARSE_OPT_LITERAL_ARGHELP: says that argh shouldn't be enclosed in brackets
77+
* (i.e. '<argh>') in the help message.
78+
* Useful for options with multiple parameters.
7579
*
7680
* `callback`::
7781
* pointer to the callback to use for OPTION_CALLBACK.

0 commit comments

Comments
 (0)