/*
 * tc_class.c		"tc class".
 *
 *		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.
 *
 * Authors:	Alexey Kuznetsov, <kuznet@ms2.inr.ac.ru>
 *
 */

#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <fcntl.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <string.h>
#include <math.h>

#include "utils.h"
#include "tc_util.h"
#include "tc_common.h"
#include "list.h"

struct graph_node {
	struct hlist_node hlist;
	__u32 id;
	__u32 parent_id;
	struct graph_node *parent_node;
	struct graph_node *right_node;
	void *data;
	int data_len;
	int nodes_count;
};

static struct hlist_head cls_list = {};
static struct hlist_head root_cls_list = {};

static void usage(void);

static void usage(void)
{
	fprintf(stderr,
		"Usage: tc class [ add | del | change | replace | show ] dev STRING\n"
		"       [ classid CLASSID ] [ root | parent CLASSID ]\n"
		"       [ [ QDISC_KIND ] [ help | OPTIONS ] ]\n"
		"\n"
		"       tc class show [ dev STRING ] [ root | parent CLASSID ]\n"
		"Where:\n"
		"QDISC_KIND := { prio | cbq | etc. }\n"
		"OPTIONS := ... try tc class add <desired QDISC_KIND> help\n");
}

static int tc_class_modify(int cmd, unsigned int flags, int argc, char **argv)
{
	struct {
		struct nlmsghdr	n;
		struct tcmsg		t;
		char			buf[4096];
	} req = {
		.n.nlmsg_len = NLMSG_LENGTH(sizeof(struct tcmsg)),
		.n.nlmsg_flags = NLM_F_REQUEST | flags,
		.n.nlmsg_type = cmd,
		.t.tcm_family = AF_UNSPEC,
	};
	struct qdisc_util *q = NULL;
	struct tc_estimator est = {};
	char  d[IFNAMSIZ] = {};
	char  k[FILTER_NAMESZ] = {};

	while (argc > 0) {
		if (strcmp(*argv, "dev") == 0) {
			NEXT_ARG();
			if (d[0])
				duparg("dev", *argv);
			strncpy(d, *argv, sizeof(d)-1);
		} else if (strcmp(*argv, "classid") == 0) {
			__u32 handle;

			NEXT_ARG();
			if (req.t.tcm_handle)
				duparg("classid", *argv);
			if (get_tc_classid(&handle, *argv))
				invarg("invalid class ID", *argv);
			req.t.tcm_handle = handle;
		} else if (strcmp(*argv, "handle") == 0) {
			fprintf(stderr, "Error: try \"classid\" instead of \"handle\"\n");
			return -1;
		} else if (strcmp(*argv, "root") == 0) {
			if (req.t.tcm_parent) {
				fprintf(stderr, "Error: \"root\" is duplicate parent ID.\n");
				return -1;
			}
			req.t.tcm_parent = TC_H_ROOT;
		} else if (strcmp(*argv, "parent") == 0) {
			__u32 handle;

			NEXT_ARG();
			if (req.t.tcm_parent)
				duparg("parent", *argv);
			if (get_tc_classid(&handle, *argv))
				invarg("invalid parent ID", *argv);
			req.t.tcm_parent = handle;
		} else if (matches(*argv, "estimator") == 0) {
			if (parse_estimator(&argc, &argv, &est))
				return -1;
		} else if (matches(*argv, "help") == 0) {
			usage();
		} else {
			strncpy(k, *argv, sizeof(k)-1);

			q = get_qdisc_kind(k);
			argc--; argv++;
			break;
		}
		argc--; argv++;
	}

	if (k[0])
		addattr_l(&req.n, sizeof(req), TCA_KIND, k, strlen(k)+1);
	if (est.ewma_log)
		addattr_l(&req.n, sizeof(req), TCA_RATE, &est, sizeof(est));

	if (q) {
		if (q->parse_copt == NULL) {
			fprintf(stderr, "Error: Qdisc \"%s\" is classless.\n", k);
			return 1;
		}
		if (q->parse_copt(q, argc, argv, &req.n, d))
			return 1;
	} else {
		if (argc) {
			if (matches(*argv, "help") == 0)
				usage();
			fprintf(stderr, "Garbage instead of arguments \"%s ...\". Try \"tc class help\".", *argv);
			return -1;
		}
	}

	if (d[0])  {
		ll_init_map(&rth);

		req.t.tcm_ifindex = ll_name_to_index(d);
		if (!req.t.tcm_ifindex)
			return -nodev(d);
	}

	if (rtnl_talk(&rth, &req.n, NULL) < 0)
		return 2;

	return 0;
}

static int filter_ifindex;
static __u32 filter_qdisc;
static __u32 filter_classid;

static void graph_node_add(__u32 parent_id, __u32 id, void *data,
		int len)
{
	struct graph_node *node = calloc(1, sizeof(struct graph_node));

	node->id         = id;
	node->parent_id  = parent_id;

	if (data && len) {
		node->data       = malloc(len);
		node->data_len   = len;
		memcpy(node->data, data, len);
	}

	if (parent_id == TC_H_ROOT)
		hlist_add_head(&node->hlist, &root_cls_list);
	else
		hlist_add_head(&node->hlist, &cls_list);
}

static void graph_indent(char *buf, struct graph_node *node, int is_newline,
		int add_spaces)
{
	char spaces[100] = {0};

	while (node && node->parent_node) {
		node->parent_node->right_node = node;
		node = node->parent_node;
	}
	while (node && node->right_node) {
		if (node->hlist.next)
			strcat(buf, "|    ");
		else
			strcat(buf, "     ");

		node = node->right_node;
	}

	if (is_newline) {
		if (node->hlist.next && node->nodes_count)
			strcat(buf, "|    |");
		else if (node->hlist.next)
			strcat(buf, "|     ");
		else if (node->nodes_count)
			strcat(buf, "     |");
		else if (!node->hlist.next)
			strcat(buf, "      ");
	}
	if (add_spaces > 0) {
		sprintf(spaces, "%-*s", add_spaces, "");
		strcat(buf, spaces);
	}
}

static void graph_cls_show(FILE *fp, char *buf, struct hlist_head *root_list,
		int level)
{
	struct hlist_node *n, *tmp_cls;
	char cls_id_str[256] = {};
	struct rtattr *tb[TCA_MAX + 1];
	struct qdisc_util *q;
	char str[300] = {};

	hlist_for_each_safe(n, tmp_cls, root_list) {
		struct hlist_node *c, *tmp_chld;
		struct hlist_head children = {};
		struct graph_node *cls = container_of(n, struct graph_node,
				hlist);

		hlist_for_each_safe(c, tmp_chld, &cls_list) {
			struct graph_node *child = container_of(c,
					struct graph_node, hlist);

			if (cls->id == child->parent_id) {
				hlist_del(c);
				hlist_add_head(c, &children);
				cls->nodes_count++;
				child->parent_node = cls;
			}
		}

		graph_indent(buf, cls, 0, 0);

		print_tc_classid(cls_id_str, sizeof(cls_id_str), cls->id);
		snprintf(str, sizeof(str),
			 "+---(%s)", cls_id_str);
		strcat(buf, str);

		parse_rtattr(tb, TCA_MAX, (struct rtattr *)cls->data,
				cls->data_len);

		if (tb[TCA_KIND] == NULL) {
			strcat(buf, " [unknown qdisc kind] ");
		} else {
			const char *kind = rta_getattr_str(tb[TCA_KIND]);

			sprintf(str, " %s ", kind);
			strcat(buf, str);
			fprintf(fp, "%s", buf);
			buf[0] = '\0';

			q = get_qdisc_kind(kind);
			if (q && q->print_copt) {
				q->print_copt(q, fp, tb[TCA_OPTIONS]);
			}
			if (q && show_stats) {
				int cls_indent = strlen(q->id) - 2 +
					strlen(cls_id_str);
				struct rtattr *stats = NULL;

				graph_indent(buf, cls, 1, cls_indent);

				if (tb[TCA_STATS] || tb[TCA_STATS2]) {
					fprintf(fp, "\n");
					print_tcstats_attr(fp, tb, buf, &stats);
					buf[0] = '\0';
				}
				if (cls->hlist.next || cls->nodes_count) {
					strcat(buf, "\n");
					graph_indent(buf, cls, 1, 0);
				}
			}
		}
		free(cls->data);
		fprintf(fp, "%s\n", buf);
		buf[0] = '\0';

		graph_cls_show(fp, buf, &children, level + 1);
		if (!cls->hlist.next) {
			graph_indent(buf, cls, 0, 0);
			strcat(buf, "\n");
		}

		fprintf(fp, "%s", buf);
		buf[0] = '\0';
		free(cls);
	}
}

int print_class(struct nlmsghdr *n, void *arg)
{
	FILE *fp = (FILE *)arg;
	struct tcmsg *t = NLMSG_DATA(n);
	int len = n->nlmsg_len;
	struct rtattr *tb[TCA_MAX + 1];
	struct qdisc_util *q;
	char abuf[256];

	if (n->nlmsg_type != RTM_NEWTCLASS && n->nlmsg_type != RTM_DELTCLASS) {
		fprintf(stderr, "Not a class\n");
		return 0;
	}
	len -= NLMSG_LENGTH(sizeof(*t));
	if (len < 0) {
		fprintf(stderr, "Wrong len %d\n", len);
		return -1;
	}

	if (show_graph) {
		graph_node_add(t->tcm_parent, t->tcm_handle, TCA_RTA(t), len);
		return 0;
	}

	if (filter_qdisc && TC_H_MAJ(t->tcm_handle^filter_qdisc))
		return 0;

	if (filter_classid && t->tcm_handle != filter_classid)
		return 0;

	parse_rtattr(tb, TCA_MAX, TCA_RTA(t), len);

	if (tb[TCA_KIND] == NULL) {
		fprintf(stderr, "print_class: NULL kind\n");
		return -1;
	}

	if (n->nlmsg_type == RTM_DELTCLASS)
		fprintf(fp, "deleted ");

	abuf[0] = 0;
	if (t->tcm_handle) {
		if (filter_qdisc)
			print_tc_classid(abuf, sizeof(abuf), TC_H_MIN(t->tcm_handle));
		else
			print_tc_classid(abuf, sizeof(abuf), t->tcm_handle);
	}
	fprintf(fp, "class %s %s ", rta_getattr_str(tb[TCA_KIND]), abuf);

	if (filter_ifindex == 0)
		fprintf(fp, "dev %s ", ll_index_to_name(t->tcm_ifindex));

	if (t->tcm_parent == TC_H_ROOT)
		fprintf(fp, "root ");
	else {
		if (filter_qdisc)
			print_tc_classid(abuf, sizeof(abuf), TC_H_MIN(t->tcm_parent));
		else
			print_tc_classid(abuf, sizeof(abuf), t->tcm_parent);
		fprintf(fp, "parent %s ", abuf);
	}
	if (t->tcm_info)
		fprintf(fp, "leaf %x: ", t->tcm_info>>16);
	q = get_qdisc_kind(RTA_DATA(tb[TCA_KIND]));
	if (tb[TCA_OPTIONS]) {
		if (q && q->print_copt)
			q->print_copt(q, fp, tb[TCA_OPTIONS]);
		else
			fprintf(fp, "[cannot parse class parameters]");
	}
	fprintf(fp, "\n");
	if (show_stats) {
		struct rtattr *xstats = NULL;

		if (tb[TCA_STATS] || tb[TCA_STATS2]) {
			print_tcstats_attr(fp, tb, " ", &xstats);
			fprintf(fp, "\n");
		}
		if (q && (xstats || tb[TCA_XSTATS]) && q->print_xstats) {
			q->print_xstats(q, fp, xstats ? : tb[TCA_XSTATS]);
			fprintf(fp, "\n");
		}
	}
	fflush(fp);
	return 0;
}


static int tc_class_list(int argc, char **argv)
{
	struct tcmsg t = { .tcm_family = AF_UNSPEC };
	char d[IFNAMSIZ] = {};
	char buf[1024] = {0};

	filter_qdisc = 0;
	filter_classid = 0;

	while (argc > 0) {
		if (strcmp(*argv, "dev") == 0) {
			NEXT_ARG();
			if (d[0])
				duparg("dev", *argv);
			strncpy(d, *argv, sizeof(d)-1);
		} else if (strcmp(*argv, "qdisc") == 0) {
			NEXT_ARG();
			if (filter_qdisc)
				duparg("qdisc", *argv);
			if (get_qdisc_handle(&filter_qdisc, *argv))
				invarg("invalid qdisc ID", *argv);
		} else if (strcmp(*argv, "classid") == 0) {
			NEXT_ARG();
			if (filter_classid)
				duparg("classid", *argv);
			if (get_tc_classid(&filter_classid, *argv))
				invarg("invalid class ID", *argv);
		} else if (strcmp(*argv, "root") == 0) {
			if (t.tcm_parent) {
				fprintf(stderr, "Error: \"root\" is duplicate parent ID\n");
				return -1;
			}
			t.tcm_parent = TC_H_ROOT;
		} else if (strcmp(*argv, "parent") == 0) {
			__u32 handle;

			if (t.tcm_parent)
				duparg("parent", *argv);
			NEXT_ARG();
			if (get_tc_classid(&handle, *argv))
				invarg("invalid parent ID", *argv);
			t.tcm_parent = handle;
		} else if (matches(*argv, "help") == 0) {
			usage();
		} else {
			fprintf(stderr, "What is \"%s\"? Try \"tc class help\".\n", *argv);
			return -1;
		}

		argc--; argv++;
	}

	ll_init_map(&rth);

	if (d[0]) {
		t.tcm_ifindex = ll_name_to_index(d);
		if (!t.tcm_ifindex)
			return -nodev(d);
		filter_ifindex = t.tcm_ifindex;
	}

	if (rtnl_dump_request(&rth, RTM_GETTCLASS, &t, sizeof(t)) < 0) {
		perror("Cannot send dump request");
		return 1;
	}

	if (rtnl_dump_filter(&rth, print_class, stdout) < 0) {
		fprintf(stderr, "Dump terminated\n");
		return 1;
	}

	if (show_graph)
		graph_cls_show(stdout, &buf[0], &root_cls_list, 0);

	return 0;
}

int do_class(int argc, char **argv)
{
	if (argc < 1)
		return tc_class_list(0, NULL);
	if (matches(*argv, "add") == 0)
		return tc_class_modify(RTM_NEWTCLASS, NLM_F_EXCL|NLM_F_CREATE, argc-1, argv+1);
	if (matches(*argv, "change") == 0)
		return tc_class_modify(RTM_NEWTCLASS, 0, argc-1, argv+1);
	if (matches(*argv, "replace") == 0)
		return tc_class_modify(RTM_NEWTCLASS, NLM_F_CREATE, argc-1, argv+1);
	if (matches(*argv, "delete") == 0)
		return tc_class_modify(RTM_DELTCLASS, 0,  argc-1, argv+1);
#if 0
	if (matches(*argv, "get") == 0)
		return tc_class_get(RTM_GETTCLASS, 0,  argc-1, argv+1);
#endif
	if (matches(*argv, "list") == 0 || matches(*argv, "show") == 0
	    || matches(*argv, "lst") == 0)
		return tc_class_list(argc-1, argv+1);
	if (matches(*argv, "help") == 0) {
		usage();
		return 0;
	}
	fprintf(stderr, "Command \"%s\" is unknown, try \"tc class help\".\n", *argv);
	return -1;
}
