1 // SPDX-License-Identifier: GPL-2.0-or-later
3 * net/core/devlink.c - Network physical/parent device Netlink interface
5 * Heavily inspired by net/wireless/
6 * Copyright (c) 2016 Mellanox Technologies. All rights reserved.
7 * Copyright (c) 2016 Jiri Pirko <jiri@mellanox.com>
10 #include <linux/etherdevice.h>
11 #include <linux/kernel.h>
12 #include <linux/module.h>
13 #include <linux/types.h>
14 #include <linux/slab.h>
15 #include <linux/gfp.h>
16 #include <linux/device.h>
17 #include <linux/list.h>
18 #include <linux/netdevice.h>
19 #include <linux/spinlock.h>
20 #include <linux/refcount.h>
21 #include <linux/workqueue.h>
22 #include <linux/u64_stats_sync.h>
23 #include <linux/timekeeping.h>
24 #include <rdma/ib_verbs.h>
25 #include <net/netlink.h>
26 #include <net/genetlink.h>
27 #include <net/rtnetlink.h>
28 #include <net/net_namespace.h>
30 #include <net/devlink.h>
31 #define CREATE_TRACE_POINTS
32 #include <trace/events/devlink.h>
34 #include "devl_internal.h"
36 struct devlink_linecard {
37 struct list_head list;
38 struct devlink *devlink;
41 const struct devlink_linecard_ops *ops;
43 enum devlink_linecard_state state;
44 struct mutex state_lock; /* Protects state */
46 struct devlink_linecard_type *types;
47 unsigned int types_count;
48 struct devlink *nested_devlink;
52 * struct devlink_resource - devlink resource
53 * @name: name of the resource
54 * @id: id, per devlink instance
55 * @size: size of the resource
56 * @size_new: updated size of the resource, reload is needed
57 * @size_valid: valid in case the total size of the resource is valid
58 * including its children
59 * @parent: parent resource
60 * @size_params: size parameters
62 * @resource_list: list of child resources
63 * @occ_get: occupancy getter callback
64 * @occ_get_priv: occupancy getter callback priv
66 struct devlink_resource {
72 struct devlink_resource *parent;
73 struct devlink_resource_size_params size_params;
74 struct list_head list;
75 struct list_head resource_list;
76 devlink_resource_occ_get_t *occ_get;
80 static struct devlink_dpipe_field devlink_dpipe_fields_ethernet[] = {
82 .name = "destination mac",
83 .id = DEVLINK_DPIPE_FIELD_ETHERNET_DST_MAC,
88 struct devlink_dpipe_header devlink_dpipe_header_ethernet = {
90 .id = DEVLINK_DPIPE_HEADER_ETHERNET,
91 .fields = devlink_dpipe_fields_ethernet,
92 .fields_count = ARRAY_SIZE(devlink_dpipe_fields_ethernet),
95 EXPORT_SYMBOL_GPL(devlink_dpipe_header_ethernet);
97 static struct devlink_dpipe_field devlink_dpipe_fields_ipv4[] = {
99 .name = "destination ip",
100 .id = DEVLINK_DPIPE_FIELD_IPV4_DST_IP,
105 struct devlink_dpipe_header devlink_dpipe_header_ipv4 = {
107 .id = DEVLINK_DPIPE_HEADER_IPV4,
108 .fields = devlink_dpipe_fields_ipv4,
109 .fields_count = ARRAY_SIZE(devlink_dpipe_fields_ipv4),
112 EXPORT_SYMBOL_GPL(devlink_dpipe_header_ipv4);
114 static struct devlink_dpipe_field devlink_dpipe_fields_ipv6[] = {
116 .name = "destination ip",
117 .id = DEVLINK_DPIPE_FIELD_IPV6_DST_IP,
122 struct devlink_dpipe_header devlink_dpipe_header_ipv6 = {
124 .id = DEVLINK_DPIPE_HEADER_IPV6,
125 .fields = devlink_dpipe_fields_ipv6,
126 .fields_count = ARRAY_SIZE(devlink_dpipe_fields_ipv6),
129 EXPORT_SYMBOL_GPL(devlink_dpipe_header_ipv6);
131 EXPORT_TRACEPOINT_SYMBOL_GPL(devlink_hwmsg);
132 EXPORT_TRACEPOINT_SYMBOL_GPL(devlink_hwerr);
133 EXPORT_TRACEPOINT_SYMBOL_GPL(devlink_trap_report);
135 #define DEVLINK_PORT_FN_CAPS_VALID_MASK \
136 (_BITUL(__DEVLINK_PORT_FN_ATTR_CAPS_MAX) - 1)
138 static const struct nla_policy devlink_function_nl_policy[DEVLINK_PORT_FUNCTION_ATTR_MAX + 1] = {
139 [DEVLINK_PORT_FUNCTION_ATTR_HW_ADDR] = { .type = NLA_BINARY },
140 [DEVLINK_PORT_FN_ATTR_STATE] =
141 NLA_POLICY_RANGE(NLA_U8, DEVLINK_PORT_FN_STATE_INACTIVE,
142 DEVLINK_PORT_FN_STATE_ACTIVE),
143 [DEVLINK_PORT_FN_ATTR_CAPS] =
144 NLA_POLICY_BITFIELD32(DEVLINK_PORT_FN_CAPS_VALID_MASK),
147 static const struct nla_policy devlink_selftest_nl_policy[DEVLINK_ATTR_SELFTEST_ID_MAX + 1] = {
148 [DEVLINK_ATTR_SELFTEST_ID_FLASH] = { .type = NLA_FLAG },
151 #define ASSERT_DEVLINK_PORT_REGISTERED(devlink_port) \
152 WARN_ON_ONCE(!(devlink_port)->registered)
153 #define ASSERT_DEVLINK_PORT_NOT_REGISTERED(devlink_port) \
154 WARN_ON_ONCE((devlink_port)->registered)
155 #define ASSERT_DEVLINK_PORT_INITIALIZED(devlink_port) \
156 WARN_ON_ONCE(!(devlink_port)->initialized)
158 static struct devlink_port *devlink_port_get_by_index(struct devlink *devlink,
159 unsigned int port_index)
161 return xa_load(&devlink->ports, port_index);
164 static struct devlink_port *devlink_port_get_from_attrs(struct devlink *devlink,
165 struct nlattr **attrs)
167 if (attrs[DEVLINK_ATTR_PORT_INDEX]) {
168 u32 port_index = nla_get_u32(attrs[DEVLINK_ATTR_PORT_INDEX]);
169 struct devlink_port *devlink_port;
171 devlink_port = devlink_port_get_by_index(devlink, port_index);
173 return ERR_PTR(-ENODEV);
176 return ERR_PTR(-EINVAL);
179 struct devlink_port *devlink_port_get_from_info(struct devlink *devlink,
180 struct genl_info *info)
182 return devlink_port_get_from_attrs(devlink, info->attrs);
186 devlink_rate_is_leaf(struct devlink_rate *devlink_rate)
188 return devlink_rate->type == DEVLINK_RATE_TYPE_LEAF;
192 devlink_rate_is_node(struct devlink_rate *devlink_rate)
194 return devlink_rate->type == DEVLINK_RATE_TYPE_NODE;
197 static struct devlink_rate *
198 devlink_rate_leaf_get_from_info(struct devlink *devlink, struct genl_info *info)
200 struct devlink_rate *devlink_rate;
201 struct devlink_port *devlink_port;
203 devlink_port = devlink_port_get_from_attrs(devlink, info->attrs);
204 if (IS_ERR(devlink_port))
205 return ERR_CAST(devlink_port);
206 devlink_rate = devlink_port->devlink_rate;
207 return devlink_rate ?: ERR_PTR(-ENODEV);
210 static struct devlink_rate *
211 devlink_rate_node_get_by_name(struct devlink *devlink, const char *node_name)
213 static struct devlink_rate *devlink_rate;
215 list_for_each_entry(devlink_rate, &devlink->rate_list, list) {
216 if (devlink_rate_is_node(devlink_rate) &&
217 !strcmp(node_name, devlink_rate->name))
220 return ERR_PTR(-ENODEV);
223 static struct devlink_rate *
224 devlink_rate_node_get_from_attrs(struct devlink *devlink, struct nlattr **attrs)
226 const char *rate_node_name;
229 if (!attrs[DEVLINK_ATTR_RATE_NODE_NAME])
230 return ERR_PTR(-EINVAL);
231 rate_node_name = nla_data(attrs[DEVLINK_ATTR_RATE_NODE_NAME]);
232 len = strlen(rate_node_name);
233 /* Name cannot be empty or decimal number */
234 if (!len || strspn(rate_node_name, "0123456789") == len)
235 return ERR_PTR(-EINVAL);
237 return devlink_rate_node_get_by_name(devlink, rate_node_name);
240 struct devlink_rate *
241 devlink_rate_node_get_from_info(struct devlink *devlink, struct genl_info *info)
243 return devlink_rate_node_get_from_attrs(devlink, info->attrs);
246 struct devlink_rate *
247 devlink_rate_get_from_info(struct devlink *devlink, struct genl_info *info)
249 struct nlattr **attrs = info->attrs;
251 if (attrs[DEVLINK_ATTR_PORT_INDEX])
252 return devlink_rate_leaf_get_from_info(devlink, info);
253 else if (attrs[DEVLINK_ATTR_RATE_NODE_NAME])
254 return devlink_rate_node_get_from_info(devlink, info);
256 return ERR_PTR(-EINVAL);
259 static struct devlink_linecard *
260 devlink_linecard_get_by_index(struct devlink *devlink,
261 unsigned int linecard_index)
263 struct devlink_linecard *devlink_linecard;
265 list_for_each_entry(devlink_linecard, &devlink->linecard_list, list) {
266 if (devlink_linecard->index == linecard_index)
267 return devlink_linecard;
272 static bool devlink_linecard_index_exists(struct devlink *devlink,
273 unsigned int linecard_index)
275 return devlink_linecard_get_by_index(devlink, linecard_index);
278 static struct devlink_linecard *
279 devlink_linecard_get_from_attrs(struct devlink *devlink, struct nlattr **attrs)
281 if (attrs[DEVLINK_ATTR_LINECARD_INDEX]) {
282 u32 linecard_index = nla_get_u32(attrs[DEVLINK_ATTR_LINECARD_INDEX]);
283 struct devlink_linecard *linecard;
285 mutex_lock(&devlink->linecards_lock);
286 linecard = devlink_linecard_get_by_index(devlink, linecard_index);
288 refcount_inc(&linecard->refcount);
289 mutex_unlock(&devlink->linecards_lock);
291 return ERR_PTR(-ENODEV);
294 return ERR_PTR(-EINVAL);
297 struct devlink_linecard *
298 devlink_linecard_get_from_info(struct devlink *devlink, struct genl_info *info)
300 return devlink_linecard_get_from_attrs(devlink, info->attrs);
303 void devlink_linecard_put(struct devlink_linecard *linecard)
305 if (refcount_dec_and_test(&linecard->refcount)) {
306 mutex_destroy(&linecard->state_lock);
312 struct list_head list;
315 u16 ingress_pools_count;
316 u16 egress_pools_count;
317 u16 ingress_tc_count;
321 static u16 devlink_sb_pool_count(struct devlink_sb *devlink_sb)
323 return devlink_sb->ingress_pools_count + devlink_sb->egress_pools_count;
326 static struct devlink_sb *devlink_sb_get_by_index(struct devlink *devlink,
327 unsigned int sb_index)
329 struct devlink_sb *devlink_sb;
331 list_for_each_entry(devlink_sb, &devlink->sb_list, list) {
332 if (devlink_sb->index == sb_index)
338 static bool devlink_sb_index_exists(struct devlink *devlink,
339 unsigned int sb_index)
341 return devlink_sb_get_by_index(devlink, sb_index);
344 static struct devlink_sb *devlink_sb_get_from_attrs(struct devlink *devlink,
345 struct nlattr **attrs)
347 if (attrs[DEVLINK_ATTR_SB_INDEX]) {
348 u32 sb_index = nla_get_u32(attrs[DEVLINK_ATTR_SB_INDEX]);
349 struct devlink_sb *devlink_sb;
351 devlink_sb = devlink_sb_get_by_index(devlink, sb_index);
353 return ERR_PTR(-ENODEV);
356 return ERR_PTR(-EINVAL);
359 static struct devlink_sb *devlink_sb_get_from_info(struct devlink *devlink,
360 struct genl_info *info)
362 return devlink_sb_get_from_attrs(devlink, info->attrs);
365 static int devlink_sb_pool_index_get_from_attrs(struct devlink_sb *devlink_sb,
366 struct nlattr **attrs,
371 if (!attrs[DEVLINK_ATTR_SB_POOL_INDEX])
374 val = nla_get_u16(attrs[DEVLINK_ATTR_SB_POOL_INDEX]);
375 if (val >= devlink_sb_pool_count(devlink_sb))
381 static int devlink_sb_pool_index_get_from_info(struct devlink_sb *devlink_sb,
382 struct genl_info *info,
385 return devlink_sb_pool_index_get_from_attrs(devlink_sb, info->attrs,
390 devlink_sb_pool_type_get_from_attrs(struct nlattr **attrs,
391 enum devlink_sb_pool_type *p_pool_type)
395 if (!attrs[DEVLINK_ATTR_SB_POOL_TYPE])
398 val = nla_get_u8(attrs[DEVLINK_ATTR_SB_POOL_TYPE]);
399 if (val != DEVLINK_SB_POOL_TYPE_INGRESS &&
400 val != DEVLINK_SB_POOL_TYPE_EGRESS)
407 devlink_sb_pool_type_get_from_info(struct genl_info *info,
408 enum devlink_sb_pool_type *p_pool_type)
410 return devlink_sb_pool_type_get_from_attrs(info->attrs, p_pool_type);
414 devlink_sb_th_type_get_from_attrs(struct nlattr **attrs,
415 enum devlink_sb_threshold_type *p_th_type)
419 if (!attrs[DEVLINK_ATTR_SB_POOL_THRESHOLD_TYPE])
422 val = nla_get_u8(attrs[DEVLINK_ATTR_SB_POOL_THRESHOLD_TYPE]);
423 if (val != DEVLINK_SB_THRESHOLD_TYPE_STATIC &&
424 val != DEVLINK_SB_THRESHOLD_TYPE_DYNAMIC)
431 devlink_sb_th_type_get_from_info(struct genl_info *info,
432 enum devlink_sb_threshold_type *p_th_type)
434 return devlink_sb_th_type_get_from_attrs(info->attrs, p_th_type);
438 devlink_sb_tc_index_get_from_attrs(struct devlink_sb *devlink_sb,
439 struct nlattr **attrs,
440 enum devlink_sb_pool_type pool_type,
445 if (!attrs[DEVLINK_ATTR_SB_TC_INDEX])
448 val = nla_get_u16(attrs[DEVLINK_ATTR_SB_TC_INDEX]);
449 if (pool_type == DEVLINK_SB_POOL_TYPE_INGRESS &&
450 val >= devlink_sb->ingress_tc_count)
452 if (pool_type == DEVLINK_SB_POOL_TYPE_EGRESS &&
453 val >= devlink_sb->egress_tc_count)
459 static void devlink_port_fn_cap_fill(struct nla_bitfield32 *caps,
460 u32 cap, bool is_enable)
462 caps->selector |= cap;
467 static int devlink_port_fn_roce_fill(const struct devlink_ops *ops,
468 struct devlink_port *devlink_port,
469 struct nla_bitfield32 *caps,
470 struct netlink_ext_ack *extack)
475 if (!ops->port_fn_roce_get)
478 err = ops->port_fn_roce_get(devlink_port, &is_enable, extack);
480 if (err == -EOPNOTSUPP)
485 devlink_port_fn_cap_fill(caps, DEVLINK_PORT_FN_CAP_ROCE, is_enable);
489 static int devlink_port_fn_migratable_fill(const struct devlink_ops *ops,
490 struct devlink_port *devlink_port,
491 struct nla_bitfield32 *caps,
492 struct netlink_ext_ack *extack)
497 if (!ops->port_fn_migratable_get ||
498 devlink_port->attrs.flavour != DEVLINK_PORT_FLAVOUR_PCI_VF)
501 err = ops->port_fn_migratable_get(devlink_port, &is_enable, extack);
503 if (err == -EOPNOTSUPP)
508 devlink_port_fn_cap_fill(caps, DEVLINK_PORT_FN_CAP_MIGRATABLE, is_enable);
512 static int devlink_port_fn_caps_fill(const struct devlink_ops *ops,
513 struct devlink_port *devlink_port,
515 struct netlink_ext_ack *extack,
518 struct nla_bitfield32 caps = {};
521 err = devlink_port_fn_roce_fill(ops, devlink_port, &caps, extack);
525 err = devlink_port_fn_migratable_fill(ops, devlink_port, &caps, extack);
531 err = nla_put_bitfield32(msg, DEVLINK_PORT_FN_ATTR_CAPS, caps.value,
541 devlink_sb_tc_index_get_from_info(struct devlink_sb *devlink_sb,
542 struct genl_info *info,
543 enum devlink_sb_pool_type pool_type,
546 return devlink_sb_tc_index_get_from_attrs(devlink_sb, info->attrs,
547 pool_type, p_tc_index);
550 struct devlink_region {
551 struct devlink *devlink;
552 struct devlink_port *port;
553 struct list_head list;
555 const struct devlink_region_ops *ops;
556 const struct devlink_port_region_ops *port_ops;
558 struct mutex snapshot_lock; /* protects snapshot_list,
559 * max_snapshots and cur_snapshots
562 struct list_head snapshot_list;
568 struct devlink_snapshot {
569 struct list_head list;
570 struct devlink_region *region;
575 static struct devlink_region *
576 devlink_region_get_by_name(struct devlink *devlink, const char *region_name)
578 struct devlink_region *region;
580 list_for_each_entry(region, &devlink->region_list, list)
581 if (!strcmp(region->ops->name, region_name))
587 static struct devlink_region *
588 devlink_port_region_get_by_name(struct devlink_port *port,
589 const char *region_name)
591 struct devlink_region *region;
593 list_for_each_entry(region, &port->region_list, list)
594 if (!strcmp(region->ops->name, region_name))
600 static struct devlink_snapshot *
601 devlink_region_snapshot_get_by_id(struct devlink_region *region, u32 id)
603 struct devlink_snapshot *snapshot;
605 list_for_each_entry(snapshot, ®ion->snapshot_list, list)
606 if (snapshot->id == id)
612 static int devlink_nl_put_handle(struct sk_buff *msg, struct devlink *devlink)
614 if (nla_put_string(msg, DEVLINK_ATTR_BUS_NAME, devlink->dev->bus->name))
616 if (nla_put_string(msg, DEVLINK_ATTR_DEV_NAME, dev_name(devlink->dev)))
621 static int devlink_nl_put_nested_handle(struct sk_buff *msg, struct devlink *devlink)
623 struct nlattr *nested_attr;
625 nested_attr = nla_nest_start(msg, DEVLINK_ATTR_NESTED_DEVLINK);
628 if (devlink_nl_put_handle(msg, devlink))
629 goto nla_put_failure;
631 nla_nest_end(msg, nested_attr);
635 nla_nest_cancel(msg, nested_attr);
639 int devlink_nl_port_handle_fill(struct sk_buff *msg, struct devlink_port *devlink_port)
641 if (devlink_nl_put_handle(msg, devlink_port->devlink))
643 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_INDEX, devlink_port->index))
648 size_t devlink_nl_port_handle_size(struct devlink_port *devlink_port)
650 struct devlink *devlink = devlink_port->devlink;
652 return nla_total_size(strlen(devlink->dev->bus->name) + 1) /* DEVLINK_ATTR_BUS_NAME */
653 + nla_total_size(strlen(dev_name(devlink->dev)) + 1) /* DEVLINK_ATTR_DEV_NAME */
654 + nla_total_size(4); /* DEVLINK_ATTR_PORT_INDEX */
657 struct devlink_reload_combination {
658 enum devlink_reload_action action;
659 enum devlink_reload_limit limit;
662 static const struct devlink_reload_combination devlink_reload_invalid_combinations[] = {
664 /* can't reinitialize driver with no down time */
665 .action = DEVLINK_RELOAD_ACTION_DRIVER_REINIT,
666 .limit = DEVLINK_RELOAD_LIMIT_NO_RESET,
671 devlink_reload_combination_is_invalid(enum devlink_reload_action action,
672 enum devlink_reload_limit limit)
676 for (i = 0; i < ARRAY_SIZE(devlink_reload_invalid_combinations); i++)
677 if (devlink_reload_invalid_combinations[i].action == action &&
678 devlink_reload_invalid_combinations[i].limit == limit)
684 devlink_reload_action_is_supported(struct devlink *devlink, enum devlink_reload_action action)
686 return test_bit(action, &devlink->ops->reload_actions);
690 devlink_reload_limit_is_supported(struct devlink *devlink, enum devlink_reload_limit limit)
692 return test_bit(limit, &devlink->ops->reload_limits);
695 static int devlink_reload_stat_put(struct sk_buff *msg,
696 enum devlink_reload_limit limit, u32 value)
698 struct nlattr *reload_stats_entry;
700 reload_stats_entry = nla_nest_start(msg, DEVLINK_ATTR_RELOAD_STATS_ENTRY);
701 if (!reload_stats_entry)
704 if (nla_put_u8(msg, DEVLINK_ATTR_RELOAD_STATS_LIMIT, limit) ||
705 nla_put_u32(msg, DEVLINK_ATTR_RELOAD_STATS_VALUE, value))
706 goto nla_put_failure;
707 nla_nest_end(msg, reload_stats_entry);
711 nla_nest_cancel(msg, reload_stats_entry);
715 static int devlink_reload_stats_put(struct sk_buff *msg, struct devlink *devlink, bool is_remote)
717 struct nlattr *reload_stats_attr, *act_info, *act_stats;
722 reload_stats_attr = nla_nest_start(msg, DEVLINK_ATTR_RELOAD_STATS);
724 reload_stats_attr = nla_nest_start(msg, DEVLINK_ATTR_REMOTE_RELOAD_STATS);
726 if (!reload_stats_attr)
729 for (i = 0; i <= DEVLINK_RELOAD_ACTION_MAX; i++) {
731 !devlink_reload_action_is_supported(devlink, i)) ||
732 i == DEVLINK_RELOAD_ACTION_UNSPEC)
734 act_info = nla_nest_start(msg, DEVLINK_ATTR_RELOAD_ACTION_INFO);
736 goto nla_put_failure;
738 if (nla_put_u8(msg, DEVLINK_ATTR_RELOAD_ACTION, i))
739 goto action_info_nest_cancel;
740 act_stats = nla_nest_start(msg, DEVLINK_ATTR_RELOAD_ACTION_STATS);
742 goto action_info_nest_cancel;
744 for (j = 0; j <= DEVLINK_RELOAD_LIMIT_MAX; j++) {
745 /* Remote stats are shown even if not locally supported.
746 * Stats of actions with unspecified limit are shown
747 * though drivers don't need to register unspecified
750 if ((!is_remote && j != DEVLINK_RELOAD_LIMIT_UNSPEC &&
751 !devlink_reload_limit_is_supported(devlink, j)) ||
752 devlink_reload_combination_is_invalid(i, j))
755 stat_idx = j * __DEVLINK_RELOAD_ACTION_MAX + i;
757 value = devlink->stats.reload_stats[stat_idx];
759 value = devlink->stats.remote_reload_stats[stat_idx];
760 if (devlink_reload_stat_put(msg, j, value))
761 goto action_stats_nest_cancel;
763 nla_nest_end(msg, act_stats);
764 nla_nest_end(msg, act_info);
766 nla_nest_end(msg, reload_stats_attr);
769 action_stats_nest_cancel:
770 nla_nest_cancel(msg, act_stats);
771 action_info_nest_cancel:
772 nla_nest_cancel(msg, act_info);
774 nla_nest_cancel(msg, reload_stats_attr);
778 static int devlink_nl_fill(struct sk_buff *msg, struct devlink *devlink,
779 enum devlink_command cmd, u32 portid,
782 struct nlattr *dev_stats;
785 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
789 if (devlink_nl_put_handle(msg, devlink))
790 goto nla_put_failure;
791 if (nla_put_u8(msg, DEVLINK_ATTR_RELOAD_FAILED, devlink->reload_failed))
792 goto nla_put_failure;
794 dev_stats = nla_nest_start(msg, DEVLINK_ATTR_DEV_STATS);
796 goto nla_put_failure;
798 if (devlink_reload_stats_put(msg, devlink, false))
799 goto dev_stats_nest_cancel;
800 if (devlink_reload_stats_put(msg, devlink, true))
801 goto dev_stats_nest_cancel;
803 nla_nest_end(msg, dev_stats);
804 genlmsg_end(msg, hdr);
807 dev_stats_nest_cancel:
808 nla_nest_cancel(msg, dev_stats);
810 genlmsg_cancel(msg, hdr);
814 static void devlink_notify(struct devlink *devlink, enum devlink_command cmd)
819 WARN_ON(cmd != DEVLINK_CMD_NEW && cmd != DEVLINK_CMD_DEL);
820 WARN_ON(!xa_get_mark(&devlinks, devlink->index, DEVLINK_REGISTERED));
822 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
826 err = devlink_nl_fill(msg, devlink, cmd, 0, 0, 0);
832 genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink),
833 msg, 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
836 static int devlink_nl_port_attrs_put(struct sk_buff *msg,
837 struct devlink_port *devlink_port)
839 struct devlink_port_attrs *attrs = &devlink_port->attrs;
841 if (!devlink_port->attrs_set)
844 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_LANES, attrs->lanes))
847 if (nla_put_u8(msg, DEVLINK_ATTR_PORT_SPLITTABLE, attrs->splittable))
849 if (nla_put_u16(msg, DEVLINK_ATTR_PORT_FLAVOUR, attrs->flavour))
851 switch (devlink_port->attrs.flavour) {
852 case DEVLINK_PORT_FLAVOUR_PCI_PF:
853 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_CONTROLLER_NUMBER,
854 attrs->pci_pf.controller) ||
855 nla_put_u16(msg, DEVLINK_ATTR_PORT_PCI_PF_NUMBER, attrs->pci_pf.pf))
857 if (nla_put_u8(msg, DEVLINK_ATTR_PORT_EXTERNAL, attrs->pci_pf.external))
860 case DEVLINK_PORT_FLAVOUR_PCI_VF:
861 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_CONTROLLER_NUMBER,
862 attrs->pci_vf.controller) ||
863 nla_put_u16(msg, DEVLINK_ATTR_PORT_PCI_PF_NUMBER, attrs->pci_vf.pf) ||
864 nla_put_u16(msg, DEVLINK_ATTR_PORT_PCI_VF_NUMBER, attrs->pci_vf.vf))
866 if (nla_put_u8(msg, DEVLINK_ATTR_PORT_EXTERNAL, attrs->pci_vf.external))
869 case DEVLINK_PORT_FLAVOUR_PCI_SF:
870 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_CONTROLLER_NUMBER,
871 attrs->pci_sf.controller) ||
872 nla_put_u16(msg, DEVLINK_ATTR_PORT_PCI_PF_NUMBER,
874 nla_put_u32(msg, DEVLINK_ATTR_PORT_PCI_SF_NUMBER,
878 case DEVLINK_PORT_FLAVOUR_PHYSICAL:
879 case DEVLINK_PORT_FLAVOUR_CPU:
880 case DEVLINK_PORT_FLAVOUR_DSA:
881 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_NUMBER,
882 attrs->phys.port_number))
886 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_SPLIT_GROUP,
887 attrs->phys.port_number))
889 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_SPLIT_SUBPORT_NUMBER,
890 attrs->phys.split_subport_number))
899 static int devlink_port_fn_hw_addr_fill(const struct devlink_ops *ops,
900 struct devlink_port *port,
902 struct netlink_ext_ack *extack,
905 u8 hw_addr[MAX_ADDR_LEN];
909 if (!ops->port_function_hw_addr_get)
912 err = ops->port_function_hw_addr_get(port, hw_addr, &hw_addr_len,
915 if (err == -EOPNOTSUPP)
919 err = nla_put(msg, DEVLINK_PORT_FUNCTION_ATTR_HW_ADDR, hw_addr_len, hw_addr);
926 static int devlink_nl_rate_fill(struct sk_buff *msg,
927 struct devlink_rate *devlink_rate,
928 enum devlink_command cmd, u32 portid, u32 seq,
929 int flags, struct netlink_ext_ack *extack)
931 struct devlink *devlink = devlink_rate->devlink;
934 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
938 if (devlink_nl_put_handle(msg, devlink))
939 goto nla_put_failure;
941 if (nla_put_u16(msg, DEVLINK_ATTR_RATE_TYPE, devlink_rate->type))
942 goto nla_put_failure;
944 if (devlink_rate_is_leaf(devlink_rate)) {
945 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_INDEX,
946 devlink_rate->devlink_port->index))
947 goto nla_put_failure;
948 } else if (devlink_rate_is_node(devlink_rate)) {
949 if (nla_put_string(msg, DEVLINK_ATTR_RATE_NODE_NAME,
951 goto nla_put_failure;
954 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_RATE_TX_SHARE,
955 devlink_rate->tx_share, DEVLINK_ATTR_PAD))
956 goto nla_put_failure;
958 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_RATE_TX_MAX,
959 devlink_rate->tx_max, DEVLINK_ATTR_PAD))
960 goto nla_put_failure;
962 if (nla_put_u32(msg, DEVLINK_ATTR_RATE_TX_PRIORITY,
963 devlink_rate->tx_priority))
964 goto nla_put_failure;
966 if (nla_put_u32(msg, DEVLINK_ATTR_RATE_TX_WEIGHT,
967 devlink_rate->tx_weight))
968 goto nla_put_failure;
970 if (devlink_rate->parent)
971 if (nla_put_string(msg, DEVLINK_ATTR_RATE_PARENT_NODE_NAME,
972 devlink_rate->parent->name))
973 goto nla_put_failure;
975 genlmsg_end(msg, hdr);
979 genlmsg_cancel(msg, hdr);
984 devlink_port_fn_state_valid(enum devlink_port_fn_state state)
986 return state == DEVLINK_PORT_FN_STATE_INACTIVE ||
987 state == DEVLINK_PORT_FN_STATE_ACTIVE;
991 devlink_port_fn_opstate_valid(enum devlink_port_fn_opstate opstate)
993 return opstate == DEVLINK_PORT_FN_OPSTATE_DETACHED ||
994 opstate == DEVLINK_PORT_FN_OPSTATE_ATTACHED;
997 static int devlink_port_fn_state_fill(const struct devlink_ops *ops,
998 struct devlink_port *port,
1000 struct netlink_ext_ack *extack,
1003 enum devlink_port_fn_opstate opstate;
1004 enum devlink_port_fn_state state;
1007 if (!ops->port_fn_state_get)
1010 err = ops->port_fn_state_get(port, &state, &opstate, extack);
1012 if (err == -EOPNOTSUPP)
1016 if (!devlink_port_fn_state_valid(state)) {
1018 NL_SET_ERR_MSG_MOD(extack, "Invalid state read from driver");
1021 if (!devlink_port_fn_opstate_valid(opstate)) {
1023 NL_SET_ERR_MSG_MOD(extack,
1024 "Invalid operational state read from driver");
1027 if (nla_put_u8(msg, DEVLINK_PORT_FN_ATTR_STATE, state) ||
1028 nla_put_u8(msg, DEVLINK_PORT_FN_ATTR_OPSTATE, opstate))
1030 *msg_updated = true;
1035 devlink_port_fn_mig_set(struct devlink_port *devlink_port, bool enable,
1036 struct netlink_ext_ack *extack)
1038 const struct devlink_ops *ops = devlink_port->devlink->ops;
1040 return ops->port_fn_migratable_set(devlink_port, enable, extack);
1044 devlink_port_fn_roce_set(struct devlink_port *devlink_port, bool enable,
1045 struct netlink_ext_ack *extack)
1047 const struct devlink_ops *ops = devlink_port->devlink->ops;
1049 return ops->port_fn_roce_set(devlink_port, enable, extack);
1052 static int devlink_port_fn_caps_set(struct devlink_port *devlink_port,
1053 const struct nlattr *attr,
1054 struct netlink_ext_ack *extack)
1056 struct nla_bitfield32 caps;
1060 caps = nla_get_bitfield32(attr);
1061 caps_value = caps.value & caps.selector;
1062 if (caps.selector & DEVLINK_PORT_FN_CAP_ROCE) {
1063 err = devlink_port_fn_roce_set(devlink_port,
1064 caps_value & DEVLINK_PORT_FN_CAP_ROCE,
1069 if (caps.selector & DEVLINK_PORT_FN_CAP_MIGRATABLE) {
1070 err = devlink_port_fn_mig_set(devlink_port, caps_value &
1071 DEVLINK_PORT_FN_CAP_MIGRATABLE,
1080 devlink_nl_port_function_attrs_put(struct sk_buff *msg, struct devlink_port *port,
1081 struct netlink_ext_ack *extack)
1083 const struct devlink_ops *ops;
1084 struct nlattr *function_attr;
1085 bool msg_updated = false;
1088 function_attr = nla_nest_start_noflag(msg, DEVLINK_ATTR_PORT_FUNCTION);
1092 ops = port->devlink->ops;
1093 err = devlink_port_fn_hw_addr_fill(ops, port, msg, extack,
1097 err = devlink_port_fn_caps_fill(ops, port, msg, extack,
1101 err = devlink_port_fn_state_fill(ops, port, msg, extack, &msg_updated);
1103 if (err || !msg_updated)
1104 nla_nest_cancel(msg, function_attr);
1106 nla_nest_end(msg, function_attr);
1110 static int devlink_nl_port_fill(struct sk_buff *msg,
1111 struct devlink_port *devlink_port,
1112 enum devlink_command cmd, u32 portid, u32 seq,
1113 int flags, struct netlink_ext_ack *extack)
1115 struct devlink *devlink = devlink_port->devlink;
1118 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
1122 if (devlink_nl_put_handle(msg, devlink))
1123 goto nla_put_failure;
1124 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_INDEX, devlink_port->index))
1125 goto nla_put_failure;
1127 spin_lock_bh(&devlink_port->type_lock);
1128 if (nla_put_u16(msg, DEVLINK_ATTR_PORT_TYPE, devlink_port->type))
1129 goto nla_put_failure_type_locked;
1130 if (devlink_port->desired_type != DEVLINK_PORT_TYPE_NOTSET &&
1131 nla_put_u16(msg, DEVLINK_ATTR_PORT_DESIRED_TYPE,
1132 devlink_port->desired_type))
1133 goto nla_put_failure_type_locked;
1134 if (devlink_port->type == DEVLINK_PORT_TYPE_ETH) {
1135 if (devlink_port->type_eth.netdev &&
1136 (nla_put_u32(msg, DEVLINK_ATTR_PORT_NETDEV_IFINDEX,
1137 devlink_port->type_eth.ifindex) ||
1138 nla_put_string(msg, DEVLINK_ATTR_PORT_NETDEV_NAME,
1139 devlink_port->type_eth.ifname)))
1140 goto nla_put_failure_type_locked;
1142 if (devlink_port->type == DEVLINK_PORT_TYPE_IB) {
1143 struct ib_device *ibdev = devlink_port->type_ib.ibdev;
1146 nla_put_string(msg, DEVLINK_ATTR_PORT_IBDEV_NAME,
1148 goto nla_put_failure_type_locked;
1150 spin_unlock_bh(&devlink_port->type_lock);
1151 if (devlink_nl_port_attrs_put(msg, devlink_port))
1152 goto nla_put_failure;
1153 if (devlink_nl_port_function_attrs_put(msg, devlink_port, extack))
1154 goto nla_put_failure;
1155 if (devlink_port->linecard &&
1156 nla_put_u32(msg, DEVLINK_ATTR_LINECARD_INDEX,
1157 devlink_port->linecard->index))
1158 goto nla_put_failure;
1160 genlmsg_end(msg, hdr);
1163 nla_put_failure_type_locked:
1164 spin_unlock_bh(&devlink_port->type_lock);
1166 genlmsg_cancel(msg, hdr);
1170 static void devlink_port_notify(struct devlink_port *devlink_port,
1171 enum devlink_command cmd)
1173 struct devlink *devlink = devlink_port->devlink;
1174 struct sk_buff *msg;
1177 WARN_ON(cmd != DEVLINK_CMD_PORT_NEW && cmd != DEVLINK_CMD_PORT_DEL);
1179 if (!xa_get_mark(&devlinks, devlink->index, DEVLINK_REGISTERED))
1182 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
1186 err = devlink_nl_port_fill(msg, devlink_port, cmd, 0, 0, 0, NULL);
1192 genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink), msg,
1193 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
1196 static void devlink_rate_notify(struct devlink_rate *devlink_rate,
1197 enum devlink_command cmd)
1199 struct devlink *devlink = devlink_rate->devlink;
1200 struct sk_buff *msg;
1203 WARN_ON(cmd != DEVLINK_CMD_RATE_NEW && cmd != DEVLINK_CMD_RATE_DEL);
1205 if (!xa_get_mark(&devlinks, devlink->index, DEVLINK_REGISTERED))
1208 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
1212 err = devlink_nl_rate_fill(msg, devlink_rate, cmd, 0, 0, 0, NULL);
1218 genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink), msg,
1219 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
1223 devlink_nl_cmd_rate_get_dump_one(struct sk_buff *msg, struct devlink *devlink,
1224 struct netlink_callback *cb)
1226 struct devlink_nl_dump_state *state = devlink_dump_state(cb);
1227 struct devlink_rate *devlink_rate;
1231 list_for_each_entry(devlink_rate, &devlink->rate_list, list) {
1232 enum devlink_command cmd = DEVLINK_CMD_RATE_NEW;
1233 u32 id = NETLINK_CB(cb->skb).portid;
1235 if (idx < state->idx) {
1239 err = devlink_nl_rate_fill(msg, devlink_rate, cmd, id,
1252 const struct devlink_gen_cmd devl_gen_rate_get = {
1253 .dump_one = devlink_nl_cmd_rate_get_dump_one,
1256 static int devlink_nl_cmd_rate_get_doit(struct sk_buff *skb,
1257 struct genl_info *info)
1259 struct devlink_rate *devlink_rate = info->user_ptr[1];
1260 struct sk_buff *msg;
1263 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
1267 err = devlink_nl_rate_fill(msg, devlink_rate, DEVLINK_CMD_RATE_NEW,
1268 info->snd_portid, info->snd_seq, 0,
1275 return genlmsg_reply(msg, info);
1279 devlink_rate_is_parent_node(struct devlink_rate *devlink_rate,
1280 struct devlink_rate *parent)
1283 if (parent == devlink_rate)
1285 parent = parent->parent;
1290 static int devlink_nl_cmd_get_doit(struct sk_buff *skb, struct genl_info *info)
1292 struct devlink *devlink = info->user_ptr[0];
1293 struct sk_buff *msg;
1296 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
1300 err = devlink_nl_fill(msg, devlink, DEVLINK_CMD_NEW,
1301 info->snd_portid, info->snd_seq, 0);
1307 return genlmsg_reply(msg, info);
1311 devlink_nl_cmd_get_dump_one(struct sk_buff *msg, struct devlink *devlink,
1312 struct netlink_callback *cb)
1314 return devlink_nl_fill(msg, devlink, DEVLINK_CMD_NEW,
1315 NETLINK_CB(cb->skb).portid,
1316 cb->nlh->nlmsg_seq, NLM_F_MULTI);
1319 const struct devlink_gen_cmd devl_gen_inst = {
1320 .dump_one = devlink_nl_cmd_get_dump_one,
1323 static int devlink_nl_cmd_port_get_doit(struct sk_buff *skb,
1324 struct genl_info *info)
1326 struct devlink_port *devlink_port = info->user_ptr[1];
1327 struct sk_buff *msg;
1330 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
1334 err = devlink_nl_port_fill(msg, devlink_port, DEVLINK_CMD_PORT_NEW,
1335 info->snd_portid, info->snd_seq, 0,
1342 return genlmsg_reply(msg, info);
1346 devlink_nl_cmd_port_get_dump_one(struct sk_buff *msg, struct devlink *devlink,
1347 struct netlink_callback *cb)
1349 struct devlink_nl_dump_state *state = devlink_dump_state(cb);
1350 struct devlink_port *devlink_port;
1351 unsigned long port_index;
1355 xa_for_each(&devlink->ports, port_index, devlink_port) {
1356 if (idx < state->idx) {
1360 err = devlink_nl_port_fill(msg, devlink_port,
1362 NETLINK_CB(cb->skb).portid,
1364 NLM_F_MULTI, cb->extack);
1375 const struct devlink_gen_cmd devl_gen_port = {
1376 .dump_one = devlink_nl_cmd_port_get_dump_one,
1379 static int devlink_port_type_set(struct devlink_port *devlink_port,
1380 enum devlink_port_type port_type)
1385 if (!devlink_port->devlink->ops->port_type_set)
1388 if (port_type == devlink_port->type)
1391 err = devlink_port->devlink->ops->port_type_set(devlink_port,
1396 devlink_port->desired_type = port_type;
1397 devlink_port_notify(devlink_port, DEVLINK_CMD_PORT_NEW);
1401 static int devlink_port_function_hw_addr_set(struct devlink_port *port,
1402 const struct nlattr *attr,
1403 struct netlink_ext_ack *extack)
1405 const struct devlink_ops *ops = port->devlink->ops;
1409 hw_addr = nla_data(attr);
1410 hw_addr_len = nla_len(attr);
1411 if (hw_addr_len > MAX_ADDR_LEN) {
1412 NL_SET_ERR_MSG_MOD(extack, "Port function hardware address too long");
1415 if (port->type == DEVLINK_PORT_TYPE_ETH) {
1416 if (hw_addr_len != ETH_ALEN) {
1417 NL_SET_ERR_MSG_MOD(extack, "Address must be 6 bytes for Ethernet device");
1420 if (!is_unicast_ether_addr(hw_addr)) {
1421 NL_SET_ERR_MSG_MOD(extack, "Non-unicast hardware address unsupported");
1426 return ops->port_function_hw_addr_set(port, hw_addr, hw_addr_len,
1430 static int devlink_port_fn_state_set(struct devlink_port *port,
1431 const struct nlattr *attr,
1432 struct netlink_ext_ack *extack)
1434 enum devlink_port_fn_state state;
1435 const struct devlink_ops *ops;
1437 state = nla_get_u8(attr);
1438 ops = port->devlink->ops;
1439 return ops->port_fn_state_set(port, state, extack);
1442 static int devlink_port_function_validate(struct devlink_port *devlink_port,
1444 struct netlink_ext_ack *extack)
1446 const struct devlink_ops *ops = devlink_port->devlink->ops;
1447 struct nlattr *attr;
1449 if (tb[DEVLINK_PORT_FUNCTION_ATTR_HW_ADDR] &&
1450 !ops->port_function_hw_addr_set) {
1451 NL_SET_ERR_MSG_ATTR(extack, tb[DEVLINK_PORT_FUNCTION_ATTR_HW_ADDR],
1452 "Port doesn't support function attributes");
1455 if (tb[DEVLINK_PORT_FN_ATTR_STATE] && !ops->port_fn_state_set) {
1456 NL_SET_ERR_MSG_ATTR(extack, tb[DEVLINK_PORT_FUNCTION_ATTR_HW_ADDR],
1457 "Function does not support state setting");
1460 attr = tb[DEVLINK_PORT_FN_ATTR_CAPS];
1462 struct nla_bitfield32 caps;
1464 caps = nla_get_bitfield32(attr);
1465 if (caps.selector & DEVLINK_PORT_FN_CAP_ROCE &&
1466 !ops->port_fn_roce_set) {
1467 NL_SET_ERR_MSG_ATTR(extack, attr,
1468 "Port doesn't support RoCE function attribute");
1471 if (caps.selector & DEVLINK_PORT_FN_CAP_MIGRATABLE) {
1472 if (!ops->port_fn_migratable_set) {
1473 NL_SET_ERR_MSG_ATTR(extack, attr,
1474 "Port doesn't support migratable function attribute");
1477 if (devlink_port->attrs.flavour != DEVLINK_PORT_FLAVOUR_PCI_VF) {
1478 NL_SET_ERR_MSG_ATTR(extack, attr,
1479 "migratable function attribute supported for VFs only");
1487 static int devlink_port_function_set(struct devlink_port *port,
1488 const struct nlattr *attr,
1489 struct netlink_ext_ack *extack)
1491 struct nlattr *tb[DEVLINK_PORT_FUNCTION_ATTR_MAX + 1];
1494 err = nla_parse_nested(tb, DEVLINK_PORT_FUNCTION_ATTR_MAX, attr,
1495 devlink_function_nl_policy, extack);
1497 NL_SET_ERR_MSG_MOD(extack, "Fail to parse port function attributes");
1501 err = devlink_port_function_validate(port, tb, extack);
1505 attr = tb[DEVLINK_PORT_FUNCTION_ATTR_HW_ADDR];
1507 err = devlink_port_function_hw_addr_set(port, attr, extack);
1512 attr = tb[DEVLINK_PORT_FN_ATTR_CAPS];
1514 err = devlink_port_fn_caps_set(port, attr, extack);
1519 /* Keep this as the last function attribute set, so that when
1520 * multiple port function attributes are set along with state,
1521 * Those can be applied first before activating the state.
1523 attr = tb[DEVLINK_PORT_FN_ATTR_STATE];
1525 err = devlink_port_fn_state_set(port, attr, extack);
1528 devlink_port_notify(port, DEVLINK_CMD_PORT_NEW);
1532 static int devlink_nl_cmd_port_set_doit(struct sk_buff *skb,
1533 struct genl_info *info)
1535 struct devlink_port *devlink_port = info->user_ptr[1];
1538 if (info->attrs[DEVLINK_ATTR_PORT_TYPE]) {
1539 enum devlink_port_type port_type;
1541 port_type = nla_get_u16(info->attrs[DEVLINK_ATTR_PORT_TYPE]);
1542 err = devlink_port_type_set(devlink_port, port_type);
1547 if (info->attrs[DEVLINK_ATTR_PORT_FUNCTION]) {
1548 struct nlattr *attr = info->attrs[DEVLINK_ATTR_PORT_FUNCTION];
1549 struct netlink_ext_ack *extack = info->extack;
1551 err = devlink_port_function_set(devlink_port, attr, extack);
1559 static int devlink_nl_cmd_port_split_doit(struct sk_buff *skb,
1560 struct genl_info *info)
1562 struct devlink_port *devlink_port = info->user_ptr[1];
1563 struct devlink *devlink = info->user_ptr[0];
1566 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_PORT_SPLIT_COUNT))
1568 if (!devlink->ops->port_split)
1571 count = nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_SPLIT_COUNT]);
1573 if (!devlink_port->attrs.splittable) {
1574 /* Split ports cannot be split. */
1575 if (devlink_port->attrs.split)
1576 NL_SET_ERR_MSG_MOD(info->extack, "Port cannot be split further");
1578 NL_SET_ERR_MSG_MOD(info->extack, "Port cannot be split");
1582 if (count < 2 || !is_power_of_2(count) || count > devlink_port->attrs.lanes) {
1583 NL_SET_ERR_MSG_MOD(info->extack, "Invalid split count");
1587 return devlink->ops->port_split(devlink, devlink_port, count,
1591 static int devlink_nl_cmd_port_unsplit_doit(struct sk_buff *skb,
1592 struct genl_info *info)
1594 struct devlink_port *devlink_port = info->user_ptr[1];
1595 struct devlink *devlink = info->user_ptr[0];
1597 if (!devlink->ops->port_unsplit)
1599 return devlink->ops->port_unsplit(devlink, devlink_port, info->extack);
1602 static int devlink_port_new_notify(struct devlink *devlink,
1603 unsigned int port_index,
1604 struct genl_info *info)
1606 struct devlink_port *devlink_port;
1607 struct sk_buff *msg;
1610 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
1614 lockdep_assert_held(&devlink->lock);
1615 devlink_port = devlink_port_get_by_index(devlink, port_index);
1616 if (!devlink_port) {
1621 err = devlink_nl_port_fill(msg, devlink_port, DEVLINK_CMD_NEW,
1622 info->snd_portid, info->snd_seq, 0, NULL);
1626 return genlmsg_reply(msg, info);
1633 static int devlink_nl_cmd_port_new_doit(struct sk_buff *skb,
1634 struct genl_info *info)
1636 struct netlink_ext_ack *extack = info->extack;
1637 struct devlink_port_new_attrs new_attrs = {};
1638 struct devlink *devlink = info->user_ptr[0];
1639 unsigned int new_port_index;
1642 if (!devlink->ops->port_new || !devlink->ops->port_del)
1645 if (!info->attrs[DEVLINK_ATTR_PORT_FLAVOUR] ||
1646 !info->attrs[DEVLINK_ATTR_PORT_PCI_PF_NUMBER]) {
1647 NL_SET_ERR_MSG_MOD(extack, "Port flavour or PCI PF are not specified");
1650 new_attrs.flavour = nla_get_u16(info->attrs[DEVLINK_ATTR_PORT_FLAVOUR]);
1652 nla_get_u16(info->attrs[DEVLINK_ATTR_PORT_PCI_PF_NUMBER]);
1654 if (info->attrs[DEVLINK_ATTR_PORT_INDEX]) {
1655 /* Port index of the new port being created by driver. */
1656 new_attrs.port_index =
1657 nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_INDEX]);
1658 new_attrs.port_index_valid = true;
1660 if (info->attrs[DEVLINK_ATTR_PORT_CONTROLLER_NUMBER]) {
1661 new_attrs.controller =
1662 nla_get_u16(info->attrs[DEVLINK_ATTR_PORT_CONTROLLER_NUMBER]);
1663 new_attrs.controller_valid = true;
1665 if (new_attrs.flavour == DEVLINK_PORT_FLAVOUR_PCI_SF &&
1666 info->attrs[DEVLINK_ATTR_PORT_PCI_SF_NUMBER]) {
1667 new_attrs.sfnum = nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_PCI_SF_NUMBER]);
1668 new_attrs.sfnum_valid = true;
1671 err = devlink->ops->port_new(devlink, &new_attrs, extack,
1676 err = devlink_port_new_notify(devlink, new_port_index, info);
1677 if (err && err != -ENODEV) {
1678 /* Fail to send the response; destroy newly created port. */
1679 devlink->ops->port_del(devlink, new_port_index, extack);
1684 static int devlink_nl_cmd_port_del_doit(struct sk_buff *skb,
1685 struct genl_info *info)
1687 struct netlink_ext_ack *extack = info->extack;
1688 struct devlink *devlink = info->user_ptr[0];
1689 unsigned int port_index;
1691 if (!devlink->ops->port_del)
1694 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_PORT_INDEX)) {
1695 NL_SET_ERR_MSG_MOD(extack, "Port index is not specified");
1698 port_index = nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_INDEX]);
1700 return devlink->ops->port_del(devlink, port_index, extack);
1704 devlink_nl_rate_parent_node_set(struct devlink_rate *devlink_rate,
1705 struct genl_info *info,
1706 struct nlattr *nla_parent)
1708 struct devlink *devlink = devlink_rate->devlink;
1709 const char *parent_name = nla_data(nla_parent);
1710 const struct devlink_ops *ops = devlink->ops;
1711 size_t len = strlen(parent_name);
1712 struct devlink_rate *parent;
1713 int err = -EOPNOTSUPP;
1715 parent = devlink_rate->parent;
1717 if (parent && !len) {
1718 if (devlink_rate_is_leaf(devlink_rate))
1719 err = ops->rate_leaf_parent_set(devlink_rate, NULL,
1720 devlink_rate->priv, NULL,
1722 else if (devlink_rate_is_node(devlink_rate))
1723 err = ops->rate_node_parent_set(devlink_rate, NULL,
1724 devlink_rate->priv, NULL,
1729 refcount_dec(&parent->refcnt);
1730 devlink_rate->parent = NULL;
1732 parent = devlink_rate_node_get_by_name(devlink, parent_name);
1736 if (parent == devlink_rate) {
1737 NL_SET_ERR_MSG_MOD(info->extack, "Parent to self is not allowed");
1741 if (devlink_rate_is_node(devlink_rate) &&
1742 devlink_rate_is_parent_node(devlink_rate, parent->parent)) {
1743 NL_SET_ERR_MSG_MOD(info->extack, "Node is already a parent of parent node.");
1747 if (devlink_rate_is_leaf(devlink_rate))
1748 err = ops->rate_leaf_parent_set(devlink_rate, parent,
1749 devlink_rate->priv, parent->priv,
1751 else if (devlink_rate_is_node(devlink_rate))
1752 err = ops->rate_node_parent_set(devlink_rate, parent,
1753 devlink_rate->priv, parent->priv,
1758 if (devlink_rate->parent)
1759 /* we're reassigning to other parent in this case */
1760 refcount_dec(&devlink_rate->parent->refcnt);
1762 refcount_inc(&parent->refcnt);
1763 devlink_rate->parent = parent;
1769 static int devlink_nl_rate_set(struct devlink_rate *devlink_rate,
1770 const struct devlink_ops *ops,
1771 struct genl_info *info)
1773 struct nlattr *nla_parent, **attrs = info->attrs;
1774 int err = -EOPNOTSUPP;
1779 if (attrs[DEVLINK_ATTR_RATE_TX_SHARE]) {
1780 rate = nla_get_u64(attrs[DEVLINK_ATTR_RATE_TX_SHARE]);
1781 if (devlink_rate_is_leaf(devlink_rate))
1782 err = ops->rate_leaf_tx_share_set(devlink_rate, devlink_rate->priv,
1783 rate, info->extack);
1784 else if (devlink_rate_is_node(devlink_rate))
1785 err = ops->rate_node_tx_share_set(devlink_rate, devlink_rate->priv,
1786 rate, info->extack);
1789 devlink_rate->tx_share = rate;
1792 if (attrs[DEVLINK_ATTR_RATE_TX_MAX]) {
1793 rate = nla_get_u64(attrs[DEVLINK_ATTR_RATE_TX_MAX]);
1794 if (devlink_rate_is_leaf(devlink_rate))
1795 err = ops->rate_leaf_tx_max_set(devlink_rate, devlink_rate->priv,
1796 rate, info->extack);
1797 else if (devlink_rate_is_node(devlink_rate))
1798 err = ops->rate_node_tx_max_set(devlink_rate, devlink_rate->priv,
1799 rate, info->extack);
1802 devlink_rate->tx_max = rate;
1805 if (attrs[DEVLINK_ATTR_RATE_TX_PRIORITY]) {
1806 priority = nla_get_u32(attrs[DEVLINK_ATTR_RATE_TX_PRIORITY]);
1807 if (devlink_rate_is_leaf(devlink_rate))
1808 err = ops->rate_leaf_tx_priority_set(devlink_rate, devlink_rate->priv,
1809 priority, info->extack);
1810 else if (devlink_rate_is_node(devlink_rate))
1811 err = ops->rate_node_tx_priority_set(devlink_rate, devlink_rate->priv,
1812 priority, info->extack);
1816 devlink_rate->tx_priority = priority;
1819 if (attrs[DEVLINK_ATTR_RATE_TX_WEIGHT]) {
1820 weight = nla_get_u32(attrs[DEVLINK_ATTR_RATE_TX_WEIGHT]);
1821 if (devlink_rate_is_leaf(devlink_rate))
1822 err = ops->rate_leaf_tx_weight_set(devlink_rate, devlink_rate->priv,
1823 weight, info->extack);
1824 else if (devlink_rate_is_node(devlink_rate))
1825 err = ops->rate_node_tx_weight_set(devlink_rate, devlink_rate->priv,
1826 weight, info->extack);
1830 devlink_rate->tx_weight = weight;
1833 nla_parent = attrs[DEVLINK_ATTR_RATE_PARENT_NODE_NAME];
1835 err = devlink_nl_rate_parent_node_set(devlink_rate, info,
1844 static bool devlink_rate_set_ops_supported(const struct devlink_ops *ops,
1845 struct genl_info *info,
1846 enum devlink_rate_type type)
1848 struct nlattr **attrs = info->attrs;
1850 if (type == DEVLINK_RATE_TYPE_LEAF) {
1851 if (attrs[DEVLINK_ATTR_RATE_TX_SHARE] && !ops->rate_leaf_tx_share_set) {
1852 NL_SET_ERR_MSG_MOD(info->extack, "TX share set isn't supported for the leafs");
1855 if (attrs[DEVLINK_ATTR_RATE_TX_MAX] && !ops->rate_leaf_tx_max_set) {
1856 NL_SET_ERR_MSG_MOD(info->extack, "TX max set isn't supported for the leafs");
1859 if (attrs[DEVLINK_ATTR_RATE_PARENT_NODE_NAME] &&
1860 !ops->rate_leaf_parent_set) {
1861 NL_SET_ERR_MSG_MOD(info->extack, "Parent set isn't supported for the leafs");
1864 if (attrs[DEVLINK_ATTR_RATE_TX_PRIORITY] && !ops->rate_leaf_tx_priority_set) {
1865 NL_SET_ERR_MSG_ATTR(info->extack,
1866 attrs[DEVLINK_ATTR_RATE_TX_PRIORITY],
1867 "TX priority set isn't supported for the leafs");
1870 if (attrs[DEVLINK_ATTR_RATE_TX_WEIGHT] && !ops->rate_leaf_tx_weight_set) {
1871 NL_SET_ERR_MSG_ATTR(info->extack,
1872 attrs[DEVLINK_ATTR_RATE_TX_WEIGHT],
1873 "TX weight set isn't supported for the leafs");
1876 } else if (type == DEVLINK_RATE_TYPE_NODE) {
1877 if (attrs[DEVLINK_ATTR_RATE_TX_SHARE] && !ops->rate_node_tx_share_set) {
1878 NL_SET_ERR_MSG_MOD(info->extack, "TX share set isn't supported for the nodes");
1881 if (attrs[DEVLINK_ATTR_RATE_TX_MAX] && !ops->rate_node_tx_max_set) {
1882 NL_SET_ERR_MSG_MOD(info->extack, "TX max set isn't supported for the nodes");
1885 if (attrs[DEVLINK_ATTR_RATE_PARENT_NODE_NAME] &&
1886 !ops->rate_node_parent_set) {
1887 NL_SET_ERR_MSG_MOD(info->extack, "Parent set isn't supported for the nodes");
1890 if (attrs[DEVLINK_ATTR_RATE_TX_PRIORITY] && !ops->rate_node_tx_priority_set) {
1891 NL_SET_ERR_MSG_ATTR(info->extack,
1892 attrs[DEVLINK_ATTR_RATE_TX_PRIORITY],
1893 "TX priority set isn't supported for the nodes");
1896 if (attrs[DEVLINK_ATTR_RATE_TX_WEIGHT] && !ops->rate_node_tx_weight_set) {
1897 NL_SET_ERR_MSG_ATTR(info->extack,
1898 attrs[DEVLINK_ATTR_RATE_TX_WEIGHT],
1899 "TX weight set isn't supported for the nodes");
1903 WARN(1, "Unknown type of rate object");
1910 static int devlink_nl_cmd_rate_set_doit(struct sk_buff *skb,
1911 struct genl_info *info)
1913 struct devlink_rate *devlink_rate = info->user_ptr[1];
1914 struct devlink *devlink = devlink_rate->devlink;
1915 const struct devlink_ops *ops = devlink->ops;
1918 if (!ops || !devlink_rate_set_ops_supported(ops, info, devlink_rate->type))
1921 err = devlink_nl_rate_set(devlink_rate, ops, info);
1924 devlink_rate_notify(devlink_rate, DEVLINK_CMD_RATE_NEW);
1928 static int devlink_nl_cmd_rate_new_doit(struct sk_buff *skb,
1929 struct genl_info *info)
1931 struct devlink *devlink = info->user_ptr[0];
1932 struct devlink_rate *rate_node;
1933 const struct devlink_ops *ops;
1937 if (!ops || !ops->rate_node_new || !ops->rate_node_del) {
1938 NL_SET_ERR_MSG_MOD(info->extack, "Rate nodes aren't supported");
1942 if (!devlink_rate_set_ops_supported(ops, info, DEVLINK_RATE_TYPE_NODE))
1945 rate_node = devlink_rate_node_get_from_attrs(devlink, info->attrs);
1946 if (!IS_ERR(rate_node))
1948 else if (rate_node == ERR_PTR(-EINVAL))
1951 rate_node = kzalloc(sizeof(*rate_node), GFP_KERNEL);
1955 rate_node->devlink = devlink;
1956 rate_node->type = DEVLINK_RATE_TYPE_NODE;
1957 rate_node->name = nla_strdup(info->attrs[DEVLINK_ATTR_RATE_NODE_NAME], GFP_KERNEL);
1958 if (!rate_node->name) {
1963 err = ops->rate_node_new(rate_node, &rate_node->priv, info->extack);
1967 err = devlink_nl_rate_set(rate_node, ops, info);
1971 refcount_set(&rate_node->refcnt, 1);
1972 list_add(&rate_node->list, &devlink->rate_list);
1973 devlink_rate_notify(rate_node, DEVLINK_CMD_RATE_NEW);
1977 ops->rate_node_del(rate_node, rate_node->priv, info->extack);
1979 kfree(rate_node->name);
1985 static int devlink_nl_cmd_rate_del_doit(struct sk_buff *skb,
1986 struct genl_info *info)
1988 struct devlink_rate *rate_node = info->user_ptr[1];
1989 struct devlink *devlink = rate_node->devlink;
1990 const struct devlink_ops *ops = devlink->ops;
1993 if (refcount_read(&rate_node->refcnt) > 1) {
1994 NL_SET_ERR_MSG_MOD(info->extack, "Node has children. Cannot delete node.");
1998 devlink_rate_notify(rate_node, DEVLINK_CMD_RATE_DEL);
1999 err = ops->rate_node_del(rate_node, rate_node->priv, info->extack);
2000 if (rate_node->parent)
2001 refcount_dec(&rate_node->parent->refcnt);
2002 list_del(&rate_node->list);
2003 kfree(rate_node->name);
2008 struct devlink_linecard_type {
2013 static int devlink_nl_linecard_fill(struct sk_buff *msg,
2014 struct devlink *devlink,
2015 struct devlink_linecard *linecard,
2016 enum devlink_command cmd, u32 portid,
2018 struct netlink_ext_ack *extack)
2020 struct devlink_linecard_type *linecard_type;
2021 struct nlattr *attr;
2025 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
2029 if (devlink_nl_put_handle(msg, devlink))
2030 goto nla_put_failure;
2031 if (nla_put_u32(msg, DEVLINK_ATTR_LINECARD_INDEX, linecard->index))
2032 goto nla_put_failure;
2033 if (nla_put_u8(msg, DEVLINK_ATTR_LINECARD_STATE, linecard->state))
2034 goto nla_put_failure;
2035 if (linecard->type &&
2036 nla_put_string(msg, DEVLINK_ATTR_LINECARD_TYPE, linecard->type))
2037 goto nla_put_failure;
2039 if (linecard->types_count) {
2040 attr = nla_nest_start(msg,
2041 DEVLINK_ATTR_LINECARD_SUPPORTED_TYPES);
2043 goto nla_put_failure;
2044 for (i = 0; i < linecard->types_count; i++) {
2045 linecard_type = &linecard->types[i];
2046 if (nla_put_string(msg, DEVLINK_ATTR_LINECARD_TYPE,
2047 linecard_type->type)) {
2048 nla_nest_cancel(msg, attr);
2049 goto nla_put_failure;
2052 nla_nest_end(msg, attr);
2055 if (linecard->nested_devlink &&
2056 devlink_nl_put_nested_handle(msg, linecard->nested_devlink))
2057 goto nla_put_failure;
2059 genlmsg_end(msg, hdr);
2063 genlmsg_cancel(msg, hdr);
2067 static void devlink_linecard_notify(struct devlink_linecard *linecard,
2068 enum devlink_command cmd)
2070 struct devlink *devlink = linecard->devlink;
2071 struct sk_buff *msg;
2074 WARN_ON(cmd != DEVLINK_CMD_LINECARD_NEW &&
2075 cmd != DEVLINK_CMD_LINECARD_DEL);
2077 if (!xa_get_mark(&devlinks, devlink->index, DEVLINK_REGISTERED))
2080 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
2084 err = devlink_nl_linecard_fill(msg, devlink, linecard, cmd, 0, 0, 0,
2091 genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink),
2092 msg, 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
2095 static int devlink_nl_cmd_linecard_get_doit(struct sk_buff *skb,
2096 struct genl_info *info)
2098 struct devlink_linecard *linecard = info->user_ptr[1];
2099 struct devlink *devlink = linecard->devlink;
2100 struct sk_buff *msg;
2103 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
2107 mutex_lock(&linecard->state_lock);
2108 err = devlink_nl_linecard_fill(msg, devlink, linecard,
2109 DEVLINK_CMD_LINECARD_NEW,
2110 info->snd_portid, info->snd_seq, 0,
2112 mutex_unlock(&linecard->state_lock);
2118 return genlmsg_reply(msg, info);
2121 static int devlink_nl_cmd_linecard_get_dumpit(struct sk_buff *msg,
2122 struct netlink_callback *cb)
2124 struct devlink_nl_dump_state *state = devlink_dump_state(cb);
2125 struct devlink_linecard *linecard;
2126 struct devlink *devlink;
2129 devlink_dump_for_each_instance_get(msg, state, devlink) {
2132 mutex_lock(&devlink->linecards_lock);
2133 if (!devl_is_registered(devlink))
2136 list_for_each_entry(linecard, &devlink->linecard_list, list) {
2137 if (idx < state->idx) {
2141 mutex_lock(&linecard->state_lock);
2142 err = devlink_nl_linecard_fill(msg, devlink, linecard,
2143 DEVLINK_CMD_LINECARD_NEW,
2144 NETLINK_CB(cb->skb).portid,
2148 mutex_unlock(&linecard->state_lock);
2150 mutex_unlock(&devlink->linecards_lock);
2151 devlink_put(devlink);
2158 mutex_unlock(&devlink->linecards_lock);
2159 devlink_put(devlink);
2165 static struct devlink_linecard_type *
2166 devlink_linecard_type_lookup(struct devlink_linecard *linecard,
2169 struct devlink_linecard_type *linecard_type;
2172 for (i = 0; i < linecard->types_count; i++) {
2173 linecard_type = &linecard->types[i];
2174 if (!strcmp(type, linecard_type->type))
2175 return linecard_type;
2180 static int devlink_linecard_type_set(struct devlink_linecard *linecard,
2182 struct netlink_ext_ack *extack)
2184 const struct devlink_linecard_ops *ops = linecard->ops;
2185 struct devlink_linecard_type *linecard_type;
2188 mutex_lock(&linecard->state_lock);
2189 if (linecard->state == DEVLINK_LINECARD_STATE_PROVISIONING) {
2190 NL_SET_ERR_MSG_MOD(extack, "Line card is currently being provisioned");
2194 if (linecard->state == DEVLINK_LINECARD_STATE_UNPROVISIONING) {
2195 NL_SET_ERR_MSG_MOD(extack, "Line card is currently being unprovisioned");
2200 linecard_type = devlink_linecard_type_lookup(linecard, type);
2201 if (!linecard_type) {
2202 NL_SET_ERR_MSG_MOD(extack, "Unsupported line card type provided");
2207 if (linecard->state != DEVLINK_LINECARD_STATE_UNPROVISIONED &&
2208 linecard->state != DEVLINK_LINECARD_STATE_PROVISIONING_FAILED) {
2209 NL_SET_ERR_MSG_MOD(extack, "Line card already provisioned");
2211 /* Check if the line card is provisioned in the same
2212 * way the user asks. In case it is, make the operation
2213 * to return success.
2215 if (ops->same_provision &&
2216 ops->same_provision(linecard, linecard->priv,
2217 linecard_type->type,
2218 linecard_type->priv))
2223 linecard->state = DEVLINK_LINECARD_STATE_PROVISIONING;
2224 linecard->type = linecard_type->type;
2225 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_NEW);
2226 mutex_unlock(&linecard->state_lock);
2227 err = ops->provision(linecard, linecard->priv, linecard_type->type,
2228 linecard_type->priv, extack);
2230 /* Provisioning failed. Assume the linecard is unprovisioned
2231 * for future operations.
2233 mutex_lock(&linecard->state_lock);
2234 linecard->state = DEVLINK_LINECARD_STATE_UNPROVISIONED;
2235 linecard->type = NULL;
2236 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_NEW);
2237 mutex_unlock(&linecard->state_lock);
2242 mutex_unlock(&linecard->state_lock);
2246 static int devlink_linecard_type_unset(struct devlink_linecard *linecard,
2247 struct netlink_ext_ack *extack)
2251 mutex_lock(&linecard->state_lock);
2252 if (linecard->state == DEVLINK_LINECARD_STATE_PROVISIONING) {
2253 NL_SET_ERR_MSG_MOD(extack, "Line card is currently being provisioned");
2257 if (linecard->state == DEVLINK_LINECARD_STATE_UNPROVISIONING) {
2258 NL_SET_ERR_MSG_MOD(extack, "Line card is currently being unprovisioned");
2262 if (linecard->state == DEVLINK_LINECARD_STATE_PROVISIONING_FAILED) {
2263 linecard->state = DEVLINK_LINECARD_STATE_UNPROVISIONED;
2264 linecard->type = NULL;
2265 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_NEW);
2270 if (linecard->state == DEVLINK_LINECARD_STATE_UNPROVISIONED) {
2271 NL_SET_ERR_MSG_MOD(extack, "Line card is not provisioned");
2275 linecard->state = DEVLINK_LINECARD_STATE_UNPROVISIONING;
2276 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_NEW);
2277 mutex_unlock(&linecard->state_lock);
2278 err = linecard->ops->unprovision(linecard, linecard->priv,
2281 /* Unprovisioning failed. Assume the linecard is unprovisioned
2282 * for future operations.
2284 mutex_lock(&linecard->state_lock);
2285 linecard->state = DEVLINK_LINECARD_STATE_UNPROVISIONED;
2286 linecard->type = NULL;
2287 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_NEW);
2288 mutex_unlock(&linecard->state_lock);
2293 mutex_unlock(&linecard->state_lock);
2297 static int devlink_nl_cmd_linecard_set_doit(struct sk_buff *skb,
2298 struct genl_info *info)
2300 struct devlink_linecard *linecard = info->user_ptr[1];
2301 struct netlink_ext_ack *extack = info->extack;
2304 if (info->attrs[DEVLINK_ATTR_LINECARD_TYPE]) {
2307 type = nla_data(info->attrs[DEVLINK_ATTR_LINECARD_TYPE]);
2308 if (strcmp(type, "")) {
2309 err = devlink_linecard_type_set(linecard, type, extack);
2313 err = devlink_linecard_type_unset(linecard, extack);
2322 static int devlink_nl_sb_fill(struct sk_buff *msg, struct devlink *devlink,
2323 struct devlink_sb *devlink_sb,
2324 enum devlink_command cmd, u32 portid,
2329 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
2333 if (devlink_nl_put_handle(msg, devlink))
2334 goto nla_put_failure;
2335 if (nla_put_u32(msg, DEVLINK_ATTR_SB_INDEX, devlink_sb->index))
2336 goto nla_put_failure;
2337 if (nla_put_u32(msg, DEVLINK_ATTR_SB_SIZE, devlink_sb->size))
2338 goto nla_put_failure;
2339 if (nla_put_u16(msg, DEVLINK_ATTR_SB_INGRESS_POOL_COUNT,
2340 devlink_sb->ingress_pools_count))
2341 goto nla_put_failure;
2342 if (nla_put_u16(msg, DEVLINK_ATTR_SB_EGRESS_POOL_COUNT,
2343 devlink_sb->egress_pools_count))
2344 goto nla_put_failure;
2345 if (nla_put_u16(msg, DEVLINK_ATTR_SB_INGRESS_TC_COUNT,
2346 devlink_sb->ingress_tc_count))
2347 goto nla_put_failure;
2348 if (nla_put_u16(msg, DEVLINK_ATTR_SB_EGRESS_TC_COUNT,
2349 devlink_sb->egress_tc_count))
2350 goto nla_put_failure;
2352 genlmsg_end(msg, hdr);
2356 genlmsg_cancel(msg, hdr);
2360 static int devlink_nl_cmd_sb_get_doit(struct sk_buff *skb,
2361 struct genl_info *info)
2363 struct devlink *devlink = info->user_ptr[0];
2364 struct devlink_sb *devlink_sb;
2365 struct sk_buff *msg;
2368 devlink_sb = devlink_sb_get_from_info(devlink, info);
2369 if (IS_ERR(devlink_sb))
2370 return PTR_ERR(devlink_sb);
2372 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
2376 err = devlink_nl_sb_fill(msg, devlink, devlink_sb,
2378 info->snd_portid, info->snd_seq, 0);
2384 return genlmsg_reply(msg, info);
2388 devlink_nl_cmd_sb_get_dump_one(struct sk_buff *msg, struct devlink *devlink,
2389 struct netlink_callback *cb)
2391 struct devlink_nl_dump_state *state = devlink_dump_state(cb);
2392 struct devlink_sb *devlink_sb;
2396 list_for_each_entry(devlink_sb, &devlink->sb_list, list) {
2397 if (idx < state->idx) {
2401 err = devlink_nl_sb_fill(msg, devlink, devlink_sb,
2403 NETLINK_CB(cb->skb).portid,
2416 const struct devlink_gen_cmd devl_gen_sb = {
2417 .dump_one = devlink_nl_cmd_sb_get_dump_one,
2420 static int devlink_nl_sb_pool_fill(struct sk_buff *msg, struct devlink *devlink,
2421 struct devlink_sb *devlink_sb,
2422 u16 pool_index, enum devlink_command cmd,
2423 u32 portid, u32 seq, int flags)
2425 struct devlink_sb_pool_info pool_info;
2429 err = devlink->ops->sb_pool_get(devlink, devlink_sb->index,
2430 pool_index, &pool_info);
2434 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
2438 if (devlink_nl_put_handle(msg, devlink))
2439 goto nla_put_failure;
2440 if (nla_put_u32(msg, DEVLINK_ATTR_SB_INDEX, devlink_sb->index))
2441 goto nla_put_failure;
2442 if (nla_put_u16(msg, DEVLINK_ATTR_SB_POOL_INDEX, pool_index))
2443 goto nla_put_failure;
2444 if (nla_put_u8(msg, DEVLINK_ATTR_SB_POOL_TYPE, pool_info.pool_type))
2445 goto nla_put_failure;
2446 if (nla_put_u32(msg, DEVLINK_ATTR_SB_POOL_SIZE, pool_info.size))
2447 goto nla_put_failure;
2448 if (nla_put_u8(msg, DEVLINK_ATTR_SB_POOL_THRESHOLD_TYPE,
2449 pool_info.threshold_type))
2450 goto nla_put_failure;
2451 if (nla_put_u32(msg, DEVLINK_ATTR_SB_POOL_CELL_SIZE,
2452 pool_info.cell_size))
2453 goto nla_put_failure;
2455 genlmsg_end(msg, hdr);
2459 genlmsg_cancel(msg, hdr);
2463 static int devlink_nl_cmd_sb_pool_get_doit(struct sk_buff *skb,
2464 struct genl_info *info)
2466 struct devlink *devlink = info->user_ptr[0];
2467 struct devlink_sb *devlink_sb;
2468 struct sk_buff *msg;
2472 devlink_sb = devlink_sb_get_from_info(devlink, info);
2473 if (IS_ERR(devlink_sb))
2474 return PTR_ERR(devlink_sb);
2476 err = devlink_sb_pool_index_get_from_info(devlink_sb, info,
2481 if (!devlink->ops->sb_pool_get)
2484 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
2488 err = devlink_nl_sb_pool_fill(msg, devlink, devlink_sb, pool_index,
2489 DEVLINK_CMD_SB_POOL_NEW,
2490 info->snd_portid, info->snd_seq, 0);
2496 return genlmsg_reply(msg, info);
2499 static int __sb_pool_get_dumpit(struct sk_buff *msg, int start, int *p_idx,
2500 struct devlink *devlink,
2501 struct devlink_sb *devlink_sb,
2502 u32 portid, u32 seq)
2504 u16 pool_count = devlink_sb_pool_count(devlink_sb);
2508 for (pool_index = 0; pool_index < pool_count; pool_index++) {
2509 if (*p_idx < start) {
2513 err = devlink_nl_sb_pool_fill(msg, devlink,
2516 DEVLINK_CMD_SB_POOL_NEW,
2517 portid, seq, NLM_F_MULTI);
2526 devlink_nl_cmd_sb_pool_get_dump_one(struct sk_buff *msg,
2527 struct devlink *devlink,
2528 struct netlink_callback *cb)
2530 struct devlink_nl_dump_state *state = devlink_dump_state(cb);
2531 struct devlink_sb *devlink_sb;
2535 if (!devlink->ops->sb_pool_get)
2538 list_for_each_entry(devlink_sb, &devlink->sb_list, list) {
2539 err = __sb_pool_get_dumpit(msg, state->idx, &idx,
2540 devlink, devlink_sb,
2541 NETLINK_CB(cb->skb).portid,
2542 cb->nlh->nlmsg_seq);
2543 if (err == -EOPNOTSUPP) {
2554 const struct devlink_gen_cmd devl_gen_sb_pool = {
2555 .dump_one = devlink_nl_cmd_sb_pool_get_dump_one,
2558 static int devlink_sb_pool_set(struct devlink *devlink, unsigned int sb_index,
2559 u16 pool_index, u32 size,
2560 enum devlink_sb_threshold_type threshold_type,
2561 struct netlink_ext_ack *extack)
2564 const struct devlink_ops *ops = devlink->ops;
2566 if (ops->sb_pool_set)
2567 return ops->sb_pool_set(devlink, sb_index, pool_index,
2568 size, threshold_type, extack);
2572 static int devlink_nl_cmd_sb_pool_set_doit(struct sk_buff *skb,
2573 struct genl_info *info)
2575 struct devlink *devlink = info->user_ptr[0];
2576 enum devlink_sb_threshold_type threshold_type;
2577 struct devlink_sb *devlink_sb;
2582 devlink_sb = devlink_sb_get_from_info(devlink, info);
2583 if (IS_ERR(devlink_sb))
2584 return PTR_ERR(devlink_sb);
2586 err = devlink_sb_pool_index_get_from_info(devlink_sb, info,
2591 err = devlink_sb_th_type_get_from_info(info, &threshold_type);
2595 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_SB_POOL_SIZE))
2598 size = nla_get_u32(info->attrs[DEVLINK_ATTR_SB_POOL_SIZE]);
2599 return devlink_sb_pool_set(devlink, devlink_sb->index,
2600 pool_index, size, threshold_type,
2604 static int devlink_nl_sb_port_pool_fill(struct sk_buff *msg,
2605 struct devlink *devlink,
2606 struct devlink_port *devlink_port,
2607 struct devlink_sb *devlink_sb,
2609 enum devlink_command cmd,
2610 u32 portid, u32 seq, int flags)
2612 const struct devlink_ops *ops = devlink->ops;
2617 err = ops->sb_port_pool_get(devlink_port, devlink_sb->index,
2618 pool_index, &threshold);
2622 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
2626 if (devlink_nl_put_handle(msg, devlink))
2627 goto nla_put_failure;
2628 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_INDEX, devlink_port->index))
2629 goto nla_put_failure;
2630 if (nla_put_u32(msg, DEVLINK_ATTR_SB_INDEX, devlink_sb->index))
2631 goto nla_put_failure;
2632 if (nla_put_u16(msg, DEVLINK_ATTR_SB_POOL_INDEX, pool_index))
2633 goto nla_put_failure;
2634 if (nla_put_u32(msg, DEVLINK_ATTR_SB_THRESHOLD, threshold))
2635 goto nla_put_failure;
2637 if (ops->sb_occ_port_pool_get) {
2641 err = ops->sb_occ_port_pool_get(devlink_port, devlink_sb->index,
2642 pool_index, &cur, &max);
2643 if (err && err != -EOPNOTSUPP)
2644 goto sb_occ_get_failure;
2646 if (nla_put_u32(msg, DEVLINK_ATTR_SB_OCC_CUR, cur))
2647 goto nla_put_failure;
2648 if (nla_put_u32(msg, DEVLINK_ATTR_SB_OCC_MAX, max))
2649 goto nla_put_failure;
2653 genlmsg_end(msg, hdr);
2659 genlmsg_cancel(msg, hdr);
2663 static int devlink_nl_cmd_sb_port_pool_get_doit(struct sk_buff *skb,
2664 struct genl_info *info)
2666 struct devlink_port *devlink_port = info->user_ptr[1];
2667 struct devlink *devlink = devlink_port->devlink;
2668 struct devlink_sb *devlink_sb;
2669 struct sk_buff *msg;
2673 devlink_sb = devlink_sb_get_from_info(devlink, info);
2674 if (IS_ERR(devlink_sb))
2675 return PTR_ERR(devlink_sb);
2677 err = devlink_sb_pool_index_get_from_info(devlink_sb, info,
2682 if (!devlink->ops->sb_port_pool_get)
2685 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
2689 err = devlink_nl_sb_port_pool_fill(msg, devlink, devlink_port,
2690 devlink_sb, pool_index,
2691 DEVLINK_CMD_SB_PORT_POOL_NEW,
2692 info->snd_portid, info->snd_seq, 0);
2698 return genlmsg_reply(msg, info);
2701 static int __sb_port_pool_get_dumpit(struct sk_buff *msg, int start, int *p_idx,
2702 struct devlink *devlink,
2703 struct devlink_sb *devlink_sb,
2704 u32 portid, u32 seq)
2706 struct devlink_port *devlink_port;
2707 u16 pool_count = devlink_sb_pool_count(devlink_sb);
2708 unsigned long port_index;
2712 xa_for_each(&devlink->ports, port_index, devlink_port) {
2713 for (pool_index = 0; pool_index < pool_count; pool_index++) {
2714 if (*p_idx < start) {
2718 err = devlink_nl_sb_port_pool_fill(msg, devlink,
2722 DEVLINK_CMD_SB_PORT_POOL_NEW,
2734 devlink_nl_cmd_sb_port_pool_get_dump_one(struct sk_buff *msg,
2735 struct devlink *devlink,
2736 struct netlink_callback *cb)
2738 struct devlink_nl_dump_state *state = devlink_dump_state(cb);
2739 struct devlink_sb *devlink_sb;
2743 if (!devlink->ops->sb_port_pool_get)
2746 list_for_each_entry(devlink_sb, &devlink->sb_list, list) {
2747 err = __sb_port_pool_get_dumpit(msg, state->idx, &idx,
2748 devlink, devlink_sb,
2749 NETLINK_CB(cb->skb).portid,
2750 cb->nlh->nlmsg_seq);
2751 if (err == -EOPNOTSUPP) {
2762 const struct devlink_gen_cmd devl_gen_sb_port_pool = {
2763 .dump_one = devlink_nl_cmd_sb_port_pool_get_dump_one,
2766 static int devlink_sb_port_pool_set(struct devlink_port *devlink_port,
2767 unsigned int sb_index, u16 pool_index,
2769 struct netlink_ext_ack *extack)
2772 const struct devlink_ops *ops = devlink_port->devlink->ops;
2774 if (ops->sb_port_pool_set)
2775 return ops->sb_port_pool_set(devlink_port, sb_index,
2776 pool_index, threshold, extack);
2780 static int devlink_nl_cmd_sb_port_pool_set_doit(struct sk_buff *skb,
2781 struct genl_info *info)
2783 struct devlink_port *devlink_port = info->user_ptr[1];
2784 struct devlink *devlink = info->user_ptr[0];
2785 struct devlink_sb *devlink_sb;
2790 devlink_sb = devlink_sb_get_from_info(devlink, info);
2791 if (IS_ERR(devlink_sb))
2792 return PTR_ERR(devlink_sb);
2794 err = devlink_sb_pool_index_get_from_info(devlink_sb, info,
2799 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_SB_THRESHOLD))
2802 threshold = nla_get_u32(info->attrs[DEVLINK_ATTR_SB_THRESHOLD]);
2803 return devlink_sb_port_pool_set(devlink_port, devlink_sb->index,
2804 pool_index, threshold, info->extack);
2808 devlink_nl_sb_tc_pool_bind_fill(struct sk_buff *msg, struct devlink *devlink,
2809 struct devlink_port *devlink_port,
2810 struct devlink_sb *devlink_sb, u16 tc_index,
2811 enum devlink_sb_pool_type pool_type,
2812 enum devlink_command cmd,
2813 u32 portid, u32 seq, int flags)
2815 const struct devlink_ops *ops = devlink->ops;
2821 err = ops->sb_tc_pool_bind_get(devlink_port, devlink_sb->index,
2822 tc_index, pool_type,
2823 &pool_index, &threshold);
2827 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
2831 if (devlink_nl_put_handle(msg, devlink))
2832 goto nla_put_failure;
2833 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_INDEX, devlink_port->index))
2834 goto nla_put_failure;
2835 if (nla_put_u32(msg, DEVLINK_ATTR_SB_INDEX, devlink_sb->index))
2836 goto nla_put_failure;
2837 if (nla_put_u16(msg, DEVLINK_ATTR_SB_TC_INDEX, tc_index))
2838 goto nla_put_failure;
2839 if (nla_put_u8(msg, DEVLINK_ATTR_SB_POOL_TYPE, pool_type))
2840 goto nla_put_failure;
2841 if (nla_put_u16(msg, DEVLINK_ATTR_SB_POOL_INDEX, pool_index))
2842 goto nla_put_failure;
2843 if (nla_put_u32(msg, DEVLINK_ATTR_SB_THRESHOLD, threshold))
2844 goto nla_put_failure;
2846 if (ops->sb_occ_tc_port_bind_get) {
2850 err = ops->sb_occ_tc_port_bind_get(devlink_port,
2852 tc_index, pool_type,
2854 if (err && err != -EOPNOTSUPP)
2857 if (nla_put_u32(msg, DEVLINK_ATTR_SB_OCC_CUR, cur))
2858 goto nla_put_failure;
2859 if (nla_put_u32(msg, DEVLINK_ATTR_SB_OCC_MAX, max))
2860 goto nla_put_failure;
2864 genlmsg_end(msg, hdr);
2868 genlmsg_cancel(msg, hdr);
2872 static int devlink_nl_cmd_sb_tc_pool_bind_get_doit(struct sk_buff *skb,
2873 struct genl_info *info)
2875 struct devlink_port *devlink_port = info->user_ptr[1];
2876 struct devlink *devlink = devlink_port->devlink;
2877 struct devlink_sb *devlink_sb;
2878 struct sk_buff *msg;
2879 enum devlink_sb_pool_type pool_type;
2883 devlink_sb = devlink_sb_get_from_info(devlink, info);
2884 if (IS_ERR(devlink_sb))
2885 return PTR_ERR(devlink_sb);
2887 err = devlink_sb_pool_type_get_from_info(info, &pool_type);
2891 err = devlink_sb_tc_index_get_from_info(devlink_sb, info,
2892 pool_type, &tc_index);
2896 if (!devlink->ops->sb_tc_pool_bind_get)
2899 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
2903 err = devlink_nl_sb_tc_pool_bind_fill(msg, devlink, devlink_port,
2904 devlink_sb, tc_index, pool_type,
2905 DEVLINK_CMD_SB_TC_POOL_BIND_NEW,
2913 return genlmsg_reply(msg, info);
2916 static int __sb_tc_pool_bind_get_dumpit(struct sk_buff *msg,
2917 int start, int *p_idx,
2918 struct devlink *devlink,
2919 struct devlink_sb *devlink_sb,
2920 u32 portid, u32 seq)
2922 struct devlink_port *devlink_port;
2923 unsigned long port_index;
2927 xa_for_each(&devlink->ports, port_index, devlink_port) {
2929 tc_index < devlink_sb->ingress_tc_count; tc_index++) {
2930 if (*p_idx < start) {
2934 err = devlink_nl_sb_tc_pool_bind_fill(msg, devlink,
2938 DEVLINK_SB_POOL_TYPE_INGRESS,
2939 DEVLINK_CMD_SB_TC_POOL_BIND_NEW,
2947 tc_index < devlink_sb->egress_tc_count; tc_index++) {
2948 if (*p_idx < start) {
2952 err = devlink_nl_sb_tc_pool_bind_fill(msg, devlink,
2956 DEVLINK_SB_POOL_TYPE_EGRESS,
2957 DEVLINK_CMD_SB_TC_POOL_BIND_NEW,
2969 devlink_nl_cmd_sb_tc_pool_bind_get_dump_one(struct sk_buff *msg,
2970 struct devlink *devlink,
2971 struct netlink_callback *cb)
2973 struct devlink_nl_dump_state *state = devlink_dump_state(cb);
2974 struct devlink_sb *devlink_sb;
2978 if (!devlink->ops->sb_tc_pool_bind_get)
2981 list_for_each_entry(devlink_sb, &devlink->sb_list, list) {
2982 err = __sb_tc_pool_bind_get_dumpit(msg, state->idx, &idx,
2983 devlink, devlink_sb,
2984 NETLINK_CB(cb->skb).portid,
2985 cb->nlh->nlmsg_seq);
2986 if (err == -EOPNOTSUPP) {
2997 const struct devlink_gen_cmd devl_gen_sb_tc_pool_bind = {
2998 .dump_one = devlink_nl_cmd_sb_tc_pool_bind_get_dump_one,
3001 static int devlink_sb_tc_pool_bind_set(struct devlink_port *devlink_port,
3002 unsigned int sb_index, u16 tc_index,
3003 enum devlink_sb_pool_type pool_type,
3004 u16 pool_index, u32 threshold,
3005 struct netlink_ext_ack *extack)
3008 const struct devlink_ops *ops = devlink_port->devlink->ops;
3010 if (ops->sb_tc_pool_bind_set)
3011 return ops->sb_tc_pool_bind_set(devlink_port, sb_index,
3012 tc_index, pool_type,
3013 pool_index, threshold, extack);
3017 static int devlink_nl_cmd_sb_tc_pool_bind_set_doit(struct sk_buff *skb,
3018 struct genl_info *info)
3020 struct devlink_port *devlink_port = info->user_ptr[1];
3021 struct devlink *devlink = info->user_ptr[0];
3022 enum devlink_sb_pool_type pool_type;
3023 struct devlink_sb *devlink_sb;
3029 devlink_sb = devlink_sb_get_from_info(devlink, info);
3030 if (IS_ERR(devlink_sb))
3031 return PTR_ERR(devlink_sb);
3033 err = devlink_sb_pool_type_get_from_info(info, &pool_type);
3037 err = devlink_sb_tc_index_get_from_info(devlink_sb, info,
3038 pool_type, &tc_index);
3042 err = devlink_sb_pool_index_get_from_info(devlink_sb, info,
3047 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_SB_THRESHOLD))
3050 threshold = nla_get_u32(info->attrs[DEVLINK_ATTR_SB_THRESHOLD]);
3051 return devlink_sb_tc_pool_bind_set(devlink_port, devlink_sb->index,
3052 tc_index, pool_type,
3053 pool_index, threshold, info->extack);
3056 static int devlink_nl_cmd_sb_occ_snapshot_doit(struct sk_buff *skb,
3057 struct genl_info *info)
3059 struct devlink *devlink = info->user_ptr[0];
3060 const struct devlink_ops *ops = devlink->ops;
3061 struct devlink_sb *devlink_sb;
3063 devlink_sb = devlink_sb_get_from_info(devlink, info);
3064 if (IS_ERR(devlink_sb))
3065 return PTR_ERR(devlink_sb);
3067 if (ops->sb_occ_snapshot)
3068 return ops->sb_occ_snapshot(devlink, devlink_sb->index);
3072 static int devlink_nl_cmd_sb_occ_max_clear_doit(struct sk_buff *skb,
3073 struct genl_info *info)
3075 struct devlink *devlink = info->user_ptr[0];
3076 const struct devlink_ops *ops = devlink->ops;
3077 struct devlink_sb *devlink_sb;
3079 devlink_sb = devlink_sb_get_from_info(devlink, info);
3080 if (IS_ERR(devlink_sb))
3081 return PTR_ERR(devlink_sb);
3083 if (ops->sb_occ_max_clear)
3084 return ops->sb_occ_max_clear(devlink, devlink_sb->index);
3088 static int devlink_nl_eswitch_fill(struct sk_buff *msg, struct devlink *devlink,
3089 enum devlink_command cmd, u32 portid,
3092 const struct devlink_ops *ops = devlink->ops;
3093 enum devlink_eswitch_encap_mode encap_mode;
3099 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
3103 err = devlink_nl_put_handle(msg, devlink);
3105 goto nla_put_failure;
3107 if (ops->eswitch_mode_get) {
3108 err = ops->eswitch_mode_get(devlink, &mode);
3110 goto nla_put_failure;
3111 err = nla_put_u16(msg, DEVLINK_ATTR_ESWITCH_MODE, mode);
3113 goto nla_put_failure;
3116 if (ops->eswitch_inline_mode_get) {
3117 err = ops->eswitch_inline_mode_get(devlink, &inline_mode);
3119 goto nla_put_failure;
3120 err = nla_put_u8(msg, DEVLINK_ATTR_ESWITCH_INLINE_MODE,
3123 goto nla_put_failure;
3126 if (ops->eswitch_encap_mode_get) {
3127 err = ops->eswitch_encap_mode_get(devlink, &encap_mode);
3129 goto nla_put_failure;
3130 err = nla_put_u8(msg, DEVLINK_ATTR_ESWITCH_ENCAP_MODE, encap_mode);
3132 goto nla_put_failure;
3135 genlmsg_end(msg, hdr);
3139 genlmsg_cancel(msg, hdr);
3143 static int devlink_nl_cmd_eswitch_get_doit(struct sk_buff *skb,
3144 struct genl_info *info)
3146 struct devlink *devlink = info->user_ptr[0];
3147 struct sk_buff *msg;
3150 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
3154 err = devlink_nl_eswitch_fill(msg, devlink, DEVLINK_CMD_ESWITCH_GET,
3155 info->snd_portid, info->snd_seq, 0);
3162 return genlmsg_reply(msg, info);
3165 static int devlink_rate_nodes_check(struct devlink *devlink, u16 mode,
3166 struct netlink_ext_ack *extack)
3168 struct devlink_rate *devlink_rate;
3170 list_for_each_entry(devlink_rate, &devlink->rate_list, list)
3171 if (devlink_rate_is_node(devlink_rate)) {
3172 NL_SET_ERR_MSG_MOD(extack, "Rate node(s) exists.");
3178 static int devlink_nl_cmd_eswitch_set_doit(struct sk_buff *skb,
3179 struct genl_info *info)
3181 struct devlink *devlink = info->user_ptr[0];
3182 const struct devlink_ops *ops = devlink->ops;
3183 enum devlink_eswitch_encap_mode encap_mode;
3188 if (info->attrs[DEVLINK_ATTR_ESWITCH_MODE]) {
3189 if (!ops->eswitch_mode_set)
3191 mode = nla_get_u16(info->attrs[DEVLINK_ATTR_ESWITCH_MODE]);
3192 err = devlink_rate_nodes_check(devlink, mode, info->extack);
3195 err = ops->eswitch_mode_set(devlink, mode, info->extack);
3200 if (info->attrs[DEVLINK_ATTR_ESWITCH_INLINE_MODE]) {
3201 if (!ops->eswitch_inline_mode_set)
3203 inline_mode = nla_get_u8(
3204 info->attrs[DEVLINK_ATTR_ESWITCH_INLINE_MODE]);
3205 err = ops->eswitch_inline_mode_set(devlink, inline_mode,
3211 if (info->attrs[DEVLINK_ATTR_ESWITCH_ENCAP_MODE]) {
3212 if (!ops->eswitch_encap_mode_set)
3214 encap_mode = nla_get_u8(info->attrs[DEVLINK_ATTR_ESWITCH_ENCAP_MODE]);
3215 err = ops->eswitch_encap_mode_set(devlink, encap_mode,
3224 int devlink_dpipe_match_put(struct sk_buff *skb,
3225 struct devlink_dpipe_match *match)
3227 struct devlink_dpipe_header *header = match->header;
3228 struct devlink_dpipe_field *field = &header->fields[match->field_id];
3229 struct nlattr *match_attr;
3231 match_attr = nla_nest_start_noflag(skb, DEVLINK_ATTR_DPIPE_MATCH);
3235 if (nla_put_u32(skb, DEVLINK_ATTR_DPIPE_MATCH_TYPE, match->type) ||
3236 nla_put_u32(skb, DEVLINK_ATTR_DPIPE_HEADER_INDEX, match->header_index) ||
3237 nla_put_u32(skb, DEVLINK_ATTR_DPIPE_HEADER_ID, header->id) ||
3238 nla_put_u32(skb, DEVLINK_ATTR_DPIPE_FIELD_ID, field->id) ||
3239 nla_put_u8(skb, DEVLINK_ATTR_DPIPE_HEADER_GLOBAL, header->global))
3240 goto nla_put_failure;
3242 nla_nest_end(skb, match_attr);
3246 nla_nest_cancel(skb, match_attr);
3249 EXPORT_SYMBOL_GPL(devlink_dpipe_match_put);
3251 static int devlink_dpipe_matches_put(struct devlink_dpipe_table *table,
3252 struct sk_buff *skb)
3254 struct nlattr *matches_attr;
3256 matches_attr = nla_nest_start_noflag(skb,
3257 DEVLINK_ATTR_DPIPE_TABLE_MATCHES);
3261 if (table->table_ops->matches_dump(table->priv, skb))
3262 goto nla_put_failure;
3264 nla_nest_end(skb, matches_attr);
3268 nla_nest_cancel(skb, matches_attr);
3272 int devlink_dpipe_action_put(struct sk_buff *skb,
3273 struct devlink_dpipe_action *action)
3275 struct devlink_dpipe_header *header = action->header;
3276 struct devlink_dpipe_field *field = &header->fields[action->field_id];
3277 struct nlattr *action_attr;
3279 action_attr = nla_nest_start_noflag(skb, DEVLINK_ATTR_DPIPE_ACTION);
3283 if (nla_put_u32(skb, DEVLINK_ATTR_DPIPE_ACTION_TYPE, action->type) ||
3284 nla_put_u32(skb, DEVLINK_ATTR_DPIPE_HEADER_INDEX, action->header_index) ||
3285 nla_put_u32(skb, DEVLINK_ATTR_DPIPE_HEADER_ID, header->id) ||
3286 nla_put_u32(skb, DEVLINK_ATTR_DPIPE_FIELD_ID, field->id) ||
3287 nla_put_u8(skb, DEVLINK_ATTR_DPIPE_HEADER_GLOBAL, header->global))
3288 goto nla_put_failure;
3290 nla_nest_end(skb, action_attr);
3294 nla_nest_cancel(skb, action_attr);
3297 EXPORT_SYMBOL_GPL(devlink_dpipe_action_put);
3299 static int devlink_dpipe_actions_put(struct devlink_dpipe_table *table,
3300 struct sk_buff *skb)
3302 struct nlattr *actions_attr;
3304 actions_attr = nla_nest_start_noflag(skb,
3305 DEVLINK_ATTR_DPIPE_TABLE_ACTIONS);
3309 if (table->table_ops->actions_dump(table->priv, skb))
3310 goto nla_put_failure;
3312 nla_nest_end(skb, actions_attr);
3316 nla_nest_cancel(skb, actions_attr);
3320 static int devlink_dpipe_table_put(struct sk_buff *skb,
3321 struct devlink_dpipe_table *table)
3323 struct nlattr *table_attr;
3326 table_size = table->table_ops->size_get(table->priv);
3327 table_attr = nla_nest_start_noflag(skb, DEVLINK_ATTR_DPIPE_TABLE);
3331 if (nla_put_string(skb, DEVLINK_ATTR_DPIPE_TABLE_NAME, table->name) ||
3332 nla_put_u64_64bit(skb, DEVLINK_ATTR_DPIPE_TABLE_SIZE, table_size,
3334 goto nla_put_failure;
3335 if (nla_put_u8(skb, DEVLINK_ATTR_DPIPE_TABLE_COUNTERS_ENABLED,
3336 table->counters_enabled))
3337 goto nla_put_failure;
3339 if (table->resource_valid) {
3340 if (nla_put_u64_64bit(skb, DEVLINK_ATTR_DPIPE_TABLE_RESOURCE_ID,
3341 table->resource_id, DEVLINK_ATTR_PAD) ||
3342 nla_put_u64_64bit(skb, DEVLINK_ATTR_DPIPE_TABLE_RESOURCE_UNITS,
3343 table->resource_units, DEVLINK_ATTR_PAD))
3344 goto nla_put_failure;
3346 if (devlink_dpipe_matches_put(table, skb))
3347 goto nla_put_failure;
3349 if (devlink_dpipe_actions_put(table, skb))
3350 goto nla_put_failure;
3352 nla_nest_end(skb, table_attr);
3356 nla_nest_cancel(skb, table_attr);
3360 static int devlink_dpipe_send_and_alloc_skb(struct sk_buff **pskb,
3361 struct genl_info *info)
3366 err = genlmsg_reply(*pskb, info);
3370 *pskb = genlmsg_new(GENLMSG_DEFAULT_SIZE, GFP_KERNEL);
3376 static int devlink_dpipe_tables_fill(struct genl_info *info,
3377 enum devlink_command cmd, int flags,
3378 struct list_head *dpipe_tables,
3379 const char *table_name)
3381 struct devlink *devlink = info->user_ptr[0];
3382 struct devlink_dpipe_table *table;
3383 struct nlattr *tables_attr;
3384 struct sk_buff *skb = NULL;
3385 struct nlmsghdr *nlh;
3391 table = list_first_entry(dpipe_tables,
3392 struct devlink_dpipe_table, list);
3394 err = devlink_dpipe_send_and_alloc_skb(&skb, info);
3398 hdr = genlmsg_put(skb, info->snd_portid, info->snd_seq,
3399 &devlink_nl_family, NLM_F_MULTI, cmd);
3405 if (devlink_nl_put_handle(skb, devlink))
3406 goto nla_put_failure;
3407 tables_attr = nla_nest_start_noflag(skb, DEVLINK_ATTR_DPIPE_TABLES);
3409 goto nla_put_failure;
3413 list_for_each_entry_from(table, dpipe_tables, list) {
3415 err = devlink_dpipe_table_put(skb, table);
3423 if (!strcmp(table->name, table_name)) {
3424 err = devlink_dpipe_table_put(skb, table);
3432 nla_nest_end(skb, tables_attr);
3433 genlmsg_end(skb, hdr);
3438 nlh = nlmsg_put(skb, info->snd_portid, info->snd_seq,
3439 NLMSG_DONE, 0, flags | NLM_F_MULTI);
3441 err = devlink_dpipe_send_and_alloc_skb(&skb, info);
3447 return genlmsg_reply(skb, info);
3456 static int devlink_nl_cmd_dpipe_table_get(struct sk_buff *skb,
3457 struct genl_info *info)
3459 struct devlink *devlink = info->user_ptr[0];
3460 const char *table_name = NULL;
3462 if (info->attrs[DEVLINK_ATTR_DPIPE_TABLE_NAME])
3463 table_name = nla_data(info->attrs[DEVLINK_ATTR_DPIPE_TABLE_NAME]);
3465 return devlink_dpipe_tables_fill(info, DEVLINK_CMD_DPIPE_TABLE_GET, 0,
3466 &devlink->dpipe_table_list,
3470 static int devlink_dpipe_value_put(struct sk_buff *skb,
3471 struct devlink_dpipe_value *value)
3473 if (nla_put(skb, DEVLINK_ATTR_DPIPE_VALUE,
3474 value->value_size, value->value))
3477 if (nla_put(skb, DEVLINK_ATTR_DPIPE_VALUE_MASK,
3478 value->value_size, value->mask))
3480 if (value->mapping_valid)
3481 if (nla_put_u32(skb, DEVLINK_ATTR_DPIPE_VALUE_MAPPING,
3482 value->mapping_value))
3487 static int devlink_dpipe_action_value_put(struct sk_buff *skb,
3488 struct devlink_dpipe_value *value)
3492 if (devlink_dpipe_action_put(skb, value->action))
3494 if (devlink_dpipe_value_put(skb, value))
3499 static int devlink_dpipe_action_values_put(struct sk_buff *skb,
3500 struct devlink_dpipe_value *values,
3501 unsigned int values_count)
3503 struct nlattr *action_attr;
3507 for (i = 0; i < values_count; i++) {
3508 action_attr = nla_nest_start_noflag(skb,
3509 DEVLINK_ATTR_DPIPE_ACTION_VALUE);
3512 err = devlink_dpipe_action_value_put(skb, &values[i]);
3514 goto err_action_value_put;
3515 nla_nest_end(skb, action_attr);
3519 err_action_value_put:
3520 nla_nest_cancel(skb, action_attr);
3524 static int devlink_dpipe_match_value_put(struct sk_buff *skb,
3525 struct devlink_dpipe_value *value)
3529 if (devlink_dpipe_match_put(skb, value->match))
3531 if (devlink_dpipe_value_put(skb, value))
3536 static int devlink_dpipe_match_values_put(struct sk_buff *skb,
3537 struct devlink_dpipe_value *values,
3538 unsigned int values_count)
3540 struct nlattr *match_attr;
3544 for (i = 0; i < values_count; i++) {
3545 match_attr = nla_nest_start_noflag(skb,
3546 DEVLINK_ATTR_DPIPE_MATCH_VALUE);
3549 err = devlink_dpipe_match_value_put(skb, &values[i]);
3551 goto err_match_value_put;
3552 nla_nest_end(skb, match_attr);
3556 err_match_value_put:
3557 nla_nest_cancel(skb, match_attr);
3561 static int devlink_dpipe_entry_put(struct sk_buff *skb,
3562 struct devlink_dpipe_entry *entry)
3564 struct nlattr *entry_attr, *matches_attr, *actions_attr;
3567 entry_attr = nla_nest_start_noflag(skb, DEVLINK_ATTR_DPIPE_ENTRY);
3571 if (nla_put_u64_64bit(skb, DEVLINK_ATTR_DPIPE_ENTRY_INDEX, entry->index,
3573 goto nla_put_failure;
3574 if (entry->counter_valid)
3575 if (nla_put_u64_64bit(skb, DEVLINK_ATTR_DPIPE_ENTRY_COUNTER,
3576 entry->counter, DEVLINK_ATTR_PAD))
3577 goto nla_put_failure;
3579 matches_attr = nla_nest_start_noflag(skb,
3580 DEVLINK_ATTR_DPIPE_ENTRY_MATCH_VALUES);
3582 goto nla_put_failure;
3584 err = devlink_dpipe_match_values_put(skb, entry->match_values,
3585 entry->match_values_count);
3587 nla_nest_cancel(skb, matches_attr);
3588 goto err_match_values_put;
3590 nla_nest_end(skb, matches_attr);
3592 actions_attr = nla_nest_start_noflag(skb,
3593 DEVLINK_ATTR_DPIPE_ENTRY_ACTION_VALUES);
3595 goto nla_put_failure;
3597 err = devlink_dpipe_action_values_put(skb, entry->action_values,
3598 entry->action_values_count);
3600 nla_nest_cancel(skb, actions_attr);
3601 goto err_action_values_put;
3603 nla_nest_end(skb, actions_attr);
3605 nla_nest_end(skb, entry_attr);
3610 err_match_values_put:
3611 err_action_values_put:
3612 nla_nest_cancel(skb, entry_attr);
3616 static struct devlink_dpipe_table *
3617 devlink_dpipe_table_find(struct list_head *dpipe_tables,
3618 const char *table_name, struct devlink *devlink)
3620 struct devlink_dpipe_table *table;
3621 list_for_each_entry_rcu(table, dpipe_tables, list,
3622 lockdep_is_held(&devlink->lock)) {
3623 if (!strcmp(table->name, table_name))
3629 int devlink_dpipe_entry_ctx_prepare(struct devlink_dpipe_dump_ctx *dump_ctx)
3631 struct devlink *devlink;
3634 err = devlink_dpipe_send_and_alloc_skb(&dump_ctx->skb,
3639 dump_ctx->hdr = genlmsg_put(dump_ctx->skb,
3640 dump_ctx->info->snd_portid,
3641 dump_ctx->info->snd_seq,
3642 &devlink_nl_family, NLM_F_MULTI,
3645 goto nla_put_failure;
3647 devlink = dump_ctx->info->user_ptr[0];
3648 if (devlink_nl_put_handle(dump_ctx->skb, devlink))
3649 goto nla_put_failure;
3650 dump_ctx->nest = nla_nest_start_noflag(dump_ctx->skb,
3651 DEVLINK_ATTR_DPIPE_ENTRIES);
3652 if (!dump_ctx->nest)
3653 goto nla_put_failure;
3657 nlmsg_free(dump_ctx->skb);
3660 EXPORT_SYMBOL_GPL(devlink_dpipe_entry_ctx_prepare);
3662 int devlink_dpipe_entry_ctx_append(struct devlink_dpipe_dump_ctx *dump_ctx,
3663 struct devlink_dpipe_entry *entry)
3665 return devlink_dpipe_entry_put(dump_ctx->skb, entry);
3667 EXPORT_SYMBOL_GPL(devlink_dpipe_entry_ctx_append);
3669 int devlink_dpipe_entry_ctx_close(struct devlink_dpipe_dump_ctx *dump_ctx)
3671 nla_nest_end(dump_ctx->skb, dump_ctx->nest);
3672 genlmsg_end(dump_ctx->skb, dump_ctx->hdr);
3675 EXPORT_SYMBOL_GPL(devlink_dpipe_entry_ctx_close);
3677 void devlink_dpipe_entry_clear(struct devlink_dpipe_entry *entry)
3680 unsigned int value_count, value_index;
3681 struct devlink_dpipe_value *value;
3683 value = entry->action_values;
3684 value_count = entry->action_values_count;
3685 for (value_index = 0; value_index < value_count; value_index++) {
3686 kfree(value[value_index].value);
3687 kfree(value[value_index].mask);
3690 value = entry->match_values;
3691 value_count = entry->match_values_count;
3692 for (value_index = 0; value_index < value_count; value_index++) {
3693 kfree(value[value_index].value);
3694 kfree(value[value_index].mask);
3697 EXPORT_SYMBOL_GPL(devlink_dpipe_entry_clear);
3699 static int devlink_dpipe_entries_fill(struct genl_info *info,
3700 enum devlink_command cmd, int flags,
3701 struct devlink_dpipe_table *table)
3703 struct devlink_dpipe_dump_ctx dump_ctx;
3704 struct nlmsghdr *nlh;
3707 dump_ctx.skb = NULL;
3709 dump_ctx.info = info;
3711 err = table->table_ops->entries_dump(table->priv,
3712 table->counters_enabled,
3718 nlh = nlmsg_put(dump_ctx.skb, info->snd_portid, info->snd_seq,
3719 NLMSG_DONE, 0, flags | NLM_F_MULTI);
3721 err = devlink_dpipe_send_and_alloc_skb(&dump_ctx.skb, info);
3726 return genlmsg_reply(dump_ctx.skb, info);
3729 static int devlink_nl_cmd_dpipe_entries_get(struct sk_buff *skb,
3730 struct genl_info *info)
3732 struct devlink *devlink = info->user_ptr[0];
3733 struct devlink_dpipe_table *table;
3734 const char *table_name;
3736 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_DPIPE_TABLE_NAME))
3739 table_name = nla_data(info->attrs[DEVLINK_ATTR_DPIPE_TABLE_NAME]);
3740 table = devlink_dpipe_table_find(&devlink->dpipe_table_list,
3741 table_name, devlink);
3745 if (!table->table_ops->entries_dump)
3748 return devlink_dpipe_entries_fill(info, DEVLINK_CMD_DPIPE_ENTRIES_GET,
3752 static int devlink_dpipe_fields_put(struct sk_buff *skb,
3753 const struct devlink_dpipe_header *header)
3755 struct devlink_dpipe_field *field;
3756 struct nlattr *field_attr;
3759 for (i = 0; i < header->fields_count; i++) {
3760 field = &header->fields[i];
3761 field_attr = nla_nest_start_noflag(skb,
3762 DEVLINK_ATTR_DPIPE_FIELD);
3765 if (nla_put_string(skb, DEVLINK_ATTR_DPIPE_FIELD_NAME, field->name) ||
3766 nla_put_u32(skb, DEVLINK_ATTR_DPIPE_FIELD_ID, field->id) ||
3767 nla_put_u32(skb, DEVLINK_ATTR_DPIPE_FIELD_BITWIDTH, field->bitwidth) ||
3768 nla_put_u32(skb, DEVLINK_ATTR_DPIPE_FIELD_MAPPING_TYPE, field->mapping_type))
3769 goto nla_put_failure;
3770 nla_nest_end(skb, field_attr);
3775 nla_nest_cancel(skb, field_attr);
3779 static int devlink_dpipe_header_put(struct sk_buff *skb,
3780 struct devlink_dpipe_header *header)
3782 struct nlattr *fields_attr, *header_attr;
3785 header_attr = nla_nest_start_noflag(skb, DEVLINK_ATTR_DPIPE_HEADER);
3789 if (nla_put_string(skb, DEVLINK_ATTR_DPIPE_HEADER_NAME, header->name) ||
3790 nla_put_u32(skb, DEVLINK_ATTR_DPIPE_HEADER_ID, header->id) ||
3791 nla_put_u8(skb, DEVLINK_ATTR_DPIPE_HEADER_GLOBAL, header->global))
3792 goto nla_put_failure;
3794 fields_attr = nla_nest_start_noflag(skb,
3795 DEVLINK_ATTR_DPIPE_HEADER_FIELDS);
3797 goto nla_put_failure;
3799 err = devlink_dpipe_fields_put(skb, header);
3801 nla_nest_cancel(skb, fields_attr);
3802 goto nla_put_failure;
3804 nla_nest_end(skb, fields_attr);
3805 nla_nest_end(skb, header_attr);
3810 nla_nest_cancel(skb, header_attr);
3814 static int devlink_dpipe_headers_fill(struct genl_info *info,
3815 enum devlink_command cmd, int flags,
3816 struct devlink_dpipe_headers *
3819 struct devlink *devlink = info->user_ptr[0];
3820 struct nlattr *headers_attr;
3821 struct sk_buff *skb = NULL;
3822 struct nlmsghdr *nlh;
3829 err = devlink_dpipe_send_and_alloc_skb(&skb, info);
3833 hdr = genlmsg_put(skb, info->snd_portid, info->snd_seq,
3834 &devlink_nl_family, NLM_F_MULTI, cmd);
3840 if (devlink_nl_put_handle(skb, devlink))
3841 goto nla_put_failure;
3842 headers_attr = nla_nest_start_noflag(skb, DEVLINK_ATTR_DPIPE_HEADERS);
3844 goto nla_put_failure;
3847 for (; i < dpipe_headers->headers_count; i++) {
3848 err = devlink_dpipe_header_put(skb, dpipe_headers->headers[i]);
3856 nla_nest_end(skb, headers_attr);
3857 genlmsg_end(skb, hdr);
3858 if (i != dpipe_headers->headers_count)
3862 nlh = nlmsg_put(skb, info->snd_portid, info->snd_seq,
3863 NLMSG_DONE, 0, flags | NLM_F_MULTI);
3865 err = devlink_dpipe_send_and_alloc_skb(&skb, info);
3870 return genlmsg_reply(skb, info);
3879 static int devlink_nl_cmd_dpipe_headers_get(struct sk_buff *skb,
3880 struct genl_info *info)
3882 struct devlink *devlink = info->user_ptr[0];
3884 if (!devlink->dpipe_headers)
3886 return devlink_dpipe_headers_fill(info, DEVLINK_CMD_DPIPE_HEADERS_GET,
3887 0, devlink->dpipe_headers);
3890 static int devlink_dpipe_table_counters_set(struct devlink *devlink,
3891 const char *table_name,
3894 struct devlink_dpipe_table *table;
3896 table = devlink_dpipe_table_find(&devlink->dpipe_table_list,
3897 table_name, devlink);
3901 if (table->counter_control_extern)
3904 if (!(table->counters_enabled ^ enable))
3907 table->counters_enabled = enable;
3908 if (table->table_ops->counters_set_update)
3909 table->table_ops->counters_set_update(table->priv, enable);
3913 static int devlink_nl_cmd_dpipe_table_counters_set(struct sk_buff *skb,
3914 struct genl_info *info)
3916 struct devlink *devlink = info->user_ptr[0];
3917 const char *table_name;
3918 bool counters_enable;
3920 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_DPIPE_TABLE_NAME) ||
3921 GENL_REQ_ATTR_CHECK(info,
3922 DEVLINK_ATTR_DPIPE_TABLE_COUNTERS_ENABLED))
3925 table_name = nla_data(info->attrs[DEVLINK_ATTR_DPIPE_TABLE_NAME]);
3926 counters_enable = !!nla_get_u8(info->attrs[DEVLINK_ATTR_DPIPE_TABLE_COUNTERS_ENABLED]);
3928 return devlink_dpipe_table_counters_set(devlink, table_name,
3932 static struct devlink_resource *
3933 devlink_resource_find(struct devlink *devlink,
3934 struct devlink_resource *resource, u64 resource_id)
3936 struct list_head *resource_list;
3939 resource_list = &resource->resource_list;
3941 resource_list = &devlink->resource_list;
3943 list_for_each_entry(resource, resource_list, list) {
3944 struct devlink_resource *child_resource;
3946 if (resource->id == resource_id)
3949 child_resource = devlink_resource_find(devlink, resource,
3952 return child_resource;
3958 devlink_resource_validate_children(struct devlink_resource *resource)
3960 struct devlink_resource *child_resource;
3961 bool size_valid = true;
3964 if (list_empty(&resource->resource_list))
3967 list_for_each_entry(child_resource, &resource->resource_list, list)
3968 parts_size += child_resource->size_new;
3970 if (parts_size > resource->size_new)
3973 resource->size_valid = size_valid;
3977 devlink_resource_validate_size(struct devlink_resource *resource, u64 size,
3978 struct netlink_ext_ack *extack)
3983 if (size > resource->size_params.size_max) {
3984 NL_SET_ERR_MSG_MOD(extack, "Size larger than maximum");
3988 if (size < resource->size_params.size_min) {
3989 NL_SET_ERR_MSG_MOD(extack, "Size smaller than minimum");
3993 div64_u64_rem(size, resource->size_params.size_granularity, &reminder);
3995 NL_SET_ERR_MSG_MOD(extack, "Wrong granularity");
4002 static int devlink_nl_cmd_resource_set(struct sk_buff *skb,
4003 struct genl_info *info)
4005 struct devlink *devlink = info->user_ptr[0];
4006 struct devlink_resource *resource;
4011 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_RESOURCE_ID) ||
4012 GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_RESOURCE_SIZE))
4014 resource_id = nla_get_u64(info->attrs[DEVLINK_ATTR_RESOURCE_ID]);
4016 resource = devlink_resource_find(devlink, NULL, resource_id);
4020 size = nla_get_u64(info->attrs[DEVLINK_ATTR_RESOURCE_SIZE]);
4021 err = devlink_resource_validate_size(resource, size, info->extack);
4025 resource->size_new = size;
4026 devlink_resource_validate_children(resource);
4027 if (resource->parent)
4028 devlink_resource_validate_children(resource->parent);
4033 devlink_resource_size_params_put(struct devlink_resource *resource,
4034 struct sk_buff *skb)
4036 struct devlink_resource_size_params *size_params;
4038 size_params = &resource->size_params;
4039 if (nla_put_u64_64bit(skb, DEVLINK_ATTR_RESOURCE_SIZE_GRAN,
4040 size_params->size_granularity, DEVLINK_ATTR_PAD) ||
4041 nla_put_u64_64bit(skb, DEVLINK_ATTR_RESOURCE_SIZE_MAX,
4042 size_params->size_max, DEVLINK_ATTR_PAD) ||
4043 nla_put_u64_64bit(skb, DEVLINK_ATTR_RESOURCE_SIZE_MIN,
4044 size_params->size_min, DEVLINK_ATTR_PAD) ||
4045 nla_put_u8(skb, DEVLINK_ATTR_RESOURCE_UNIT, size_params->unit))
4050 static int devlink_resource_occ_put(struct devlink_resource *resource,
4051 struct sk_buff *skb)
4053 if (!resource->occ_get)
4055 return nla_put_u64_64bit(skb, DEVLINK_ATTR_RESOURCE_OCC,
4056 resource->occ_get(resource->occ_get_priv),
4060 static int devlink_resource_put(struct devlink *devlink, struct sk_buff *skb,
4061 struct devlink_resource *resource)
4063 struct devlink_resource *child_resource;
4064 struct nlattr *child_resource_attr;
4065 struct nlattr *resource_attr;
4067 resource_attr = nla_nest_start_noflag(skb, DEVLINK_ATTR_RESOURCE);
4071 if (nla_put_string(skb, DEVLINK_ATTR_RESOURCE_NAME, resource->name) ||
4072 nla_put_u64_64bit(skb, DEVLINK_ATTR_RESOURCE_SIZE, resource->size,
4073 DEVLINK_ATTR_PAD) ||
4074 nla_put_u64_64bit(skb, DEVLINK_ATTR_RESOURCE_ID, resource->id,
4076 goto nla_put_failure;
4077 if (resource->size != resource->size_new &&
4078 nla_put_u64_64bit(skb, DEVLINK_ATTR_RESOURCE_SIZE_NEW,
4079 resource->size_new, DEVLINK_ATTR_PAD))
4080 goto nla_put_failure;
4081 if (devlink_resource_occ_put(resource, skb))
4082 goto nla_put_failure;
4083 if (devlink_resource_size_params_put(resource, skb))
4084 goto nla_put_failure;
4085 if (list_empty(&resource->resource_list))
4088 if (nla_put_u8(skb, DEVLINK_ATTR_RESOURCE_SIZE_VALID,
4089 resource->size_valid))
4090 goto nla_put_failure;
4092 child_resource_attr = nla_nest_start_noflag(skb,
4093 DEVLINK_ATTR_RESOURCE_LIST);
4094 if (!child_resource_attr)
4095 goto nla_put_failure;
4097 list_for_each_entry(child_resource, &resource->resource_list, list) {
4098 if (devlink_resource_put(devlink, skb, child_resource))
4099 goto resource_put_failure;
4102 nla_nest_end(skb, child_resource_attr);
4104 nla_nest_end(skb, resource_attr);
4107 resource_put_failure:
4108 nla_nest_cancel(skb, child_resource_attr);
4110 nla_nest_cancel(skb, resource_attr);
4114 static int devlink_resource_fill(struct genl_info *info,
4115 enum devlink_command cmd, int flags)
4117 struct devlink *devlink = info->user_ptr[0];
4118 struct devlink_resource *resource;
4119 struct nlattr *resources_attr;
4120 struct sk_buff *skb = NULL;
4121 struct nlmsghdr *nlh;
4127 resource = list_first_entry(&devlink->resource_list,
4128 struct devlink_resource, list);
4130 err = devlink_dpipe_send_and_alloc_skb(&skb, info);
4134 hdr = genlmsg_put(skb, info->snd_portid, info->snd_seq,
4135 &devlink_nl_family, NLM_F_MULTI, cmd);
4141 if (devlink_nl_put_handle(skb, devlink))
4142 goto nla_put_failure;
4144 resources_attr = nla_nest_start_noflag(skb,
4145 DEVLINK_ATTR_RESOURCE_LIST);
4146 if (!resources_attr)
4147 goto nla_put_failure;
4151 list_for_each_entry_from(resource, &devlink->resource_list, list) {
4152 err = devlink_resource_put(devlink, skb, resource);
4155 goto err_resource_put;
4161 nla_nest_end(skb, resources_attr);
4162 genlmsg_end(skb, hdr);
4166 nlh = nlmsg_put(skb, info->snd_portid, info->snd_seq,
4167 NLMSG_DONE, 0, flags | NLM_F_MULTI);
4169 err = devlink_dpipe_send_and_alloc_skb(&skb, info);
4174 return genlmsg_reply(skb, info);
4183 static int devlink_nl_cmd_resource_dump(struct sk_buff *skb,
4184 struct genl_info *info)
4186 struct devlink *devlink = info->user_ptr[0];
4188 if (list_empty(&devlink->resource_list))
4191 return devlink_resource_fill(info, DEVLINK_CMD_RESOURCE_DUMP, 0);
4195 devlink_resources_validate(struct devlink *devlink,
4196 struct devlink_resource *resource,
4197 struct genl_info *info)
4199 struct list_head *resource_list;
4203 resource_list = &resource->resource_list;
4205 resource_list = &devlink->resource_list;
4207 list_for_each_entry(resource, resource_list, list) {
4208 if (!resource->size_valid)
4210 err = devlink_resources_validate(devlink, resource, info);
4217 static struct net *devlink_netns_get(struct sk_buff *skb,
4218 struct genl_info *info)
4220 struct nlattr *netns_pid_attr = info->attrs[DEVLINK_ATTR_NETNS_PID];
4221 struct nlattr *netns_fd_attr = info->attrs[DEVLINK_ATTR_NETNS_FD];
4222 struct nlattr *netns_id_attr = info->attrs[DEVLINK_ATTR_NETNS_ID];
4225 if (!!netns_pid_attr + !!netns_fd_attr + !!netns_id_attr > 1) {
4226 NL_SET_ERR_MSG_MOD(info->extack, "multiple netns identifying attributes specified");
4227 return ERR_PTR(-EINVAL);
4230 if (netns_pid_attr) {
4231 net = get_net_ns_by_pid(nla_get_u32(netns_pid_attr));
4232 } else if (netns_fd_attr) {
4233 net = get_net_ns_by_fd(nla_get_u32(netns_fd_attr));
4234 } else if (netns_id_attr) {
4235 net = get_net_ns_by_id(sock_net(skb->sk),
4236 nla_get_u32(netns_id_attr));
4238 net = ERR_PTR(-EINVAL);
4241 net = ERR_PTR(-EINVAL);
4244 NL_SET_ERR_MSG_MOD(info->extack, "Unknown network namespace");
4245 return ERR_PTR(-EINVAL);
4247 if (!netlink_ns_capable(skb, net->user_ns, CAP_NET_ADMIN)) {
4249 return ERR_PTR(-EPERM);
4254 static void devlink_param_notify(struct devlink *devlink,
4255 unsigned int port_index,
4256 struct devlink_param_item *param_item,
4257 enum devlink_command cmd);
4259 static void devlink_ns_change_notify(struct devlink *devlink,
4260 struct net *dest_net, struct net *curr_net,
4263 struct devlink_param_item *param_item;
4264 enum devlink_command cmd;
4266 /* Userspace needs to be notified about devlink objects
4267 * removed from original and entering new network namespace.
4268 * The rest of the devlink objects are re-created during
4269 * reload process so the notifications are generated separatelly.
4272 if (!dest_net || net_eq(dest_net, curr_net))
4276 devlink_notify(devlink, DEVLINK_CMD_NEW);
4278 cmd = new ? DEVLINK_CMD_PARAM_NEW : DEVLINK_CMD_PARAM_DEL;
4279 list_for_each_entry(param_item, &devlink->param_list, list)
4280 devlink_param_notify(devlink, 0, param_item, cmd);
4283 devlink_notify(devlink, DEVLINK_CMD_DEL);
4286 static void devlink_reload_failed_set(struct devlink *devlink,
4289 if (devlink->reload_failed == reload_failed)
4291 devlink->reload_failed = reload_failed;
4292 devlink_notify(devlink, DEVLINK_CMD_NEW);
4295 bool devlink_is_reload_failed(const struct devlink *devlink)
4297 return devlink->reload_failed;
4299 EXPORT_SYMBOL_GPL(devlink_is_reload_failed);
4302 __devlink_reload_stats_update(struct devlink *devlink, u32 *reload_stats,
4303 enum devlink_reload_limit limit, u32 actions_performed)
4305 unsigned long actions = actions_performed;
4309 for_each_set_bit(action, &actions, __DEVLINK_RELOAD_ACTION_MAX) {
4310 stat_idx = limit * __DEVLINK_RELOAD_ACTION_MAX + action;
4311 reload_stats[stat_idx]++;
4313 devlink_notify(devlink, DEVLINK_CMD_NEW);
4317 devlink_reload_stats_update(struct devlink *devlink, enum devlink_reload_limit limit,
4318 u32 actions_performed)
4320 __devlink_reload_stats_update(devlink, devlink->stats.reload_stats, limit,
4325 * devlink_remote_reload_actions_performed - Update devlink on reload actions
4326 * performed which are not a direct result of devlink reload call.
4328 * This should be called by a driver after performing reload actions in case it was not
4329 * a result of devlink reload call. For example fw_activate was performed as a result
4330 * of devlink reload triggered fw_activate on another host.
4331 * The motivation for this function is to keep data on reload actions performed on this
4332 * function whether it was done due to direct devlink reload call or not.
4335 * @limit: reload limit
4336 * @actions_performed: bitmask of actions performed
4338 void devlink_remote_reload_actions_performed(struct devlink *devlink,
4339 enum devlink_reload_limit limit,
4340 u32 actions_performed)
4342 if (WARN_ON(!actions_performed ||
4343 actions_performed & BIT(DEVLINK_RELOAD_ACTION_UNSPEC) ||
4344 actions_performed >= BIT(__DEVLINK_RELOAD_ACTION_MAX) ||
4345 limit > DEVLINK_RELOAD_LIMIT_MAX))
4348 __devlink_reload_stats_update(devlink, devlink->stats.remote_reload_stats, limit,
4351 EXPORT_SYMBOL_GPL(devlink_remote_reload_actions_performed);
4353 int devlink_reload(struct devlink *devlink, struct net *dest_net,
4354 enum devlink_reload_action action,
4355 enum devlink_reload_limit limit,
4356 u32 *actions_performed, struct netlink_ext_ack *extack)
4358 u32 remote_reload_stats[DEVLINK_RELOAD_STATS_ARRAY_SIZE];
4359 struct net *curr_net;
4362 memcpy(remote_reload_stats, devlink->stats.remote_reload_stats,
4363 sizeof(remote_reload_stats));
4365 curr_net = devlink_net(devlink);
4366 devlink_ns_change_notify(devlink, dest_net, curr_net, false);
4367 err = devlink->ops->reload_down(devlink, !!dest_net, action, limit, extack);
4371 if (dest_net && !net_eq(dest_net, curr_net)) {
4372 move_netdevice_notifier_net(curr_net, dest_net,
4373 &devlink->netdevice_nb);
4374 write_pnet(&devlink->_net, dest_net);
4377 err = devlink->ops->reload_up(devlink, action, limit, actions_performed, extack);
4378 devlink_reload_failed_set(devlink, !!err);
4382 devlink_ns_change_notify(devlink, dest_net, curr_net, true);
4383 WARN_ON(!(*actions_performed & BIT(action)));
4384 /* Catch driver on updating the remote action within devlink reload */
4385 WARN_ON(memcmp(remote_reload_stats, devlink->stats.remote_reload_stats,
4386 sizeof(remote_reload_stats)));
4387 devlink_reload_stats_update(devlink, limit, *actions_performed);
4392 devlink_nl_reload_actions_performed_snd(struct devlink *devlink, u32 actions_performed,
4393 enum devlink_command cmd, struct genl_info *info)
4395 struct sk_buff *msg;
4398 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
4402 hdr = genlmsg_put(msg, info->snd_portid, info->snd_seq, &devlink_nl_family, 0, cmd);
4406 if (devlink_nl_put_handle(msg, devlink))
4407 goto nla_put_failure;
4409 if (nla_put_bitfield32(msg, DEVLINK_ATTR_RELOAD_ACTIONS_PERFORMED, actions_performed,
4411 goto nla_put_failure;
4412 genlmsg_end(msg, hdr);
4414 return genlmsg_reply(msg, info);
4417 genlmsg_cancel(msg, hdr);
4423 static int devlink_nl_cmd_reload(struct sk_buff *skb, struct genl_info *info)
4425 struct devlink *devlink = info->user_ptr[0];
4426 enum devlink_reload_action action;
4427 enum devlink_reload_limit limit;
4428 struct net *dest_net = NULL;
4429 u32 actions_performed;
4432 if (!(devlink->features & DEVLINK_F_RELOAD))
4435 err = devlink_resources_validate(devlink, NULL, info);
4437 NL_SET_ERR_MSG_MOD(info->extack, "resources size validation failed");
4441 if (info->attrs[DEVLINK_ATTR_RELOAD_ACTION])
4442 action = nla_get_u8(info->attrs[DEVLINK_ATTR_RELOAD_ACTION]);
4444 action = DEVLINK_RELOAD_ACTION_DRIVER_REINIT;
4446 if (!devlink_reload_action_is_supported(devlink, action)) {
4447 NL_SET_ERR_MSG_MOD(info->extack,
4448 "Requested reload action is not supported by the driver");
4452 limit = DEVLINK_RELOAD_LIMIT_UNSPEC;
4453 if (info->attrs[DEVLINK_ATTR_RELOAD_LIMITS]) {
4454 struct nla_bitfield32 limits;
4455 u32 limits_selected;
4457 limits = nla_get_bitfield32(info->attrs[DEVLINK_ATTR_RELOAD_LIMITS]);
4458 limits_selected = limits.value & limits.selector;
4459 if (!limits_selected) {
4460 NL_SET_ERR_MSG_MOD(info->extack, "Invalid limit selected");
4463 for (limit = 0 ; limit <= DEVLINK_RELOAD_LIMIT_MAX ; limit++)
4464 if (limits_selected & BIT(limit))
4466 /* UAPI enables multiselection, but currently it is not used */
4467 if (limits_selected != BIT(limit)) {
4468 NL_SET_ERR_MSG_MOD(info->extack,
4469 "Multiselection of limit is not supported");
4472 if (!devlink_reload_limit_is_supported(devlink, limit)) {
4473 NL_SET_ERR_MSG_MOD(info->extack,
4474 "Requested limit is not supported by the driver");
4477 if (devlink_reload_combination_is_invalid(action, limit)) {
4478 NL_SET_ERR_MSG_MOD(info->extack,
4479 "Requested limit is invalid for this action");
4483 if (info->attrs[DEVLINK_ATTR_NETNS_PID] ||
4484 info->attrs[DEVLINK_ATTR_NETNS_FD] ||
4485 info->attrs[DEVLINK_ATTR_NETNS_ID]) {
4486 dest_net = devlink_netns_get(skb, info);
4487 if (IS_ERR(dest_net))
4488 return PTR_ERR(dest_net);
4491 err = devlink_reload(devlink, dest_net, action, limit, &actions_performed, info->extack);
4498 /* For backward compatibility generate reply only if attributes used by user */
4499 if (!info->attrs[DEVLINK_ATTR_RELOAD_ACTION] && !info->attrs[DEVLINK_ATTR_RELOAD_LIMITS])
4502 return devlink_nl_reload_actions_performed_snd(devlink, actions_performed,
4503 DEVLINK_CMD_RELOAD, info);
4506 static int devlink_nl_flash_update_fill(struct sk_buff *msg,
4507 struct devlink *devlink,
4508 enum devlink_command cmd,
4509 struct devlink_flash_notify *params)
4513 hdr = genlmsg_put(msg, 0, 0, &devlink_nl_family, 0, cmd);
4517 if (devlink_nl_put_handle(msg, devlink))
4518 goto nla_put_failure;
4520 if (cmd != DEVLINK_CMD_FLASH_UPDATE_STATUS)
4523 if (params->status_msg &&
4524 nla_put_string(msg, DEVLINK_ATTR_FLASH_UPDATE_STATUS_MSG,
4525 params->status_msg))
4526 goto nla_put_failure;
4527 if (params->component &&
4528 nla_put_string(msg, DEVLINK_ATTR_FLASH_UPDATE_COMPONENT,
4530 goto nla_put_failure;
4531 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_FLASH_UPDATE_STATUS_DONE,
4532 params->done, DEVLINK_ATTR_PAD))
4533 goto nla_put_failure;
4534 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_FLASH_UPDATE_STATUS_TOTAL,
4535 params->total, DEVLINK_ATTR_PAD))
4536 goto nla_put_failure;
4537 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_FLASH_UPDATE_STATUS_TIMEOUT,
4538 params->timeout, DEVLINK_ATTR_PAD))
4539 goto nla_put_failure;
4542 genlmsg_end(msg, hdr);
4546 genlmsg_cancel(msg, hdr);
4550 static void __devlink_flash_update_notify(struct devlink *devlink,
4551 enum devlink_command cmd,
4552 struct devlink_flash_notify *params)
4554 struct sk_buff *msg;
4557 WARN_ON(cmd != DEVLINK_CMD_FLASH_UPDATE &&
4558 cmd != DEVLINK_CMD_FLASH_UPDATE_END &&
4559 cmd != DEVLINK_CMD_FLASH_UPDATE_STATUS);
4561 if (!xa_get_mark(&devlinks, devlink->index, DEVLINK_REGISTERED))
4564 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
4568 err = devlink_nl_flash_update_fill(msg, devlink, cmd, params);
4572 genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink),
4573 msg, 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
4580 static void devlink_flash_update_begin_notify(struct devlink *devlink)
4582 struct devlink_flash_notify params = {};
4584 __devlink_flash_update_notify(devlink,
4585 DEVLINK_CMD_FLASH_UPDATE,
4589 static void devlink_flash_update_end_notify(struct devlink *devlink)
4591 struct devlink_flash_notify params = {};
4593 __devlink_flash_update_notify(devlink,
4594 DEVLINK_CMD_FLASH_UPDATE_END,
4598 void devlink_flash_update_status_notify(struct devlink *devlink,
4599 const char *status_msg,
4600 const char *component,
4602 unsigned long total)
4604 struct devlink_flash_notify params = {
4605 .status_msg = status_msg,
4606 .component = component,
4611 __devlink_flash_update_notify(devlink,
4612 DEVLINK_CMD_FLASH_UPDATE_STATUS,
4615 EXPORT_SYMBOL_GPL(devlink_flash_update_status_notify);
4617 void devlink_flash_update_timeout_notify(struct devlink *devlink,
4618 const char *status_msg,
4619 const char *component,
4620 unsigned long timeout)
4622 struct devlink_flash_notify params = {
4623 .status_msg = status_msg,
4624 .component = component,
4628 __devlink_flash_update_notify(devlink,
4629 DEVLINK_CMD_FLASH_UPDATE_STATUS,
4632 EXPORT_SYMBOL_GPL(devlink_flash_update_timeout_notify);
4634 struct devlink_info_req {
4635 struct sk_buff *msg;
4636 void (*version_cb)(const char *version_name,
4637 enum devlink_info_version_type version_type,
4638 void *version_cb_priv);
4639 void *version_cb_priv;
4642 struct devlink_flash_component_lookup_ctx {
4643 const char *lookup_name;
4644 bool lookup_name_found;
4648 devlink_flash_component_lookup_cb(const char *version_name,
4649 enum devlink_info_version_type version_type,
4650 void *version_cb_priv)
4652 struct devlink_flash_component_lookup_ctx *lookup_ctx = version_cb_priv;
4654 if (version_type != DEVLINK_INFO_VERSION_TYPE_COMPONENT ||
4655 lookup_ctx->lookup_name_found)
4658 lookup_ctx->lookup_name_found =
4659 !strcmp(lookup_ctx->lookup_name, version_name);
4662 static int devlink_flash_component_get(struct devlink *devlink,
4663 struct nlattr *nla_component,
4664 const char **p_component,
4665 struct netlink_ext_ack *extack)
4667 struct devlink_flash_component_lookup_ctx lookup_ctx = {};
4668 struct devlink_info_req req = {};
4669 const char *component;
4675 component = nla_data(nla_component);
4677 if (!devlink->ops->info_get) {
4678 NL_SET_ERR_MSG_ATTR(extack, nla_component,
4679 "component update is not supported by this device");
4683 lookup_ctx.lookup_name = component;
4684 req.version_cb = devlink_flash_component_lookup_cb;
4685 req.version_cb_priv = &lookup_ctx;
4687 ret = devlink->ops->info_get(devlink, &req, NULL);
4691 if (!lookup_ctx.lookup_name_found) {
4692 NL_SET_ERR_MSG_ATTR(extack, nla_component,
4693 "selected component is not supported by this device");
4696 *p_component = component;
4700 static int devlink_nl_cmd_flash_update(struct sk_buff *skb,
4701 struct genl_info *info)
4703 struct nlattr *nla_overwrite_mask, *nla_file_name;
4704 struct devlink_flash_update_params params = {};
4705 struct devlink *devlink = info->user_ptr[0];
4706 const char *file_name;
4707 u32 supported_params;
4710 if (!devlink->ops->flash_update)
4713 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_FLASH_UPDATE_FILE_NAME))
4716 ret = devlink_flash_component_get(devlink,
4717 info->attrs[DEVLINK_ATTR_FLASH_UPDATE_COMPONENT],
4718 ¶ms.component, info->extack);
4722 supported_params = devlink->ops->supported_flash_update_params;
4724 nla_overwrite_mask = info->attrs[DEVLINK_ATTR_FLASH_UPDATE_OVERWRITE_MASK];
4725 if (nla_overwrite_mask) {
4726 struct nla_bitfield32 sections;
4728 if (!(supported_params & DEVLINK_SUPPORT_FLASH_UPDATE_OVERWRITE_MASK)) {
4729 NL_SET_ERR_MSG_ATTR(info->extack, nla_overwrite_mask,
4730 "overwrite settings are not supported by this device");
4733 sections = nla_get_bitfield32(nla_overwrite_mask);
4734 params.overwrite_mask = sections.value & sections.selector;
4737 nla_file_name = info->attrs[DEVLINK_ATTR_FLASH_UPDATE_FILE_NAME];
4738 file_name = nla_data(nla_file_name);
4739 ret = request_firmware(¶ms.fw, file_name, devlink->dev);
4741 NL_SET_ERR_MSG_ATTR(info->extack, nla_file_name, "failed to locate the requested firmware file");
4745 devlink_flash_update_begin_notify(devlink);
4746 ret = devlink->ops->flash_update(devlink, ¶ms, info->extack);
4747 devlink_flash_update_end_notify(devlink);
4749 release_firmware(params.fw);
4755 devlink_nl_selftests_fill(struct sk_buff *msg, struct devlink *devlink,
4756 u32 portid, u32 seq, int flags,
4757 struct netlink_ext_ack *extack)
4759 struct nlattr *selftests;
4764 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags,
4765 DEVLINK_CMD_SELFTESTS_GET);
4770 if (devlink_nl_put_handle(msg, devlink))
4771 goto err_cancel_msg;
4773 selftests = nla_nest_start(msg, DEVLINK_ATTR_SELFTESTS);
4775 goto err_cancel_msg;
4777 for (i = DEVLINK_ATTR_SELFTEST_ID_UNSPEC + 1;
4778 i <= DEVLINK_ATTR_SELFTEST_ID_MAX; i++) {
4779 if (devlink->ops->selftest_check(devlink, i, extack)) {
4780 err = nla_put_flag(msg, i);
4782 goto err_cancel_msg;
4786 nla_nest_end(msg, selftests);
4787 genlmsg_end(msg, hdr);
4791 genlmsg_cancel(msg, hdr);
4795 static int devlink_nl_cmd_selftests_get_doit(struct sk_buff *skb,
4796 struct genl_info *info)
4798 struct devlink *devlink = info->user_ptr[0];
4799 struct sk_buff *msg;
4802 if (!devlink->ops->selftest_check)
4805 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
4809 err = devlink_nl_selftests_fill(msg, devlink, info->snd_portid,
4810 info->snd_seq, 0, info->extack);
4816 return genlmsg_reply(msg, info);
4820 devlink_nl_cmd_selftests_get_dump_one(struct sk_buff *msg,
4821 struct devlink *devlink,
4822 struct netlink_callback *cb)
4824 if (!devlink->ops->selftest_check)
4827 return devlink_nl_selftests_fill(msg, devlink,
4828 NETLINK_CB(cb->skb).portid,
4829 cb->nlh->nlmsg_seq, NLM_F_MULTI,
4833 const struct devlink_gen_cmd devl_gen_selftests = {
4834 .dump_one = devlink_nl_cmd_selftests_get_dump_one,
4837 static int devlink_selftest_result_put(struct sk_buff *skb, unsigned int id,
4838 enum devlink_selftest_status test_status)
4840 struct nlattr *result_attr;
4842 result_attr = nla_nest_start(skb, DEVLINK_ATTR_SELFTEST_RESULT);
4846 if (nla_put_u32(skb, DEVLINK_ATTR_SELFTEST_RESULT_ID, id) ||
4847 nla_put_u8(skb, DEVLINK_ATTR_SELFTEST_RESULT_STATUS,
4849 goto nla_put_failure;
4851 nla_nest_end(skb, result_attr);
4855 nla_nest_cancel(skb, result_attr);
4859 static int devlink_nl_cmd_selftests_run(struct sk_buff *skb,
4860 struct genl_info *info)
4862 struct nlattr *tb[DEVLINK_ATTR_SELFTEST_ID_MAX + 1];
4863 struct devlink *devlink = info->user_ptr[0];
4864 struct nlattr *attrs, *selftests;
4865 struct sk_buff *msg;
4870 if (!devlink->ops->selftest_run || !devlink->ops->selftest_check)
4873 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_SELFTESTS))
4876 attrs = info->attrs[DEVLINK_ATTR_SELFTESTS];
4878 err = nla_parse_nested(tb, DEVLINK_ATTR_SELFTEST_ID_MAX, attrs,
4879 devlink_selftest_nl_policy, info->extack);
4883 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
4888 hdr = genlmsg_put(msg, info->snd_portid, info->snd_seq,
4889 &devlink_nl_family, 0, DEVLINK_CMD_SELFTESTS_RUN);
4893 if (devlink_nl_put_handle(msg, devlink))
4894 goto genlmsg_cancel;
4896 selftests = nla_nest_start(msg, DEVLINK_ATTR_SELFTESTS);
4898 goto genlmsg_cancel;
4900 for (i = DEVLINK_ATTR_SELFTEST_ID_UNSPEC + 1;
4901 i <= DEVLINK_ATTR_SELFTEST_ID_MAX; i++) {
4902 enum devlink_selftest_status test_status;
4904 if (nla_get_flag(tb[i])) {
4905 if (!devlink->ops->selftest_check(devlink, i,
4907 if (devlink_selftest_result_put(msg, i,
4908 DEVLINK_SELFTEST_STATUS_SKIP))
4909 goto selftests_nest_cancel;
4913 test_status = devlink->ops->selftest_run(devlink, i,
4915 if (devlink_selftest_result_put(msg, i, test_status))
4916 goto selftests_nest_cancel;
4920 nla_nest_end(msg, selftests);
4921 genlmsg_end(msg, hdr);
4922 return genlmsg_reply(msg, info);
4924 selftests_nest_cancel:
4925 nla_nest_cancel(msg, selftests);
4927 genlmsg_cancel(msg, hdr);
4933 static const struct devlink_param devlink_param_generic[] = {
4935 .id = DEVLINK_PARAM_GENERIC_ID_INT_ERR_RESET,
4936 .name = DEVLINK_PARAM_GENERIC_INT_ERR_RESET_NAME,
4937 .type = DEVLINK_PARAM_GENERIC_INT_ERR_RESET_TYPE,
4940 .id = DEVLINK_PARAM_GENERIC_ID_MAX_MACS,
4941 .name = DEVLINK_PARAM_GENERIC_MAX_MACS_NAME,
4942 .type = DEVLINK_PARAM_GENERIC_MAX_MACS_TYPE,
4945 .id = DEVLINK_PARAM_GENERIC_ID_ENABLE_SRIOV,
4946 .name = DEVLINK_PARAM_GENERIC_ENABLE_SRIOV_NAME,
4947 .type = DEVLINK_PARAM_GENERIC_ENABLE_SRIOV_TYPE,
4950 .id = DEVLINK_PARAM_GENERIC_ID_REGION_SNAPSHOT,
4951 .name = DEVLINK_PARAM_GENERIC_REGION_SNAPSHOT_NAME,
4952 .type = DEVLINK_PARAM_GENERIC_REGION_SNAPSHOT_TYPE,
4955 .id = DEVLINK_PARAM_GENERIC_ID_IGNORE_ARI,
4956 .name = DEVLINK_PARAM_GENERIC_IGNORE_ARI_NAME,
4957 .type = DEVLINK_PARAM_GENERIC_IGNORE_ARI_TYPE,
4960 .id = DEVLINK_PARAM_GENERIC_ID_MSIX_VEC_PER_PF_MAX,
4961 .name = DEVLINK_PARAM_GENERIC_MSIX_VEC_PER_PF_MAX_NAME,
4962 .type = DEVLINK_PARAM_GENERIC_MSIX_VEC_PER_PF_MAX_TYPE,
4965 .id = DEVLINK_PARAM_GENERIC_ID_MSIX_VEC_PER_PF_MIN,
4966 .name = DEVLINK_PARAM_GENERIC_MSIX_VEC_PER_PF_MIN_NAME,
4967 .type = DEVLINK_PARAM_GENERIC_MSIX_VEC_PER_PF_MIN_TYPE,
4970 .id = DEVLINK_PARAM_GENERIC_ID_FW_LOAD_POLICY,
4971 .name = DEVLINK_PARAM_GENERIC_FW_LOAD_POLICY_NAME,
4972 .type = DEVLINK_PARAM_GENERIC_FW_LOAD_POLICY_TYPE,
4975 .id = DEVLINK_PARAM_GENERIC_ID_RESET_DEV_ON_DRV_PROBE,
4976 .name = DEVLINK_PARAM_GENERIC_RESET_DEV_ON_DRV_PROBE_NAME,
4977 .type = DEVLINK_PARAM_GENERIC_RESET_DEV_ON_DRV_PROBE_TYPE,
4980 .id = DEVLINK_PARAM_GENERIC_ID_ENABLE_ROCE,
4981 .name = DEVLINK_PARAM_GENERIC_ENABLE_ROCE_NAME,
4982 .type = DEVLINK_PARAM_GENERIC_ENABLE_ROCE_TYPE,
4985 .id = DEVLINK_PARAM_GENERIC_ID_ENABLE_REMOTE_DEV_RESET,
4986 .name = DEVLINK_PARAM_GENERIC_ENABLE_REMOTE_DEV_RESET_NAME,
4987 .type = DEVLINK_PARAM_GENERIC_ENABLE_REMOTE_DEV_RESET_TYPE,
4990 .id = DEVLINK_PARAM_GENERIC_ID_ENABLE_ETH,
4991 .name = DEVLINK_PARAM_GENERIC_ENABLE_ETH_NAME,
4992 .type = DEVLINK_PARAM_GENERIC_ENABLE_ETH_TYPE,
4995 .id = DEVLINK_PARAM_GENERIC_ID_ENABLE_RDMA,
4996 .name = DEVLINK_PARAM_GENERIC_ENABLE_RDMA_NAME,
4997 .type = DEVLINK_PARAM_GENERIC_ENABLE_RDMA_TYPE,
5000 .id = DEVLINK_PARAM_GENERIC_ID_ENABLE_VNET,
5001 .name = DEVLINK_PARAM_GENERIC_ENABLE_VNET_NAME,
5002 .type = DEVLINK_PARAM_GENERIC_ENABLE_VNET_TYPE,
5005 .id = DEVLINK_PARAM_GENERIC_ID_ENABLE_IWARP,
5006 .name = DEVLINK_PARAM_GENERIC_ENABLE_IWARP_NAME,
5007 .type = DEVLINK_PARAM_GENERIC_ENABLE_IWARP_TYPE,
5010 .id = DEVLINK_PARAM_GENERIC_ID_IO_EQ_SIZE,
5011 .name = DEVLINK_PARAM_GENERIC_IO_EQ_SIZE_NAME,
5012 .type = DEVLINK_PARAM_GENERIC_IO_EQ_SIZE_TYPE,
5015 .id = DEVLINK_PARAM_GENERIC_ID_EVENT_EQ_SIZE,
5016 .name = DEVLINK_PARAM_GENERIC_EVENT_EQ_SIZE_NAME,
5017 .type = DEVLINK_PARAM_GENERIC_EVENT_EQ_SIZE_TYPE,
5021 static int devlink_param_generic_verify(const struct devlink_param *param)
5023 /* verify it match generic parameter by id and name */
5024 if (param->id > DEVLINK_PARAM_GENERIC_ID_MAX)
5026 if (strcmp(param->name, devlink_param_generic[param->id].name))
5029 WARN_ON(param->type != devlink_param_generic[param->id].type);
5034 static int devlink_param_driver_verify(const struct devlink_param *param)
5038 if (param->id <= DEVLINK_PARAM_GENERIC_ID_MAX)
5040 /* verify no such name in generic params */
5041 for (i = 0; i <= DEVLINK_PARAM_GENERIC_ID_MAX; i++)
5042 if (!strcmp(param->name, devlink_param_generic[i].name))
5048 static struct devlink_param_item *
5049 devlink_param_find_by_name(struct list_head *param_list,
5050 const char *param_name)
5052 struct devlink_param_item *param_item;
5054 list_for_each_entry(param_item, param_list, list)
5055 if (!strcmp(param_item->param->name, param_name))
5060 static struct devlink_param_item *
5061 devlink_param_find_by_id(struct list_head *param_list, u32 param_id)
5063 struct devlink_param_item *param_item;
5065 list_for_each_entry(param_item, param_list, list)
5066 if (param_item->param->id == param_id)
5072 devlink_param_cmode_is_supported(const struct devlink_param *param,
5073 enum devlink_param_cmode cmode)
5075 return test_bit(cmode, ¶m->supported_cmodes);
5078 static int devlink_param_get(struct devlink *devlink,
5079 const struct devlink_param *param,
5080 struct devlink_param_gset_ctx *ctx)
5082 if (!param->get || devlink->reload_failed)
5084 return param->get(devlink, param->id, ctx);
5087 static int devlink_param_set(struct devlink *devlink,
5088 const struct devlink_param *param,
5089 struct devlink_param_gset_ctx *ctx)
5091 if (!param->set || devlink->reload_failed)
5093 return param->set(devlink, param->id, ctx);
5097 devlink_param_type_to_nla_type(enum devlink_param_type param_type)
5099 switch (param_type) {
5100 case DEVLINK_PARAM_TYPE_U8:
5102 case DEVLINK_PARAM_TYPE_U16:
5104 case DEVLINK_PARAM_TYPE_U32:
5106 case DEVLINK_PARAM_TYPE_STRING:
5108 case DEVLINK_PARAM_TYPE_BOOL:
5116 devlink_nl_param_value_fill_one(struct sk_buff *msg,
5117 enum devlink_param_type type,
5118 enum devlink_param_cmode cmode,
5119 union devlink_param_value val)
5121 struct nlattr *param_value_attr;
5123 param_value_attr = nla_nest_start_noflag(msg,
5124 DEVLINK_ATTR_PARAM_VALUE);
5125 if (!param_value_attr)
5126 goto nla_put_failure;
5128 if (nla_put_u8(msg, DEVLINK_ATTR_PARAM_VALUE_CMODE, cmode))
5129 goto value_nest_cancel;
5132 case DEVLINK_PARAM_TYPE_U8:
5133 if (nla_put_u8(msg, DEVLINK_ATTR_PARAM_VALUE_DATA, val.vu8))
5134 goto value_nest_cancel;
5136 case DEVLINK_PARAM_TYPE_U16:
5137 if (nla_put_u16(msg, DEVLINK_ATTR_PARAM_VALUE_DATA, val.vu16))
5138 goto value_nest_cancel;
5140 case DEVLINK_PARAM_TYPE_U32:
5141 if (nla_put_u32(msg, DEVLINK_ATTR_PARAM_VALUE_DATA, val.vu32))
5142 goto value_nest_cancel;
5144 case DEVLINK_PARAM_TYPE_STRING:
5145 if (nla_put_string(msg, DEVLINK_ATTR_PARAM_VALUE_DATA,
5147 goto value_nest_cancel;
5149 case DEVLINK_PARAM_TYPE_BOOL:
5151 nla_put_flag(msg, DEVLINK_ATTR_PARAM_VALUE_DATA))
5152 goto value_nest_cancel;
5156 nla_nest_end(msg, param_value_attr);
5160 nla_nest_cancel(msg, param_value_attr);
5165 static int devlink_nl_param_fill(struct sk_buff *msg, struct devlink *devlink,
5166 unsigned int port_index,
5167 struct devlink_param_item *param_item,
5168 enum devlink_command cmd,
5169 u32 portid, u32 seq, int flags)
5171 union devlink_param_value param_value[DEVLINK_PARAM_CMODE_MAX + 1];
5172 bool param_value_set[DEVLINK_PARAM_CMODE_MAX + 1] = {};
5173 const struct devlink_param *param = param_item->param;
5174 struct devlink_param_gset_ctx ctx;
5175 struct nlattr *param_values_list;
5176 struct nlattr *param_attr;
5182 /* Get value from driver part to driverinit configuration mode */
5183 for (i = 0; i <= DEVLINK_PARAM_CMODE_MAX; i++) {
5184 if (!devlink_param_cmode_is_supported(param, i))
5186 if (i == DEVLINK_PARAM_CMODE_DRIVERINIT) {
5187 if (!param_item->driverinit_value_valid)
5189 param_value[i] = param_item->driverinit_value;
5192 err = devlink_param_get(devlink, param, &ctx);
5195 param_value[i] = ctx.val;
5197 param_value_set[i] = true;
5200 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
5204 if (devlink_nl_put_handle(msg, devlink))
5205 goto genlmsg_cancel;
5207 if (cmd == DEVLINK_CMD_PORT_PARAM_GET ||
5208 cmd == DEVLINK_CMD_PORT_PARAM_NEW ||
5209 cmd == DEVLINK_CMD_PORT_PARAM_DEL)
5210 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_INDEX, port_index))
5211 goto genlmsg_cancel;
5213 param_attr = nla_nest_start_noflag(msg, DEVLINK_ATTR_PARAM);
5215 goto genlmsg_cancel;
5216 if (nla_put_string(msg, DEVLINK_ATTR_PARAM_NAME, param->name))
5217 goto param_nest_cancel;
5218 if (param->generic && nla_put_flag(msg, DEVLINK_ATTR_PARAM_GENERIC))
5219 goto param_nest_cancel;
5221 nla_type = devlink_param_type_to_nla_type(param->type);
5223 goto param_nest_cancel;
5224 if (nla_put_u8(msg, DEVLINK_ATTR_PARAM_TYPE, nla_type))
5225 goto param_nest_cancel;
5227 param_values_list = nla_nest_start_noflag(msg,
5228 DEVLINK_ATTR_PARAM_VALUES_LIST);
5229 if (!param_values_list)
5230 goto param_nest_cancel;
5232 for (i = 0; i <= DEVLINK_PARAM_CMODE_MAX; i++) {
5233 if (!param_value_set[i])
5235 err = devlink_nl_param_value_fill_one(msg, param->type,
5238 goto values_list_nest_cancel;
5241 nla_nest_end(msg, param_values_list);
5242 nla_nest_end(msg, param_attr);
5243 genlmsg_end(msg, hdr);
5246 values_list_nest_cancel:
5247 nla_nest_end(msg, param_values_list);
5249 nla_nest_cancel(msg, param_attr);
5251 genlmsg_cancel(msg, hdr);
5255 static void devlink_param_notify(struct devlink *devlink,
5256 unsigned int port_index,
5257 struct devlink_param_item *param_item,
5258 enum devlink_command cmd)
5260 struct sk_buff *msg;
5263 WARN_ON(cmd != DEVLINK_CMD_PARAM_NEW && cmd != DEVLINK_CMD_PARAM_DEL &&
5264 cmd != DEVLINK_CMD_PORT_PARAM_NEW &&
5265 cmd != DEVLINK_CMD_PORT_PARAM_DEL);
5267 /* devlink_notify_register() / devlink_notify_unregister()
5268 * will replay the notifications if the params are added/removed
5269 * outside of the lifetime of the instance.
5271 if (!devl_is_registered(devlink))
5274 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
5277 err = devlink_nl_param_fill(msg, devlink, port_index, param_item, cmd,
5284 genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink),
5285 msg, 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
5289 devlink_nl_cmd_param_get_dump_one(struct sk_buff *msg, struct devlink *devlink,
5290 struct netlink_callback *cb)
5292 struct devlink_nl_dump_state *state = devlink_dump_state(cb);
5293 struct devlink_param_item *param_item;
5297 list_for_each_entry(param_item, &devlink->param_list, list) {
5298 if (idx < state->idx) {
5302 err = devlink_nl_param_fill(msg, devlink, 0, param_item,
5303 DEVLINK_CMD_PARAM_GET,
5304 NETLINK_CB(cb->skb).portid,
5307 if (err == -EOPNOTSUPP) {
5319 const struct devlink_gen_cmd devl_gen_param = {
5320 .dump_one = devlink_nl_cmd_param_get_dump_one,
5324 devlink_param_type_get_from_info(struct genl_info *info,
5325 enum devlink_param_type *param_type)
5327 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_PARAM_TYPE))
5330 switch (nla_get_u8(info->attrs[DEVLINK_ATTR_PARAM_TYPE])) {
5332 *param_type = DEVLINK_PARAM_TYPE_U8;
5335 *param_type = DEVLINK_PARAM_TYPE_U16;
5338 *param_type = DEVLINK_PARAM_TYPE_U32;
5341 *param_type = DEVLINK_PARAM_TYPE_STRING;
5344 *param_type = DEVLINK_PARAM_TYPE_BOOL;
5354 devlink_param_value_get_from_info(const struct devlink_param *param,
5355 struct genl_info *info,
5356 union devlink_param_value *value)
5358 struct nlattr *param_data;
5361 param_data = info->attrs[DEVLINK_ATTR_PARAM_VALUE_DATA];
5363 if (param->type != DEVLINK_PARAM_TYPE_BOOL && !param_data)
5366 switch (param->type) {
5367 case DEVLINK_PARAM_TYPE_U8:
5368 if (nla_len(param_data) != sizeof(u8))
5370 value->vu8 = nla_get_u8(param_data);
5372 case DEVLINK_PARAM_TYPE_U16:
5373 if (nla_len(param_data) != sizeof(u16))
5375 value->vu16 = nla_get_u16(param_data);
5377 case DEVLINK_PARAM_TYPE_U32:
5378 if (nla_len(param_data) != sizeof(u32))
5380 value->vu32 = nla_get_u32(param_data);
5382 case DEVLINK_PARAM_TYPE_STRING:
5383 len = strnlen(nla_data(param_data), nla_len(param_data));
5384 if (len == nla_len(param_data) ||
5385 len >= __DEVLINK_PARAM_MAX_STRING_VALUE)
5387 strcpy(value->vstr, nla_data(param_data));
5389 case DEVLINK_PARAM_TYPE_BOOL:
5390 if (param_data && nla_len(param_data))
5392 value->vbool = nla_get_flag(param_data);
5398 static struct devlink_param_item *
5399 devlink_param_get_from_info(struct list_head *param_list,
5400 struct genl_info *info)
5404 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_PARAM_NAME))
5407 param_name = nla_data(info->attrs[DEVLINK_ATTR_PARAM_NAME]);
5408 return devlink_param_find_by_name(param_list, param_name);
5411 static int devlink_nl_cmd_param_get_doit(struct sk_buff *skb,
5412 struct genl_info *info)
5414 struct devlink *devlink = info->user_ptr[0];
5415 struct devlink_param_item *param_item;
5416 struct sk_buff *msg;
5419 param_item = devlink_param_get_from_info(&devlink->param_list, info);
5423 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
5427 err = devlink_nl_param_fill(msg, devlink, 0, param_item,
5428 DEVLINK_CMD_PARAM_GET,
5429 info->snd_portid, info->snd_seq, 0);
5435 return genlmsg_reply(msg, info);
5438 static int __devlink_nl_cmd_param_set_doit(struct devlink *devlink,
5439 unsigned int port_index,
5440 struct list_head *param_list,
5441 struct genl_info *info,
5442 enum devlink_command cmd)
5444 enum devlink_param_type param_type;
5445 struct devlink_param_gset_ctx ctx;
5446 enum devlink_param_cmode cmode;
5447 struct devlink_param_item *param_item;
5448 const struct devlink_param *param;
5449 union devlink_param_value value;
5452 param_item = devlink_param_get_from_info(param_list, info);
5455 param = param_item->param;
5456 err = devlink_param_type_get_from_info(info, ¶m_type);
5459 if (param_type != param->type)
5461 err = devlink_param_value_get_from_info(param, info, &value);
5464 if (param->validate) {
5465 err = param->validate(devlink, param->id, value, info->extack);
5470 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_PARAM_VALUE_CMODE))
5472 cmode = nla_get_u8(info->attrs[DEVLINK_ATTR_PARAM_VALUE_CMODE]);
5473 if (!devlink_param_cmode_is_supported(param, cmode))
5476 if (cmode == DEVLINK_PARAM_CMODE_DRIVERINIT) {
5477 if (param->type == DEVLINK_PARAM_TYPE_STRING)
5478 strcpy(param_item->driverinit_value.vstr, value.vstr);
5480 param_item->driverinit_value = value;
5481 param_item->driverinit_value_valid = true;
5487 err = devlink_param_set(devlink, param, &ctx);
5492 devlink_param_notify(devlink, port_index, param_item, cmd);
5496 static int devlink_nl_cmd_param_set_doit(struct sk_buff *skb,
5497 struct genl_info *info)
5499 struct devlink *devlink = info->user_ptr[0];
5501 return __devlink_nl_cmd_param_set_doit(devlink, 0, &devlink->param_list,
5502 info, DEVLINK_CMD_PARAM_NEW);
5505 static int devlink_nl_cmd_port_param_get_dumpit(struct sk_buff *msg,
5506 struct netlink_callback *cb)
5508 NL_SET_ERR_MSG_MOD(cb->extack, "Port params are not supported");
5512 static int devlink_nl_cmd_port_param_get_doit(struct sk_buff *skb,
5513 struct genl_info *info)
5515 NL_SET_ERR_MSG_MOD(info->extack, "Port params are not supported");
5519 static int devlink_nl_cmd_port_param_set_doit(struct sk_buff *skb,
5520 struct genl_info *info)
5522 NL_SET_ERR_MSG_MOD(info->extack, "Port params are not supported");
5526 static int devlink_nl_region_snapshot_id_put(struct sk_buff *msg,
5527 struct devlink *devlink,
5528 struct devlink_snapshot *snapshot)
5530 struct nlattr *snap_attr;
5533 snap_attr = nla_nest_start_noflag(msg, DEVLINK_ATTR_REGION_SNAPSHOT);
5537 err = nla_put_u32(msg, DEVLINK_ATTR_REGION_SNAPSHOT_ID, snapshot->id);
5539 goto nla_put_failure;
5541 nla_nest_end(msg, snap_attr);
5545 nla_nest_cancel(msg, snap_attr);
5549 static int devlink_nl_region_snapshots_id_put(struct sk_buff *msg,
5550 struct devlink *devlink,
5551 struct devlink_region *region)
5553 struct devlink_snapshot *snapshot;
5554 struct nlattr *snapshots_attr;
5557 snapshots_attr = nla_nest_start_noflag(msg,
5558 DEVLINK_ATTR_REGION_SNAPSHOTS);
5559 if (!snapshots_attr)
5562 list_for_each_entry(snapshot, ®ion->snapshot_list, list) {
5563 err = devlink_nl_region_snapshot_id_put(msg, devlink, snapshot);
5565 goto nla_put_failure;
5568 nla_nest_end(msg, snapshots_attr);
5572 nla_nest_cancel(msg, snapshots_attr);
5576 static int devlink_nl_region_fill(struct sk_buff *msg, struct devlink *devlink,
5577 enum devlink_command cmd, u32 portid,
5579 struct devlink_region *region)
5584 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
5588 err = devlink_nl_put_handle(msg, devlink);
5590 goto nla_put_failure;
5593 err = nla_put_u32(msg, DEVLINK_ATTR_PORT_INDEX,
5594 region->port->index);
5596 goto nla_put_failure;
5599 err = nla_put_string(msg, DEVLINK_ATTR_REGION_NAME, region->ops->name);
5601 goto nla_put_failure;
5603 err = nla_put_u64_64bit(msg, DEVLINK_ATTR_REGION_SIZE,
5607 goto nla_put_failure;
5609 err = nla_put_u32(msg, DEVLINK_ATTR_REGION_MAX_SNAPSHOTS,
5610 region->max_snapshots);
5612 goto nla_put_failure;
5614 err = devlink_nl_region_snapshots_id_put(msg, devlink, region);
5616 goto nla_put_failure;
5618 genlmsg_end(msg, hdr);
5622 genlmsg_cancel(msg, hdr);
5626 static struct sk_buff *
5627 devlink_nl_region_notify_build(struct devlink_region *region,
5628 struct devlink_snapshot *snapshot,
5629 enum devlink_command cmd, u32 portid, u32 seq)
5631 struct devlink *devlink = region->devlink;
5632 struct sk_buff *msg;
5637 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
5639 return ERR_PTR(-ENOMEM);
5641 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, 0, cmd);
5647 err = devlink_nl_put_handle(msg, devlink);
5649 goto out_cancel_msg;
5652 err = nla_put_u32(msg, DEVLINK_ATTR_PORT_INDEX,
5653 region->port->index);
5655 goto out_cancel_msg;
5658 err = nla_put_string(msg, DEVLINK_ATTR_REGION_NAME,
5661 goto out_cancel_msg;
5664 err = nla_put_u32(msg, DEVLINK_ATTR_REGION_SNAPSHOT_ID,
5667 goto out_cancel_msg;
5669 err = nla_put_u64_64bit(msg, DEVLINK_ATTR_REGION_SIZE,
5670 region->size, DEVLINK_ATTR_PAD);
5672 goto out_cancel_msg;
5674 genlmsg_end(msg, hdr);
5679 genlmsg_cancel(msg, hdr);
5682 return ERR_PTR(err);
5685 static void devlink_nl_region_notify(struct devlink_region *region,
5686 struct devlink_snapshot *snapshot,
5687 enum devlink_command cmd)
5689 struct devlink *devlink = region->devlink;
5690 struct sk_buff *msg;
5692 WARN_ON(cmd != DEVLINK_CMD_REGION_NEW && cmd != DEVLINK_CMD_REGION_DEL);
5693 if (!xa_get_mark(&devlinks, devlink->index, DEVLINK_REGISTERED))
5696 msg = devlink_nl_region_notify_build(region, snapshot, cmd, 0, 0);
5700 genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink), msg,
5701 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
5705 * __devlink_snapshot_id_increment - Increment number of snapshots using an id
5706 * @devlink: devlink instance
5707 * @id: the snapshot id
5709 * Track when a new snapshot begins using an id. Load the count for the
5710 * given id from the snapshot xarray, increment it, and store it back.
5712 * Called when a new snapshot is created with the given id.
5714 * The id *must* have been previously allocated by
5715 * devlink_region_snapshot_id_get().
5717 * Returns 0 on success, or an error on failure.
5719 static int __devlink_snapshot_id_increment(struct devlink *devlink, u32 id)
5721 unsigned long count;
5725 xa_lock(&devlink->snapshot_ids);
5726 p = xa_load(&devlink->snapshot_ids, id);
5732 if (WARN_ON(!xa_is_value(p))) {
5737 count = xa_to_value(p);
5740 err = xa_err(__xa_store(&devlink->snapshot_ids, id, xa_mk_value(count),
5743 xa_unlock(&devlink->snapshot_ids);
5748 * __devlink_snapshot_id_decrement - Decrease number of snapshots using an id
5749 * @devlink: devlink instance
5750 * @id: the snapshot id
5752 * Track when a snapshot is deleted and stops using an id. Load the count
5753 * for the given id from the snapshot xarray, decrement it, and store it
5756 * If the count reaches zero, erase this id from the xarray, freeing it
5757 * up for future re-use by devlink_region_snapshot_id_get().
5759 * Called when a snapshot using the given id is deleted, and when the
5760 * initial allocator of the id is finished using it.
5762 static void __devlink_snapshot_id_decrement(struct devlink *devlink, u32 id)
5764 unsigned long count;
5767 xa_lock(&devlink->snapshot_ids);
5768 p = xa_load(&devlink->snapshot_ids, id);
5772 if (WARN_ON(!xa_is_value(p)))
5775 count = xa_to_value(p);
5779 __xa_store(&devlink->snapshot_ids, id, xa_mk_value(count),
5782 /* If this was the last user, we can erase this id */
5783 __xa_erase(&devlink->snapshot_ids, id);
5786 xa_unlock(&devlink->snapshot_ids);
5790 * __devlink_snapshot_id_insert - Insert a specific snapshot ID
5791 * @devlink: devlink instance
5792 * @id: the snapshot id
5794 * Mark the given snapshot id as used by inserting a zero value into the
5797 * This must be called while holding the devlink instance lock. Unlike
5798 * devlink_snapshot_id_get, the initial reference count is zero, not one.
5799 * It is expected that the id will immediately be used before
5800 * releasing the devlink instance lock.
5802 * Returns zero on success, or an error code if the snapshot id could not
5805 static int __devlink_snapshot_id_insert(struct devlink *devlink, u32 id)
5809 xa_lock(&devlink->snapshot_ids);
5810 if (xa_load(&devlink->snapshot_ids, id)) {
5811 xa_unlock(&devlink->snapshot_ids);
5814 err = xa_err(__xa_store(&devlink->snapshot_ids, id, xa_mk_value(0),
5816 xa_unlock(&devlink->snapshot_ids);
5821 * __devlink_region_snapshot_id_get - get snapshot ID
5822 * @devlink: devlink instance
5823 * @id: storage to return snapshot id
5825 * Allocates a new snapshot id. Returns zero on success, or a negative
5826 * error on failure. Must be called while holding the devlink instance
5829 * Snapshot IDs are tracked using an xarray which stores the number of
5830 * users of the snapshot id.
5832 * Note that the caller of this function counts as a 'user', in order to
5833 * avoid race conditions. The caller must release its hold on the
5834 * snapshot by using devlink_region_snapshot_id_put.
5836 static int __devlink_region_snapshot_id_get(struct devlink *devlink, u32 *id)
5838 return xa_alloc(&devlink->snapshot_ids, id, xa_mk_value(1),
5839 xa_limit_32b, GFP_KERNEL);
5843 * __devlink_region_snapshot_create - create a new snapshot
5844 * This will add a new snapshot of a region. The snapshot
5845 * will be stored on the region struct and can be accessed
5846 * from devlink. This is useful for future analyses of snapshots.
5847 * Multiple snapshots can be created on a region.
5848 * The @snapshot_id should be obtained using the getter function.
5850 * Must be called only while holding the region snapshot lock.
5852 * @region: devlink region of the snapshot
5853 * @data: snapshot data
5854 * @snapshot_id: snapshot id to be created
5857 __devlink_region_snapshot_create(struct devlink_region *region,
5858 u8 *data, u32 snapshot_id)
5860 struct devlink *devlink = region->devlink;
5861 struct devlink_snapshot *snapshot;
5864 lockdep_assert_held(®ion->snapshot_lock);
5866 /* check if region can hold one more snapshot */
5867 if (region->cur_snapshots == region->max_snapshots)
5870 if (devlink_region_snapshot_get_by_id(region, snapshot_id))
5873 snapshot = kzalloc(sizeof(*snapshot), GFP_KERNEL);
5877 err = __devlink_snapshot_id_increment(devlink, snapshot_id);
5879 goto err_snapshot_id_increment;
5881 snapshot->id = snapshot_id;
5882 snapshot->region = region;
5883 snapshot->data = data;
5885 list_add_tail(&snapshot->list, ®ion->snapshot_list);
5887 region->cur_snapshots++;
5889 devlink_nl_region_notify(region, snapshot, DEVLINK_CMD_REGION_NEW);
5892 err_snapshot_id_increment:
5897 static void devlink_region_snapshot_del(struct devlink_region *region,
5898 struct devlink_snapshot *snapshot)
5900 struct devlink *devlink = region->devlink;
5902 lockdep_assert_held(®ion->snapshot_lock);
5904 devlink_nl_region_notify(region, snapshot, DEVLINK_CMD_REGION_DEL);
5905 region->cur_snapshots--;
5906 list_del(&snapshot->list);
5907 region->ops->destructor(snapshot->data);
5908 __devlink_snapshot_id_decrement(devlink, snapshot->id);
5912 static int devlink_nl_cmd_region_get_doit(struct sk_buff *skb,
5913 struct genl_info *info)
5915 struct devlink *devlink = info->user_ptr[0];
5916 struct devlink_port *port = NULL;
5917 struct devlink_region *region;
5918 const char *region_name;
5919 struct sk_buff *msg;
5923 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_REGION_NAME))
5926 if (info->attrs[DEVLINK_ATTR_PORT_INDEX]) {
5927 index = nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_INDEX]);
5929 port = devlink_port_get_by_index(devlink, index);
5934 region_name = nla_data(info->attrs[DEVLINK_ATTR_REGION_NAME]);
5936 region = devlink_port_region_get_by_name(port, region_name);
5938 region = devlink_region_get_by_name(devlink, region_name);
5943 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
5947 err = devlink_nl_region_fill(msg, devlink, DEVLINK_CMD_REGION_GET,
5948 info->snd_portid, info->snd_seq, 0,
5955 return genlmsg_reply(msg, info);
5958 static int devlink_nl_cmd_region_get_port_dumpit(struct sk_buff *msg,
5959 struct netlink_callback *cb,
5960 struct devlink_port *port,
5964 struct devlink_region *region;
5967 list_for_each_entry(region, &port->region_list, list) {
5972 err = devlink_nl_region_fill(msg, port->devlink,
5973 DEVLINK_CMD_REGION_GET,
5974 NETLINK_CB(cb->skb).portid,
5976 NLM_F_MULTI, region);
5987 devlink_nl_cmd_region_get_dump_one(struct sk_buff *msg, struct devlink *devlink,
5988 struct netlink_callback *cb)
5990 struct devlink_nl_dump_state *state = devlink_dump_state(cb);
5991 struct devlink_region *region;
5992 struct devlink_port *port;
5993 unsigned long port_index;
5997 list_for_each_entry(region, &devlink->region_list, list) {
5998 if (idx < state->idx) {
6002 err = devlink_nl_region_fill(msg, devlink,
6003 DEVLINK_CMD_REGION_GET,
6004 NETLINK_CB(cb->skb).portid,
6006 NLM_F_MULTI, region);
6014 xa_for_each(&devlink->ports, port_index, port) {
6015 err = devlink_nl_cmd_region_get_port_dumpit(msg, cb, port, &idx,
6026 const struct devlink_gen_cmd devl_gen_region = {
6027 .dump_one = devlink_nl_cmd_region_get_dump_one,
6030 static int devlink_nl_cmd_region_del(struct sk_buff *skb,
6031 struct genl_info *info)
6033 struct devlink *devlink = info->user_ptr[0];
6034 struct devlink_snapshot *snapshot;
6035 struct devlink_port *port = NULL;
6036 struct devlink_region *region;
6037 const char *region_name;
6041 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_REGION_NAME) ||
6042 GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_REGION_SNAPSHOT_ID))
6045 region_name = nla_data(info->attrs[DEVLINK_ATTR_REGION_NAME]);
6046 snapshot_id = nla_get_u32(info->attrs[DEVLINK_ATTR_REGION_SNAPSHOT_ID]);
6048 if (info->attrs[DEVLINK_ATTR_PORT_INDEX]) {
6049 index = nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_INDEX]);
6051 port = devlink_port_get_by_index(devlink, index);
6057 region = devlink_port_region_get_by_name(port, region_name);
6059 region = devlink_region_get_by_name(devlink, region_name);
6064 mutex_lock(®ion->snapshot_lock);
6065 snapshot = devlink_region_snapshot_get_by_id(region, snapshot_id);
6067 mutex_unlock(®ion->snapshot_lock);
6071 devlink_region_snapshot_del(region, snapshot);
6072 mutex_unlock(®ion->snapshot_lock);
6077 devlink_nl_cmd_region_new(struct sk_buff *skb, struct genl_info *info)
6079 struct devlink *devlink = info->user_ptr[0];
6080 struct devlink_snapshot *snapshot;
6081 struct devlink_port *port = NULL;
6082 struct nlattr *snapshot_id_attr;
6083 struct devlink_region *region;
6084 const char *region_name;
6090 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_REGION_NAME)) {
6091 NL_SET_ERR_MSG_MOD(info->extack, "No region name provided");
6095 region_name = nla_data(info->attrs[DEVLINK_ATTR_REGION_NAME]);
6097 if (info->attrs[DEVLINK_ATTR_PORT_INDEX]) {
6098 index = nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_INDEX]);
6100 port = devlink_port_get_by_index(devlink, index);
6106 region = devlink_port_region_get_by_name(port, region_name);
6108 region = devlink_region_get_by_name(devlink, region_name);
6111 NL_SET_ERR_MSG_MOD(info->extack, "The requested region does not exist");
6115 if (!region->ops->snapshot) {
6116 NL_SET_ERR_MSG_MOD(info->extack, "The requested region does not support taking an immediate snapshot");
6120 mutex_lock(®ion->snapshot_lock);
6122 if (region->cur_snapshots == region->max_snapshots) {
6123 NL_SET_ERR_MSG_MOD(info->extack, "The region has reached the maximum number of stored snapshots");
6128 snapshot_id_attr = info->attrs[DEVLINK_ATTR_REGION_SNAPSHOT_ID];
6129 if (snapshot_id_attr) {
6130 snapshot_id = nla_get_u32(snapshot_id_attr);
6132 if (devlink_region_snapshot_get_by_id(region, snapshot_id)) {
6133 NL_SET_ERR_MSG_MOD(info->extack, "The requested snapshot id is already in use");
6138 err = __devlink_snapshot_id_insert(devlink, snapshot_id);
6142 err = __devlink_region_snapshot_id_get(devlink, &snapshot_id);
6144 NL_SET_ERR_MSG_MOD(info->extack, "Failed to allocate a new snapshot id");
6150 err = region->port_ops->snapshot(port, region->port_ops,
6151 info->extack, &data);
6153 err = region->ops->snapshot(devlink, region->ops,
6154 info->extack, &data);
6156 goto err_snapshot_capture;
6158 err = __devlink_region_snapshot_create(region, data, snapshot_id);
6160 goto err_snapshot_create;
6162 if (!snapshot_id_attr) {
6163 struct sk_buff *msg;
6165 snapshot = devlink_region_snapshot_get_by_id(region,
6167 if (WARN_ON(!snapshot)) {
6172 msg = devlink_nl_region_notify_build(region, snapshot,
6173 DEVLINK_CMD_REGION_NEW,
6176 err = PTR_ERR_OR_ZERO(msg);
6180 err = genlmsg_reply(msg, info);
6185 mutex_unlock(®ion->snapshot_lock);
6188 err_snapshot_create:
6189 region->ops->destructor(data);
6190 err_snapshot_capture:
6191 __devlink_snapshot_id_decrement(devlink, snapshot_id);
6192 mutex_unlock(®ion->snapshot_lock);
6196 devlink_region_snapshot_del(region, snapshot);
6198 mutex_unlock(®ion->snapshot_lock);
6202 static int devlink_nl_cmd_region_read_chunk_fill(struct sk_buff *msg,
6203 u8 *chunk, u32 chunk_size,
6206 struct nlattr *chunk_attr;
6209 chunk_attr = nla_nest_start_noflag(msg, DEVLINK_ATTR_REGION_CHUNK);
6213 err = nla_put(msg, DEVLINK_ATTR_REGION_CHUNK_DATA, chunk_size, chunk);
6215 goto nla_put_failure;
6217 err = nla_put_u64_64bit(msg, DEVLINK_ATTR_REGION_CHUNK_ADDR, addr,
6220 goto nla_put_failure;
6222 nla_nest_end(msg, chunk_attr);
6226 nla_nest_cancel(msg, chunk_attr);
6230 #define DEVLINK_REGION_READ_CHUNK_SIZE 256
6232 typedef int devlink_chunk_fill_t(void *cb_priv, u8 *chunk, u32 chunk_size,
6234 struct netlink_ext_ack *extack);
6237 devlink_nl_region_read_fill(struct sk_buff *skb, devlink_chunk_fill_t *cb,
6238 void *cb_priv, u64 start_offset, u64 end_offset,
6239 u64 *new_offset, struct netlink_ext_ack *extack)
6241 u64 curr_offset = start_offset;
6245 /* Allocate and re-use a single buffer */
6246 data = kmalloc(DEVLINK_REGION_READ_CHUNK_SIZE, GFP_KERNEL);
6250 *new_offset = start_offset;
6252 while (curr_offset < end_offset) {
6255 data_size = min_t(u32, end_offset - curr_offset,
6256 DEVLINK_REGION_READ_CHUNK_SIZE);
6258 err = cb(cb_priv, data, data_size, curr_offset, extack);
6262 err = devlink_nl_cmd_region_read_chunk_fill(skb, data, data_size, curr_offset);
6266 curr_offset += data_size;
6268 *new_offset = curr_offset;
6276 devlink_region_snapshot_fill(void *cb_priv, u8 *chunk, u32 chunk_size,
6278 struct netlink_ext_ack __always_unused *extack)
6280 struct devlink_snapshot *snapshot = cb_priv;
6282 memcpy(chunk, &snapshot->data[curr_offset], chunk_size);
6288 devlink_region_port_direct_fill(void *cb_priv, u8 *chunk, u32 chunk_size,
6289 u64 curr_offset, struct netlink_ext_ack *extack)
6291 struct devlink_region *region = cb_priv;
6293 return region->port_ops->read(region->port, region->port_ops, extack,
6294 curr_offset, chunk_size, chunk);
6298 devlink_region_direct_fill(void *cb_priv, u8 *chunk, u32 chunk_size,
6299 u64 curr_offset, struct netlink_ext_ack *extack)
6301 struct devlink_region *region = cb_priv;
6303 return region->ops->read(region->devlink, region->ops, extack,
6304 curr_offset, chunk_size, chunk);
6307 static int devlink_nl_cmd_region_read_dumpit(struct sk_buff *skb,
6308 struct netlink_callback *cb)
6310 const struct genl_dumpit_info *info = genl_dumpit_info(cb);
6311 struct devlink_nl_dump_state *state = devlink_dump_state(cb);
6312 struct nlattr *chunks_attr, *region_attr, *snapshot_attr;
6313 u64 ret_offset, start_offset, end_offset = U64_MAX;
6314 struct nlattr **attrs = info->attrs;
6315 struct devlink_port *port = NULL;
6316 devlink_chunk_fill_t *region_cb;
6317 struct devlink_region *region;
6318 const char *region_name;
6319 struct devlink *devlink;
6321 void *region_cb_priv;
6325 start_offset = state->start_offset;
6327 devlink = devlink_get_from_attrs_lock(sock_net(cb->skb->sk), attrs);
6328 if (IS_ERR(devlink))
6329 return PTR_ERR(devlink);
6331 if (!attrs[DEVLINK_ATTR_REGION_NAME]) {
6332 NL_SET_ERR_MSG(cb->extack, "No region name provided");
6337 if (info->attrs[DEVLINK_ATTR_PORT_INDEX]) {
6338 index = nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_INDEX]);
6340 port = devlink_port_get_by_index(devlink, index);
6347 region_attr = attrs[DEVLINK_ATTR_REGION_NAME];
6348 region_name = nla_data(region_attr);
6351 region = devlink_port_region_get_by_name(port, region_name);
6353 region = devlink_region_get_by_name(devlink, region_name);
6356 NL_SET_ERR_MSG_ATTR(cb->extack, region_attr, "Requested region does not exist");
6361 snapshot_attr = attrs[DEVLINK_ATTR_REGION_SNAPSHOT_ID];
6362 if (!snapshot_attr) {
6363 if (!nla_get_flag(attrs[DEVLINK_ATTR_REGION_DIRECT])) {
6364 NL_SET_ERR_MSG(cb->extack, "No snapshot id provided");
6369 if (!region->ops->read) {
6370 NL_SET_ERR_MSG(cb->extack, "Requested region does not support direct read");
6376 region_cb = &devlink_region_port_direct_fill;
6378 region_cb = &devlink_region_direct_fill;
6379 region_cb_priv = region;
6381 struct devlink_snapshot *snapshot;
6384 if (nla_get_flag(attrs[DEVLINK_ATTR_REGION_DIRECT])) {
6385 NL_SET_ERR_MSG_ATTR(cb->extack, snapshot_attr, "Direct region read does not use snapshot");
6390 snapshot_id = nla_get_u32(snapshot_attr);
6391 snapshot = devlink_region_snapshot_get_by_id(region, snapshot_id);
6393 NL_SET_ERR_MSG_ATTR(cb->extack, snapshot_attr, "Requested snapshot does not exist");
6397 region_cb = &devlink_region_snapshot_fill;
6398 region_cb_priv = snapshot;
6401 if (attrs[DEVLINK_ATTR_REGION_CHUNK_ADDR] &&
6402 attrs[DEVLINK_ATTR_REGION_CHUNK_LEN]) {
6405 nla_get_u64(attrs[DEVLINK_ATTR_REGION_CHUNK_ADDR]);
6407 end_offset = nla_get_u64(attrs[DEVLINK_ATTR_REGION_CHUNK_ADDR]);
6408 end_offset += nla_get_u64(attrs[DEVLINK_ATTR_REGION_CHUNK_LEN]);
6411 if (end_offset > region->size)
6412 end_offset = region->size;
6414 /* return 0 if there is no further data to read */
6415 if (start_offset == end_offset) {
6420 hdr = genlmsg_put(skb, NETLINK_CB(cb->skb).portid, cb->nlh->nlmsg_seq,
6421 &devlink_nl_family, NLM_F_ACK | NLM_F_MULTI,
6422 DEVLINK_CMD_REGION_READ);
6428 err = devlink_nl_put_handle(skb, devlink);
6430 goto nla_put_failure;
6433 err = nla_put_u32(skb, DEVLINK_ATTR_PORT_INDEX,
6434 region->port->index);
6436 goto nla_put_failure;
6439 err = nla_put_string(skb, DEVLINK_ATTR_REGION_NAME, region_name);
6441 goto nla_put_failure;
6443 chunks_attr = nla_nest_start_noflag(skb, DEVLINK_ATTR_REGION_CHUNKS);
6446 goto nla_put_failure;
6449 err = devlink_nl_region_read_fill(skb, region_cb, region_cb_priv,
6450 start_offset, end_offset, &ret_offset,
6453 if (err && err != -EMSGSIZE)
6454 goto nla_put_failure;
6456 /* Check if there was any progress done to prevent infinite loop */
6457 if (ret_offset == start_offset) {
6459 goto nla_put_failure;
6462 state->start_offset = ret_offset;
6464 nla_nest_end(skb, chunks_attr);
6465 genlmsg_end(skb, hdr);
6466 devl_unlock(devlink);
6467 devlink_put(devlink);
6471 genlmsg_cancel(skb, hdr);
6473 devl_unlock(devlink);
6474 devlink_put(devlink);
6478 int devlink_info_serial_number_put(struct devlink_info_req *req, const char *sn)
6482 return nla_put_string(req->msg, DEVLINK_ATTR_INFO_SERIAL_NUMBER, sn);
6484 EXPORT_SYMBOL_GPL(devlink_info_serial_number_put);
6486 int devlink_info_board_serial_number_put(struct devlink_info_req *req,
6491 return nla_put_string(req->msg, DEVLINK_ATTR_INFO_BOARD_SERIAL_NUMBER,
6494 EXPORT_SYMBOL_GPL(devlink_info_board_serial_number_put);
6496 static int devlink_info_version_put(struct devlink_info_req *req, int attr,
6497 const char *version_name,
6498 const char *version_value,
6499 enum devlink_info_version_type version_type)
6501 struct nlattr *nest;
6504 if (req->version_cb)
6505 req->version_cb(version_name, version_type,
6506 req->version_cb_priv);
6511 nest = nla_nest_start_noflag(req->msg, attr);
6515 err = nla_put_string(req->msg, DEVLINK_ATTR_INFO_VERSION_NAME,
6518 goto nla_put_failure;
6520 err = nla_put_string(req->msg, DEVLINK_ATTR_INFO_VERSION_VALUE,
6523 goto nla_put_failure;
6525 nla_nest_end(req->msg, nest);
6530 nla_nest_cancel(req->msg, nest);
6534 int devlink_info_version_fixed_put(struct devlink_info_req *req,
6535 const char *version_name,
6536 const char *version_value)
6538 return devlink_info_version_put(req, DEVLINK_ATTR_INFO_VERSION_FIXED,
6539 version_name, version_value,
6540 DEVLINK_INFO_VERSION_TYPE_NONE);
6542 EXPORT_SYMBOL_GPL(devlink_info_version_fixed_put);
6544 int devlink_info_version_stored_put(struct devlink_info_req *req,
6545 const char *version_name,
6546 const char *version_value)
6548 return devlink_info_version_put(req, DEVLINK_ATTR_INFO_VERSION_STORED,
6549 version_name, version_value,
6550 DEVLINK_INFO_VERSION_TYPE_NONE);
6552 EXPORT_SYMBOL_GPL(devlink_info_version_stored_put);
6554 int devlink_info_version_stored_put_ext(struct devlink_info_req *req,
6555 const char *version_name,
6556 const char *version_value,
6557 enum devlink_info_version_type version_type)
6559 return devlink_info_version_put(req, DEVLINK_ATTR_INFO_VERSION_STORED,
6560 version_name, version_value,
6563 EXPORT_SYMBOL_GPL(devlink_info_version_stored_put_ext);
6565 int devlink_info_version_running_put(struct devlink_info_req *req,
6566 const char *version_name,
6567 const char *version_value)
6569 return devlink_info_version_put(req, DEVLINK_ATTR_INFO_VERSION_RUNNING,
6570 version_name, version_value,
6571 DEVLINK_INFO_VERSION_TYPE_NONE);
6573 EXPORT_SYMBOL_GPL(devlink_info_version_running_put);
6575 int devlink_info_version_running_put_ext(struct devlink_info_req *req,
6576 const char *version_name,
6577 const char *version_value,
6578 enum devlink_info_version_type version_type)
6580 return devlink_info_version_put(req, DEVLINK_ATTR_INFO_VERSION_RUNNING,
6581 version_name, version_value,
6584 EXPORT_SYMBOL_GPL(devlink_info_version_running_put_ext);
6586 static int devlink_nl_driver_info_get(struct device_driver *drv,
6587 struct devlink_info_req *req)
6593 return nla_put_string(req->msg, DEVLINK_ATTR_INFO_DRIVER_NAME,
6600 devlink_nl_info_fill(struct sk_buff *msg, struct devlink *devlink,
6601 enum devlink_command cmd, u32 portid,
6602 u32 seq, int flags, struct netlink_ext_ack *extack)
6604 struct device *dev = devlink_to_dev(devlink);
6605 struct devlink_info_req req = {};
6609 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
6614 if (devlink_nl_put_handle(msg, devlink))
6615 goto err_cancel_msg;
6618 if (devlink->ops->info_get) {
6619 err = devlink->ops->info_get(devlink, &req, extack);
6621 goto err_cancel_msg;
6624 err = devlink_nl_driver_info_get(dev->driver, &req);
6626 goto err_cancel_msg;
6628 genlmsg_end(msg, hdr);
6632 genlmsg_cancel(msg, hdr);
6636 static int devlink_nl_cmd_info_get_doit(struct sk_buff *skb,
6637 struct genl_info *info)
6639 struct devlink *devlink = info->user_ptr[0];
6640 struct sk_buff *msg;
6643 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
6647 err = devlink_nl_info_fill(msg, devlink, DEVLINK_CMD_INFO_GET,
6648 info->snd_portid, info->snd_seq, 0,
6655 return genlmsg_reply(msg, info);
6659 devlink_nl_cmd_info_get_dump_one(struct sk_buff *msg, struct devlink *devlink,
6660 struct netlink_callback *cb)
6664 err = devlink_nl_info_fill(msg, devlink, DEVLINK_CMD_INFO_GET,
6665 NETLINK_CB(cb->skb).portid,
6666 cb->nlh->nlmsg_seq, NLM_F_MULTI,
6668 if (err == -EOPNOTSUPP)
6673 const struct devlink_gen_cmd devl_gen_info = {
6674 .dump_one = devlink_nl_cmd_info_get_dump_one,
6677 struct devlink_fmsg_item {
6678 struct list_head list;
6685 struct devlink_fmsg {
6686 struct list_head item_list;
6687 bool putting_binary; /* This flag forces enclosing of binary data
6688 * in an array brackets. It forces using
6689 * of designated API:
6690 * devlink_fmsg_binary_pair_nest_start()
6691 * devlink_fmsg_binary_pair_nest_end()
6695 static struct devlink_fmsg *devlink_fmsg_alloc(void)
6697 struct devlink_fmsg *fmsg;
6699 fmsg = kzalloc(sizeof(*fmsg), GFP_KERNEL);
6703 INIT_LIST_HEAD(&fmsg->item_list);
6708 static void devlink_fmsg_free(struct devlink_fmsg *fmsg)
6710 struct devlink_fmsg_item *item, *tmp;
6712 list_for_each_entry_safe(item, tmp, &fmsg->item_list, list) {
6713 list_del(&item->list);
6719 static int devlink_fmsg_nest_common(struct devlink_fmsg *fmsg,
6722 struct devlink_fmsg_item *item;
6724 item = kzalloc(sizeof(*item), GFP_KERNEL);
6728 item->attrtype = attrtype;
6729 list_add_tail(&item->list, &fmsg->item_list);
6734 int devlink_fmsg_obj_nest_start(struct devlink_fmsg *fmsg)
6736 if (fmsg->putting_binary)
6739 return devlink_fmsg_nest_common(fmsg, DEVLINK_ATTR_FMSG_OBJ_NEST_START);
6741 EXPORT_SYMBOL_GPL(devlink_fmsg_obj_nest_start);
6743 static int devlink_fmsg_nest_end(struct devlink_fmsg *fmsg)
6745 if (fmsg->putting_binary)
6748 return devlink_fmsg_nest_common(fmsg, DEVLINK_ATTR_FMSG_NEST_END);
6751 int devlink_fmsg_obj_nest_end(struct devlink_fmsg *fmsg)
6753 if (fmsg->putting_binary)
6756 return devlink_fmsg_nest_end(fmsg);
6758 EXPORT_SYMBOL_GPL(devlink_fmsg_obj_nest_end);
6760 #define DEVLINK_FMSG_MAX_SIZE (GENLMSG_DEFAULT_SIZE - GENL_HDRLEN - NLA_HDRLEN)
6762 static int devlink_fmsg_put_name(struct devlink_fmsg *fmsg, const char *name)
6764 struct devlink_fmsg_item *item;
6766 if (fmsg->putting_binary)
6769 if (strlen(name) + 1 > DEVLINK_FMSG_MAX_SIZE)
6772 item = kzalloc(sizeof(*item) + strlen(name) + 1, GFP_KERNEL);
6776 item->nla_type = NLA_NUL_STRING;
6777 item->len = strlen(name) + 1;
6778 item->attrtype = DEVLINK_ATTR_FMSG_OBJ_NAME;
6779 memcpy(&item->value, name, item->len);
6780 list_add_tail(&item->list, &fmsg->item_list);
6785 int devlink_fmsg_pair_nest_start(struct devlink_fmsg *fmsg, const char *name)
6789 if (fmsg->putting_binary)
6792 err = devlink_fmsg_nest_common(fmsg, DEVLINK_ATTR_FMSG_PAIR_NEST_START);
6796 err = devlink_fmsg_put_name(fmsg, name);
6802 EXPORT_SYMBOL_GPL(devlink_fmsg_pair_nest_start);
6804 int devlink_fmsg_pair_nest_end(struct devlink_fmsg *fmsg)
6806 if (fmsg->putting_binary)
6809 return devlink_fmsg_nest_end(fmsg);
6811 EXPORT_SYMBOL_GPL(devlink_fmsg_pair_nest_end);
6813 int devlink_fmsg_arr_pair_nest_start(struct devlink_fmsg *fmsg,
6818 if (fmsg->putting_binary)
6821 err = devlink_fmsg_pair_nest_start(fmsg, name);
6825 err = devlink_fmsg_nest_common(fmsg, DEVLINK_ATTR_FMSG_ARR_NEST_START);
6831 EXPORT_SYMBOL_GPL(devlink_fmsg_arr_pair_nest_start);
6833 int devlink_fmsg_arr_pair_nest_end(struct devlink_fmsg *fmsg)
6837 if (fmsg->putting_binary)
6840 err = devlink_fmsg_nest_end(fmsg);
6844 err = devlink_fmsg_nest_end(fmsg);
6850 EXPORT_SYMBOL_GPL(devlink_fmsg_arr_pair_nest_end);
6852 int devlink_fmsg_binary_pair_nest_start(struct devlink_fmsg *fmsg,
6857 err = devlink_fmsg_arr_pair_nest_start(fmsg, name);
6861 fmsg->putting_binary = true;
6864 EXPORT_SYMBOL_GPL(devlink_fmsg_binary_pair_nest_start);
6866 int devlink_fmsg_binary_pair_nest_end(struct devlink_fmsg *fmsg)
6868 if (!fmsg->putting_binary)
6871 fmsg->putting_binary = false;
6872 return devlink_fmsg_arr_pair_nest_end(fmsg);
6874 EXPORT_SYMBOL_GPL(devlink_fmsg_binary_pair_nest_end);
6876 static int devlink_fmsg_put_value(struct devlink_fmsg *fmsg,
6877 const void *value, u16 value_len,
6880 struct devlink_fmsg_item *item;
6882 if (value_len > DEVLINK_FMSG_MAX_SIZE)
6885 item = kzalloc(sizeof(*item) + value_len, GFP_KERNEL);
6889 item->nla_type = value_nla_type;
6890 item->len = value_len;
6891 item->attrtype = DEVLINK_ATTR_FMSG_OBJ_VALUE_DATA;
6892 memcpy(&item->value, value, item->len);
6893 list_add_tail(&item->list, &fmsg->item_list);
6898 static int devlink_fmsg_bool_put(struct devlink_fmsg *fmsg, bool value)
6900 if (fmsg->putting_binary)
6903 return devlink_fmsg_put_value(fmsg, &value, sizeof(value), NLA_FLAG);
6906 static int devlink_fmsg_u8_put(struct devlink_fmsg *fmsg, u8 value)
6908 if (fmsg->putting_binary)
6911 return devlink_fmsg_put_value(fmsg, &value, sizeof(value), NLA_U8);
6914 int devlink_fmsg_u32_put(struct devlink_fmsg *fmsg, u32 value)
6916 if (fmsg->putting_binary)
6919 return devlink_fmsg_put_value(fmsg, &value, sizeof(value), NLA_U32);
6921 EXPORT_SYMBOL_GPL(devlink_fmsg_u32_put);
6923 static int devlink_fmsg_u64_put(struct devlink_fmsg *fmsg, u64 value)
6925 if (fmsg->putting_binary)
6928 return devlink_fmsg_put_value(fmsg, &value, sizeof(value), NLA_U64);
6931 int devlink_fmsg_string_put(struct devlink_fmsg *fmsg, const char *value)
6933 if (fmsg->putting_binary)
6936 return devlink_fmsg_put_value(fmsg, value, strlen(value) + 1,
6939 EXPORT_SYMBOL_GPL(devlink_fmsg_string_put);
6941 int devlink_fmsg_binary_put(struct devlink_fmsg *fmsg, const void *value,
6944 if (!fmsg->putting_binary)
6947 return devlink_fmsg_put_value(fmsg, value, value_len, NLA_BINARY);
6949 EXPORT_SYMBOL_GPL(devlink_fmsg_binary_put);
6951 int devlink_fmsg_bool_pair_put(struct devlink_fmsg *fmsg, const char *name,
6956 err = devlink_fmsg_pair_nest_start(fmsg, name);
6960 err = devlink_fmsg_bool_put(fmsg, value);
6964 err = devlink_fmsg_pair_nest_end(fmsg);
6970 EXPORT_SYMBOL_GPL(devlink_fmsg_bool_pair_put);
6972 int devlink_fmsg_u8_pair_put(struct devlink_fmsg *fmsg, const char *name,
6977 err = devlink_fmsg_pair_nest_start(fmsg, name);
6981 err = devlink_fmsg_u8_put(fmsg, value);
6985 err = devlink_fmsg_pair_nest_end(fmsg);
6991 EXPORT_SYMBOL_GPL(devlink_fmsg_u8_pair_put);
6993 int devlink_fmsg_u32_pair_put(struct devlink_fmsg *fmsg, const char *name,
6998 err = devlink_fmsg_pair_nest_start(fmsg, name);
7002 err = devlink_fmsg_u32_put(fmsg, value);
7006 err = devlink_fmsg_pair_nest_end(fmsg);
7012 EXPORT_SYMBOL_GPL(devlink_fmsg_u32_pair_put);
7014 int devlink_fmsg_u64_pair_put(struct devlink_fmsg *fmsg, const char *name,
7019 err = devlink_fmsg_pair_nest_start(fmsg, name);
7023 err = devlink_fmsg_u64_put(fmsg, value);
7027 err = devlink_fmsg_pair_nest_end(fmsg);
7033 EXPORT_SYMBOL_GPL(devlink_fmsg_u64_pair_put);
7035 int devlink_fmsg_string_pair_put(struct devlink_fmsg *fmsg, const char *name,
7040 err = devlink_fmsg_pair_nest_start(fmsg, name);
7044 err = devlink_fmsg_string_put(fmsg, value);
7048 err = devlink_fmsg_pair_nest_end(fmsg);
7054 EXPORT_SYMBOL_GPL(devlink_fmsg_string_pair_put);
7056 int devlink_fmsg_binary_pair_put(struct devlink_fmsg *fmsg, const char *name,
7057 const void *value, u32 value_len)
7064 err = devlink_fmsg_binary_pair_nest_start(fmsg, name);
7068 for (offset = 0; offset < value_len; offset += data_size) {
7069 data_size = value_len - offset;
7070 if (data_size > DEVLINK_FMSG_MAX_SIZE)
7071 data_size = DEVLINK_FMSG_MAX_SIZE;
7072 err = devlink_fmsg_binary_put(fmsg, value + offset, data_size);
7075 /* Exit from loop with a break (instead of
7076 * return) to make sure putting_binary is turned off in
7077 * devlink_fmsg_binary_pair_nest_end
7081 end_err = devlink_fmsg_binary_pair_nest_end(fmsg);
7087 EXPORT_SYMBOL_GPL(devlink_fmsg_binary_pair_put);
7090 devlink_fmsg_item_fill_type(struct devlink_fmsg_item *msg, struct sk_buff *skb)
7092 switch (msg->nla_type) {
7097 case NLA_NUL_STRING:
7099 return nla_put_u8(skb, DEVLINK_ATTR_FMSG_OBJ_VALUE_TYPE,
7107 devlink_fmsg_item_fill_data(struct devlink_fmsg_item *msg, struct sk_buff *skb)
7109 int attrtype = DEVLINK_ATTR_FMSG_OBJ_VALUE_DATA;
7112 switch (msg->nla_type) {
7114 /* Always provide flag data, regardless of its value */
7115 tmp = *(bool *) msg->value;
7117 return nla_put_u8(skb, attrtype, tmp);
7119 return nla_put_u8(skb, attrtype, *(u8 *) msg->value);
7121 return nla_put_u32(skb, attrtype, *(u32 *) msg->value);
7123 return nla_put_u64_64bit(skb, attrtype, *(u64 *) msg->value,
7125 case NLA_NUL_STRING:
7126 return nla_put_string(skb, attrtype, (char *) &msg->value);
7128 return nla_put(skb, attrtype, msg->len, (void *) &msg->value);
7135 devlink_fmsg_prepare_skb(struct devlink_fmsg *fmsg, struct sk_buff *skb,
7138 struct devlink_fmsg_item *item;
7139 struct nlattr *fmsg_nlattr;
7143 fmsg_nlattr = nla_nest_start_noflag(skb, DEVLINK_ATTR_FMSG);
7147 list_for_each_entry(item, &fmsg->item_list, list) {
7153 switch (item->attrtype) {
7154 case DEVLINK_ATTR_FMSG_OBJ_NEST_START:
7155 case DEVLINK_ATTR_FMSG_PAIR_NEST_START:
7156 case DEVLINK_ATTR_FMSG_ARR_NEST_START:
7157 case DEVLINK_ATTR_FMSG_NEST_END:
7158 err = nla_put_flag(skb, item->attrtype);
7160 case DEVLINK_ATTR_FMSG_OBJ_VALUE_DATA:
7161 err = devlink_fmsg_item_fill_type(item, skb);
7164 err = devlink_fmsg_item_fill_data(item, skb);
7166 case DEVLINK_ATTR_FMSG_OBJ_NAME:
7167 err = nla_put_string(skb, item->attrtype,
7168 (char *) &item->value);
7180 nla_nest_end(skb, fmsg_nlattr);
7184 static int devlink_fmsg_snd(struct devlink_fmsg *fmsg,
7185 struct genl_info *info,
7186 enum devlink_command cmd, int flags)
7188 struct nlmsghdr *nlh;
7189 struct sk_buff *skb;
7196 int tmp_index = index;
7198 skb = genlmsg_new(GENLMSG_DEFAULT_SIZE, GFP_KERNEL);
7202 hdr = genlmsg_put(skb, info->snd_portid, info->snd_seq,
7203 &devlink_nl_family, flags | NLM_F_MULTI, cmd);
7206 goto nla_put_failure;
7209 err = devlink_fmsg_prepare_skb(fmsg, skb, &index);
7212 else if (err != -EMSGSIZE || tmp_index == index)
7213 goto nla_put_failure;
7215 genlmsg_end(skb, hdr);
7216 err = genlmsg_reply(skb, info);
7221 skb = genlmsg_new(GENLMSG_DEFAULT_SIZE, GFP_KERNEL);
7224 nlh = nlmsg_put(skb, info->snd_portid, info->snd_seq,
7225 NLMSG_DONE, 0, flags | NLM_F_MULTI);
7228 goto nla_put_failure;
7231 return genlmsg_reply(skb, info);
7238 static int devlink_fmsg_dumpit(struct devlink_fmsg *fmsg, struct sk_buff *skb,
7239 struct netlink_callback *cb,
7240 enum devlink_command cmd)
7242 struct devlink_nl_dump_state *state = devlink_dump_state(cb);
7243 int index = state->idx;
7244 int tmp_index = index;
7248 hdr = genlmsg_put(skb, NETLINK_CB(cb->skb).portid, cb->nlh->nlmsg_seq,
7249 &devlink_nl_family, NLM_F_ACK | NLM_F_MULTI, cmd);
7252 goto nla_put_failure;
7255 err = devlink_fmsg_prepare_skb(fmsg, skb, &index);
7256 if ((err && err != -EMSGSIZE) || tmp_index == index)
7257 goto nla_put_failure;
7260 genlmsg_end(skb, hdr);
7264 genlmsg_cancel(skb, hdr);
7268 struct devlink_health_reporter {
7269 struct list_head list;
7271 const struct devlink_health_reporter_ops *ops;
7272 struct devlink *devlink;
7273 struct devlink_port *devlink_port;
7274 struct devlink_fmsg *dump_fmsg;
7275 struct mutex dump_lock; /* lock parallel read/write from dump buffers */
7276 u64 graceful_period;
7284 u64 last_recovery_ts;
7285 refcount_t refcount;
7289 devlink_health_reporter_priv(struct devlink_health_reporter *reporter)
7291 return reporter->priv;
7293 EXPORT_SYMBOL_GPL(devlink_health_reporter_priv);
7295 static struct devlink_health_reporter *
7296 __devlink_health_reporter_find_by_name(struct list_head *reporter_list,
7297 struct mutex *list_lock,
7298 const char *reporter_name)
7300 struct devlink_health_reporter *reporter;
7302 lockdep_assert_held(list_lock);
7303 list_for_each_entry(reporter, reporter_list, list)
7304 if (!strcmp(reporter->ops->name, reporter_name))
7309 static struct devlink_health_reporter *
7310 devlink_health_reporter_find_by_name(struct devlink *devlink,
7311 const char *reporter_name)
7313 return __devlink_health_reporter_find_by_name(&devlink->reporter_list,
7314 &devlink->reporters_lock,
7318 static struct devlink_health_reporter *
7319 devlink_port_health_reporter_find_by_name(struct devlink_port *devlink_port,
7320 const char *reporter_name)
7322 return __devlink_health_reporter_find_by_name(&devlink_port->reporter_list,
7323 &devlink_port->reporters_lock,
7327 static struct devlink_health_reporter *
7328 __devlink_health_reporter_create(struct devlink *devlink,
7329 const struct devlink_health_reporter_ops *ops,
7330 u64 graceful_period, void *priv)
7332 struct devlink_health_reporter *reporter;
7334 if (WARN_ON(graceful_period && !ops->recover))
7335 return ERR_PTR(-EINVAL);
7337 reporter = kzalloc(sizeof(*reporter), GFP_KERNEL);
7339 return ERR_PTR(-ENOMEM);
7341 reporter->priv = priv;
7342 reporter->ops = ops;
7343 reporter->devlink = devlink;
7344 reporter->graceful_period = graceful_period;
7345 reporter->auto_recover = !!ops->recover;
7346 reporter->auto_dump = !!ops->dump;
7347 mutex_init(&reporter->dump_lock);
7348 refcount_set(&reporter->refcount, 1);
7353 * devlink_port_health_reporter_create - create devlink health reporter for
7354 * specified port instance
7356 * @port: devlink_port which should contain the new reporter
7358 * @graceful_period: to avoid recovery loops, in msecs
7361 struct devlink_health_reporter *
7362 devlink_port_health_reporter_create(struct devlink_port *port,
7363 const struct devlink_health_reporter_ops *ops,
7364 u64 graceful_period, void *priv)
7366 struct devlink_health_reporter *reporter;
7368 mutex_lock(&port->reporters_lock);
7369 if (__devlink_health_reporter_find_by_name(&port->reporter_list,
7370 &port->reporters_lock, ops->name)) {
7371 reporter = ERR_PTR(-EEXIST);
7375 reporter = __devlink_health_reporter_create(port->devlink, ops,
7376 graceful_period, priv);
7377 if (IS_ERR(reporter))
7380 reporter->devlink_port = port;
7381 list_add_tail(&reporter->list, &port->reporter_list);
7383 mutex_unlock(&port->reporters_lock);
7386 EXPORT_SYMBOL_GPL(devlink_port_health_reporter_create);
7389 * devlink_health_reporter_create - create devlink health reporter
7393 * @graceful_period: to avoid recovery loops, in msecs
7396 struct devlink_health_reporter *
7397 devlink_health_reporter_create(struct devlink *devlink,
7398 const struct devlink_health_reporter_ops *ops,
7399 u64 graceful_period, void *priv)
7401 struct devlink_health_reporter *reporter;
7403 mutex_lock(&devlink->reporters_lock);
7404 if (devlink_health_reporter_find_by_name(devlink, ops->name)) {
7405 reporter = ERR_PTR(-EEXIST);
7409 reporter = __devlink_health_reporter_create(devlink, ops,
7410 graceful_period, priv);
7411 if (IS_ERR(reporter))
7414 list_add_tail(&reporter->list, &devlink->reporter_list);
7416 mutex_unlock(&devlink->reporters_lock);
7419 EXPORT_SYMBOL_GPL(devlink_health_reporter_create);
7422 devlink_health_reporter_free(struct devlink_health_reporter *reporter)
7424 mutex_destroy(&reporter->dump_lock);
7425 if (reporter->dump_fmsg)
7426 devlink_fmsg_free(reporter->dump_fmsg);
7431 devlink_health_reporter_put(struct devlink_health_reporter *reporter)
7433 if (refcount_dec_and_test(&reporter->refcount))
7434 devlink_health_reporter_free(reporter);
7438 __devlink_health_reporter_destroy(struct devlink_health_reporter *reporter)
7440 list_del(&reporter->list);
7441 devlink_health_reporter_put(reporter);
7445 * devlink_health_reporter_destroy - destroy devlink health reporter
7447 * @reporter: devlink health reporter to destroy
7450 devlink_health_reporter_destroy(struct devlink_health_reporter *reporter)
7452 struct mutex *lock = &reporter->devlink->reporters_lock;
7455 __devlink_health_reporter_destroy(reporter);
7458 EXPORT_SYMBOL_GPL(devlink_health_reporter_destroy);
7461 * devlink_port_health_reporter_destroy - destroy devlink port health reporter
7463 * @reporter: devlink health reporter to destroy
7466 devlink_port_health_reporter_destroy(struct devlink_health_reporter *reporter)
7468 struct mutex *lock = &reporter->devlink_port->reporters_lock;
7471 __devlink_health_reporter_destroy(reporter);
7474 EXPORT_SYMBOL_GPL(devlink_port_health_reporter_destroy);
7477 devlink_nl_health_reporter_fill(struct sk_buff *msg,
7478 struct devlink_health_reporter *reporter,
7479 enum devlink_command cmd, u32 portid,
7482 struct devlink *devlink = reporter->devlink;
7483 struct nlattr *reporter_attr;
7486 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
7490 if (devlink_nl_put_handle(msg, devlink))
7491 goto genlmsg_cancel;
7493 if (reporter->devlink_port) {
7494 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_INDEX, reporter->devlink_port->index))
7495 goto genlmsg_cancel;
7497 reporter_attr = nla_nest_start_noflag(msg,
7498 DEVLINK_ATTR_HEALTH_REPORTER);
7500 goto genlmsg_cancel;
7501 if (nla_put_string(msg, DEVLINK_ATTR_HEALTH_REPORTER_NAME,
7502 reporter->ops->name))
7503 goto reporter_nest_cancel;
7504 if (nla_put_u8(msg, DEVLINK_ATTR_HEALTH_REPORTER_STATE,
7505 reporter->health_state))
7506 goto reporter_nest_cancel;
7507 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_HEALTH_REPORTER_ERR_COUNT,
7508 reporter->error_count, DEVLINK_ATTR_PAD))
7509 goto reporter_nest_cancel;
7510 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_HEALTH_REPORTER_RECOVER_COUNT,
7511 reporter->recovery_count, DEVLINK_ATTR_PAD))
7512 goto reporter_nest_cancel;
7513 if (reporter->ops->recover &&
7514 nla_put_u64_64bit(msg, DEVLINK_ATTR_HEALTH_REPORTER_GRACEFUL_PERIOD,
7515 reporter->graceful_period,
7517 goto reporter_nest_cancel;
7518 if (reporter->ops->recover &&
7519 nla_put_u8(msg, DEVLINK_ATTR_HEALTH_REPORTER_AUTO_RECOVER,
7520 reporter->auto_recover))
7521 goto reporter_nest_cancel;
7522 if (reporter->dump_fmsg &&
7523 nla_put_u64_64bit(msg, DEVLINK_ATTR_HEALTH_REPORTER_DUMP_TS,
7524 jiffies_to_msecs(reporter->dump_ts),
7526 goto reporter_nest_cancel;
7527 if (reporter->dump_fmsg &&
7528 nla_put_u64_64bit(msg, DEVLINK_ATTR_HEALTH_REPORTER_DUMP_TS_NS,
7529 reporter->dump_real_ts, DEVLINK_ATTR_PAD))
7530 goto reporter_nest_cancel;
7531 if (reporter->ops->dump &&
7532 nla_put_u8(msg, DEVLINK_ATTR_HEALTH_REPORTER_AUTO_DUMP,
7533 reporter->auto_dump))
7534 goto reporter_nest_cancel;
7536 nla_nest_end(msg, reporter_attr);
7537 genlmsg_end(msg, hdr);
7540 reporter_nest_cancel:
7541 nla_nest_end(msg, reporter_attr);
7543 genlmsg_cancel(msg, hdr);
7547 static void devlink_recover_notify(struct devlink_health_reporter *reporter,
7548 enum devlink_command cmd)
7550 struct devlink *devlink = reporter->devlink;
7551 struct sk_buff *msg;
7554 WARN_ON(cmd != DEVLINK_CMD_HEALTH_REPORTER_RECOVER);
7555 WARN_ON(!xa_get_mark(&devlinks, devlink->index, DEVLINK_REGISTERED));
7557 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
7561 err = devlink_nl_health_reporter_fill(msg, reporter, cmd, 0, 0, 0);
7567 genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink), msg,
7568 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
7572 devlink_health_reporter_recovery_done(struct devlink_health_reporter *reporter)
7574 reporter->recovery_count++;
7575 reporter->last_recovery_ts = jiffies;
7577 EXPORT_SYMBOL_GPL(devlink_health_reporter_recovery_done);
7580 devlink_health_reporter_recover(struct devlink_health_reporter *reporter,
7581 void *priv_ctx, struct netlink_ext_ack *extack)
7585 if (reporter->health_state == DEVLINK_HEALTH_REPORTER_STATE_HEALTHY)
7588 if (!reporter->ops->recover)
7591 err = reporter->ops->recover(reporter, priv_ctx, extack);
7595 devlink_health_reporter_recovery_done(reporter);
7596 reporter->health_state = DEVLINK_HEALTH_REPORTER_STATE_HEALTHY;
7597 devlink_recover_notify(reporter, DEVLINK_CMD_HEALTH_REPORTER_RECOVER);
7603 devlink_health_dump_clear(struct devlink_health_reporter *reporter)
7605 if (!reporter->dump_fmsg)
7607 devlink_fmsg_free(reporter->dump_fmsg);
7608 reporter->dump_fmsg = NULL;
7611 static int devlink_health_do_dump(struct devlink_health_reporter *reporter,
7613 struct netlink_ext_ack *extack)
7617 if (!reporter->ops->dump)
7620 if (reporter->dump_fmsg)
7623 reporter->dump_fmsg = devlink_fmsg_alloc();
7624 if (!reporter->dump_fmsg) {
7629 err = devlink_fmsg_obj_nest_start(reporter->dump_fmsg);
7633 err = reporter->ops->dump(reporter, reporter->dump_fmsg,
7638 err = devlink_fmsg_obj_nest_end(reporter->dump_fmsg);
7642 reporter->dump_ts = jiffies;
7643 reporter->dump_real_ts = ktime_get_real_ns();
7648 devlink_health_dump_clear(reporter);
7652 int devlink_health_report(struct devlink_health_reporter *reporter,
7653 const char *msg, void *priv_ctx)
7655 enum devlink_health_reporter_state prev_health_state;
7656 struct devlink *devlink = reporter->devlink;
7657 unsigned long recover_ts_threshold;
7660 /* write a log message of the current error */
7662 trace_devlink_health_report(devlink, reporter->ops->name, msg);
7663 reporter->error_count++;
7664 prev_health_state = reporter->health_state;
7665 reporter->health_state = DEVLINK_HEALTH_REPORTER_STATE_ERROR;
7666 devlink_recover_notify(reporter, DEVLINK_CMD_HEALTH_REPORTER_RECOVER);
7668 /* abort if the previous error wasn't recovered */
7669 recover_ts_threshold = reporter->last_recovery_ts +
7670 msecs_to_jiffies(reporter->graceful_period);
7671 if (reporter->auto_recover &&
7672 (prev_health_state != DEVLINK_HEALTH_REPORTER_STATE_HEALTHY ||
7673 (reporter->last_recovery_ts && reporter->recovery_count &&
7674 time_is_after_jiffies(recover_ts_threshold)))) {
7675 trace_devlink_health_recover_aborted(devlink,
7676 reporter->ops->name,
7677 reporter->health_state,
7679 reporter->last_recovery_ts);
7683 if (reporter->auto_dump) {
7684 mutex_lock(&reporter->dump_lock);
7685 /* store current dump of current error, for later analysis */
7686 devlink_health_do_dump(reporter, priv_ctx, NULL);
7687 mutex_unlock(&reporter->dump_lock);
7690 if (!reporter->auto_recover)
7694 ret = devlink_health_reporter_recover(reporter, priv_ctx, NULL);
7695 devl_unlock(devlink);
7699 EXPORT_SYMBOL_GPL(devlink_health_report);
7701 static struct devlink_health_reporter *
7702 devlink_health_reporter_get_from_attrs(struct devlink *devlink,
7703 struct nlattr **attrs)
7705 struct devlink_health_reporter *reporter;
7706 struct devlink_port *devlink_port;
7707 char *reporter_name;
7709 if (!attrs[DEVLINK_ATTR_HEALTH_REPORTER_NAME])
7712 reporter_name = nla_data(attrs[DEVLINK_ATTR_HEALTH_REPORTER_NAME]);
7713 devlink_port = devlink_port_get_from_attrs(devlink, attrs);
7714 if (IS_ERR(devlink_port)) {
7715 mutex_lock(&devlink->reporters_lock);
7716 reporter = devlink_health_reporter_find_by_name(devlink, reporter_name);
7718 refcount_inc(&reporter->refcount);
7719 mutex_unlock(&devlink->reporters_lock);
7721 mutex_lock(&devlink_port->reporters_lock);
7722 reporter = devlink_port_health_reporter_find_by_name(devlink_port, reporter_name);
7724 refcount_inc(&reporter->refcount);
7725 mutex_unlock(&devlink_port->reporters_lock);
7731 static struct devlink_health_reporter *
7732 devlink_health_reporter_get_from_info(struct devlink *devlink,
7733 struct genl_info *info)
7735 return devlink_health_reporter_get_from_attrs(devlink, info->attrs);
7738 static struct devlink_health_reporter *
7739 devlink_health_reporter_get_from_cb(struct netlink_callback *cb)
7741 const struct genl_dumpit_info *info = genl_dumpit_info(cb);
7742 struct devlink_health_reporter *reporter;
7743 struct nlattr **attrs = info->attrs;
7744 struct devlink *devlink;
7746 devlink = devlink_get_from_attrs_lock(sock_net(cb->skb->sk), attrs);
7747 if (IS_ERR(devlink))
7749 devl_unlock(devlink);
7751 reporter = devlink_health_reporter_get_from_attrs(devlink, attrs);
7752 devlink_put(devlink);
7757 devlink_health_reporter_state_update(struct devlink_health_reporter *reporter,
7758 enum devlink_health_reporter_state state)
7760 if (WARN_ON(state != DEVLINK_HEALTH_REPORTER_STATE_HEALTHY &&
7761 state != DEVLINK_HEALTH_REPORTER_STATE_ERROR))
7764 if (reporter->health_state == state)
7767 reporter->health_state = state;
7768 trace_devlink_health_reporter_state_update(reporter->devlink,
7769 reporter->ops->name, state);
7770 devlink_recover_notify(reporter, DEVLINK_CMD_HEALTH_REPORTER_RECOVER);
7772 EXPORT_SYMBOL_GPL(devlink_health_reporter_state_update);
7774 static int devlink_nl_cmd_health_reporter_get_doit(struct sk_buff *skb,
7775 struct genl_info *info)
7777 struct devlink *devlink = info->user_ptr[0];
7778 struct devlink_health_reporter *reporter;
7779 struct sk_buff *msg;
7782 reporter = devlink_health_reporter_get_from_info(devlink, info);
7786 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
7792 err = devlink_nl_health_reporter_fill(msg, reporter,
7793 DEVLINK_CMD_HEALTH_REPORTER_GET,
7794 info->snd_portid, info->snd_seq,
7801 err = genlmsg_reply(msg, info);
7803 devlink_health_reporter_put(reporter);
7808 devlink_nl_cmd_health_reporter_get_dumpit(struct sk_buff *msg,
7809 struct netlink_callback *cb)
7811 struct devlink_nl_dump_state *state = devlink_dump_state(cb);
7812 struct devlink *devlink;
7815 devlink_dump_for_each_instance_get(msg, state, devlink) {
7816 struct devlink_health_reporter *reporter;
7817 struct devlink_port *port;
7818 unsigned long port_index;
7821 mutex_lock(&devlink->reporters_lock);
7822 if (!devl_is_registered(devlink)) {
7823 mutex_unlock(&devlink->reporters_lock);
7824 devlink_put(devlink);
7828 list_for_each_entry(reporter, &devlink->reporter_list,
7830 if (idx < state->idx) {
7834 err = devlink_nl_health_reporter_fill(
7835 msg, reporter, DEVLINK_CMD_HEALTH_REPORTER_GET,
7836 NETLINK_CB(cb->skb).portid, cb->nlh->nlmsg_seq,
7839 mutex_unlock(&devlink->reporters_lock);
7840 devlink_put(devlink);
7846 mutex_unlock(&devlink->reporters_lock);
7849 if (!devl_is_registered(devlink))
7852 xa_for_each(&devlink->ports, port_index, port) {
7853 mutex_lock(&port->reporters_lock);
7854 list_for_each_entry(reporter, &port->reporter_list, list) {
7855 if (idx < state->idx) {
7859 err = devlink_nl_health_reporter_fill(
7861 DEVLINK_CMD_HEALTH_REPORTER_GET,
7862 NETLINK_CB(cb->skb).portid,
7863 cb->nlh->nlmsg_seq, NLM_F_MULTI);
7865 mutex_unlock(&port->reporters_lock);
7866 devl_unlock(devlink);
7867 devlink_put(devlink);
7873 mutex_unlock(&port->reporters_lock);
7876 devl_unlock(devlink);
7877 devlink_put(devlink);
7884 devlink_nl_cmd_health_reporter_set_doit(struct sk_buff *skb,
7885 struct genl_info *info)
7887 struct devlink *devlink = info->user_ptr[0];
7888 struct devlink_health_reporter *reporter;
7891 reporter = devlink_health_reporter_get_from_info(devlink, info);
7895 if (!reporter->ops->recover &&
7896 (info->attrs[DEVLINK_ATTR_HEALTH_REPORTER_GRACEFUL_PERIOD] ||
7897 info->attrs[DEVLINK_ATTR_HEALTH_REPORTER_AUTO_RECOVER])) {
7901 if (!reporter->ops->dump &&
7902 info->attrs[DEVLINK_ATTR_HEALTH_REPORTER_AUTO_DUMP]) {
7907 if (info->attrs[DEVLINK_ATTR_HEALTH_REPORTER_GRACEFUL_PERIOD])
7908 reporter->graceful_period =
7909 nla_get_u64(info->attrs[DEVLINK_ATTR_HEALTH_REPORTER_GRACEFUL_PERIOD]);
7911 if (info->attrs[DEVLINK_ATTR_HEALTH_REPORTER_AUTO_RECOVER])
7912 reporter->auto_recover =
7913 nla_get_u8(info->attrs[DEVLINK_ATTR_HEALTH_REPORTER_AUTO_RECOVER]);
7915 if (info->attrs[DEVLINK_ATTR_HEALTH_REPORTER_AUTO_DUMP])
7916 reporter->auto_dump =
7917 nla_get_u8(info->attrs[DEVLINK_ATTR_HEALTH_REPORTER_AUTO_DUMP]);
7919 devlink_health_reporter_put(reporter);
7922 devlink_health_reporter_put(reporter);
7926 static int devlink_nl_cmd_health_reporter_recover_doit(struct sk_buff *skb,
7927 struct genl_info *info)
7929 struct devlink *devlink = info->user_ptr[0];
7930 struct devlink_health_reporter *reporter;
7933 reporter = devlink_health_reporter_get_from_info(devlink, info);
7937 err = devlink_health_reporter_recover(reporter, NULL, info->extack);
7939 devlink_health_reporter_put(reporter);
7943 static int devlink_nl_cmd_health_reporter_diagnose_doit(struct sk_buff *skb,
7944 struct genl_info *info)
7946 struct devlink *devlink = info->user_ptr[0];
7947 struct devlink_health_reporter *reporter;
7948 struct devlink_fmsg *fmsg;
7951 reporter = devlink_health_reporter_get_from_info(devlink, info);
7955 if (!reporter->ops->diagnose) {
7956 devlink_health_reporter_put(reporter);
7960 fmsg = devlink_fmsg_alloc();
7962 devlink_health_reporter_put(reporter);
7966 err = devlink_fmsg_obj_nest_start(fmsg);
7970 err = reporter->ops->diagnose(reporter, fmsg, info->extack);
7974 err = devlink_fmsg_obj_nest_end(fmsg);
7978 err = devlink_fmsg_snd(fmsg, info,
7979 DEVLINK_CMD_HEALTH_REPORTER_DIAGNOSE, 0);
7982 devlink_fmsg_free(fmsg);
7983 devlink_health_reporter_put(reporter);
7988 devlink_nl_cmd_health_reporter_dump_get_dumpit(struct sk_buff *skb,
7989 struct netlink_callback *cb)
7991 struct devlink_nl_dump_state *state = devlink_dump_state(cb);
7992 struct devlink_health_reporter *reporter;
7995 reporter = devlink_health_reporter_get_from_cb(cb);
7999 if (!reporter->ops->dump) {
8003 mutex_lock(&reporter->dump_lock);
8005 err = devlink_health_do_dump(reporter, NULL, cb->extack);
8008 state->dump_ts = reporter->dump_ts;
8010 if (!reporter->dump_fmsg || state->dump_ts != reporter->dump_ts) {
8011 NL_SET_ERR_MSG_MOD(cb->extack, "Dump trampled, please retry");
8016 err = devlink_fmsg_dumpit(reporter->dump_fmsg, skb, cb,
8017 DEVLINK_CMD_HEALTH_REPORTER_DUMP_GET);
8019 mutex_unlock(&reporter->dump_lock);
8021 devlink_health_reporter_put(reporter);
8026 devlink_nl_cmd_health_reporter_dump_clear_doit(struct sk_buff *skb,
8027 struct genl_info *info)
8029 struct devlink *devlink = info->user_ptr[0];
8030 struct devlink_health_reporter *reporter;
8032 reporter = devlink_health_reporter_get_from_info(devlink, info);
8036 if (!reporter->ops->dump) {
8037 devlink_health_reporter_put(reporter);
8041 mutex_lock(&reporter->dump_lock);
8042 devlink_health_dump_clear(reporter);
8043 mutex_unlock(&reporter->dump_lock);
8044 devlink_health_reporter_put(reporter);
8048 static int devlink_nl_cmd_health_reporter_test_doit(struct sk_buff *skb,
8049 struct genl_info *info)
8051 struct devlink *devlink = info->user_ptr[0];
8052 struct devlink_health_reporter *reporter;
8055 reporter = devlink_health_reporter_get_from_info(devlink, info);
8059 if (!reporter->ops->test) {
8060 devlink_health_reporter_put(reporter);
8064 err = reporter->ops->test(reporter, info->extack);
8066 devlink_health_reporter_put(reporter);
8070 struct devlink_stats {
8071 u64_stats_t rx_bytes;
8072 u64_stats_t rx_packets;
8073 struct u64_stats_sync syncp;
8077 * struct devlink_trap_policer_item - Packet trap policer attributes.
8078 * @policer: Immutable packet trap policer attributes.
8079 * @rate: Rate in packets / sec.
8080 * @burst: Burst size in packets.
8081 * @list: trap_policer_list member.
8083 * Describes packet trap policer attributes. Created by devlink during trap
8084 * policer registration.
8086 struct devlink_trap_policer_item {
8087 const struct devlink_trap_policer *policer;
8090 struct list_head list;
8094 * struct devlink_trap_group_item - Packet trap group attributes.
8095 * @group: Immutable packet trap group attributes.
8096 * @policer_item: Associated policer item. Can be NULL.
8097 * @list: trap_group_list member.
8098 * @stats: Trap group statistics.
8100 * Describes packet trap group attributes. Created by devlink during trap
8101 * group registration.
8103 struct devlink_trap_group_item {
8104 const struct devlink_trap_group *group;
8105 struct devlink_trap_policer_item *policer_item;
8106 struct list_head list;
8107 struct devlink_stats __percpu *stats;
8111 * struct devlink_trap_item - Packet trap attributes.
8112 * @trap: Immutable packet trap attributes.
8113 * @group_item: Associated group item.
8114 * @list: trap_list member.
8115 * @action: Trap action.
8116 * @stats: Trap statistics.
8117 * @priv: Driver private information.
8119 * Describes both mutable and immutable packet trap attributes. Created by
8120 * devlink during trap registration and used for all trap related operations.
8122 struct devlink_trap_item {
8123 const struct devlink_trap *trap;
8124 struct devlink_trap_group_item *group_item;
8125 struct list_head list;
8126 enum devlink_trap_action action;
8127 struct devlink_stats __percpu *stats;
8131 static struct devlink_trap_policer_item *
8132 devlink_trap_policer_item_lookup(struct devlink *devlink, u32 id)
8134 struct devlink_trap_policer_item *policer_item;
8136 list_for_each_entry(policer_item, &devlink->trap_policer_list, list) {
8137 if (policer_item->policer->id == id)
8138 return policer_item;
8144 static struct devlink_trap_item *
8145 devlink_trap_item_lookup(struct devlink *devlink, const char *name)
8147 struct devlink_trap_item *trap_item;
8149 list_for_each_entry(trap_item, &devlink->trap_list, list) {
8150 if (!strcmp(trap_item->trap->name, name))
8157 static struct devlink_trap_item *
8158 devlink_trap_item_get_from_info(struct devlink *devlink,
8159 struct genl_info *info)
8161 struct nlattr *attr;
8163 if (!info->attrs[DEVLINK_ATTR_TRAP_NAME])
8165 attr = info->attrs[DEVLINK_ATTR_TRAP_NAME];
8167 return devlink_trap_item_lookup(devlink, nla_data(attr));
8171 devlink_trap_action_get_from_info(struct genl_info *info,
8172 enum devlink_trap_action *p_trap_action)
8176 val = nla_get_u8(info->attrs[DEVLINK_ATTR_TRAP_ACTION]);
8178 case DEVLINK_TRAP_ACTION_DROP:
8179 case DEVLINK_TRAP_ACTION_TRAP:
8180 case DEVLINK_TRAP_ACTION_MIRROR:
8181 *p_trap_action = val;
8190 static int devlink_trap_metadata_put(struct sk_buff *msg,
8191 const struct devlink_trap *trap)
8193 struct nlattr *attr;
8195 attr = nla_nest_start(msg, DEVLINK_ATTR_TRAP_METADATA);
8199 if ((trap->metadata_cap & DEVLINK_TRAP_METADATA_TYPE_F_IN_PORT) &&
8200 nla_put_flag(msg, DEVLINK_ATTR_TRAP_METADATA_TYPE_IN_PORT))
8201 goto nla_put_failure;
8202 if ((trap->metadata_cap & DEVLINK_TRAP_METADATA_TYPE_F_FA_COOKIE) &&
8203 nla_put_flag(msg, DEVLINK_ATTR_TRAP_METADATA_TYPE_FA_COOKIE))
8204 goto nla_put_failure;
8206 nla_nest_end(msg, attr);
8211 nla_nest_cancel(msg, attr);
8215 static void devlink_trap_stats_read(struct devlink_stats __percpu *trap_stats,
8216 struct devlink_stats *stats)
8220 memset(stats, 0, sizeof(*stats));
8221 for_each_possible_cpu(i) {
8222 struct devlink_stats *cpu_stats;
8223 u64 rx_packets, rx_bytes;
8226 cpu_stats = per_cpu_ptr(trap_stats, i);
8228 start = u64_stats_fetch_begin(&cpu_stats->syncp);
8229 rx_packets = u64_stats_read(&cpu_stats->rx_packets);
8230 rx_bytes = u64_stats_read(&cpu_stats->rx_bytes);
8231 } while (u64_stats_fetch_retry(&cpu_stats->syncp, start));
8233 u64_stats_add(&stats->rx_packets, rx_packets);
8234 u64_stats_add(&stats->rx_bytes, rx_bytes);
8239 devlink_trap_group_stats_put(struct sk_buff *msg,
8240 struct devlink_stats __percpu *trap_stats)
8242 struct devlink_stats stats;
8243 struct nlattr *attr;
8245 devlink_trap_stats_read(trap_stats, &stats);
8247 attr = nla_nest_start(msg, DEVLINK_ATTR_STATS);
8251 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_STATS_RX_PACKETS,
8252 u64_stats_read(&stats.rx_packets),
8254 goto nla_put_failure;
8256 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_STATS_RX_BYTES,
8257 u64_stats_read(&stats.rx_bytes),
8259 goto nla_put_failure;
8261 nla_nest_end(msg, attr);
8266 nla_nest_cancel(msg, attr);
8270 static int devlink_trap_stats_put(struct sk_buff *msg, struct devlink *devlink,
8271 const struct devlink_trap_item *trap_item)
8273 struct devlink_stats stats;
8274 struct nlattr *attr;
8278 if (devlink->ops->trap_drop_counter_get) {
8279 err = devlink->ops->trap_drop_counter_get(devlink,
8286 devlink_trap_stats_read(trap_item->stats, &stats);
8288 attr = nla_nest_start(msg, DEVLINK_ATTR_STATS);
8292 if (devlink->ops->trap_drop_counter_get &&
8293 nla_put_u64_64bit(msg, DEVLINK_ATTR_STATS_RX_DROPPED, drops,
8295 goto nla_put_failure;
8297 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_STATS_RX_PACKETS,
8298 u64_stats_read(&stats.rx_packets),
8300 goto nla_put_failure;
8302 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_STATS_RX_BYTES,
8303 u64_stats_read(&stats.rx_bytes),
8305 goto nla_put_failure;
8307 nla_nest_end(msg, attr);
8312 nla_nest_cancel(msg, attr);
8316 static int devlink_nl_trap_fill(struct sk_buff *msg, struct devlink *devlink,
8317 const struct devlink_trap_item *trap_item,
8318 enum devlink_command cmd, u32 portid, u32 seq,
8321 struct devlink_trap_group_item *group_item = trap_item->group_item;
8325 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
8329 if (devlink_nl_put_handle(msg, devlink))
8330 goto nla_put_failure;
8332 if (nla_put_string(msg, DEVLINK_ATTR_TRAP_GROUP_NAME,
8333 group_item->group->name))
8334 goto nla_put_failure;
8336 if (nla_put_string(msg, DEVLINK_ATTR_TRAP_NAME, trap_item->trap->name))
8337 goto nla_put_failure;
8339 if (nla_put_u8(msg, DEVLINK_ATTR_TRAP_TYPE, trap_item->trap->type))
8340 goto nla_put_failure;
8342 if (trap_item->trap->generic &&
8343 nla_put_flag(msg, DEVLINK_ATTR_TRAP_GENERIC))
8344 goto nla_put_failure;
8346 if (nla_put_u8(msg, DEVLINK_ATTR_TRAP_ACTION, trap_item->action))
8347 goto nla_put_failure;
8349 err = devlink_trap_metadata_put(msg, trap_item->trap);
8351 goto nla_put_failure;
8353 err = devlink_trap_stats_put(msg, devlink, trap_item);
8355 goto nla_put_failure;
8357 genlmsg_end(msg, hdr);
8362 genlmsg_cancel(msg, hdr);
8366 static int devlink_nl_cmd_trap_get_doit(struct sk_buff *skb,
8367 struct genl_info *info)
8369 struct netlink_ext_ack *extack = info->extack;
8370 struct devlink *devlink = info->user_ptr[0];
8371 struct devlink_trap_item *trap_item;
8372 struct sk_buff *msg;
8375 if (list_empty(&devlink->trap_list))
8378 trap_item = devlink_trap_item_get_from_info(devlink, info);
8380 NL_SET_ERR_MSG_MOD(extack, "Device did not register this trap");
8384 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
8388 err = devlink_nl_trap_fill(msg, devlink, trap_item,
8389 DEVLINK_CMD_TRAP_NEW, info->snd_portid,
8394 return genlmsg_reply(msg, info);
8402 devlink_nl_cmd_trap_get_dump_one(struct sk_buff *msg, struct devlink *devlink,
8403 struct netlink_callback *cb)
8405 struct devlink_nl_dump_state *state = devlink_dump_state(cb);
8406 struct devlink_trap_item *trap_item;
8410 list_for_each_entry(trap_item, &devlink->trap_list, list) {
8411 if (idx < state->idx) {
8415 err = devlink_nl_trap_fill(msg, devlink, trap_item,
8416 DEVLINK_CMD_TRAP_NEW,
8417 NETLINK_CB(cb->skb).portid,
8430 const struct devlink_gen_cmd devl_gen_trap = {
8431 .dump_one = devlink_nl_cmd_trap_get_dump_one,
8434 static int __devlink_trap_action_set(struct devlink *devlink,
8435 struct devlink_trap_item *trap_item,
8436 enum devlink_trap_action trap_action,
8437 struct netlink_ext_ack *extack)
8441 if (trap_item->action != trap_action &&
8442 trap_item->trap->type != DEVLINK_TRAP_TYPE_DROP) {
8443 NL_SET_ERR_MSG_MOD(extack, "Cannot change action of non-drop traps. Skipping");
8447 err = devlink->ops->trap_action_set(devlink, trap_item->trap,
8448 trap_action, extack);
8452 trap_item->action = trap_action;
8457 static int devlink_trap_action_set(struct devlink *devlink,
8458 struct devlink_trap_item *trap_item,
8459 struct genl_info *info)
8461 enum devlink_trap_action trap_action;
8464 if (!info->attrs[DEVLINK_ATTR_TRAP_ACTION])
8467 err = devlink_trap_action_get_from_info(info, &trap_action);
8469 NL_SET_ERR_MSG_MOD(info->extack, "Invalid trap action");
8473 return __devlink_trap_action_set(devlink, trap_item, trap_action,
8477 static int devlink_nl_cmd_trap_set_doit(struct sk_buff *skb,
8478 struct genl_info *info)
8480 struct netlink_ext_ack *extack = info->extack;
8481 struct devlink *devlink = info->user_ptr[0];
8482 struct devlink_trap_item *trap_item;
8484 if (list_empty(&devlink->trap_list))
8487 trap_item = devlink_trap_item_get_from_info(devlink, info);
8489 NL_SET_ERR_MSG_MOD(extack, "Device did not register this trap");
8493 return devlink_trap_action_set(devlink, trap_item, info);
8496 static struct devlink_trap_group_item *
8497 devlink_trap_group_item_lookup(struct devlink *devlink, const char *name)
8499 struct devlink_trap_group_item *group_item;
8501 list_for_each_entry(group_item, &devlink->trap_group_list, list) {
8502 if (!strcmp(group_item->group->name, name))
8509 static struct devlink_trap_group_item *
8510 devlink_trap_group_item_lookup_by_id(struct devlink *devlink, u16 id)
8512 struct devlink_trap_group_item *group_item;
8514 list_for_each_entry(group_item, &devlink->trap_group_list, list) {
8515 if (group_item->group->id == id)
8522 static struct devlink_trap_group_item *
8523 devlink_trap_group_item_get_from_info(struct devlink *devlink,
8524 struct genl_info *info)
8528 if (!info->attrs[DEVLINK_ATTR_TRAP_GROUP_NAME])
8530 name = nla_data(info->attrs[DEVLINK_ATTR_TRAP_GROUP_NAME]);
8532 return devlink_trap_group_item_lookup(devlink, name);
8536 devlink_nl_trap_group_fill(struct sk_buff *msg, struct devlink *devlink,
8537 const struct devlink_trap_group_item *group_item,
8538 enum devlink_command cmd, u32 portid, u32 seq,
8544 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
8548 if (devlink_nl_put_handle(msg, devlink))
8549 goto nla_put_failure;
8551 if (nla_put_string(msg, DEVLINK_ATTR_TRAP_GROUP_NAME,
8552 group_item->group->name))
8553 goto nla_put_failure;
8555 if (group_item->group->generic &&
8556 nla_put_flag(msg, DEVLINK_ATTR_TRAP_GENERIC))
8557 goto nla_put_failure;
8559 if (group_item->policer_item &&
8560 nla_put_u32(msg, DEVLINK_ATTR_TRAP_POLICER_ID,
8561 group_item->policer_item->policer->id))
8562 goto nla_put_failure;
8564 err = devlink_trap_group_stats_put(msg, group_item->stats);
8566 goto nla_put_failure;
8568 genlmsg_end(msg, hdr);
8573 genlmsg_cancel(msg, hdr);
8577 static int devlink_nl_cmd_trap_group_get_doit(struct sk_buff *skb,
8578 struct genl_info *info)
8580 struct netlink_ext_ack *extack = info->extack;
8581 struct devlink *devlink = info->user_ptr[0];
8582 struct devlink_trap_group_item *group_item;
8583 struct sk_buff *msg;
8586 if (list_empty(&devlink->trap_group_list))
8589 group_item = devlink_trap_group_item_get_from_info(devlink, info);
8591 NL_SET_ERR_MSG_MOD(extack, "Device did not register this trap group");
8595 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
8599 err = devlink_nl_trap_group_fill(msg, devlink, group_item,
8600 DEVLINK_CMD_TRAP_GROUP_NEW,
8601 info->snd_portid, info->snd_seq, 0);
8603 goto err_trap_group_fill;
8605 return genlmsg_reply(msg, info);
8607 err_trap_group_fill:
8613 devlink_nl_cmd_trap_group_get_dump_one(struct sk_buff *msg,
8614 struct devlink *devlink,
8615 struct netlink_callback *cb)
8617 struct devlink_nl_dump_state *state = devlink_dump_state(cb);
8618 struct devlink_trap_group_item *group_item;
8623 list_for_each_entry(group_item, &devlink->trap_group_list, list) {
8624 if (idx < state->idx) {
8628 err = devlink_nl_trap_group_fill(msg, devlink, group_item,
8629 DEVLINK_CMD_TRAP_GROUP_NEW,
8630 NETLINK_CB(cb->skb).portid,
8643 const struct devlink_gen_cmd devl_gen_trap_group = {
8644 .dump_one = devlink_nl_cmd_trap_group_get_dump_one,
8648 __devlink_trap_group_action_set(struct devlink *devlink,
8649 struct devlink_trap_group_item *group_item,
8650 enum devlink_trap_action trap_action,
8651 struct netlink_ext_ack *extack)
8653 const char *group_name = group_item->group->name;
8654 struct devlink_trap_item *trap_item;
8657 if (devlink->ops->trap_group_action_set) {
8658 err = devlink->ops->trap_group_action_set(devlink, group_item->group,
8659 trap_action, extack);
8663 list_for_each_entry(trap_item, &devlink->trap_list, list) {
8664 if (strcmp(trap_item->group_item->group->name, group_name))
8666 if (trap_item->action != trap_action &&
8667 trap_item->trap->type != DEVLINK_TRAP_TYPE_DROP)
8669 trap_item->action = trap_action;
8675 list_for_each_entry(trap_item, &devlink->trap_list, list) {
8676 if (strcmp(trap_item->group_item->group->name, group_name))
8678 err = __devlink_trap_action_set(devlink, trap_item,
8679 trap_action, extack);
8688 devlink_trap_group_action_set(struct devlink *devlink,
8689 struct devlink_trap_group_item *group_item,
8690 struct genl_info *info, bool *p_modified)
8692 enum devlink_trap_action trap_action;
8695 if (!info->attrs[DEVLINK_ATTR_TRAP_ACTION])
8698 err = devlink_trap_action_get_from_info(info, &trap_action);
8700 NL_SET_ERR_MSG_MOD(info->extack, "Invalid trap action");
8704 err = __devlink_trap_group_action_set(devlink, group_item, trap_action,
8714 static int devlink_trap_group_set(struct devlink *devlink,
8715 struct devlink_trap_group_item *group_item,
8716 struct genl_info *info)
8718 struct devlink_trap_policer_item *policer_item;
8719 struct netlink_ext_ack *extack = info->extack;
8720 const struct devlink_trap_policer *policer;
8721 struct nlattr **attrs = info->attrs;
8725 if (!attrs[DEVLINK_ATTR_TRAP_POLICER_ID])
8728 if (!devlink->ops->trap_group_set)
8731 policer_id = nla_get_u32(attrs[DEVLINK_ATTR_TRAP_POLICER_ID]);
8732 policer_item = devlink_trap_policer_item_lookup(devlink, policer_id);
8733 if (policer_id && !policer_item) {
8734 NL_SET_ERR_MSG_MOD(extack, "Device did not register this trap policer");
8737 policer = policer_item ? policer_item->policer : NULL;
8739 err = devlink->ops->trap_group_set(devlink, group_item->group, policer,
8744 group_item->policer_item = policer_item;
8749 static int devlink_nl_cmd_trap_group_set_doit(struct sk_buff *skb,
8750 struct genl_info *info)
8752 struct netlink_ext_ack *extack = info->extack;
8753 struct devlink *devlink = info->user_ptr[0];
8754 struct devlink_trap_group_item *group_item;
8755 bool modified = false;
8758 if (list_empty(&devlink->trap_group_list))
8761 group_item = devlink_trap_group_item_get_from_info(devlink, info);
8763 NL_SET_ERR_MSG_MOD(extack, "Device did not register this trap group");
8767 err = devlink_trap_group_action_set(devlink, group_item, info,
8772 err = devlink_trap_group_set(devlink, group_item, info);
8774 goto err_trap_group_set;
8780 NL_SET_ERR_MSG_MOD(extack, "Trap group set failed, but some changes were committed already");
8784 static struct devlink_trap_policer_item *
8785 devlink_trap_policer_item_get_from_info(struct devlink *devlink,
8786 struct genl_info *info)
8790 if (!info->attrs[DEVLINK_ATTR_TRAP_POLICER_ID])
8792 id = nla_get_u32(info->attrs[DEVLINK_ATTR_TRAP_POLICER_ID]);
8794 return devlink_trap_policer_item_lookup(devlink, id);
8798 devlink_trap_policer_stats_put(struct sk_buff *msg, struct devlink *devlink,
8799 const struct devlink_trap_policer *policer)
8801 struct nlattr *attr;
8805 if (!devlink->ops->trap_policer_counter_get)
8808 err = devlink->ops->trap_policer_counter_get(devlink, policer, &drops);
8812 attr = nla_nest_start(msg, DEVLINK_ATTR_STATS);
8816 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_STATS_RX_DROPPED, drops,
8818 goto nla_put_failure;
8820 nla_nest_end(msg, attr);
8825 nla_nest_cancel(msg, attr);
8830 devlink_nl_trap_policer_fill(struct sk_buff *msg, struct devlink *devlink,
8831 const struct devlink_trap_policer_item *policer_item,
8832 enum devlink_command cmd, u32 portid, u32 seq,
8838 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
8842 if (devlink_nl_put_handle(msg, devlink))
8843 goto nla_put_failure;
8845 if (nla_put_u32(msg, DEVLINK_ATTR_TRAP_POLICER_ID,
8846 policer_item->policer->id))
8847 goto nla_put_failure;
8849 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_TRAP_POLICER_RATE,
8850 policer_item->rate, DEVLINK_ATTR_PAD))
8851 goto nla_put_failure;
8853 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_TRAP_POLICER_BURST,
8854 policer_item->burst, DEVLINK_ATTR_PAD))
8855 goto nla_put_failure;
8857 err = devlink_trap_policer_stats_put(msg, devlink,
8858 policer_item->policer);
8860 goto nla_put_failure;
8862 genlmsg_end(msg, hdr);
8867 genlmsg_cancel(msg, hdr);
8871 static int devlink_nl_cmd_trap_policer_get_doit(struct sk_buff *skb,
8872 struct genl_info *info)
8874 struct devlink_trap_policer_item *policer_item;
8875 struct netlink_ext_ack *extack = info->extack;
8876 struct devlink *devlink = info->user_ptr[0];
8877 struct sk_buff *msg;
8880 if (list_empty(&devlink->trap_policer_list))
8883 policer_item = devlink_trap_policer_item_get_from_info(devlink, info);
8884 if (!policer_item) {
8885 NL_SET_ERR_MSG_MOD(extack, "Device did not register this trap policer");
8889 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
8893 err = devlink_nl_trap_policer_fill(msg, devlink, policer_item,
8894 DEVLINK_CMD_TRAP_POLICER_NEW,
8895 info->snd_portid, info->snd_seq, 0);
8897 goto err_trap_policer_fill;
8899 return genlmsg_reply(msg, info);
8901 err_trap_policer_fill:
8907 devlink_nl_cmd_trap_policer_get_dump_one(struct sk_buff *msg,
8908 struct devlink *devlink,
8909 struct netlink_callback *cb)
8911 struct devlink_nl_dump_state *state = devlink_dump_state(cb);
8912 struct devlink_trap_policer_item *policer_item;
8916 list_for_each_entry(policer_item, &devlink->trap_policer_list, list) {
8917 if (idx < state->idx) {
8921 err = devlink_nl_trap_policer_fill(msg, devlink, policer_item,
8922 DEVLINK_CMD_TRAP_POLICER_NEW,
8923 NETLINK_CB(cb->skb).portid,
8936 const struct devlink_gen_cmd devl_gen_trap_policer = {
8937 .dump_one = devlink_nl_cmd_trap_policer_get_dump_one,
8941 devlink_trap_policer_set(struct devlink *devlink,
8942 struct devlink_trap_policer_item *policer_item,
8943 struct genl_info *info)
8945 struct netlink_ext_ack *extack = info->extack;
8946 struct nlattr **attrs = info->attrs;
8950 rate = policer_item->rate;
8951 burst = policer_item->burst;
8953 if (attrs[DEVLINK_ATTR_TRAP_POLICER_RATE])
8954 rate = nla_get_u64(attrs[DEVLINK_ATTR_TRAP_POLICER_RATE]);
8956 if (attrs[DEVLINK_ATTR_TRAP_POLICER_BURST])
8957 burst = nla_get_u64(attrs[DEVLINK_ATTR_TRAP_POLICER_BURST]);
8959 if (rate < policer_item->policer->min_rate) {
8960 NL_SET_ERR_MSG_MOD(extack, "Policer rate lower than limit");
8964 if (rate > policer_item->policer->max_rate) {
8965 NL_SET_ERR_MSG_MOD(extack, "Policer rate higher than limit");
8969 if (burst < policer_item->policer->min_burst) {
8970 NL_SET_ERR_MSG_MOD(extack, "Policer burst size lower than limit");
8974 if (burst > policer_item->policer->max_burst) {
8975 NL_SET_ERR_MSG_MOD(extack, "Policer burst size higher than limit");
8979 err = devlink->ops->trap_policer_set(devlink, policer_item->policer,
8980 rate, burst, info->extack);
8984 policer_item->rate = rate;
8985 policer_item->burst = burst;
8990 static int devlink_nl_cmd_trap_policer_set_doit(struct sk_buff *skb,
8991 struct genl_info *info)
8993 struct devlink_trap_policer_item *policer_item;
8994 struct netlink_ext_ack *extack = info->extack;
8995 struct devlink *devlink = info->user_ptr[0];
8997 if (list_empty(&devlink->trap_policer_list))
9000 if (!devlink->ops->trap_policer_set)
9003 policer_item = devlink_trap_policer_item_get_from_info(devlink, info);
9004 if (!policer_item) {
9005 NL_SET_ERR_MSG_MOD(extack, "Device did not register this trap policer");
9009 return devlink_trap_policer_set(devlink, policer_item, info);
9012 const struct genl_small_ops devlink_nl_ops[56] = {
9014 .cmd = DEVLINK_CMD_GET,
9015 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9016 .doit = devlink_nl_cmd_get_doit,
9017 .dumpit = devlink_nl_instance_iter_dump,
9018 /* can be retrieved by unprivileged users */
9021 .cmd = DEVLINK_CMD_PORT_GET,
9022 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9023 .doit = devlink_nl_cmd_port_get_doit,
9024 .dumpit = devlink_nl_instance_iter_dump,
9025 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
9026 /* can be retrieved by unprivileged users */
9029 .cmd = DEVLINK_CMD_PORT_SET,
9030 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9031 .doit = devlink_nl_cmd_port_set_doit,
9032 .flags = GENL_ADMIN_PERM,
9033 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
9036 .cmd = DEVLINK_CMD_RATE_GET,
9037 .doit = devlink_nl_cmd_rate_get_doit,
9038 .dumpit = devlink_nl_instance_iter_dump,
9039 .internal_flags = DEVLINK_NL_FLAG_NEED_RATE,
9040 /* can be retrieved by unprivileged users */
9043 .cmd = DEVLINK_CMD_RATE_SET,
9044 .doit = devlink_nl_cmd_rate_set_doit,
9045 .flags = GENL_ADMIN_PERM,
9046 .internal_flags = DEVLINK_NL_FLAG_NEED_RATE,
9049 .cmd = DEVLINK_CMD_RATE_NEW,
9050 .doit = devlink_nl_cmd_rate_new_doit,
9051 .flags = GENL_ADMIN_PERM,
9054 .cmd = DEVLINK_CMD_RATE_DEL,
9055 .doit = devlink_nl_cmd_rate_del_doit,
9056 .flags = GENL_ADMIN_PERM,
9057 .internal_flags = DEVLINK_NL_FLAG_NEED_RATE_NODE,
9060 .cmd = DEVLINK_CMD_PORT_SPLIT,
9061 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9062 .doit = devlink_nl_cmd_port_split_doit,
9063 .flags = GENL_ADMIN_PERM,
9064 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
9067 .cmd = DEVLINK_CMD_PORT_UNSPLIT,
9068 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9069 .doit = devlink_nl_cmd_port_unsplit_doit,
9070 .flags = GENL_ADMIN_PERM,
9071 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
9074 .cmd = DEVLINK_CMD_PORT_NEW,
9075 .doit = devlink_nl_cmd_port_new_doit,
9076 .flags = GENL_ADMIN_PERM,
9079 .cmd = DEVLINK_CMD_PORT_DEL,
9080 .doit = devlink_nl_cmd_port_del_doit,
9081 .flags = GENL_ADMIN_PERM,
9084 .cmd = DEVLINK_CMD_LINECARD_GET,
9085 .doit = devlink_nl_cmd_linecard_get_doit,
9086 .dumpit = devlink_nl_cmd_linecard_get_dumpit,
9087 .internal_flags = DEVLINK_NL_FLAG_NEED_LINECARD,
9088 /* can be retrieved by unprivileged users */
9091 .cmd = DEVLINK_CMD_LINECARD_SET,
9092 .doit = devlink_nl_cmd_linecard_set_doit,
9093 .flags = GENL_ADMIN_PERM,
9094 .internal_flags = DEVLINK_NL_FLAG_NEED_LINECARD,
9097 .cmd = DEVLINK_CMD_SB_GET,
9098 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9099 .doit = devlink_nl_cmd_sb_get_doit,
9100 .dumpit = devlink_nl_instance_iter_dump,
9101 /* can be retrieved by unprivileged users */
9104 .cmd = DEVLINK_CMD_SB_POOL_GET,
9105 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9106 .doit = devlink_nl_cmd_sb_pool_get_doit,
9107 .dumpit = devlink_nl_instance_iter_dump,
9108 /* can be retrieved by unprivileged users */
9111 .cmd = DEVLINK_CMD_SB_POOL_SET,
9112 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9113 .doit = devlink_nl_cmd_sb_pool_set_doit,
9114 .flags = GENL_ADMIN_PERM,
9117 .cmd = DEVLINK_CMD_SB_PORT_POOL_GET,
9118 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9119 .doit = devlink_nl_cmd_sb_port_pool_get_doit,
9120 .dumpit = devlink_nl_instance_iter_dump,
9121 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
9122 /* can be retrieved by unprivileged users */
9125 .cmd = DEVLINK_CMD_SB_PORT_POOL_SET,
9126 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9127 .doit = devlink_nl_cmd_sb_port_pool_set_doit,
9128 .flags = GENL_ADMIN_PERM,
9129 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
9132 .cmd = DEVLINK_CMD_SB_TC_POOL_BIND_GET,
9133 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9134 .doit = devlink_nl_cmd_sb_tc_pool_bind_get_doit,
9135 .dumpit = devlink_nl_instance_iter_dump,
9136 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
9137 /* can be retrieved by unprivileged users */
9140 .cmd = DEVLINK_CMD_SB_TC_POOL_BIND_SET,
9141 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9142 .doit = devlink_nl_cmd_sb_tc_pool_bind_set_doit,
9143 .flags = GENL_ADMIN_PERM,
9144 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
9147 .cmd = DEVLINK_CMD_SB_OCC_SNAPSHOT,
9148 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9149 .doit = devlink_nl_cmd_sb_occ_snapshot_doit,
9150 .flags = GENL_ADMIN_PERM,
9153 .cmd = DEVLINK_CMD_SB_OCC_MAX_CLEAR,
9154 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9155 .doit = devlink_nl_cmd_sb_occ_max_clear_doit,
9156 .flags = GENL_ADMIN_PERM,
9159 .cmd = DEVLINK_CMD_ESWITCH_GET,
9160 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9161 .doit = devlink_nl_cmd_eswitch_get_doit,
9162 .flags = GENL_ADMIN_PERM,
9165 .cmd = DEVLINK_CMD_ESWITCH_SET,
9166 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9167 .doit = devlink_nl_cmd_eswitch_set_doit,
9168 .flags = GENL_ADMIN_PERM,
9171 .cmd = DEVLINK_CMD_DPIPE_TABLE_GET,
9172 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9173 .doit = devlink_nl_cmd_dpipe_table_get,
9174 /* can be retrieved by unprivileged users */
9177 .cmd = DEVLINK_CMD_DPIPE_ENTRIES_GET,
9178 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9179 .doit = devlink_nl_cmd_dpipe_entries_get,
9180 /* can be retrieved by unprivileged users */
9183 .cmd = DEVLINK_CMD_DPIPE_HEADERS_GET,
9184 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9185 .doit = devlink_nl_cmd_dpipe_headers_get,
9186 /* can be retrieved by unprivileged users */
9189 .cmd = DEVLINK_CMD_DPIPE_TABLE_COUNTERS_SET,
9190 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9191 .doit = devlink_nl_cmd_dpipe_table_counters_set,
9192 .flags = GENL_ADMIN_PERM,
9195 .cmd = DEVLINK_CMD_RESOURCE_SET,
9196 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9197 .doit = devlink_nl_cmd_resource_set,
9198 .flags = GENL_ADMIN_PERM,
9201 .cmd = DEVLINK_CMD_RESOURCE_DUMP,
9202 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9203 .doit = devlink_nl_cmd_resource_dump,
9204 /* can be retrieved by unprivileged users */
9207 .cmd = DEVLINK_CMD_RELOAD,
9208 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9209 .doit = devlink_nl_cmd_reload,
9210 .flags = GENL_ADMIN_PERM,
9213 .cmd = DEVLINK_CMD_PARAM_GET,
9214 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9215 .doit = devlink_nl_cmd_param_get_doit,
9216 .dumpit = devlink_nl_instance_iter_dump,
9217 /* can be retrieved by unprivileged users */
9220 .cmd = DEVLINK_CMD_PARAM_SET,
9221 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9222 .doit = devlink_nl_cmd_param_set_doit,
9223 .flags = GENL_ADMIN_PERM,
9226 .cmd = DEVLINK_CMD_PORT_PARAM_GET,
9227 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9228 .doit = devlink_nl_cmd_port_param_get_doit,
9229 .dumpit = devlink_nl_cmd_port_param_get_dumpit,
9230 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
9231 /* can be retrieved by unprivileged users */
9234 .cmd = DEVLINK_CMD_PORT_PARAM_SET,
9235 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9236 .doit = devlink_nl_cmd_port_param_set_doit,
9237 .flags = GENL_ADMIN_PERM,
9238 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
9241 .cmd = DEVLINK_CMD_REGION_GET,
9242 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9243 .doit = devlink_nl_cmd_region_get_doit,
9244 .dumpit = devlink_nl_instance_iter_dump,
9245 .flags = GENL_ADMIN_PERM,
9248 .cmd = DEVLINK_CMD_REGION_NEW,
9249 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9250 .doit = devlink_nl_cmd_region_new,
9251 .flags = GENL_ADMIN_PERM,
9254 .cmd = DEVLINK_CMD_REGION_DEL,
9255 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9256 .doit = devlink_nl_cmd_region_del,
9257 .flags = GENL_ADMIN_PERM,
9260 .cmd = DEVLINK_CMD_REGION_READ,
9261 .validate = GENL_DONT_VALIDATE_STRICT |
9262 GENL_DONT_VALIDATE_DUMP_STRICT,
9263 .dumpit = devlink_nl_cmd_region_read_dumpit,
9264 .flags = GENL_ADMIN_PERM,
9267 .cmd = DEVLINK_CMD_INFO_GET,
9268 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9269 .doit = devlink_nl_cmd_info_get_doit,
9270 .dumpit = devlink_nl_instance_iter_dump,
9271 /* can be retrieved by unprivileged users */
9274 .cmd = DEVLINK_CMD_HEALTH_REPORTER_GET,
9275 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9276 .doit = devlink_nl_cmd_health_reporter_get_doit,
9277 .dumpit = devlink_nl_cmd_health_reporter_get_dumpit,
9278 .internal_flags = DEVLINK_NL_FLAG_NEED_DEVLINK_OR_PORT,
9279 /* can be retrieved by unprivileged users */
9282 .cmd = DEVLINK_CMD_HEALTH_REPORTER_SET,
9283 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9284 .doit = devlink_nl_cmd_health_reporter_set_doit,
9285 .flags = GENL_ADMIN_PERM,
9286 .internal_flags = DEVLINK_NL_FLAG_NEED_DEVLINK_OR_PORT,
9289 .cmd = DEVLINK_CMD_HEALTH_REPORTER_RECOVER,
9290 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9291 .doit = devlink_nl_cmd_health_reporter_recover_doit,
9292 .flags = GENL_ADMIN_PERM,
9293 .internal_flags = DEVLINK_NL_FLAG_NEED_DEVLINK_OR_PORT,
9296 .cmd = DEVLINK_CMD_HEALTH_REPORTER_DIAGNOSE,
9297 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9298 .doit = devlink_nl_cmd_health_reporter_diagnose_doit,
9299 .flags = GENL_ADMIN_PERM,
9300 .internal_flags = DEVLINK_NL_FLAG_NEED_DEVLINK_OR_PORT,
9303 .cmd = DEVLINK_CMD_HEALTH_REPORTER_DUMP_GET,
9304 .validate = GENL_DONT_VALIDATE_STRICT |
9305 GENL_DONT_VALIDATE_DUMP_STRICT,
9306 .dumpit = devlink_nl_cmd_health_reporter_dump_get_dumpit,
9307 .flags = GENL_ADMIN_PERM,
9310 .cmd = DEVLINK_CMD_HEALTH_REPORTER_DUMP_CLEAR,
9311 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9312 .doit = devlink_nl_cmd_health_reporter_dump_clear_doit,
9313 .flags = GENL_ADMIN_PERM,
9314 .internal_flags = DEVLINK_NL_FLAG_NEED_DEVLINK_OR_PORT,
9317 .cmd = DEVLINK_CMD_HEALTH_REPORTER_TEST,
9318 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9319 .doit = devlink_nl_cmd_health_reporter_test_doit,
9320 .flags = GENL_ADMIN_PERM,
9321 .internal_flags = DEVLINK_NL_FLAG_NEED_DEVLINK_OR_PORT,
9324 .cmd = DEVLINK_CMD_FLASH_UPDATE,
9325 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9326 .doit = devlink_nl_cmd_flash_update,
9327 .flags = GENL_ADMIN_PERM,
9330 .cmd = DEVLINK_CMD_TRAP_GET,
9331 .doit = devlink_nl_cmd_trap_get_doit,
9332 .dumpit = devlink_nl_instance_iter_dump,
9333 /* can be retrieved by unprivileged users */
9336 .cmd = DEVLINK_CMD_TRAP_SET,
9337 .doit = devlink_nl_cmd_trap_set_doit,
9338 .flags = GENL_ADMIN_PERM,
9341 .cmd = DEVLINK_CMD_TRAP_GROUP_GET,
9342 .doit = devlink_nl_cmd_trap_group_get_doit,
9343 .dumpit = devlink_nl_instance_iter_dump,
9344 /* can be retrieved by unprivileged users */
9347 .cmd = DEVLINK_CMD_TRAP_GROUP_SET,
9348 .doit = devlink_nl_cmd_trap_group_set_doit,
9349 .flags = GENL_ADMIN_PERM,
9352 .cmd = DEVLINK_CMD_TRAP_POLICER_GET,
9353 .doit = devlink_nl_cmd_trap_policer_get_doit,
9354 .dumpit = devlink_nl_instance_iter_dump,
9355 /* can be retrieved by unprivileged users */
9358 .cmd = DEVLINK_CMD_TRAP_POLICER_SET,
9359 .doit = devlink_nl_cmd_trap_policer_set_doit,
9360 .flags = GENL_ADMIN_PERM,
9363 .cmd = DEVLINK_CMD_SELFTESTS_GET,
9364 .doit = devlink_nl_cmd_selftests_get_doit,
9365 .dumpit = devlink_nl_instance_iter_dump,
9366 /* can be retrieved by unprivileged users */
9369 .cmd = DEVLINK_CMD_SELFTESTS_RUN,
9370 .doit = devlink_nl_cmd_selftests_run,
9371 .flags = GENL_ADMIN_PERM,
9373 /* -- No new ops here! Use split ops going forward! -- */
9376 bool devlink_reload_actions_valid(const struct devlink_ops *ops)
9378 const struct devlink_reload_combination *comb;
9381 if (!devlink_reload_supported(ops)) {
9382 if (WARN_ON(ops->reload_actions))
9387 if (WARN_ON(!ops->reload_actions ||
9388 ops->reload_actions & BIT(DEVLINK_RELOAD_ACTION_UNSPEC) ||
9389 ops->reload_actions >= BIT(__DEVLINK_RELOAD_ACTION_MAX)))
9392 if (WARN_ON(ops->reload_limits & BIT(DEVLINK_RELOAD_LIMIT_UNSPEC) ||
9393 ops->reload_limits >= BIT(__DEVLINK_RELOAD_LIMIT_MAX)))
9396 for (i = 0; i < ARRAY_SIZE(devlink_reload_invalid_combinations); i++) {
9397 comb = &devlink_reload_invalid_combinations[i];
9398 if (ops->reload_actions == BIT(comb->action) &&
9399 ops->reload_limits == BIT(comb->limit))
9406 devlink_trap_policer_notify(struct devlink *devlink,
9407 const struct devlink_trap_policer_item *policer_item,
9408 enum devlink_command cmd);
9410 devlink_trap_group_notify(struct devlink *devlink,
9411 const struct devlink_trap_group_item *group_item,
9412 enum devlink_command cmd);
9413 static void devlink_trap_notify(struct devlink *devlink,
9414 const struct devlink_trap_item *trap_item,
9415 enum devlink_command cmd);
9417 void devlink_notify_register(struct devlink *devlink)
9419 struct devlink_trap_policer_item *policer_item;
9420 struct devlink_trap_group_item *group_item;
9421 struct devlink_param_item *param_item;
9422 struct devlink_trap_item *trap_item;
9423 struct devlink_port *devlink_port;
9424 struct devlink_linecard *linecard;
9425 struct devlink_rate *rate_node;
9426 struct devlink_region *region;
9427 unsigned long port_index;
9429 devlink_notify(devlink, DEVLINK_CMD_NEW);
9430 list_for_each_entry(linecard, &devlink->linecard_list, list)
9431 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_NEW);
9433 xa_for_each(&devlink->ports, port_index, devlink_port)
9434 devlink_port_notify(devlink_port, DEVLINK_CMD_PORT_NEW);
9436 list_for_each_entry(policer_item, &devlink->trap_policer_list, list)
9437 devlink_trap_policer_notify(devlink, policer_item,
9438 DEVLINK_CMD_TRAP_POLICER_NEW);
9440 list_for_each_entry(group_item, &devlink->trap_group_list, list)
9441 devlink_trap_group_notify(devlink, group_item,
9442 DEVLINK_CMD_TRAP_GROUP_NEW);
9444 list_for_each_entry(trap_item, &devlink->trap_list, list)
9445 devlink_trap_notify(devlink, trap_item, DEVLINK_CMD_TRAP_NEW);
9447 list_for_each_entry(rate_node, &devlink->rate_list, list)
9448 devlink_rate_notify(rate_node, DEVLINK_CMD_RATE_NEW);
9450 list_for_each_entry(region, &devlink->region_list, list)
9451 devlink_nl_region_notify(region, NULL, DEVLINK_CMD_REGION_NEW);
9453 list_for_each_entry(param_item, &devlink->param_list, list)
9454 devlink_param_notify(devlink, 0, param_item,
9455 DEVLINK_CMD_PARAM_NEW);
9458 void devlink_notify_unregister(struct devlink *devlink)
9460 struct devlink_trap_policer_item *policer_item;
9461 struct devlink_trap_group_item *group_item;
9462 struct devlink_param_item *param_item;
9463 struct devlink_trap_item *trap_item;
9464 struct devlink_port *devlink_port;
9465 struct devlink_rate *rate_node;
9466 struct devlink_region *region;
9467 unsigned long port_index;
9469 list_for_each_entry_reverse(param_item, &devlink->param_list, list)
9470 devlink_param_notify(devlink, 0, param_item,
9471 DEVLINK_CMD_PARAM_DEL);
9473 list_for_each_entry_reverse(region, &devlink->region_list, list)
9474 devlink_nl_region_notify(region, NULL, DEVLINK_CMD_REGION_DEL);
9476 list_for_each_entry_reverse(rate_node, &devlink->rate_list, list)
9477 devlink_rate_notify(rate_node, DEVLINK_CMD_RATE_DEL);
9479 list_for_each_entry_reverse(trap_item, &devlink->trap_list, list)
9480 devlink_trap_notify(devlink, trap_item, DEVLINK_CMD_TRAP_DEL);
9482 list_for_each_entry_reverse(group_item, &devlink->trap_group_list, list)
9483 devlink_trap_group_notify(devlink, group_item,
9484 DEVLINK_CMD_TRAP_GROUP_DEL);
9485 list_for_each_entry_reverse(policer_item, &devlink->trap_policer_list,
9487 devlink_trap_policer_notify(devlink, policer_item,
9488 DEVLINK_CMD_TRAP_POLICER_DEL);
9490 xa_for_each(&devlink->ports, port_index, devlink_port)
9491 devlink_port_notify(devlink_port, DEVLINK_CMD_PORT_DEL);
9492 devlink_notify(devlink, DEVLINK_CMD_DEL);
9495 static void devlink_port_type_warn(struct work_struct *work)
9497 WARN(true, "Type was not set for devlink port.");
9500 static bool devlink_port_type_should_warn(struct devlink_port *devlink_port)
9502 /* Ignore CPU and DSA flavours. */
9503 return devlink_port->attrs.flavour != DEVLINK_PORT_FLAVOUR_CPU &&
9504 devlink_port->attrs.flavour != DEVLINK_PORT_FLAVOUR_DSA &&
9505 devlink_port->attrs.flavour != DEVLINK_PORT_FLAVOUR_UNUSED;
9508 #define DEVLINK_PORT_TYPE_WARN_TIMEOUT (HZ * 3600)
9510 static void devlink_port_type_warn_schedule(struct devlink_port *devlink_port)
9512 if (!devlink_port_type_should_warn(devlink_port))
9514 /* Schedule a work to WARN in case driver does not set port
9515 * type within timeout.
9517 schedule_delayed_work(&devlink_port->type_warn_dw,
9518 DEVLINK_PORT_TYPE_WARN_TIMEOUT);
9521 static void devlink_port_type_warn_cancel(struct devlink_port *devlink_port)
9523 if (!devlink_port_type_should_warn(devlink_port))
9525 cancel_delayed_work_sync(&devlink_port->type_warn_dw);
9529 * devlink_port_init() - Init devlink port
9532 * @devlink_port: devlink port
9534 * Initialize essencial stuff that is needed for functions
9535 * that may be called before devlink port registration.
9536 * Call to this function is optional and not needed
9537 * in case the driver does not use such functions.
9539 void devlink_port_init(struct devlink *devlink,
9540 struct devlink_port *devlink_port)
9542 if (devlink_port->initialized)
9544 devlink_port->devlink = devlink;
9545 INIT_LIST_HEAD(&devlink_port->region_list);
9546 devlink_port->initialized = true;
9548 EXPORT_SYMBOL_GPL(devlink_port_init);
9551 * devlink_port_fini() - Deinitialize devlink port
9553 * @devlink_port: devlink port
9555 * Deinitialize essencial stuff that is in use for functions
9556 * that may be called after devlink port unregistration.
9557 * Call to this function is optional and not needed
9558 * in case the driver does not use such functions.
9560 void devlink_port_fini(struct devlink_port *devlink_port)
9562 WARN_ON(!list_empty(&devlink_port->region_list));
9564 EXPORT_SYMBOL_GPL(devlink_port_fini);
9567 * devl_port_register() - Register devlink port
9570 * @devlink_port: devlink port
9571 * @port_index: driver-specific numerical identifier of the port
9573 * Register devlink port with provided port index. User can use
9574 * any indexing, even hw-related one. devlink_port structure
9575 * is convenient to be embedded inside user driver private structure.
9576 * Note that the caller should take care of zeroing the devlink_port
9579 int devl_port_register(struct devlink *devlink,
9580 struct devlink_port *devlink_port,
9581 unsigned int port_index)
9585 devl_assert_locked(devlink);
9587 ASSERT_DEVLINK_PORT_NOT_REGISTERED(devlink_port);
9589 devlink_port_init(devlink, devlink_port);
9590 devlink_port->registered = true;
9591 devlink_port->index = port_index;
9592 spin_lock_init(&devlink_port->type_lock);
9593 INIT_LIST_HEAD(&devlink_port->reporter_list);
9594 mutex_init(&devlink_port->reporters_lock);
9595 err = xa_insert(&devlink->ports, port_index, devlink_port, GFP_KERNEL);
9597 mutex_destroy(&devlink_port->reporters_lock);
9601 INIT_DELAYED_WORK(&devlink_port->type_warn_dw, &devlink_port_type_warn);
9602 devlink_port_type_warn_schedule(devlink_port);
9603 devlink_port_notify(devlink_port, DEVLINK_CMD_PORT_NEW);
9606 EXPORT_SYMBOL_GPL(devl_port_register);
9609 * devlink_port_register - Register devlink port
9612 * @devlink_port: devlink port
9613 * @port_index: driver-specific numerical identifier of the port
9615 * Register devlink port with provided port index. User can use
9616 * any indexing, even hw-related one. devlink_port structure
9617 * is convenient to be embedded inside user driver private structure.
9618 * Note that the caller should take care of zeroing the devlink_port
9621 * Context: Takes and release devlink->lock <mutex>.
9623 int devlink_port_register(struct devlink *devlink,
9624 struct devlink_port *devlink_port,
9625 unsigned int port_index)
9630 err = devl_port_register(devlink, devlink_port, port_index);
9631 devl_unlock(devlink);
9634 EXPORT_SYMBOL_GPL(devlink_port_register);
9637 * devl_port_unregister() - Unregister devlink port
9639 * @devlink_port: devlink port
9641 void devl_port_unregister(struct devlink_port *devlink_port)
9643 lockdep_assert_held(&devlink_port->devlink->lock);
9644 WARN_ON(devlink_port->type != DEVLINK_PORT_TYPE_NOTSET);
9646 devlink_port_type_warn_cancel(devlink_port);
9647 devlink_port_notify(devlink_port, DEVLINK_CMD_PORT_DEL);
9648 xa_erase(&devlink_port->devlink->ports, devlink_port->index);
9649 WARN_ON(!list_empty(&devlink_port->reporter_list));
9650 mutex_destroy(&devlink_port->reporters_lock);
9651 devlink_port->registered = false;
9653 EXPORT_SYMBOL_GPL(devl_port_unregister);
9656 * devlink_port_unregister - Unregister devlink port
9658 * @devlink_port: devlink port
9660 * Context: Takes and release devlink->lock <mutex>.
9662 void devlink_port_unregister(struct devlink_port *devlink_port)
9664 struct devlink *devlink = devlink_port->devlink;
9667 devl_port_unregister(devlink_port);
9668 devl_unlock(devlink);
9670 EXPORT_SYMBOL_GPL(devlink_port_unregister);
9672 static void devlink_port_type_netdev_checks(struct devlink_port *devlink_port,
9673 struct net_device *netdev)
9675 const struct net_device_ops *ops = netdev->netdev_ops;
9677 /* If driver registers devlink port, it should set devlink port
9678 * attributes accordingly so the compat functions are called
9679 * and the original ops are not used.
9681 if (ops->ndo_get_phys_port_name) {
9682 /* Some drivers use the same set of ndos for netdevs
9683 * that have devlink_port registered and also for
9684 * those who don't. Make sure that ndo_get_phys_port_name
9685 * returns -EOPNOTSUPP here in case it is defined.
9688 char name[IFNAMSIZ];
9691 err = ops->ndo_get_phys_port_name(netdev, name, sizeof(name));
9692 WARN_ON(err != -EOPNOTSUPP);
9694 if (ops->ndo_get_port_parent_id) {
9695 /* Some drivers use the same set of ndos for netdevs
9696 * that have devlink_port registered and also for
9697 * those who don't. Make sure that ndo_get_port_parent_id
9698 * returns -EOPNOTSUPP here in case it is defined.
9701 struct netdev_phys_item_id ppid;
9704 err = ops->ndo_get_port_parent_id(netdev, &ppid);
9705 WARN_ON(err != -EOPNOTSUPP);
9709 static void __devlink_port_type_set(struct devlink_port *devlink_port,
9710 enum devlink_port_type type,
9713 struct net_device *netdev = type_dev;
9715 ASSERT_DEVLINK_PORT_REGISTERED(devlink_port);
9717 if (type == DEVLINK_PORT_TYPE_NOTSET) {
9718 devlink_port_type_warn_schedule(devlink_port);
9720 devlink_port_type_warn_cancel(devlink_port);
9721 if (type == DEVLINK_PORT_TYPE_ETH && netdev)
9722 devlink_port_type_netdev_checks(devlink_port, netdev);
9725 spin_lock_bh(&devlink_port->type_lock);
9726 devlink_port->type = type;
9728 case DEVLINK_PORT_TYPE_ETH:
9729 devlink_port->type_eth.netdev = netdev;
9732 devlink_port->type_eth.ifindex = netdev->ifindex;
9733 BUILD_BUG_ON(sizeof(devlink_port->type_eth.ifname) !=
9734 sizeof(netdev->name));
9735 strcpy(devlink_port->type_eth.ifname, netdev->name);
9738 case DEVLINK_PORT_TYPE_IB:
9739 devlink_port->type_ib.ibdev = type_dev;
9744 spin_unlock_bh(&devlink_port->type_lock);
9745 devlink_port_notify(devlink_port, DEVLINK_CMD_PORT_NEW);
9749 * devlink_port_type_eth_set - Set port type to Ethernet
9751 * @devlink_port: devlink port
9753 * If driver is calling this, most likely it is doing something wrong.
9755 void devlink_port_type_eth_set(struct devlink_port *devlink_port)
9757 dev_warn(devlink_port->devlink->dev,
9758 "devlink port type for port %d set to Ethernet without a software interface reference, device type not supported by the kernel?\n",
9759 devlink_port->index);
9760 __devlink_port_type_set(devlink_port, DEVLINK_PORT_TYPE_ETH, NULL);
9762 EXPORT_SYMBOL_GPL(devlink_port_type_eth_set);
9765 * devlink_port_type_ib_set - Set port type to InfiniBand
9767 * @devlink_port: devlink port
9768 * @ibdev: related IB device
9770 void devlink_port_type_ib_set(struct devlink_port *devlink_port,
9771 struct ib_device *ibdev)
9773 __devlink_port_type_set(devlink_port, DEVLINK_PORT_TYPE_IB, ibdev);
9775 EXPORT_SYMBOL_GPL(devlink_port_type_ib_set);
9778 * devlink_port_type_clear - Clear port type
9780 * @devlink_port: devlink port
9782 * If driver is calling this for clearing Ethernet type, most likely
9783 * it is doing something wrong.
9785 void devlink_port_type_clear(struct devlink_port *devlink_port)
9787 if (devlink_port->type == DEVLINK_PORT_TYPE_ETH)
9788 dev_warn(devlink_port->devlink->dev,
9789 "devlink port type for port %d cleared without a software interface reference, device type not supported by the kernel?\n",
9790 devlink_port->index);
9791 __devlink_port_type_set(devlink_port, DEVLINK_PORT_TYPE_NOTSET, NULL);
9793 EXPORT_SYMBOL_GPL(devlink_port_type_clear);
9795 int devlink_port_netdevice_event(struct notifier_block *nb,
9796 unsigned long event, void *ptr)
9798 struct net_device *netdev = netdev_notifier_info_to_dev(ptr);
9799 struct devlink_port *devlink_port = netdev->devlink_port;
9800 struct devlink *devlink;
9802 devlink = container_of(nb, struct devlink, netdevice_nb);
9804 if (!devlink_port || devlink_port->devlink != devlink)
9808 case NETDEV_POST_INIT:
9809 /* Set the type but not netdev pointer. It is going to be set
9810 * later on by NETDEV_REGISTER event. Happens once during
9811 * netdevice register
9813 __devlink_port_type_set(devlink_port, DEVLINK_PORT_TYPE_ETH,
9816 case NETDEV_REGISTER:
9817 case NETDEV_CHANGENAME:
9818 /* Set the netdev on top of previously set type. Note this
9819 * event happens also during net namespace change so here
9820 * we take into account netdev pointer appearing in this
9823 __devlink_port_type_set(devlink_port, devlink_port->type,
9826 case NETDEV_UNREGISTER:
9827 /* Clear netdev pointer, but not the type. This event happens
9828 * also during net namespace change so we need to clear
9829 * pointer to netdev that is going to another net namespace.
9831 __devlink_port_type_set(devlink_port, devlink_port->type,
9834 case NETDEV_PRE_UNINIT:
9835 /* Clear the type and the netdev pointer. Happens one during
9836 * netdevice unregister.
9838 __devlink_port_type_set(devlink_port, DEVLINK_PORT_TYPE_NOTSET,
9846 static int __devlink_port_attrs_set(struct devlink_port *devlink_port,
9847 enum devlink_port_flavour flavour)
9849 struct devlink_port_attrs *attrs = &devlink_port->attrs;
9851 devlink_port->attrs_set = true;
9852 attrs->flavour = flavour;
9853 if (attrs->switch_id.id_len) {
9854 devlink_port->switch_port = true;
9855 if (WARN_ON(attrs->switch_id.id_len > MAX_PHYS_ITEM_ID_LEN))
9856 attrs->switch_id.id_len = MAX_PHYS_ITEM_ID_LEN;
9858 devlink_port->switch_port = false;
9864 * devlink_port_attrs_set - Set port attributes
9866 * @devlink_port: devlink port
9867 * @attrs: devlink port attrs
9869 void devlink_port_attrs_set(struct devlink_port *devlink_port,
9870 struct devlink_port_attrs *attrs)
9874 ASSERT_DEVLINK_PORT_NOT_REGISTERED(devlink_port);
9876 devlink_port->attrs = *attrs;
9877 ret = __devlink_port_attrs_set(devlink_port, attrs->flavour);
9880 WARN_ON(attrs->splittable && attrs->split);
9882 EXPORT_SYMBOL_GPL(devlink_port_attrs_set);
9885 * devlink_port_attrs_pci_pf_set - Set PCI PF port attributes
9887 * @devlink_port: devlink port
9888 * @controller: associated controller number for the devlink port instance
9889 * @pf: associated PF for the devlink port instance
9890 * @external: indicates if the port is for an external controller
9892 void devlink_port_attrs_pci_pf_set(struct devlink_port *devlink_port, u32 controller,
9893 u16 pf, bool external)
9895 struct devlink_port_attrs *attrs = &devlink_port->attrs;
9898 ASSERT_DEVLINK_PORT_NOT_REGISTERED(devlink_port);
9900 ret = __devlink_port_attrs_set(devlink_port,
9901 DEVLINK_PORT_FLAVOUR_PCI_PF);
9904 attrs->pci_pf.controller = controller;
9905 attrs->pci_pf.pf = pf;
9906 attrs->pci_pf.external = external;
9908 EXPORT_SYMBOL_GPL(devlink_port_attrs_pci_pf_set);
9911 * devlink_port_attrs_pci_vf_set - Set PCI VF port attributes
9913 * @devlink_port: devlink port
9914 * @controller: associated controller number for the devlink port instance
9915 * @pf: associated PF for the devlink port instance
9916 * @vf: associated VF of a PF for the devlink port instance
9917 * @external: indicates if the port is for an external controller
9919 void devlink_port_attrs_pci_vf_set(struct devlink_port *devlink_port, u32 controller,
9920 u16 pf, u16 vf, bool external)
9922 struct devlink_port_attrs *attrs = &devlink_port->attrs;
9925 ASSERT_DEVLINK_PORT_NOT_REGISTERED(devlink_port);
9927 ret = __devlink_port_attrs_set(devlink_port,
9928 DEVLINK_PORT_FLAVOUR_PCI_VF);
9931 attrs->pci_vf.controller = controller;
9932 attrs->pci_vf.pf = pf;
9933 attrs->pci_vf.vf = vf;
9934 attrs->pci_vf.external = external;
9936 EXPORT_SYMBOL_GPL(devlink_port_attrs_pci_vf_set);
9939 * devlink_port_attrs_pci_sf_set - Set PCI SF port attributes
9941 * @devlink_port: devlink port
9942 * @controller: associated controller number for the devlink port instance
9943 * @pf: associated PF for the devlink port instance
9944 * @sf: associated SF of a PF for the devlink port instance
9945 * @external: indicates if the port is for an external controller
9947 void devlink_port_attrs_pci_sf_set(struct devlink_port *devlink_port, u32 controller,
9948 u16 pf, u32 sf, bool external)
9950 struct devlink_port_attrs *attrs = &devlink_port->attrs;
9953 ASSERT_DEVLINK_PORT_NOT_REGISTERED(devlink_port);
9955 ret = __devlink_port_attrs_set(devlink_port,
9956 DEVLINK_PORT_FLAVOUR_PCI_SF);
9959 attrs->pci_sf.controller = controller;
9960 attrs->pci_sf.pf = pf;
9961 attrs->pci_sf.sf = sf;
9962 attrs->pci_sf.external = external;
9964 EXPORT_SYMBOL_GPL(devlink_port_attrs_pci_sf_set);
9967 * devl_rate_node_create - create devlink rate node
9968 * @devlink: devlink instance
9969 * @priv: driver private data
9970 * @node_name: name of the resulting node
9971 * @parent: parent devlink_rate struct
9973 * Create devlink rate object of type node
9975 struct devlink_rate *
9976 devl_rate_node_create(struct devlink *devlink, void *priv, char *node_name,
9977 struct devlink_rate *parent)
9979 struct devlink_rate *rate_node;
9981 rate_node = devlink_rate_node_get_by_name(devlink, node_name);
9982 if (!IS_ERR(rate_node))
9983 return ERR_PTR(-EEXIST);
9985 rate_node = kzalloc(sizeof(*rate_node), GFP_KERNEL);
9987 return ERR_PTR(-ENOMEM);
9990 rate_node->parent = parent;
9991 refcount_inc(&rate_node->parent->refcnt);
9994 rate_node->type = DEVLINK_RATE_TYPE_NODE;
9995 rate_node->devlink = devlink;
9996 rate_node->priv = priv;
9998 rate_node->name = kstrdup(node_name, GFP_KERNEL);
9999 if (!rate_node->name) {
10001 return ERR_PTR(-ENOMEM);
10004 refcount_set(&rate_node->refcnt, 1);
10005 list_add(&rate_node->list, &devlink->rate_list);
10006 devlink_rate_notify(rate_node, DEVLINK_CMD_RATE_NEW);
10009 EXPORT_SYMBOL_GPL(devl_rate_node_create);
10012 * devl_rate_leaf_create - create devlink rate leaf
10013 * @devlink_port: devlink port object to create rate object on
10014 * @priv: driver private data
10015 * @parent: parent devlink_rate struct
10017 * Create devlink rate object of type leaf on provided @devlink_port.
10019 int devl_rate_leaf_create(struct devlink_port *devlink_port, void *priv,
10020 struct devlink_rate *parent)
10022 struct devlink *devlink = devlink_port->devlink;
10023 struct devlink_rate *devlink_rate;
10025 devl_assert_locked(devlink_port->devlink);
10027 if (WARN_ON(devlink_port->devlink_rate))
10030 devlink_rate = kzalloc(sizeof(*devlink_rate), GFP_KERNEL);
10035 devlink_rate->parent = parent;
10036 refcount_inc(&devlink_rate->parent->refcnt);
10039 devlink_rate->type = DEVLINK_RATE_TYPE_LEAF;
10040 devlink_rate->devlink = devlink;
10041 devlink_rate->devlink_port = devlink_port;
10042 devlink_rate->priv = priv;
10043 list_add_tail(&devlink_rate->list, &devlink->rate_list);
10044 devlink_port->devlink_rate = devlink_rate;
10045 devlink_rate_notify(devlink_rate, DEVLINK_CMD_RATE_NEW);
10049 EXPORT_SYMBOL_GPL(devl_rate_leaf_create);
10052 * devl_rate_leaf_destroy - destroy devlink rate leaf
10054 * @devlink_port: devlink port linked to the rate object
10056 * Destroy the devlink rate object of type leaf on provided @devlink_port.
10058 void devl_rate_leaf_destroy(struct devlink_port *devlink_port)
10060 struct devlink_rate *devlink_rate = devlink_port->devlink_rate;
10062 devl_assert_locked(devlink_port->devlink);
10066 devlink_rate_notify(devlink_rate, DEVLINK_CMD_RATE_DEL);
10067 if (devlink_rate->parent)
10068 refcount_dec(&devlink_rate->parent->refcnt);
10069 list_del(&devlink_rate->list);
10070 devlink_port->devlink_rate = NULL;
10071 kfree(devlink_rate);
10073 EXPORT_SYMBOL_GPL(devl_rate_leaf_destroy);
10076 * devl_rate_nodes_destroy - destroy all devlink rate nodes on device
10077 * @devlink: devlink instance
10079 * Unset parent for all rate objects and destroy all rate nodes
10080 * on specified device.
10082 void devl_rate_nodes_destroy(struct devlink *devlink)
10084 static struct devlink_rate *devlink_rate, *tmp;
10085 const struct devlink_ops *ops = devlink->ops;
10087 devl_assert_locked(devlink);
10089 list_for_each_entry(devlink_rate, &devlink->rate_list, list) {
10090 if (!devlink_rate->parent)
10093 refcount_dec(&devlink_rate->parent->refcnt);
10094 if (devlink_rate_is_leaf(devlink_rate))
10095 ops->rate_leaf_parent_set(devlink_rate, NULL, devlink_rate->priv,
10097 else if (devlink_rate_is_node(devlink_rate))
10098 ops->rate_node_parent_set(devlink_rate, NULL, devlink_rate->priv,
10101 list_for_each_entry_safe(devlink_rate, tmp, &devlink->rate_list, list) {
10102 if (devlink_rate_is_node(devlink_rate)) {
10103 ops->rate_node_del(devlink_rate, devlink_rate->priv, NULL);
10104 list_del(&devlink_rate->list);
10105 kfree(devlink_rate->name);
10106 kfree(devlink_rate);
10110 EXPORT_SYMBOL_GPL(devl_rate_nodes_destroy);
10113 * devlink_port_linecard_set - Link port with a linecard
10115 * @devlink_port: devlink port
10116 * @linecard: devlink linecard
10118 void devlink_port_linecard_set(struct devlink_port *devlink_port,
10119 struct devlink_linecard *linecard)
10121 ASSERT_DEVLINK_PORT_NOT_REGISTERED(devlink_port);
10123 devlink_port->linecard = linecard;
10125 EXPORT_SYMBOL_GPL(devlink_port_linecard_set);
10127 static int __devlink_port_phys_port_name_get(struct devlink_port *devlink_port,
10128 char *name, size_t len)
10130 struct devlink_port_attrs *attrs = &devlink_port->attrs;
10133 if (!devlink_port->attrs_set)
10134 return -EOPNOTSUPP;
10136 switch (attrs->flavour) {
10137 case DEVLINK_PORT_FLAVOUR_PHYSICAL:
10138 if (devlink_port->linecard)
10139 n = snprintf(name, len, "l%u",
10140 devlink_port->linecard->index);
10142 n += snprintf(name + n, len - n, "p%u",
10143 attrs->phys.port_number);
10144 if (n < len && attrs->split)
10145 n += snprintf(name + n, len - n, "s%u",
10146 attrs->phys.split_subport_number);
10148 case DEVLINK_PORT_FLAVOUR_CPU:
10149 case DEVLINK_PORT_FLAVOUR_DSA:
10150 case DEVLINK_PORT_FLAVOUR_UNUSED:
10151 /* As CPU and DSA ports do not have a netdevice associated
10152 * case should not ever happen.
10156 case DEVLINK_PORT_FLAVOUR_PCI_PF:
10157 if (attrs->pci_pf.external) {
10158 n = snprintf(name, len, "c%u", attrs->pci_pf.controller);
10164 n = snprintf(name, len, "pf%u", attrs->pci_pf.pf);
10166 case DEVLINK_PORT_FLAVOUR_PCI_VF:
10167 if (attrs->pci_vf.external) {
10168 n = snprintf(name, len, "c%u", attrs->pci_vf.controller);
10174 n = snprintf(name, len, "pf%uvf%u",
10175 attrs->pci_vf.pf, attrs->pci_vf.vf);
10177 case DEVLINK_PORT_FLAVOUR_PCI_SF:
10178 if (attrs->pci_sf.external) {
10179 n = snprintf(name, len, "c%u", attrs->pci_sf.controller);
10185 n = snprintf(name, len, "pf%usf%u", attrs->pci_sf.pf,
10188 case DEVLINK_PORT_FLAVOUR_VIRTUAL:
10189 return -EOPNOTSUPP;
10198 static int devlink_linecard_types_init(struct devlink_linecard *linecard)
10200 struct devlink_linecard_type *linecard_type;
10201 unsigned int count;
10204 count = linecard->ops->types_count(linecard, linecard->priv);
10205 linecard->types = kmalloc_array(count, sizeof(*linecard_type),
10207 if (!linecard->types)
10209 linecard->types_count = count;
10211 for (i = 0; i < count; i++) {
10212 linecard_type = &linecard->types[i];
10213 linecard->ops->types_get(linecard, linecard->priv, i,
10214 &linecard_type->type,
10215 &linecard_type->priv);
10220 static void devlink_linecard_types_fini(struct devlink_linecard *linecard)
10222 kfree(linecard->types);
10226 * devlink_linecard_create - Create devlink linecard
10228 * @devlink: devlink
10229 * @linecard_index: driver-specific numerical identifier of the linecard
10230 * @ops: linecards ops
10231 * @priv: user priv pointer
10233 * Create devlink linecard instance with provided linecard index.
10234 * Caller can use any indexing, even hw-related one.
10236 * Return: Line card structure or an ERR_PTR() encoded error code.
10238 struct devlink_linecard *
10239 devlink_linecard_create(struct devlink *devlink, unsigned int linecard_index,
10240 const struct devlink_linecard_ops *ops, void *priv)
10242 struct devlink_linecard *linecard;
10245 if (WARN_ON(!ops || !ops->provision || !ops->unprovision ||
10246 !ops->types_count || !ops->types_get))
10247 return ERR_PTR(-EINVAL);
10249 mutex_lock(&devlink->linecards_lock);
10250 if (devlink_linecard_index_exists(devlink, linecard_index)) {
10251 mutex_unlock(&devlink->linecards_lock);
10252 return ERR_PTR(-EEXIST);
10255 linecard = kzalloc(sizeof(*linecard), GFP_KERNEL);
10257 mutex_unlock(&devlink->linecards_lock);
10258 return ERR_PTR(-ENOMEM);
10261 linecard->devlink = devlink;
10262 linecard->index = linecard_index;
10263 linecard->ops = ops;
10264 linecard->priv = priv;
10265 linecard->state = DEVLINK_LINECARD_STATE_UNPROVISIONED;
10266 mutex_init(&linecard->state_lock);
10268 err = devlink_linecard_types_init(linecard);
10270 mutex_destroy(&linecard->state_lock);
10272 mutex_unlock(&devlink->linecards_lock);
10273 return ERR_PTR(err);
10276 list_add_tail(&linecard->list, &devlink->linecard_list);
10277 refcount_set(&linecard->refcount, 1);
10278 mutex_unlock(&devlink->linecards_lock);
10279 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_NEW);
10282 EXPORT_SYMBOL_GPL(devlink_linecard_create);
10285 * devlink_linecard_destroy - Destroy devlink linecard
10287 * @linecard: devlink linecard
10289 void devlink_linecard_destroy(struct devlink_linecard *linecard)
10291 struct devlink *devlink = linecard->devlink;
10293 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_DEL);
10294 mutex_lock(&devlink->linecards_lock);
10295 list_del(&linecard->list);
10296 devlink_linecard_types_fini(linecard);
10297 mutex_unlock(&devlink->linecards_lock);
10298 devlink_linecard_put(linecard);
10300 EXPORT_SYMBOL_GPL(devlink_linecard_destroy);
10303 * devlink_linecard_provision_set - Set provisioning on linecard
10305 * @linecard: devlink linecard
10306 * @type: linecard type
10308 * This is either called directly from the provision() op call or
10309 * as a result of the provision() op call asynchronously.
10311 void devlink_linecard_provision_set(struct devlink_linecard *linecard,
10314 mutex_lock(&linecard->state_lock);
10315 WARN_ON(linecard->type && strcmp(linecard->type, type));
10316 linecard->state = DEVLINK_LINECARD_STATE_PROVISIONED;
10317 linecard->type = type;
10318 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_NEW);
10319 mutex_unlock(&linecard->state_lock);
10321 EXPORT_SYMBOL_GPL(devlink_linecard_provision_set);
10324 * devlink_linecard_provision_clear - Clear provisioning on linecard
10326 * @linecard: devlink linecard
10328 * This is either called directly from the unprovision() op call or
10329 * as a result of the unprovision() op call asynchronously.
10331 void devlink_linecard_provision_clear(struct devlink_linecard *linecard)
10333 mutex_lock(&linecard->state_lock);
10334 WARN_ON(linecard->nested_devlink);
10335 linecard->state = DEVLINK_LINECARD_STATE_UNPROVISIONED;
10336 linecard->type = NULL;
10337 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_NEW);
10338 mutex_unlock(&linecard->state_lock);
10340 EXPORT_SYMBOL_GPL(devlink_linecard_provision_clear);
10343 * devlink_linecard_provision_fail - Fail provisioning on linecard
10345 * @linecard: devlink linecard
10347 * This is either called directly from the provision() op call or
10348 * as a result of the provision() op call asynchronously.
10350 void devlink_linecard_provision_fail(struct devlink_linecard *linecard)
10352 mutex_lock(&linecard->state_lock);
10353 WARN_ON(linecard->nested_devlink);
10354 linecard->state = DEVLINK_LINECARD_STATE_PROVISIONING_FAILED;
10355 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_NEW);
10356 mutex_unlock(&linecard->state_lock);
10358 EXPORT_SYMBOL_GPL(devlink_linecard_provision_fail);
10361 * devlink_linecard_activate - Set linecard active
10363 * @linecard: devlink linecard
10365 void devlink_linecard_activate(struct devlink_linecard *linecard)
10367 mutex_lock(&linecard->state_lock);
10368 WARN_ON(linecard->state != DEVLINK_LINECARD_STATE_PROVISIONED);
10369 linecard->state = DEVLINK_LINECARD_STATE_ACTIVE;
10370 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_NEW);
10371 mutex_unlock(&linecard->state_lock);
10373 EXPORT_SYMBOL_GPL(devlink_linecard_activate);
10376 * devlink_linecard_deactivate - Set linecard inactive
10378 * @linecard: devlink linecard
10380 void devlink_linecard_deactivate(struct devlink_linecard *linecard)
10382 mutex_lock(&linecard->state_lock);
10383 switch (linecard->state) {
10384 case DEVLINK_LINECARD_STATE_ACTIVE:
10385 linecard->state = DEVLINK_LINECARD_STATE_PROVISIONED;
10386 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_NEW);
10388 case DEVLINK_LINECARD_STATE_UNPROVISIONING:
10389 /* Line card is being deactivated as part
10390 * of unprovisioning flow.
10397 mutex_unlock(&linecard->state_lock);
10399 EXPORT_SYMBOL_GPL(devlink_linecard_deactivate);
10402 * devlink_linecard_nested_dl_set - Attach/detach nested devlink
10403 * instance to linecard.
10405 * @linecard: devlink linecard
10406 * @nested_devlink: devlink instance to attach or NULL to detach
10408 void devlink_linecard_nested_dl_set(struct devlink_linecard *linecard,
10409 struct devlink *nested_devlink)
10411 mutex_lock(&linecard->state_lock);
10412 linecard->nested_devlink = nested_devlink;
10413 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_NEW);
10414 mutex_unlock(&linecard->state_lock);
10416 EXPORT_SYMBOL_GPL(devlink_linecard_nested_dl_set);
10418 int devl_sb_register(struct devlink *devlink, unsigned int sb_index,
10419 u32 size, u16 ingress_pools_count,
10420 u16 egress_pools_count, u16 ingress_tc_count,
10421 u16 egress_tc_count)
10423 struct devlink_sb *devlink_sb;
10425 lockdep_assert_held(&devlink->lock);
10427 if (devlink_sb_index_exists(devlink, sb_index))
10430 devlink_sb = kzalloc(sizeof(*devlink_sb), GFP_KERNEL);
10433 devlink_sb->index = sb_index;
10434 devlink_sb->size = size;
10435 devlink_sb->ingress_pools_count = ingress_pools_count;
10436 devlink_sb->egress_pools_count = egress_pools_count;
10437 devlink_sb->ingress_tc_count = ingress_tc_count;
10438 devlink_sb->egress_tc_count = egress_tc_count;
10439 list_add_tail(&devlink_sb->list, &devlink->sb_list);
10442 EXPORT_SYMBOL_GPL(devl_sb_register);
10444 int devlink_sb_register(struct devlink *devlink, unsigned int sb_index,
10445 u32 size, u16 ingress_pools_count,
10446 u16 egress_pools_count, u16 ingress_tc_count,
10447 u16 egress_tc_count)
10451 devl_lock(devlink);
10452 err = devl_sb_register(devlink, sb_index, size, ingress_pools_count,
10453 egress_pools_count, ingress_tc_count,
10455 devl_unlock(devlink);
10458 EXPORT_SYMBOL_GPL(devlink_sb_register);
10460 void devl_sb_unregister(struct devlink *devlink, unsigned int sb_index)
10462 struct devlink_sb *devlink_sb;
10464 lockdep_assert_held(&devlink->lock);
10466 devlink_sb = devlink_sb_get_by_index(devlink, sb_index);
10467 WARN_ON(!devlink_sb);
10468 list_del(&devlink_sb->list);
10471 EXPORT_SYMBOL_GPL(devl_sb_unregister);
10473 void devlink_sb_unregister(struct devlink *devlink, unsigned int sb_index)
10475 devl_lock(devlink);
10476 devl_sb_unregister(devlink, sb_index);
10477 devl_unlock(devlink);
10479 EXPORT_SYMBOL_GPL(devlink_sb_unregister);
10482 * devl_dpipe_headers_register - register dpipe headers
10484 * @devlink: devlink
10485 * @dpipe_headers: dpipe header array
10487 * Register the headers supported by hardware.
10489 void devl_dpipe_headers_register(struct devlink *devlink,
10490 struct devlink_dpipe_headers *dpipe_headers)
10492 lockdep_assert_held(&devlink->lock);
10494 devlink->dpipe_headers = dpipe_headers;
10496 EXPORT_SYMBOL_GPL(devl_dpipe_headers_register);
10499 * devl_dpipe_headers_unregister - unregister dpipe headers
10501 * @devlink: devlink
10503 * Unregister the headers supported by hardware.
10505 void devl_dpipe_headers_unregister(struct devlink *devlink)
10507 lockdep_assert_held(&devlink->lock);
10509 devlink->dpipe_headers = NULL;
10511 EXPORT_SYMBOL_GPL(devl_dpipe_headers_unregister);
10514 * devlink_dpipe_table_counter_enabled - check if counter allocation
10516 * @devlink: devlink
10517 * @table_name: tables name
10519 * Used by driver to check if counter allocation is required.
10520 * After counter allocation is turned on the table entries
10521 * are updated to include counter statistics.
10523 * After that point on the driver must respect the counter
10524 * state so that each entry added to the table is added
10527 bool devlink_dpipe_table_counter_enabled(struct devlink *devlink,
10528 const char *table_name)
10530 struct devlink_dpipe_table *table;
10534 table = devlink_dpipe_table_find(&devlink->dpipe_table_list,
10535 table_name, devlink);
10538 enabled = table->counters_enabled;
10542 EXPORT_SYMBOL_GPL(devlink_dpipe_table_counter_enabled);
10545 * devl_dpipe_table_register - register dpipe table
10547 * @devlink: devlink
10548 * @table_name: table name
10549 * @table_ops: table ops
10551 * @counter_control_extern: external control for counters
10553 int devl_dpipe_table_register(struct devlink *devlink,
10554 const char *table_name,
10555 struct devlink_dpipe_table_ops *table_ops,
10556 void *priv, bool counter_control_extern)
10558 struct devlink_dpipe_table *table;
10560 lockdep_assert_held(&devlink->lock);
10562 if (WARN_ON(!table_ops->size_get))
10565 if (devlink_dpipe_table_find(&devlink->dpipe_table_list, table_name,
10569 table = kzalloc(sizeof(*table), GFP_KERNEL);
10573 table->name = table_name;
10574 table->table_ops = table_ops;
10575 table->priv = priv;
10576 table->counter_control_extern = counter_control_extern;
10578 list_add_tail_rcu(&table->list, &devlink->dpipe_table_list);
10582 EXPORT_SYMBOL_GPL(devl_dpipe_table_register);
10585 * devl_dpipe_table_unregister - unregister dpipe table
10587 * @devlink: devlink
10588 * @table_name: table name
10590 void devl_dpipe_table_unregister(struct devlink *devlink,
10591 const char *table_name)
10593 struct devlink_dpipe_table *table;
10595 lockdep_assert_held(&devlink->lock);
10597 table = devlink_dpipe_table_find(&devlink->dpipe_table_list,
10598 table_name, devlink);
10601 list_del_rcu(&table->list);
10602 kfree_rcu(table, rcu);
10604 EXPORT_SYMBOL_GPL(devl_dpipe_table_unregister);
10607 * devl_resource_register - devlink resource register
10609 * @devlink: devlink
10610 * @resource_name: resource's name
10611 * @resource_size: resource's size
10612 * @resource_id: resource's id
10613 * @parent_resource_id: resource's parent id
10614 * @size_params: size parameters
10616 * Generic resources should reuse the same names across drivers.
10617 * Please see the generic resources list at:
10618 * Documentation/networking/devlink/devlink-resource.rst
10620 int devl_resource_register(struct devlink *devlink,
10621 const char *resource_name,
10624 u64 parent_resource_id,
10625 const struct devlink_resource_size_params *size_params)
10627 struct devlink_resource *resource;
10628 struct list_head *resource_list;
10629 bool top_hierarchy;
10631 lockdep_assert_held(&devlink->lock);
10633 top_hierarchy = parent_resource_id == DEVLINK_RESOURCE_ID_PARENT_TOP;
10635 resource = devlink_resource_find(devlink, NULL, resource_id);
10639 resource = kzalloc(sizeof(*resource), GFP_KERNEL);
10643 if (top_hierarchy) {
10644 resource_list = &devlink->resource_list;
10646 struct devlink_resource *parent_resource;
10648 parent_resource = devlink_resource_find(devlink, NULL,
10649 parent_resource_id);
10650 if (parent_resource) {
10651 resource_list = &parent_resource->resource_list;
10652 resource->parent = parent_resource;
10659 resource->name = resource_name;
10660 resource->size = resource_size;
10661 resource->size_new = resource_size;
10662 resource->id = resource_id;
10663 resource->size_valid = true;
10664 memcpy(&resource->size_params, size_params,
10665 sizeof(resource->size_params));
10666 INIT_LIST_HEAD(&resource->resource_list);
10667 list_add_tail(&resource->list, resource_list);
10671 EXPORT_SYMBOL_GPL(devl_resource_register);
10674 * devlink_resource_register - devlink resource register
10676 * @devlink: devlink
10677 * @resource_name: resource's name
10678 * @resource_size: resource's size
10679 * @resource_id: resource's id
10680 * @parent_resource_id: resource's parent id
10681 * @size_params: size parameters
10683 * Generic resources should reuse the same names across drivers.
10684 * Please see the generic resources list at:
10685 * Documentation/networking/devlink/devlink-resource.rst
10687 * Context: Takes and release devlink->lock <mutex>.
10689 int devlink_resource_register(struct devlink *devlink,
10690 const char *resource_name,
10693 u64 parent_resource_id,
10694 const struct devlink_resource_size_params *size_params)
10698 devl_lock(devlink);
10699 err = devl_resource_register(devlink, resource_name, resource_size,
10700 resource_id, parent_resource_id, size_params);
10701 devl_unlock(devlink);
10704 EXPORT_SYMBOL_GPL(devlink_resource_register);
10706 static void devlink_resource_unregister(struct devlink *devlink,
10707 struct devlink_resource *resource)
10709 struct devlink_resource *tmp, *child_resource;
10711 list_for_each_entry_safe(child_resource, tmp, &resource->resource_list,
10713 devlink_resource_unregister(devlink, child_resource);
10714 list_del(&child_resource->list);
10715 kfree(child_resource);
10720 * devl_resources_unregister - free all resources
10722 * @devlink: devlink
10724 void devl_resources_unregister(struct devlink *devlink)
10726 struct devlink_resource *tmp, *child_resource;
10728 lockdep_assert_held(&devlink->lock);
10730 list_for_each_entry_safe(child_resource, tmp, &devlink->resource_list,
10732 devlink_resource_unregister(devlink, child_resource);
10733 list_del(&child_resource->list);
10734 kfree(child_resource);
10737 EXPORT_SYMBOL_GPL(devl_resources_unregister);
10740 * devlink_resources_unregister - free all resources
10742 * @devlink: devlink
10744 * Context: Takes and release devlink->lock <mutex>.
10746 void devlink_resources_unregister(struct devlink *devlink)
10748 devl_lock(devlink);
10749 devl_resources_unregister(devlink);
10750 devl_unlock(devlink);
10752 EXPORT_SYMBOL_GPL(devlink_resources_unregister);
10755 * devl_resource_size_get - get and update size
10757 * @devlink: devlink
10758 * @resource_id: the requested resource id
10759 * @p_resource_size: ptr to update
10761 int devl_resource_size_get(struct devlink *devlink,
10763 u64 *p_resource_size)
10765 struct devlink_resource *resource;
10767 lockdep_assert_held(&devlink->lock);
10769 resource = devlink_resource_find(devlink, NULL, resource_id);
10772 *p_resource_size = resource->size_new;
10773 resource->size = resource->size_new;
10776 EXPORT_SYMBOL_GPL(devl_resource_size_get);
10779 * devl_dpipe_table_resource_set - set the resource id
10781 * @devlink: devlink
10782 * @table_name: table name
10783 * @resource_id: resource id
10784 * @resource_units: number of resource's units consumed per table's entry
10786 int devl_dpipe_table_resource_set(struct devlink *devlink,
10787 const char *table_name, u64 resource_id,
10788 u64 resource_units)
10790 struct devlink_dpipe_table *table;
10792 table = devlink_dpipe_table_find(&devlink->dpipe_table_list,
10793 table_name, devlink);
10797 table->resource_id = resource_id;
10798 table->resource_units = resource_units;
10799 table->resource_valid = true;
10802 EXPORT_SYMBOL_GPL(devl_dpipe_table_resource_set);
10805 * devl_resource_occ_get_register - register occupancy getter
10807 * @devlink: devlink
10808 * @resource_id: resource id
10809 * @occ_get: occupancy getter callback
10810 * @occ_get_priv: occupancy getter callback priv
10812 void devl_resource_occ_get_register(struct devlink *devlink,
10814 devlink_resource_occ_get_t *occ_get,
10815 void *occ_get_priv)
10817 struct devlink_resource *resource;
10819 lockdep_assert_held(&devlink->lock);
10821 resource = devlink_resource_find(devlink, NULL, resource_id);
10822 if (WARN_ON(!resource))
10824 WARN_ON(resource->occ_get);
10826 resource->occ_get = occ_get;
10827 resource->occ_get_priv = occ_get_priv;
10829 EXPORT_SYMBOL_GPL(devl_resource_occ_get_register);
10832 * devlink_resource_occ_get_register - register occupancy getter
10834 * @devlink: devlink
10835 * @resource_id: resource id
10836 * @occ_get: occupancy getter callback
10837 * @occ_get_priv: occupancy getter callback priv
10839 * Context: Takes and release devlink->lock <mutex>.
10841 void devlink_resource_occ_get_register(struct devlink *devlink,
10843 devlink_resource_occ_get_t *occ_get,
10844 void *occ_get_priv)
10846 devl_lock(devlink);
10847 devl_resource_occ_get_register(devlink, resource_id,
10848 occ_get, occ_get_priv);
10849 devl_unlock(devlink);
10851 EXPORT_SYMBOL_GPL(devlink_resource_occ_get_register);
10854 * devl_resource_occ_get_unregister - unregister occupancy getter
10856 * @devlink: devlink
10857 * @resource_id: resource id
10859 void devl_resource_occ_get_unregister(struct devlink *devlink,
10862 struct devlink_resource *resource;
10864 lockdep_assert_held(&devlink->lock);
10866 resource = devlink_resource_find(devlink, NULL, resource_id);
10867 if (WARN_ON(!resource))
10869 WARN_ON(!resource->occ_get);
10871 resource->occ_get = NULL;
10872 resource->occ_get_priv = NULL;
10874 EXPORT_SYMBOL_GPL(devl_resource_occ_get_unregister);
10877 * devlink_resource_occ_get_unregister - unregister occupancy getter
10879 * @devlink: devlink
10880 * @resource_id: resource id
10882 * Context: Takes and release devlink->lock <mutex>.
10884 void devlink_resource_occ_get_unregister(struct devlink *devlink,
10887 devl_lock(devlink);
10888 devl_resource_occ_get_unregister(devlink, resource_id);
10889 devl_unlock(devlink);
10891 EXPORT_SYMBOL_GPL(devlink_resource_occ_get_unregister);
10893 static int devlink_param_verify(const struct devlink_param *param)
10895 if (!param || !param->name || !param->supported_cmodes)
10897 if (param->generic)
10898 return devlink_param_generic_verify(param);
10900 return devlink_param_driver_verify(param);
10904 * devlink_params_register - register configuration parameters
10906 * @devlink: devlink
10907 * @params: configuration parameters array
10908 * @params_count: number of parameters provided
10910 * Register the configuration parameters supported by the driver.
10912 int devlink_params_register(struct devlink *devlink,
10913 const struct devlink_param *params,
10914 size_t params_count)
10916 const struct devlink_param *param = params;
10919 for (i = 0; i < params_count; i++, param++) {
10920 err = devlink_param_register(devlink, param);
10930 for (param--; i > 0; i--, param--)
10931 devlink_param_unregister(devlink, param);
10934 EXPORT_SYMBOL_GPL(devlink_params_register);
10937 * devlink_params_unregister - unregister configuration parameters
10938 * @devlink: devlink
10939 * @params: configuration parameters to unregister
10940 * @params_count: number of parameters provided
10942 void devlink_params_unregister(struct devlink *devlink,
10943 const struct devlink_param *params,
10944 size_t params_count)
10946 const struct devlink_param *param = params;
10949 for (i = 0; i < params_count; i++, param++)
10950 devlink_param_unregister(devlink, param);
10952 EXPORT_SYMBOL_GPL(devlink_params_unregister);
10955 * devlink_param_register - register one configuration parameter
10957 * @devlink: devlink
10958 * @param: one configuration parameter
10960 * Register the configuration parameter supported by the driver.
10961 * Return: returns 0 on successful registration or error code otherwise.
10963 int devlink_param_register(struct devlink *devlink,
10964 const struct devlink_param *param)
10966 struct devlink_param_item *param_item;
10968 WARN_ON(devlink_param_verify(param));
10969 WARN_ON(devlink_param_find_by_name(&devlink->param_list, param->name));
10971 if (param->supported_cmodes == BIT(DEVLINK_PARAM_CMODE_DRIVERINIT))
10972 WARN_ON(param->get || param->set);
10974 WARN_ON(!param->get || !param->set);
10976 param_item = kzalloc(sizeof(*param_item), GFP_KERNEL);
10980 param_item->param = param;
10982 list_add_tail(¶m_item->list, &devlink->param_list);
10983 devlink_param_notify(devlink, 0, param_item, DEVLINK_CMD_PARAM_NEW);
10986 EXPORT_SYMBOL_GPL(devlink_param_register);
10989 * devlink_param_unregister - unregister one configuration parameter
10990 * @devlink: devlink
10991 * @param: configuration parameter to unregister
10993 void devlink_param_unregister(struct devlink *devlink,
10994 const struct devlink_param *param)
10996 struct devlink_param_item *param_item;
10999 devlink_param_find_by_name(&devlink->param_list, param->name);
11000 WARN_ON(!param_item);
11001 devlink_param_notify(devlink, 0, param_item, DEVLINK_CMD_PARAM_DEL);
11002 list_del(¶m_item->list);
11005 EXPORT_SYMBOL_GPL(devlink_param_unregister);
11008 * devlink_param_driverinit_value_get - get configuration parameter
11009 * value for driver initializing
11011 * @devlink: devlink
11012 * @param_id: parameter ID
11013 * @init_val: value of parameter in driverinit configuration mode
11015 * This function should be used by the driver to get driverinit
11016 * configuration for initialization after reload command.
11018 int devlink_param_driverinit_value_get(struct devlink *devlink, u32 param_id,
11019 union devlink_param_value *init_val)
11021 struct devlink_param_item *param_item;
11023 if (!devlink_reload_supported(devlink->ops))
11024 return -EOPNOTSUPP;
11026 param_item = devlink_param_find_by_id(&devlink->param_list, param_id);
11030 if (!param_item->driverinit_value_valid ||
11031 !devlink_param_cmode_is_supported(param_item->param,
11032 DEVLINK_PARAM_CMODE_DRIVERINIT))
11033 return -EOPNOTSUPP;
11035 if (param_item->param->type == DEVLINK_PARAM_TYPE_STRING)
11036 strcpy(init_val->vstr, param_item->driverinit_value.vstr);
11038 *init_val = param_item->driverinit_value;
11042 EXPORT_SYMBOL_GPL(devlink_param_driverinit_value_get);
11045 * devlink_param_driverinit_value_set - set value of configuration
11046 * parameter for driverinit
11047 * configuration mode
11049 * @devlink: devlink
11050 * @param_id: parameter ID
11051 * @init_val: value of parameter to set for driverinit configuration mode
11053 * This function should be used by the driver to set driverinit
11054 * configuration mode default value.
11056 int devlink_param_driverinit_value_set(struct devlink *devlink, u32 param_id,
11057 union devlink_param_value init_val)
11059 struct devlink_param_item *param_item;
11061 param_item = devlink_param_find_by_id(&devlink->param_list, param_id);
11065 if (!devlink_param_cmode_is_supported(param_item->param,
11066 DEVLINK_PARAM_CMODE_DRIVERINIT))
11067 return -EOPNOTSUPP;
11069 if (param_item->param->type == DEVLINK_PARAM_TYPE_STRING)
11070 strcpy(param_item->driverinit_value.vstr, init_val.vstr);
11072 param_item->driverinit_value = init_val;
11073 param_item->driverinit_value_valid = true;
11075 devlink_param_notify(devlink, 0, param_item, DEVLINK_CMD_PARAM_NEW);
11078 EXPORT_SYMBOL_GPL(devlink_param_driverinit_value_set);
11081 * devlink_param_value_changed - notify devlink on a parameter's value
11082 * change. Should be called by the driver
11083 * right after the change.
11085 * @devlink: devlink
11086 * @param_id: parameter ID
11088 * This function should be used by the driver to notify devlink on value
11089 * change, excluding driverinit configuration mode.
11090 * For driverinit configuration mode driver should use the function
11092 void devlink_param_value_changed(struct devlink *devlink, u32 param_id)
11094 struct devlink_param_item *param_item;
11096 param_item = devlink_param_find_by_id(&devlink->param_list, param_id);
11097 WARN_ON(!param_item);
11099 devlink_param_notify(devlink, 0, param_item, DEVLINK_CMD_PARAM_NEW);
11101 EXPORT_SYMBOL_GPL(devlink_param_value_changed);
11104 * devl_region_create - create a new address region
11106 * @devlink: devlink
11107 * @ops: region operations and name
11108 * @region_max_snapshots: Maximum supported number of snapshots for region
11109 * @region_size: size of region
11111 struct devlink_region *devl_region_create(struct devlink *devlink,
11112 const struct devlink_region_ops *ops,
11113 u32 region_max_snapshots,
11116 struct devlink_region *region;
11118 devl_assert_locked(devlink);
11120 if (WARN_ON(!ops) || WARN_ON(!ops->destructor))
11121 return ERR_PTR(-EINVAL);
11123 if (devlink_region_get_by_name(devlink, ops->name))
11124 return ERR_PTR(-EEXIST);
11126 region = kzalloc(sizeof(*region), GFP_KERNEL);
11128 return ERR_PTR(-ENOMEM);
11130 region->devlink = devlink;
11131 region->max_snapshots = region_max_snapshots;
11133 region->size = region_size;
11134 INIT_LIST_HEAD(®ion->snapshot_list);
11135 mutex_init(®ion->snapshot_lock);
11136 list_add_tail(®ion->list, &devlink->region_list);
11137 devlink_nl_region_notify(region, NULL, DEVLINK_CMD_REGION_NEW);
11141 EXPORT_SYMBOL_GPL(devl_region_create);
11144 * devlink_region_create - create a new address region
11146 * @devlink: devlink
11147 * @ops: region operations and name
11148 * @region_max_snapshots: Maximum supported number of snapshots for region
11149 * @region_size: size of region
11151 * Context: Takes and release devlink->lock <mutex>.
11153 struct devlink_region *
11154 devlink_region_create(struct devlink *devlink,
11155 const struct devlink_region_ops *ops,
11156 u32 region_max_snapshots, u64 region_size)
11158 struct devlink_region *region;
11160 devl_lock(devlink);
11161 region = devl_region_create(devlink, ops, region_max_snapshots,
11163 devl_unlock(devlink);
11166 EXPORT_SYMBOL_GPL(devlink_region_create);
11169 * devlink_port_region_create - create a new address region for a port
11171 * @port: devlink port
11172 * @ops: region operations and name
11173 * @region_max_snapshots: Maximum supported number of snapshots for region
11174 * @region_size: size of region
11176 * Context: Takes and release devlink->lock <mutex>.
11178 struct devlink_region *
11179 devlink_port_region_create(struct devlink_port *port,
11180 const struct devlink_port_region_ops *ops,
11181 u32 region_max_snapshots, u64 region_size)
11183 struct devlink *devlink = port->devlink;
11184 struct devlink_region *region;
11187 ASSERT_DEVLINK_PORT_INITIALIZED(port);
11189 if (WARN_ON(!ops) || WARN_ON(!ops->destructor))
11190 return ERR_PTR(-EINVAL);
11192 devl_lock(devlink);
11194 if (devlink_port_region_get_by_name(port, ops->name)) {
11199 region = kzalloc(sizeof(*region), GFP_KERNEL);
11205 region->devlink = devlink;
11206 region->port = port;
11207 region->max_snapshots = region_max_snapshots;
11208 region->port_ops = ops;
11209 region->size = region_size;
11210 INIT_LIST_HEAD(®ion->snapshot_list);
11211 mutex_init(®ion->snapshot_lock);
11212 list_add_tail(®ion->list, &port->region_list);
11213 devlink_nl_region_notify(region, NULL, DEVLINK_CMD_REGION_NEW);
11215 devl_unlock(devlink);
11219 devl_unlock(devlink);
11220 return ERR_PTR(err);
11222 EXPORT_SYMBOL_GPL(devlink_port_region_create);
11225 * devl_region_destroy - destroy address region
11227 * @region: devlink region to destroy
11229 void devl_region_destroy(struct devlink_region *region)
11231 struct devlink *devlink = region->devlink;
11232 struct devlink_snapshot *snapshot, *ts;
11234 devl_assert_locked(devlink);
11236 /* Free all snapshots of region */
11237 mutex_lock(®ion->snapshot_lock);
11238 list_for_each_entry_safe(snapshot, ts, ®ion->snapshot_list, list)
11239 devlink_region_snapshot_del(region, snapshot);
11240 mutex_unlock(®ion->snapshot_lock);
11242 list_del(®ion->list);
11243 mutex_destroy(®ion->snapshot_lock);
11245 devlink_nl_region_notify(region, NULL, DEVLINK_CMD_REGION_DEL);
11248 EXPORT_SYMBOL_GPL(devl_region_destroy);
11251 * devlink_region_destroy - destroy address region
11253 * @region: devlink region to destroy
11255 * Context: Takes and release devlink->lock <mutex>.
11257 void devlink_region_destroy(struct devlink_region *region)
11259 struct devlink *devlink = region->devlink;
11261 devl_lock(devlink);
11262 devl_region_destroy(region);
11263 devl_unlock(devlink);
11265 EXPORT_SYMBOL_GPL(devlink_region_destroy);
11268 * devlink_region_snapshot_id_get - get snapshot ID
11270 * This callback should be called when adding a new snapshot,
11271 * Driver should use the same id for multiple snapshots taken
11272 * on multiple regions at the same time/by the same trigger.
11274 * The caller of this function must use devlink_region_snapshot_id_put
11275 * when finished creating regions using this id.
11277 * Returns zero on success, or a negative error code on failure.
11279 * @devlink: devlink
11280 * @id: storage to return id
11282 int devlink_region_snapshot_id_get(struct devlink *devlink, u32 *id)
11284 return __devlink_region_snapshot_id_get(devlink, id);
11286 EXPORT_SYMBOL_GPL(devlink_region_snapshot_id_get);
11289 * devlink_region_snapshot_id_put - put snapshot ID reference
11291 * This should be called by a driver after finishing creating snapshots
11292 * with an id. Doing so ensures that the ID can later be released in the
11293 * event that all snapshots using it have been destroyed.
11295 * @devlink: devlink
11296 * @id: id to release reference on
11298 void devlink_region_snapshot_id_put(struct devlink *devlink, u32 id)
11300 __devlink_snapshot_id_decrement(devlink, id);
11302 EXPORT_SYMBOL_GPL(devlink_region_snapshot_id_put);
11305 * devlink_region_snapshot_create - create a new snapshot
11306 * This will add a new snapshot of a region. The snapshot
11307 * will be stored on the region struct and can be accessed
11308 * from devlink. This is useful for future analyses of snapshots.
11309 * Multiple snapshots can be created on a region.
11310 * The @snapshot_id should be obtained using the getter function.
11312 * @region: devlink region of the snapshot
11313 * @data: snapshot data
11314 * @snapshot_id: snapshot id to be created
11316 int devlink_region_snapshot_create(struct devlink_region *region,
11317 u8 *data, u32 snapshot_id)
11321 mutex_lock(®ion->snapshot_lock);
11322 err = __devlink_region_snapshot_create(region, data, snapshot_id);
11323 mutex_unlock(®ion->snapshot_lock);
11326 EXPORT_SYMBOL_GPL(devlink_region_snapshot_create);
11328 #define DEVLINK_TRAP(_id, _type) \
11330 .type = DEVLINK_TRAP_TYPE_##_type, \
11331 .id = DEVLINK_TRAP_GENERIC_ID_##_id, \
11332 .name = DEVLINK_TRAP_GENERIC_NAME_##_id, \
11335 static const struct devlink_trap devlink_trap_generic[] = {
11336 DEVLINK_TRAP(SMAC_MC, DROP),
11337 DEVLINK_TRAP(VLAN_TAG_MISMATCH, DROP),
11338 DEVLINK_TRAP(INGRESS_VLAN_FILTER, DROP),
11339 DEVLINK_TRAP(INGRESS_STP_FILTER, DROP),
11340 DEVLINK_TRAP(EMPTY_TX_LIST, DROP),
11341 DEVLINK_TRAP(PORT_LOOPBACK_FILTER, DROP),
11342 DEVLINK_TRAP(BLACKHOLE_ROUTE, DROP),
11343 DEVLINK_TRAP(TTL_ERROR, EXCEPTION),
11344 DEVLINK_TRAP(TAIL_DROP, DROP),
11345 DEVLINK_TRAP(NON_IP_PACKET, DROP),
11346 DEVLINK_TRAP(UC_DIP_MC_DMAC, DROP),
11347 DEVLINK_TRAP(DIP_LB, DROP),
11348 DEVLINK_TRAP(SIP_MC, DROP),
11349 DEVLINK_TRAP(SIP_LB, DROP),
11350 DEVLINK_TRAP(CORRUPTED_IP_HDR, DROP),
11351 DEVLINK_TRAP(IPV4_SIP_BC, DROP),
11352 DEVLINK_TRAP(IPV6_MC_DIP_RESERVED_SCOPE, DROP),
11353 DEVLINK_TRAP(IPV6_MC_DIP_INTERFACE_LOCAL_SCOPE, DROP),
11354 DEVLINK_TRAP(MTU_ERROR, EXCEPTION),
11355 DEVLINK_TRAP(UNRESOLVED_NEIGH, EXCEPTION),
11356 DEVLINK_TRAP(RPF, EXCEPTION),
11357 DEVLINK_TRAP(REJECT_ROUTE, EXCEPTION),
11358 DEVLINK_TRAP(IPV4_LPM_UNICAST_MISS, EXCEPTION),
11359 DEVLINK_TRAP(IPV6_LPM_UNICAST_MISS, EXCEPTION),
11360 DEVLINK_TRAP(NON_ROUTABLE, DROP),
11361 DEVLINK_TRAP(DECAP_ERROR, EXCEPTION),
11362 DEVLINK_TRAP(OVERLAY_SMAC_MC, DROP),
11363 DEVLINK_TRAP(INGRESS_FLOW_ACTION_DROP, DROP),
11364 DEVLINK_TRAP(EGRESS_FLOW_ACTION_DROP, DROP),
11365 DEVLINK_TRAP(STP, CONTROL),
11366 DEVLINK_TRAP(LACP, CONTROL),
11367 DEVLINK_TRAP(LLDP, CONTROL),
11368 DEVLINK_TRAP(IGMP_QUERY, CONTROL),
11369 DEVLINK_TRAP(IGMP_V1_REPORT, CONTROL),
11370 DEVLINK_TRAP(IGMP_V2_REPORT, CONTROL),
11371 DEVLINK_TRAP(IGMP_V3_REPORT, CONTROL),
11372 DEVLINK_TRAP(IGMP_V2_LEAVE, CONTROL),
11373 DEVLINK_TRAP(MLD_QUERY, CONTROL),
11374 DEVLINK_TRAP(MLD_V1_REPORT, CONTROL),
11375 DEVLINK_TRAP(MLD_V2_REPORT, CONTROL),
11376 DEVLINK_TRAP(MLD_V1_DONE, CONTROL),
11377 DEVLINK_TRAP(IPV4_DHCP, CONTROL),
11378 DEVLINK_TRAP(IPV6_DHCP, CONTROL),
11379 DEVLINK_TRAP(ARP_REQUEST, CONTROL),
11380 DEVLINK_TRAP(ARP_RESPONSE, CONTROL),
11381 DEVLINK_TRAP(ARP_OVERLAY, CONTROL),
11382 DEVLINK_TRAP(IPV6_NEIGH_SOLICIT, CONTROL),
11383 DEVLINK_TRAP(IPV6_NEIGH_ADVERT, CONTROL),
11384 DEVLINK_TRAP(IPV4_BFD, CONTROL),
11385 DEVLINK_TRAP(IPV6_BFD, CONTROL),
11386 DEVLINK_TRAP(IPV4_OSPF, CONTROL),
11387 DEVLINK_TRAP(IPV6_OSPF, CONTROL),
11388 DEVLINK_TRAP(IPV4_BGP, CONTROL),
11389 DEVLINK_TRAP(IPV6_BGP, CONTROL),
11390 DEVLINK_TRAP(IPV4_VRRP, CONTROL),
11391 DEVLINK_TRAP(IPV6_VRRP, CONTROL),
11392 DEVLINK_TRAP(IPV4_PIM, CONTROL),
11393 DEVLINK_TRAP(IPV6_PIM, CONTROL),
11394 DEVLINK_TRAP(UC_LB, CONTROL),
11395 DEVLINK_TRAP(LOCAL_ROUTE, CONTROL),
11396 DEVLINK_TRAP(EXTERNAL_ROUTE, CONTROL),
11397 DEVLINK_TRAP(IPV6_UC_DIP_LINK_LOCAL_SCOPE, CONTROL),
11398 DEVLINK_TRAP(IPV6_DIP_ALL_NODES, CONTROL),
11399 DEVLINK_TRAP(IPV6_DIP_ALL_ROUTERS, CONTROL),
11400 DEVLINK_TRAP(IPV6_ROUTER_SOLICIT, CONTROL),
11401 DEVLINK_TRAP(IPV6_ROUTER_ADVERT, CONTROL),
11402 DEVLINK_TRAP(IPV6_REDIRECT, CONTROL),
11403 DEVLINK_TRAP(IPV4_ROUTER_ALERT, CONTROL),
11404 DEVLINK_TRAP(IPV6_ROUTER_ALERT, CONTROL),
11405 DEVLINK_TRAP(PTP_EVENT, CONTROL),
11406 DEVLINK_TRAP(PTP_GENERAL, CONTROL),
11407 DEVLINK_TRAP(FLOW_ACTION_SAMPLE, CONTROL),
11408 DEVLINK_TRAP(FLOW_ACTION_TRAP, CONTROL),
11409 DEVLINK_TRAP(EARLY_DROP, DROP),
11410 DEVLINK_TRAP(VXLAN_PARSING, DROP),
11411 DEVLINK_TRAP(LLC_SNAP_PARSING, DROP),
11412 DEVLINK_TRAP(VLAN_PARSING, DROP),
11413 DEVLINK_TRAP(PPPOE_PPP_PARSING, DROP),
11414 DEVLINK_TRAP(MPLS_PARSING, DROP),
11415 DEVLINK_TRAP(ARP_PARSING, DROP),
11416 DEVLINK_TRAP(IP_1_PARSING, DROP),
11417 DEVLINK_TRAP(IP_N_PARSING, DROP),
11418 DEVLINK_TRAP(GRE_PARSING, DROP),
11419 DEVLINK_TRAP(UDP_PARSING, DROP),
11420 DEVLINK_TRAP(TCP_PARSING, DROP),
11421 DEVLINK_TRAP(IPSEC_PARSING, DROP),
11422 DEVLINK_TRAP(SCTP_PARSING, DROP),
11423 DEVLINK_TRAP(DCCP_PARSING, DROP),
11424 DEVLINK_TRAP(GTP_PARSING, DROP),
11425 DEVLINK_TRAP(ESP_PARSING, DROP),
11426 DEVLINK_TRAP(BLACKHOLE_NEXTHOP, DROP),
11427 DEVLINK_TRAP(DMAC_FILTER, DROP),
11428 DEVLINK_TRAP(EAPOL, CONTROL),
11429 DEVLINK_TRAP(LOCKED_PORT, DROP),
11432 #define DEVLINK_TRAP_GROUP(_id) \
11434 .id = DEVLINK_TRAP_GROUP_GENERIC_ID_##_id, \
11435 .name = DEVLINK_TRAP_GROUP_GENERIC_NAME_##_id, \
11438 static const struct devlink_trap_group devlink_trap_group_generic[] = {
11439 DEVLINK_TRAP_GROUP(L2_DROPS),
11440 DEVLINK_TRAP_GROUP(L3_DROPS),
11441 DEVLINK_TRAP_GROUP(L3_EXCEPTIONS),
11442 DEVLINK_TRAP_GROUP(BUFFER_DROPS),
11443 DEVLINK_TRAP_GROUP(TUNNEL_DROPS),
11444 DEVLINK_TRAP_GROUP(ACL_DROPS),
11445 DEVLINK_TRAP_GROUP(STP),
11446 DEVLINK_TRAP_GROUP(LACP),
11447 DEVLINK_TRAP_GROUP(LLDP),
11448 DEVLINK_TRAP_GROUP(MC_SNOOPING),
11449 DEVLINK_TRAP_GROUP(DHCP),
11450 DEVLINK_TRAP_GROUP(NEIGH_DISCOVERY),
11451 DEVLINK_TRAP_GROUP(BFD),
11452 DEVLINK_TRAP_GROUP(OSPF),
11453 DEVLINK_TRAP_GROUP(BGP),
11454 DEVLINK_TRAP_GROUP(VRRP),
11455 DEVLINK_TRAP_GROUP(PIM),
11456 DEVLINK_TRAP_GROUP(UC_LB),
11457 DEVLINK_TRAP_GROUP(LOCAL_DELIVERY),
11458 DEVLINK_TRAP_GROUP(EXTERNAL_DELIVERY),
11459 DEVLINK_TRAP_GROUP(IPV6),
11460 DEVLINK_TRAP_GROUP(PTP_EVENT),
11461 DEVLINK_TRAP_GROUP(PTP_GENERAL),
11462 DEVLINK_TRAP_GROUP(ACL_SAMPLE),
11463 DEVLINK_TRAP_GROUP(ACL_TRAP),
11464 DEVLINK_TRAP_GROUP(PARSER_ERROR_DROPS),
11465 DEVLINK_TRAP_GROUP(EAPOL),
11468 static int devlink_trap_generic_verify(const struct devlink_trap *trap)
11470 if (trap->id > DEVLINK_TRAP_GENERIC_ID_MAX)
11473 if (strcmp(trap->name, devlink_trap_generic[trap->id].name))
11476 if (trap->type != devlink_trap_generic[trap->id].type)
11482 static int devlink_trap_driver_verify(const struct devlink_trap *trap)
11486 if (trap->id <= DEVLINK_TRAP_GENERIC_ID_MAX)
11489 for (i = 0; i < ARRAY_SIZE(devlink_trap_generic); i++) {
11490 if (!strcmp(trap->name, devlink_trap_generic[i].name))
11497 static int devlink_trap_verify(const struct devlink_trap *trap)
11499 if (!trap || !trap->name)
11503 return devlink_trap_generic_verify(trap);
11505 return devlink_trap_driver_verify(trap);
11509 devlink_trap_group_generic_verify(const struct devlink_trap_group *group)
11511 if (group->id > DEVLINK_TRAP_GROUP_GENERIC_ID_MAX)
11514 if (strcmp(group->name, devlink_trap_group_generic[group->id].name))
11521 devlink_trap_group_driver_verify(const struct devlink_trap_group *group)
11525 if (group->id <= DEVLINK_TRAP_GROUP_GENERIC_ID_MAX)
11528 for (i = 0; i < ARRAY_SIZE(devlink_trap_group_generic); i++) {
11529 if (!strcmp(group->name, devlink_trap_group_generic[i].name))
11536 static int devlink_trap_group_verify(const struct devlink_trap_group *group)
11538 if (group->generic)
11539 return devlink_trap_group_generic_verify(group);
11541 return devlink_trap_group_driver_verify(group);
11545 devlink_trap_group_notify(struct devlink *devlink,
11546 const struct devlink_trap_group_item *group_item,
11547 enum devlink_command cmd)
11549 struct sk_buff *msg;
11552 WARN_ON_ONCE(cmd != DEVLINK_CMD_TRAP_GROUP_NEW &&
11553 cmd != DEVLINK_CMD_TRAP_GROUP_DEL);
11554 if (!xa_get_mark(&devlinks, devlink->index, DEVLINK_REGISTERED))
11557 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
11561 err = devlink_nl_trap_group_fill(msg, devlink, group_item, cmd, 0, 0,
11568 genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink),
11569 msg, 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
11573 devlink_trap_item_group_link(struct devlink *devlink,
11574 struct devlink_trap_item *trap_item)
11576 u16 group_id = trap_item->trap->init_group_id;
11577 struct devlink_trap_group_item *group_item;
11579 group_item = devlink_trap_group_item_lookup_by_id(devlink, group_id);
11580 if (WARN_ON_ONCE(!group_item))
11583 trap_item->group_item = group_item;
11588 static void devlink_trap_notify(struct devlink *devlink,
11589 const struct devlink_trap_item *trap_item,
11590 enum devlink_command cmd)
11592 struct sk_buff *msg;
11595 WARN_ON_ONCE(cmd != DEVLINK_CMD_TRAP_NEW &&
11596 cmd != DEVLINK_CMD_TRAP_DEL);
11597 if (!xa_get_mark(&devlinks, devlink->index, DEVLINK_REGISTERED))
11600 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
11604 err = devlink_nl_trap_fill(msg, devlink, trap_item, cmd, 0, 0, 0);
11610 genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink),
11611 msg, 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
11615 devlink_trap_register(struct devlink *devlink,
11616 const struct devlink_trap *trap, void *priv)
11618 struct devlink_trap_item *trap_item;
11621 if (devlink_trap_item_lookup(devlink, trap->name))
11624 trap_item = kzalloc(sizeof(*trap_item), GFP_KERNEL);
11628 trap_item->stats = netdev_alloc_pcpu_stats(struct devlink_stats);
11629 if (!trap_item->stats) {
11631 goto err_stats_alloc;
11634 trap_item->trap = trap;
11635 trap_item->action = trap->init_action;
11636 trap_item->priv = priv;
11638 err = devlink_trap_item_group_link(devlink, trap_item);
11640 goto err_group_link;
11642 err = devlink->ops->trap_init(devlink, trap, trap_item);
11644 goto err_trap_init;
11646 list_add_tail(&trap_item->list, &devlink->trap_list);
11647 devlink_trap_notify(devlink, trap_item, DEVLINK_CMD_TRAP_NEW);
11653 free_percpu(trap_item->stats);
11659 static void devlink_trap_unregister(struct devlink *devlink,
11660 const struct devlink_trap *trap)
11662 struct devlink_trap_item *trap_item;
11664 trap_item = devlink_trap_item_lookup(devlink, trap->name);
11665 if (WARN_ON_ONCE(!trap_item))
11668 devlink_trap_notify(devlink, trap_item, DEVLINK_CMD_TRAP_DEL);
11669 list_del(&trap_item->list);
11670 if (devlink->ops->trap_fini)
11671 devlink->ops->trap_fini(devlink, trap, trap_item);
11672 free_percpu(trap_item->stats);
11676 static void devlink_trap_disable(struct devlink *devlink,
11677 const struct devlink_trap *trap)
11679 struct devlink_trap_item *trap_item;
11681 trap_item = devlink_trap_item_lookup(devlink, trap->name);
11682 if (WARN_ON_ONCE(!trap_item))
11685 devlink->ops->trap_action_set(devlink, trap, DEVLINK_TRAP_ACTION_DROP,
11687 trap_item->action = DEVLINK_TRAP_ACTION_DROP;
11691 * devl_traps_register - Register packet traps with devlink.
11692 * @devlink: devlink.
11693 * @traps: Packet traps.
11694 * @traps_count: Count of provided packet traps.
11695 * @priv: Driver private information.
11697 * Return: Non-zero value on failure.
11699 int devl_traps_register(struct devlink *devlink,
11700 const struct devlink_trap *traps,
11701 size_t traps_count, void *priv)
11705 if (!devlink->ops->trap_init || !devlink->ops->trap_action_set)
11708 devl_assert_locked(devlink);
11709 for (i = 0; i < traps_count; i++) {
11710 const struct devlink_trap *trap = &traps[i];
11712 err = devlink_trap_verify(trap);
11714 goto err_trap_verify;
11716 err = devlink_trap_register(devlink, trap, priv);
11718 goto err_trap_register;
11725 for (i--; i >= 0; i--)
11726 devlink_trap_unregister(devlink, &traps[i]);
11729 EXPORT_SYMBOL_GPL(devl_traps_register);
11732 * devlink_traps_register - Register packet traps with devlink.
11733 * @devlink: devlink.
11734 * @traps: Packet traps.
11735 * @traps_count: Count of provided packet traps.
11736 * @priv: Driver private information.
11738 * Context: Takes and release devlink->lock <mutex>.
11740 * Return: Non-zero value on failure.
11742 int devlink_traps_register(struct devlink *devlink,
11743 const struct devlink_trap *traps,
11744 size_t traps_count, void *priv)
11748 devl_lock(devlink);
11749 err = devl_traps_register(devlink, traps, traps_count, priv);
11750 devl_unlock(devlink);
11753 EXPORT_SYMBOL_GPL(devlink_traps_register);
11756 * devl_traps_unregister - Unregister packet traps from devlink.
11757 * @devlink: devlink.
11758 * @traps: Packet traps.
11759 * @traps_count: Count of provided packet traps.
11761 void devl_traps_unregister(struct devlink *devlink,
11762 const struct devlink_trap *traps,
11763 size_t traps_count)
11767 devl_assert_locked(devlink);
11768 /* Make sure we do not have any packets in-flight while unregistering
11769 * traps by disabling all of them and waiting for a grace period.
11771 for (i = traps_count - 1; i >= 0; i--)
11772 devlink_trap_disable(devlink, &traps[i]);
11774 for (i = traps_count - 1; i >= 0; i--)
11775 devlink_trap_unregister(devlink, &traps[i]);
11777 EXPORT_SYMBOL_GPL(devl_traps_unregister);
11780 * devlink_traps_unregister - Unregister packet traps from devlink.
11781 * @devlink: devlink.
11782 * @traps: Packet traps.
11783 * @traps_count: Count of provided packet traps.
11785 * Context: Takes and release devlink->lock <mutex>.
11787 void devlink_traps_unregister(struct devlink *devlink,
11788 const struct devlink_trap *traps,
11789 size_t traps_count)
11791 devl_lock(devlink);
11792 devl_traps_unregister(devlink, traps, traps_count);
11793 devl_unlock(devlink);
11795 EXPORT_SYMBOL_GPL(devlink_traps_unregister);
11798 devlink_trap_stats_update(struct devlink_stats __percpu *trap_stats,
11801 struct devlink_stats *stats;
11803 stats = this_cpu_ptr(trap_stats);
11804 u64_stats_update_begin(&stats->syncp);
11805 u64_stats_add(&stats->rx_bytes, skb_len);
11806 u64_stats_inc(&stats->rx_packets);
11807 u64_stats_update_end(&stats->syncp);
11811 devlink_trap_report_metadata_set(struct devlink_trap_metadata *metadata,
11812 const struct devlink_trap_item *trap_item,
11813 struct devlink_port *in_devlink_port,
11814 const struct flow_action_cookie *fa_cookie)
11816 metadata->trap_name = trap_item->trap->name;
11817 metadata->trap_group_name = trap_item->group_item->group->name;
11818 metadata->fa_cookie = fa_cookie;
11819 metadata->trap_type = trap_item->trap->type;
11821 spin_lock(&in_devlink_port->type_lock);
11822 if (in_devlink_port->type == DEVLINK_PORT_TYPE_ETH)
11823 metadata->input_dev = in_devlink_port->type_eth.netdev;
11824 spin_unlock(&in_devlink_port->type_lock);
11828 * devlink_trap_report - Report trapped packet to drop monitor.
11829 * @devlink: devlink.
11830 * @skb: Trapped packet.
11831 * @trap_ctx: Trap context.
11832 * @in_devlink_port: Input devlink port.
11833 * @fa_cookie: Flow action cookie. Could be NULL.
11835 void devlink_trap_report(struct devlink *devlink, struct sk_buff *skb,
11836 void *trap_ctx, struct devlink_port *in_devlink_port,
11837 const struct flow_action_cookie *fa_cookie)
11840 struct devlink_trap_item *trap_item = trap_ctx;
11842 devlink_trap_stats_update(trap_item->stats, skb->len);
11843 devlink_trap_stats_update(trap_item->group_item->stats, skb->len);
11845 if (trace_devlink_trap_report_enabled()) {
11846 struct devlink_trap_metadata metadata = {};
11848 devlink_trap_report_metadata_set(&metadata, trap_item,
11849 in_devlink_port, fa_cookie);
11850 trace_devlink_trap_report(devlink, skb, &metadata);
11853 EXPORT_SYMBOL_GPL(devlink_trap_report);
11856 * devlink_trap_ctx_priv - Trap context to driver private information.
11857 * @trap_ctx: Trap context.
11859 * Return: Driver private information passed during registration.
11861 void *devlink_trap_ctx_priv(void *trap_ctx)
11863 struct devlink_trap_item *trap_item = trap_ctx;
11865 return trap_item->priv;
11867 EXPORT_SYMBOL_GPL(devlink_trap_ctx_priv);
11870 devlink_trap_group_item_policer_link(struct devlink *devlink,
11871 struct devlink_trap_group_item *group_item)
11873 u32 policer_id = group_item->group->init_policer_id;
11874 struct devlink_trap_policer_item *policer_item;
11876 if (policer_id == 0)
11879 policer_item = devlink_trap_policer_item_lookup(devlink, policer_id);
11880 if (WARN_ON_ONCE(!policer_item))
11883 group_item->policer_item = policer_item;
11889 devlink_trap_group_register(struct devlink *devlink,
11890 const struct devlink_trap_group *group)
11892 struct devlink_trap_group_item *group_item;
11895 if (devlink_trap_group_item_lookup(devlink, group->name))
11898 group_item = kzalloc(sizeof(*group_item), GFP_KERNEL);
11902 group_item->stats = netdev_alloc_pcpu_stats(struct devlink_stats);
11903 if (!group_item->stats) {
11905 goto err_stats_alloc;
11908 group_item->group = group;
11910 err = devlink_trap_group_item_policer_link(devlink, group_item);
11912 goto err_policer_link;
11914 if (devlink->ops->trap_group_init) {
11915 err = devlink->ops->trap_group_init(devlink, group);
11917 goto err_group_init;
11920 list_add_tail(&group_item->list, &devlink->trap_group_list);
11921 devlink_trap_group_notify(devlink, group_item,
11922 DEVLINK_CMD_TRAP_GROUP_NEW);
11928 free_percpu(group_item->stats);
11935 devlink_trap_group_unregister(struct devlink *devlink,
11936 const struct devlink_trap_group *group)
11938 struct devlink_trap_group_item *group_item;
11940 group_item = devlink_trap_group_item_lookup(devlink, group->name);
11941 if (WARN_ON_ONCE(!group_item))
11944 devlink_trap_group_notify(devlink, group_item,
11945 DEVLINK_CMD_TRAP_GROUP_DEL);
11946 list_del(&group_item->list);
11947 free_percpu(group_item->stats);
11952 * devl_trap_groups_register - Register packet trap groups with devlink.
11953 * @devlink: devlink.
11954 * @groups: Packet trap groups.
11955 * @groups_count: Count of provided packet trap groups.
11957 * Return: Non-zero value on failure.
11959 int devl_trap_groups_register(struct devlink *devlink,
11960 const struct devlink_trap_group *groups,
11961 size_t groups_count)
11965 devl_assert_locked(devlink);
11966 for (i = 0; i < groups_count; i++) {
11967 const struct devlink_trap_group *group = &groups[i];
11969 err = devlink_trap_group_verify(group);
11971 goto err_trap_group_verify;
11973 err = devlink_trap_group_register(devlink, group);
11975 goto err_trap_group_register;
11980 err_trap_group_register:
11981 err_trap_group_verify:
11982 for (i--; i >= 0; i--)
11983 devlink_trap_group_unregister(devlink, &groups[i]);
11986 EXPORT_SYMBOL_GPL(devl_trap_groups_register);
11989 * devlink_trap_groups_register - Register packet trap groups with devlink.
11990 * @devlink: devlink.
11991 * @groups: Packet trap groups.
11992 * @groups_count: Count of provided packet trap groups.
11994 * Context: Takes and release devlink->lock <mutex>.
11996 * Return: Non-zero value on failure.
11998 int devlink_trap_groups_register(struct devlink *devlink,
11999 const struct devlink_trap_group *groups,
12000 size_t groups_count)
12004 devl_lock(devlink);
12005 err = devl_trap_groups_register(devlink, groups, groups_count);
12006 devl_unlock(devlink);
12009 EXPORT_SYMBOL_GPL(devlink_trap_groups_register);
12012 * devl_trap_groups_unregister - Unregister packet trap groups from devlink.
12013 * @devlink: devlink.
12014 * @groups: Packet trap groups.
12015 * @groups_count: Count of provided packet trap groups.
12017 void devl_trap_groups_unregister(struct devlink *devlink,
12018 const struct devlink_trap_group *groups,
12019 size_t groups_count)
12023 devl_assert_locked(devlink);
12024 for (i = groups_count - 1; i >= 0; i--)
12025 devlink_trap_group_unregister(devlink, &groups[i]);
12027 EXPORT_SYMBOL_GPL(devl_trap_groups_unregister);
12030 * devlink_trap_groups_unregister - Unregister packet trap groups from devlink.
12031 * @devlink: devlink.
12032 * @groups: Packet trap groups.
12033 * @groups_count: Count of provided packet trap groups.
12035 * Context: Takes and release devlink->lock <mutex>.
12037 void devlink_trap_groups_unregister(struct devlink *devlink,
12038 const struct devlink_trap_group *groups,
12039 size_t groups_count)
12041 devl_lock(devlink);
12042 devl_trap_groups_unregister(devlink, groups, groups_count);
12043 devl_unlock(devlink);
12045 EXPORT_SYMBOL_GPL(devlink_trap_groups_unregister);
12048 devlink_trap_policer_notify(struct devlink *devlink,
12049 const struct devlink_trap_policer_item *policer_item,
12050 enum devlink_command cmd)
12052 struct sk_buff *msg;
12055 WARN_ON_ONCE(cmd != DEVLINK_CMD_TRAP_POLICER_NEW &&
12056 cmd != DEVLINK_CMD_TRAP_POLICER_DEL);
12057 if (!xa_get_mark(&devlinks, devlink->index, DEVLINK_REGISTERED))
12060 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
12064 err = devlink_nl_trap_policer_fill(msg, devlink, policer_item, cmd, 0,
12071 genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink),
12072 msg, 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
12076 devlink_trap_policer_register(struct devlink *devlink,
12077 const struct devlink_trap_policer *policer)
12079 struct devlink_trap_policer_item *policer_item;
12082 if (devlink_trap_policer_item_lookup(devlink, policer->id))
12085 policer_item = kzalloc(sizeof(*policer_item), GFP_KERNEL);
12089 policer_item->policer = policer;
12090 policer_item->rate = policer->init_rate;
12091 policer_item->burst = policer->init_burst;
12093 if (devlink->ops->trap_policer_init) {
12094 err = devlink->ops->trap_policer_init(devlink, policer);
12096 goto err_policer_init;
12099 list_add_tail(&policer_item->list, &devlink->trap_policer_list);
12100 devlink_trap_policer_notify(devlink, policer_item,
12101 DEVLINK_CMD_TRAP_POLICER_NEW);
12106 kfree(policer_item);
12111 devlink_trap_policer_unregister(struct devlink *devlink,
12112 const struct devlink_trap_policer *policer)
12114 struct devlink_trap_policer_item *policer_item;
12116 policer_item = devlink_trap_policer_item_lookup(devlink, policer->id);
12117 if (WARN_ON_ONCE(!policer_item))
12120 devlink_trap_policer_notify(devlink, policer_item,
12121 DEVLINK_CMD_TRAP_POLICER_DEL);
12122 list_del(&policer_item->list);
12123 if (devlink->ops->trap_policer_fini)
12124 devlink->ops->trap_policer_fini(devlink, policer);
12125 kfree(policer_item);
12129 * devl_trap_policers_register - Register packet trap policers with devlink.
12130 * @devlink: devlink.
12131 * @policers: Packet trap policers.
12132 * @policers_count: Count of provided packet trap policers.
12134 * Return: Non-zero value on failure.
12137 devl_trap_policers_register(struct devlink *devlink,
12138 const struct devlink_trap_policer *policers,
12139 size_t policers_count)
12143 devl_assert_locked(devlink);
12144 for (i = 0; i < policers_count; i++) {
12145 const struct devlink_trap_policer *policer = &policers[i];
12147 if (WARN_ON(policer->id == 0 ||
12148 policer->max_rate < policer->min_rate ||
12149 policer->max_burst < policer->min_burst)) {
12151 goto err_trap_policer_verify;
12154 err = devlink_trap_policer_register(devlink, policer);
12156 goto err_trap_policer_register;
12160 err_trap_policer_register:
12161 err_trap_policer_verify:
12162 for (i--; i >= 0; i--)
12163 devlink_trap_policer_unregister(devlink, &policers[i]);
12166 EXPORT_SYMBOL_GPL(devl_trap_policers_register);
12169 * devl_trap_policers_unregister - Unregister packet trap policers from devlink.
12170 * @devlink: devlink.
12171 * @policers: Packet trap policers.
12172 * @policers_count: Count of provided packet trap policers.
12175 devl_trap_policers_unregister(struct devlink *devlink,
12176 const struct devlink_trap_policer *policers,
12177 size_t policers_count)
12181 devl_assert_locked(devlink);
12182 for (i = policers_count - 1; i >= 0; i--)
12183 devlink_trap_policer_unregister(devlink, &policers[i]);
12185 EXPORT_SYMBOL_GPL(devl_trap_policers_unregister);
12187 static void __devlink_compat_running_version(struct devlink *devlink,
12188 char *buf, size_t len)
12190 struct devlink_info_req req = {};
12191 const struct nlattr *nlattr;
12192 struct sk_buff *msg;
12195 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
12200 err = devlink->ops->info_get(devlink, &req, NULL);
12204 nla_for_each_attr(nlattr, (void *)msg->data, msg->len, rem) {
12205 const struct nlattr *kv;
12208 if (nla_type(nlattr) != DEVLINK_ATTR_INFO_VERSION_RUNNING)
12211 nla_for_each_nested(kv, nlattr, rem_kv) {
12212 if (nla_type(kv) != DEVLINK_ATTR_INFO_VERSION_VALUE)
12215 strlcat(buf, nla_data(kv), len);
12216 strlcat(buf, " ", len);
12223 void devlink_compat_running_version(struct devlink *devlink,
12224 char *buf, size_t len)
12226 if (!devlink->ops->info_get)
12229 devl_lock(devlink);
12230 if (devl_is_registered(devlink))
12231 __devlink_compat_running_version(devlink, buf, len);
12232 devl_unlock(devlink);
12235 int devlink_compat_flash_update(struct devlink *devlink, const char *file_name)
12237 struct devlink_flash_update_params params = {};
12240 devl_lock(devlink);
12241 if (!devl_is_registered(devlink)) {
12246 if (!devlink->ops->flash_update) {
12251 ret = request_firmware(¶ms.fw, file_name, devlink->dev);
12255 devlink_flash_update_begin_notify(devlink);
12256 ret = devlink->ops->flash_update(devlink, ¶ms, NULL);
12257 devlink_flash_update_end_notify(devlink);
12259 release_firmware(params.fw);
12261 devl_unlock(devlink);
12266 int devlink_compat_phys_port_name_get(struct net_device *dev,
12267 char *name, size_t len)
12269 struct devlink_port *devlink_port;
12271 /* RTNL mutex is held here which ensures that devlink_port
12272 * instance cannot disappear in the middle. No need to take
12273 * any devlink lock as only permanent values are accessed.
12277 devlink_port = dev->devlink_port;
12279 return -EOPNOTSUPP;
12281 return __devlink_port_phys_port_name_get(devlink_port, name, len);
12284 int devlink_compat_switch_id_get(struct net_device *dev,
12285 struct netdev_phys_item_id *ppid)
12287 struct devlink_port *devlink_port;
12289 /* Caller must hold RTNL mutex or reference to dev, which ensures that
12290 * devlink_port instance cannot disappear in the middle. No need to take
12291 * any devlink lock as only permanent values are accessed.
12293 devlink_port = dev->devlink_port;
12294 if (!devlink_port || !devlink_port->switch_port)
12295 return -EOPNOTSUPP;
12297 memcpy(ppid, &devlink_port->attrs.switch_id, sizeof(*ppid));