// SPDX-License-Identifier: GPL-2.0
#include <linux/compiler.h>
#include <linux/string.h>
#include <linux/types.h>
#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
#include <string.h>
#include <ctype.h>
#include "subcmd-util.h"
#include "parse-options.h"
#include "subcmd-config.h"
#include "pager.h"

#define OPT_SHORT 1
#define OPT_UNSET 2

char *error_buf;

static int opterror(const struct option *opt, const char *reason, int flags)
{
	if (flags & OPT_SHORT)
		fprintf(stderr, " Error: switch `%c' %s", opt->short_name, reason);
	else if (flags & OPT_UNSET)
		fprintf(stderr, " Error: option `no-%s' %s", opt->long_name, reason);
	else
		fprintf(stderr, " Error: option `%s' %s", opt->long_name, reason);

	return -1;
}

static const char *skip_prefix(const char *str, const char *prefix)
{
	size_t len = strlen(prefix);
	return strncmp(str, prefix, len) ? NULL : str + len;
}

static void optwarning(const struct option *opt, const char *reason, int flags)
{
	if (flags & OPT_SHORT)
		fprintf(stderr, " Warning: switch `%c' %s", opt->short_name, reason);
	else if (flags & OPT_UNSET)
		fprintf(stderr, " Warning: option `no-%s' %s", opt->long_name, reason);
	else
		fprintf(stderr, " Warning: option `%s' %s", opt->long_name, reason);
}

static int get_arg(struct parse_opt_ctx_t *p, const struct option *opt,
		   int flags, const char **arg)
{
	const char *res;

	if (p->opt) {
		res = p->opt;
		p->opt = NULL;
	} else if ((opt->flags & PARSE_OPT_LASTARG_DEFAULT) && (p->argc == 1 ||
		    **(p->argv + 1) == '-')) {
		res = (const char *)opt->defval;
	} else if (p->argc > 1) {
		p->argc--;
		res = *++p->argv;
	} else
		return opterror(opt, "requires a value", flags);
	if (arg)
		*arg = res;
	return 0;
}

static int get_value(struct parse_opt_ctx_t *p,
		     const struct option *opt, int flags)
{
	const char *s, *arg = NULL;
	const int unset = flags & OPT_UNSET;
	int err;

	if (unset && p->opt)
		return opterror(opt, "takes no value", flags);
	if (unset && (opt->flags & PARSE_OPT_NONEG))
		return opterror(opt, "isn't available", flags);
	if (opt->flags & PARSE_OPT_DISABLED)
		return opterror(opt, "is not usable", flags);

	if (opt->flags & PARSE_OPT_EXCLUSIVE) {
		if (p->excl_opt && p->excl_opt != opt) {
			char msg[128];

			if (((flags & OPT_SHORT) && p->excl_opt->short_name) ||
			    p->excl_opt->long_name == NULL) {
				snprintf(msg, sizeof(msg), "cannot be used with switch `%c'",
					 p->excl_opt->short_name);
			} else {
				snprintf(msg, sizeof(msg), "cannot be used with %s",
					 p->excl_opt->long_name);
			}
			opterror(opt, msg, flags);
			return -3;
		}
		p->excl_opt = opt;
	}
	if (!(flags & OPT_SHORT) && p->opt) {
		switch (opt->type) {
		case OPTION_CALLBACK:
			if (!(opt->flags & PARSE_OPT_NOARG))
				break;
			/* FALLTHROUGH */
		case OPTION_BOOLEAN:
		case OPTION_INCR:
		case OPTION_BIT:
		case OPTION_SET_UINT:
		case OPTION_SET_PTR:
			return opterror(opt, "takes no value", flags);
		case OPTION_END:
		case OPTION_ARGUMENT:
		case OPTION_GROUP:
		case OPTION_STRING:
		case OPTION_INTEGER:
		case OPTION_UINTEGER:
		case OPTION_LONG:
		case OPTION_U64:
		default:
			break;
		}
	}

	if (opt->flags & PARSE_OPT_NOBUILD) {
		char reason[128];
		bool noarg = false;

		err = snprintf(reason, sizeof(reason),
				opt->flags & PARSE_OPT_CANSKIP ?
					"is being ignored because %s " :
					"is not available because %s",
				opt->build_opt);
		reason[sizeof(reason) - 1] = '\0';

		if (err < 0)
			strncpy(reason, opt->flags & PARSE_OPT_CANSKIP ?
					"is being ignored" :
					"is not available",
					sizeof(reason));

		if (!(opt->flags & PARSE_OPT_CANSKIP))
			return opterror(opt, reason, flags);

		err = 0;
		if (unset)
			noarg = true;
		if (opt->flags & PARSE_OPT_NOARG)
			noarg = true;
		if (opt->flags & PARSE_OPT_OPTARG && !p->opt)
			noarg = true;

		switch (opt->type) {
		case OPTION_BOOLEAN:
		case OPTION_INCR:
		case OPTION_BIT:
		case OPTION_SET_UINT:
		case OPTION_SET_PTR:
		case OPTION_END:
		case OPTION_ARGUMENT:
		case OPTION_GROUP:
			noarg = true;
			break;
		case OPTION_CALLBACK:
		case OPTION_STRING:
		case OPTION_INTEGER:
		case OPTION_UINTEGER:
		case OPTION_LONG:
		case OPTION_U64:
		default:
			break;
		}

		if (!noarg)
			err = get_arg(p, opt, flags, NULL);
		if (err)
			return err;

		optwarning(opt, reason, flags);
		return 0;
	}

	switch (opt->type) {
	case OPTION_BIT:
		if (unset)
			*(int *)opt->value &= ~opt->defval;
		else
			*(int *)opt->value |= opt->defval;
		return 0;

	case OPTION_BOOLEAN:
		*(bool *)opt->value = unset ? false : true;
		if (opt->set)
			*(bool *)opt->set = true;
		return 0;

	case OPTION_INCR:
		*(int *)opt->value = unset ? 0 : *(int *)opt->value + 1;
		return 0;

	case OPTION_SET_UINT:
		*(unsigned int *)opt->value = unset ? 0 : opt->defval;
		return 0;

	case OPTION_SET_PTR:
		*(void **)opt->value = unset ? NULL : (void *)opt->defval;
		return 0;

	case OPTION_STRING:
		err = 0;
		if (unset)
			*(const char **)opt->value = NULL;
		else if (opt->flags & PARSE_OPT_OPTARG && !p->opt)
			*(const char **)opt->value = (const char *)opt->defval;
		else
			err = get_arg(p, opt, flags, (const char **)opt->value);

		if (opt->set)
			*(bool *)opt->set = true;

		/* PARSE_OPT_NOEMPTY: Allow NULL but disallow empty string. */
		if (opt->flags & PARSE_OPT_NOEMPTY) {
			const char *val = *(const char **)opt->value;

			if (!val)
				return err;

			/* Similar to unset if we are given an empty string. */
			if (val[0] == '\0') {
				*(const char **)opt->value = NULL;
				return 0;
			}
		}

		return err;

	case OPTION_CALLBACK:
		if (unset)
			return (*opt->callback)(opt, NULL, 1) ? (-1) : 0;
		if (opt->flags & PARSE_OPT_NOARG)
			return (*opt->callback)(opt, NULL, 0) ? (-1) : 0;
		if (opt->flags & PARSE_OPT_OPTARG && !p->opt)
			return (*opt->callback)(opt, NULL, 0) ? (-1) : 0;
		if (get_arg(p, opt, flags, &arg))
			return -1;
		return (*opt->callback)(opt, arg, 0) ? (-1) : 0;

	case OPTION_INTEGER:
		if (unset) {
			*(int *)opt->value = 0;
			return 0;
		}
		if (opt->flags & PARSE_OPT_OPTARG && !p->opt) {
			*(int *)opt->value = opt->defval;
			return 0;
		}
		if (get_arg(p, opt, flags, &arg))
			return -1;
		*(int *)opt->value = strtol(arg, (char **)&s, 10);
		if (*s)
			return opterror(opt, "expects a numerical value", flags);
		return 0;

	case OPTION_UINTEGER:
		if (unset) {
			*(unsigned int *)opt->value = 0;
			return 0;
		}
		if (opt->flags & PARSE_OPT_OPTARG && !p->opt) {
			*(unsigned int *)opt->value = opt->defval;
			return 0;
		}
		if (get_arg(p, opt, flags, &arg))
			return -1;
		if (arg[0] == '-')
			return opterror(opt, "expects an unsigned numerical value", flags);
		*(unsigned int *)opt->value = strtol(arg, (char **)&s, 10);
		if (*s)
			return opterror(opt, "expects a numerical value", flags);
		return 0;

	case OPTION_LONG:
		if (unset) {
			*(long *)opt->value = 0;
			return 0;
		}
		if (opt->flags & PARSE_OPT_OPTARG && !p->opt) {
			*(long *)opt->value = opt->defval;
			return 0;
		}
		if (get_arg(p, opt, flags, &arg))
			return -1;
		*(long *)opt->value = strtol(arg, (char **)&s, 10);
		if (*s)
			return opterror(opt, "expects a numerical value", flags);
		return 0;

	case OPTION_U64:
		if (unset) {
			*(u64 *)opt->value = 0;
			return 0;
		}
		if (opt->flags & PARSE_OPT_OPTARG && !p->opt) {
			*(u64 *)opt->value = opt->defval;
			return 0;
		}
		if (get_arg(p, opt, flags, &arg))
			return -1;
		if (arg[0] == '-')
			return opterror(opt, "expects an unsigned numerical value", flags);
		*(u64 *)opt->value = strtoull(arg, (char **)&s, 10);
		if (*s)
			return opterror(opt, "expects a numerical value", flags);
		return 0;

	case OPTION_END:
	case OPTION_ARGUMENT:
	case OPTION_GROUP:
	default:
		die("should not happen, someone must be hit on the forehead");
	}
}

static int parse_short_opt(struct parse_opt_ctx_t *p, const struct option *options)
{
retry:
	for (; options->type != OPTION_END; options++) {
		if (options->short_name == *p->opt) {
			p->opt = p->opt[1] ? p->opt + 1 : NULL;
			return get_value(p, options, OPT_SHORT);
		}
	}

	if (options->parent) {
		options = options->parent;
		goto retry;
	}

	return -2;
}

static int parse_long_opt(struct parse_opt_ctx_t *p, const char *arg,
                          const struct option *options)
{
	const char *arg_end = strchr(arg, '=');
	const struct option *abbrev_option = NULL, *ambiguous_option = NULL;
	int abbrev_flags = 0, ambiguous_flags = 0;

	if (!arg_end)
		arg_end = arg + strlen(arg);

retry:
	for (; options->type != OPTION_END; options++) {
		const char *rest;
		int flags = 0;

		if (!options->long_name)
			continue;

		rest = skip_prefix(arg, options->long_name);
		if (options->type == OPTION_ARGUMENT) {
			if (!rest)
				continue;
			if (*rest == '=')
				return opterror(options, "takes no value", flags);
			if (*rest)
				continue;
			p->out[p->cpidx++] = arg - 2;
			return 0;
		}
		if (!rest) {
			if (strstarts(options->long_name, "no-")) {
				/*
				 * The long name itself starts with "no-", so
				 * accept the option without "no-" so that users
				 * do not have to enter "no-no-" to get the
				 * negation.
				 */
				rest = skip_prefix(arg, options->long_name + 3);
				if (rest) {
					flags |= OPT_UNSET;
					goto match;
				}
				/* Abbreviated case */
				if (strstarts(options->long_name + 3, arg)) {
					flags |= OPT_UNSET;
					goto is_abbreviated;
				}
			}
			/* abbreviated? */
			if (!strncmp(options->long_name, arg, arg_end - arg)) {
is_abbreviated:
				if (abbrev_option) {
					/*
					 * If this is abbreviated, it is
					 * ambiguous. So when there is no
					 * exact match later, we need to
					 * error out.
					 */
					ambiguous_option = abbrev_option;
					ambiguous_flags = abbrev_flags;
				}
				if (!(flags & OPT_UNSET) && *arg_end)
					p->opt = arg_end + 1;
				abbrev_option = options;
				abbrev_flags = flags;
				continue;
			}
			/* negated and abbreviated very much? */
			if (strstarts("no-", arg)) {
				flags |= OPT_UNSET;
				goto is_abbreviated;
			}
			/* negated? */
			if (strncmp(arg, "no-", 3))
				continue;
			flags |= OPT_UNSET;
			rest = skip_prefix(arg + 3, options->long_name);
			/* abbreviated and negated? */
			if (!rest && strstarts(options->long_name, arg + 3))
				goto is_abbreviated;
			if (!rest)
				continue;
		}
match:
		if (*rest) {
			if (*rest != '=')
				continue;
			p->opt = rest + 1;
		}
		return get_value(p, options, flags);
	}

	if (ambiguous_option) {
		 fprintf(stderr,
			 " Error: Ambiguous option: %s (could be --%s%s or --%s%s)",
			 arg,
			 (ambiguous_flags & OPT_UNSET) ?  "no-" : "",
			 ambiguous_option->long_name,
			 (abbrev_flags & OPT_UNSET) ?  "no-" : "",
			 abbrev_option->long_name);
		 return -1;
	}
	if (abbrev_option)
		return get_value(p, abbrev_option, abbrev_flags);

	if (options->parent) {
		options = options->parent;
		goto retry;
	}

	return -2;
}

static void check_typos(const char *arg, const struct option *options)
{
	if (strlen(arg) < 3)
		return;

	if (strstarts(arg, "no-")) {
		fprintf(stderr, " Error: did you mean `--%s` (with two dashes ?)", arg);
		exit(129);
	}

	for (; options->type != OPTION_END; options++) {
		if (!options->long_name)
			continue;
		if (strstarts(options->long_name, arg)) {
			fprintf(stderr, " Error: did you mean `--%s` (with two dashes ?)", arg);
			exit(129);
		}
	}
}

static void parse_options_start(struct parse_opt_ctx_t *ctx,
				int argc, const char **argv, int flags)
{
	memset(ctx, 0, sizeof(*ctx));
	ctx->argc = argc - 1;
	ctx->argv = argv + 1;
	ctx->out  = argv;
	ctx->cpidx = ((flags & PARSE_OPT_KEEP_ARGV0) != 0);
	ctx->flags = flags;
	if ((flags & PARSE_OPT_KEEP_UNKNOWN) &&
	    (flags & PARSE_OPT_STOP_AT_NON_OPTION))
		die("STOP_AT_NON_OPTION and KEEP_UNKNOWN don't go together");
}

static int usage_with_options_internal(const char * const *,
				       const struct option *, int,
				       struct parse_opt_ctx_t *);

static int parse_options_step(struct parse_opt_ctx_t *ctx,
			      const struct option *options,
			      const char * const usagestr[])
{
	int internal_help = !(ctx->flags & PARSE_OPT_NO_INTERNAL_HELP);
	int excl_short_opt = 1;
	const char *arg;

	/* we must reset ->opt, unknown short option leave it dangling */
	ctx->opt = NULL;

	for (; ctx->argc; ctx->argc--, ctx->argv++) {
		arg = ctx->argv[0];
		if (*arg != '-' || !arg[1]) {
			if (ctx->flags & PARSE_OPT_STOP_AT_NON_OPTION)
				break;
			ctx->out[ctx->cpidx++] = ctx->argv[0];
			continue;
		}

		if (arg[1] != '-') {
			ctx->opt = ++arg;
			if (internal_help && *ctx->opt == 'h') {
				return usage_with_options_internal(usagestr, options, 0, ctx);
			}
			switch (parse_short_opt(ctx, options)) {
			case -1:
				return parse_options_usage(usagestr, options, arg, 1);
			case -2:
				goto unknown;
			case -3:
				goto exclusive;
			default:
				break;
			}
			if (ctx->opt)
				check_typos(arg, options);
			while (ctx->opt) {
				if (internal_help && *ctx->opt == 'h')
					return usage_with_options_internal(usagestr, options, 0, ctx);
				arg = ctx->opt;
				switch (parse_short_opt(ctx, options)) {
				case -1:
					return parse_options_usage(usagestr, options, arg, 1);
				case -2:
					/* fake a short option thing to hide the fact that we may have
					 * started to parse aggregated stuff
					 *
					 * This is leaky, too bad.
					 */
					ctx->argv[0] = strdup(ctx->opt - 1);
					*(char *)ctx->argv[0] = '-';
					goto unknown;
				case -3:
					goto exclusive;
				default:
					break;
				}
			}
			continue;
		}

		if (!arg[2]) { /* "--" */
			if (!(ctx->flags & PARSE_OPT_KEEP_DASHDASH)) {
				ctx->argc--;
				ctx->argv++;
			}
			break;
		}

		arg += 2;
		if (internal_help && !strcmp(arg, "help-all"))
			return usage_with_options_internal(usagestr, options, 1, ctx);
		if (internal_help && !strcmp(arg, "help"))
			return usage_with_options_internal(usagestr, options, 0, ctx);
		if (!strcmp(arg, "list-opts"))
			return PARSE_OPT_LIST_OPTS;
		if (!strcmp(arg, "list-cmds"))
			return PARSE_OPT_LIST_SUBCMDS;
		switch (parse_long_opt(ctx, arg, options)) {
		case -1:
			return parse_options_usage(usagestr, options, arg, 0);
		case -2:
			goto unknown;
		case -3:
			excl_short_opt = 0;
			goto exclusive;
		default:
			break;
		}
		continue;
unknown:
		if (!(ctx->flags & PARSE_OPT_KEEP_UNKNOWN))
			return PARSE_OPT_UNKNOWN;
		ctx->out[ctx->cpidx++] = ctx->argv[0];
		ctx->opt = NULL;
	}
	return PARSE_OPT_DONE;

exclusive:
	parse_options_usage(usagestr, options, arg, excl_short_opt);
	if ((excl_short_opt && ctx->excl_opt->short_name) ||
	    ctx->excl_opt->long_name == NULL) {
		char opt = ctx->excl_opt->short_name;
		parse_options_usage(NULL, options, &opt, 1);
	} else {
		parse_options_usage(NULL, options, ctx->excl_opt->long_name, 0);
	}
	return PARSE_OPT_HELP;
}

static int parse_options_end(struct parse_opt_ctx_t *ctx)
{
	memmove(ctx->out + ctx->cpidx, ctx->argv, ctx->argc * sizeof(*ctx->out));
	ctx->out[ctx->cpidx + ctx->argc] = NULL;
	return ctx->cpidx + ctx->argc;
}

int parse_options_subcommand(int argc, const char **argv, const struct option *options,
			const char *const subcommands[], const char *usagestr[], int flags)
{
	struct parse_opt_ctx_t ctx;
	char *buf = NULL;

	/* build usage string if it's not provided */
	if (subcommands && !usagestr[0]) {
		astrcatf(&buf, "%s %s [<options>] {", subcmd_config.exec_name, argv[0]);

		for (int i = 0; subcommands[i]; i++) {
			if (i)
				astrcat(&buf, "|");
			astrcat(&buf, subcommands[i]);
		}
		astrcat(&buf, "}");

		usagestr[0] = buf;
	}

	parse_options_start(&ctx, argc, argv, flags);
	switch (parse_options_step(&ctx, options, usagestr)) {
	case PARSE_OPT_HELP:
		exit(129);
	case PARSE_OPT_DONE:
		break;
	case PARSE_OPT_LIST_OPTS:
		while (options->type != OPTION_END) {
			if (options->long_name)
				printf("--%s ", options->long_name);
			options++;
		}
		putchar('\n');
		exit(130);
	case PARSE_OPT_LIST_SUBCMDS:
		if (subcommands) {
			for (int i = 0; subcommands[i]; i++)
				printf("%s ", subcommands[i]);
		}
		putchar('\n');
		exit(130);
	default: /* PARSE_OPT_UNKNOWN */
		if (ctx.argv[0][1] == '-')
			astrcatf(&error_buf, "unknown option `%s'",
				 ctx.argv[0] + 2);
		else
			astrcatf(&error_buf, "unknown switch `%c'", *ctx.opt);
		usage_with_options(usagestr, options);
	}
	if (buf) {
		usagestr[0] = NULL;
		free(buf);
	}
	return parse_options_end(&ctx);
}

int parse_options(int argc, const char **argv, const struct option *options,
		  const char * const usagestr[], int flags)
{
	return parse_options_subcommand(argc, argv, options, NULL,
					(const char **) usagestr, flags);
}

#define USAGE_OPTS_WIDTH 24
#define USAGE_GAP         2

static void print_option_help(const struct option *opts, int full)
{
	size_t pos;
	int pad;

	if (opts->type == OPTION_GROUP) {
		fputc('\n', stderr);
		if (*opts->help)
			fprintf(stderr, "%s\n", opts->help);
		return;
	}
	if (!full && (opts->flags & PARSE_OPT_HIDDEN))
		return;
	if (opts->flags & PARSE_OPT_DISABLED)
		return;

	pos = fprintf(stderr, "    ");
	if (opts->short_name)
		pos += fprintf(stderr, "-%c", opts->short_name);
	else
		pos += fprintf(stderr, "    ");

	if (opts->long_name && opts->short_name)
		pos += fprintf(stderr, ", ");
	if (opts->long_name)
		pos += fprintf(stderr, "--%s", opts->long_name);

	switch (opts->type) {
	case OPTION_ARGUMENT:
		break;
	case OPTION_LONG:
	case OPTION_U64:
	case OPTION_INTEGER:
	case OPTION_UINTEGER:
		if (opts->flags & PARSE_OPT_OPTARG)
			if (opts->long_name)
				pos += fprintf(stderr, "[=<n>]");
			else
				pos += fprintf(stderr, "[<n>]");
		else
			pos += fprintf(stderr, " <n>");
		break;
	case OPTION_CALLBACK:
		if (opts->flags & PARSE_OPT_NOARG)
			break;
		/* FALLTHROUGH */
	case OPTION_STRING:
		if (opts->argh) {
			if (opts->flags & PARSE_OPT_OPTARG)
				if (opts->long_name)
					pos += fprintf(stderr, "[=<%s>]", opts->argh);
				else
					pos += fprintf(stderr, "[<%s>]", opts->argh);
			else
				pos += fprintf(stderr, " <%s>", opts->argh);
		} else {
			if (opts->flags & PARSE_OPT_OPTARG)
				if (opts->long_name)
					pos += fprintf(stderr, "[=...]");
				else
					pos += fprintf(stderr, "[...]");
			else
				pos += fprintf(stderr, " ...");
		}
		break;
	default: /* OPTION_{BIT,BOOLEAN,SET_UINT,SET_PTR} */
	case OPTION_END:
	case OPTION_GROUP:
	case OPTION_BIT:
	case OPTION_BOOLEAN:
	case OPTION_INCR:
	case OPTION_SET_UINT:
	case OPTION_SET_PTR:
		break;
	}

	if (pos <= USAGE_OPTS_WIDTH)
		pad = USAGE_OPTS_WIDTH - pos;
	else {
		fputc('\n', stderr);
		pad = USAGE_OPTS_WIDTH;
	}
	fprintf(stderr, "%*s%s\n", pad + USAGE_GAP, "", opts->help);
	if (opts->flags & PARSE_OPT_NOBUILD)
		fprintf(stderr, "%*s(not built-in because %s)\n",
			USAGE_OPTS_WIDTH + USAGE_GAP, "",
			opts->build_opt);
}

static int option__cmp(const void *va, const void *vb)
{
	const struct option *a = va, *b = vb;
	int sa = tolower(a->short_name), sb = tolower(b->short_name), ret;

	if (sa == 0)
		sa = 'z' + 1;
	if (sb == 0)
		sb = 'z' + 1;

	ret = sa - sb;

	if (ret == 0) {
		const char *la = a->long_name ?: "",
			   *lb = b->long_name ?: "";
		ret = strcmp(la, lb);
	}

	return ret;
}

static struct option *options__order(const struct option *opts)
{
	int nr_opts = 0, len;
	const struct option *o = opts;
	struct option *ordered;

	for (o = opts; o->type != OPTION_END; o++)
		++nr_opts;

	len = sizeof(*o) * (nr_opts + 1);
	ordered = malloc(len);
	if (!ordered)
		goto out;
	memcpy(ordered, opts, len);

	qsort(ordered, nr_opts, sizeof(*o), option__cmp);
out:
	return ordered;
}

static bool option__in_argv(const struct option *opt, const struct parse_opt_ctx_t *ctx)
{
	int i;

	for (i = 1; i < ctx->argc; ++i) {
		const char *arg = ctx->argv[i];

		if (arg[0] != '-') {
			if (arg[1] == '\0') {
				if (arg[0] == opt->short_name)
					return true;
				continue;
			}

			if (opt->long_name && strcmp(opt->long_name, arg) == 0)
				return true;

			if (opt->help && strcasestr(opt->help, arg) != NULL)
				return true;

			continue;
		}

		if (arg[1] == opt->short_name ||
		    (arg[1] == '-' && opt->long_name && strcmp(opt->long_name, arg + 2) == 0))
			return true;
	}

	return false;
}

static int usage_with_options_internal(const char * const *usagestr,
				       const struct option *opts, int full,
				       struct parse_opt_ctx_t *ctx)
{
	struct option *ordered;

	if (!usagestr)
		return PARSE_OPT_HELP;

	setup_pager();

	if (error_buf) {
		fprintf(stderr, "  Error: %s\n", error_buf);
		zfree(&error_buf);
	}

	fprintf(stderr, "\n Usage: %s\n", *usagestr++);
	while (*usagestr && **usagestr)
		fprintf(stderr, "    or: %s\n", *usagestr++);
	while (*usagestr) {
		fprintf(stderr, "%s%s\n",
				**usagestr ? "    " : "",
				*usagestr);
		usagestr++;
	}

	if (opts->type != OPTION_GROUP)
		fputc('\n', stderr);

	ordered = options__order(opts);
	if (ordered)
		opts = ordered;

	for (  ; opts->type != OPTION_END; opts++) {
		if (ctx && ctx->argc > 1 && !option__in_argv(opts, ctx))
			continue;
		print_option_help(opts, full);
	}

	fputc('\n', stderr);

	free(ordered);

	return PARSE_OPT_HELP;
}

void usage_with_options(const char * const *usagestr,
			const struct option *opts)
{
	usage_with_options_internal(usagestr, opts, 0, NULL);
	exit(129);
}

void usage_with_options_msg(const char * const *usagestr,
			    const struct option *opts, const char *fmt, ...)
{
	va_list ap;
	char *tmp = error_buf;

	va_start(ap, fmt);
	if (vasprintf(&error_buf, fmt, ap) == -1)
		die("vasprintf failed");
	va_end(ap);

	free(tmp);

	usage_with_options_internal(usagestr, opts, 0, NULL);
	exit(129);
}

int parse_options_usage(const char * const *usagestr,
			const struct option *opts,
			const char *optstr, bool short_opt)
{
	if (!usagestr)
		goto opt;

	fprintf(stderr, "\n Usage: %s\n", *usagestr++);
	while (*usagestr && **usagestr)
		fprintf(stderr, "    or: %s\n", *usagestr++);
	while (*usagestr) {
		fprintf(stderr, "%s%s\n",
				**usagestr ? "    " : "",
				*usagestr);
		usagestr++;
	}
	fputc('\n', stderr);

opt:
	for (  ; opts->type != OPTION_END; opts++) {
		if (short_opt) {
			if (opts->short_name == *optstr) {
				print_option_help(opts, 0);
				break;
			}
			continue;
		}

		if (opts->long_name == NULL)
			continue;

		if (strstarts(opts->long_name, optstr))
			print_option_help(opts, 0);
		if (strstarts("no-", optstr) &&
		    strstarts(opts->long_name, optstr + 3))
			print_option_help(opts, 0);
	}

	return PARSE_OPT_HELP;
}


int parse_opt_verbosity_cb(const struct option *opt,
			   const char *arg __maybe_unused,
			   int unset)
{
	int *target = opt->value;

	if (unset)
		/* --no-quiet, --no-verbose */
		*target = 0;
	else if (opt->short_name == 'v') {
		if (*target >= 0)
			(*target)++;
		else
			*target = 1;
	} else {
		if (*target <= 0)
			(*target)--;
		else
			*target = -1;
	}
	return 0;
}

static struct option *
find_option(struct option *opts, int shortopt, const char *longopt)
{
	for (; opts->type != OPTION_END; opts++) {
		if ((shortopt && opts->short_name == shortopt) ||
		    (opts->long_name && longopt &&
		     !strcmp(opts->long_name, longopt)))
			return opts;
	}
	return NULL;
}

void set_option_flag(struct option *opts, int shortopt, const char *longopt,
		     int flag)
{
	struct option *opt = find_option(opts, shortopt, longopt);

	if (opt)
		opt->flags |= flag;
	return;
}

void set_option_nobuild(struct option *opts, int shortopt,
			const char *longopt,
			const char *build_opt,
			bool can_skip)
{
	struct option *opt = find_option(opts, shortopt, longopt);

	if (!opt)
		return;

	opt->flags |= PARSE_OPT_NOBUILD;
	opt->flags |= can_skip ? PARSE_OPT_CANSKIP : 0;
	opt->build_opt = build_opt;
}
