// SPDX-License-Identifier: GPL-2.0
/*
 * Copyright (C) 2002 Roman Zippel <zippel@linux-m68k.org>
 */

#include <ctype.h>
#include <limits.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>
#include <unistd.h>
#include <getopt.h>
#include <sys/time.h>
#include <errno.h>

#include "internal.h"
#include "lkc.h"

static void conf(struct menu *menu);
static void check_conf(struct menu *menu);

enum input_mode {
	oldaskconfig,
	syncconfig,
	oldconfig,
	allnoconfig,
	allyesconfig,
	allmodconfig,
	alldefconfig,
	randconfig,
	defconfig,
	savedefconfig,
	listnewconfig,
	helpnewconfig,
	olddefconfig,
	yes2modconfig,
	mod2yesconfig,
	mod2noconfig,
};
static enum input_mode input_mode = oldaskconfig;
static int input_mode_opt;
static int indent = 1;
static int tty_stdio;
static int sync_kconfig;
static int conf_cnt;
static char line[PATH_MAX];
static struct menu *rootEntry;

static void print_help(struct menu *menu)
{
	struct gstr help = str_new();

	menu_get_ext_help(menu, &help);

	printf("\n%s\n", str_get(&help));
	str_free(&help);
}

static void strip(char *str)
{
	char *p = str;
	int l;

	while ((isspace(*p)))
		p++;
	l = strlen(p);
	if (p != str)
		memmove(str, p, l + 1);
	if (!l)
		return;
	p = str + l - 1;
	while ((isspace(*p)))
		*p-- = 0;
}

/* Helper function to facilitate fgets() by Jean Sacren. */
static void xfgets(char *str, int size, FILE *in)
{
	if (!fgets(str, size, in))
		fprintf(stderr, "\nError in reading or end of file.\n");

	if (!tty_stdio)
		printf("%s", str);
}

static void set_randconfig_seed(void)
{
	unsigned int seed;
	char *env;
	bool seed_set = false;

	env = getenv("KCONFIG_SEED");
	if (env && *env) {
		char *endp;

		seed = strtol(env, &endp, 0);
		if (*endp == '\0')
			seed_set = true;
	}

	if (!seed_set) {
		struct timeval now;

		/*
		 * Use microseconds derived seed, compensate for systems where it may
		 * be zero.
		 */
		gettimeofday(&now, NULL);
		seed = (now.tv_sec + 1) * (now.tv_usec + 1);
	}

	printf("KCONFIG_SEED=0x%X\n", seed);
	srand(seed);
}

/**
 * randomize_choice_values - randomize choice block
 *
 * @choice: menu entry for the choice
 */
static void randomize_choice_values(struct menu *choice)
{
	struct menu *menu;
	int x;
	int cnt = 0;

	/*
	 * First, count the number of symbols to randomize. If sym_has_value()
	 * is true, it was specified by KCONFIG_ALLCONFIG. It needs to be
	 * respected.
	 */
	menu_for_each_sub_entry(menu, choice) {
		struct symbol *sym = menu->sym;

		if (sym && !sym_has_value(sym))
			cnt++;
	}

	while (cnt > 0) {
		x = rand() % cnt;

		menu_for_each_sub_entry(menu, choice) {
			struct symbol *sym = menu->sym;

			if (sym && !sym_has_value(sym))
				x--;

			if (x < 0) {
				sym->def[S_DEF_USER].tri = yes;
				sym->flags |= SYMBOL_DEF_USER;
				/*
				 * Move the selected item to the _tail_ because
				 * this needs to have a lower priority than the
				 * user input from KCONFIG_ALLCONFIG.
				 */
				list_move_tail(&sym->choice_link,
					       &choice->choice_members);

				break;
			}
		}
		cnt--;
	}
}

enum conf_def_mode {
	def_default,
	def_yes,
	def_mod,
	def_no,
	def_random
};

static void conf_set_all_new_symbols(enum conf_def_mode mode)
{
	struct menu *menu;
	int cnt;
	/*
	 * can't go as the default in switch-case below, otherwise gcc whines
	 * about -Wmaybe-uninitialized
	 */
	int pby = 50; /* probability of bool     = y */
	int pty = 33; /* probability of tristate = y */
	int ptm = 33; /* probability of tristate = m */

	if (mode == def_random) {
		int n, p[3];
		char *env = getenv("KCONFIG_PROBABILITY");

		n = 0;
		while (env && *env) {
			char *endp;
			int tmp = strtol(env, &endp, 10);

			if (tmp >= 0 && tmp <= 100) {
				p[n++] = tmp;
			} else {
				errno = ERANGE;
				perror("KCONFIG_PROBABILITY");
				exit(1);
			}
			env = (*endp == ':') ? endp + 1 : endp;
			if (n >= 3)
				break;
		}
		switch (n) {
		case 1:
			pby = p[0];
			ptm = pby / 2;
			pty = pby - ptm;
			break;
		case 2:
			pty = p[0];
			ptm = p[1];
			pby = pty + ptm;
			break;
		case 3:
			pby = p[0];
			pty = p[1];
			ptm = p[2];
			break;
		}

		if (pty + ptm > 100) {
			errno = ERANGE;
			perror("KCONFIG_PROBABILITY");
			exit(1);
		}
	}

	menu_for_each_entry(menu) {
		struct symbol *sym = menu->sym;
		tristate val;

		if (!sym || !menu->prompt || sym_has_value(sym) ||
		    (sym->type != S_BOOLEAN && sym->type != S_TRISTATE) ||
		    sym_is_choice_value(sym))
			continue;

		if (sym_is_choice(sym)) {
			if (mode == def_random)
				randomize_choice_values(menu);
			continue;
		}

		switch (mode) {
		case def_yes:
			val = yes;
			break;
		case def_mod:
			val = mod;
			break;
		case def_no:
			val = no;
			break;
		case def_random:
			val = no;
			cnt = rand() % 100;
			if (sym->type == S_TRISTATE) {
				if (cnt < pty)
					val = yes;
				else if (cnt < pty + ptm)
					val = mod;
			} else if (cnt < pby) {
				val = yes;
			}
			break;
		default:
			continue;
		}
		sym->def[S_DEF_USER].tri = val;
		sym->flags |= SYMBOL_DEF_USER;
	}

	sym_clear_all_valid();
}

static void conf_rewrite_tristates(tristate old_val, tristate new_val)
{
	struct symbol *sym;

	for_all_symbols(sym) {
		if (sym_get_type(sym) == S_TRISTATE &&
		    sym->def[S_DEF_USER].tri == old_val)
			sym->def[S_DEF_USER].tri = new_val;
	}
	sym_clear_all_valid();
}

static int conf_askvalue(struct symbol *sym, const char *def)
{
	if (!sym_has_value(sym))
		printf("(NEW) ");

	line[0] = '\n';
	line[1] = 0;

	if (!sym_is_changeable(sym)) {
		printf("%s\n", def);
		line[0] = '\n';
		line[1] = 0;
		return 0;
	}

	switch (input_mode) {
	case oldconfig:
	case syncconfig:
		if (sym_has_value(sym)) {
			printf("%s\n", def);
			return 0;
		}
		/* fall through */
	default:
		fflush(stdout);
		xfgets(line, sizeof(line), stdin);
		break;
	}

	return 1;
}

static int conf_string(struct menu *menu)
{
	struct symbol *sym = menu->sym;
	const char *def;

	while (1) {
		printf("%*s%s ", indent - 1, "", menu->prompt->text);
		printf("(%s) ", sym->name);
		def = sym_get_string_value(sym);
		if (def)
			printf("[%s] ", def);
		if (!conf_askvalue(sym, def))
			return 0;
		switch (line[0]) {
		case '\n':
			break;
		case '?':
			/* print help */
			if (line[1] == '\n') {
				print_help(menu);
				def = NULL;
				break;
			}
			/* fall through */
		default:
			line[strlen(line)-1] = 0;
			def = line;
		}
		if (def && sym_set_string_value(sym, def))
			return 0;
	}
}

static int conf_sym(struct menu *menu)
{
	struct symbol *sym = menu->sym;
	tristate oldval, newval;

	while (1) {
		printf("%*s%s ", indent - 1, "", menu->prompt->text);
		if (sym->name)
			printf("(%s) ", sym->name);
		putchar('[');
		oldval = sym_get_tristate_value(sym);
		switch (oldval) {
		case no:
			putchar('N');
			break;
		case mod:
			putchar('M');
			break;
		case yes:
			putchar('Y');
			break;
		}
		if (oldval != no && sym_tristate_within_range(sym, no))
			printf("/n");
		if (oldval != mod && sym_tristate_within_range(sym, mod))
			printf("/m");
		if (oldval != yes && sym_tristate_within_range(sym, yes))
			printf("/y");
		printf("/?] ");
		if (!conf_askvalue(sym, sym_get_string_value(sym)))
			return 0;
		strip(line);

		switch (line[0]) {
		case 'n':
		case 'N':
			newval = no;
			if (!line[1] || !strcmp(&line[1], "o"))
				break;
			continue;
		case 'm':
		case 'M':
			newval = mod;
			if (!line[1])
				break;
			continue;
		case 'y':
		case 'Y':
			newval = yes;
			if (!line[1] || !strcmp(&line[1], "es"))
				break;
			continue;
		case 0:
			newval = oldval;
			break;
		case '?':
			goto help;
		default:
			continue;
		}
		if (sym_set_tristate_value(sym, newval))
			return 0;
help:
		print_help(menu);
	}
}

static void conf_choice(struct menu *menu)
{
	struct symbol *def_sym;
	struct menu *child;
	bool is_new = false;

	while (1) {
		int cnt, def;

		printf("%*s%s\n", indent - 1, "", menu_get_prompt(menu));
		def_sym = sym_calc_choice(menu);
		cnt = def = 0;
		line[0] = 0;
		for (child = menu->list; child; child = child->next) {
			if (!menu_is_visible(child))
				continue;
			if (!child->sym) {
				printf("%*c %s\n", indent, '*', menu_get_prompt(child));
				continue;
			}
			cnt++;
			if (child->sym == def_sym) {
				def = cnt;
				printf("%*c", indent, '>');
			} else
				printf("%*c", indent, ' ');
			printf(" %d. %s (%s)", cnt, menu_get_prompt(child),
			       child->sym->name);
			if (!sym_has_value(child->sym)) {
				is_new = true;
				printf(" (NEW)");
			}
			printf("\n");
		}
		printf("%*schoice", indent - 1, "");
		if (cnt == 1) {
			printf("[1]: 1\n");
			goto conf_childs;
		}
		printf("[1-%d?]: ", cnt);
		switch (input_mode) {
		case oldconfig:
		case syncconfig:
			if (!is_new) {
				cnt = def;
				printf("%d\n", cnt);
				break;
			}
			/* fall through */
		case oldaskconfig:
			fflush(stdout);
			xfgets(line, sizeof(line), stdin);
			strip(line);
			if (line[0] == '?') {
				print_help(menu);
				continue;
			}
			if (!line[0])
				cnt = def;
			else if (isdigit(line[0]))
				cnt = atoi(line);
			else
				continue;
			break;
		default:
			break;
		}

	conf_childs:
		for (child = menu->list; child; child = child->next) {
			if (!child->sym || !menu_is_visible(child))
				continue;
			if (!--cnt)
				break;
		}
		if (!child)
			continue;
		if (line[0] && line[strlen(line) - 1] == '?') {
			print_help(child);
			continue;
		}
		choice_set_value(menu, child->sym);
		return;
	}
}

static void conf(struct menu *menu)
{
	struct symbol *sym;
	struct property *prop;
	struct menu *child;

	if (!menu_is_visible(menu))
		return;

	sym = menu->sym;
	prop = menu->prompt;
	if (prop) {
		const char *prompt;

		switch (prop->type) {
		case P_MENU:
			/*
			 * Except in oldaskconfig mode, we show only menus that
			 * contain new symbols.
			 */
			if (input_mode != oldaskconfig && rootEntry != menu) {
				check_conf(menu);
				return;
			}
			/* fall through */
		case P_COMMENT:
			prompt = menu_get_prompt(menu);
			if (prompt)
				printf("%*c\n%*c %s\n%*c\n",
					indent, '*',
					indent, '*', prompt,
					indent, '*');
		default:
			;
		}
	}

	if (!sym)
		goto conf_childs;

	if (sym_is_choice(sym)) {
		conf_choice(menu);
		return;
	}

	switch (sym->type) {
	case S_INT:
	case S_HEX:
	case S_STRING:
		conf_string(menu);
		break;
	default:
		conf_sym(menu);
		break;
	}

conf_childs:
	if (sym)
		indent += 2;
	for (child = menu->list; child; child = child->next)
		conf(child);
	if (sym)
		indent -= 2;
}

static void check_conf(struct menu *menu)
{
	struct symbol *sym;
	struct menu *child;

	if (!menu_is_visible(menu))
		return;

	sym = menu->sym;
	if (sym && !sym_has_value(sym) && sym_is_changeable(sym)) {
		switch (input_mode) {
		case listnewconfig:
			if (sym->name)
				print_symbol_for_listconfig(sym);
			break;
		case helpnewconfig:
			printf("-----\n");
			print_help(menu);
			printf("-----\n");
			break;
		default:
			if (!conf_cnt++)
				printf("*\n* Restart config...\n*\n");
			rootEntry = menu_get_parent_menu(menu);
			conf(rootEntry);
			break;
		}
	}

	for (child = menu->list; child; child = child->next)
		check_conf(child);
}

static const struct option long_opts[] = {
	{"help",          no_argument,       NULL,            'h'},
	{"silent",        no_argument,       NULL,            's'},
	{"oldaskconfig",  no_argument,       &input_mode_opt, oldaskconfig},
	{"oldconfig",     no_argument,       &input_mode_opt, oldconfig},
	{"syncconfig",    no_argument,       &input_mode_opt, syncconfig},
	{"defconfig",     required_argument, &input_mode_opt, defconfig},
	{"savedefconfig", required_argument, &input_mode_opt, savedefconfig},
	{"allnoconfig",   no_argument,       &input_mode_opt, allnoconfig},
	{"allyesconfig",  no_argument,       &input_mode_opt, allyesconfig},
	{"allmodconfig",  no_argument,       &input_mode_opt, allmodconfig},
	{"alldefconfig",  no_argument,       &input_mode_opt, alldefconfig},
	{"randconfig",    no_argument,       &input_mode_opt, randconfig},
	{"listnewconfig", no_argument,       &input_mode_opt, listnewconfig},
	{"helpnewconfig", no_argument,       &input_mode_opt, helpnewconfig},
	{"olddefconfig",  no_argument,       &input_mode_opt, olddefconfig},
	{"yes2modconfig", no_argument,       &input_mode_opt, yes2modconfig},
	{"mod2yesconfig", no_argument,       &input_mode_opt, mod2yesconfig},
	{"mod2noconfig",  no_argument,       &input_mode_opt, mod2noconfig},
	{NULL, 0, NULL, 0}
};

static void conf_usage(const char *progname)
{
	printf("Usage: %s [options] <kconfig-file>\n", progname);
	printf("\n");
	printf("Generic options:\n");
	printf("  -h, --help              Print this message and exit.\n");
	printf("  -s, --silent            Do not print log.\n");
	printf("\n");
	printf("Mode options:\n");
	printf("  --listnewconfig         List new options\n");
	printf("  --helpnewconfig         List new options and help text\n");
	printf("  --oldaskconfig          Start a new configuration using a line-oriented program\n");
	printf("  --oldconfig             Update a configuration using a provided .config as base\n");
	printf("  --syncconfig            Similar to oldconfig but generates configuration in\n"
	       "                          include/{generated/,config/}\n");
	printf("  --olddefconfig          Same as oldconfig but sets new symbols to their default value\n");
	printf("  --defconfig <file>      New config with default defined in <file>\n");
	printf("  --savedefconfig <file>  Save the minimal current configuration to <file>\n");
	printf("  --allnoconfig           New config where all options are answered with no\n");
	printf("  --allyesconfig          New config where all options are answered with yes\n");
	printf("  --allmodconfig          New config where all options are answered with mod\n");
	printf("  --alldefconfig          New config with all symbols set to default\n");
	printf("  --randconfig            New config with random answer to all options\n");
	printf("  --yes2modconfig         Change answers from yes to mod if possible\n");
	printf("  --mod2yesconfig         Change answers from mod to yes if possible\n");
	printf("  --mod2noconfig          Change answers from mod to no if possible\n");
	printf("  (If none of the above is given, --oldaskconfig is the default)\n");
}

int main(int ac, char **av)
{
	const char *progname = av[0];
	int opt;
	const char *name, *defconfig_file = NULL /* gcc uninit */;
	int no_conf_write = 0;

	tty_stdio = isatty(0) && isatty(1);

	while ((opt = getopt_long(ac, av, "hs", long_opts, NULL)) != -1) {
		switch (opt) {
		case 'h':
			conf_usage(progname);
			exit(1);
			break;
		case 's':
			conf_set_message_callback(NULL);
			break;
		case 0:
			input_mode = input_mode_opt;
			switch (input_mode) {
			case syncconfig:
				/*
				 * syncconfig is invoked during the build stage.
				 * Suppress distracting
				 *   "configuration written to ..."
				 */
				conf_set_message_callback(NULL);
				sync_kconfig = 1;
				break;
			case defconfig:
			case savedefconfig:
				defconfig_file = optarg;
				break;
			case randconfig:
				set_randconfig_seed();
				break;
			default:
				break;
			}
		default:
			break;
		}
	}
	if (ac == optind) {
		fprintf(stderr, "%s: Kconfig file missing\n", av[0]);
		conf_usage(progname);
		exit(1);
	}
	conf_parse(av[optind]);
	//zconfdump(stdout);

	switch (input_mode) {
	case defconfig:
		if (conf_read(defconfig_file)) {
			fprintf(stderr,
				"***\n"
				  "*** Can't find default configuration \"%s\"!\n"
				  "***\n",
				defconfig_file);
			exit(1);
		}
		break;
	case savedefconfig:
	case syncconfig:
	case oldaskconfig:
	case oldconfig:
	case listnewconfig:
	case helpnewconfig:
	case olddefconfig:
	case yes2modconfig:
	case mod2yesconfig:
	case mod2noconfig:
		conf_read(NULL);
		break;
	case allnoconfig:
	case allyesconfig:
	case allmodconfig:
	case alldefconfig:
	case randconfig:
		name = getenv("KCONFIG_ALLCONFIG");
		if (!name)
			break;
		if ((strcmp(name, "") != 0) && (strcmp(name, "1") != 0)) {
			if (conf_read_simple(name, S_DEF_USER)) {
				fprintf(stderr,
					"*** Can't read seed configuration \"%s\"!\n",
					name);
				exit(1);
			}
			break;
		}
		switch (input_mode) {
		case allnoconfig:	name = "allno.config"; break;
		case allyesconfig:	name = "allyes.config"; break;
		case allmodconfig:	name = "allmod.config"; break;
		case alldefconfig:	name = "alldef.config"; break;
		case randconfig:	name = "allrandom.config"; break;
		default: break;
		}
		if (conf_read_simple(name, S_DEF_USER) &&
		    conf_read_simple("all.config", S_DEF_USER)) {
			fprintf(stderr,
				"*** KCONFIG_ALLCONFIG set, but no \"%s\" or \"all.config\" file found\n",
				name);
			exit(1);
		}
		break;
	default:
		break;
	}

	if (conf_errors())
		exit(1);

	if (sync_kconfig) {
		name = getenv("KCONFIG_NOSILENTUPDATE");
		if (name && *name) {
			if (conf_get_changed()) {
				fprintf(stderr,
					"\n*** The configuration requires explicit update.\n\n");
				return 1;
			}
			no_conf_write = 1;
		}
	}

	switch (input_mode) {
	case allnoconfig:
		conf_set_all_new_symbols(def_no);
		break;
	case allyesconfig:
		conf_set_all_new_symbols(def_yes);
		break;
	case allmodconfig:
		conf_set_all_new_symbols(def_mod);
		break;
	case alldefconfig:
		conf_set_all_new_symbols(def_default);
		break;
	case randconfig:
		conf_set_all_new_symbols(def_random);
		break;
	case defconfig:
		conf_set_all_new_symbols(def_default);
		break;
	case savedefconfig:
		break;
	case yes2modconfig:
		conf_rewrite_tristates(yes, mod);
		break;
	case mod2yesconfig:
		conf_rewrite_tristates(mod, yes);
		break;
	case mod2noconfig:
		conf_rewrite_tristates(mod, no);
		break;
	case oldaskconfig:
		rootEntry = &rootmenu;
		conf(&rootmenu);
		input_mode = oldconfig;
		/* fall through */
	case oldconfig:
	case listnewconfig:
	case helpnewconfig:
	case syncconfig:
		/* Update until a loop caused no more changes */
		do {
			conf_cnt = 0;
			check_conf(&rootmenu);
		} while (conf_cnt);
		break;
	case olddefconfig:
	default:
		break;
	}

	if (sym_dep_errors())
		exit(1);

	if (input_mode == savedefconfig) {
		if (conf_write_defconfig(defconfig_file)) {
			fprintf(stderr, "n*** Error while saving defconfig to: %s\n\n",
				defconfig_file);
			return 1;
		}
	} else if (input_mode != listnewconfig && input_mode != helpnewconfig) {
		if (!no_conf_write && conf_write(NULL)) {
			fprintf(stderr, "\n*** Error during writing of the configuration.\n\n");
			exit(1);
		}

		/*
		 * Create auto.conf if it does not exist.
		 * This prevents GNU Make 4.1 or older from emitting
		 * "include/config/auto.conf: No such file or directory"
		 * in the top-level Makefile
		 *
		 * syncconfig always creates or updates auto.conf because it is
		 * used during the build.
		 */
		if (conf_write_autoconf(sync_kconfig) && sync_kconfig) {
			fprintf(stderr,
				"\n*** Error during sync of the configuration.\n\n");
			return 1;
		}
	}
	return 0;
}
