]>
git.proxmox.com Git - mirror_iproute2.git/blob - lib/libgenl.c
1 /* SPDX-License-Identifier: GPL-2.0 */
3 * libgenl.c GENL library
10 #include <linux/genetlink.h>
13 static int genl_parse_getfamily(struct nlmsghdr
*nlh
)
15 struct rtattr
*tb
[CTRL_ATTR_MAX
+ 1];
16 struct genlmsghdr
*ghdr
= NLMSG_DATA(nlh
);
17 int len
= nlh
->nlmsg_len
;
20 if (nlh
->nlmsg_type
!= GENL_ID_CTRL
) {
21 fprintf(stderr
, "Not a controller message, nlmsg_len=%d "
22 "nlmsg_type=0x%x\n", nlh
->nlmsg_len
, nlh
->nlmsg_type
);
26 len
-= NLMSG_LENGTH(GENL_HDRLEN
);
29 fprintf(stderr
, "wrong controller message len %d\n", len
);
33 if (ghdr
->cmd
!= CTRL_CMD_NEWFAMILY
) {
34 fprintf(stderr
, "Unknown controller command %d\n", ghdr
->cmd
);
38 attrs
= (struct rtattr
*) ((char *) ghdr
+ GENL_HDRLEN
);
39 parse_rtattr(tb
, CTRL_ATTR_MAX
, attrs
, len
);
41 if (tb
[CTRL_ATTR_FAMILY_ID
] == NULL
) {
42 fprintf(stderr
, "Missing family id TLV\n");
46 return rta_getattr_u16(tb
[CTRL_ATTR_FAMILY_ID
]);
49 int genl_resolve_family(struct rtnl_handle
*grth
, const char *family
)
51 GENL_REQUEST(req
, 1024, GENL_ID_CTRL
, 0, 0, CTRL_CMD_GETFAMILY
,
53 struct nlmsghdr
*answer
;
56 addattr_l(&req
.n
, sizeof(req
), CTRL_ATTR_FAMILY_NAME
,
57 family
, strlen(family
) + 1);
59 if (rtnl_talk(grth
, &req
.n
, &answer
) < 0) {
60 fprintf(stderr
, "Error talking to the kernel\n");
64 fnum
= genl_parse_getfamily(answer
);
70 int genl_init_handle(struct rtnl_handle
*grth
, const char *family
,
73 if (*genl_family
>= 0)
76 if (rtnl_open_byproto(grth
, 0, NETLINK_GENERIC
) < 0) {
77 fprintf(stderr
, "Cannot open generic netlink socket\n");
81 *genl_family
= genl_resolve_family(grth
, family
);