/*
 * (C) 2014 by Pablo Neira Ayuso <pablo@netfilter.org>
 *
 * 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.
 */

#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
#include <string.h>
#include <iptables.h>
#include <time.h>
#include "xtables-multi.h"
#include "nft.h"

#include <string.h>
#include <netdb.h>
#include <errno.h>
#include <stdbool.h>
#include <stdio.h>
#include <stdlib.h>
#include <ctype.h>
#include <stdarg.h>
#include <limits.h>
#include <unistd.h>
#include <iptables.h>
#include <xtables.h>
#include <libiptc/libxtc.h>
#include <fcntl.h>
#include <getopt.h>
#include "xshared.h"
#include "nft-shared.h"

int xlate_action(const struct iptables_command_state *cs, bool goto_set,
		 struct xt_buf *buf)
{
	int ret = 1;

	/* If no target at all, add nothing (default to continue) */
	if (cs->target != NULL) {
		/* Standard target? */
		if (strcmp(cs->jumpto, XTC_LABEL_ACCEPT) == 0)
			xt_buf_add(buf, "accept");
		else if (strcmp(cs->jumpto, XTC_LABEL_DROP) == 0)
			xt_buf_add(buf, "drop");
		else if (strcmp(cs->jumpto, XTC_LABEL_RETURN) == 0)
			xt_buf_add(buf, "return");
		else if (cs->target->xlate)
			ret = cs->target->xlate(cs->target->t, buf);
		else
			return 0;
	} else if (strlen(cs->jumpto) > 0) {
		/* Not standard, then it's a go / jump to chain */
		if (goto_set)
			xt_buf_add(buf, "goto %s", cs->jumpto);
		else
			xt_buf_add(buf, "jump %s", cs->jumpto);
	}

	return ret;
}

int xlate_matches(const struct iptables_command_state *cs, struct xt_buf *buf)
{
	struct xtables_rule_match *matchp;
	int ret = 1;

	for (matchp = cs->matches; matchp; matchp = matchp->next) {
		if (!matchp->match->xlate)
			return 0;

		ret = matchp->match->xlate(matchp->match->m, buf);
		if (!ret)
			break;
	}
	return ret;
}

bool xlate_find_match(const struct iptables_command_state *cs, const char *p_name)
{
	struct xtables_rule_match *matchp;

	/* Skip redundant protocol, eg. ip protocol tcp tcp dport */
	for (matchp = cs->matches; matchp; matchp = matchp->next) {
		if (strcmp(matchp->match->name, p_name) == 0)
			return true;
	}
	return false;
}

const char *family2str[] = {
	[NFPROTO_IPV4]	= "ip",
	[NFPROTO_IPV6]	= "ip6",
};

static int nft_rule_xlate_add(struct nft_handle *h,
			      const struct nft_xt_cmd_parse *p,
			      const struct iptables_command_state *cs,
			      bool append)
{
	struct xt_buf *buf = xt_buf_alloc(10240);
	int ret;

	if (append) {
		xt_buf_add(buf, "add rule %s %s %s ",
			   family2str[h->family], p->table, p->chain);
	} else {
		xt_buf_add(buf, "insert rule %s %s %s ",
			   family2str[h->family], p->table, p->chain);
	}

	ret = h->ops->xlate(cs, buf);
	if (ret)
		printf("%s\n", xt_buf_get(buf));

	xt_buf_free(buf);
	return ret;
}

static int xlate(struct nft_handle *h, struct nft_xt_cmd_parse *p,
		 struct iptables_command_state *cs,
		 struct xtables_args *args, bool append,
		 int (*cb)(struct nft_handle *h,
			   const struct nft_xt_cmd_parse *p,
			   const struct iptables_command_state *cs,
			   bool append))
{
	unsigned int i, j;
	int ret = 1;

	for (i = 0; i < args->s.naddrs; i++) {
		switch (h->family) {
		case AF_INET:
			cs->fw.ip.src.s_addr = args->s.addr.v4[i].s_addr;
			cs->fw.ip.smsk.s_addr = args->s.mask.v4[i].s_addr;
			for (j = 0; j < args->d.naddrs; j++) {
				cs->fw.ip.dst.s_addr =
					args->d.addr.v4[j].s_addr;
				cs->fw.ip.dmsk.s_addr =
					args->d.mask.v4[j].s_addr;
				ret = cb(h, p, cs, append);
			}
			break;
		case AF_INET6:
			memcpy(&cs->fw6.ipv6.src,
			       &args->s.addr.v6[i], sizeof(struct in6_addr));
			memcpy(&cs->fw6.ipv6.smsk,
			       &args->s.mask.v6[i], sizeof(struct in6_addr));
			for (j = 0; j < args->d.naddrs; j++) {
				memcpy(&cs->fw6.ipv6.dst,
				       &args->d.addr.v6[j],
				       sizeof(struct in6_addr));
				memcpy(&cs->fw6.ipv6.dmsk,
				       &args->d.mask.v6[j],
				       sizeof(struct in6_addr));
				ret = cb(h, p, cs, append);
			}
			break;
		}
	}

	return ret;
}

static void print_ipt_cmd(int argc, char *argv[])
{
	int i;

	printf("# ");
	for (i = 1; i < argc; i++)
		printf("%s ", argv[i]);

	printf("\n");
}

static int do_command_xlate(struct nft_handle *h, int argc, char *argv[],
			    char **table, bool restore)
{
	int ret = 0;
	struct nft_xt_cmd_parse p = {
		.table		= *table,
		.restore	= restore,
	};
	struct iptables_command_state cs;
	struct xtables_args args = {
		.family = h->family,
	};

	do_parse(h, argc, argv, &p, &cs, &args);

	switch (p.command) {
	case CMD_APPEND:
		ret = 1;
		if (!xlate(h, &p, &cs, &args, true, nft_rule_xlate_add))
			print_ipt_cmd(argc, argv);
		break;
	case CMD_DELETE:
		break;
	case CMD_DELETE_NUM:
		break;
	case CMD_CHECK:
		break;
	case CMD_REPLACE:
		break;
	case CMD_INSERT:
		ret = 1;
		if (!xlate(h, &p, &cs, &args, false, nft_rule_xlate_add))
			print_ipt_cmd(argc, argv);
		break;
	case CMD_FLUSH:
		break;
	case CMD_ZERO:
		break;
	case CMD_ZERO_NUM:
		break;
	case CMD_LIST:
	case CMD_LIST|CMD_ZERO:
	case CMD_LIST|CMD_ZERO_NUM:
		printf("list table %s %s\n",
		       family2str[h->family], p.table);
		ret = 1;
		break;
	case CMD_LIST_RULES:
	case CMD_LIST_RULES|CMD_ZERO:
	case CMD_LIST_RULES|CMD_ZERO_NUM:
		break;
	case CMD_NEW_CHAIN:
		printf("add chain %s %s %s\n",
		       family2str[h->family], p.table, p.chain);
		ret = 1;
		break;
	case CMD_DELETE_CHAIN:
		printf("delete chain %s %s %s\n",
		       family2str[h->family], p.table, p.chain);
		ret = 1;
		break;
	case CMD_RENAME_CHAIN:
		break;
	case CMD_SET_POLICY:
		break;
	default:
		/* We should never reach this... */
		printf("Unsupported command?\n");
		exit(1);
	}

	xtables_rule_matches_free(&cs.matches);

	if (h->family == AF_INET) {
		free(args.s.addr.v4);
		free(args.s.mask.v4);
		free(args.d.addr.v4);
		free(args.d.mask.v4);
	} else if (h->family == AF_INET6) {
		free(args.s.addr.v6);
		free(args.s.mask.v6);
		free(args.d.addr.v6);
		free(args.d.mask.v6);
	}
	xtables_free_opts(1);

	return ret;
}

static void print_usage(const char *name, const char *version)
{
	fprintf(stderr, "%s %s "
			"(c) 2014 by Pablo Neira Ayuso <pablo@netfilter.org>\n"
			"Usage: %s [-h] [-f]\n"
                        "	[ --help ]\n"
                        "	[ --file=<FILE> ]\n", name, version, name);
        exit(1);
}

static const struct option options[] = {
	{ .name = "help",	.has_arg = false,	.val = 'h' },
	{ .name = "file",	.has_arg = true,	.val = 'f' },
	{ NULL },
};

static int xlate_chain_user_add(struct nft_handle *h, const char *chain,
				const char *table)
{
	printf("add chain %s %s %s\n", family2str[h->family], chain, table);
	return 0;
}

static int commit(struct nft_handle *h)
{
	return 1;
}

static void xlate_table_new(struct nft_handle *h, const char *table)
{
	printf("add table %s %s\n", family2str[h->family], table);
}

static int xlate_chain_set(struct nft_handle *h, const char *table,
			   const char *chain, const char *policy,
			   const struct xt_counters *counters)
{
	printf("add chain %s %s %s ", family2str[h->family], table, chain);
	if (strcmp(chain, "PREROUTING") == 0)
		printf("{ type filter hook prerouting priority 0; }\n");
	else if (strcmp(chain, "INPUT") == 0)
		printf("{ type filter hook input priority 0; }\n");
	else if (strcmp(chain, "FORWARD") == 0)
		printf("{ type filter hook forward priority 0; }\n");
	else if (strcmp(chain, "OUTPUT") == 0)
		printf("{ type filter hook output priority 0; }\n");
	else if (strcmp(chain, "POSTROUTING") == 0)
		printf("{ type filter hook postrouting priority 0; }\n");

	return 1;
}

static struct nft_xt_restore_cb cb_xlate = {
	.table_new	= xlate_table_new,
	.chain_set	= xlate_chain_set,
	.chain_user_add	= xlate_chain_user_add,
	.do_command	= do_command_xlate,
	.commit		= commit,
	.abort		= commit,
};

static int xtables_xlate_main(int family, const char *progname, int argc,
			      char *argv[])
{
	int ret;
	char *table = "filter";
	struct nft_handle h = {
		.family = family,
	};

	xtables_globals.program_name = progname;
	ret = xtables_init_all(&xtables_globals, family);
	if (ret < 0) {
		fprintf(stderr, "%s/%s Failed to initialize xtables\n",
				xtables_globals.program_name,
				xtables_globals.program_version);
				exit(1);
	}
#if defined(ALL_INCLUSIVE) || defined(NO_SHARED_LIBS)
	init_extensions();
	init_extensions4();
#endif

	if (nft_init(&h, xtables_ipv4) < 0) {
		fprintf(stderr, "%s/%s Failed to initialize nft: %s\n",
				xtables_globals.program_name,
				xtables_globals.program_version,
				strerror(errno));
		nft_fini(&h);
		exit(EXIT_FAILURE);
	}

	printf("nft ");
	ret = do_command_xlate(&h, argc, argv, &table, false);
	if (!ret)
		fprintf(stderr, "Translation not implemented\n");

	nft_fini(&h);
	exit(!ret);
}

static int xtables_restore_xlate_main(int family, const char *progname,
				      int argc, char *argv[])
{
	int ret;
	struct nft_handle h = {
		.family = family,
	};
	const char *file = NULL;
	struct nft_xt_restore_parse p = {};
	time_t now = time(NULL);
	int c;

	xtables_globals.program_name = progname;
	ret = xtables_init_all(&xtables_globals, family);
	if (ret < 0) {
		fprintf(stderr, "%s/%s Failed to initialize xtables\n",
				xtables_globals.program_name,
				xtables_globals.program_version);
				exit(1);
	}
#if defined(ALL_INCLUSIVE) || defined(NO_SHARED_LIBS)
	init_extensions();
	init_extensions4();
#endif

	if (nft_init(&h, xtables_ipv4) < 0) {
		fprintf(stderr, "%s/%s Failed to initialize nft: %s\n",
				xtables_globals.program_name,
				xtables_globals.program_version,
				strerror(errno));
		nft_fini(&h);
		exit(EXIT_FAILURE);
	}

	opterr = 0;
	while ((c = getopt_long(argc, argv, "hf:", options, NULL)) != -1) {
		switch (c) {
		case 'h':
			print_usage(argv[0], IPTABLES_VERSION);
			exit(0);
		case 'f':
			file = optarg;
			break;
		}
	}

	if (file == NULL) {
		fprintf(stderr, "ERROR: missing file name\n");
		print_usage(argv[0], IPTABLES_VERSION);
		exit(0);
	}

	p.in = fopen(file, "r");
	if (p.in == NULL) {
		fprintf(stderr, "Cannot open file %s\n", file);
		exit(1);
	}

	printf("# Translated by %s v%s on %s",
	       argv[0], IPTABLES_VERSION, ctime(&now));
	xtables_restore_parse(&h, &p, &cb_xlate, argc, argv);
	printf("# Completed on %s", ctime(&now));

	nft_fini(&h);
	fclose(p.in);
	exit(0);
}

int xtables_ip4_xlate_main(int argc, char *argv[])
{
	return xtables_xlate_main(NFPROTO_IPV4, "iptables-translate",
				  argc, argv);
}

int xtables_ip6_xlate_main(int argc, char *argv[])
{
	return xtables_xlate_main(NFPROTO_IPV6, "ip6tables-translate",
				  argc, argv);
}

int xtables_ip4_xlate_restore_main(int argc, char *argv[])
{
	return xtables_restore_xlate_main(NFPROTO_IPV4,
					  "iptables-translate-restore",
					  argc, argv);
}

int xtables_ip6_xlate_restore_main(int argc, char *argv[])
{
	return xtables_restore_xlate_main(NFPROTO_IPV6,
					  "ip6tables-translate-restore",
					  argc, argv);
}
