144d362409d5469aed47d19e7908d19bd194493aThomas Graf/*
244d362409d5469aed47d19e7908d19bd194493aThomas Graf * lib/route/neightbl.c         neighbour tables
344d362409d5469aed47d19e7908d19bd194493aThomas Graf *
444d362409d5469aed47d19e7908d19bd194493aThomas Graf *	This library is free software; you can redistribute it and/or
544d362409d5469aed47d19e7908d19bd194493aThomas Graf *	modify it under the terms of the GNU Lesser General Public
644d362409d5469aed47d19e7908d19bd194493aThomas Graf *	License as published by the Free Software Foundation version 2.1
744d362409d5469aed47d19e7908d19bd194493aThomas Graf *	of the License.
844d362409d5469aed47d19e7908d19bd194493aThomas Graf *
98a3efffa5b3fde252675239914118664d36a2c24Thomas Graf * Copyright (c) 2003-2008 Thomas Graf <tgraf@suug.ch>
1044d362409d5469aed47d19e7908d19bd194493aThomas Graf */
1144d362409d5469aed47d19e7908d19bd194493aThomas Graf
1244d362409d5469aed47d19e7908d19bd194493aThomas Graf/**
1344d362409d5469aed47d19e7908d19bd194493aThomas Graf * @ingroup rtnl
1444d362409d5469aed47d19e7908d19bd194493aThomas Graf * @defgroup neightbl Neighbour Tables
1544d362409d5469aed47d19e7908d19bd194493aThomas Graf * @brief
1644d362409d5469aed47d19e7908d19bd194493aThomas Graf * @{
1744d362409d5469aed47d19e7908d19bd194493aThomas Graf */
1844d362409d5469aed47d19e7908d19bd194493aThomas Graf
19054c80d775f2ae9b8f50260bdfcb821e99c0da2aPaul Stewart#include <netlink-private/netlink.h>
2044d362409d5469aed47d19e7908d19bd194493aThomas Graf#include <netlink/netlink.h>
2144d362409d5469aed47d19e7908d19bd194493aThomas Graf#include <netlink/utils.h>
2244d362409d5469aed47d19e7908d19bd194493aThomas Graf#include <netlink/route/rtnl.h>
2344d362409d5469aed47d19e7908d19bd194493aThomas Graf#include <netlink/route/neightbl.h>
2444d362409d5469aed47d19e7908d19bd194493aThomas Graf#include <netlink/route/link.h>
2544d362409d5469aed47d19e7908d19bd194493aThomas Graf
2644d362409d5469aed47d19e7908d19bd194493aThomas Graf/** @cond SKIP */
2744d362409d5469aed47d19e7908d19bd194493aThomas Graf#define NEIGHTBL_ATTR_FAMILY       0x001
2844d362409d5469aed47d19e7908d19bd194493aThomas Graf#define NEIGHTBL_ATTR_STATS        0x002
2944d362409d5469aed47d19e7908d19bd194493aThomas Graf#define NEIGHTBL_ATTR_NAME	  0x004
3044d362409d5469aed47d19e7908d19bd194493aThomas Graf#define NEIGHTBL_ATTR_THRESH1	  0x008
3144d362409d5469aed47d19e7908d19bd194493aThomas Graf#define NEIGHTBL_ATTR_THRESH2	  0x010
3244d362409d5469aed47d19e7908d19bd194493aThomas Graf#define NEIGHTBL_ATTR_THRESH3	  0x020
3344d362409d5469aed47d19e7908d19bd194493aThomas Graf#define NEIGHTBL_ATTR_CONFIG	  0x040
3444d362409d5469aed47d19e7908d19bd194493aThomas Graf#define NEIGHTBL_ATTR_PARMS	  0x080
3544d362409d5469aed47d19e7908d19bd194493aThomas Graf#define NEIGHTBL_ATTR_GC_INTERVAL  0x100
3644d362409d5469aed47d19e7908d19bd194493aThomas Graf
3744d362409d5469aed47d19e7908d19bd194493aThomas Graf#define NEIGHTBLPARM_ATTR_IFINDEX	0x0001
3844d362409d5469aed47d19e7908d19bd194493aThomas Graf#define NEIGHTBLPARM_ATTR_REFCNT		0x0002
3944d362409d5469aed47d19e7908d19bd194493aThomas Graf#define NEIGHTBLPARM_ATTR_QUEUE_LEN	0x0004
4044d362409d5469aed47d19e7908d19bd194493aThomas Graf#define NEIGHTBLPARM_ATTR_APP_PROBES	0x0008
4144d362409d5469aed47d19e7908d19bd194493aThomas Graf#define NEIGHTBLPARM_ATTR_UCAST_PROBES	0x0010
4244d362409d5469aed47d19e7908d19bd194493aThomas Graf#define NEIGHTBLPARM_ATTR_MCAST_PROBES	0x0020
4344d362409d5469aed47d19e7908d19bd194493aThomas Graf#define NEIGHTBLPARM_ATTR_PROXY_QLEN	0x0040
4444d362409d5469aed47d19e7908d19bd194493aThomas Graf#define NEIGHTBLPARM_ATTR_REACHABLE_TIME	0x0080
4544d362409d5469aed47d19e7908d19bd194493aThomas Graf#define NEIGHTBLPARM_ATTR_BASE_REACHABLE_TIME 0x0100
4644d362409d5469aed47d19e7908d19bd194493aThomas Graf#define NEIGHTBLPARM_ATTR_RETRANS_TIME	0x0200
4744d362409d5469aed47d19e7908d19bd194493aThomas Graf#define NEIGHTBLPARM_ATTR_GC_STALETIME	0x0400
4844d362409d5469aed47d19e7908d19bd194493aThomas Graf#define NEIGHTBLPARM_ATTR_DELAY_PROBE_TIME 0x0800
4944d362409d5469aed47d19e7908d19bd194493aThomas Graf#define NEIGHTBLPARM_ATTR_ANYCAST_DELAY	0x1000
5044d362409d5469aed47d19e7908d19bd194493aThomas Graf#define NEIGHTBLPARM_ATTR_PROXY_DELAY	0x2000
5144d362409d5469aed47d19e7908d19bd194493aThomas Graf#define NEIGHTBLPARM_ATTR_LOCKTIME	0x4000
5244d362409d5469aed47d19e7908d19bd194493aThomas Graf
5344d362409d5469aed47d19e7908d19bd194493aThomas Grafstatic struct nl_cache_ops rtnl_neightbl_ops;
5444d362409d5469aed47d19e7908d19bd194493aThomas Grafstatic struct nl_object_ops neightbl_obj_ops;
5544d362409d5469aed47d19e7908d19bd194493aThomas Graf/** @endcond */
5644d362409d5469aed47d19e7908d19bd194493aThomas Graf
5744d362409d5469aed47d19e7908d19bd194493aThomas Grafstatic int neightbl_compare(struct nl_object *_a, struct nl_object *_b,
5844d362409d5469aed47d19e7908d19bd194493aThomas Graf			uint32_t attrs, int flags)
5944d362409d5469aed47d19e7908d19bd194493aThomas Graf{
6044d362409d5469aed47d19e7908d19bd194493aThomas Graf	struct rtnl_neightbl *a = (struct rtnl_neightbl *) _a;
6144d362409d5469aed47d19e7908d19bd194493aThomas Graf	struct rtnl_neightbl *b = (struct rtnl_neightbl *) _b;
6244d362409d5469aed47d19e7908d19bd194493aThomas Graf	int diff = 0;
6344d362409d5469aed47d19e7908d19bd194493aThomas Graf
6444d362409d5469aed47d19e7908d19bd194493aThomas Graf#define NT_DIFF(ATTR, EXPR) ATTR_DIFF(attrs, NEIGHTBL_ATTR_##ATTR, a, b, EXPR)
6544d362409d5469aed47d19e7908d19bd194493aThomas Graf
6644d362409d5469aed47d19e7908d19bd194493aThomas Graf	diff |= NT_DIFF(FAMILY,		a->nt_family != b->nt_family);
6744d362409d5469aed47d19e7908d19bd194493aThomas Graf	diff |= NT_DIFF(NAME,		strcmp(a->nt_name, b->nt_name));
6844d362409d5469aed47d19e7908d19bd194493aThomas Graf	diff |= NT_DIFF(THRESH1,	a->nt_gc_thresh1 != b->nt_gc_thresh1);
6944d362409d5469aed47d19e7908d19bd194493aThomas Graf	diff |= NT_DIFF(THRESH2,	a->nt_gc_thresh2 != b->nt_gc_thresh2);
7044d362409d5469aed47d19e7908d19bd194493aThomas Graf	diff |= NT_DIFF(THRESH3,	a->nt_gc_thresh3 != b->nt_gc_thresh3);
7144d362409d5469aed47d19e7908d19bd194493aThomas Graf	diff |= NT_DIFF(GC_INTERVAL,	a->nt_gc_interval != b->nt_gc_interval);
7244d362409d5469aed47d19e7908d19bd194493aThomas Graf
7344d362409d5469aed47d19e7908d19bd194493aThomas Graf#undef NT_DIFF
7444d362409d5469aed47d19e7908d19bd194493aThomas Graf
7544d362409d5469aed47d19e7908d19bd194493aThomas Graf	if (!(a->ce_mask & NEIGHTBL_ATTR_PARMS) &&
7644d362409d5469aed47d19e7908d19bd194493aThomas Graf	    !(b->ce_mask & NEIGHTBL_ATTR_PARMS))
7744d362409d5469aed47d19e7908d19bd194493aThomas Graf		return diff;
7844d362409d5469aed47d19e7908d19bd194493aThomas Graf
7944d362409d5469aed47d19e7908d19bd194493aThomas Graf	/* XXX: FIXME: Compare parameter table */
8044d362409d5469aed47d19e7908d19bd194493aThomas Graf
8144d362409d5469aed47d19e7908d19bd194493aThomas Graf
8244d362409d5469aed47d19e7908d19bd194493aThomas Graf#if 0
8344d362409d5469aed47d19e7908d19bd194493aThomas Graf#define REQ(F) (fp->ntp_mask & NEIGHTBLPARM_ATTR_##F)
8444d362409d5469aed47d19e7908d19bd194493aThomas Graf#define AVAIL(F) (op->ntp_mask & NEIGHTBLPARM_ATTR_##F)
8544d362409d5469aed47d19e7908d19bd194493aThomas Graf#define _C(F, N) (REQ(F) && (!AVAIL(F) || (op->N != fp->N)))
8644d362409d5469aed47d19e7908d19bd194493aThomas Graf	if (_C(IFINDEX,			ntp_ifindex)			||
8744d362409d5469aed47d19e7908d19bd194493aThomas Graf	    _C(QUEUE_LEN,		ntp_queue_len)			||
8844d362409d5469aed47d19e7908d19bd194493aThomas Graf	    _C(APP_PROBES,		ntp_app_probes)			||
8944d362409d5469aed47d19e7908d19bd194493aThomas Graf	    _C(UCAST_PROBES,		ntp_ucast_probes)		||
9044d362409d5469aed47d19e7908d19bd194493aThomas Graf	    _C(MCAST_PROBES,		ntp_mcast_probes)		||
9144d362409d5469aed47d19e7908d19bd194493aThomas Graf	    _C(PROXY_QLEN,		ntp_proxy_qlen)			||
9244d362409d5469aed47d19e7908d19bd194493aThomas Graf	    _C(LOCKTIME,		ntp_locktime)			||
9344d362409d5469aed47d19e7908d19bd194493aThomas Graf	    _C(RETRANS_TIME,		ntp_retrans_time)		||
9444d362409d5469aed47d19e7908d19bd194493aThomas Graf	    _C(BASE_REACHABLE_TIME,	ntp_base_reachable_time)	||
9544d362409d5469aed47d19e7908d19bd194493aThomas Graf	    _C(GC_STALETIME,		ntp_gc_stale_time)		||
9644d362409d5469aed47d19e7908d19bd194493aThomas Graf	    _C(DELAY_PROBE_TIME,	ntp_probe_delay)		||
9744d362409d5469aed47d19e7908d19bd194493aThomas Graf	    _C(ANYCAST_DELAY,		ntp_anycast_delay)		||
9844d362409d5469aed47d19e7908d19bd194493aThomas Graf	    _C(PROXY_DELAY,		ntp_proxy_delay))
9944d362409d5469aed47d19e7908d19bd194493aThomas Graf		return 0;
10044d362409d5469aed47d19e7908d19bd194493aThomas Graf#undef REQ
10144d362409d5469aed47d19e7908d19bd194493aThomas Graf#undef AVAIL
10244d362409d5469aed47d19e7908d19bd194493aThomas Graf#undef _C
10344d362409d5469aed47d19e7908d19bd194493aThomas Graf#endif
10444d362409d5469aed47d19e7908d19bd194493aThomas Graf
10544d362409d5469aed47d19e7908d19bd194493aThomas Graf	return diff;
10644d362409d5469aed47d19e7908d19bd194493aThomas Graf}
10744d362409d5469aed47d19e7908d19bd194493aThomas Graf
10844d362409d5469aed47d19e7908d19bd194493aThomas Graf
10944d362409d5469aed47d19e7908d19bd194493aThomas Grafstatic struct nla_policy neightbl_policy[NDTA_MAX+1] = {
11044d362409d5469aed47d19e7908d19bd194493aThomas Graf	[NDTA_NAME]		= { .type = NLA_STRING,
11144d362409d5469aed47d19e7908d19bd194493aThomas Graf				    .maxlen = NTBLNAMSIZ },
11244d362409d5469aed47d19e7908d19bd194493aThomas Graf	[NDTA_THRESH1]		= { .type = NLA_U32 },
11344d362409d5469aed47d19e7908d19bd194493aThomas Graf	[NDTA_THRESH2]		= { .type = NLA_U32 },
11444d362409d5469aed47d19e7908d19bd194493aThomas Graf	[NDTA_THRESH3]		= { .type = NLA_U32 },
11544d362409d5469aed47d19e7908d19bd194493aThomas Graf	[NDTA_GC_INTERVAL]	= { .type = NLA_U32 },
11644d362409d5469aed47d19e7908d19bd194493aThomas Graf	[NDTA_CONFIG]		= { .minlen = sizeof(struct ndt_config) },
11744d362409d5469aed47d19e7908d19bd194493aThomas Graf	[NDTA_STATS]		= { .minlen = sizeof(struct ndt_stats) },
11844d362409d5469aed47d19e7908d19bd194493aThomas Graf	[NDTA_PARMS]		= { .type = NLA_NESTED },
11944d362409d5469aed47d19e7908d19bd194493aThomas Graf};
12044d362409d5469aed47d19e7908d19bd194493aThomas Graf
12144d362409d5469aed47d19e7908d19bd194493aThomas Grafstatic int neightbl_msg_parser(struct nl_cache_ops *ops,
12244d362409d5469aed47d19e7908d19bd194493aThomas Graf			       struct sockaddr_nl *who, struct nlmsghdr *n,
1233040a1d6254465bed9e44e4d1bf279c2c50cd16aThomas Graf			       struct nl_parser_param *pp)
12444d362409d5469aed47d19e7908d19bd194493aThomas Graf{
12544d362409d5469aed47d19e7908d19bd194493aThomas Graf	struct rtnl_neightbl *ntbl;
12644d362409d5469aed47d19e7908d19bd194493aThomas Graf	struct nlattr *tb[NDTA_MAX + 1];
12744d362409d5469aed47d19e7908d19bd194493aThomas Graf	struct rtgenmsg *rtmsg;
12844d362409d5469aed47d19e7908d19bd194493aThomas Graf	int err;
12944d362409d5469aed47d19e7908d19bd194493aThomas Graf
13044d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl = rtnl_neightbl_alloc();
13144d362409d5469aed47d19e7908d19bd194493aThomas Graf	if (!ntbl) {
1328a3efffa5b3fde252675239914118664d36a2c24Thomas Graf		err = -NLE_NOMEM;
13344d362409d5469aed47d19e7908d19bd194493aThomas Graf		goto errout;
13444d362409d5469aed47d19e7908d19bd194493aThomas Graf	}
13544d362409d5469aed47d19e7908d19bd194493aThomas Graf
13644d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->ce_msgtype = n->nlmsg_type;
13744d362409d5469aed47d19e7908d19bd194493aThomas Graf	rtmsg = nlmsg_data(n);
13844d362409d5469aed47d19e7908d19bd194493aThomas Graf
13944d362409d5469aed47d19e7908d19bd194493aThomas Graf	err = nlmsg_parse(n, sizeof(*rtmsg), tb, NDTA_MAX, neightbl_policy);
14044d362409d5469aed47d19e7908d19bd194493aThomas Graf	if (err < 0)
14144d362409d5469aed47d19e7908d19bd194493aThomas Graf		goto errout;
14244d362409d5469aed47d19e7908d19bd194493aThomas Graf
14344d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_family = rtmsg->rtgen_family;
14444d362409d5469aed47d19e7908d19bd194493aThomas Graf
14544d362409d5469aed47d19e7908d19bd194493aThomas Graf	if (tb[NDTA_NAME] == NULL) {
146054c80d775f2ae9b8f50260bdfcb821e99c0da2aPaul Stewart		err = -NLE_MISSING_ATTR;
14744d362409d5469aed47d19e7908d19bd194493aThomas Graf		goto errout;
14844d362409d5469aed47d19e7908d19bd194493aThomas Graf	}
14944d362409d5469aed47d19e7908d19bd194493aThomas Graf
15044d362409d5469aed47d19e7908d19bd194493aThomas Graf	nla_strlcpy(ntbl->nt_name, tb[NDTA_NAME], NTBLNAMSIZ);
15144d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->ce_mask |= NEIGHTBL_ATTR_NAME;
15244d362409d5469aed47d19e7908d19bd194493aThomas Graf
15344d362409d5469aed47d19e7908d19bd194493aThomas Graf	if (tb[NDTA_THRESH1]) {
15444d362409d5469aed47d19e7908d19bd194493aThomas Graf		ntbl->nt_gc_thresh1 = nla_get_u32(tb[NDTA_THRESH1]);
15544d362409d5469aed47d19e7908d19bd194493aThomas Graf		ntbl->ce_mask |= NEIGHTBL_ATTR_THRESH1;
15644d362409d5469aed47d19e7908d19bd194493aThomas Graf	}
15744d362409d5469aed47d19e7908d19bd194493aThomas Graf
15844d362409d5469aed47d19e7908d19bd194493aThomas Graf	if (tb[NDTA_THRESH2]) {
15944d362409d5469aed47d19e7908d19bd194493aThomas Graf		ntbl->nt_gc_thresh2 = nla_get_u32(tb[NDTA_THRESH2]);
16044d362409d5469aed47d19e7908d19bd194493aThomas Graf		ntbl->ce_mask |= NEIGHTBL_ATTR_THRESH2;
16144d362409d5469aed47d19e7908d19bd194493aThomas Graf	}
16244d362409d5469aed47d19e7908d19bd194493aThomas Graf
16344d362409d5469aed47d19e7908d19bd194493aThomas Graf	if (tb[NDTA_THRESH3]) {
16444d362409d5469aed47d19e7908d19bd194493aThomas Graf		ntbl->nt_gc_thresh3 = nla_get_u32(tb[NDTA_THRESH3]);
16544d362409d5469aed47d19e7908d19bd194493aThomas Graf		ntbl->ce_mask |= NEIGHTBL_ATTR_THRESH3;
16644d362409d5469aed47d19e7908d19bd194493aThomas Graf	}
16744d362409d5469aed47d19e7908d19bd194493aThomas Graf
16844d362409d5469aed47d19e7908d19bd194493aThomas Graf	if (tb[NDTA_GC_INTERVAL]) {
16944d362409d5469aed47d19e7908d19bd194493aThomas Graf		ntbl->nt_gc_interval = nla_get_u32(tb[NDTA_GC_INTERVAL]);
17044d362409d5469aed47d19e7908d19bd194493aThomas Graf		ntbl->ce_mask |= NEIGHTBL_ATTR_GC_INTERVAL;
17144d362409d5469aed47d19e7908d19bd194493aThomas Graf	}
17244d362409d5469aed47d19e7908d19bd194493aThomas Graf
17344d362409d5469aed47d19e7908d19bd194493aThomas Graf	if (tb[NDTA_CONFIG]) {
17444d362409d5469aed47d19e7908d19bd194493aThomas Graf		nla_memcpy(&ntbl->nt_config, tb[NDTA_CONFIG],
17544d362409d5469aed47d19e7908d19bd194493aThomas Graf			   sizeof(ntbl->nt_config));
17644d362409d5469aed47d19e7908d19bd194493aThomas Graf		ntbl->ce_mask |= NEIGHTBL_ATTR_CONFIG;
17744d362409d5469aed47d19e7908d19bd194493aThomas Graf	}
17844d362409d5469aed47d19e7908d19bd194493aThomas Graf
17944d362409d5469aed47d19e7908d19bd194493aThomas Graf	if (tb[NDTA_STATS]) {
18044d362409d5469aed47d19e7908d19bd194493aThomas Graf		nla_memcpy(&ntbl->nt_stats, tb[NDTA_STATS],
18144d362409d5469aed47d19e7908d19bd194493aThomas Graf			   sizeof(ntbl->nt_stats));
18244d362409d5469aed47d19e7908d19bd194493aThomas Graf		ntbl->ce_mask |= NEIGHTBL_ATTR_STATS;
18344d362409d5469aed47d19e7908d19bd194493aThomas Graf	}
18444d362409d5469aed47d19e7908d19bd194493aThomas Graf
18544d362409d5469aed47d19e7908d19bd194493aThomas Graf	if (tb[NDTA_PARMS]) {
18644d362409d5469aed47d19e7908d19bd194493aThomas Graf		struct nlattr *tbp[NDTPA_MAX + 1];
18744d362409d5469aed47d19e7908d19bd194493aThomas Graf		struct rtnl_neightbl_parms *p = &ntbl->nt_parms;
18844d362409d5469aed47d19e7908d19bd194493aThomas Graf
18944d362409d5469aed47d19e7908d19bd194493aThomas Graf		err = nla_parse_nested(tbp, NDTPA_MAX, tb[NDTA_PARMS], NULL);
19044d362409d5469aed47d19e7908d19bd194493aThomas Graf		if (err < 0)
19144d362409d5469aed47d19e7908d19bd194493aThomas Graf			goto errout;
19244d362409d5469aed47d19e7908d19bd194493aThomas Graf
19344d362409d5469aed47d19e7908d19bd194493aThomas Graf#define COPY_ENTRY(name, var) \
19444d362409d5469aed47d19e7908d19bd194493aThomas Graf		if (tbp[NDTPA_ ##name]) { \
19544d362409d5469aed47d19e7908d19bd194493aThomas Graf			p->ntp_ ##var = nla_get_u32(tbp[NDTPA_ ##name]); \
19644d362409d5469aed47d19e7908d19bd194493aThomas Graf			p->ntp_mask |= NEIGHTBLPARM_ATTR_ ##name; \
19744d362409d5469aed47d19e7908d19bd194493aThomas Graf		}
19844d362409d5469aed47d19e7908d19bd194493aThomas Graf
19944d362409d5469aed47d19e7908d19bd194493aThomas Graf		COPY_ENTRY(IFINDEX, ifindex);
20044d362409d5469aed47d19e7908d19bd194493aThomas Graf		COPY_ENTRY(REFCNT, refcnt);
20144d362409d5469aed47d19e7908d19bd194493aThomas Graf		COPY_ENTRY(QUEUE_LEN, queue_len);
20244d362409d5469aed47d19e7908d19bd194493aThomas Graf		COPY_ENTRY(APP_PROBES, app_probes);
20344d362409d5469aed47d19e7908d19bd194493aThomas Graf		COPY_ENTRY(UCAST_PROBES, ucast_probes);
20444d362409d5469aed47d19e7908d19bd194493aThomas Graf		COPY_ENTRY(MCAST_PROBES, mcast_probes);
20544d362409d5469aed47d19e7908d19bd194493aThomas Graf		COPY_ENTRY(PROXY_QLEN, proxy_qlen);
20644d362409d5469aed47d19e7908d19bd194493aThomas Graf		COPY_ENTRY(PROXY_DELAY, proxy_delay);
20744d362409d5469aed47d19e7908d19bd194493aThomas Graf		COPY_ENTRY(ANYCAST_DELAY, anycast_delay);
20844d362409d5469aed47d19e7908d19bd194493aThomas Graf		COPY_ENTRY(LOCKTIME, locktime);
20944d362409d5469aed47d19e7908d19bd194493aThomas Graf		COPY_ENTRY(REACHABLE_TIME, reachable_time);
21044d362409d5469aed47d19e7908d19bd194493aThomas Graf		COPY_ENTRY(BASE_REACHABLE_TIME, base_reachable_time);
21144d362409d5469aed47d19e7908d19bd194493aThomas Graf		COPY_ENTRY(RETRANS_TIME, retrans_time);
21244d362409d5469aed47d19e7908d19bd194493aThomas Graf		COPY_ENTRY(GC_STALETIME, gc_stale_time);
21344d362409d5469aed47d19e7908d19bd194493aThomas Graf		COPY_ENTRY(DELAY_PROBE_TIME, probe_delay);
21444d362409d5469aed47d19e7908d19bd194493aThomas Graf#undef COPY_ENTRY
21544d362409d5469aed47d19e7908d19bd194493aThomas Graf
21644d362409d5469aed47d19e7908d19bd194493aThomas Graf		ntbl->ce_mask |= NEIGHTBL_ATTR_PARMS;
21744d362409d5469aed47d19e7908d19bd194493aThomas Graf	}
21844d362409d5469aed47d19e7908d19bd194493aThomas Graf
21944d362409d5469aed47d19e7908d19bd194493aThomas Graf	err = pp->pp_cb((struct nl_object *) ntbl, pp);
22044d362409d5469aed47d19e7908d19bd194493aThomas Graferrout:
22144d362409d5469aed47d19e7908d19bd194493aThomas Graf	rtnl_neightbl_put(ntbl);
22244d362409d5469aed47d19e7908d19bd194493aThomas Graf	return err;
22344d362409d5469aed47d19e7908d19bd194493aThomas Graf}
22444d362409d5469aed47d19e7908d19bd194493aThomas Graf
2251155370f520cb64657e25153255cf7dc1424317fThomas Grafstatic int neightbl_request_update(struct nl_cache *c, struct nl_sock *h)
22644d362409d5469aed47d19e7908d19bd194493aThomas Graf{
22744d362409d5469aed47d19e7908d19bd194493aThomas Graf	return nl_rtgen_request(h, RTM_GETNEIGHTBL, AF_UNSPEC, NLM_F_DUMP);
22844d362409d5469aed47d19e7908d19bd194493aThomas Graf}
22944d362409d5469aed47d19e7908d19bd194493aThomas Graf
23044d362409d5469aed47d19e7908d19bd194493aThomas Graf
231d84430702496f617c01c5e2d27d0e82e02390bb7Thomas Grafstatic void neightbl_dump_line(struct nl_object *arg, struct nl_dump_params *p)
23244d362409d5469aed47d19e7908d19bd194493aThomas Graf{
23344d362409d5469aed47d19e7908d19bd194493aThomas Graf	struct rtnl_neightbl *ntbl = (struct rtnl_neightbl *) arg;
23444d362409d5469aed47d19e7908d19bd194493aThomas Graf
235d84430702496f617c01c5e2d27d0e82e02390bb7Thomas Graf	nl_dump_line(p, "%s", ntbl->nt_name);
23644d362409d5469aed47d19e7908d19bd194493aThomas Graf
23744d362409d5469aed47d19e7908d19bd194493aThomas Graf	if (ntbl->nt_parms.ntp_mask & NEIGHTBLPARM_ATTR_IFINDEX) {
23844d362409d5469aed47d19e7908d19bd194493aThomas Graf		struct nl_cache *link_cache;
23944d362409d5469aed47d19e7908d19bd194493aThomas Graf
240054c80d775f2ae9b8f50260bdfcb821e99c0da2aPaul Stewart		link_cache = nl_cache_mngt_require_safe("route/link");
24144d362409d5469aed47d19e7908d19bd194493aThomas Graf
24244d362409d5469aed47d19e7908d19bd194493aThomas Graf		if (link_cache) {
24344d362409d5469aed47d19e7908d19bd194493aThomas Graf			char buf[32];
244d84430702496f617c01c5e2d27d0e82e02390bb7Thomas Graf			nl_dump(p, "<%s> ",
24544d362409d5469aed47d19e7908d19bd194493aThomas Graf				rtnl_link_i2name(link_cache,
24644d362409d5469aed47d19e7908d19bd194493aThomas Graf						 ntbl->nt_parms.ntp_ifindex,
24744d362409d5469aed47d19e7908d19bd194493aThomas Graf						 buf, sizeof(buf)));
248054c80d775f2ae9b8f50260bdfcb821e99c0da2aPaul Stewart			nl_cache_put(link_cache);
24944d362409d5469aed47d19e7908d19bd194493aThomas Graf		} else
250d84430702496f617c01c5e2d27d0e82e02390bb7Thomas Graf			nl_dump(p, "<%u> ", ntbl->nt_parms.ntp_ifindex);
25144d362409d5469aed47d19e7908d19bd194493aThomas Graf	} else
252d84430702496f617c01c5e2d27d0e82e02390bb7Thomas Graf		nl_dump(p, " ");
25344d362409d5469aed47d19e7908d19bd194493aThomas Graf
25444d362409d5469aed47d19e7908d19bd194493aThomas Graf	if (ntbl->ce_mask & NEIGHTBL_ATTR_CONFIG)
255d84430702496f617c01c5e2d27d0e82e02390bb7Thomas Graf		nl_dump(p, "entries %u ", ntbl->nt_config.ndtc_entries);
25644d362409d5469aed47d19e7908d19bd194493aThomas Graf
25744d362409d5469aed47d19e7908d19bd194493aThomas Graf	if (ntbl->ce_mask & NEIGHTBL_ATTR_PARMS) {
25844d362409d5469aed47d19e7908d19bd194493aThomas Graf		char rt[32], rt2[32];
25944d362409d5469aed47d19e7908d19bd194493aThomas Graf		struct rtnl_neightbl_parms *pa = &ntbl->nt_parms;
26044d362409d5469aed47d19e7908d19bd194493aThomas Graf
261d84430702496f617c01c5e2d27d0e82e02390bb7Thomas Graf		nl_dump(p, "reachable-time %s retransmit-time %s",
26244d362409d5469aed47d19e7908d19bd194493aThomas Graf			nl_msec2str(pa->ntp_reachable_time, rt, sizeof(rt)),
26344d362409d5469aed47d19e7908d19bd194493aThomas Graf			nl_msec2str(pa->ntp_retrans_time, rt2, sizeof(rt2)));
26444d362409d5469aed47d19e7908d19bd194493aThomas Graf	}
26544d362409d5469aed47d19e7908d19bd194493aThomas Graf
266d84430702496f617c01c5e2d27d0e82e02390bb7Thomas Graf	nl_dump(p, "\n");
26744d362409d5469aed47d19e7908d19bd194493aThomas Graf}
26844d362409d5469aed47d19e7908d19bd194493aThomas Graf
269d84430702496f617c01c5e2d27d0e82e02390bb7Thomas Grafstatic void neightbl_dump_details(struct nl_object *arg, struct nl_dump_params *p)
27044d362409d5469aed47d19e7908d19bd194493aThomas Graf{
27144d362409d5469aed47d19e7908d19bd194493aThomas Graf	char x[32], y[32], z[32];
27244d362409d5469aed47d19e7908d19bd194493aThomas Graf	struct rtnl_neightbl *ntbl = (struct rtnl_neightbl *) arg;
27344d362409d5469aed47d19e7908d19bd194493aThomas Graf
274d84430702496f617c01c5e2d27d0e82e02390bb7Thomas Graf	neightbl_dump_line(arg, p);
27544d362409d5469aed47d19e7908d19bd194493aThomas Graf
27644d362409d5469aed47d19e7908d19bd194493aThomas Graf	if (ntbl->ce_mask & NEIGHTBL_ATTR_CONFIG) {
277d84430702496f617c01c5e2d27d0e82e02390bb7Thomas Graf		nl_dump_line(p, "    key-len %u entry-size %u last-flush %s\n",
27844d362409d5469aed47d19e7908d19bd194493aThomas Graf			ntbl->nt_config.ndtc_key_len,
27944d362409d5469aed47d19e7908d19bd194493aThomas Graf			ntbl->nt_config.ndtc_entry_size,
28044d362409d5469aed47d19e7908d19bd194493aThomas Graf			nl_msec2str(ntbl->nt_config.ndtc_last_flush,
28144d362409d5469aed47d19e7908d19bd194493aThomas Graf				      x, sizeof(x)));
28244d362409d5469aed47d19e7908d19bd194493aThomas Graf
283d84430702496f617c01c5e2d27d0e82e02390bb7Thomas Graf		nl_dump_line(p, "    gc threshold %u/%u/%u interval %s " \
28444d362409d5469aed47d19e7908d19bd194493aThomas Graf			    "chain-position %u\n",
28544d362409d5469aed47d19e7908d19bd194493aThomas Graf			ntbl->nt_gc_thresh1, ntbl->nt_gc_thresh2,
28644d362409d5469aed47d19e7908d19bd194493aThomas Graf			ntbl->nt_gc_thresh3,
28744d362409d5469aed47d19e7908d19bd194493aThomas Graf			nl_msec2str(ntbl->nt_gc_interval, x, sizeof(x)),
28844d362409d5469aed47d19e7908d19bd194493aThomas Graf			ntbl->nt_config.ndtc_hash_chain_gc);
28944d362409d5469aed47d19e7908d19bd194493aThomas Graf
290d84430702496f617c01c5e2d27d0e82e02390bb7Thomas Graf		nl_dump_line(p, "    hash-rand 0x%08X/0x%08X last-rand %s\n",
29144d362409d5469aed47d19e7908d19bd194493aThomas Graf			ntbl->nt_config.ndtc_hash_rnd,
29244d362409d5469aed47d19e7908d19bd194493aThomas Graf			ntbl->nt_config.ndtc_hash_mask,
29344d362409d5469aed47d19e7908d19bd194493aThomas Graf			nl_msec2str(ntbl->nt_config.ndtc_last_rand,
29444d362409d5469aed47d19e7908d19bd194493aThomas Graf				      x, sizeof(x)));
29544d362409d5469aed47d19e7908d19bd194493aThomas Graf	}
29644d362409d5469aed47d19e7908d19bd194493aThomas Graf
29744d362409d5469aed47d19e7908d19bd194493aThomas Graf	if (ntbl->ce_mask & NEIGHTBL_ATTR_PARMS) {
29844d362409d5469aed47d19e7908d19bd194493aThomas Graf		struct rtnl_neightbl_parms *pa = &ntbl->nt_parms;
29944d362409d5469aed47d19e7908d19bd194493aThomas Graf
300d84430702496f617c01c5e2d27d0e82e02390bb7Thomas Graf		nl_dump_line(p, "    refcnt %u pending-queue-limit %u " \
30144d362409d5469aed47d19e7908d19bd194493aThomas Graf			    "proxy-delayed-queue-limit %u\n",
30244d362409d5469aed47d19e7908d19bd194493aThomas Graf			pa->ntp_refcnt,
30344d362409d5469aed47d19e7908d19bd194493aThomas Graf			pa->ntp_queue_len,
30444d362409d5469aed47d19e7908d19bd194493aThomas Graf			pa->ntp_proxy_qlen);
30544d362409d5469aed47d19e7908d19bd194493aThomas Graf
306d84430702496f617c01c5e2d27d0e82e02390bb7Thomas Graf		nl_dump_line(p, "    num-userspace-probes %u num-unicast-probes " \
30744d362409d5469aed47d19e7908d19bd194493aThomas Graf			    "%u num-multicast-probes %u\n",
30844d362409d5469aed47d19e7908d19bd194493aThomas Graf			pa->ntp_app_probes,
30944d362409d5469aed47d19e7908d19bd194493aThomas Graf			pa->ntp_ucast_probes,
31044d362409d5469aed47d19e7908d19bd194493aThomas Graf			pa->ntp_mcast_probes);
31144d362409d5469aed47d19e7908d19bd194493aThomas Graf
312d84430702496f617c01c5e2d27d0e82e02390bb7Thomas Graf		nl_dump_line(p, "    min-age %s base-reachable-time %s " \
31344d362409d5469aed47d19e7908d19bd194493aThomas Graf			    "stale-check-interval %s\n",
31444d362409d5469aed47d19e7908d19bd194493aThomas Graf			nl_msec2str(pa->ntp_locktime, x, sizeof(x)),
31544d362409d5469aed47d19e7908d19bd194493aThomas Graf			nl_msec2str(pa->ntp_base_reachable_time,
31644d362409d5469aed47d19e7908d19bd194493aThomas Graf				      y, sizeof(y)),
31744d362409d5469aed47d19e7908d19bd194493aThomas Graf			nl_msec2str(pa->ntp_gc_stale_time, z, sizeof(z)));
31844d362409d5469aed47d19e7908d19bd194493aThomas Graf
319d84430702496f617c01c5e2d27d0e82e02390bb7Thomas Graf		nl_dump_line(p, "    initial-probe-delay %s answer-delay %s " \
32044d362409d5469aed47d19e7908d19bd194493aThomas Graf			    "proxy-answer-delay %s\n",
32144d362409d5469aed47d19e7908d19bd194493aThomas Graf			nl_msec2str(pa->ntp_probe_delay, x, sizeof(x)),
32244d362409d5469aed47d19e7908d19bd194493aThomas Graf			nl_msec2str(pa->ntp_anycast_delay, y, sizeof(y)),
32344d362409d5469aed47d19e7908d19bd194493aThomas Graf			nl_msec2str(pa->ntp_proxy_delay, z, sizeof(z)));
32444d362409d5469aed47d19e7908d19bd194493aThomas Graf	}
32544d362409d5469aed47d19e7908d19bd194493aThomas Graf}
32644d362409d5469aed47d19e7908d19bd194493aThomas Graf
327d84430702496f617c01c5e2d27d0e82e02390bb7Thomas Grafstatic void neightbl_dump_stats(struct nl_object *arg, struct nl_dump_params *p)
32844d362409d5469aed47d19e7908d19bd194493aThomas Graf{
32944d362409d5469aed47d19e7908d19bd194493aThomas Graf	struct rtnl_neightbl *ntbl = (struct rtnl_neightbl *) arg;
330d84430702496f617c01c5e2d27d0e82e02390bb7Thomas Graf
331d84430702496f617c01c5e2d27d0e82e02390bb7Thomas Graf	neightbl_dump_details(arg, p);
33244d362409d5469aed47d19e7908d19bd194493aThomas Graf
33344d362409d5469aed47d19e7908d19bd194493aThomas Graf	if (!(ntbl->ce_mask & NEIGHTBL_ATTR_STATS))
334d84430702496f617c01c5e2d27d0e82e02390bb7Thomas Graf		return;
33544d362409d5469aed47d19e7908d19bd194493aThomas Graf
336054c80d775f2ae9b8f50260bdfcb821e99c0da2aPaul Stewart	nl_dump_line(p, "   " \
337054c80d775f2ae9b8f50260bdfcb821e99c0da2aPaul Stewart                    " lookups %" PRIu64 \
338054c80d775f2ae9b8f50260bdfcb821e99c0da2aPaul Stewart                    " hits %" PRIu64 \
339054c80d775f2ae9b8f50260bdfcb821e99c0da2aPaul Stewart                    " failed %" PRIu64 \
340054c80d775f2ae9b8f50260bdfcb821e99c0da2aPaul Stewart		    " allocations %" PRIu64 \
341054c80d775f2ae9b8f50260bdfcb821e99c0da2aPaul Stewart                    " destroys %" PRIu64 \
342054c80d775f2ae9b8f50260bdfcb821e99c0da2aPaul Stewart                    "\n",
34344d362409d5469aed47d19e7908d19bd194493aThomas Graf		ntbl->nt_stats.ndts_lookups,
34444d362409d5469aed47d19e7908d19bd194493aThomas Graf		ntbl->nt_stats.ndts_hits,
34544d362409d5469aed47d19e7908d19bd194493aThomas Graf		ntbl->nt_stats.ndts_res_failed,
34644d362409d5469aed47d19e7908d19bd194493aThomas Graf		ntbl->nt_stats.ndts_allocs,
34744d362409d5469aed47d19e7908d19bd194493aThomas Graf		ntbl->nt_stats.ndts_destroys);
34844d362409d5469aed47d19e7908d19bd194493aThomas Graf
349054c80d775f2ae9b8f50260bdfcb821e99c0da2aPaul Stewart	nl_dump_line(p, "   " \
350054c80d775f2ae9b8f50260bdfcb821e99c0da2aPaul Stewart                        " hash-grows %" PRIu64 \
351054c80d775f2ae9b8f50260bdfcb821e99c0da2aPaul Stewart                        " forced-gc-runs %" PRIu64 \
352054c80d775f2ae9b8f50260bdfcb821e99c0da2aPaul Stewart                        " periodic-gc-runs %" PRIu64 \
353054c80d775f2ae9b8f50260bdfcb821e99c0da2aPaul Stewart                        "\n",
35444d362409d5469aed47d19e7908d19bd194493aThomas Graf		ntbl->nt_stats.ndts_hash_grows,
35544d362409d5469aed47d19e7908d19bd194493aThomas Graf		ntbl->nt_stats.ndts_forced_gc_runs,
35644d362409d5469aed47d19e7908d19bd194493aThomas Graf		ntbl->nt_stats.ndts_periodic_gc_runs);
35744d362409d5469aed47d19e7908d19bd194493aThomas Graf
358054c80d775f2ae9b8f50260bdfcb821e99c0da2aPaul Stewart	nl_dump_line(p, "   " \
359054c80d775f2ae9b8f50260bdfcb821e99c0da2aPaul Stewart                        " rcv-unicast-probes %" PRIu64 \
360054c80d775f2ae9b8f50260bdfcb821e99c0da2aPaul Stewart                        " rcv-multicast-probes %" PRIu64 \
361054c80d775f2ae9b8f50260bdfcb821e99c0da2aPaul Stewart                        "\n",
36244d362409d5469aed47d19e7908d19bd194493aThomas Graf		ntbl->nt_stats.ndts_rcv_probes_ucast,
36344d362409d5469aed47d19e7908d19bd194493aThomas Graf		ntbl->nt_stats.ndts_rcv_probes_mcast);
36444d362409d5469aed47d19e7908d19bd194493aThomas Graf}
36544d362409d5469aed47d19e7908d19bd194493aThomas Graf
36644d362409d5469aed47d19e7908d19bd194493aThomas Graf/**
36744d362409d5469aed47d19e7908d19bd194493aThomas Graf * @name Allocation/Freeing
36844d362409d5469aed47d19e7908d19bd194493aThomas Graf * @{
36944d362409d5469aed47d19e7908d19bd194493aThomas Graf */
37044d362409d5469aed47d19e7908d19bd194493aThomas Graf
37144d362409d5469aed47d19e7908d19bd194493aThomas Grafstruct rtnl_neightbl *rtnl_neightbl_alloc(void)
37244d362409d5469aed47d19e7908d19bd194493aThomas Graf{
37344d362409d5469aed47d19e7908d19bd194493aThomas Graf	return (struct rtnl_neightbl *) nl_object_alloc(&neightbl_obj_ops);
37444d362409d5469aed47d19e7908d19bd194493aThomas Graf}
37544d362409d5469aed47d19e7908d19bd194493aThomas Graf
37644d362409d5469aed47d19e7908d19bd194493aThomas Grafvoid rtnl_neightbl_put(struct rtnl_neightbl *neightbl)
37744d362409d5469aed47d19e7908d19bd194493aThomas Graf{
37844d362409d5469aed47d19e7908d19bd194493aThomas Graf	nl_object_put((struct nl_object *) neightbl);
37944d362409d5469aed47d19e7908d19bd194493aThomas Graf}
38044d362409d5469aed47d19e7908d19bd194493aThomas Graf
38144d362409d5469aed47d19e7908d19bd194493aThomas Graf/** @} */
38244d362409d5469aed47d19e7908d19bd194493aThomas Graf
38344d362409d5469aed47d19e7908d19bd194493aThomas Graf/**
38444d362409d5469aed47d19e7908d19bd194493aThomas Graf * @name Neighbour Table Cache Management
38544d362409d5469aed47d19e7908d19bd194493aThomas Graf * @{
38644d362409d5469aed47d19e7908d19bd194493aThomas Graf */
38744d362409d5469aed47d19e7908d19bd194493aThomas Graf
38844d362409d5469aed47d19e7908d19bd194493aThomas Graf/**
38944d362409d5469aed47d19e7908d19bd194493aThomas Graf * Build a neighbour table cache including all neighbour tables currently configured in the kernel.
3901155370f520cb64657e25153255cf7dc1424317fThomas Graf * @arg sk		Netlink socket.
3918a3efffa5b3fde252675239914118664d36a2c24Thomas Graf * @arg result		Pointer to store resulting cache.
39244d362409d5469aed47d19e7908d19bd194493aThomas Graf *
39344d362409d5469aed47d19e7908d19bd194493aThomas Graf * Allocates a new neighbour table cache, initializes it properly and
39444d362409d5469aed47d19e7908d19bd194493aThomas Graf * updates it to include all neighbour tables currently configured in
39544d362409d5469aed47d19e7908d19bd194493aThomas Graf * the kernel.
39644d362409d5469aed47d19e7908d19bd194493aThomas Graf *
3978a3efffa5b3fde252675239914118664d36a2c24Thomas Graf * @return 0 on success or a negative error code.
39844d362409d5469aed47d19e7908d19bd194493aThomas Graf */
3991155370f520cb64657e25153255cf7dc1424317fThomas Grafint rtnl_neightbl_alloc_cache(struct nl_sock *sk, struct nl_cache **result)
40044d362409d5469aed47d19e7908d19bd194493aThomas Graf{
4011155370f520cb64657e25153255cf7dc1424317fThomas Graf	return nl_cache_alloc_and_fill(&rtnl_neightbl_ops, sk, result);
40244d362409d5469aed47d19e7908d19bd194493aThomas Graf}
40344d362409d5469aed47d19e7908d19bd194493aThomas Graf
40444d362409d5469aed47d19e7908d19bd194493aThomas Graf/**
40544d362409d5469aed47d19e7908d19bd194493aThomas Graf * Lookup neighbour table by name and optional interface index
40644d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg cache		neighbour table cache
40744d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg name		name of table
40844d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg ifindex		optional interface index
40944d362409d5469aed47d19e7908d19bd194493aThomas Graf *
41044d362409d5469aed47d19e7908d19bd194493aThomas Graf * Looks up the neighbour table matching the specified name and
41144d362409d5469aed47d19e7908d19bd194493aThomas Graf * optionally the specified ifindex to retrieve device specific
41244d362409d5469aed47d19e7908d19bd194493aThomas Graf * parameter sets.
41344d362409d5469aed47d19e7908d19bd194493aThomas Graf *
41444d362409d5469aed47d19e7908d19bd194493aThomas Graf * @return ptr to neighbour table inside the cache or NULL if no
41544d362409d5469aed47d19e7908d19bd194493aThomas Graf *         match was found.
41644d362409d5469aed47d19e7908d19bd194493aThomas Graf */
41744d362409d5469aed47d19e7908d19bd194493aThomas Grafstruct rtnl_neightbl *rtnl_neightbl_get(struct nl_cache *cache,
41844d362409d5469aed47d19e7908d19bd194493aThomas Graf					const char *name, int ifindex)
41944d362409d5469aed47d19e7908d19bd194493aThomas Graf{
42044d362409d5469aed47d19e7908d19bd194493aThomas Graf	struct rtnl_neightbl *nt;
42144d362409d5469aed47d19e7908d19bd194493aThomas Graf
42244d362409d5469aed47d19e7908d19bd194493aThomas Graf	if (cache->c_ops != &rtnl_neightbl_ops)
42344d362409d5469aed47d19e7908d19bd194493aThomas Graf		return NULL;
42444d362409d5469aed47d19e7908d19bd194493aThomas Graf
42544d362409d5469aed47d19e7908d19bd194493aThomas Graf	nl_list_for_each_entry(nt, &cache->c_items, ce_list) {
42644d362409d5469aed47d19e7908d19bd194493aThomas Graf		if (!strcasecmp(nt->nt_name, name) &&
42744d362409d5469aed47d19e7908d19bd194493aThomas Graf		    ((!ifindex && !nt->nt_parms.ntp_ifindex) ||
42844d362409d5469aed47d19e7908d19bd194493aThomas Graf		     (ifindex && ifindex == nt->nt_parms.ntp_ifindex))) {
42944d362409d5469aed47d19e7908d19bd194493aThomas Graf			nl_object_get((struct nl_object *) nt);
43044d362409d5469aed47d19e7908d19bd194493aThomas Graf			return nt;
43144d362409d5469aed47d19e7908d19bd194493aThomas Graf		}
43244d362409d5469aed47d19e7908d19bd194493aThomas Graf	}
43344d362409d5469aed47d19e7908d19bd194493aThomas Graf
43444d362409d5469aed47d19e7908d19bd194493aThomas Graf	return NULL;
43544d362409d5469aed47d19e7908d19bd194493aThomas Graf}
43644d362409d5469aed47d19e7908d19bd194493aThomas Graf
43744d362409d5469aed47d19e7908d19bd194493aThomas Graf/** @} */
43844d362409d5469aed47d19e7908d19bd194493aThomas Graf
43944d362409d5469aed47d19e7908d19bd194493aThomas Graf/**
44044d362409d5469aed47d19e7908d19bd194493aThomas Graf * @name Neighbour Table Modifications
44144d362409d5469aed47d19e7908d19bd194493aThomas Graf * @{
44244d362409d5469aed47d19e7908d19bd194493aThomas Graf */
44344d362409d5469aed47d19e7908d19bd194493aThomas Graf
44444d362409d5469aed47d19e7908d19bd194493aThomas Graf/**
44544d362409d5469aed47d19e7908d19bd194493aThomas Graf * Builds a netlink change request message to change neighbour table attributes
44644d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg old		neighbour table to change
44744d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg tmpl		template with requested changes
4488a3efffa5b3fde252675239914118664d36a2c24Thomas Graf * @arg result		Pointer to store resulting message.
44944d362409d5469aed47d19e7908d19bd194493aThomas Graf *
45044d362409d5469aed47d19e7908d19bd194493aThomas Graf * Builds a new netlink message requesting a change of neighbour table
45144d362409d5469aed47d19e7908d19bd194493aThomas Graf * attributes. The netlink message header isn't fully equipped with all
45244d362409d5469aed47d19e7908d19bd194493aThomas Graf * relevant fields and must be sent out via nl_send_auto_complete() or
45344d362409d5469aed47d19e7908d19bd194493aThomas Graf * supplemented as needed.
45444d362409d5469aed47d19e7908d19bd194493aThomas Graf * \a old must point to a neighbour table currently configured in the
45544d362409d5469aed47d19e7908d19bd194493aThomas Graf * kernel and \a tmpl must contain the attributes to be changed set via
45644d362409d5469aed47d19e7908d19bd194493aThomas Graf * \c rtnl_neightbl_set_* functions.
45744d362409d5469aed47d19e7908d19bd194493aThomas Graf *
4588a3efffa5b3fde252675239914118664d36a2c24Thomas Graf * @return 0 on success or a negative error code.
45944d362409d5469aed47d19e7908d19bd194493aThomas Graf */
4608a3efffa5b3fde252675239914118664d36a2c24Thomas Grafint rtnl_neightbl_build_change_request(struct rtnl_neightbl *old,
4618a3efffa5b3fde252675239914118664d36a2c24Thomas Graf				       struct rtnl_neightbl *tmpl,
4628a3efffa5b3fde252675239914118664d36a2c24Thomas Graf				       struct nl_msg **result)
46344d362409d5469aed47d19e7908d19bd194493aThomas Graf{
4648a3efffa5b3fde252675239914118664d36a2c24Thomas Graf	struct nl_msg *m, *parms = NULL;
46544d362409d5469aed47d19e7908d19bd194493aThomas Graf	struct ndtmsg ndt = {
46644d362409d5469aed47d19e7908d19bd194493aThomas Graf		.ndtm_family = old->nt_family,
46744d362409d5469aed47d19e7908d19bd194493aThomas Graf	};
46844d362409d5469aed47d19e7908d19bd194493aThomas Graf
46944d362409d5469aed47d19e7908d19bd194493aThomas Graf	m = nlmsg_alloc_simple(RTM_SETNEIGHTBL, 0);
4708a3efffa5b3fde252675239914118664d36a2c24Thomas Graf	if (!m)
4718a3efffa5b3fde252675239914118664d36a2c24Thomas Graf		return -NLE_NOMEM;
4728a3efffa5b3fde252675239914118664d36a2c24Thomas Graf
4738a3efffa5b3fde252675239914118664d36a2c24Thomas Graf	if (nlmsg_append(m, &ndt, sizeof(ndt), NLMSG_ALIGNTO) < 0)
4748a3efffa5b3fde252675239914118664d36a2c24Thomas Graf		goto nla_put_failure;
47544d362409d5469aed47d19e7908d19bd194493aThomas Graf
4768a3efffa5b3fde252675239914118664d36a2c24Thomas Graf	NLA_PUT_STRING(m, NDTA_NAME, old->nt_name);
47744d362409d5469aed47d19e7908d19bd194493aThomas Graf
47844d362409d5469aed47d19e7908d19bd194493aThomas Graf	if (tmpl->ce_mask & NEIGHTBL_ATTR_THRESH1)
4798a3efffa5b3fde252675239914118664d36a2c24Thomas Graf		NLA_PUT_U32(m, NDTA_THRESH1, tmpl->nt_gc_thresh1);
48044d362409d5469aed47d19e7908d19bd194493aThomas Graf
48144d362409d5469aed47d19e7908d19bd194493aThomas Graf	if (tmpl->ce_mask & NEIGHTBL_ATTR_THRESH2)
4828a3efffa5b3fde252675239914118664d36a2c24Thomas Graf		NLA_PUT_U32(m, NDTA_THRESH2, tmpl->nt_gc_thresh2);
48344d362409d5469aed47d19e7908d19bd194493aThomas Graf
48444d362409d5469aed47d19e7908d19bd194493aThomas Graf	if (tmpl->ce_mask & NEIGHTBL_ATTR_THRESH2)
4858a3efffa5b3fde252675239914118664d36a2c24Thomas Graf		NLA_PUT_U32(m, NDTA_THRESH2, tmpl->nt_gc_thresh2);
48644d362409d5469aed47d19e7908d19bd194493aThomas Graf
48744d362409d5469aed47d19e7908d19bd194493aThomas Graf	if (tmpl->ce_mask & NEIGHTBL_ATTR_GC_INTERVAL)
4888a3efffa5b3fde252675239914118664d36a2c24Thomas Graf		NLA_PUT_U64(m, NDTA_GC_INTERVAL,
48944d362409d5469aed47d19e7908d19bd194493aThomas Graf				      tmpl->nt_gc_interval);
49044d362409d5469aed47d19e7908d19bd194493aThomas Graf
49144d362409d5469aed47d19e7908d19bd194493aThomas Graf	if (tmpl->ce_mask & NEIGHTBL_ATTR_PARMS) {
49244d362409d5469aed47d19e7908d19bd194493aThomas Graf		struct rtnl_neightbl_parms *p = &tmpl->nt_parms;
4938a3efffa5b3fde252675239914118664d36a2c24Thomas Graf
4948a3efffa5b3fde252675239914118664d36a2c24Thomas Graf		parms = nlmsg_alloc();
4958a3efffa5b3fde252675239914118664d36a2c24Thomas Graf		if (!parms)
4968a3efffa5b3fde252675239914118664d36a2c24Thomas Graf			goto nla_put_failure;
49744d362409d5469aed47d19e7908d19bd194493aThomas Graf
49844d362409d5469aed47d19e7908d19bd194493aThomas Graf		if (old->nt_parms.ntp_mask & NEIGHTBLPARM_ATTR_IFINDEX)
4998a3efffa5b3fde252675239914118664d36a2c24Thomas Graf			NLA_PUT_U32(parms, NDTPA_IFINDEX,
50044d362409d5469aed47d19e7908d19bd194493aThomas Graf					      old->nt_parms.ntp_ifindex);
50144d362409d5469aed47d19e7908d19bd194493aThomas Graf
50244d362409d5469aed47d19e7908d19bd194493aThomas Graf
50344d362409d5469aed47d19e7908d19bd194493aThomas Graf		if (p->ntp_mask & NEIGHTBLPARM_ATTR_QUEUE_LEN)
5048a3efffa5b3fde252675239914118664d36a2c24Thomas Graf			NLA_PUT_U32(parms, NDTPA_QUEUE_LEN, p->ntp_queue_len);
50544d362409d5469aed47d19e7908d19bd194493aThomas Graf
50644d362409d5469aed47d19e7908d19bd194493aThomas Graf		if (p->ntp_mask & NEIGHTBLPARM_ATTR_APP_PROBES)
5078a3efffa5b3fde252675239914118664d36a2c24Thomas Graf			NLA_PUT_U32(parms, NDTPA_APP_PROBES, p->ntp_app_probes);
50844d362409d5469aed47d19e7908d19bd194493aThomas Graf
50944d362409d5469aed47d19e7908d19bd194493aThomas Graf		if (p->ntp_mask & NEIGHTBLPARM_ATTR_UCAST_PROBES)
5108a3efffa5b3fde252675239914118664d36a2c24Thomas Graf			NLA_PUT_U32(parms, NDTPA_UCAST_PROBES,
51144d362409d5469aed47d19e7908d19bd194493aThomas Graf				    p->ntp_ucast_probes);
51244d362409d5469aed47d19e7908d19bd194493aThomas Graf
51344d362409d5469aed47d19e7908d19bd194493aThomas Graf		if (p->ntp_mask & NEIGHTBLPARM_ATTR_MCAST_PROBES)
5148a3efffa5b3fde252675239914118664d36a2c24Thomas Graf			NLA_PUT_U32(parms, NDTPA_MCAST_PROBES,
51544d362409d5469aed47d19e7908d19bd194493aThomas Graf				    p->ntp_mcast_probes);
51644d362409d5469aed47d19e7908d19bd194493aThomas Graf
51744d362409d5469aed47d19e7908d19bd194493aThomas Graf		if (p->ntp_mask & NEIGHTBLPARM_ATTR_PROXY_QLEN)
5188a3efffa5b3fde252675239914118664d36a2c24Thomas Graf			NLA_PUT_U32(parms, NDTPA_PROXY_QLEN,
51944d362409d5469aed47d19e7908d19bd194493aThomas Graf				    p->ntp_proxy_qlen);
52044d362409d5469aed47d19e7908d19bd194493aThomas Graf
52144d362409d5469aed47d19e7908d19bd194493aThomas Graf		if (p->ntp_mask & NEIGHTBLPARM_ATTR_BASE_REACHABLE_TIME)
5228a3efffa5b3fde252675239914118664d36a2c24Thomas Graf			NLA_PUT_U64(parms, NDTPA_BASE_REACHABLE_TIME,
52344d362409d5469aed47d19e7908d19bd194493aThomas Graf				    p->ntp_base_reachable_time);
52444d362409d5469aed47d19e7908d19bd194493aThomas Graf
52544d362409d5469aed47d19e7908d19bd194493aThomas Graf		if (p->ntp_mask & NEIGHTBLPARM_ATTR_RETRANS_TIME)
5268a3efffa5b3fde252675239914118664d36a2c24Thomas Graf			NLA_PUT_U64(parms, NDTPA_RETRANS_TIME,
52744d362409d5469aed47d19e7908d19bd194493aThomas Graf				    p->ntp_retrans_time);
52844d362409d5469aed47d19e7908d19bd194493aThomas Graf
52944d362409d5469aed47d19e7908d19bd194493aThomas Graf		if (p->ntp_mask & NEIGHTBLPARM_ATTR_GC_STALETIME)
5308a3efffa5b3fde252675239914118664d36a2c24Thomas Graf			NLA_PUT_U64(parms, NDTPA_GC_STALETIME,
53144d362409d5469aed47d19e7908d19bd194493aThomas Graf				    p->ntp_gc_stale_time);
53244d362409d5469aed47d19e7908d19bd194493aThomas Graf
53344d362409d5469aed47d19e7908d19bd194493aThomas Graf		if (p->ntp_mask & NEIGHTBLPARM_ATTR_DELAY_PROBE_TIME)
5348a3efffa5b3fde252675239914118664d36a2c24Thomas Graf			NLA_PUT_U64(parms, NDTPA_DELAY_PROBE_TIME,
53544d362409d5469aed47d19e7908d19bd194493aThomas Graf				    p->ntp_proxy_delay);
53644d362409d5469aed47d19e7908d19bd194493aThomas Graf
53744d362409d5469aed47d19e7908d19bd194493aThomas Graf		if (p->ntp_mask & NEIGHTBLPARM_ATTR_ANYCAST_DELAY)
5388a3efffa5b3fde252675239914118664d36a2c24Thomas Graf			NLA_PUT_U64(parms, NDTPA_ANYCAST_DELAY,
53944d362409d5469aed47d19e7908d19bd194493aThomas Graf				    p->ntp_anycast_delay);
54044d362409d5469aed47d19e7908d19bd194493aThomas Graf
54144d362409d5469aed47d19e7908d19bd194493aThomas Graf		if (p->ntp_mask & NEIGHTBLPARM_ATTR_PROXY_DELAY)
5428a3efffa5b3fde252675239914118664d36a2c24Thomas Graf			NLA_PUT_U64(parms, NDTPA_PROXY_DELAY,
54344d362409d5469aed47d19e7908d19bd194493aThomas Graf					      p->ntp_proxy_delay);
54444d362409d5469aed47d19e7908d19bd194493aThomas Graf
54544d362409d5469aed47d19e7908d19bd194493aThomas Graf		if (p->ntp_mask & NEIGHTBLPARM_ATTR_LOCKTIME)
5468a3efffa5b3fde252675239914118664d36a2c24Thomas Graf			NLA_PUT_U64(parms, NDTPA_LOCKTIME, p->ntp_locktime);
5478a3efffa5b3fde252675239914118664d36a2c24Thomas Graf
5488a3efffa5b3fde252675239914118664d36a2c24Thomas Graf		if (nla_put_nested(m, NDTA_PARMS, parms) < 0)
5498a3efffa5b3fde252675239914118664d36a2c24Thomas Graf			goto nla_put_failure;
55044d362409d5469aed47d19e7908d19bd194493aThomas Graf
55144d362409d5469aed47d19e7908d19bd194493aThomas Graf		nlmsg_free(parms);
55244d362409d5469aed47d19e7908d19bd194493aThomas Graf	}
5538a3efffa5b3fde252675239914118664d36a2c24Thomas Graf
5548a3efffa5b3fde252675239914118664d36a2c24Thomas Graf	*result = m;
5558a3efffa5b3fde252675239914118664d36a2c24Thomas Graf	return 0;
5568a3efffa5b3fde252675239914118664d36a2c24Thomas Graf
5578a3efffa5b3fde252675239914118664d36a2c24Thomas Grafnla_put_failure:
5588a3efffa5b3fde252675239914118664d36a2c24Thomas Graf	if (parms)
5598a3efffa5b3fde252675239914118664d36a2c24Thomas Graf		nlmsg_free(parms);
5608a3efffa5b3fde252675239914118664d36a2c24Thomas Graf	nlmsg_free(m);
5618a3efffa5b3fde252675239914118664d36a2c24Thomas Graf	return -NLE_MSGSIZE;
56244d362409d5469aed47d19e7908d19bd194493aThomas Graf}
56344d362409d5469aed47d19e7908d19bd194493aThomas Graf
56444d362409d5469aed47d19e7908d19bd194493aThomas Graf/**
56544d362409d5469aed47d19e7908d19bd194493aThomas Graf * Change neighbour table attributes
5661155370f520cb64657e25153255cf7dc1424317fThomas Graf * @arg sk		Netlink socket.
56744d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg old		neighbour table to be changed
56844d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg tmpl		template with requested changes
56944d362409d5469aed47d19e7908d19bd194493aThomas Graf *
57044d362409d5469aed47d19e7908d19bd194493aThomas Graf * Builds a new netlink message by calling
57144d362409d5469aed47d19e7908d19bd194493aThomas Graf * rtnl_neightbl_build_change_request(), sends the request to the
57244d362409d5469aed47d19e7908d19bd194493aThomas Graf * kernel and waits for the next ACK to be received, i.e. blocks
57344d362409d5469aed47d19e7908d19bd194493aThomas Graf * until the request has been processed.
57444d362409d5469aed47d19e7908d19bd194493aThomas Graf *
57544d362409d5469aed47d19e7908d19bd194493aThomas Graf * @return 0 on success or a negative error code
57644d362409d5469aed47d19e7908d19bd194493aThomas Graf */
5771155370f520cb64657e25153255cf7dc1424317fThomas Grafint rtnl_neightbl_change(struct nl_sock *sk, struct rtnl_neightbl *old,
57844d362409d5469aed47d19e7908d19bd194493aThomas Graf			 struct rtnl_neightbl *tmpl)
57944d362409d5469aed47d19e7908d19bd194493aThomas Graf{
58044d362409d5469aed47d19e7908d19bd194493aThomas Graf	struct nl_msg *msg;
5818a3efffa5b3fde252675239914118664d36a2c24Thomas Graf	int err;
58244d362409d5469aed47d19e7908d19bd194493aThomas Graf
5838a3efffa5b3fde252675239914118664d36a2c24Thomas Graf	if ((err = rtnl_neightbl_build_change_request(old, tmpl, &msg)) < 0)
5848a3efffa5b3fde252675239914118664d36a2c24Thomas Graf		return err;
5858a3efffa5b3fde252675239914118664d36a2c24Thomas Graf
586ef50a38fbd8682a5c9efd559e7db68664977f080Thomas Graf	err = nl_send_auto_complete(sk, msg);
587ef50a38fbd8682a5c9efd559e7db68664977f080Thomas Graf	nlmsg_free(msg);
588ef50a38fbd8682a5c9efd559e7db68664977f080Thomas Graf	if (err < 0)
58944d362409d5469aed47d19e7908d19bd194493aThomas Graf		return err;
59044d362409d5469aed47d19e7908d19bd194493aThomas Graf
591cfcfca070355b246028df60da79813f09ed65755Thomas Graf	return wait_for_ack(sk);
59244d362409d5469aed47d19e7908d19bd194493aThomas Graf}
59344d362409d5469aed47d19e7908d19bd194493aThomas Graf
59444d362409d5469aed47d19e7908d19bd194493aThomas Graf/** @} */
59544d362409d5469aed47d19e7908d19bd194493aThomas Graf
59644d362409d5469aed47d19e7908d19bd194493aThomas Graf/**
59744d362409d5469aed47d19e7908d19bd194493aThomas Graf * @name Attribute Modification
59844d362409d5469aed47d19e7908d19bd194493aThomas Graf * @{
59944d362409d5469aed47d19e7908d19bd194493aThomas Graf */
60044d362409d5469aed47d19e7908d19bd194493aThomas Graf
60144d362409d5469aed47d19e7908d19bd194493aThomas Grafvoid rtnl_neightbl_set_family(struct rtnl_neightbl *ntbl, int family)
60244d362409d5469aed47d19e7908d19bd194493aThomas Graf{
60344d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_family = family;
60444d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->ce_mask |= NEIGHTBL_ATTR_FAMILY;
60544d362409d5469aed47d19e7908d19bd194493aThomas Graf}
60644d362409d5469aed47d19e7908d19bd194493aThomas Graf
60744d362409d5469aed47d19e7908d19bd194493aThomas Grafvoid rtnl_neightbl_set_gc_interval(struct rtnl_neightbl *ntbl, uint64_t ms)
60844d362409d5469aed47d19e7908d19bd194493aThomas Graf{
60944d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_gc_interval = ms;
61044d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->ce_mask |= NEIGHTBL_ATTR_GC_INTERVAL;
61144d362409d5469aed47d19e7908d19bd194493aThomas Graf}
61244d362409d5469aed47d19e7908d19bd194493aThomas Graf
61344d362409d5469aed47d19e7908d19bd194493aThomas Grafvoid rtnl_neightbl_set_gc_tresh1(struct rtnl_neightbl *ntbl, int thresh)
61444d362409d5469aed47d19e7908d19bd194493aThomas Graf{
61544d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_gc_thresh1 = thresh;
61644d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->ce_mask |= NEIGHTBL_ATTR_THRESH1;
61744d362409d5469aed47d19e7908d19bd194493aThomas Graf}
61844d362409d5469aed47d19e7908d19bd194493aThomas Graf
61944d362409d5469aed47d19e7908d19bd194493aThomas Grafvoid rtnl_neightbl_set_gc_tresh2(struct rtnl_neightbl *ntbl, int thresh)
62044d362409d5469aed47d19e7908d19bd194493aThomas Graf{
62144d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_gc_thresh2 = thresh;
62244d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->ce_mask |= NEIGHTBL_ATTR_THRESH2;
62344d362409d5469aed47d19e7908d19bd194493aThomas Graf}
62444d362409d5469aed47d19e7908d19bd194493aThomas Graf
62544d362409d5469aed47d19e7908d19bd194493aThomas Grafvoid rtnl_neightbl_set_gc_tresh3(struct rtnl_neightbl *ntbl, int thresh)
62644d362409d5469aed47d19e7908d19bd194493aThomas Graf{
62744d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_gc_thresh3 = thresh;
62844d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->ce_mask |= NEIGHTBL_ATTR_THRESH3;
62944d362409d5469aed47d19e7908d19bd194493aThomas Graf}
63044d362409d5469aed47d19e7908d19bd194493aThomas Graf
63144d362409d5469aed47d19e7908d19bd194493aThomas Grafvoid rtnl_neightbl_set_name(struct rtnl_neightbl *ntbl, const char *name)
63244d362409d5469aed47d19e7908d19bd194493aThomas Graf{
63344d362409d5469aed47d19e7908d19bd194493aThomas Graf	strncpy(ntbl->nt_name, name, sizeof(ntbl->nt_name) - 1);
63444d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->ce_mask |= NEIGHTBL_ATTR_NAME;
63544d362409d5469aed47d19e7908d19bd194493aThomas Graf}
63644d362409d5469aed47d19e7908d19bd194493aThomas Graf
63744d362409d5469aed47d19e7908d19bd194493aThomas Grafvoid rtnl_neightbl_set_dev(struct rtnl_neightbl *ntbl, int ifindex)
63844d362409d5469aed47d19e7908d19bd194493aThomas Graf{
63944d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_parms.ntp_ifindex = ifindex;
64044d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_parms.ntp_mask |= NEIGHTBLPARM_ATTR_IFINDEX;
64144d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->ce_mask |= NEIGHTBL_ATTR_PARMS;
64244d362409d5469aed47d19e7908d19bd194493aThomas Graf}
64344d362409d5469aed47d19e7908d19bd194493aThomas Graf
64444d362409d5469aed47d19e7908d19bd194493aThomas Graf/**
64544d362409d5469aed47d19e7908d19bd194493aThomas Graf * Set the queue length for pending requests of a neighbour table to the specified value
64644d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg ntbl		neighbour table to change
64744d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg len		new queue len
64844d362409d5469aed47d19e7908d19bd194493aThomas Graf */
64944d362409d5469aed47d19e7908d19bd194493aThomas Grafvoid rtnl_neightbl_set_queue_len(struct rtnl_neightbl *ntbl, int len)
65044d362409d5469aed47d19e7908d19bd194493aThomas Graf{
65144d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_parms.ntp_queue_len = len;
65244d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_parms.ntp_mask |= NEIGHTBLPARM_ATTR_QUEUE_LEN;
65344d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->ce_mask |= NEIGHTBL_ATTR_PARMS;
65444d362409d5469aed47d19e7908d19bd194493aThomas Graf}
65544d362409d5469aed47d19e7908d19bd194493aThomas Graf
65644d362409d5469aed47d19e7908d19bd194493aThomas Graf/**
65744d362409d5469aed47d19e7908d19bd194493aThomas Graf * Set the queue length for delay proxy arp requests of a neighbour table to the specified value
65844d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg ntbl		neighbour table to change
65944d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg len		new queue len
66044d362409d5469aed47d19e7908d19bd194493aThomas Graf */
66144d362409d5469aed47d19e7908d19bd194493aThomas Grafvoid rtnl_neightbl_set_proxy_queue_len(struct rtnl_neightbl *ntbl, int len)
66244d362409d5469aed47d19e7908d19bd194493aThomas Graf{
66344d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_parms.ntp_proxy_qlen = len;
66444d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_parms.ntp_mask |= NEIGHTBLPARM_ATTR_PROXY_QLEN;
66544d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->ce_mask |= NEIGHTBL_ATTR_PARMS;
66644d362409d5469aed47d19e7908d19bd194493aThomas Graf}
66744d362409d5469aed47d19e7908d19bd194493aThomas Graf
66844d362409d5469aed47d19e7908d19bd194493aThomas Graf/**
66944d362409d5469aed47d19e7908d19bd194493aThomas Graf * Set the number of application probes of a neighbour table to the specified value
67044d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg ntbl		neighbour table to change
67144d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg probes		new probes value
67244d362409d5469aed47d19e7908d19bd194493aThomas Graf */
67344d362409d5469aed47d19e7908d19bd194493aThomas Grafvoid rtnl_neightbl_set_app_probes(struct rtnl_neightbl *ntbl, int probes)
67444d362409d5469aed47d19e7908d19bd194493aThomas Graf{
67544d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_parms.ntp_app_probes = probes;
67644d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_parms.ntp_mask |= NEIGHTBLPARM_ATTR_APP_PROBES;
67744d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->ce_mask |= NEIGHTBL_ATTR_PARMS;
67844d362409d5469aed47d19e7908d19bd194493aThomas Graf}
67944d362409d5469aed47d19e7908d19bd194493aThomas Graf
68044d362409d5469aed47d19e7908d19bd194493aThomas Graf/**
68144d362409d5469aed47d19e7908d19bd194493aThomas Graf * Set the number of unicast probes of a neighbour table to the specified value
68244d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg ntbl		neighbour table to change
68344d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg probes		new probes value
68444d362409d5469aed47d19e7908d19bd194493aThomas Graf */
68544d362409d5469aed47d19e7908d19bd194493aThomas Grafvoid rtnl_neightbl_set_ucast_probes(struct rtnl_neightbl *ntbl, int probes)
68644d362409d5469aed47d19e7908d19bd194493aThomas Graf{
68744d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_parms.ntp_ucast_probes = probes;
68844d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_parms.ntp_mask |= NEIGHTBLPARM_ATTR_UCAST_PROBES;
68944d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->ce_mask |= NEIGHTBL_ATTR_PARMS;
69044d362409d5469aed47d19e7908d19bd194493aThomas Graf}
69144d362409d5469aed47d19e7908d19bd194493aThomas Graf
69244d362409d5469aed47d19e7908d19bd194493aThomas Graf/**
69344d362409d5469aed47d19e7908d19bd194493aThomas Graf * Set the number of multicast probes of a neighbour table to the specified value
69444d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg ntbl		neighbour table to change
69544d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg probes		new probes value
69644d362409d5469aed47d19e7908d19bd194493aThomas Graf */
69744d362409d5469aed47d19e7908d19bd194493aThomas Grafvoid rtnl_neightbl_set_mcast_probes(struct rtnl_neightbl *ntbl, int probes)
69844d362409d5469aed47d19e7908d19bd194493aThomas Graf{
69944d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_parms.ntp_mcast_probes = probes;
70044d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_parms.ntp_mask |= NEIGHTBLPARM_ATTR_MCAST_PROBES;
70144d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->ce_mask |= NEIGHTBL_ATTR_PARMS;
70244d362409d5469aed47d19e7908d19bd194493aThomas Graf}
70344d362409d5469aed47d19e7908d19bd194493aThomas Graf
70444d362409d5469aed47d19e7908d19bd194493aThomas Graf/**
70544d362409d5469aed47d19e7908d19bd194493aThomas Graf * Set the base reachable time of a neighbour table to the specified value
70644d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg ntbl		neighbour table to change
70744d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg ms		new base reachable time in milliseconds
70844d362409d5469aed47d19e7908d19bd194493aThomas Graf */
70944d362409d5469aed47d19e7908d19bd194493aThomas Grafvoid rtnl_neightbl_set_base_reachable_time(struct rtnl_neightbl *ntbl,
71044d362409d5469aed47d19e7908d19bd194493aThomas Graf					   uint64_t ms)
71144d362409d5469aed47d19e7908d19bd194493aThomas Graf{
71244d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_parms.ntp_base_reachable_time = ms;
71344d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_parms.ntp_mask |= NEIGHTBLPARM_ATTR_BASE_REACHABLE_TIME;
71444d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->ce_mask |= NEIGHTBL_ATTR_PARMS;
71544d362409d5469aed47d19e7908d19bd194493aThomas Graf}
71644d362409d5469aed47d19e7908d19bd194493aThomas Graf
71744d362409d5469aed47d19e7908d19bd194493aThomas Graf/**
71844d362409d5469aed47d19e7908d19bd194493aThomas Graf * Set the retransmit time of a neighbour table to the specified value
71944d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg ntbl		neighbour table to change
72044d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg ms		new retransmit time
72144d362409d5469aed47d19e7908d19bd194493aThomas Graf */
72244d362409d5469aed47d19e7908d19bd194493aThomas Grafvoid rtnl_neightbl_set_retrans_time(struct rtnl_neightbl *ntbl, uint64_t ms)
72344d362409d5469aed47d19e7908d19bd194493aThomas Graf{
72444d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_parms.ntp_retrans_time = ms;
72544d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_parms.ntp_mask |= NEIGHTBLPARM_ATTR_RETRANS_TIME;
72644d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->ce_mask |= NEIGHTBL_ATTR_PARMS;
72744d362409d5469aed47d19e7908d19bd194493aThomas Graf}
72844d362409d5469aed47d19e7908d19bd194493aThomas Graf
72944d362409d5469aed47d19e7908d19bd194493aThomas Graf/**
73044d362409d5469aed47d19e7908d19bd194493aThomas Graf * Set the gc stale time of a neighbour table to the specified value
73144d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg ntbl		neighbour table to change
73244d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg ms		new gc stale time in milliseconds
73344d362409d5469aed47d19e7908d19bd194493aThomas Graf */
73444d362409d5469aed47d19e7908d19bd194493aThomas Grafvoid rtnl_neightbl_set_gc_stale_time(struct rtnl_neightbl *ntbl, uint64_t ms)
73544d362409d5469aed47d19e7908d19bd194493aThomas Graf{
73644d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_parms.ntp_gc_stale_time = ms;
73744d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_parms.ntp_mask |= NEIGHTBLPARM_ATTR_GC_STALETIME;
73844d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->ce_mask |= NEIGHTBL_ATTR_PARMS;
73944d362409d5469aed47d19e7908d19bd194493aThomas Graf}
74044d362409d5469aed47d19e7908d19bd194493aThomas Graf
74144d362409d5469aed47d19e7908d19bd194493aThomas Graf/**
74244d362409d5469aed47d19e7908d19bd194493aThomas Graf * Set the first probe delay time of a neighbour table to the specified value
74344d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg ntbl		neighbour table to change
74444d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg ms		new first probe delay time in milliseconds
74544d362409d5469aed47d19e7908d19bd194493aThomas Graf */
74644d362409d5469aed47d19e7908d19bd194493aThomas Grafvoid rtnl_neightbl_set_delay_probe_time(struct rtnl_neightbl *ntbl, uint64_t ms)
74744d362409d5469aed47d19e7908d19bd194493aThomas Graf{
74844d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_parms.ntp_probe_delay = ms;
74944d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_parms.ntp_mask |= NEIGHTBLPARM_ATTR_DELAY_PROBE_TIME;
75044d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->ce_mask |= NEIGHTBL_ATTR_PARMS;
75144d362409d5469aed47d19e7908d19bd194493aThomas Graf}
75244d362409d5469aed47d19e7908d19bd194493aThomas Graf
75344d362409d5469aed47d19e7908d19bd194493aThomas Graf/**
75444d362409d5469aed47d19e7908d19bd194493aThomas Graf * Set the anycast delay of a neighbour table to the specified value
75544d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg ntbl		neighbour table to change
75644d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg ms		new anycast delay in milliseconds
75744d362409d5469aed47d19e7908d19bd194493aThomas Graf */
75844d362409d5469aed47d19e7908d19bd194493aThomas Grafvoid rtnl_neightbl_set_anycast_delay(struct rtnl_neightbl *ntbl, uint64_t ms)
75944d362409d5469aed47d19e7908d19bd194493aThomas Graf{
76044d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_parms.ntp_anycast_delay = ms;
76144d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_parms.ntp_mask |= NEIGHTBLPARM_ATTR_ANYCAST_DELAY;
76244d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->ce_mask |= NEIGHTBL_ATTR_PARMS;
76344d362409d5469aed47d19e7908d19bd194493aThomas Graf}
76444d362409d5469aed47d19e7908d19bd194493aThomas Graf
76544d362409d5469aed47d19e7908d19bd194493aThomas Graf/**
76644d362409d5469aed47d19e7908d19bd194493aThomas Graf * Set the proxy delay of a neighbour table to the specified value
76744d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg ntbl		neighbour table to change
76844d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg ms		new proxy delay in milliseconds
76944d362409d5469aed47d19e7908d19bd194493aThomas Graf */
77044d362409d5469aed47d19e7908d19bd194493aThomas Grafvoid rtnl_neightbl_set_proxy_delay(struct rtnl_neightbl *ntbl, uint64_t ms)
77144d362409d5469aed47d19e7908d19bd194493aThomas Graf{
77244d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_parms.ntp_proxy_delay = ms;
77344d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_parms.ntp_mask |= NEIGHTBLPARM_ATTR_PROXY_DELAY;
77444d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->ce_mask |= NEIGHTBL_ATTR_PARMS;
77544d362409d5469aed47d19e7908d19bd194493aThomas Graf}
77644d362409d5469aed47d19e7908d19bd194493aThomas Graf
77744d362409d5469aed47d19e7908d19bd194493aThomas Graf/**
77844d362409d5469aed47d19e7908d19bd194493aThomas Graf * Set the locktime of a neighbour table to the specified value
77944d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg ntbl		neighbour table to change
78044d362409d5469aed47d19e7908d19bd194493aThomas Graf * @arg ms		new locktime in milliseconds
78144d362409d5469aed47d19e7908d19bd194493aThomas Graf */
78244d362409d5469aed47d19e7908d19bd194493aThomas Grafvoid rtnl_neightbl_set_locktime(struct rtnl_neightbl *ntbl, uint64_t ms)
78344d362409d5469aed47d19e7908d19bd194493aThomas Graf{
78444d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_parms.ntp_locktime = ms;
78544d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->nt_parms.ntp_mask |= NEIGHTBLPARM_ATTR_LOCKTIME;
78644d362409d5469aed47d19e7908d19bd194493aThomas Graf	ntbl->ce_mask |= NEIGHTBL_ATTR_PARMS;
78744d362409d5469aed47d19e7908d19bd194493aThomas Graf}
78844d362409d5469aed47d19e7908d19bd194493aThomas Graf
78944d362409d5469aed47d19e7908d19bd194493aThomas Graf/** @} */
79044d362409d5469aed47d19e7908d19bd194493aThomas Graf
79144d362409d5469aed47d19e7908d19bd194493aThomas Grafstatic struct nl_object_ops neightbl_obj_ops = {
79244d362409d5469aed47d19e7908d19bd194493aThomas Graf	.oo_name		= "route/neightbl",
79344d362409d5469aed47d19e7908d19bd194493aThomas Graf	.oo_size		= sizeof(struct rtnl_neightbl),
794d84430702496f617c01c5e2d27d0e82e02390bb7Thomas Graf	.oo_dump = {
795d84430702496f617c01c5e2d27d0e82e02390bb7Thomas Graf	    [NL_DUMP_LINE]	= neightbl_dump_line,
796d84430702496f617c01c5e2d27d0e82e02390bb7Thomas Graf	    [NL_DUMP_DETAILS]	= neightbl_dump_details,
797d84430702496f617c01c5e2d27d0e82e02390bb7Thomas Graf	    [NL_DUMP_STATS]	= neightbl_dump_stats,
798d84430702496f617c01c5e2d27d0e82e02390bb7Thomas Graf	},
79944d362409d5469aed47d19e7908d19bd194493aThomas Graf	.oo_compare		= neightbl_compare,
80044d362409d5469aed47d19e7908d19bd194493aThomas Graf};
80144d362409d5469aed47d19e7908d19bd194493aThomas Graf
80244d362409d5469aed47d19e7908d19bd194493aThomas Grafstatic struct nl_cache_ops rtnl_neightbl_ops = {
80344d362409d5469aed47d19e7908d19bd194493aThomas Graf	.co_name		= "route/neightbl",
80444d362409d5469aed47d19e7908d19bd194493aThomas Graf	.co_hdrsize		= sizeof(struct rtgenmsg),
80544d362409d5469aed47d19e7908d19bd194493aThomas Graf	.co_msgtypes		= {
80644d362409d5469aed47d19e7908d19bd194493aThomas Graf					{ RTM_NEWNEIGHTBL, NL_ACT_NEW, "new" },
80744d362409d5469aed47d19e7908d19bd194493aThomas Graf					{ RTM_SETNEIGHTBL, NL_ACT_SET, "set" },
80844d362409d5469aed47d19e7908d19bd194493aThomas Graf					{ RTM_GETNEIGHTBL, NL_ACT_GET, "get" },
80944d362409d5469aed47d19e7908d19bd194493aThomas Graf					END_OF_MSGTYPES_LIST,
81044d362409d5469aed47d19e7908d19bd194493aThomas Graf				  },
81144d362409d5469aed47d19e7908d19bd194493aThomas Graf	.co_protocol		= NETLINK_ROUTE,
81244d362409d5469aed47d19e7908d19bd194493aThomas Graf	.co_request_update	= neightbl_request_update,
81344d362409d5469aed47d19e7908d19bd194493aThomas Graf	.co_msg_parser		= neightbl_msg_parser,
81444d362409d5469aed47d19e7908d19bd194493aThomas Graf	.co_obj_ops		= &neightbl_obj_ops,
81544d362409d5469aed47d19e7908d19bd194493aThomas Graf};
81644d362409d5469aed47d19e7908d19bd194493aThomas Graf
81744d362409d5469aed47d19e7908d19bd194493aThomas Grafstatic void __init neightbl_init(void)
81844d362409d5469aed47d19e7908d19bd194493aThomas Graf{
81944d362409d5469aed47d19e7908d19bd194493aThomas Graf	nl_cache_mngt_register(&rtnl_neightbl_ops);
82044d362409d5469aed47d19e7908d19bd194493aThomas Graf}
82144d362409d5469aed47d19e7908d19bd194493aThomas Graf
82244d362409d5469aed47d19e7908d19bd194493aThomas Grafstatic void __exit neightbl_exit(void)
82344d362409d5469aed47d19e7908d19bd194493aThomas Graf{
82444d362409d5469aed47d19e7908d19bd194493aThomas Graf	nl_cache_mngt_unregister(&rtnl_neightbl_ops);
82544d362409d5469aed47d19e7908d19bd194493aThomas Graf}
82644d362409d5469aed47d19e7908d19bd194493aThomas Graf
82744d362409d5469aed47d19e7908d19bd194493aThomas Graf/** @} */
828