/* vi: set sw=4 ts=4: */
/*
 * universal getopt_ulflags implementation for busybox
 *
 * Copyright (C) 2003-2005  Vladimir Oleynik  <dzo@simtreas.ru>
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation; either version 2 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
 * General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
 *
 */

#include <getopt.h>
#include <string.h>
#include <assert.h>
#include <stdlib.h>
#include "libbb.h"

/*                  Documentation

unsigned long
bb_getopt_ulflags (int argc, char **argv, const char *applet_opts, ...)

	The command line options must be declared in const char
	*applet_opts as a string of chars, for example:

	flags = bb_getopt_ulflags(argc, argv, "rnug");

	If one of the given options is found, a flag value is added to
	the return value (an unsigned long).

	The flag value is determined by the position of the char in
	applet_opts string.  For example, in the above case:

	flags = bb_getopt_ulflags(argc, argv, "rnug");

	"r" will add 1    (bit 0)
	"n" will add 2    (bit 1)
	"u  will add 4    (bit 2)
	"g" will add 8    (bit 3)

	and so on.  You can also look at the return value as a bit
	field and each option sets one bit.

 ":"    If one of the options requires an argument, then add a ":"
	after the char in applet_opts and provide a pointer to store
	the argument.  For example:

	char *pointer_to_arg_for_a;
	char *pointer_to_arg_for_b;
	char *pointer_to_arg_for_c;
	char *pointer_to_arg_for_d;

	flags = bb_getopt_ulflags(argc, argv, "a:b:c:d:",
			&pointer_to_arg_for_a, &pointer_to_arg_for_b,
			&pointer_to_arg_for_c, &pointer_to_arg_for_d);

	The type of the pointer (char* or llist_t*) may be controlled
	by the "::" special separator that is set in the external string
	bb_opt_complementally (see below for more info).

 "+"    If the first character in the applet_opts string is a plus,
	then option processing will stop as soon as a non-option is
	encountered in the argv array.  Useful for applets like env
	which should not process arguments to subprograms:
	env -i ls -d /
	Here we want env to process just the '-i', not the '-d'.

const struct option *bb_applet_long_options

	This struct allows you to define long options.  The syntax for
	declaring the array is just like that of getopt's longopts.
	(see getopt(3))

	static const struct option applet_long_options[] = {
		{ "verbose", 0, 0, 'v' },
		{ 0, 0, 0, 0 }
	};
	bb_applet_long_options = applet_long_options;

	The last member of struct option (val) typically is set to
	matching short option from applet_opts. If there is no matching
	char in applet_opts, then:
	- return bit have next position after short options
	- if has_arg is not "no_argument", use ptr for arg also
	- bb_opt_complementally affects it too

	Note: a good applet will make long options configurable via the
	config process and not a required feature.  The current standard
	is to name the config option CONFIG_FEATURE_<applet>_LONG_OPTIONS.

const char *bb_opt_complementally
	this should be bb_opt_complementary, but we'll just keep it as
	bb_opt_complementally due to the Russian origins

 ":"    The colon (":") is used to separate groups of two or more chars
	and/or groups of chars and special characters (stating some
	conditions to be checked).

 "abc"  If groups of two or more chars are specified, the first char
	is the main option and the other chars are secondary options.
	Their flags will be turned on if the main option is found even
	if they are not specifed on the command line.  For example:

	bb_opt_complementally = "abc";

	flags = bb_getopt_ulflags(argc, argv, "abcd")

	If getopt() finds "-a" on the command line, then
	bb_getopt_ulflags's return value will be as if "-a -b -c" were
	found.

 "ww"   Adjacent double options have a counter associated which indicates
	the number of occurences of the option.
	For example the ps applet needs:
	if w is given once, GNU ps sets the width to 132,
	if w is given more than once, it is "unlimited"

	int w_counter = 0;
	bb_opt_complementally = "ww";
	bb_getopt_ulflags(argc, argv, "w", &w_counter);

	if(w_counter)
		width = (w_counter == 1) ? 132 : INT_MAX;
	else
		get_terminal_width(...&width...);

	w_counter is a pointer to an integer. It has to be passed to
	bb_getopt_ulflags() after all other option argument sinks.
	For example: accept multiple -v to indicate the level of verbosity
	and for each -b optarg, add optarg to my_b. Finally, if b is given,
	turn off c and vice versa:

	llist_t *my_b = NULL;
	int verbose_level = 0;
	bb_opt_complementally = "vv:b::b-c:c-b";
	f = bb_getopt_ulflags(argc, argv, "vb:c", &my_b, &verbose_level);
	if((f & 2))     // -c after -b unsets -b flag
		while(my_b) { dosomething_with(my_b->data) ; my_b = my_b->link; }
	if(my_b)        // but llist is stored if -b is specified
		free_llist(my_b);
	if(verbose_level) bb_printf("verbose level is %d\n", verbose_level);

Special characters:

 "-"    A dash between two options causes the second of the two
	to be unset (and ignored) if it is given on the command line.

	[FIXME: what if they are the same? like "x-x"? Is it ever useful?]

	For example:
	The du applet has the options "-s" and "-d depth".  If
	bb_getopt_ulflags finds -s, then -d is unset or if it finds -d
	then -s is unset.  (Note:  busybox implements the GNU
	"--max-depth" option as "-d".)  To obtain this behavior, you
	set bb_opt_complementally = "s-d:d-s".  Only one flag value is
	added to bb_getopt_ulflags's return value depending on the
	position of the options on the command line.  If one of the
	two options requires an argument pointer (":" in applet_opts
	as in "d:") optarg is set accordingly.

	char *smax_print_depth;

	bb_opt_complementally = "s-d:d-s:x-x";
	opt = bb_getopt_ulflags(argc, argv, "sd:x", &smax_print_depth);

	if (opt & 2)
		max_print_depth = atoi(smax_print_depth);
	if (opt & 4)
		printf("Detected odd -x usage\n");

 "-"    A dash as the first char in a bb_opt_complementally group forces
	all arguments to be treated as options, even if they have
	no leading dashes. Next char in this case can't be a digit (0-9),
	use ':' or end of line. For example:

	bb_opt_complementally = "-:w-x:x-w";
	bb_getopt_ulflags(argc, argv, "wx");

	Allows any arguments to be given without a dash (./program w x)
	as well as with a dash (./program -x).

 "-N"   A dash as the first char in a bb_opt_complementally group followed
	by a single digit (0-9) means that at least N non-option
	arguments must be present on the command line

 "V-"   An option with dash before colon or end-of-line results in
	bb_show_usage being called if this option is encountered.
	This is typically used to implement "print verbose usage message
	and exit" option.

 "--"   A double dash between two options, or between an option and a group
	of options, means that they are mutually exclusive.  Unlike
	the "-" case above, an error will be forced if the options
	are used together.

	For example:
	The cut applet must have only one type of list specified, so
	-b, -c and -f are mutally exclusive and should raise an error
	if specified together.  In this case you must set
	bb_opt_complementally = "b--cf:c--bf:f--bc".  If two of the
	mutually exclusive options are found, bb_getopt_ulflags's
	return value will have the error flag set (BB_GETOPT_ERROR) so
	that we can check for it:

	if (flags & BB_GETOPT_ERROR)
		bb_show_usage();

 "?"    A "?" as the first char in a bb_opt_complementally group means:
	if BB_GETOPT_ERROR is detected, don't return, call bb_show_usage
	and exit instead. Next char after '?' can't be a digit.

 "?N"   A "?" as the first char in a bb_opt_complementally group followed
	by a single digit (0-9) means that at most N arguments must be present
	on the command line.

 "::"   A double colon after a char in bb_opt_complementally means that the
	option can occur multiple times. Each occurrence will be saved as
	a llist_t element instead of char*.

	For example:
	The grep applet can have one or more "-e pattern" arguments.
	In this case you should use bb_getopt_ulflags() as follows:

	llist_t *patterns = NULL;

	(this pointer must be initializated to NULL if the list is empty
	as required by *llist_add_to(llist_t *old_head, char *new_item).)

	bb_opt_complementally = "e::";

	bb_getopt_ulflags(argc, argv, "e:", &patterns);
	$ grep -e user -e root /etc/passwd
	root:x:0:0:root:/root:/bin/bash
	user:x:500:500::/home/user:/bin/bash

 "--"   A double dash at the beginning of bb_opt_complementally means the
	argv[1] string should always be treated as options, even if it isn't
	prefixed with a "-".  This is to support the special syntax in applets
	such as "ar" and "tar":
	tar xvf foo.tar

 "?"    An "?" between an option and a group of options means that
	at least one of them is required to occur if the first option
	occurs in preceding command line arguments.

	For example from "id" applet:

	// Don't allow -n -r -rn -ug -rug -nug -rnug
	bb_opt_complementally = "r?ug:n?ug:?u--g:g--u";
	flags = bb_getopt_ulflags(argc, argv, "rnug");

	This example allowed only:
	$ id; id -u; id -g; id -ru; id -nu; id -rg; id -ng; id -rnu; id -rng

 "X"    A bb_opt_complementally group with just a single letter means
	that this this option is required. If more than one such group exists,
	at least one option is required to occur (not all of them).
	For example from "start-stop-daemon" applet:

	// Don't allow -KS -SK, but -S or -K is required
	bb_opt_complementally = "K:S:?K--S:S--K";
	flags = bb_getopt_ulflags(argc, argv, "KS...);


 "x--x" give error if double or more used -x option

 Don't forget to use ':'. For example "?322-22-23X-x-a" is interpreted as
 "?3:22:-2:2-2:2-3Xa:2--x": max 3 args; count uses of '-2'; min 2 args;
 if there is a '-2' option then unset '-3', '-X' and '-a'; if there is
 a '-2' and after it a '-x' then error out.

*/

/* this should be bb_opt_complementary, but we'll just keep it as
   bb_opt_complementally due to the Russian origins */
const char *bb_opt_complementally;

typedef struct {
	int opt;
	int list_flg;
	unsigned long switch_on;
	unsigned long switch_off;
	unsigned long incongruously;
	unsigned long requires;
	void **optarg;               /* char **optarg or llist_t **optarg */
	int *counter;
} t_complementally;

/* You can set bb_applet_long_options for parse called long options */

static const struct option bb_default_long_options[] = {
/*      { "help", 0, NULL, '?' }, */
	{ 0, 0, 0, 0 }
};

const struct option *bb_applet_long_options = bb_default_long_options;

unsigned long
bb_getopt_ulflags (int argc, char **argv, const char *applet_opts, ...)
{
	unsigned long flags = 0;
	unsigned long requires = 0;
	t_complementally complementally[sizeof(flags) * 8 + 1];
	int c;
	const unsigned char *s;
	t_complementally *on_off;
	va_list p;
	const struct option *l_o;
	unsigned long trigger;
#ifdef CONFIG_PS
	char **pargv = NULL;
#endif
	int min_arg = 0;
	int max_arg = -1;

#define SHOW_USAGE_IF_ERROR     1
#define ALL_ARGV_IS_OPTS        2
#define FIRST_ARGV_IS_OPT       4
#define FREE_FIRST_ARGV_IS_OPT  8
	int spec_flgs = 0;

	va_start (p, applet_opts);

	c = 0;
	on_off = complementally;
	memset(on_off, 0, sizeof(complementally));

	/* skip GNU extension */
	s = (const unsigned char *)applet_opts;
	if(*s == '+' || *s == '-')
		s++;
	for (; *s; s++) {
		if(c >= (int)(sizeof(flags)*8))
			break;
		on_off->opt = *s;
		on_off->switch_on = (1 << c);
		if (s[1] == ':') {
			on_off->optarg = va_arg (p, void **);
			do
				s++;
			while (s[1] == ':');
		}
		on_off++;
		c++;
	}

	for(l_o = bb_applet_long_options; l_o->name; l_o++) {
		if(l_o->flag)
			continue;
		for(on_off = complementally; on_off->opt != 0; on_off++)
			if(on_off->opt == l_o->val)
				break;
		if(on_off->opt == 0) {
			if(c >= (int)(sizeof(flags)*8))
				break;
			on_off->opt = l_o->val;
			on_off->switch_on = (1 << c);
			if(l_o->has_arg != no_argument)
				on_off->optarg = va_arg (p, void **);
			c++;
		}
	}
	for (s = (const unsigned char *)bb_opt_complementally; s && *s; s++) {
		t_complementally *pair;
		unsigned long *pair_switch;

		if (*s == ':')
			continue;
		c = s[1];
		if(*s == '?') {
			if(c < '0' || c > '9') {
				spec_flgs |= SHOW_USAGE_IF_ERROR;
			} else {
				max_arg = c - '0';
				s++;
			}
			continue;
		}
		if(*s == '-') {
			if(c < '0' || c > '9') {
				if(c == '-') {
					spec_flgs |= FIRST_ARGV_IS_OPT;
					s++;
				} else
					spec_flgs |= ALL_ARGV_IS_OPTS;
			} else {
				min_arg = c - '0';
				s++;
			}
			continue;
		}
		for (on_off = complementally; on_off->opt; on_off++)
			if (on_off->opt == *s)
				break;
		if(c == ':' && s[2] == ':') {
			on_off->list_flg++;
			continue;
		}
		if(c == ':' || c == '\0') {
			requires |= on_off->switch_on;
			continue;
		}
		if(c == '-' && (s[2] == ':' || s[2] == '\0')) {
			flags |= on_off->switch_on;
			on_off->incongruously |= on_off->switch_on;
			s++;
			continue;
		}
		if(c == *s) {
			on_off->counter = va_arg (p, int *);
			s++;
		}
		pair = on_off;
		pair_switch = &(pair->switch_on);
		for(s++; *s && *s != ':'; s++) {
			if(*s == '?') {
				pair_switch = &(pair->requires);
			} else if (*s == '-') {
				if(pair_switch == &(pair->switch_off))
					pair_switch = &(pair->incongruously);
				else
					pair_switch = &(pair->switch_off);
			} else {
			    for (on_off = complementally; on_off->opt; on_off++)
				if (on_off->opt == *s) {
				    *pair_switch |= on_off->switch_on;
				    break;
				}
			}
		}
		s--;
	}
	va_end (p);

#if defined(CONFIG_AR) || defined(CONFIG_TAR)
	if((spec_flgs & FIRST_ARGV_IS_OPT)) {
		if(argv[1] && argv[1][0] != '-' && argv[1][0] != '\0') {
			argv[1] = bb_xasprintf("-%s", argv[1]);
			if(ENABLE_FEATURE_CLEAN_UP)
				spec_flgs |= FREE_FIRST_ARGV_IS_OPT;
		}
	}
#endif
	while ((c = getopt_long (argc, argv, applet_opts,
				 bb_applet_long_options, NULL)) >= 0) {
#ifdef CONFIG_PS
loop_arg_is_opt:
#endif
		for (on_off = complementally; on_off->opt != c; on_off++) {
			/* c==0 if long opt have non NULL flag */
			if(on_off->opt == 0 && c != 0)
				bb_show_usage ();
		}
		if(flags & on_off->incongruously) {
			if((spec_flgs & SHOW_USAGE_IF_ERROR))
				bb_show_usage ();
			flags |= BB_GETOPT_ERROR;
		}
		trigger = on_off->switch_on & on_off->switch_off;
		flags &= ~(on_off->switch_off ^ trigger);
		flags |= on_off->switch_on ^ trigger;
		flags ^= trigger;
		if(on_off->counter)
			(*(on_off->counter))++;
		if(on_off->list_flg) {
			llist_add_to((llist_t **)(on_off->optarg), optarg);
		} else if (on_off->optarg) {
			*(char **)(on_off->optarg) = optarg;
		}
#ifdef CONFIG_PS
		if(pargv != NULL)
			break;
#endif
	}

#ifdef CONFIG_PS
	if((spec_flgs & ALL_ARGV_IS_OPTS)) {
		/* process argv is option, for example "ps" applet */
		if(pargv == NULL)
			pargv = argv + optind;
		while(*pargv) {
			c = **pargv;
			if(c == '\0') {
				pargv++;
			} else {
				(*pargv)++;
				goto loop_arg_is_opt;
			}
		}
	}
#endif

#if (defined(CONFIG_AR) || defined(CONFIG_TAR)) && \
				defined(CONFIG_FEATURE_CLEAN_UP)
	if((spec_flgs & FREE_FIRST_ARGV_IS_OPT))
		free(argv[1]);
#endif
	/* check depending requires for given options */
	for (on_off = complementally; on_off->opt; on_off++) {
		if(on_off->requires && (flags & on_off->switch_on) &&
					(flags & on_off->requires) == 0)
			bb_show_usage ();
	}
	if(requires && (flags & requires) == 0)
		bb_show_usage ();
	argc -= optind;
	if(argc < min_arg || (max_arg >= 0 && argc > max_arg))
		bb_show_usage ();
	return flags;
}
