summaryrefslogtreecommitdiff
path: root/tools/net/ynl/generated/netdev-user.c
diff options
context:
space:
mode:
authorJakub Kicinski <kuba@kernel.org>2023-06-06 12:31:33 -0700
committerJakub Kicinski <kuba@kernel.org>2023-06-06 12:31:34 -0700
commit2dc476404efa8546a08561877e88bfb2006facab (patch)
tree65b79b41b3c90757860329b086e354d2b68312fc /tools/net/ynl/generated/netdev-user.c
parentae91f7e436f8b631c47e244b892ecac62a4d9430 (diff)
parentee0202e2e731d074639461b3db2296bf44d847ce (diff)
Merge branch 'tools-ynl-user-space-c'
Jakub Kicinski says: ==================== tools: ynl: user space C Use the code gen which is already in tree to generate a user space library for a handful of simple families. I find YNL C quite useful in some WIP projects, and I think others may find it useful, too. I was hoping someone will pick this work up and finish it... but it seems that Python YNL has largely stolen the thunder. Python may not be great for selftest, tho, and actually this lib is more fully-featured. The Python script was meant as a quick demo, funny how those things go. v2: https://lore.kernel.org/all/20230604175843.662084-1-kuba@kernel.org/ v1: https://lore.kernel.org/all/20230603052547.631384-1-kuba@kernel.org/ ==================== Link: https://lore.kernel.org/r/20230605190108.809439-1-kuba@kernel.org Signed-off-by: Jakub Kicinski <kuba@kernel.org>
Diffstat (limited to 'tools/net/ynl/generated/netdev-user.c')
-rw-r--r--tools/net/ynl/generated/netdev-user.c250
1 files changed, 250 insertions, 0 deletions
diff --git a/tools/net/ynl/generated/netdev-user.c b/tools/net/ynl/generated/netdev-user.c
new file mode 100644
index 000000000000..aea5c7cc8ead
--- /dev/null
+++ b/tools/net/ynl/generated/netdev-user.c
@@ -0,0 +1,250 @@
+// SPDX-License-Identifier: ((GPL-2.0 WITH Linux-syscall-note) OR BSD-3-Clause)
+/* Do not edit directly, auto-generated from: */
+/* Documentation/netlink/specs/netdev.yaml */
+/* YNL-GEN user source */
+
+#include <stdlib.h>
+#include "netdev-user.h"
+#include "ynl.h"
+#include <linux/netdev.h>
+
+#include <stdlib.h>
+#include <stdio.h>
+#include <string.h>
+#include <libmnl/libmnl.h>
+#include <linux/genetlink.h>
+
+/* Enums */
+static const char * const netdev_op_strmap[] = {
+ [NETDEV_CMD_DEV_GET] = "dev-get",
+ [NETDEV_CMD_DEV_ADD_NTF] = "dev-add-ntf",
+ [NETDEV_CMD_DEV_DEL_NTF] = "dev-del-ntf",
+ [NETDEV_CMD_DEV_CHANGE_NTF] = "dev-change-ntf",
+};
+
+const char *netdev_op_str(int op)
+{
+ if (op < 0 || op >= (int)MNL_ARRAY_SIZE(netdev_op_strmap))
+ return NULL;
+ return netdev_op_strmap[op];
+}
+
+static const char * const netdev_xdp_act_strmap[] = {
+ [0] = "basic",
+ [1] = "redirect",
+ [2] = "ndo-xmit",
+ [3] = "xsk-zerocopy",
+ [4] = "hw-offload",
+ [5] = "rx-sg",
+ [6] = "ndo-xmit-sg",
+};
+
+const char *netdev_xdp_act_str(enum netdev_xdp_act value)
+{
+ value = ffs(value) - 1;
+ if (value < 0 || value >= (int)MNL_ARRAY_SIZE(netdev_xdp_act_strmap))
+ return NULL;
+ return netdev_xdp_act_strmap[value];
+}
+
+/* Policies */
+extern struct ynl_policy_nest netdev_dev_nest;
+
+struct ynl_policy_attr netdev_dev_policy[NETDEV_A_DEV_MAX + 1] = {
+ [NETDEV_A_DEV_IFINDEX] = { .name = "ifindex", .type = YNL_PT_U32, },
+ [NETDEV_A_DEV_PAD] = { .name = "pad", .type = YNL_PT_IGNORE, },
+ [NETDEV_A_DEV_XDP_FEATURES] = { .name = "xdp-features", .type = YNL_PT_U64, },
+};
+
+struct ynl_policy_nest netdev_dev_nest = {
+ .max_attr = NETDEV_A_DEV_MAX,
+ .table = netdev_dev_policy,
+};
+
+/* Common nested types */
+/* ============== NETDEV_CMD_DEV_GET ============== */
+/* NETDEV_CMD_DEV_GET - do */
+void netdev_dev_get_req_free(struct netdev_dev_get_req *req)
+{
+ free(req);
+}
+
+void netdev_dev_get_rsp_free(struct netdev_dev_get_rsp *rsp)
+{
+ free(rsp);
+}
+
+int netdev_dev_get_rsp_parse(const struct nlmsghdr *nlh, void *data)
+{
+ struct ynl_parse_arg *yarg = data;
+ struct netdev_dev_get_rsp *dst;
+ const struct nlattr *attr;
+
+ dst = yarg->data;
+
+ mnl_attr_for_each(attr, nlh, sizeof(struct genlmsghdr)) {
+ if (mnl_attr_get_type(attr) == NETDEV_A_DEV_IFINDEX) {
+ if (ynl_attr_validate(yarg, attr))
+ return MNL_CB_ERROR;
+ dst->_present.ifindex = 1;
+ dst->ifindex = mnl_attr_get_u32(attr);
+ }
+ else if (mnl_attr_get_type(attr) == NETDEV_A_DEV_XDP_FEATURES) {
+ if (ynl_attr_validate(yarg, attr))
+ return MNL_CB_ERROR;
+ dst->_present.xdp_features = 1;
+ dst->xdp_features = mnl_attr_get_u64(attr);
+ }
+ }
+
+ return MNL_CB_OK;
+}
+
+struct netdev_dev_get_rsp *
+netdev_dev_get(struct ynl_sock *ys, struct netdev_dev_get_req *req)
+{
+ struct ynl_req_state yrs = { .yarg = { .ys = ys, }, };
+ struct netdev_dev_get_rsp *rsp;
+ struct nlmsghdr *nlh;
+ int err;
+
+ nlh = ynl_gemsg_start_req(ys, ys->family_id, NETDEV_CMD_DEV_GET, 1);
+ ys->req_policy = &netdev_dev_nest;
+ yrs.yarg.rsp_policy = &netdev_dev_nest;
+
+ if (req->_present.ifindex)
+ mnl_attr_put_u32(nlh, NETDEV_A_DEV_IFINDEX, req->ifindex);
+
+ rsp = calloc(1, sizeof(*rsp));
+ yrs.yarg.data = rsp;
+ yrs.cb = netdev_dev_get_rsp_parse;
+ yrs.rsp_cmd = NETDEV_CMD_DEV_GET;
+
+ err = ynl_exec(ys, nlh, &yrs);
+ if (err < 0)
+ goto err_free;
+
+ return rsp;
+
+err_free:
+ netdev_dev_get_rsp_free(rsp);
+ return NULL;
+}
+
+/* NETDEV_CMD_DEV_GET - dump */
+void netdev_dev_get_list_free(struct netdev_dev_get_list *rsp)
+{
+ struct netdev_dev_get_list *next = rsp;
+
+ while ((void *)next != YNL_LIST_END) {
+ rsp = next;
+ next = rsp->next;
+
+ free(rsp);
+ }
+}
+
+struct netdev_dev_get_list *netdev_dev_get_dump(struct ynl_sock *ys)
+{
+ struct ynl_dump_state yds = {};
+ struct nlmsghdr *nlh;
+ int err;
+
+ yds.ys = ys;
+ yds.alloc_sz = sizeof(struct netdev_dev_get_list);
+ yds.cb = netdev_dev_get_rsp_parse;
+ yds.rsp_cmd = NETDEV_CMD_DEV_GET;
+ yds.rsp_policy = &netdev_dev_nest;
+
+ nlh = ynl_gemsg_start_dump(ys, ys->family_id, NETDEV_CMD_DEV_GET, 1);
+
+ err = ynl_exec_dump(ys, nlh, &yds);
+ if (err < 0)
+ goto free_list;
+
+ return yds.first;
+
+free_list:
+ netdev_dev_get_list_free(yds.first);
+ return NULL;
+}
+
+/* NETDEV_CMD_DEV_GET - notify */
+void netdev_dev_get_ntf_free(struct netdev_dev_get_ntf *rsp)
+{
+ free(rsp);
+}
+
+/* --------------- Common notification parsing --------------- */
+struct ynl_ntf_base_type *netdev_ntf_parse(struct ynl_sock *ys)
+{
+ struct ynl_parse_arg yarg = { .ys = ys, };
+ struct ynl_ntf_base_type *rsp;
+ struct genlmsghdr *genlh;
+ struct nlmsghdr *nlh;
+ mnl_cb_t parse;
+ int len, err;
+
+ len = mnl_socket_recvfrom(ys->sock, ys->rx_buf, MNL_SOCKET_BUFFER_SIZE);
+ if (len < (ssize_t)(sizeof(*nlh) + sizeof(*genlh)))
+ return NULL;
+
+ nlh = (struct nlmsghdr *)ys->rx_buf;
+ genlh = mnl_nlmsg_get_payload(nlh);
+
+ switch (genlh->cmd) {
+ case NETDEV_CMD_DEV_ADD_NTF:
+ case NETDEV_CMD_DEV_DEL_NTF:
+ case NETDEV_CMD_DEV_CHANGE_NTF:
+ rsp = calloc(1, sizeof(struct netdev_dev_get_ntf));
+ parse = netdev_dev_get_rsp_parse;
+ yarg.rsp_policy = &netdev_dev_nest;
+ rsp->free = (void *)netdev_dev_get_ntf_free;
+ break;
+ default:
+ ynl_error_unknown_notification(ys, genlh->cmd);
+ return NULL;
+ }
+
+ yarg.data = rsp->data;
+
+ err = mnl_cb_run2(ys->rx_buf, len, 0, 0, parse, &yarg,
+ ynl_cb_array, NLMSG_MIN_TYPE);
+ if (err < 0)
+ goto err_free;
+
+ rsp->family = nlh->nlmsg_type;
+ rsp->cmd = genlh->cmd;
+ return rsp;
+
+err_free:
+ free(rsp);
+ return NULL;
+}
+
+static const struct ynl_ntf_info netdev_ntf_info[] = {
+ [NETDEV_CMD_DEV_ADD_NTF] = {
+ .alloc_sz = sizeof(struct netdev_dev_get_ntf),
+ .cb = netdev_dev_get_rsp_parse,
+ .policy = &netdev_dev_nest,
+ .free = (void *)netdev_dev_get_ntf_free,
+ },
+ [NETDEV_CMD_DEV_DEL_NTF] = {
+ .alloc_sz = sizeof(struct netdev_dev_get_ntf),
+ .cb = netdev_dev_get_rsp_parse,
+ .policy = &netdev_dev_nest,
+ .free = (void *)netdev_dev_get_ntf_free,
+ },
+ [NETDEV_CMD_DEV_CHANGE_NTF] = {
+ .alloc_sz = sizeof(struct netdev_dev_get_ntf),
+ .cb = netdev_dev_get_rsp_parse,
+ .policy = &netdev_dev_nest,
+ .free = (void *)netdev_dev_get_ntf_free,
+ },
+};
+
+const struct ynl_family ynl_netdev_family = {
+ .name = "netdev",
+ .ntf_info = netdev_ntf_info,
+ .ntf_info_size = MNL_ARRAY_SIZE(netdev_ntf_info),
+};