/* vi: set sw=4 ts=4: */
/*
 * Licensed under GPLv2 or later, see file LICENSE in this source tree.
 *
 * Authors: Alexey Kuznetsov, <kuznet@ms2.inr.ac.ru>
 *
 * Bernhard Reutner-Fischer adjusted for busybox
 */

//usage:#define tc_trivial_usage
/* //usage: "[OPTIONS] OBJECT CMD [dev STRING]" */
//usage:	"OBJECT CMD [dev STRING]"
//usage:#define tc_full_usage "\n\n"
//usage:	"OBJECT: {qdisc|class|filter}\n"
//usage:	"CMD: {add|del|change|replace|show}\n"
//usage:	"\n"
//usage:	"qdisc [ handle QHANDLE ] [ root |"IF_FEATURE_TC_INGRESS(" ingress |")" parent CLASSID ]\n"
/* //usage: "[ estimator INTERVAL TIME_CONSTANT ]\n" */
//usage:	"	[ [ QDISC_KIND ] [ help | OPTIONS ] ]\n"
//usage:	"	QDISC_KIND := { [p|b]fifo | tbf | prio | cbq | red | etc. }\n"
//usage:	"qdisc show [ dev STRING ]"IF_FEATURE_TC_INGRESS(" [ingress]")"\n"
//usage:	"class [ classid CLASSID ] [ root | parent CLASSID ]\n"
//usage:	"	[ [ QDISC_KIND ] [ help | OPTIONS ] ]\n"
//usage:	"class show [ dev STRING ] [ root | parent CLASSID ]\n"
//usage:	"filter [ pref PRIO ] [ protocol PROTO ]\n"
/* //usage: "\t[ estimator INTERVAL TIME_CONSTANT ]\n" */
//usage:	"	[ root | classid CLASSID ] [ handle FILTERID ]\n"
//usage:	"	[ [ FILTER_TYPE ] [ help | OPTIONS ] ]\n"
//usage:	"filter show [ dev STRING ] [ root | parent CLASSID ]"

#include "libbb.h"

#include "libiproute/utils.h"
#include "libiproute/ip_common.h"
#include "libiproute/rt_names.h"
#include <linux/pkt_sched.h> /* for the TC_H_* macros */

#define parse_rtattr_nested(tb, max, rta) \
	(parse_rtattr((tb), (max), RTA_DATA(rta), RTA_PAYLOAD(rta)))

/* nullifies tb on error */
#define __parse_rtattr_nested_compat(tb, max, rta, len) \
	({if ((RTA_PAYLOAD(rta) >= len) && \
		 (RTA_PAYLOAD(rta) >= RTA_ALIGN(len) + sizeof(struct rtattr))) { \
			rta = RTA_DATA(rta) + RTA_ALIGN(len); \
			parse_rtattr_nested(tb, max, rta); \
	  } else \
			memset(tb, 0, sizeof(struct rtattr *) * (max + 1)); \
	})

#define parse_rtattr_nested_compat(tb, max, rta, data, len) \
	({data = RTA_PAYLOAD(rta) >= len ? RTA_DATA(rta) : NULL; \
	__parse_rtattr_nested_compat(tb, max, rta, len); })

#define show_details (0) /* not implemented. Does anyone need it? */
#define use_iec (0) /* not currently documented in the upstream manpage */


struct globals {
	int filter_ifindex;
	uint32_t filter_qdisc;
	uint32_t filter_parent;
	uint32_t filter_prio;
	uint32_t filter_proto;
} FIX_ALIASING;
#define G (*(struct globals*)&bb_common_bufsiz1)
struct BUG_G_too_big {
        char BUG_G_too_big[sizeof(G) <= COMMON_BUFSIZE ? 1 : -1];
};
#define filter_ifindex (G.filter_ifindex)
#define filter_qdisc (G.filter_qdisc)
#define filter_parent (G.filter_parent)
#define filter_prio (G.filter_prio)
#define filter_proto (G.filter_proto)
#define INIT_G() do { } while (0)

/* Allocates a buffer containing the name of a class id.
 * The caller must free the returned memory.  */
static char* print_tc_classid(uint32_t cid)
{
#if 0 /* IMPOSSIBLE */
	if (cid == TC_H_ROOT)
		return xasprintf("root");
	else
#endif
	if (cid == TC_H_UNSPEC)
		return xasprintf("none");
	else if (TC_H_MAJ(cid) == 0)
		return xasprintf(":%x", TC_H_MIN(cid));
	else if (TC_H_MIN(cid) == 0)
		return xasprintf("%x:", TC_H_MAJ(cid)>>16);
	else
		return xasprintf("%x:%x", TC_H_MAJ(cid)>>16, TC_H_MIN(cid));
}

/* Get a qdisc handle.  Return 0 on success, !0 otherwise.  */
static int get_qdisc_handle(uint32_t *h, const char *str) {
	uint32_t maj;
	char *p;

	maj = TC_H_UNSPEC;
	if (!strcmp(str, "none"))
		goto ok;
	maj = strtoul(str, &p, 16);
	if (p == str)
		return 1;
	maj <<= 16;
	if (*p != ':' && *p != '\0')
		return 1;
 ok:
	*h = maj;
	return 0;
}

/* Get class ID.  Return 0 on success, !0 otherwise.  */
static int get_tc_classid(uint32_t *h, const char *str) {
	uint32_t maj, min;
	char *p;

	maj = TC_H_ROOT;
	if (!strcmp(str, "root"))
		goto ok;
	maj = TC_H_UNSPEC;
	if (!strcmp(str, "none"))
		goto ok;
	maj = strtoul(str, &p, 16);
	if (p == str) {
		if (*p != ':')
			return 1;
		maj = 0;
	}
	if (*p == ':') {
		if (maj >= (1<<16))
			return 1;
		maj <<= 16;
		str = p + 1;
		min = strtoul(str, &p, 16);
//FIXME: check for "" too?
		if (*p != '\0' || min >= (1<<16))
			return 1;
		maj |= min;
	} else if (*p != 0)
		return 1;
 ok:
	*h = maj;
	return 0;
}

static void print_rate(char *buf, int len, uint32_t rate)
{
	double tmp = (double)rate*8;

	if (use_iec) {
		if (tmp >= 1000.0*1024.0*1024.0)
			snprintf(buf, len, "%.0fMibit", tmp/1024.0*1024.0);
		else if (tmp >= 1000.0*1024)
			snprintf(buf, len, "%.0fKibit", tmp/1024);
		else
			snprintf(buf, len, "%.0fbit", tmp);
	} else {
		if (tmp >= 1000.0*1000000.0)
			snprintf(buf, len, "%.0fMbit", tmp/1000000.0);
		else if (tmp >= 1000.0 * 1000.0)
			snprintf(buf, len, "%.0fKbit", tmp/1000.0);
		else
			snprintf(buf, len, "%.0fbit",  tmp);
	}
}

/* This is "pfifo_fast".  */
static int prio_parse_opt(int argc, char **argv, struct nlmsghdr *n)
{
	return 0;
}
static int prio_print_opt(struct rtattr *opt)
{
	int i;
	struct tc_prio_qopt *qopt;
	struct rtattr *tb[TCA_PRIO_MAX+1];

	if (opt == NULL)
		return 0;
	parse_rtattr_nested_compat(tb, TCA_PRIO_MAX, opt, qopt, sizeof(*qopt));
	if (tb == NULL)
		return 0;
	printf("bands %u priomap ", qopt->bands);
	for (i=0; i<=TC_PRIO_MAX; i++)
		printf(" %d", qopt->priomap[i]);

	if (tb[TCA_PRIO_MQ])
		printf(" multiqueue: o%s ",
		    *(unsigned char *)RTA_DATA(tb[TCA_PRIO_MQ]) ? "n" : "ff");

	return 0;
}

/* Class Based Queue */
static int cbq_parse_opt(int argc, char **argv, struct nlmsghdr *n)
{
	return 0;
}
static int cbq_print_opt(struct rtattr *opt)
{
	struct rtattr *tb[TCA_CBQ_MAX+1];
	struct tc_ratespec *r = NULL;
	struct tc_cbq_lssopt *lss = NULL;
	struct tc_cbq_wrropt *wrr = NULL;
	struct tc_cbq_fopt *fopt = NULL;
	struct tc_cbq_ovl *ovl = NULL;
	const char *const error = "CBQ: too short %s opt";
	char buf[64];

	if (opt == NULL)
		goto done;
	parse_rtattr_nested(tb, TCA_CBQ_MAX, opt);

	if (tb[TCA_CBQ_RATE]) {
		if (RTA_PAYLOAD(tb[TCA_CBQ_RATE]) < sizeof(*r))
			bb_error_msg(error, "rate");
		else
			r = RTA_DATA(tb[TCA_CBQ_RATE]);
	}
	if (tb[TCA_CBQ_LSSOPT]) {
		if (RTA_PAYLOAD(tb[TCA_CBQ_LSSOPT]) < sizeof(*lss))
			bb_error_msg(error, "lss");
		else
			lss = RTA_DATA(tb[TCA_CBQ_LSSOPT]);
	}
	if (tb[TCA_CBQ_WRROPT]) {
		if (RTA_PAYLOAD(tb[TCA_CBQ_WRROPT]) < sizeof(*wrr))
			bb_error_msg(error, "wrr");
		else
			wrr = RTA_DATA(tb[TCA_CBQ_WRROPT]);
	}
	if (tb[TCA_CBQ_FOPT]) {
		if (RTA_PAYLOAD(tb[TCA_CBQ_FOPT]) < sizeof(*fopt))
			bb_error_msg(error, "fopt");
		else
			fopt = RTA_DATA(tb[TCA_CBQ_FOPT]);
	}
	if (tb[TCA_CBQ_OVL_STRATEGY]) {
		if (RTA_PAYLOAD(tb[TCA_CBQ_OVL_STRATEGY]) < sizeof(*ovl))
			bb_error_msg("CBQ: too short overlimit strategy %u/%u",
				(unsigned) RTA_PAYLOAD(tb[TCA_CBQ_OVL_STRATEGY]),
				(unsigned) sizeof(*ovl));
		else
			ovl = RTA_DATA(tb[TCA_CBQ_OVL_STRATEGY]);
	}

	if (r) {
		print_rate(buf, sizeof(buf), r->rate);
		printf("rate %s ", buf);
		if (show_details) {
			printf("cell %ub ", 1<<r->cell_log);
			if (r->mpu)
				printf("mpu %ub ", r->mpu);
			if (r->overhead)
				printf("overhead %ub ", r->overhead);
		}
	}
	if (lss && lss->flags) {
		bool comma = false;
		bb_putchar('(');
		if (lss->flags&TCF_CBQ_LSS_BOUNDED) {
			printf("bounded");
			comma = true;
		}
		if (lss->flags&TCF_CBQ_LSS_ISOLATED) {
			if (comma)
				bb_putchar(',');
			printf("isolated");
		}
		printf(") ");
	}
	if (wrr) {
		if (wrr->priority != TC_CBQ_MAXPRIO)
			printf("prio %u", wrr->priority);
		else
			printf("prio no-transmit");
		if (show_details) {
			printf("/%u ", wrr->cpriority);
			if (wrr->weight != 1) {
				print_rate(buf, sizeof(buf), wrr->weight);
				printf("weight %s ", buf);
			}
			if (wrr->allot)
				printf("allot %ub ", wrr->allot);
		}
	}
 done:
	return 0;
}

static int print_qdisc(const struct sockaddr_nl *who UNUSED_PARAM,
						struct nlmsghdr *hdr, void *arg UNUSED_PARAM)
{
	struct tcmsg *msg = NLMSG_DATA(hdr);
	int len = hdr->nlmsg_len;
	struct rtattr * tb[TCA_MAX+1];
	char *name;

	if (hdr->nlmsg_type != RTM_NEWQDISC && hdr->nlmsg_type != RTM_DELQDISC) {
		/* bb_error_msg("not a qdisc"); */
		return 0; /* ??? mimic upstream; should perhaps return -1 */
	}
	len -= NLMSG_LENGTH(sizeof(*msg));
	if (len < 0) {
		/* bb_error_msg("wrong len %d", len); */
		return -1;
	}
	/* not the desired interface? */
	if (filter_ifindex && filter_ifindex != msg->tcm_ifindex)
		return 0;
	memset (tb, 0, sizeof(tb));
	parse_rtattr(tb, TCA_MAX, TCA_RTA(msg), len);
	if (tb[TCA_KIND] == NULL) {
		/* bb_error_msg("%s: NULL kind", "qdisc"); */
		return -1;
	}
	if (hdr->nlmsg_type == RTM_DELQDISC)
		printf("deleted ");
	name = (char*)RTA_DATA(tb[TCA_KIND]);
	printf("qdisc %s %x: ", name, msg->tcm_handle>>16);
	if (filter_ifindex == 0)
		printf("dev %s ", ll_index_to_name(msg->tcm_ifindex));
	if (msg->tcm_parent == TC_H_ROOT)
		printf("root ");
	else if (msg->tcm_parent) {
		char *classid = print_tc_classid(msg->tcm_parent);
		printf("parent %s ", classid);
		if (ENABLE_FEATURE_CLEAN_UP)
			free(classid);
	}
	if (msg->tcm_info != 1)
		printf("refcnt %d ", msg->tcm_info);
	if (tb[TCA_OPTIONS]) {
		static const char _q_[] ALIGN1 = "pfifo_fast\0""cbq\0";
		int qqq = index_in_strings(_q_, name);
		if (qqq == 0) { /* pfifo_fast aka prio */
			prio_print_opt(tb[TCA_OPTIONS]);
		} else if (qqq == 1) { /* class based queuing */
			cbq_print_opt(tb[TCA_OPTIONS]);
		} else
			bb_error_msg("unknown %s", name);
	}
	bb_putchar('\n');
	return 0;
}

static int print_class(const struct sockaddr_nl *who UNUSED_PARAM,
						struct nlmsghdr *hdr, void *arg UNUSED_PARAM)
{
	struct tcmsg *msg = NLMSG_DATA(hdr);
	int len = hdr->nlmsg_len;
	struct rtattr * tb[TCA_MAX+1];
	char *name, *classid;

	/*XXX Eventually factor out common code */

	if (hdr->nlmsg_type != RTM_NEWTCLASS && hdr->nlmsg_type != RTM_DELTCLASS) {
		/* bb_error_msg("not a class"); */
		return 0; /* ??? mimic upstream; should perhaps return -1 */
	}
	len -= NLMSG_LENGTH(sizeof(*msg));
	if (len < 0) {
		/* bb_error_msg("wrong len %d", len); */
		return -1;
	}
	/* not the desired interface? */
	if (filter_qdisc && TC_H_MAJ(msg->tcm_handle^filter_qdisc))
		return 0;
	memset (tb, 0, sizeof(tb));
	parse_rtattr(tb, TCA_MAX, TCA_RTA(msg), len);
	if (tb[TCA_KIND] == NULL) {
		/* bb_error_msg("%s: NULL kind", "class"); */
		return -1;
	}
	if (hdr->nlmsg_type == RTM_DELTCLASS)
		printf("deleted ");

	name = (char*)RTA_DATA(tb[TCA_KIND]);
	classid = !msg->tcm_handle ? NULL : print_tc_classid(
				filter_qdisc ? TC_H_MIN(msg->tcm_parent) : msg->tcm_parent);
	printf ("class %s %s", name, classid);
	if (ENABLE_FEATURE_CLEAN_UP)
		free(classid);

	if (filter_ifindex == 0)
		printf("dev %s ", ll_index_to_name(msg->tcm_ifindex));
	if (msg->tcm_parent == TC_H_ROOT)
		printf("root ");
	else if (msg->tcm_parent) {
		classid = print_tc_classid(filter_qdisc ?
								   TC_H_MIN(msg->tcm_parent) : msg->tcm_parent);
		printf("parent %s ", classid);
		if (ENABLE_FEATURE_CLEAN_UP)
			free(classid);
	}
	if (msg->tcm_info)
		printf("leaf %x ", msg->tcm_info >> 16);
	/* Do that get_qdisc_kind(RTA_DATA(tb[TCA_KIND])).  */
	if (tb[TCA_OPTIONS]) {
		static const char _q_[] ALIGN1 = "pfifo_fast\0""cbq\0";
		int qqq = index_in_strings(_q_, name);
		if (qqq == 0) { /* pfifo_fast aka prio */
			/* nothing. */ /*prio_print_opt(tb[TCA_OPTIONS]);*/
		} else if (qqq == 1) { /* class based queuing */
			/* cbq_print_copt() is identical to cbq_print_opt(). */
			cbq_print_opt(tb[TCA_OPTIONS]);
		} else
			bb_error_msg("unknown %s", name);
	}
	bb_putchar('\n');

	return 0;
}

static int print_filter(const struct sockaddr_nl *who UNUSED_PARAM,
						struct nlmsghdr *hdr, void *arg UNUSED_PARAM)
{
	struct tcmsg *msg = NLMSG_DATA(hdr);
	int len = hdr->nlmsg_len;
	struct rtattr * tb[TCA_MAX+1];
	return 0;
}

int tc_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE;
int tc_main(int argc UNUSED_PARAM, char **argv)
{
	static const char objects[] ALIGN1 =
		"qdisc\0""class\0""filter\0"
		;
	enum { OBJ_qdisc = 0, OBJ_class, OBJ_filter };
	static const char commands[] ALIGN1 =
		"add\0""delete\0""change\0"
		"link\0" /* only qdisc */
		"replace\0"
		"show\0""list\0"
		;
	static const char args[] ALIGN1 =
		"dev\0" /* qdisc, class, filter */
		"root\0" /* class, filter */
		"parent\0" /* class, filter */
		"qdisc\0" /* class */
		"handle\0" /* change: qdisc, class(classid) list: filter */
		"classid\0" /* change: for class use "handle" */
		"preference\0""priority\0""protocol\0" /* filter */
		;
	enum { CMD_add = 0, CMD_del, CMD_change, CMD_link, CMD_replace, CMD_show };
	enum { ARG_dev = 0, ARG_root, ARG_parent, ARG_qdisc,
			ARG_handle, ARG_classid, ARG_pref, ARG_prio, ARG_proto};
	struct rtnl_handle rth;
	struct tcmsg msg;
	int ret, obj, cmd, arg;
	char *dev = NULL;

	INIT_G();

	if (!*++argv)
		bb_show_usage();
	xrtnl_open(&rth);
	ret = EXIT_SUCCESS;

	obj = index_in_substrings(objects, *argv++);

	if (obj < OBJ_qdisc)
		bb_show_usage();
	if (!*argv)
		cmd = CMD_show; /* list is the default */
	else {
		cmd = index_in_substrings(commands, *argv);
		if (cmd < 0)
			bb_error_msg_and_die(bb_msg_invalid_arg, *argv, applet_name);
		argv++;
	}
	memset(&msg, 0, sizeof(msg));
	msg.tcm_family = AF_UNSPEC;
	ll_init_map(&rth);
	while (*argv) {
		arg = index_in_substrings(args, *argv);
		if (arg == ARG_dev) {
			NEXT_ARG();
			if (dev)
				duparg2("dev", *argv);
			dev = *argv++;
			msg.tcm_ifindex = xll_name_to_index(dev);
			if (cmd >= CMD_show)
				filter_ifindex = msg.tcm_ifindex;
		} else
		if ((arg == ARG_qdisc && obj == OBJ_class && cmd >= CMD_show)
		 || (arg == ARG_handle && obj == OBJ_qdisc && cmd == CMD_change)
		) {
			NEXT_ARG();
			/* We don't care about duparg2("qdisc handle",*argv) for now */
			if (get_qdisc_handle(&filter_qdisc, *argv))
				invarg(*argv, "qdisc");
		} else
		if (obj != OBJ_qdisc
		 && (arg == ARG_root
		    || arg == ARG_parent
		    || (obj == OBJ_filter && arg >= ARG_pref)
		    )
		) {
			/* nothing */
		} else {
			invarg(*argv, "command");
		}
		NEXT_ARG();
		if (arg == ARG_root) {
			if (msg.tcm_parent)
				duparg("parent", *argv);
			msg.tcm_parent = TC_H_ROOT;
			if (obj == OBJ_filter)
				filter_parent = TC_H_ROOT;
		} else if (arg == ARG_parent) {
			uint32_t handle;
			if (msg.tcm_parent)
				duparg(*argv, "parent");
			if (get_tc_classid(&handle, *argv))
				invarg(*argv, "parent");
			msg.tcm_parent = handle;
			if (obj == OBJ_filter)
				filter_parent = handle;
		} else if (arg == ARG_handle) { /* filter::list */
			if (msg.tcm_handle)
				duparg(*argv, "handle");
			/* reject LONG_MIN || LONG_MAX */
			/* TODO: for fw
			   if ((slash = strchr(handle, '/')) != NULL)
				   *slash = '\0';
			 */
			msg.tcm_handle = get_u32(*argv, "handle");
			/* if (slash) {if (get_u32(uint32_t &mask, slash+1, NULL)) inv mask; addattr32(n, MAX_MSG, TCA_FW_MASK, mask); */
		} else if (arg == ARG_classid && obj == OBJ_class && cmd == CMD_change){
		} else if (arg == ARG_pref || arg == ARG_prio) { /* filter::list */
			if (filter_prio)
				duparg(*argv, "priority");
			filter_prio = get_u32(*argv, "priority");
		} else if (arg == ARG_proto) { /* filter::list */
			uint16_t tmp;
			if (filter_proto)
				duparg(*argv, "protocol");
			if (ll_proto_a2n(&tmp, *argv))
				invarg(*argv, "protocol");
			filter_proto = tmp;
		}
	}
	if (cmd >= CMD_show) { /* show or list */
		if (obj == OBJ_filter)
			msg.tcm_info = TC_H_MAKE(filter_prio<<16, filter_proto);
		if (rtnl_dump_request(&rth, obj == OBJ_qdisc ? RTM_GETQDISC :
						obj == OBJ_class ? RTM_GETTCLASS : RTM_GETTFILTER,
						&msg, sizeof(msg)) < 0)
			bb_simple_perror_msg_and_die("can't send dump request");

		xrtnl_dump_filter(&rth, obj == OBJ_qdisc ? print_qdisc :
						obj == OBJ_class ? print_class : print_filter,
						NULL);
	}
	if (ENABLE_FEATURE_CLEAN_UP) {
		rtnl_close(&rth);
	}
	return ret;
}
