xref: /linux/net/tipc/netlink.c (revision bfb3e5dd8dfd84dfd13649393abab63e43267b00)
1b97bf3fdSPer Liden /*
2b97bf3fdSPer Liden  * net/tipc/netlink.c: TIPC configuration handling
3b97bf3fdSPer Liden  *
40655f6a8SRichard Alpe  * Copyright (c) 2005-2006, 2014, Ericsson AB
559f0c452SAllan Stephens  * Copyright (c) 2005-2007, Wind River Systems
6b97bf3fdSPer Liden  * All rights reserved.
7b97bf3fdSPer Liden  *
8b97bf3fdSPer Liden  * Redistribution and use in source and binary forms, with or without
9b97bf3fdSPer Liden  * modification, are permitted provided that the following conditions are met:
10b97bf3fdSPer Liden  *
119ea1fd3cSPer Liden  * 1. Redistributions of source code must retain the above copyright
129ea1fd3cSPer Liden  *    notice, this list of conditions and the following disclaimer.
139ea1fd3cSPer Liden  * 2. Redistributions in binary form must reproduce the above copyright
149ea1fd3cSPer Liden  *    notice, this list of conditions and the following disclaimer in the
159ea1fd3cSPer Liden  *    documentation and/or other materials provided with the distribution.
169ea1fd3cSPer Liden  * 3. Neither the names of the copyright holders nor the names of its
179ea1fd3cSPer Liden  *    contributors may be used to endorse or promote products derived from
189ea1fd3cSPer Liden  *    this software without specific prior written permission.
199ea1fd3cSPer Liden  *
209ea1fd3cSPer Liden  * Alternatively, this software may be distributed under the terms of the
219ea1fd3cSPer Liden  * GNU General Public License ("GPL") version 2 as published by the Free
229ea1fd3cSPer Liden  * Software Foundation.
23b97bf3fdSPer Liden  *
24b97bf3fdSPer Liden  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
25b97bf3fdSPer Liden  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
26b97bf3fdSPer Liden  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
27b97bf3fdSPer Liden  * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
28b97bf3fdSPer Liden  * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
29b97bf3fdSPer Liden  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
30b97bf3fdSPer Liden  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
31b97bf3fdSPer Liden  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
32b97bf3fdSPer Liden  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
33b97bf3fdSPer Liden  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
34b97bf3fdSPer Liden  * POSSIBILITY OF SUCH DAMAGE.
35b97bf3fdSPer Liden  */
36b97bf3fdSPer Liden 
37b97bf3fdSPer Liden #include "core.h"
3834b78a12SRichard Alpe #include "socket.h"
391593123aSRichard Alpe #include "name_table.h"
400655f6a8SRichard Alpe #include "bearer.h"
417be57fc6SRichard Alpe #include "link.h"
423e4b6ab5SRichard Alpe #include "node.h"
43fd3cf2adSRichard Alpe #include "net.h"
44b97bf3fdSPer Liden #include <net/genetlink.h>
45b97bf3fdSPer Liden 
460655f6a8SRichard Alpe static const struct nla_policy tipc_nl_policy[TIPC_NLA_MAX + 1] = {
470655f6a8SRichard Alpe 	[TIPC_NLA_UNSPEC]	= { .type = NLA_UNSPEC, },
480655f6a8SRichard Alpe 	[TIPC_NLA_BEARER]	= { .type = NLA_NESTED, },
4934b78a12SRichard Alpe 	[TIPC_NLA_SOCK]		= { .type = NLA_NESTED, },
507be57fc6SRichard Alpe 	[TIPC_NLA_PUBL]		= { .type = NLA_NESTED, },
517be57fc6SRichard Alpe 	[TIPC_NLA_LINK]		= { .type = NLA_NESTED, },
5246f15c67SRichard Alpe 	[TIPC_NLA_MEDIA]	= { .type = NLA_NESTED, },
53fd3cf2adSRichard Alpe 	[TIPC_NLA_NODE]		= { .type = NLA_NESTED, },
541593123aSRichard Alpe 	[TIPC_NLA_NET]		= { .type = NLA_NESTED, },
551593123aSRichard Alpe 	[TIPC_NLA_NAME_TABLE]	= { .type = NLA_NESTED, }
560655f6a8SRichard Alpe };
570655f6a8SRichard Alpe 
580655f6a8SRichard Alpe /* Users of the legacy API (tipc-config) can't handle that we add operations,
590655f6a8SRichard Alpe  * so we have a separate genl handling for the new API.
600655f6a8SRichard Alpe  */
61*bfb3e5ddSRichard Alpe struct genl_family tipc_genl_family = {
620655f6a8SRichard Alpe 	.id		= GENL_ID_GENERATE,
630655f6a8SRichard Alpe 	.name		= TIPC_GENL_V2_NAME,
640655f6a8SRichard Alpe 	.version	= TIPC_GENL_V2_VERSION,
650655f6a8SRichard Alpe 	.hdrsize	= 0,
660655f6a8SRichard Alpe 	.maxattr	= TIPC_NLA_MAX,
67d49e2041SYing Xue 	.netnsok	= true,
680655f6a8SRichard Alpe };
690655f6a8SRichard Alpe 
700655f6a8SRichard Alpe static const struct genl_ops tipc_genl_v2_ops[] = {
710655f6a8SRichard Alpe 	{
720655f6a8SRichard Alpe 		.cmd	= TIPC_NL_BEARER_DISABLE,
730655f6a8SRichard Alpe 		.doit	= tipc_nl_bearer_disable,
740655f6a8SRichard Alpe 		.policy = tipc_nl_policy,
750655f6a8SRichard Alpe 	},
760655f6a8SRichard Alpe 	{
770655f6a8SRichard Alpe 		.cmd	= TIPC_NL_BEARER_ENABLE,
780655f6a8SRichard Alpe 		.doit	= tipc_nl_bearer_enable,
790655f6a8SRichard Alpe 		.policy = tipc_nl_policy,
8035b9dd76SRichard Alpe 	},
8135b9dd76SRichard Alpe 	{
8235b9dd76SRichard Alpe 		.cmd	= TIPC_NL_BEARER_GET,
8335b9dd76SRichard Alpe 		.doit	= tipc_nl_bearer_get,
8435b9dd76SRichard Alpe 		.dumpit	= tipc_nl_bearer_dump,
8535b9dd76SRichard Alpe 		.policy = tipc_nl_policy,
86315c00bcSRichard Alpe 	},
87315c00bcSRichard Alpe 	{
88315c00bcSRichard Alpe 		.cmd	= TIPC_NL_BEARER_SET,
89315c00bcSRichard Alpe 		.doit	= tipc_nl_bearer_set,
90315c00bcSRichard Alpe 		.policy = tipc_nl_policy,
9134b78a12SRichard Alpe 	},
9234b78a12SRichard Alpe 	{
9334b78a12SRichard Alpe 		.cmd	= TIPC_NL_SOCK_GET,
9434b78a12SRichard Alpe 		.dumpit	= tipc_nl_sk_dump,
9534b78a12SRichard Alpe 		.policy = tipc_nl_policy,
961a1a143dSRichard Alpe 	},
971a1a143dSRichard Alpe 	{
981a1a143dSRichard Alpe 		.cmd	= TIPC_NL_PUBL_GET,
991a1a143dSRichard Alpe 		.dumpit	= tipc_nl_publ_dump,
1001a1a143dSRichard Alpe 		.policy = tipc_nl_policy,
1017be57fc6SRichard Alpe 	},
1027be57fc6SRichard Alpe 	{
1037be57fc6SRichard Alpe 		.cmd	= TIPC_NL_LINK_GET,
1047be57fc6SRichard Alpe 		.doit   = tipc_nl_link_get,
1057be57fc6SRichard Alpe 		.dumpit	= tipc_nl_link_dump,
1067be57fc6SRichard Alpe 		.policy = tipc_nl_policy,
107f96ce7a2SRichard Alpe 	},
108f96ce7a2SRichard Alpe 	{
109f96ce7a2SRichard Alpe 		.cmd	= TIPC_NL_LINK_SET,
110f96ce7a2SRichard Alpe 		.doit	= tipc_nl_link_set,
111f96ce7a2SRichard Alpe 		.policy = tipc_nl_policy,
112ae36342bSRichard Alpe 	},
113ae36342bSRichard Alpe 	{
114ae36342bSRichard Alpe 		.cmd	= TIPC_NL_LINK_RESET_STATS,
115ae36342bSRichard Alpe 		.doit   = tipc_nl_link_reset_stats,
116ae36342bSRichard Alpe 		.policy = tipc_nl_policy,
11746f15c67SRichard Alpe 	},
11846f15c67SRichard Alpe 	{
11946f15c67SRichard Alpe 		.cmd	= TIPC_NL_MEDIA_GET,
12046f15c67SRichard Alpe 		.doit	= tipc_nl_media_get,
12146f15c67SRichard Alpe 		.dumpit	= tipc_nl_media_dump,
12246f15c67SRichard Alpe 		.policy = tipc_nl_policy,
1231e55417dSRichard Alpe 	},
1241e55417dSRichard Alpe 	{
1251e55417dSRichard Alpe 		.cmd	= TIPC_NL_MEDIA_SET,
1261e55417dSRichard Alpe 		.doit	= tipc_nl_media_set,
1271e55417dSRichard Alpe 		.policy = tipc_nl_policy,
1283e4b6ab5SRichard Alpe 	},
1293e4b6ab5SRichard Alpe 	{
1303e4b6ab5SRichard Alpe 		.cmd	= TIPC_NL_NODE_GET,
1313e4b6ab5SRichard Alpe 		.dumpit	= tipc_nl_node_dump,
1323e4b6ab5SRichard Alpe 		.policy = tipc_nl_policy,
133fd3cf2adSRichard Alpe 	},
134fd3cf2adSRichard Alpe 	{
135fd3cf2adSRichard Alpe 		.cmd	= TIPC_NL_NET_GET,
136fd3cf2adSRichard Alpe 		.dumpit	= tipc_nl_net_dump,
137fd3cf2adSRichard Alpe 		.policy = tipc_nl_policy,
13827c21416SRichard Alpe 	},
13927c21416SRichard Alpe 	{
14027c21416SRichard Alpe 		.cmd	= TIPC_NL_NET_SET,
14127c21416SRichard Alpe 		.doit	= tipc_nl_net_set,
14227c21416SRichard Alpe 		.policy = tipc_nl_policy,
1431593123aSRichard Alpe 	},
1441593123aSRichard Alpe 	{
1451593123aSRichard Alpe 		.cmd	= TIPC_NL_NAME_TABLE_GET,
1461593123aSRichard Alpe 		.dumpit	= tipc_nl_name_table_dump,
1471593123aSRichard Alpe 		.policy = tipc_nl_policy,
1480655f6a8SRichard Alpe 	}
1490655f6a8SRichard Alpe };
1500655f6a8SRichard Alpe 
1511a1a143dSRichard Alpe int tipc_nlmsg_parse(const struct nlmsghdr *nlh, struct nlattr ***attr)
1521a1a143dSRichard Alpe {
153*bfb3e5ddSRichard Alpe 	u32 maxattr = tipc_genl_family.maxattr;
1541a1a143dSRichard Alpe 
155*bfb3e5ddSRichard Alpe 	*attr = tipc_genl_family.attrbuf;
1561a1a143dSRichard Alpe 	if (!*attr)
1571a1a143dSRichard Alpe 		return -EOPNOTSUPP;
1581a1a143dSRichard Alpe 
1591a1a143dSRichard Alpe 	return nlmsg_parse(nlh, GENL_HDRLEN, *attr, maxattr, tipc_nl_policy);
1601a1a143dSRichard Alpe }
1611a1a143dSRichard Alpe 
1624323add6SPer Liden int tipc_netlink_start(void)
163b97bf3fdSPer Liden {
164acb0a200SMichał Mirosław 	int res;
165b70e4f45SJon Maloy 
166*bfb3e5ddSRichard Alpe 	res = genl_register_family_with_ops(&tipc_genl_family,
1670655f6a8SRichard Alpe 					    tipc_genl_v2_ops);
1680655f6a8SRichard Alpe 	if (res) {
1692cf8aa19SErik Hugne 		pr_err("Failed to register netlink interface\n");
170acb0a200SMichał Mirosław 		return res;
171acb0a200SMichał Mirosław 	}
172acb0a200SMichał Mirosław 	return 0;
173b97bf3fdSPer Liden }
174b97bf3fdSPer Liden 
1754323add6SPer Liden void tipc_netlink_stop(void)
176b97bf3fdSPer Liden {
177acb0a200SMichał Mirosław 	genl_unregister_family(&tipc_genl_family);
178b97bf3fdSPer Liden }
179