/*
 * ipconfig/main.c
 */
#include <errno.h>
#include <poll.h>
#include <limits.h>
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <time.h>
#include <arpa/inet.h>

#include "ipconfig.h"
#include "netdev.h"
#include "bootp_packet.h"
#include "bootp_proto.h"
#include "dhcp_proto.h"
#include "packet.h"

static const char *progname;
static char do_not_config;
static unsigned int default_caps = CAP_DHCP | CAP_BOOTP | CAP_RARP;
static int loop_timeout = -1;
static int configured;

struct state {
	int		state;
	int		restart_state;
	time_t		expire;
	int		retry_period;

	struct netdev	*dev;
	struct state	*next;
};

static inline const char *my_inet_ntoa(__u32 addr)
{
	struct in_addr a;

	a.s_addr = addr;

	return inet_ntoa(a);
}

static void print_device_config(struct netdev *dev)
{
	printf("IP-Config: %s complete (from %s):\n", dev->name,
		my_inet_ntoa(dev->serverid ? dev->serverid : dev->ip_server));
	printf(" address: %-16s ", my_inet_ntoa(dev->ip_addr));
	printf("broadcast: %-16s ", my_inet_ntoa(dev->ip_broadcast));
	printf("netmask: %-16s\n", my_inet_ntoa(dev->ip_netmask));
	printf(" gateway: %-16s ", my_inet_ntoa(dev->ip_gateway));
	printf("dns0     : %-16s ", my_inet_ntoa(dev->ip_nameserver[0]));
	printf("dns1   : %-16s\n", my_inet_ntoa(dev->ip_nameserver[1]));
	if (dev->hostname[0])
		printf(" host   : %-64s\n", dev->hostname);
	if (dev->dnsdomainname[0])
		printf(" domain : %-64s\n", dev->dnsdomainname);
	if (dev->nisdomainname[0])
		printf(" nisdomain: %-64s\n", dev->nisdomainname);
	printf(" rootserver: %s ", my_inet_ntoa(dev->ip_server));
	printf("rootpath: %s\n", dev->bootpath);
}

static void configure_device(struct netdev *dev)
{
	if (do_not_config)
		return;

	if (netdev_setmtu(dev))
		printf("IP-Config: failed to set MTU on %s to %u\n",
		       dev->name, dev->mtu);

	if (netdev_setaddress(dev))
		printf("IP-Config: failed to set addresses on %s\n", dev->name);
	if (netdev_setdefaultroute(dev))
		printf("IP-Config: failed to set default route on %s\n", dev->name);
}

static void dump_device_config(struct netdev *dev)
{
	char fn[40];
	FILE *f;

	snprintf(fn, sizeof(fn), "/tmp/net-%s.conf", dev->name);
	f = fopen(fn, "w");
	if (f) {
		fprintf(f, "DEVICE=%s\n", dev->name);
		fprintf(f, "IPV4ADDR=%s\n", my_inet_ntoa(dev->ip_addr));
		fprintf(f, "IPV4BROADCAST=%s\n", my_inet_ntoa(dev->ip_broadcast));
		fprintf(f, "IPV4NETMASK=%s\n", my_inet_ntoa(dev->ip_netmask));
		fprintf(f, "IPV4GATEWAY=%s\n", my_inet_ntoa(dev->ip_gateway));
		fprintf(f, "IPV4DNS0=%s\n", my_inet_ntoa(dev->ip_nameserver[0]));
		fprintf(f, "IPV4DNS1=%s\n", my_inet_ntoa(dev->ip_nameserver[1]));
		fprintf(f, "HOSTNAME=%s\n", dev->hostname);
		fprintf(f, "DNSDOMAIN=%s\n", dev->dnsdomainname);
		fprintf(f, "NISDOMAIN=%s\n", dev->nisdomainname);
		fprintf(f, "ROOTSERVER=%s\n", my_inet_ntoa(dev->ip_server));
		fprintf(f, "ROOTPATH=%s\n", dev->bootpath);
		fclose(f);
	}
}

static __u32 inet_class_netmask(__u32 ip)
{
	ip = ntohl(ip);
	if (IN_CLASSA(ip))
		return htonl(IN_CLASSA_NET);
	if (IN_CLASSB(ip))
		return htonl(IN_CLASSB_NET);
	if (IN_CLASSC(ip))
		return htonl(IN_CLASSC_NET);
	return INADDR_ANY;
}

static void postprocess_device(struct netdev *dev)
{
	if (dev->ip_netmask == INADDR_ANY) {
		dev->ip_netmask = inet_class_netmask(dev->ip_addr);
		printf("IP-Config: %s guessed netmask %s\n",
			dev->name, my_inet_ntoa(dev->ip_netmask));
	}
	if (dev->ip_broadcast == INADDR_ANY) {
		dev->ip_broadcast = (dev->ip_addr & dev->ip_netmask) | ~dev->ip_netmask;
		printf("IP-Config: %s guessed broadcast address %s\n",
			dev->name, my_inet_ntoa(dev->ip_broadcast));
	}
	if (dev->ip_nameserver[0] == INADDR_ANY) {
		dev->ip_nameserver[0] = dev->ip_server;
		printf("IP-Config: %s guessed nameserver address %s\n",
			dev->name, my_inet_ntoa(dev->ip_nameserver[0]));
	}
}

static void complete_device(struct netdev *dev)
{
	postprocess_device(dev);
	configure_device(dev);
	dump_device_config(dev);
	print_device_config(dev);

	++configured;

	dev->next = ifaces;
	ifaces = dev;
}

static int process_receive_event(struct state *s, time_t now)
{
	int handled = 1;

	switch (s->state) {
	case DEVST_BOOTP:
		s->restart_state = DEVST_BOOTP;
		switch (bootp_recv_reply(s->dev)) {
		case -1:
			s->state = DEVST_ERROR;
			break;
		case 1:
			s->state = DEVST_COMPLETE;
			DEBUG(("\n   bootp reply\n"));
			break;
		}
		break;

	case DEVST_DHCPDISC:
		s->restart_state = DEVST_DHCPDISC;
		switch (dhcp_recv_offer(s->dev)) {
		case -1:
			s->state = DEVST_ERROR;
			break;
		case 1: /* Offer received */
			s->state = DEVST_DHCPREQ;
			dhcp_send_request(s->dev);
			break;
		}
		break;

	case DEVST_DHCPREQ:
		s->restart_state = DEVST_DHCPDISC;
		switch (dhcp_recv_ack(s->dev)) {
		case -1: /* error */
			s->state = DEVST_ERROR;
			break;
		case 1:	/* ACK received */
			s->state = DEVST_COMPLETE;
			break;
		case 2:	/* NAK received */
			s->state = DEVST_DHCPDISC;
			break;
		}
		break;
	}

	switch (s->state) {
	case DEVST_COMPLETE:
		complete_device(s->dev);
		break;

	case DEVST_ERROR:
		/* error occurred, try again in 10 seconds */
		s->expire = now + 10;
	default:
		DEBUG(("\n"));
		handled = 0;
		break;
	}

	return handled;
}

static void process_timeout_event(struct state *s, time_t now)
{
	int ret = 0;

	/*
	 * Is the link up?  If not, try again in 1 second.
	 */
	if (!netdev_running(s->dev)) {
		s->expire = now + 1;
		s->state = s->restart_state;
		return;
	}

	/*
	 * If we had an error, restore a sane state to
	 * restart from.
	 */
	if (s->state == DEVST_ERROR)
		s->state = s->restart_state;

	/*
	 * Now send a packet depending on our state.
	 */
	switch (s->state) {
	case DEVST_BOOTP:
		ret = bootp_send_request(s->dev);
		s->restart_state = DEVST_BOOTP;
		break;

	case DEVST_DHCPDISC:
		ret = dhcp_send_discover(s->dev);
		s->restart_state = DEVST_DHCPDISC;
		break;

	case DEVST_DHCPREQ:
		ret = dhcp_send_request(s->dev);
		s->restart_state = DEVST_DHCPDISC;
		break;
	}

	if (ret == -1) {
		s->state = DEVST_ERROR;
		s->expire = now + 10;
	} else {
		s->expire = now + s->retry_period;

		s->retry_period *= 2;
		if (s->retry_period > 60)
			s->retry_period = 60;
	}
}

static struct state *slist;
struct netdev *ifaces;

static int do_pkt_recv(int pkt_fd, time_t now)
{
	int ifindex, ret;
	struct state *s;

	ret = packet_peek(&ifindex);
	if (ret < 0)
		goto bail;

	for (s = slist; s; s = s->next) {
		if (s->dev->ifindex == ifindex) {
			ret |= process_receive_event(s, now);
			break;
		}
	}

 bail:
	return ret;
}

static int loop(void)
{
#define NR_FDS	1
	struct pollfd fds[NR_FDS];
	struct state *s;
	int pkt_fd;
	int nr = 0;
	struct timeval now, prev;
	time_t start;

	pkt_fd = packet_open();
	if (pkt_fd == -1) {
		perror("packet_open");
		return -1;
	}

	fds[0].fd = pkt_fd;
	fds[0].events = POLLRDNORM;

	gettimeofday(&now, NULL);
	start = now.tv_sec;
	while (1) {
		int timeout = 60;
		int pending = 0;
		int timeout_ms;
		int x;

		for (s = slist; s; s = s->next) {
			if (s->state == DEVST_COMPLETE)
				continue;

			pending++;

			if (s->expire - now.tv_sec <= 0)
				process_timeout_event(s, now.tv_sec);

			if (timeout > s->expire - now.tv_sec)
				timeout = s->expire - now.tv_sec;
		}

		if (pending == 0)
			break;

		timeout_ms = timeout * 1000;

		for (x = 0; x < 2; x++) {
			int delta_ms;

			if (timeout_ms <= 0)
				timeout_ms = 100;

			nr = poll(fds, NR_FDS, timeout_ms);
			prev = now;
			gettimeofday(&now, NULL);

			if ((fds[0].revents & POLLRDNORM)) {
				nr = do_pkt_recv(pkt_fd, now.tv_sec);
				if (nr == 1)
					break;
				else if (nr == 0)
					packet_discard();
			}

			if (loop_timeout >= 0 &&
			    now.tv_sec - start >= loop_timeout) {
				printf("IP-Config: no response after %d "
				       "secs - giving up\n", loop_timeout);
				goto bail;
			}

			delta_ms = (now.tv_sec - prev.tv_sec) * 1000;
			delta_ms += (now.tv_usec - prev.tv_usec) / 1000;

			DEBUG(("Delta: %d ms\n", delta_ms));

			timeout_ms -= delta_ms;
		}
	}
 bail:
	packet_close();

	return 0;
}

static int add_one_dev(struct netdev *dev)
{
	struct state *state;

	state = malloc(sizeof(struct state));
	if (!state)
		return -1;

	state->dev = dev;
	state->expire = time(NULL);
	state->retry_period = 1;

	/*
	 * Select the state that we start from.
	 */
	if (dev->caps & CAP_DHCP && dev->ip_addr == INADDR_ANY) {
		state->restart_state = state->state = DEVST_DHCPDISC;
	} else if (dev->caps & CAP_DHCP) {
		state->restart_state = state->state = DEVST_DHCPREQ;
	} else if (dev->caps & CAP_BOOTP) {
		state->restart_state = state->state = DEVST_BOOTP;
	}

	state->next = slist;
	slist = state;

	return 0;
}

static void parse_addr(__u32 *addr, const char *ip)
{
	struct in_addr in;
	if (inet_aton(ip, &in) == 0) {
		fprintf(stderr, "%s: can't parse IP address '%s'\n",
			progname, ip);
		exit(1);
	}
	*addr = in.s_addr;
}

static unsigned int parse_proto(const char *ip)
{
	unsigned int caps = 0;

	if (*ip == '\0' || strcmp(ip, "on") == 0 || strcmp(ip, "any") == 0)
		caps = CAP_BOOTP | CAP_DHCP | CAP_RARP;
	else if (strcmp(ip, "dhcp") == 0)
		caps = CAP_BOOTP | CAP_DHCP;
	else if (strcmp(ip, "bootp") == 0)
		caps = CAP_BOOTP;
	else if (strcmp(ip, "rarp") == 0)
		caps = CAP_RARP;
	else if (strcmp(ip, "none") == 0 || strcmp(ip, "static") == 0)
		goto bail;
	else {
		fprintf(stderr, "%s: invalid protocol '%s'\n",
			progname, ip);
		exit(1);
	}
 bail:
	return caps;
}

static void bringup_device(struct netdev *dev)
{
	if (netdev_up(dev) == 0) {
		if (dev->caps) {
			add_one_dev(dev);
		} else {
			complete_device(dev);
		}
	}
}

static struct netdev *add_device(const char *info);

static void add_all_devices(struct netdev *template)
{
#define MAX_IFS 128
	struct ifreq ifr[MAX_IFS];
	struct ifconf ifc;
	int fd, nif, i;

	fd = packet_open();

	ifc.ifc_len = sizeof(ifr);
	ifc.ifc_req = ifr;

	if (ioctl(fd, SIOCGIFCONF, &ifc) == -1) {
		perror("SIOCGIFCONF");
		exit(1);
	}
	nif = ifc.ifc_len / sizeof(ifr[0]);

	for (i = 0; i < nif; i++) {
		struct netdev *dev;

		if (strcmp(ifr[i].ifr_name, "lo") == 0)
			continue;
		if ((dev = add_device(ifr[i].ifr_name)) == NULL)
			continue;

		if (template->ip_addr != INADDR_NONE)
			dev->ip_addr = template->ip_addr;
		if (template->ip_server != INADDR_NONE)
			dev->ip_server = template->ip_server;
		if (template->ip_gateway != INADDR_NONE)
			dev->ip_gateway = template->ip_gateway;
		if (template->ip_nameserver[0] != INADDR_NONE)
			dev->ip_nameserver[0] = template->ip_nameserver[0];
		if (template->ip_nameserver[1] != INADDR_NONE)
			dev->ip_nameserver[1] = template->ip_nameserver[1];
		if (template->hostname[0] != '\0')
			strcpy(dev->hostname, template->hostname);
		dev->caps &= template->caps;

		bringup_device(dev);
	}
}

static int parse_device(struct netdev *dev, const char *ip)
{
	char *cp;
	int i, opt;

	if (strncmp(ip, "ip=", 3) == 0) {
		ip += 3;
	}
	else if (strncmp(ip, "nfsaddrs=", 9) == 0) {
		ip += 9;
	}

	if (strchr(ip, ':') == NULL) {
		dev->name = ip;
		goto done;
	}

	for (i = opt = 0; ip && *ip; ip = cp, opt++) {
		if ((cp = strchr(ip, ':'))) {
			*cp++ = '\0';
		}
		if (opt > 6) {
			fprintf(stderr, "%s: too many options for %s\n",
				progname, dev->name);
			exit(1);
		}

		if (*ip == '\0')
			continue;
		DEBUG(("IP-Config: opt #%d: '%s'\n", opt, ip));
		switch (opt) {
		case 0:
			parse_addr(&dev->ip_addr, ip);
			break;
		case 1:
			parse_addr(&dev->ip_server, ip);
			break;
		case 2:
			parse_addr(&dev->ip_gateway, ip);
			break;
		case 3:
			parse_addr(&dev->ip_netmask, ip);
			break;
		case 4:
			strncpy(dev->hostname, ip, SYS_NMLN - 1);
			dev->hostname[SYS_NMLN - 1] = '\0';
			break;
		case 5:
			dev->name = ip;
			break;
		case 6:
			dev->caps = parse_proto(ip);
			break;
		}
	}
 done:
	if (dev->name == NULL ||
	    dev->name[0] == '\0' ||
	    strcmp(dev->name, "all") == 0) {
		add_all_devices(dev);
		return 0;
	}
	return 1;
}

static struct netdev *add_device(const char *info)
{
	struct netdev *dev;
	int i;

	dev = malloc(sizeof(struct netdev));
	if (dev == NULL) {
		fprintf(stderr, "%s: out of memory\n", progname);
		exit(1);
	}

	memset(dev, 0, sizeof(struct netdev));
	dev->caps = default_caps;

	if (parse_device(dev, info) == 0)
		goto bail;

	if (netdev_init_if(dev) == -1)
		goto bail;

	if (bootp_init_if(dev) == -1)
		goto bail;

	printf("IP-Config: %s hardware address", dev->name);
	for (i = 0; i < dev->hwlen; i++)
		printf("%c%02x", i == 0 ? ' ' : ':', dev->hwaddr[i]);
	printf(" mtu %d%s%s\n", dev->mtu,
		dev->caps & CAP_DHCP  ? " DHCP"  :
		dev->caps & CAP_BOOTP ? " BOOTP" : "",
	       dev->caps & CAP_RARP  ? " RARP"  : "");
	return dev;
 bail:
	free(dev);
	return NULL;
}

static int check_autoconfig(void)
{
	int ndev = 0, nauto = 0;
	struct state *s;

	for (s = slist; s; s = s->next) {
		ndev++;
		if (s->dev->caps)
			nauto++;
	}

	if (ndev == 0) {
		if (configured == 0) {
			fprintf(stderr, "%s: no devices to configure\n",
				progname);
			exit(1);
		}
	}

	return nauto;
}

int main(int argc, char *argv[])
	__attribute__ ((weak, alias ("ipconfig_main")));

int ipconfig_main(int argc, char *argv[])
{
	struct netdev *dev;
	struct timeval now;
	int c, port;

	progname = argv[0];

	gettimeofday(&now, NULL);
	srand48(now.tv_usec ^ (now.tv_sec << 24));

	do {
		c = getopt(argc, argv, "c:d:np:t:");
		if (c == EOF)
			break;

		switch (c) {
		case 'c':
			default_caps = parse_proto(optarg);
			break;
		case 'p':
			port = atoi(optarg);
			if (port <= 0 || port > USHRT_MAX) {
				fprintf(stderr,
					"%s: invalid port number %d\n",
					progname, port);
				exit(1);
			}
			cfg_local_port = port;
			cfg_remote_port = cfg_local_port - 1;
			break;
		case 't':
			loop_timeout = atoi(optarg);
			if (loop_timeout < 0) {
				fprintf(stderr,
					"%s: invalid timeout %d\n",
					progname, loop_timeout);
				exit(1);
			}
			break;
		case 'n':
			do_not_config = 1;
			break;
		case 'd':
			dev = add_device(optarg);
			if (dev)
				bringup_device(dev);
			break;
		case '?':
			fprintf(stderr, "%s: invalid option -%c\n",
				progname, optopt);
			exit(1);
		}
	} while (1);

	for (c = optind; c < argc; c++) {
		dev = add_device(argv[c]);
		if (dev)
			bringup_device(dev);
	}

	if (check_autoconfig()) {
		if (cfg_local_port != LOCAL_PORT) {
			printf("IP-Config: binding source port to %d, "
			       "dest to %d\n",
			       cfg_local_port,
			       cfg_remote_port);
		}
		loop();
	}

	return 0;
}
