/*
 * ipaddress.c		"ip address".
 *
 *		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 <inttypes.h>
#include <fcntl.h>
#include <sys/ioctl.h>
#include <sys/socket.h>
#include <sys/param.h>
#include <errno.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <string.h>
#include <fnmatch.h>

#include <linux/netdevice.h>
#include <linux/if_arp.h>
#include <linux/if_infiniband.h>
#include <linux/sockios.h>
#include <linux/net_namespace.h>

#include "utils.h"
#include "rt_names.h"
#include "utils.h"
#include "ll_map.h"
#include "ip_common.h"
#include "color.h"

enum {
	IPADD_LIST,
	IPADD_FLUSH,
	IPADD_SAVE,
};

static struct link_filter filter;
static int do_link;

static void usage(void) __attribute__((noreturn));

static void usage(void)
{
	if (do_link)
		iplink_usage();

	fprintf(stderr,
		"Usage: ip address {add|change|replace} IFADDR dev IFNAME [ LIFETIME ]\n"
		"                                                      [ CONFFLAG-LIST ]\n"
		"       ip address del IFADDR dev IFNAME [mngtmpaddr]\n"
		"       ip address {save|flush} [ dev IFNAME ] [ scope SCOPE-ID ]\n"
		"                            [ to PREFIX ] [ FLAG-LIST ] [ label LABEL ] [up]\n"
		"       ip address [ show [ dev IFNAME ] [ scope SCOPE-ID ] [ master DEVICE ]\n"
		"                         [ type TYPE ] [ to PREFIX ] [ FLAG-LIST ]\n"
		"                         [ label LABEL ] [up] [ vrf NAME ] ]\n"
		"       ip address {showdump|restore}\n"
		"IFADDR := PREFIX | ADDR peer PREFIX\n"
		"          [ broadcast ADDR ] [ anycast ADDR ]\n"
		"          [ label IFNAME ] [ scope SCOPE-ID ] [ metric METRIC ]\n"
		"SCOPE-ID := [ host | link | global | NUMBER ]\n"
		"FLAG-LIST := [ FLAG-LIST ] FLAG\n"
		"FLAG  := [ permanent | dynamic | secondary | primary |\n"
		"           [-]tentative | [-]deprecated | [-]dadfailed | temporary |\n"
		"           CONFFLAG-LIST ]\n"
		"CONFFLAG-LIST := [ CONFFLAG-LIST ] CONFFLAG\n"
		"CONFFLAG  := [ home | nodad | optimistic | mngtmpaddr | noprefixroute | autojoin ]\n"
		"LIFETIME := [ valid_lft LFT ] [ preferred_lft LFT ]\n"
		"LFT := forever | SECONDS\n"
		"TYPE := { vlan | veth | vcan | vxcan | dummy | ifb | macvlan | macvtap |\n"
		"          bridge | bond | ipoib | ip6tnl | ipip | sit | vxlan | lowpan |\n"
		"          gre | gretap | erspan | ip6gre | ip6gretap | ip6erspan | vti |\n"
		"          nlmon | can | bond_slave | ipvlan | geneve | bridge_slave |\n"
		"          hsr | macsec | netdevsim }\n");

	exit(-1);
}

static void print_link_flags(FILE *fp, unsigned int flags, unsigned int mdown)
{
	open_json_array(PRINT_ANY, is_json_context() ? "flags" : "<");
	if (flags & IFF_UP && !(flags & IFF_RUNNING))
		print_string(PRINT_ANY, NULL,
			     flags ? "%s," : "%s", "NO-CARRIER");
	flags &= ~IFF_RUNNING;
#define _PF(f) if (flags&IFF_##f) {					\
		flags &= ~IFF_##f ;					\
		print_string(PRINT_ANY, NULL, flags ? "%s," : "%s", #f); }
	_PF(LOOPBACK);
	_PF(BROADCAST);
	_PF(POINTOPOINT);
	_PF(MULTICAST);
	_PF(NOARP);
	_PF(ALLMULTI);
	_PF(PROMISC);
	_PF(MASTER);
	_PF(SLAVE);
	_PF(DEBUG);
	_PF(DYNAMIC);
	_PF(AUTOMEDIA);
	_PF(PORTSEL);
	_PF(NOTRAILERS);
	_PF(UP);
	_PF(LOWER_UP);
	_PF(DORMANT);
	_PF(ECHO);
#undef _PF
	if (flags)
		print_hex(PRINT_ANY, NULL, "%x", flags);
	if (mdown)
		print_string(PRINT_ANY, NULL, ",%s", "M-DOWN");
	close_json_array(PRINT_ANY, "> ");
}

static const char *oper_states[] = {
	"UNKNOWN", "NOTPRESENT", "DOWN", "LOWERLAYERDOWN",
	"TESTING", "DORMANT",	 "UP"
};

static void print_operstate(FILE *f, __u8 state)
{
	if (state >= ARRAY_SIZE(oper_states)) {
		if (is_json_context())
			print_uint(PRINT_JSON, "operstate_index", NULL, state);
		else
			print_0xhex(PRINT_FP, NULL, "state %#llx", state);
	} else if (brief) {
		print_color_string(PRINT_ANY,
				   oper_state_color(state),
				   "operstate",
				   "%-14s ",
				   oper_states[state]);
	} else {
		if (is_json_context())
			print_string(PRINT_JSON,
				     "operstate",
				     NULL, oper_states[state]);
		else {
			fprintf(f, "state ");
			color_fprintf(f, oper_state_color(state),
				      "%s ", oper_states[state]);
		}
	}
}

int get_operstate(const char *name)
{
	int i;

	for (i = 0; i < ARRAY_SIZE(oper_states); i++)
		if (strcasecmp(name, oper_states[i]) == 0)
			return i;
	return -1;
}

static void print_queuelen(FILE *f, struct rtattr *tb[IFLA_MAX + 1])
{
	int qlen;

	if (tb[IFLA_TXQLEN])
		qlen = rta_getattr_u32(tb[IFLA_TXQLEN]);
	else {
		struct ifreq ifr = {};
		int s = socket(AF_INET, SOCK_STREAM, 0);

		if (s < 0)
			return;

		strcpy(ifr.ifr_name, rta_getattr_str(tb[IFLA_IFNAME]));
		if (ioctl(s, SIOCGIFTXQLEN, &ifr) < 0) {
			fprintf(stderr,
				"ioctl(SIOCGIFTXQLEN) failed: %s\n",
				strerror(errno));
			close(s);
			return;
		}
		close(s);
		qlen = ifr.ifr_qlen;
	}
	if (qlen)
		print_int(PRINT_ANY, "txqlen", "qlen %d", qlen);
}

static const char *link_modes[] = {
	"DEFAULT", "DORMANT"
};

static void print_linkmode(FILE *f, struct rtattr *tb)
{
	unsigned int mode = rta_getattr_u8(tb);

	if (mode >= ARRAY_SIZE(link_modes))
		print_int(PRINT_ANY,
			  "linkmode_index",
			  "mode %d ",
			  mode);
	else
		print_string(PRINT_ANY,
			     "linkmode",
			     "mode %s "
			     , link_modes[mode]);
}

static char *parse_link_kind(struct rtattr *tb, bool slave)
{
	struct rtattr *linkinfo[IFLA_INFO_MAX+1];
	int attr = slave ? IFLA_INFO_SLAVE_KIND : IFLA_INFO_KIND;

	parse_rtattr_nested(linkinfo, IFLA_INFO_MAX, tb);

	if (linkinfo[attr])
		return RTA_DATA(linkinfo[attr]);

	return "";
}

static int match_link_kind(struct rtattr **tb, const char *kind, bool slave)
{
	if (!tb[IFLA_LINKINFO])
		return -1;

	return strcmp(parse_link_kind(tb[IFLA_LINKINFO], slave), kind);
}

static void print_linktype(FILE *fp, struct rtattr *tb)
{
	struct rtattr *linkinfo[IFLA_INFO_MAX+1];
	struct link_util *lu;
	struct link_util *slave_lu;
	char slave[32];

	parse_rtattr_nested(linkinfo, IFLA_INFO_MAX, tb);
	open_json_object("linkinfo");

	if (linkinfo[IFLA_INFO_KIND]) {
		const char *kind
			= rta_getattr_str(linkinfo[IFLA_INFO_KIND]);

		print_nl();
		print_string(PRINT_ANY, "info_kind", "    %s ", kind);

		lu = get_link_kind(kind);
		if (lu && lu->print_opt) {
			struct rtattr *attr[lu->maxattr+1], **data = NULL;

			if (linkinfo[IFLA_INFO_DATA]) {
				parse_rtattr_nested(attr, lu->maxattr,
						    linkinfo[IFLA_INFO_DATA]);
				data = attr;
			}
			open_json_object("info_data");
			lu->print_opt(lu, fp, data);
			close_json_object();

			if (linkinfo[IFLA_INFO_XSTATS] && show_stats &&
			    lu->print_xstats) {
				open_json_object("info_xstats");
				lu->print_xstats(lu, fp, linkinfo[IFLA_INFO_XSTATS]);
				close_json_object();
			}
		}
	}

	if (linkinfo[IFLA_INFO_SLAVE_KIND]) {
		const char *slave_kind
			= rta_getattr_str(linkinfo[IFLA_INFO_SLAVE_KIND]);

		print_nl();
		print_string(PRINT_ANY,
			     "info_slave_kind",
			     "    %s_slave ",
			     slave_kind);

		snprintf(slave, sizeof(slave), "%s_slave", slave_kind);

		slave_lu = get_link_kind(slave);
		if (slave_lu && slave_lu->print_opt) {
			struct rtattr *attr[slave_lu->maxattr+1], **data = NULL;

			if (linkinfo[IFLA_INFO_SLAVE_DATA]) {
				parse_rtattr_nested(attr, slave_lu->maxattr,
						    linkinfo[IFLA_INFO_SLAVE_DATA]);
				data = attr;
			}
			open_json_object("info_slave_data");
			slave_lu->print_opt(slave_lu, fp, data);
			close_json_object();
		}
	}
	close_json_object();
}

static void print_af_spec(FILE *fp, struct rtattr *af_spec_attr)
{
	struct rtattr *inet6_attr;
	struct rtattr *tb[IFLA_INET6_MAX + 1];

	inet6_attr = parse_rtattr_one_nested(AF_INET6, af_spec_attr);
	if (!inet6_attr)
		return;

	parse_rtattr_nested(tb, IFLA_INET6_MAX, inet6_attr);

	if (tb[IFLA_INET6_ADDR_GEN_MODE]) {
		__u8 mode = rta_getattr_u8(tb[IFLA_INET6_ADDR_GEN_MODE]);
		SPRINT_BUF(b1);

		switch (mode) {
		case IN6_ADDR_GEN_MODE_EUI64:
			print_string(PRINT_ANY,
				     "inet6_addr_gen_mode",
				     "addrgenmode %s ",
				     "eui64");
			break;
		case IN6_ADDR_GEN_MODE_NONE:
			print_string(PRINT_ANY,
				     "inet6_addr_gen_mode",
				     "addrgenmode %s ",
				     "none");
			break;
		case IN6_ADDR_GEN_MODE_STABLE_PRIVACY:
			print_string(PRINT_ANY,
				     "inet6_addr_gen_mode",
				     "addrgenmode %s ",
				     "stable_secret");
			break;
		case IN6_ADDR_GEN_MODE_RANDOM:
			print_string(PRINT_ANY,
				     "inet6_addr_gen_mode",
				     "addrgenmode %s ",
				     "random");
			break;
		default:
			snprintf(b1, sizeof(b1), "%#.2hhx", mode);
			print_string(PRINT_ANY,
				     "inet6_addr_gen_mode",
				     "addrgenmode %s ",
				     b1);
			break;
		}
	}
}

static void print_vf_stats64(FILE *fp, struct rtattr *vfstats);

static void print_vfinfo(FILE *fp, struct ifinfomsg *ifi, struct rtattr *vfinfo)
{
	struct ifla_vf_mac *vf_mac;
	struct ifla_vf_broadcast *vf_broadcast;
	struct ifla_vf_tx_rate *vf_tx_rate;
	struct rtattr *vf[IFLA_VF_MAX + 1] = {};

	SPRINT_BUF(b1);

	if (vfinfo->rta_type != IFLA_VF_INFO) {
		fprintf(stderr, "BUG: rta type is %d\n", vfinfo->rta_type);
		return;
	}

	parse_rtattr_nested(vf, IFLA_VF_MAX, vfinfo);

	vf_mac = RTA_DATA(vf[IFLA_VF_MAC]);
	vf_broadcast = RTA_DATA(vf[IFLA_VF_BROADCAST]);
	vf_tx_rate = RTA_DATA(vf[IFLA_VF_TX_RATE]);

	print_string(PRINT_FP, NULL, "%s    ", _SL_);
	print_int(PRINT_ANY, "vf", "vf %d ", vf_mac->vf);

	print_string(PRINT_ANY,
		     "link_type",
		     "    link/%s ",
		     ll_type_n2a(ifi->ifi_type, b1, sizeof(b1)));

	print_color_string(PRINT_ANY, COLOR_MAC,
			   "address", "%s",
			   ll_addr_n2a((unsigned char *) &vf_mac->mac,
				       ifi->ifi_type == ARPHRD_ETHER ?
				       ETH_ALEN : INFINIBAND_ALEN,
				       ifi->ifi_type,
				       b1, sizeof(b1)));

	if (vf[IFLA_VF_BROADCAST]) {
		if (ifi->ifi_flags&IFF_POINTOPOINT) {
			print_string(PRINT_FP, NULL, " peer ", NULL);
			print_bool(PRINT_JSON,
				   "link_pointtopoint", NULL, true);
		} else
			print_string(PRINT_FP, NULL, " brd ", NULL);

		print_color_string(PRINT_ANY, COLOR_MAC,
				   "broadcast", "%s",
				   ll_addr_n2a((unsigned char *) &vf_broadcast->broadcast,
					       ifi->ifi_type == ARPHRD_ETHER ?
					       ETH_ALEN : INFINIBAND_ALEN,
					       ifi->ifi_type,
					       b1, sizeof(b1)));
	}

	if (vf[IFLA_VF_VLAN_LIST]) {
		struct rtattr *i, *vfvlanlist = vf[IFLA_VF_VLAN_LIST];
		int rem = RTA_PAYLOAD(vfvlanlist);

		open_json_array(PRINT_JSON, "vlan_list");
		for (i = RTA_DATA(vfvlanlist);
		     RTA_OK(i, rem); i = RTA_NEXT(i, rem)) {
			struct ifla_vf_vlan_info *vf_vlan_info = RTA_DATA(i);
			SPRINT_BUF(b2);

			open_json_object(NULL);
			if (vf_vlan_info->vlan)
				print_int(PRINT_ANY,
					  "vlan",
					  ", vlan %d",
					  vf_vlan_info->vlan);
			if (vf_vlan_info->qos)
				print_int(PRINT_ANY,
					  "qos",
					  ", qos %d",
					  vf_vlan_info->qos);
			if (vf_vlan_info->vlan_proto &&
			    vf_vlan_info->vlan_proto != htons(ETH_P_8021Q))
				print_string(PRINT_ANY,
					     "protocol",
					     ", vlan protocol %s",
					     ll_proto_n2a(
						     vf_vlan_info->vlan_proto,
						     b2, sizeof(b2)));
			close_json_object();
		}
		close_json_array(PRINT_JSON, NULL);
	} else {
		struct ifla_vf_vlan *vf_vlan = RTA_DATA(vf[IFLA_VF_VLAN]);

		if (vf_vlan->vlan)
			print_int(PRINT_ANY,
				  "vlan",
				  ", vlan %d",
				  vf_vlan->vlan);
		if (vf_vlan->qos)
			print_int(PRINT_ANY, "qos", ", qos %d", vf_vlan->qos);
	}

	if (vf_tx_rate->rate)
		print_uint(PRINT_ANY,
			   "tx_rate",
			   ", tx rate %u (Mbps)",
			   vf_tx_rate->rate);

	if (vf[IFLA_VF_RATE]) {
		struct ifla_vf_rate *vf_rate = RTA_DATA(vf[IFLA_VF_RATE]);
		int max_tx = vf_rate->max_tx_rate;
		int min_tx = vf_rate->min_tx_rate;

		if (is_json_context()) {
			open_json_object("rate");
			print_uint(PRINT_JSON, "max_tx", NULL, max_tx);
			print_uint(PRINT_ANY, "min_tx", NULL, min_tx);
			close_json_object();
		} else {
			if (max_tx)
				fprintf(fp, ", max_tx_rate %uMbps", max_tx);
			if (min_tx)
				fprintf(fp, ", min_tx_rate %uMbps", min_tx);
		}
	}

	if (vf[IFLA_VF_SPOOFCHK]) {
		struct ifla_vf_spoofchk *vf_spoofchk =
			RTA_DATA(vf[IFLA_VF_SPOOFCHK]);

		if (vf_spoofchk->setting != -1)
			print_bool(PRINT_ANY,
				   "spoofchk",
				   vf_spoofchk->setting ?
				   ", spoof checking on" : ", spoof checking off",
				   vf_spoofchk->setting);
	}

	if (vf[IFLA_VF_LINK_STATE]) {
		struct ifla_vf_link_state *vf_linkstate =
			RTA_DATA(vf[IFLA_VF_LINK_STATE]);

		if (vf_linkstate->link_state == IFLA_VF_LINK_STATE_AUTO)
			print_string(PRINT_ANY,
				     "link_state",
				     ", link-state %s",
				     "auto");
		else if (vf_linkstate->link_state == IFLA_VF_LINK_STATE_ENABLE)
			print_string(PRINT_ANY,
				     "link_state",
				     ", link-state %s",
				     "enable");
		else
			print_string(PRINT_ANY,
				     "link_state",
				     ", link-state %s",
				     "disable");
	}

	if (vf[IFLA_VF_TRUST]) {
		struct ifla_vf_trust *vf_trust = RTA_DATA(vf[IFLA_VF_TRUST]);

		if (vf_trust->setting != -1)
			print_bool(PRINT_ANY,
				   "trust",
				   vf_trust->setting ? ", trust on" : ", trust off",
				   vf_trust->setting);
	}

	if (vf[IFLA_VF_RSS_QUERY_EN]) {
		struct ifla_vf_rss_query_en *rss_query =
			RTA_DATA(vf[IFLA_VF_RSS_QUERY_EN]);

		if (rss_query->setting != -1)
			print_bool(PRINT_ANY,
				   "query_rss_en",
				   rss_query->setting ? ", query_rss on"
				   : ", query_rss off",
				   rss_query->setting);
	}

	if (vf[IFLA_VF_STATS] && show_stats)
		print_vf_stats64(fp, vf[IFLA_VF_STATS]);
}

void print_num(FILE *fp, unsigned int width, uint64_t count)
{
	const char *prefix = "kMGTPE";
	const unsigned int base = use_iec ? 1024 : 1000;
	uint64_t powi = 1;
	uint16_t powj = 1;
	uint8_t precision = 2;
	char buf[64];

	if (!human_readable || count < base) {
		fprintf(fp, "%-*"PRIu64" ", width, count);
		return;
	}

	/* increase value by a factor of 1000/1024 and print
	 * if result is something a human can read
	 */
	for (;;) {
		powi *= base;
		if (count / base < powi)
			break;

		if (!prefix[1])
			break;
		++prefix;
	}

	/* try to guess a good number of digits for precision */
	for (; precision > 0; precision--) {
		powj *= 10;
		if (count / powi < powj)
			break;
	}

	snprintf(buf, sizeof(buf), "%.*f%c%s", precision,
		 (double) count / powi, *prefix, use_iec ? "i" : "");

	fprintf(fp, "%-*s ", width, buf);
}

static void print_vf_stats64(FILE *fp, struct rtattr *vfstats)
{
	struct rtattr *vf[IFLA_VF_STATS_MAX + 1];

	if (vfstats->rta_type != IFLA_VF_STATS) {
		fprintf(stderr, "BUG: rta type is %d\n", vfstats->rta_type);
		return;
	}

	parse_rtattr_nested(vf, IFLA_VF_STATS_MAX, vfstats);

	if (is_json_context()) {
		open_json_object("stats");

		/* RX stats */
		open_json_object("rx");
		print_u64(PRINT_JSON, "bytes", NULL,
			   rta_getattr_u64(vf[IFLA_VF_STATS_RX_BYTES]));
		print_u64(PRINT_JSON, "packets", NULL,
			   rta_getattr_u64(vf[IFLA_VF_STATS_RX_PACKETS]));
		print_u64(PRINT_JSON, "multicast", NULL,
			   rta_getattr_u64(vf[IFLA_VF_STATS_MULTICAST]));
		print_u64(PRINT_JSON, "broadcast", NULL,
			   rta_getattr_u64(vf[IFLA_VF_STATS_BROADCAST]));
		if (vf[IFLA_VF_STATS_RX_DROPPED])
			print_u64(PRINT_JSON, "dropped", NULL,
				  rta_getattr_u64(vf[IFLA_VF_STATS_RX_DROPPED]));
		close_json_object();

		/* TX stats */
		open_json_object("tx");
		print_u64(PRINT_JSON, "tx_bytes", NULL,
			   rta_getattr_u64(vf[IFLA_VF_STATS_TX_BYTES]));
		print_u64(PRINT_JSON, "tx_packets", NULL,
			   rta_getattr_u64(vf[IFLA_VF_STATS_TX_PACKETS]));
		if (vf[IFLA_VF_STATS_TX_DROPPED])
			print_u64(PRINT_JSON, "dropped", NULL,
				  rta_getattr_u64(vf[IFLA_VF_STATS_TX_DROPPED]));
		close_json_object();
		close_json_object();
	} else {
		/* RX stats */
		fprintf(fp, "%s", _SL_);
		fprintf(fp, "    RX: bytes  packets  mcast   bcast ");
		if (vf[IFLA_VF_STATS_RX_DROPPED])
			fprintf(fp, "  dropped ");
		fprintf(fp, "%s", _SL_);
		fprintf(fp, "    ");

		print_num(fp, 10, rta_getattr_u64(vf[IFLA_VF_STATS_RX_BYTES]));
		print_num(fp, 8, rta_getattr_u64(vf[IFLA_VF_STATS_RX_PACKETS]));
		print_num(fp, 7, rta_getattr_u64(vf[IFLA_VF_STATS_MULTICAST]));
		print_num(fp, 7, rta_getattr_u64(vf[IFLA_VF_STATS_BROADCAST]));
		if (vf[IFLA_VF_STATS_RX_DROPPED])
			print_num(fp, 8, rta_getattr_u64(vf[IFLA_VF_STATS_RX_DROPPED]));

		/* TX stats */
		fprintf(fp, "%s", _SL_);
		fprintf(fp, "    TX: bytes  packets ");
		if (vf[IFLA_VF_STATS_TX_DROPPED])
			fprintf(fp, "  dropped ");
		fprintf(fp, "%s", _SL_);
		fprintf(fp, "    ");

		print_num(fp, 10, rta_getattr_u64(vf[IFLA_VF_STATS_TX_BYTES]));
		print_num(fp, 8, rta_getattr_u64(vf[IFLA_VF_STATS_TX_PACKETS]));
		if (vf[IFLA_VF_STATS_TX_DROPPED])
			print_num(fp, 8, rta_getattr_u64(vf[IFLA_VF_STATS_TX_DROPPED]));
	}
}

static void __print_link_stats(FILE *fp, struct rtattr *tb[])
{
	const struct rtattr *carrier_changes = tb[IFLA_CARRIER_CHANGES];
	struct rtnl_link_stats64 _s, *s = &_s;
	int ret;

	ret = get_rtnl_link_stats_rta(s, tb);
	if (ret < 0)
		return;

	if (is_json_context()) {
		open_json_object((ret == sizeof(*s)) ? "stats64" : "stats");

		/* RX stats */
		open_json_object("rx");
		print_u64(PRINT_JSON, "bytes", NULL, s->rx_bytes);
		print_u64(PRINT_JSON, "packets", NULL, s->rx_packets);
		print_u64(PRINT_JSON, "errors", NULL, s->rx_errors);
		print_u64(PRINT_JSON, "dropped", NULL, s->rx_dropped);
		print_u64(PRINT_JSON, "over_errors", NULL, s->rx_over_errors);
		print_u64(PRINT_JSON, "multicast", NULL, s->multicast);
		if (s->rx_compressed)
			print_u64(PRINT_JSON,
				   "compressed", NULL, s->rx_compressed);

		/* RX error stats */
		if (show_stats > 1) {
			print_u64(PRINT_JSON,
				   "length_errors",
				   NULL, s->rx_length_errors);
			print_u64(PRINT_JSON,
				   "crc_errors",
				   NULL, s->rx_crc_errors);
			print_u64(PRINT_JSON,
				   "frame_errors",
				   NULL, s->rx_frame_errors);
			print_u64(PRINT_JSON,
				   "fifo_errors",
				   NULL, s->rx_fifo_errors);
			print_u64(PRINT_JSON,
				   "missed_errors",
				   NULL, s->rx_missed_errors);
			if (s->rx_nohandler)
				print_u64(PRINT_JSON,
					   "nohandler", NULL, s->rx_nohandler);
		}
		close_json_object();

		/* TX stats */
		open_json_object("tx");
		print_u64(PRINT_JSON, "bytes", NULL, s->tx_bytes);
		print_u64(PRINT_JSON, "packets", NULL, s->tx_packets);
		print_u64(PRINT_JSON, "errors", NULL, s->tx_errors);
		print_u64(PRINT_JSON, "dropped", NULL, s->tx_dropped);
		print_u64(PRINT_JSON,
			   "carrier_errors",
			   NULL, s->tx_carrier_errors);
		print_u64(PRINT_JSON, "collisions", NULL, s->collisions);
		if (s->tx_compressed)
			print_u64(PRINT_JSON,
				   "compressed", NULL, s->tx_compressed);

		/* TX error stats */
		if (show_stats > 1) {
			print_u64(PRINT_JSON,
				   "aborted_errors",
				   NULL, s->tx_aborted_errors);
			print_u64(PRINT_JSON,
				   "fifo_errors",
				   NULL, s->tx_fifo_errors);
			print_u64(PRINT_JSON,
				   "window_errors",
				   NULL, s->tx_window_errors);
			print_u64(PRINT_JSON,
				   "heartbeat_errors",
				   NULL, s->tx_heartbeat_errors);
			if (carrier_changes)
				print_u64(PRINT_JSON, "carrier_changes", NULL,
					   rta_getattr_u32(carrier_changes));
		}

		close_json_object();
		close_json_object();
	} else {
		/* RX stats */
		fprintf(fp, "    RX: bytes  packets  errors  dropped overrun mcast   %s%s",
			s->rx_compressed ? "compressed" : "", _SL_);

		fprintf(fp, "    ");
		print_num(fp, 10, s->rx_bytes);
		print_num(fp, 8, s->rx_packets);
		print_num(fp, 7, s->rx_errors);
		print_num(fp, 7, s->rx_dropped);
		print_num(fp, 7, s->rx_over_errors);
		print_num(fp, 7, s->multicast);
		if (s->rx_compressed)
			print_num(fp, 7, s->rx_compressed);

		/* RX error stats */
		if (show_stats > 1) {
			fprintf(fp, "%s", _SL_);
			fprintf(fp, "    RX errors: length   crc     frame   fifo    missed%s%s",
				s->rx_nohandler ? "   nohandler" : "", _SL_);
			fprintf(fp, "               ");
			print_num(fp, 8, s->rx_length_errors);
			print_num(fp, 7, s->rx_crc_errors);
			print_num(fp, 7, s->rx_frame_errors);
			print_num(fp, 7, s->rx_fifo_errors);
			print_num(fp, 7, s->rx_missed_errors);
			if (s->rx_nohandler)
				print_num(fp, 7, s->rx_nohandler);
		}
		fprintf(fp, "%s", _SL_);

		/* TX stats */
		fprintf(fp, "    TX: bytes  packets  errors  dropped carrier collsns %s%s",
			s->tx_compressed ? "compressed" : "", _SL_);

		fprintf(fp, "    ");
		print_num(fp, 10, s->tx_bytes);
		print_num(fp, 8, s->tx_packets);
		print_num(fp, 7, s->tx_errors);
		print_num(fp, 7, s->tx_dropped);
		print_num(fp, 7, s->tx_carrier_errors);
		print_num(fp, 7, s->collisions);
		if (s->tx_compressed)
			print_num(fp, 7, s->tx_compressed);

		/* TX error stats */
		if (show_stats > 1) {
			fprintf(fp, "%s", _SL_);
			fprintf(fp, "    TX errors: aborted  fifo   window heartbeat");
			if (carrier_changes)
				fprintf(fp, " transns");
			fprintf(fp, "%s", _SL_);

			fprintf(fp, "               ");
			print_num(fp, 8, s->tx_aborted_errors);
			print_num(fp, 7, s->tx_fifo_errors);
			print_num(fp, 7, s->tx_window_errors);
			print_num(fp, 7, s->tx_heartbeat_errors);
			if (carrier_changes)
				print_num(fp, 7,
					  rta_getattr_u32(carrier_changes));
		}
	}
}

static void print_link_stats(FILE *fp, struct nlmsghdr *n)
{
	struct ifinfomsg *ifi = NLMSG_DATA(n);
	struct rtattr *tb[IFLA_MAX+1];

	parse_rtattr(tb, IFLA_MAX, IFLA_RTA(ifi),
		     n->nlmsg_len - NLMSG_LENGTH(sizeof(*ifi)));
	__print_link_stats(fp, tb);
	print_nl();
}

static int print_linkinfo_brief(FILE *fp, const char *name,
				const struct ifinfomsg *ifi,
				struct rtattr *tb[])
{
	unsigned int m_flag = 0;

	m_flag = print_name_and_link("%-16s ", name, tb);

	if (tb[IFLA_OPERSTATE])
		print_operstate(fp, rta_getattr_u8(tb[IFLA_OPERSTATE]));

	if (filter.family == AF_PACKET) {
		SPRINT_BUF(b1);

		if (tb[IFLA_ADDRESS]) {
			print_color_string(PRINT_ANY, COLOR_MAC,
					   "address", "%s ",
					   ll_addr_n2a(
						   RTA_DATA(tb[IFLA_ADDRESS]),
						   RTA_PAYLOAD(tb[IFLA_ADDRESS]),
						   ifi->ifi_type,
						   b1, sizeof(b1)));
		}
	}

	if (filter.family == AF_PACKET) {
		print_link_flags(fp, ifi->ifi_flags, m_flag);
		print_string(PRINT_FP, NULL, "%s", "\n");
	}

	fflush(fp);
	return 0;
}

static const char *link_events[] = {
	[IFLA_EVENT_NONE] = "NONE",
	[IFLA_EVENT_REBOOT] = "REBOOT",
	[IFLA_EVENT_FEATURES] = "FEATURE CHANGE",
	[IFLA_EVENT_BONDING_FAILOVER] = "BONDING FAILOVER",
	[IFLA_EVENT_NOTIFY_PEERS] = "NOTIFY PEERS",
	[IFLA_EVENT_IGMP_RESEND] = "RESEND IGMP",
	[IFLA_EVENT_BONDING_OPTIONS] = "BONDING OPTION"
};

static void print_link_event(FILE *f, __u32 event)
{
	if (event >= ARRAY_SIZE(link_events))
		print_int(PRINT_ANY, "event", "event %d ", event);
	else {
		if (event)
			print_string(PRINT_ANY,
				     "event", "event %s ",
				     link_events[event]);
	}
}

int print_linkinfo(struct nlmsghdr *n, void *arg)
{
	FILE *fp = (FILE *)arg;
	struct ifinfomsg *ifi = NLMSG_DATA(n);
	struct rtattr *tb[IFLA_MAX+1];
	int len = n->nlmsg_len;
	const char *name;
	unsigned int m_flag = 0;
	SPRINT_BUF(b1);

	if (n->nlmsg_type != RTM_NEWLINK && n->nlmsg_type != RTM_DELLINK)
		return 0;

	len -= NLMSG_LENGTH(sizeof(*ifi));
	if (len < 0)
		return -1;

	if (filter.ifindex && ifi->ifi_index != filter.ifindex)
		return -1;
	if (filter.up && !(ifi->ifi_flags&IFF_UP))
		return -1;

	parse_rtattr(tb, IFLA_MAX, IFLA_RTA(ifi), len);

	name = get_ifname_rta(ifi->ifi_index, tb[IFLA_IFNAME]);
	if (!name)
		return -1;

	if (filter.label)
		return 0;

	if (tb[IFLA_GROUP]) {
		int group = rta_getattr_u32(tb[IFLA_GROUP]);

		if (filter.group != -1 && group != filter.group)
			return -1;
	}

	if (tb[IFLA_MASTER]) {
		int master = rta_getattr_u32(tb[IFLA_MASTER]);

		if (filter.master > 0 && master != filter.master)
			return -1;
	} else if (filter.master > 0)
		return -1;

	if (filter.kind && match_link_kind(tb, filter.kind, 0))
		return -1;

	if (filter.slave_kind && match_link_kind(tb, filter.slave_kind, 1))
		return -1;

	if (n->nlmsg_type == RTM_DELLINK)
		print_bool(PRINT_ANY, "deleted", "Deleted ", true);

	if (brief)
		return print_linkinfo_brief(fp, name, ifi, tb);

	print_int(PRINT_ANY, "ifindex", "%d: ", ifi->ifi_index);

	m_flag = print_name_and_link("%s: ", name, tb);
	print_link_flags(fp, ifi->ifi_flags, m_flag);

	if (tb[IFLA_MTU])
		print_int(PRINT_ANY,
			  "mtu", "mtu %u ",
			  rta_getattr_u32(tb[IFLA_MTU]));
	if (tb[IFLA_XDP])
		xdp_dump(fp, tb[IFLA_XDP], do_link, false);
	if (tb[IFLA_QDISC])
		print_string(PRINT_ANY,
			     "qdisc",
			     "qdisc %s ",
			     rta_getattr_str(tb[IFLA_QDISC]));
	if (tb[IFLA_MASTER]) {
		int master = rta_getattr_u32(tb[IFLA_MASTER]);

		print_string(PRINT_ANY,
			     "master", "master %s ",
			     ll_index_to_name(master));
	}

	if (tb[IFLA_OPERSTATE])
		print_operstate(fp, rta_getattr_u8(tb[IFLA_OPERSTATE]));

	if (do_link && tb[IFLA_LINKMODE])
		print_linkmode(fp, tb[IFLA_LINKMODE]);

	if (tb[IFLA_GROUP]) {
		int group = rta_getattr_u32(tb[IFLA_GROUP]);

		print_string(PRINT_ANY,
			     "group",
			     "group %s ",
			     rtnl_group_n2a(group, b1, sizeof(b1)));
	}

	if (filter.showqueue)
		print_queuelen(fp, tb);

	if (tb[IFLA_EVENT])
		print_link_event(fp, rta_getattr_u32(tb[IFLA_EVENT]));

	if (!filter.family || filter.family == AF_PACKET || show_details) {
		print_nl();
		print_string(PRINT_ANY,
			     "link_type",
			     "    link/%s ",
			     ll_type_n2a(ifi->ifi_type, b1, sizeof(b1)));
		if (tb[IFLA_ADDRESS]) {
			print_color_string(PRINT_ANY,
					   COLOR_MAC,
					   "address",
					   "%s",
					   ll_addr_n2a(RTA_DATA(tb[IFLA_ADDRESS]),
						       RTA_PAYLOAD(tb[IFLA_ADDRESS]),
						       ifi->ifi_type,
						       b1, sizeof(b1)));
		}
		if (tb[IFLA_BROADCAST]) {
			if (ifi->ifi_flags&IFF_POINTOPOINT) {
				print_string(PRINT_FP, NULL, " peer ", NULL);
				print_bool(PRINT_JSON,
					   "link_pointtopoint", NULL, true);
			} else {
				print_string(PRINT_FP, NULL, " brd ", NULL);
			}
			print_color_string(PRINT_ANY,
					   COLOR_MAC,
					   "broadcast",
					   "%s",
					   ll_addr_n2a(RTA_DATA(tb[IFLA_BROADCAST]),
						       RTA_PAYLOAD(tb[IFLA_BROADCAST]),
						       ifi->ifi_type,
						       b1, sizeof(b1)));
		}
	}

	if (tb[IFLA_LINK_NETNSID]) {
		int id = rta_getattr_u32(tb[IFLA_LINK_NETNSID]);

		if (is_json_context()) {
			print_int(PRINT_JSON, "link_netnsid", NULL, id);
		} else {
			if (id >= 0) {
				char *name = get_name_from_nsid(id);

				if (name)
					print_string(PRINT_FP, NULL,
						     " link-netns %s", name);
				else
					print_int(PRINT_FP, NULL,
						  " link-netnsid %d", id);
			} else
				print_string(PRINT_FP, NULL,
					     " link-netnsid %s", "unknown");
		}
	}

	if (tb[IFLA_NEW_NETNSID]) {
		int id = rta_getattr_u32(tb[IFLA_NEW_NETNSID]);
		char *name = get_name_from_nsid(id);

		if (name)
			print_string(PRINT_FP, NULL, " new-netns %s", name);
		else
			print_int(PRINT_FP, NULL, " new-netnsid %d", id);
	}
	if (tb[IFLA_NEW_IFINDEX]) {
		int id = rta_getattr_u32(tb[IFLA_NEW_IFINDEX]);

		print_int(PRINT_FP, NULL, " new-ifindex %d", id);
	}

	if (tb[IFLA_PROTO_DOWN]) {
		if (rta_getattr_u8(tb[IFLA_PROTO_DOWN]))
			print_bool(PRINT_ANY,
				   "proto_down", " protodown on ", true);
	}

	if (show_details) {
		if (tb[IFLA_PROMISCUITY])
			print_uint(PRINT_ANY,
				   "promiscuity",
				   " promiscuity %u ",
				   rta_getattr_u32(tb[IFLA_PROMISCUITY]));

		if (tb[IFLA_MIN_MTU])
			print_uint(PRINT_ANY,
				   "min_mtu", "minmtu %u ",
				   rta_getattr_u32(tb[IFLA_MIN_MTU]));

		if (tb[IFLA_MAX_MTU])
			print_uint(PRINT_ANY,
				   "max_mtu", "maxmtu %u ",
				   rta_getattr_u32(tb[IFLA_MAX_MTU]));

		if (tb[IFLA_LINKINFO])
			print_linktype(fp, tb[IFLA_LINKINFO]);

		if (do_link && tb[IFLA_AF_SPEC])
			print_af_spec(fp, tb[IFLA_AF_SPEC]);

		if (tb[IFLA_NUM_TX_QUEUES])
			print_uint(PRINT_ANY,
				   "num_tx_queues",
				   "numtxqueues %u ",
				   rta_getattr_u32(tb[IFLA_NUM_TX_QUEUES]));

		if (tb[IFLA_NUM_RX_QUEUES])
			print_uint(PRINT_ANY,
				   "num_rx_queues",
				   "numrxqueues %u ",
				   rta_getattr_u32(tb[IFLA_NUM_RX_QUEUES]));

		if (tb[IFLA_GSO_MAX_SIZE])
			print_uint(PRINT_ANY,
				   "gso_max_size",
				   "gso_max_size %u ",
				   rta_getattr_u32(tb[IFLA_GSO_MAX_SIZE]));

		if (tb[IFLA_GSO_MAX_SEGS])
			print_uint(PRINT_ANY,
				   "gso_max_segs",
				   "gso_max_segs %u ",
				   rta_getattr_u32(tb[IFLA_GSO_MAX_SEGS]));

		if (tb[IFLA_PHYS_PORT_NAME])
			print_string(PRINT_ANY,
				     "phys_port_name",
				     "portname %s ",
				     rta_getattr_str(tb[IFLA_PHYS_PORT_NAME]));

		if (tb[IFLA_PHYS_PORT_ID]) {
			print_string(PRINT_ANY,
				     "phys_port_id",
				     "portid %s ",
				     hexstring_n2a(
					     RTA_DATA(tb[IFLA_PHYS_PORT_ID]),
					     RTA_PAYLOAD(tb[IFLA_PHYS_PORT_ID]),
					     b1, sizeof(b1)));
		}

		if (tb[IFLA_PHYS_SWITCH_ID]) {
			print_string(PRINT_ANY,
				     "phys_switch_id",
				     "switchid %s ",
				     hexstring_n2a(RTA_DATA(tb[IFLA_PHYS_SWITCH_ID]),
						   RTA_PAYLOAD(tb[IFLA_PHYS_SWITCH_ID]),
						   b1, sizeof(b1)));
		}
	}

	if ((do_link || show_details) && tb[IFLA_IFALIAS]) {
		print_string(PRINT_FP, NULL, "%s    ", _SL_);
		print_string(PRINT_ANY,
			     "ifalias",
			     "alias %s",
			     rta_getattr_str(tb[IFLA_IFALIAS]));
	}

	if ((do_link || show_details) && tb[IFLA_XDP])
		xdp_dump(fp, tb[IFLA_XDP], true, true);

	if (do_link && show_stats) {
		print_nl();
		__print_link_stats(fp, tb);
	}

	if ((do_link || show_details) && tb[IFLA_VFINFO_LIST] && tb[IFLA_NUM_VF]) {
		struct rtattr *i, *vflist = tb[IFLA_VFINFO_LIST];
		int rem = RTA_PAYLOAD(vflist);

		open_json_array(PRINT_JSON, "vfinfo_list");
		for (i = RTA_DATA(vflist); RTA_OK(i, rem); i = RTA_NEXT(i, rem)) {
			open_json_object(NULL);
			print_vfinfo(fp, ifi, i);
			close_json_object();
		}
		close_json_array(PRINT_JSON, NULL);
	}

	print_string(PRINT_FP, NULL, "%s", "\n");
	fflush(fp);
	return 1;
}

static int flush_update(void)
{

	/*
	 * Note that the kernel may delete multiple addresses for one
	 * delete request (e.g. if ipv4 address promotion is disabled).
	 * Since a flush operation is really a series of delete requests
	 * its possible that we may request an address delete that has
	 * already been done by the kernel. Therefore, ignore EADDRNOTAVAIL
	 * errors returned from a flush request
	 */
	if ((rtnl_send_check(&rth, filter.flushb, filter.flushp) < 0) &&
	    (errno != EADDRNOTAVAIL)) {
		perror("Failed to send flush request");
		return -1;
	}
	filter.flushp = 0;
	return 0;
}

static int set_lifetime(unsigned int *lifetime, char *argv)
{
	if (strcmp(argv, "forever") == 0)
		*lifetime = INFINITY_LIFE_TIME;
	else if (get_u32(lifetime, argv, 0))
		return -1;

	return 0;
}

static unsigned int get_ifa_flags(struct ifaddrmsg *ifa,
				  struct rtattr *ifa_flags_attr)
{
	return ifa_flags_attr ? rta_getattr_u32(ifa_flags_attr) :
		ifa->ifa_flags;
}

/* Mapping from argument to address flag mask */
static const struct {
	const char *name;
	unsigned long value;
} ifa_flag_names[] = {
	{ "secondary",		IFA_F_SECONDARY },
	{ "temporary",		IFA_F_SECONDARY },
	{ "nodad",		IFA_F_NODAD },
	{ "optimistic",		IFA_F_OPTIMISTIC },
	{ "dadfailed",		IFA_F_DADFAILED },
	{ "home",		IFA_F_HOMEADDRESS },
	{ "deprecated",		IFA_F_DEPRECATED },
	{ "tentative",		IFA_F_TENTATIVE },
	{ "permanent",		IFA_F_PERMANENT },
	{ "mngtmpaddr",		IFA_F_MANAGETEMPADDR },
	{ "noprefixroute",	IFA_F_NOPREFIXROUTE },
	{ "autojoin",		IFA_F_MCAUTOJOIN },
	{ "stable-privacy",	IFA_F_STABLE_PRIVACY },
};

static void print_ifa_flags(FILE *fp, const struct ifaddrmsg *ifa,
			    unsigned int flags)
{
	unsigned int i;

	for (i = 0; i < ARRAY_SIZE(ifa_flag_names); i++) {
		unsigned long mask = ifa_flag_names[i].value;

		if (mask == IFA_F_PERMANENT) {
			if (!(flags & mask))
				print_bool(PRINT_ANY,
					   "dynamic", "dynamic ", true);
		} else if (flags & mask) {
			if (mask == IFA_F_SECONDARY &&
			    ifa->ifa_family == AF_INET6) {
				print_bool(PRINT_ANY,
					   "temporary", "temporary ", true);
			} else {
				print_string(PRINT_FP, NULL,
					     "%s ", ifa_flag_names[i].name);
				print_bool(PRINT_JSON,
					   ifa_flag_names[i].name, NULL, true);
			}
		}

		flags &= ~mask;
	}

	if (flags) {
		if (is_json_context()) {
			SPRINT_BUF(b1);

			snprintf(b1, sizeof(b1), "%02x", flags);
			print_string(PRINT_JSON, "ifa_flags", NULL, b1);
		} else {
			fprintf(fp, "flags %02x ", flags);
		}
	}

}

static int get_filter(const char *arg)
{
	bool inv = false;
	unsigned int i;

	if (arg[0] == '-') {
		inv = true;
		arg++;
	}

	/* Special cases */
	if (strcmp(arg, "dynamic") == 0) {
		inv = !inv;
		arg = "permanent";
	} else if (strcmp(arg, "primary") == 0) {
		inv = !inv;
		arg = "secondary";
	}

	for (i = 0; i < ARRAY_SIZE(ifa_flag_names); i++) {
		if (strcmp(arg, ifa_flag_names[i].name))
			continue;

		if (inv)
			filter.flags &= ~ifa_flag_names[i].value;
		else
			filter.flags |= ifa_flag_names[i].value;
		filter.flagmask |= ifa_flag_names[i].value;
		return 0;
	}
	return -1;
}

static int ifa_label_match_rta(int ifindex, const struct rtattr *rta)
{
	const char *label;

	if (!filter.label)
		return 0;

	if (rta)
		label = RTA_DATA(rta);
	else
		label = ll_index_to_name(ifindex);

	return fnmatch(filter.label, label, 0);
}

int print_addrinfo(struct nlmsghdr *n, void *arg)
{
	FILE *fp = arg;
	struct ifaddrmsg *ifa = NLMSG_DATA(n);
	int len = n->nlmsg_len;
	unsigned int ifa_flags;
	struct rtattr *rta_tb[IFA_MAX+1];

	SPRINT_BUF(b1);

	if (n->nlmsg_type != RTM_NEWADDR && n->nlmsg_type != RTM_DELADDR)
		return 0;
	len -= NLMSG_LENGTH(sizeof(*ifa));
	if (len < 0) {
		fprintf(stderr, "BUG: wrong nlmsg len %d\n", len);
		return -1;
	}

	if (filter.flushb && n->nlmsg_type != RTM_NEWADDR)
		return 0;

	parse_rtattr(rta_tb, IFA_MAX, IFA_RTA(ifa),
		     n->nlmsg_len - NLMSG_LENGTH(sizeof(*ifa)));

	ifa_flags = get_ifa_flags(ifa, rta_tb[IFA_FLAGS]);

	if (!rta_tb[IFA_LOCAL])
		rta_tb[IFA_LOCAL] = rta_tb[IFA_ADDRESS];
	if (!rta_tb[IFA_ADDRESS])
		rta_tb[IFA_ADDRESS] = rta_tb[IFA_LOCAL];

	if (filter.ifindex && filter.ifindex != ifa->ifa_index)
		return 0;
	if ((filter.scope^ifa->ifa_scope)&filter.scopemask)
		return 0;
	if ((filter.flags ^ ifa_flags) & filter.flagmask)
		return 0;

	if (filter.family && filter.family != ifa->ifa_family)
		return 0;

	if (ifa_label_match_rta(ifa->ifa_index, rta_tb[IFA_LABEL]))
		return 0;

	if (inet_addr_match_rta(&filter.pfx, rta_tb[IFA_LOCAL]))
		return 0;

	if (filter.flushb) {
		struct nlmsghdr *fn;

		if (NLMSG_ALIGN(filter.flushp) + n->nlmsg_len > filter.flushe) {
			if (flush_update())
				return -1;
		}
		fn = (struct nlmsghdr *)(filter.flushb + NLMSG_ALIGN(filter.flushp));
		memcpy(fn, n, n->nlmsg_len);
		fn->nlmsg_type = RTM_DELADDR;
		fn->nlmsg_flags = NLM_F_REQUEST;
		fn->nlmsg_seq = ++rth.seq;
		filter.flushp = (((char *)fn) + n->nlmsg_len) - filter.flushb;
		filter.flushed++;
		if (show_stats < 2)
			return 0;
	}

	if (n->nlmsg_type == RTM_DELADDR)
		print_bool(PRINT_ANY, "deleted", "Deleted ", true);

	if (!brief) {
		const char *name;

		if (filter.oneline || filter.flushb) {
			const char *dev = ll_index_to_name(ifa->ifa_index);

			if (is_json_context()) {
				print_int(PRINT_JSON,
					  "index", NULL, ifa->ifa_index);
				print_string(PRINT_JSON, "dev", NULL, dev);
			} else {
				fprintf(fp, "%u: %s", ifa->ifa_index, dev);
			}
		}

		name = family_name(ifa->ifa_family);
		if (*name != '?') {
			print_string(PRINT_ANY, "family", "    %s ", name);
		} else {
			print_int(PRINT_ANY, "family_index", "    family %d ",
				  ifa->ifa_family);
		}
	}

	if (rta_tb[IFA_LOCAL]) {
		print_color_string(PRINT_ANY,
				   ifa_family_color(ifa->ifa_family),
				   "local", "%s",
				   format_host_rta(ifa->ifa_family,
						   rta_tb[IFA_LOCAL]));
		if (rta_tb[IFA_ADDRESS] &&
		    memcmp(RTA_DATA(rta_tb[IFA_ADDRESS]),
			   RTA_DATA(rta_tb[IFA_LOCAL]),
			   ifa->ifa_family == AF_INET ? 4 : 16)) {
			print_string(PRINT_FP, NULL, " %s ", "peer");
			print_color_string(PRINT_ANY,
					   ifa_family_color(ifa->ifa_family),
					   "address",
					   "%s",
					   format_host_rta(ifa->ifa_family,
							   rta_tb[IFA_ADDRESS]));
		}
		print_int(PRINT_ANY, "prefixlen", "/%d ", ifa->ifa_prefixlen);

		if (rta_tb[IFA_RT_PRIORITY])
			print_uint(PRINT_ANY, "metric", "metric %u ",
				   rta_getattr_u32(rta_tb[IFA_RT_PRIORITY]));
	}

	if (brief)
		goto brief_exit;

	if (rta_tb[IFA_BROADCAST]) {
		print_string(PRINT_FP, NULL, "%s ", "brd");
		print_color_string(PRINT_ANY,
				   ifa_family_color(ifa->ifa_family),
				   "broadcast",
				   "%s ",
				   format_host_rta(ifa->ifa_family,
						   rta_tb[IFA_BROADCAST]));
	}

	if (rta_tb[IFA_ANYCAST]) {
		print_string(PRINT_FP, NULL, "%s ", "any");
		print_color_string(PRINT_ANY,
				   ifa_family_color(ifa->ifa_family),
				   "anycast",
				   "%s ",
				   format_host_rta(ifa->ifa_family,
						   rta_tb[IFA_ANYCAST]));
	}

	print_string(PRINT_ANY,
		     "scope",
		     "scope %s ",
		     rtnl_rtscope_n2a(ifa->ifa_scope, b1, sizeof(b1)));

	print_ifa_flags(fp, ifa, ifa_flags);

	if (rta_tb[IFA_LABEL])
		print_string(PRINT_ANY,
			     "label",
			     "%s",
			     rta_getattr_str(rta_tb[IFA_LABEL]));

	if (rta_tb[IFA_CACHEINFO]) {
		struct ifa_cacheinfo *ci = RTA_DATA(rta_tb[IFA_CACHEINFO]);

		print_nl();
		print_string(PRINT_FP, NULL, "       valid_lft ", NULL);

		if (ci->ifa_valid == INFINITY_LIFE_TIME) {
			print_uint(PRINT_JSON,
				   "valid_life_time",
				   NULL, INFINITY_LIFE_TIME);
			print_string(PRINT_FP, NULL, "%s", "forever");
		} else {
			print_uint(PRINT_ANY,
				   "valid_life_time", "%usec", ci->ifa_valid);
		}

		print_string(PRINT_FP, NULL, " preferred_lft ", NULL);
		if (ci->ifa_prefered == INFINITY_LIFE_TIME) {
			print_uint(PRINT_JSON,
				   "preferred_life_time",
				   NULL, INFINITY_LIFE_TIME);
			print_string(PRINT_FP, NULL, "%s", "forever");
		} else {
			if (ifa_flags & IFA_F_DEPRECATED)
				print_int(PRINT_ANY,
					  "preferred_life_time",
					  "%dsec",
					  ci->ifa_prefered);
			else
				print_uint(PRINT_ANY,
					   "preferred_life_time",
					   "%usec",
					   ci->ifa_prefered);
		}
	}
	print_string(PRINT_FP, NULL, "%s", "\n");
brief_exit:
	fflush(fp);
	return 0;
}

static int print_selected_addrinfo(struct ifinfomsg *ifi,
				   struct nlmsg_list *ainfo, FILE *fp)
{
	open_json_array(PRINT_JSON, "addr_info");
	for ( ; ainfo ;  ainfo = ainfo->next) {
		struct nlmsghdr *n = &ainfo->h;
		struct ifaddrmsg *ifa = NLMSG_DATA(n);

		if (n->nlmsg_type != RTM_NEWADDR)
			continue;

		if (n->nlmsg_len < NLMSG_LENGTH(sizeof(*ifa)))
			return -1;

		if (ifa->ifa_index != ifi->ifi_index ||
		    (filter.family && filter.family != ifa->ifa_family))
			continue;

		if (filter.up && !(ifi->ifi_flags&IFF_UP))
			continue;

		open_json_object(NULL);
		print_addrinfo(n, fp);
		close_json_object();
	}
	close_json_array(PRINT_JSON, NULL);

	if (brief) {
		print_string(PRINT_FP, NULL, "%s", "\n");
		fflush(fp);
	}
	return 0;
}


static int store_nlmsg(struct nlmsghdr *n, void *arg)
{
	struct nlmsg_chain *lchain = (struct nlmsg_chain *)arg;
	struct nlmsg_list *h;

	h = malloc(n->nlmsg_len+sizeof(void *));
	if (h == NULL)
		return -1;

	memcpy(&h->h, n, n->nlmsg_len);
	h->next = NULL;

	if (lchain->tail)
		lchain->tail->next = h;
	else
		lchain->head = h;
	lchain->tail = h;

	ll_remember_index(n, NULL);
	return 0;
}

static __u32 ipadd_dump_magic = 0x47361222;

static int ipadd_save_prep(void)
{
	int ret;

	if (isatty(STDOUT_FILENO)) {
		fprintf(stderr, "Not sending a binary stream to stdout\n");
		return -1;
	}

	ret = write(STDOUT_FILENO, &ipadd_dump_magic, sizeof(ipadd_dump_magic));
	if (ret != sizeof(ipadd_dump_magic)) {
		fprintf(stderr, "Can't write magic to dump file\n");
		return -1;
	}

	return 0;
}

static int ipadd_dump_check_magic(void)
{
	int ret;
	__u32 magic = 0;

	if (isatty(STDIN_FILENO)) {
		fprintf(stderr, "Can't restore address dump from a terminal\n");
		return -1;
	}

	ret = fread(&magic, sizeof(magic), 1, stdin);
	if (magic != ipadd_dump_magic) {
		fprintf(stderr, "Magic mismatch (%d elems, %x magic)\n", ret, magic);
		return -1;
	}

	return 0;
}

static int save_nlmsg(struct nlmsghdr *n, void *arg)
{
	int ret;

	ret = write(STDOUT_FILENO, n, n->nlmsg_len);
	if ((ret > 0) && (ret != n->nlmsg_len)) {
		fprintf(stderr, "Short write while saving nlmsg\n");
		ret = -EIO;
	}

	return ret == n->nlmsg_len ? 0 : ret;
}

static int show_handler(struct rtnl_ctrl_data *ctrl,
			struct nlmsghdr *n, void *arg)
{
	struct ifaddrmsg *ifa = NLMSG_DATA(n);

	open_json_object(NULL);
	print_int(PRINT_ANY, "index", "if%d:\n", ifa->ifa_index);
	print_addrinfo(n, stdout);
	close_json_object();
	return 0;
}

static int ipaddr_showdump(void)
{
	int err;

	if (ipadd_dump_check_magic())
		exit(-1);

	new_json_obj(json);
	open_json_object(NULL);
	open_json_array(PRINT_JSON, "addr_info");

	err = rtnl_from_file(stdin, &show_handler, NULL);

	close_json_array(PRINT_JSON, NULL);
	close_json_object();
	delete_json_obj();

	exit(err);
}

static int restore_handler(struct rtnl_ctrl_data *ctrl,
			   struct nlmsghdr *n, void *arg)
{
	int ret;

	n->nlmsg_flags |= NLM_F_REQUEST | NLM_F_CREATE | NLM_F_ACK;

	ll_init_map(&rth);

	ret = rtnl_talk(&rth, n, NULL);
	if ((ret < 0) && (errno == EEXIST))
		ret = 0;

	return ret;
}

static int ipaddr_restore(void)
{
	if (ipadd_dump_check_magic())
		exit(-1);

	exit(rtnl_from_file(stdin, &restore_handler, NULL));
}

void free_nlmsg_chain(struct nlmsg_chain *info)
{
	struct nlmsg_list *l, *n;

	for (l = info->head; l; l = n) {
		n = l->next;
		free(l);
	}
}

static void ipaddr_filter(struct nlmsg_chain *linfo, struct nlmsg_chain *ainfo)
{
	struct nlmsg_list *l, **lp;

	lp = &linfo->head;
	while ((l = *lp) != NULL) {
		int ok = 0;
		int missing_net_address = 1;
		struct ifinfomsg *ifi = NLMSG_DATA(&l->h);
		struct nlmsg_list *a;

		for (a = ainfo->head; a; a = a->next) {
			struct nlmsghdr *n = &a->h;
			struct ifaddrmsg *ifa = NLMSG_DATA(n);
			struct rtattr *tb[IFA_MAX + 1];
			unsigned int ifa_flags;

			if (ifa->ifa_index != ifi->ifi_index)
				continue;
			missing_net_address = 0;
			if (filter.family && filter.family != ifa->ifa_family)
				continue;
			if ((filter.scope^ifa->ifa_scope)&filter.scopemask)
				continue;

			parse_rtattr(tb, IFA_MAX, IFA_RTA(ifa), IFA_PAYLOAD(n));
			ifa_flags = get_ifa_flags(ifa, tb[IFA_FLAGS]);

			if ((filter.flags ^ ifa_flags) & filter.flagmask)
				continue;

			if (ifa_label_match_rta(ifa->ifa_index, tb[IFA_LABEL]))
				continue;

			if (!tb[IFA_LOCAL])
				tb[IFA_LOCAL] = tb[IFA_ADDRESS];
			if (inet_addr_match_rta(&filter.pfx, tb[IFA_LOCAL]))
				continue;

			ok = 1;
			break;
		}
		if (missing_net_address &&
		    (filter.family == AF_UNSPEC || filter.family == AF_PACKET))
			ok = 1;
		if (!ok) {
			*lp = l->next;
			free(l);
		} else
			lp = &l->next;
	}
}

static int ipaddr_dump_filter(struct nlmsghdr *nlh, int reqlen)
{
	struct ifaddrmsg *ifa = NLMSG_DATA(nlh);

	ifa->ifa_index = filter.ifindex;

	return 0;
}

static int ipaddr_flush(void)
{
	int round = 0;
	char flushb[4096-512];

	filter.flushb = flushb;
	filter.flushp = 0;
	filter.flushe = sizeof(flushb);

	while ((max_flush_loops == 0) || (round < max_flush_loops)) {
		if (rtnl_addrdump_req(&rth, filter.family,
				      ipaddr_dump_filter) < 0) {
			perror("Cannot send dump request");
			exit(1);
		}
		filter.flushed = 0;
		if (rtnl_dump_filter_nc(&rth, print_addrinfo,
					stdout, NLM_F_DUMP_INTR) < 0) {
			fprintf(stderr, "Flush terminated\n");
			exit(1);
		}
		if (filter.flushed == 0) {
 flush_done:
			if (show_stats) {
				if (round == 0)
					printf("Nothing to flush.\n");
				else
					printf("*** Flush is complete after %d round%s ***\n", round, round > 1?"s":"");
			}
			fflush(stdout);
			return 0;
		}
		round++;
		if (flush_update() < 0)
			return 1;

		if (show_stats) {
			printf("\n*** Round %d, deleting %d addresses ***\n", round, filter.flushed);
			fflush(stdout);
		}

		/* If we are flushing, and specifying primary, then we
		 * want to flush only a single round.  Otherwise, we'll
		 * start flushing secondaries that were promoted to
		 * primaries.
		 */
		if (!(filter.flags & IFA_F_SECONDARY) && (filter.flagmask & IFA_F_SECONDARY))
			goto flush_done;
	}
	fprintf(stderr, "*** Flush remains incomplete after %d rounds. ***\n", max_flush_loops);
	fflush(stderr);
	return 1;
}

static int iplink_filter_req(struct nlmsghdr *nlh, int reqlen)
{
	int err;

	err = addattr32(nlh, reqlen, IFLA_EXT_MASK, RTEXT_FILTER_VF);
	if (err)
		return err;

	if (filter.master) {
		err = addattr32(nlh, reqlen, IFLA_MASTER, filter.master);
		if (err)
			return err;
	}

	if (filter.kind) {
		struct rtattr *linkinfo;

		linkinfo = addattr_nest(nlh, reqlen, IFLA_LINKINFO);

		err = addattr_l(nlh, reqlen, IFLA_INFO_KIND, filter.kind,
				strlen(filter.kind));
		if (err)
			return err;

		addattr_nest_end(nlh, linkinfo);
	}

	return 0;
}

static int ipaddr_link_get(int index, struct nlmsg_chain *linfo)
{
	struct iplink_req req = {
		.n.nlmsg_len = NLMSG_LENGTH(sizeof(struct ifinfomsg)),
		.n.nlmsg_flags = NLM_F_REQUEST,
		.n.nlmsg_type = RTM_GETLINK,
		.i.ifi_family = filter.family,
		.i.ifi_index = index,
	};
	__u32 filt_mask = RTEXT_FILTER_VF;
	struct nlmsghdr *answer;

	if (!show_stats)
		filt_mask |= RTEXT_FILTER_SKIP_STATS;

	addattr32(&req.n, sizeof(req), IFLA_EXT_MASK, filt_mask);

	if (rtnl_talk(&rth, &req.n, &answer) < 0) {
		perror("Cannot send link request");
		return 1;
	}

	if (store_nlmsg(answer, linfo) < 0) {
		fprintf(stderr, "Failed to process link information\n");
		return 1;
	}

	return 0;
}

/* fills in linfo with link data and optionally ainfo with address info
 * caller can walk lists as desired and must call free_nlmsg_chain for
 * both when done
 */
int ip_link_list(req_filter_fn_t filter_fn, struct nlmsg_chain *linfo)
{
	if (rtnl_linkdump_req_filter_fn(&rth, preferred_family,
					filter_fn) < 0) {
		perror("Cannot send dump request");
		return 1;
	}

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

	return 0;
}

static int ip_addr_list(struct nlmsg_chain *ainfo)
{
	if (rtnl_addrdump_req(&rth, filter.family, ipaddr_dump_filter) < 0) {
		perror("Cannot send dump request");
		return 1;
	}

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

	return 0;
}

static int ipaddr_list_flush_or_save(int argc, char **argv, int action)
{
	struct nlmsg_chain linfo = { NULL, NULL};
	struct nlmsg_chain _ainfo = { NULL, NULL}, *ainfo = &_ainfo;
	struct nlmsg_list *l;
	char *filter_dev = NULL;
	int no_link = 0;

	ipaddr_reset_filter(oneline, 0);
	filter.showqueue = 1;
	filter.family = preferred_family;

	if (action == IPADD_FLUSH) {
		if (argc <= 0) {
			fprintf(stderr, "Flush requires arguments.\n");

			return -1;
		}
		if (filter.family == AF_PACKET) {
			fprintf(stderr, "Cannot flush link addresses.\n");
			return -1;
		}
	}

	while (argc > 0) {
		if (strcmp(*argv, "to") == 0) {
			NEXT_ARG();
			if (get_prefix(&filter.pfx, *argv, filter.family))
				invarg("invalid \"to\"\n", *argv);
			if (filter.family == AF_UNSPEC)
				filter.family = filter.pfx.family;
		} else if (strcmp(*argv, "scope") == 0) {
			unsigned int scope = 0;

			NEXT_ARG();
			filter.scopemask = -1;
			if (rtnl_rtscope_a2n(&scope, *argv)) {
				if (strcmp(*argv, "all") != 0)
					invarg("invalid \"scope\"\n", *argv);
				scope = RT_SCOPE_NOWHERE;
				filter.scopemask = 0;
			}
			filter.scope = scope;
		} else if (strcmp(*argv, "up") == 0) {
			filter.up = 1;
		} else if (get_filter(*argv) == 0) {

		} else if (strcmp(*argv, "label") == 0) {
			NEXT_ARG();
			filter.label = *argv;
		} else if (strcmp(*argv, "group") == 0) {
			NEXT_ARG();
			if (rtnl_group_a2n(&filter.group, *argv))
				invarg("Invalid \"group\" value\n", *argv);
		} else if (strcmp(*argv, "master") == 0) {
			int ifindex;

			NEXT_ARG();
			ifindex = ll_name_to_index(*argv);
			if (!ifindex)
				invarg("Device does not exist\n", *argv);
			filter.master = ifindex;
		} else if (strcmp(*argv, "vrf") == 0) {
			int ifindex;

			NEXT_ARG();
			ifindex = ll_name_to_index(*argv);
			if (!ifindex)
				invarg("Not a valid VRF name\n", *argv);
			if (!name_is_vrf(*argv))
				invarg("Not a valid VRF name\n", *argv);
			filter.master = ifindex;
		} else if (strcmp(*argv, "type") == 0) {
			int soff;

			NEXT_ARG();
			soff = strlen(*argv) - strlen("_slave");
			if (!strcmp(*argv + soff, "_slave")) {
				(*argv)[soff] = '\0';
				filter.slave_kind = *argv;
			} else {
				filter.kind = *argv;
			}
		} else {
			if (strcmp(*argv, "dev") == 0)
				NEXT_ARG();
			else if (matches(*argv, "help") == 0)
				usage();
			if (filter_dev)
				duparg2("dev", *argv);
			filter_dev = *argv;
		}
		argv++; argc--;
	}

	if (filter_dev) {
		filter.ifindex = ll_name_to_index(filter_dev);
		if (filter.ifindex <= 0) {
			fprintf(stderr, "Device \"%s\" does not exist.\n", filter_dev);
			return -1;
		}
	}

	if (action == IPADD_FLUSH)
		return ipaddr_flush();

	if (action == IPADD_SAVE) {
		if (ipadd_save_prep())
			exit(1);

		if (rtnl_addrdump_req(&rth, preferred_family,
				      ipaddr_dump_filter) < 0) {
			perror("Cannot send dump request");
			exit(1);
		}

		if (rtnl_dump_filter(&rth, save_nlmsg, stdout) < 0) {
			fprintf(stderr, "Save terminated\n");
			exit(1);
		}

		exit(0);
	}

	/*
	 * Initialize a json_writer and open an array object
	 * if -json was specified.
	 */
	new_json_obj(json);

	/*
	 * If only filter_dev present and none of the other
	 * link filters are present, use RTM_GETLINK to get
	 * the link device
	 */
	if (filter_dev && filter.group == -1 && do_link == 1) {
		if (iplink_get(filter_dev, RTEXT_FILTER_VF) < 0) {
			perror("Cannot send link get request");
			delete_json_obj();
			exit(1);
		}
		delete_json_obj();
		goto out;
	}

	if (filter.ifindex) {
		if (ipaddr_link_get(filter.ifindex, &linfo) != 0)
			goto out;
	} else {
		if (ip_link_list(iplink_filter_req, &linfo) != 0)
			goto out;
	}

	if (filter.family != AF_PACKET) {
		if (filter.oneline)
			no_link = 1;

		if (ip_addr_list(ainfo) != 0)
			goto out;

		ipaddr_filter(&linfo, ainfo);
	}

	for (l = linfo.head; l; l = l->next) {
		struct nlmsghdr *n = &l->h;
		struct ifinfomsg *ifi = NLMSG_DATA(n);
		int res = 0;

		open_json_object(NULL);
		if (brief || !no_link)
			res = print_linkinfo(n, stdout);
		if (res >= 0 && filter.family != AF_PACKET)
			print_selected_addrinfo(ifi, ainfo->head, stdout);
		if (res > 0 && !do_link && show_stats)
			print_link_stats(stdout, n);
		close_json_object();
	}
	fflush(stdout);

out:
	free_nlmsg_chain(ainfo);
	free_nlmsg_chain(&linfo);
	delete_json_obj();
	return 0;
}

static void
ipaddr_loop_each_vf(struct rtattr *tb[], int vfnum, int *min, int *max)
{
	struct rtattr *vflist = tb[IFLA_VFINFO_LIST];
	struct rtattr *i, *vf[IFLA_VF_MAX+1];
	struct ifla_vf_rate *vf_rate;
	int rem;

	rem = RTA_PAYLOAD(vflist);

	for (i = RTA_DATA(vflist); RTA_OK(i, rem); i = RTA_NEXT(i, rem)) {
		parse_rtattr_nested(vf, IFLA_VF_MAX, i);

		if (!vf[IFLA_VF_RATE]) {
			fprintf(stderr, "VF min/max rate API not supported\n");
			exit(1);
		}

		vf_rate = RTA_DATA(vf[IFLA_VF_RATE]);
		if (vf_rate->vf == vfnum) {
			*min = vf_rate->min_tx_rate;
			*max = vf_rate->max_tx_rate;
			return;
		}
	}
	fprintf(stderr, "Cannot find VF %d\n", vfnum);
	exit(1);
}

void ipaddr_get_vf_rate(int vfnum, int *min, int *max, const char *dev)
{
	struct nlmsg_chain linfo = { NULL, NULL};
	struct rtattr *tb[IFLA_MAX+1];
	struct ifinfomsg *ifi;
	struct nlmsg_list *l;
	struct nlmsghdr *n;
	int idx, len;

	idx = ll_name_to_index(dev);
	if (idx == 0) {
		fprintf(stderr, "Device %s does not exist\n", dev);
		exit(1);
	}

	if (rtnl_linkdump_req(&rth, AF_UNSPEC) < 0) {
		perror("Cannot send dump request");
		exit(1);
	}
	if (rtnl_dump_filter(&rth, store_nlmsg, &linfo) < 0) {
		fprintf(stderr, "Dump terminated\n");
		exit(1);
	}
	for (l = linfo.head; l; l = l->next) {
		n = &l->h;
		ifi = NLMSG_DATA(n);

		len = n->nlmsg_len - NLMSG_LENGTH(sizeof(*ifi));
		if (len < 0 || (idx && idx != ifi->ifi_index))
			continue;

		parse_rtattr(tb, IFLA_MAX, IFLA_RTA(ifi), len);

		if ((tb[IFLA_VFINFO_LIST] && tb[IFLA_NUM_VF])) {
			ipaddr_loop_each_vf(tb, vfnum, min, max);
			return;
		}
	}
}

int ipaddr_list_link(int argc, char **argv)
{
	preferred_family = AF_PACKET;
	do_link = 1;
	return ipaddr_list_flush_or_save(argc, argv, IPADD_LIST);
}

void ipaddr_reset_filter(int oneline, int ifindex)
{
	memset(&filter, 0, sizeof(filter));
	filter.oneline = oneline;
	filter.ifindex = ifindex;
	filter.group = -1;
}

static int default_scope(inet_prefix *lcl)
{
	if (lcl->family == AF_INET) {
		if (lcl->bytelen >= 1 && *(__u8 *)&lcl->data == 127)
			return RT_SCOPE_HOST;
	}
	return 0;
}

static bool ipaddr_is_multicast(inet_prefix *a)
{
	if (a->family == AF_INET)
		return IN_MULTICAST(ntohl(a->data[0]));
	else if (a->family == AF_INET6)
		return IN6_IS_ADDR_MULTICAST(a->data);
	else
		return false;
}

static bool is_valid_label(const char *dev, const char *label)
{
	size_t len = strlen(dev);

	if (strncmp(label, dev, len) != 0)
		return false;

	return label[len] == '\0' || label[len] == ':';
}

static int ipaddr_modify(int cmd, int flags, int argc, char **argv)
{
	struct {
		struct nlmsghdr	n;
		struct ifaddrmsg	ifa;
		char			buf[256];
	} req = {
		.n.nlmsg_len = NLMSG_LENGTH(sizeof(struct ifaddrmsg)),
		.n.nlmsg_flags = NLM_F_REQUEST | flags,
		.n.nlmsg_type = cmd,
		.ifa.ifa_family = preferred_family,
	};
	char  *d = NULL;
	char  *l = NULL;
	char  *lcl_arg = NULL;
	char  *valid_lftp = NULL;
	char  *preferred_lftp = NULL;
	inet_prefix lcl = {};
	inet_prefix peer;
	int local_len = 0;
	int peer_len = 0;
	int brd_len = 0;
	int any_len = 0;
	int scoped = 0;
	__u32 preferred_lft = INFINITY_LIFE_TIME;
	__u32 valid_lft = INFINITY_LIFE_TIME;
	unsigned int ifa_flags = 0;

	while (argc > 0) {
		if (strcmp(*argv, "peer") == 0 ||
		    strcmp(*argv, "remote") == 0) {
			NEXT_ARG();

			if (peer_len)
				duparg("peer", *argv);
			get_prefix(&peer, *argv, req.ifa.ifa_family);
			peer_len = peer.bytelen;
			if (req.ifa.ifa_family == AF_UNSPEC)
				req.ifa.ifa_family = peer.family;
			addattr_l(&req.n, sizeof(req), IFA_ADDRESS, &peer.data, peer.bytelen);
			req.ifa.ifa_prefixlen = peer.bitlen;
		} else if (matches(*argv, "broadcast") == 0 ||
			   strcmp(*argv, "brd") == 0) {
			inet_prefix addr;

			NEXT_ARG();
			if (brd_len)
				duparg("broadcast", *argv);
			if (strcmp(*argv, "+") == 0)
				brd_len = -1;
			else if (strcmp(*argv, "-") == 0)
				brd_len = -2;
			else {
				get_addr(&addr, *argv, req.ifa.ifa_family);
				if (req.ifa.ifa_family == AF_UNSPEC)
					req.ifa.ifa_family = addr.family;
				addattr_l(&req.n, sizeof(req), IFA_BROADCAST, &addr.data, addr.bytelen);
				brd_len = addr.bytelen;
			}
		} else if (strcmp(*argv, "anycast") == 0) {
			inet_prefix addr;

			NEXT_ARG();
			if (any_len)
				duparg("anycast", *argv);
			get_addr(&addr, *argv, req.ifa.ifa_family);
			if (req.ifa.ifa_family == AF_UNSPEC)
				req.ifa.ifa_family = addr.family;
			addattr_l(&req.n, sizeof(req), IFA_ANYCAST, &addr.data, addr.bytelen);
			any_len = addr.bytelen;
		} else if (strcmp(*argv, "scope") == 0) {
			unsigned int scope = 0;

			NEXT_ARG();
			if (rtnl_rtscope_a2n(&scope, *argv))
				invarg("invalid scope value.", *argv);
			req.ifa.ifa_scope = scope;
			scoped = 1;
		} else if (strcmp(*argv, "dev") == 0) {
			NEXT_ARG();
			d = *argv;
		} else if (strcmp(*argv, "label") == 0) {
			NEXT_ARG();
			l = *argv;
			addattr_l(&req.n, sizeof(req), IFA_LABEL, l, strlen(l)+1);
		} else if (matches(*argv, "metric") == 0 ||
			   matches(*argv, "priority") == 0 ||
			   matches(*argv, "preference") == 0) {
			__u32 metric;

			NEXT_ARG();
			if (get_u32(&metric, *argv, 0))
				invarg("\"metric\" value is invalid\n", *argv);
			addattr32(&req.n, sizeof(req), IFA_RT_PRIORITY, metric);
		} else if (matches(*argv, "valid_lft") == 0) {
			if (valid_lftp)
				duparg("valid_lft", *argv);
			NEXT_ARG();
			valid_lftp = *argv;
			if (set_lifetime(&valid_lft, *argv))
				invarg("valid_lft value", *argv);
		} else if (matches(*argv, "preferred_lft") == 0) {
			if (preferred_lftp)
				duparg("preferred_lft", *argv);
			NEXT_ARG();
			preferred_lftp = *argv;
			if (set_lifetime(&preferred_lft, *argv))
				invarg("preferred_lft value", *argv);
		} else if (strcmp(*argv, "home") == 0) {
			if (req.ifa.ifa_family == AF_INET6)
				ifa_flags |= IFA_F_HOMEADDRESS;
			else
				fprintf(stderr, "Warning: home option can be set only for IPv6 addresses\n");
		} else if (strcmp(*argv, "optimistic") == 0) {
			if (req.ifa.ifa_family == AF_INET6)
				ifa_flags |= IFA_F_OPTIMISTIC;
			else
				fprintf(stderr, "Warning: optimistic option can be set only for IPv6 addresses\n");
		} else if (strcmp(*argv, "nodad") == 0) {
			if (req.ifa.ifa_family == AF_INET6)
				ifa_flags |= IFA_F_NODAD;
			else
				fprintf(stderr, "Warning: nodad option can be set only for IPv6 addresses\n");
		} else if (strcmp(*argv, "mngtmpaddr") == 0) {
			if (req.ifa.ifa_family == AF_INET6)
				ifa_flags |= IFA_F_MANAGETEMPADDR;
			else
				fprintf(stderr, "Warning: mngtmpaddr option can be set only for IPv6 addresses\n");
		} else if (strcmp(*argv, "noprefixroute") == 0) {
			ifa_flags |= IFA_F_NOPREFIXROUTE;
		} else if (strcmp(*argv, "autojoin") == 0) {
			ifa_flags |= IFA_F_MCAUTOJOIN;
		} else {
			if (strcmp(*argv, "local") == 0)
				NEXT_ARG();
			if (matches(*argv, "help") == 0)
				usage();
			if (local_len)
				duparg2("local", *argv);
			lcl_arg = *argv;
			get_prefix(&lcl, *argv, req.ifa.ifa_family);
			if (req.ifa.ifa_family == AF_UNSPEC)
				req.ifa.ifa_family = lcl.family;
			addattr_l(&req.n, sizeof(req), IFA_LOCAL, &lcl.data, lcl.bytelen);
			local_len = lcl.bytelen;
		}
		argc--; argv++;
	}
	if (ifa_flags <= 0xff)
		req.ifa.ifa_flags = ifa_flags;
	else
		addattr32(&req.n, sizeof(req), IFA_FLAGS, ifa_flags);

	if (d == NULL) {
		fprintf(stderr, "Not enough information: \"dev\" argument is required.\n");
		return -1;
	}
	if (l && !is_valid_label(d, l)) {
		fprintf(stderr,
			"\"label\" (%s) must match \"dev\" (%s) or be prefixed by \"dev\" with a colon.\n",
			l, d);
		return -1;
	}

	if (peer_len == 0 && local_len) {
		if (cmd == RTM_DELADDR && lcl.family == AF_INET && !(lcl.flags & PREFIXLEN_SPECIFIED)) {
			fprintf(stderr,
			    "Warning: Executing wildcard deletion to stay compatible with old scripts.\n"
			    "         Explicitly specify the prefix length (%s/%d) to avoid this warning.\n"
			    "         This special behaviour is likely to disappear in further releases,\n"
			    "         fix your scripts!\n", lcl_arg, local_len*8);
		} else {
			peer = lcl;
			addattr_l(&req.n, sizeof(req), IFA_ADDRESS, &lcl.data, lcl.bytelen);
		}
	}
	if (req.ifa.ifa_prefixlen == 0)
		req.ifa.ifa_prefixlen = lcl.bitlen;

	if (brd_len < 0 && cmd != RTM_DELADDR) {
		inet_prefix brd;
		int i;

		if (req.ifa.ifa_family != AF_INET) {
			fprintf(stderr, "Broadcast can be set only for IPv4 addresses\n");
			return -1;
		}
		brd = peer;
		if (brd.bitlen <= 30) {
			for (i = 31; i >= brd.bitlen; i--) {
				if (brd_len == -1)
					brd.data[0] |= htonl(1<<(31-i));
				else
					brd.data[0] &= ~htonl(1<<(31-i));
			}
			addattr_l(&req.n, sizeof(req), IFA_BROADCAST, &brd.data, brd.bytelen);
			brd_len = brd.bytelen;
		}
	}
	if (!scoped && cmd != RTM_DELADDR)
		req.ifa.ifa_scope = default_scope(&lcl);

	req.ifa.ifa_index = ll_name_to_index(d);
	if (!req.ifa.ifa_index)
		return nodev(d);

	if (valid_lftp || preferred_lftp) {
		struct ifa_cacheinfo cinfo = {};

		if (!valid_lft) {
			fprintf(stderr, "valid_lft is zero\n");
			return -1;
		}
		if (valid_lft < preferred_lft) {
			fprintf(stderr, "preferred_lft is greater than valid_lft\n");
			return -1;
		}

		cinfo.ifa_prefered = preferred_lft;
		cinfo.ifa_valid = valid_lft;
		addattr_l(&req.n, sizeof(req), IFA_CACHEINFO, &cinfo,
			  sizeof(cinfo));
	}

	if ((ifa_flags & IFA_F_MCAUTOJOIN) && !ipaddr_is_multicast(&lcl)) {
		fprintf(stderr, "autojoin needs multicast address\n");
		return -1;
	}

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

	return 0;
}

int do_ipaddr(int argc, char **argv)
{
	if (argc < 1)
		return ipaddr_list_flush_or_save(0, NULL, IPADD_LIST);
	if (matches(*argv, "add") == 0)
		return ipaddr_modify(RTM_NEWADDR, NLM_F_CREATE|NLM_F_EXCL, argc-1, argv+1);
	if (matches(*argv, "change") == 0 ||
		strcmp(*argv, "chg") == 0)
		return ipaddr_modify(RTM_NEWADDR, NLM_F_REPLACE, argc-1, argv+1);
	if (matches(*argv, "replace") == 0)
		return ipaddr_modify(RTM_NEWADDR, NLM_F_CREATE|NLM_F_REPLACE, argc-1, argv+1);
	if (matches(*argv, "delete") == 0)
		return ipaddr_modify(RTM_DELADDR, 0, argc-1, argv+1);
	if (matches(*argv, "list") == 0 || matches(*argv, "show") == 0
	    || matches(*argv, "lst") == 0)
		return ipaddr_list_flush_or_save(argc-1, argv+1, IPADD_LIST);
	if (matches(*argv, "flush") == 0)
		return ipaddr_list_flush_or_save(argc-1, argv+1, IPADD_FLUSH);
	if (matches(*argv, "save") == 0)
		return ipaddr_list_flush_or_save(argc-1, argv+1, IPADD_SAVE);
	if (matches(*argv, "showdump") == 0)
		return ipaddr_showdump();
	if (matches(*argv, "restore") == 0)
		return ipaddr_restore();
	if (matches(*argv, "help") == 0)
		usage();
	fprintf(stderr, "Command \"%s\" is unknown, try \"ip address help\".\n", *argv);
	exit(-1);
}
