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.
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 #define DEVLINK_RELOAD_STATS_ARRAY_SIZE \
35 (__DEVLINK_RELOAD_LIMIT_MAX * __DEVLINK_RELOAD_ACTION_MAX)
37 struct devlink_dev_stats {
38 u32 reload_stats[DEVLINK_RELOAD_STATS_ARRAY_SIZE];
39 u32 remote_reload_stats[DEVLINK_RELOAD_STATS_ARRAY_SIZE];
44 struct list_head port_list;
45 struct list_head rate_list;
46 struct list_head sb_list;
47 struct list_head dpipe_table_list;
48 struct list_head resource_list;
49 struct list_head param_list;
50 struct list_head region_list;
51 struct list_head reporter_list;
52 struct mutex reporters_lock; /* protects reporter_list */
53 struct devlink_dpipe_headers *dpipe_headers;
54 struct list_head trap_list;
55 struct list_head trap_group_list;
56 struct list_head trap_policer_list;
57 struct list_head linecard_list;
58 struct mutex linecards_lock; /* protects linecard_list */
59 const struct devlink_ops *ops;
61 struct xarray snapshot_ids;
62 struct devlink_dev_stats stats;
65 /* Serializes access to devlink instance specific objects such as
66 * port, sb, dpipe, resource, params, region, traps and more.
69 struct lock_class_key lock_key;
72 struct completion comp;
74 char priv[] __aligned(NETDEV_ALIGN);
77 struct devlink_linecard_ops;
78 struct devlink_linecard_type;
80 struct devlink_linecard {
81 struct list_head list;
82 struct devlink *devlink;
85 const struct devlink_linecard_ops *ops;
87 enum devlink_linecard_state state;
88 struct mutex state_lock; /* Protects state */
90 struct devlink_linecard_type *types;
91 unsigned int types_count;
92 struct devlink *nested_devlink;
96 * struct devlink_resource - devlink resource
97 * @name: name of the resource
98 * @id: id, per devlink instance
99 * @size: size of the resource
100 * @size_new: updated size of the resource, reload is needed
101 * @size_valid: valid in case the total size of the resource is valid
102 * including its children
103 * @parent: parent resource
104 * @size_params: size parameters
106 * @resource_list: list of child resources
107 * @occ_get: occupancy getter callback
108 * @occ_get_priv: occupancy getter callback priv
110 struct devlink_resource {
116 struct devlink_resource *parent;
117 struct devlink_resource_size_params size_params;
118 struct list_head list;
119 struct list_head resource_list;
120 devlink_resource_occ_get_t *occ_get;
124 void *devlink_priv(struct devlink *devlink)
126 return &devlink->priv;
128 EXPORT_SYMBOL_GPL(devlink_priv);
130 struct devlink *priv_to_devlink(void *priv)
132 return container_of(priv, struct devlink, priv);
134 EXPORT_SYMBOL_GPL(priv_to_devlink);
136 struct device *devlink_to_dev(const struct devlink *devlink)
140 EXPORT_SYMBOL_GPL(devlink_to_dev);
142 static struct devlink_dpipe_field devlink_dpipe_fields_ethernet[] = {
144 .name = "destination mac",
145 .id = DEVLINK_DPIPE_FIELD_ETHERNET_DST_MAC,
150 struct devlink_dpipe_header devlink_dpipe_header_ethernet = {
152 .id = DEVLINK_DPIPE_HEADER_ETHERNET,
153 .fields = devlink_dpipe_fields_ethernet,
154 .fields_count = ARRAY_SIZE(devlink_dpipe_fields_ethernet),
157 EXPORT_SYMBOL_GPL(devlink_dpipe_header_ethernet);
159 static struct devlink_dpipe_field devlink_dpipe_fields_ipv4[] = {
161 .name = "destination ip",
162 .id = DEVLINK_DPIPE_FIELD_IPV4_DST_IP,
167 struct devlink_dpipe_header devlink_dpipe_header_ipv4 = {
169 .id = DEVLINK_DPIPE_HEADER_IPV4,
170 .fields = devlink_dpipe_fields_ipv4,
171 .fields_count = ARRAY_SIZE(devlink_dpipe_fields_ipv4),
174 EXPORT_SYMBOL_GPL(devlink_dpipe_header_ipv4);
176 static struct devlink_dpipe_field devlink_dpipe_fields_ipv6[] = {
178 .name = "destination ip",
179 .id = DEVLINK_DPIPE_FIELD_IPV6_DST_IP,
184 struct devlink_dpipe_header devlink_dpipe_header_ipv6 = {
186 .id = DEVLINK_DPIPE_HEADER_IPV6,
187 .fields = devlink_dpipe_fields_ipv6,
188 .fields_count = ARRAY_SIZE(devlink_dpipe_fields_ipv6),
191 EXPORT_SYMBOL_GPL(devlink_dpipe_header_ipv6);
193 EXPORT_TRACEPOINT_SYMBOL_GPL(devlink_hwmsg);
194 EXPORT_TRACEPOINT_SYMBOL_GPL(devlink_hwerr);
195 EXPORT_TRACEPOINT_SYMBOL_GPL(devlink_trap_report);
197 static const struct nla_policy devlink_function_nl_policy[DEVLINK_PORT_FUNCTION_ATTR_MAX + 1] = {
198 [DEVLINK_PORT_FUNCTION_ATTR_HW_ADDR] = { .type = NLA_BINARY },
199 [DEVLINK_PORT_FN_ATTR_STATE] =
200 NLA_POLICY_RANGE(NLA_U8, DEVLINK_PORT_FN_STATE_INACTIVE,
201 DEVLINK_PORT_FN_STATE_ACTIVE),
204 static const struct nla_policy devlink_selftest_nl_policy[DEVLINK_ATTR_SELFTEST_ID_MAX + 1] = {
205 [DEVLINK_ATTR_SELFTEST_ID_FLASH] = { .type = NLA_FLAG },
208 static DEFINE_XARRAY_FLAGS(devlinks, XA_FLAGS_ALLOC);
209 #define DEVLINK_REGISTERED XA_MARK_1
210 #define DEVLINK_UNREGISTERING XA_MARK_2
212 /* devlink instances are open to the access from the user space after
213 * devlink_register() call. Such logical barrier allows us to have certain
214 * expectations related to locking.
216 * Before *_register() - we are in initialization stage and no parallel
217 * access possible to the devlink instance. All drivers perform that phase
218 * by implicitly holding device_lock.
220 * After *_register() - users and driver can access devlink instance at
223 #define ASSERT_DEVLINK_REGISTERED(d) \
224 WARN_ON_ONCE(!xa_get_mark(&devlinks, (d)->index, DEVLINK_REGISTERED))
225 #define ASSERT_DEVLINK_NOT_REGISTERED(d) \
226 WARN_ON_ONCE(xa_get_mark(&devlinks, (d)->index, DEVLINK_REGISTERED))
228 struct net *devlink_net(const struct devlink *devlink)
230 return read_pnet(&devlink->_net);
232 EXPORT_SYMBOL_GPL(devlink_net);
234 static void __devlink_put_rcu(struct rcu_head *head)
236 struct devlink *devlink = container_of(head, struct devlink, rcu);
238 complete(&devlink->comp);
241 void devlink_put(struct devlink *devlink)
243 if (refcount_dec_and_test(&devlink->refcount))
244 /* Make sure unregister operation that may await the completion
245 * is unblocked only after all users are after the end of
248 call_rcu(&devlink->rcu, __devlink_put_rcu);
251 struct devlink *__must_check devlink_try_get(struct devlink *devlink)
253 if (refcount_inc_not_zero(&devlink->refcount))
258 void devl_assert_locked(struct devlink *devlink)
260 lockdep_assert_held(&devlink->lock);
262 EXPORT_SYMBOL_GPL(devl_assert_locked);
264 #ifdef CONFIG_LOCKDEP
265 /* For use in conjunction with LOCKDEP only e.g. rcu_dereference_protected() */
266 bool devl_lock_is_held(struct devlink *devlink)
268 return lockdep_is_held(&devlink->lock);
270 EXPORT_SYMBOL_GPL(devl_lock_is_held);
273 void devl_lock(struct devlink *devlink)
275 mutex_lock(&devlink->lock);
277 EXPORT_SYMBOL_GPL(devl_lock);
279 int devl_trylock(struct devlink *devlink)
281 return mutex_trylock(&devlink->lock);
283 EXPORT_SYMBOL_GPL(devl_trylock);
285 void devl_unlock(struct devlink *devlink)
287 mutex_unlock(&devlink->lock);
289 EXPORT_SYMBOL_GPL(devl_unlock);
291 static struct devlink *
292 devlinks_xa_find_get(struct net *net, unsigned long *indexp, xa_mark_t filter,
293 void * (*xa_find_fn)(struct xarray *, unsigned long *,
294 unsigned long, xa_mark_t))
296 struct devlink *devlink;
300 devlink = xa_find_fn(&devlinks, indexp, ULONG_MAX, DEVLINK_REGISTERED);
304 /* In case devlink_unregister() was already called and "unregistering"
305 * mark was set, do not allow to get a devlink reference here.
306 * This prevents live-lock of devlink_unregister() wait for completion.
308 if (xa_get_mark(&devlinks, *indexp, DEVLINK_UNREGISTERING))
311 /* For a possible retry, the xa_find_after() should be always used */
312 xa_find_fn = xa_find_after;
313 if (!devlink_try_get(devlink))
315 if (!net_eq(devlink_net(devlink), net)) {
316 devlink_put(devlink);
324 static struct devlink *devlinks_xa_find_get_first(struct net *net,
325 unsigned long *indexp,
328 return devlinks_xa_find_get(net, indexp, filter, xa_find);
331 static struct devlink *devlinks_xa_find_get_next(struct net *net,
332 unsigned long *indexp,
335 return devlinks_xa_find_get(net, indexp, filter, xa_find_after);
338 /* Iterate over devlink pointers which were possible to get reference to.
339 * devlink_put() needs to be called for each iterated devlink pointer
340 * in loop body in order to release the reference.
342 #define devlinks_xa_for_each_get(net, index, devlink, filter) \
344 devlink = devlinks_xa_find_get_first(net, &index, filter); \
345 devlink; devlink = devlinks_xa_find_get_next(net, &index, filter))
347 #define devlinks_xa_for_each_registered_get(net, index, devlink) \
348 devlinks_xa_for_each_get(net, index, devlink, DEVLINK_REGISTERED)
350 static struct devlink *devlink_get_from_attrs(struct net *net,
351 struct nlattr **attrs)
353 struct devlink *devlink;
358 if (!attrs[DEVLINK_ATTR_BUS_NAME] || !attrs[DEVLINK_ATTR_DEV_NAME])
359 return ERR_PTR(-EINVAL);
361 busname = nla_data(attrs[DEVLINK_ATTR_BUS_NAME]);
362 devname = nla_data(attrs[DEVLINK_ATTR_DEV_NAME]);
364 devlinks_xa_for_each_registered_get(net, index, devlink) {
365 if (strcmp(devlink->dev->bus->name, busname) == 0 &&
366 strcmp(dev_name(devlink->dev), devname) == 0)
368 devlink_put(devlink);
371 return ERR_PTR(-ENODEV);
374 #define ASSERT_DEVLINK_PORT_REGISTERED(devlink_port) \
375 WARN_ON_ONCE(!(devlink_port)->registered)
376 #define ASSERT_DEVLINK_PORT_NOT_REGISTERED(devlink_port) \
377 WARN_ON_ONCE((devlink_port)->registered)
378 #define ASSERT_DEVLINK_PORT_INITIALIZED(devlink_port) \
379 WARN_ON_ONCE(!(devlink_port)->initialized)
381 static struct devlink_port *devlink_port_get_by_index(struct devlink *devlink,
382 unsigned int port_index)
384 struct devlink_port *devlink_port;
386 list_for_each_entry(devlink_port, &devlink->port_list, list) {
387 if (devlink_port->index == port_index)
393 static bool devlink_port_index_exists(struct devlink *devlink,
394 unsigned int port_index)
396 return devlink_port_get_by_index(devlink, port_index);
399 static struct devlink_port *devlink_port_get_from_attrs(struct devlink *devlink,
400 struct nlattr **attrs)
402 if (attrs[DEVLINK_ATTR_PORT_INDEX]) {
403 u32 port_index = nla_get_u32(attrs[DEVLINK_ATTR_PORT_INDEX]);
404 struct devlink_port *devlink_port;
406 devlink_port = devlink_port_get_by_index(devlink, port_index);
408 return ERR_PTR(-ENODEV);
411 return ERR_PTR(-EINVAL);
414 static struct devlink_port *devlink_port_get_from_info(struct devlink *devlink,
415 struct genl_info *info)
417 return devlink_port_get_from_attrs(devlink, info->attrs);
421 devlink_rate_is_leaf(struct devlink_rate *devlink_rate)
423 return devlink_rate->type == DEVLINK_RATE_TYPE_LEAF;
427 devlink_rate_is_node(struct devlink_rate *devlink_rate)
429 return devlink_rate->type == DEVLINK_RATE_TYPE_NODE;
432 static struct devlink_rate *
433 devlink_rate_leaf_get_from_info(struct devlink *devlink, struct genl_info *info)
435 struct devlink_rate *devlink_rate;
436 struct devlink_port *devlink_port;
438 devlink_port = devlink_port_get_from_attrs(devlink, info->attrs);
439 if (IS_ERR(devlink_port))
440 return ERR_CAST(devlink_port);
441 devlink_rate = devlink_port->devlink_rate;
442 return devlink_rate ?: ERR_PTR(-ENODEV);
445 static struct devlink_rate *
446 devlink_rate_node_get_by_name(struct devlink *devlink, const char *node_name)
448 static struct devlink_rate *devlink_rate;
450 list_for_each_entry(devlink_rate, &devlink->rate_list, list) {
451 if (devlink_rate_is_node(devlink_rate) &&
452 !strcmp(node_name, devlink_rate->name))
455 return ERR_PTR(-ENODEV);
458 static struct devlink_rate *
459 devlink_rate_node_get_from_attrs(struct devlink *devlink, struct nlattr **attrs)
461 const char *rate_node_name;
464 if (!attrs[DEVLINK_ATTR_RATE_NODE_NAME])
465 return ERR_PTR(-EINVAL);
466 rate_node_name = nla_data(attrs[DEVLINK_ATTR_RATE_NODE_NAME]);
467 len = strlen(rate_node_name);
468 /* Name cannot be empty or decimal number */
469 if (!len || strspn(rate_node_name, "0123456789") == len)
470 return ERR_PTR(-EINVAL);
472 return devlink_rate_node_get_by_name(devlink, rate_node_name);
475 static struct devlink_rate *
476 devlink_rate_node_get_from_info(struct devlink *devlink, struct genl_info *info)
478 return devlink_rate_node_get_from_attrs(devlink, info->attrs);
481 static struct devlink_rate *
482 devlink_rate_get_from_info(struct devlink *devlink, struct genl_info *info)
484 struct nlattr **attrs = info->attrs;
486 if (attrs[DEVLINK_ATTR_PORT_INDEX])
487 return devlink_rate_leaf_get_from_info(devlink, info);
488 else if (attrs[DEVLINK_ATTR_RATE_NODE_NAME])
489 return devlink_rate_node_get_from_info(devlink, info);
491 return ERR_PTR(-EINVAL);
494 static struct devlink_linecard *
495 devlink_linecard_get_by_index(struct devlink *devlink,
496 unsigned int linecard_index)
498 struct devlink_linecard *devlink_linecard;
500 list_for_each_entry(devlink_linecard, &devlink->linecard_list, list) {
501 if (devlink_linecard->index == linecard_index)
502 return devlink_linecard;
507 static bool devlink_linecard_index_exists(struct devlink *devlink,
508 unsigned int linecard_index)
510 return devlink_linecard_get_by_index(devlink, linecard_index);
513 static struct devlink_linecard *
514 devlink_linecard_get_from_attrs(struct devlink *devlink, struct nlattr **attrs)
516 if (attrs[DEVLINK_ATTR_LINECARD_INDEX]) {
517 u32 linecard_index = nla_get_u32(attrs[DEVLINK_ATTR_LINECARD_INDEX]);
518 struct devlink_linecard *linecard;
520 mutex_lock(&devlink->linecards_lock);
521 linecard = devlink_linecard_get_by_index(devlink, linecard_index);
523 refcount_inc(&linecard->refcount);
524 mutex_unlock(&devlink->linecards_lock);
526 return ERR_PTR(-ENODEV);
529 return ERR_PTR(-EINVAL);
532 static struct devlink_linecard *
533 devlink_linecard_get_from_info(struct devlink *devlink, struct genl_info *info)
535 return devlink_linecard_get_from_attrs(devlink, info->attrs);
538 static void devlink_linecard_put(struct devlink_linecard *linecard)
540 if (refcount_dec_and_test(&linecard->refcount)) {
541 mutex_destroy(&linecard->state_lock);
547 struct list_head list;
550 u16 ingress_pools_count;
551 u16 egress_pools_count;
552 u16 ingress_tc_count;
556 static u16 devlink_sb_pool_count(struct devlink_sb *devlink_sb)
558 return devlink_sb->ingress_pools_count + devlink_sb->egress_pools_count;
561 static struct devlink_sb *devlink_sb_get_by_index(struct devlink *devlink,
562 unsigned int sb_index)
564 struct devlink_sb *devlink_sb;
566 list_for_each_entry(devlink_sb, &devlink->sb_list, list) {
567 if (devlink_sb->index == sb_index)
573 static bool devlink_sb_index_exists(struct devlink *devlink,
574 unsigned int sb_index)
576 return devlink_sb_get_by_index(devlink, sb_index);
579 static struct devlink_sb *devlink_sb_get_from_attrs(struct devlink *devlink,
580 struct nlattr **attrs)
582 if (attrs[DEVLINK_ATTR_SB_INDEX]) {
583 u32 sb_index = nla_get_u32(attrs[DEVLINK_ATTR_SB_INDEX]);
584 struct devlink_sb *devlink_sb;
586 devlink_sb = devlink_sb_get_by_index(devlink, sb_index);
588 return ERR_PTR(-ENODEV);
591 return ERR_PTR(-EINVAL);
594 static struct devlink_sb *devlink_sb_get_from_info(struct devlink *devlink,
595 struct genl_info *info)
597 return devlink_sb_get_from_attrs(devlink, info->attrs);
600 static int devlink_sb_pool_index_get_from_attrs(struct devlink_sb *devlink_sb,
601 struct nlattr **attrs,
606 if (!attrs[DEVLINK_ATTR_SB_POOL_INDEX])
609 val = nla_get_u16(attrs[DEVLINK_ATTR_SB_POOL_INDEX]);
610 if (val >= devlink_sb_pool_count(devlink_sb))
616 static int devlink_sb_pool_index_get_from_info(struct devlink_sb *devlink_sb,
617 struct genl_info *info,
620 return devlink_sb_pool_index_get_from_attrs(devlink_sb, info->attrs,
625 devlink_sb_pool_type_get_from_attrs(struct nlattr **attrs,
626 enum devlink_sb_pool_type *p_pool_type)
630 if (!attrs[DEVLINK_ATTR_SB_POOL_TYPE])
633 val = nla_get_u8(attrs[DEVLINK_ATTR_SB_POOL_TYPE]);
634 if (val != DEVLINK_SB_POOL_TYPE_INGRESS &&
635 val != DEVLINK_SB_POOL_TYPE_EGRESS)
642 devlink_sb_pool_type_get_from_info(struct genl_info *info,
643 enum devlink_sb_pool_type *p_pool_type)
645 return devlink_sb_pool_type_get_from_attrs(info->attrs, p_pool_type);
649 devlink_sb_th_type_get_from_attrs(struct nlattr **attrs,
650 enum devlink_sb_threshold_type *p_th_type)
654 if (!attrs[DEVLINK_ATTR_SB_POOL_THRESHOLD_TYPE])
657 val = nla_get_u8(attrs[DEVLINK_ATTR_SB_POOL_THRESHOLD_TYPE]);
658 if (val != DEVLINK_SB_THRESHOLD_TYPE_STATIC &&
659 val != DEVLINK_SB_THRESHOLD_TYPE_DYNAMIC)
666 devlink_sb_th_type_get_from_info(struct genl_info *info,
667 enum devlink_sb_threshold_type *p_th_type)
669 return devlink_sb_th_type_get_from_attrs(info->attrs, p_th_type);
673 devlink_sb_tc_index_get_from_attrs(struct devlink_sb *devlink_sb,
674 struct nlattr **attrs,
675 enum devlink_sb_pool_type pool_type,
680 if (!attrs[DEVLINK_ATTR_SB_TC_INDEX])
683 val = nla_get_u16(attrs[DEVLINK_ATTR_SB_TC_INDEX]);
684 if (pool_type == DEVLINK_SB_POOL_TYPE_INGRESS &&
685 val >= devlink_sb->ingress_tc_count)
687 if (pool_type == DEVLINK_SB_POOL_TYPE_EGRESS &&
688 val >= devlink_sb->egress_tc_count)
695 devlink_sb_tc_index_get_from_info(struct devlink_sb *devlink_sb,
696 struct genl_info *info,
697 enum devlink_sb_pool_type pool_type,
700 return devlink_sb_tc_index_get_from_attrs(devlink_sb, info->attrs,
701 pool_type, p_tc_index);
704 struct devlink_region {
705 struct devlink *devlink;
706 struct devlink_port *port;
707 struct list_head list;
709 const struct devlink_region_ops *ops;
710 const struct devlink_port_region_ops *port_ops;
712 struct mutex snapshot_lock; /* protects snapshot_list,
713 * max_snapshots and cur_snapshots
716 struct list_head snapshot_list;
722 struct devlink_snapshot {
723 struct list_head list;
724 struct devlink_region *region;
729 static struct devlink_region *
730 devlink_region_get_by_name(struct devlink *devlink, const char *region_name)
732 struct devlink_region *region;
734 list_for_each_entry(region, &devlink->region_list, list)
735 if (!strcmp(region->ops->name, region_name))
741 static struct devlink_region *
742 devlink_port_region_get_by_name(struct devlink_port *port,
743 const char *region_name)
745 struct devlink_region *region;
747 list_for_each_entry(region, &port->region_list, list)
748 if (!strcmp(region->ops->name, region_name))
754 static struct devlink_snapshot *
755 devlink_region_snapshot_get_by_id(struct devlink_region *region, u32 id)
757 struct devlink_snapshot *snapshot;
759 list_for_each_entry(snapshot, ®ion->snapshot_list, list)
760 if (snapshot->id == id)
766 #define DEVLINK_NL_FLAG_NEED_PORT BIT(0)
767 #define DEVLINK_NL_FLAG_NEED_DEVLINK_OR_PORT BIT(1)
768 #define DEVLINK_NL_FLAG_NEED_RATE BIT(2)
769 #define DEVLINK_NL_FLAG_NEED_RATE_NODE BIT(3)
770 #define DEVLINK_NL_FLAG_NEED_LINECARD BIT(4)
772 static int devlink_nl_pre_doit(const struct genl_ops *ops,
773 struct sk_buff *skb, struct genl_info *info)
775 struct devlink_linecard *linecard;
776 struct devlink_port *devlink_port;
777 struct devlink *devlink;
780 devlink = devlink_get_from_attrs(genl_info_net(info), info->attrs);
782 return PTR_ERR(devlink);
784 info->user_ptr[0] = devlink;
785 if (ops->internal_flags & DEVLINK_NL_FLAG_NEED_PORT) {
786 devlink_port = devlink_port_get_from_info(devlink, info);
787 if (IS_ERR(devlink_port)) {
788 err = PTR_ERR(devlink_port);
791 info->user_ptr[1] = devlink_port;
792 } else if (ops->internal_flags & DEVLINK_NL_FLAG_NEED_DEVLINK_OR_PORT) {
793 devlink_port = devlink_port_get_from_info(devlink, info);
794 if (!IS_ERR(devlink_port))
795 info->user_ptr[1] = devlink_port;
796 } else if (ops->internal_flags & DEVLINK_NL_FLAG_NEED_RATE) {
797 struct devlink_rate *devlink_rate;
799 devlink_rate = devlink_rate_get_from_info(devlink, info);
800 if (IS_ERR(devlink_rate)) {
801 err = PTR_ERR(devlink_rate);
804 info->user_ptr[1] = devlink_rate;
805 } else if (ops->internal_flags & DEVLINK_NL_FLAG_NEED_RATE_NODE) {
806 struct devlink_rate *rate_node;
808 rate_node = devlink_rate_node_get_from_info(devlink, info);
809 if (IS_ERR(rate_node)) {
810 err = PTR_ERR(rate_node);
813 info->user_ptr[1] = rate_node;
814 } else if (ops->internal_flags & DEVLINK_NL_FLAG_NEED_LINECARD) {
815 linecard = devlink_linecard_get_from_info(devlink, info);
816 if (IS_ERR(linecard)) {
817 err = PTR_ERR(linecard);
820 info->user_ptr[1] = linecard;
825 devl_unlock(devlink);
826 devlink_put(devlink);
830 static void devlink_nl_post_doit(const struct genl_ops *ops,
831 struct sk_buff *skb, struct genl_info *info)
833 struct devlink_linecard *linecard;
834 struct devlink *devlink;
836 devlink = info->user_ptr[0];
837 if (ops->internal_flags & DEVLINK_NL_FLAG_NEED_LINECARD) {
838 linecard = info->user_ptr[1];
839 devlink_linecard_put(linecard);
841 devl_unlock(devlink);
842 devlink_put(devlink);
845 static struct genl_family devlink_nl_family;
847 enum devlink_multicast_groups {
848 DEVLINK_MCGRP_CONFIG,
851 static const struct genl_multicast_group devlink_nl_mcgrps[] = {
852 [DEVLINK_MCGRP_CONFIG] = { .name = DEVLINK_GENL_MCGRP_CONFIG_NAME },
855 static int devlink_nl_put_handle(struct sk_buff *msg, struct devlink *devlink)
857 if (nla_put_string(msg, DEVLINK_ATTR_BUS_NAME, devlink->dev->bus->name))
859 if (nla_put_string(msg, DEVLINK_ATTR_DEV_NAME, dev_name(devlink->dev)))
864 static int devlink_nl_put_nested_handle(struct sk_buff *msg, struct devlink *devlink)
866 struct nlattr *nested_attr;
868 nested_attr = nla_nest_start(msg, DEVLINK_ATTR_NESTED_DEVLINK);
871 if (devlink_nl_put_handle(msg, devlink))
872 goto nla_put_failure;
874 nla_nest_end(msg, nested_attr);
878 nla_nest_cancel(msg, nested_attr);
882 struct devlink_reload_combination {
883 enum devlink_reload_action action;
884 enum devlink_reload_limit limit;
887 static const struct devlink_reload_combination devlink_reload_invalid_combinations[] = {
889 /* can't reinitialize driver with no down time */
890 .action = DEVLINK_RELOAD_ACTION_DRIVER_REINIT,
891 .limit = DEVLINK_RELOAD_LIMIT_NO_RESET,
896 devlink_reload_combination_is_invalid(enum devlink_reload_action action,
897 enum devlink_reload_limit limit)
901 for (i = 0; i < ARRAY_SIZE(devlink_reload_invalid_combinations); i++)
902 if (devlink_reload_invalid_combinations[i].action == action &&
903 devlink_reload_invalid_combinations[i].limit == limit)
909 devlink_reload_action_is_supported(struct devlink *devlink, enum devlink_reload_action action)
911 return test_bit(action, &devlink->ops->reload_actions);
915 devlink_reload_limit_is_supported(struct devlink *devlink, enum devlink_reload_limit limit)
917 return test_bit(limit, &devlink->ops->reload_limits);
920 static int devlink_reload_stat_put(struct sk_buff *msg,
921 enum devlink_reload_limit limit, u32 value)
923 struct nlattr *reload_stats_entry;
925 reload_stats_entry = nla_nest_start(msg, DEVLINK_ATTR_RELOAD_STATS_ENTRY);
926 if (!reload_stats_entry)
929 if (nla_put_u8(msg, DEVLINK_ATTR_RELOAD_STATS_LIMIT, limit) ||
930 nla_put_u32(msg, DEVLINK_ATTR_RELOAD_STATS_VALUE, value))
931 goto nla_put_failure;
932 nla_nest_end(msg, reload_stats_entry);
936 nla_nest_cancel(msg, reload_stats_entry);
940 static int devlink_reload_stats_put(struct sk_buff *msg, struct devlink *devlink, bool is_remote)
942 struct nlattr *reload_stats_attr, *act_info, *act_stats;
947 reload_stats_attr = nla_nest_start(msg, DEVLINK_ATTR_RELOAD_STATS);
949 reload_stats_attr = nla_nest_start(msg, DEVLINK_ATTR_REMOTE_RELOAD_STATS);
951 if (!reload_stats_attr)
954 for (i = 0; i <= DEVLINK_RELOAD_ACTION_MAX; i++) {
956 !devlink_reload_action_is_supported(devlink, i)) ||
957 i == DEVLINK_RELOAD_ACTION_UNSPEC)
959 act_info = nla_nest_start(msg, DEVLINK_ATTR_RELOAD_ACTION_INFO);
961 goto nla_put_failure;
963 if (nla_put_u8(msg, DEVLINK_ATTR_RELOAD_ACTION, i))
964 goto action_info_nest_cancel;
965 act_stats = nla_nest_start(msg, DEVLINK_ATTR_RELOAD_ACTION_STATS);
967 goto action_info_nest_cancel;
969 for (j = 0; j <= DEVLINK_RELOAD_LIMIT_MAX; j++) {
970 /* Remote stats are shown even if not locally supported.
971 * Stats of actions with unspecified limit are shown
972 * though drivers don't need to register unspecified
975 if ((!is_remote && j != DEVLINK_RELOAD_LIMIT_UNSPEC &&
976 !devlink_reload_limit_is_supported(devlink, j)) ||
977 devlink_reload_combination_is_invalid(i, j))
980 stat_idx = j * __DEVLINK_RELOAD_ACTION_MAX + i;
982 value = devlink->stats.reload_stats[stat_idx];
984 value = devlink->stats.remote_reload_stats[stat_idx];
985 if (devlink_reload_stat_put(msg, j, value))
986 goto action_stats_nest_cancel;
988 nla_nest_end(msg, act_stats);
989 nla_nest_end(msg, act_info);
991 nla_nest_end(msg, reload_stats_attr);
994 action_stats_nest_cancel:
995 nla_nest_cancel(msg, act_stats);
996 action_info_nest_cancel:
997 nla_nest_cancel(msg, act_info);
999 nla_nest_cancel(msg, reload_stats_attr);
1003 static int devlink_nl_fill(struct sk_buff *msg, struct devlink *devlink,
1004 enum devlink_command cmd, u32 portid,
1007 struct nlattr *dev_stats;
1010 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
1014 if (devlink_nl_put_handle(msg, devlink))
1015 goto nla_put_failure;
1016 if (nla_put_u8(msg, DEVLINK_ATTR_RELOAD_FAILED, devlink->reload_failed))
1017 goto nla_put_failure;
1019 dev_stats = nla_nest_start(msg, DEVLINK_ATTR_DEV_STATS);
1021 goto nla_put_failure;
1023 if (devlink_reload_stats_put(msg, devlink, false))
1024 goto dev_stats_nest_cancel;
1025 if (devlink_reload_stats_put(msg, devlink, true))
1026 goto dev_stats_nest_cancel;
1028 nla_nest_end(msg, dev_stats);
1029 genlmsg_end(msg, hdr);
1032 dev_stats_nest_cancel:
1033 nla_nest_cancel(msg, dev_stats);
1035 genlmsg_cancel(msg, hdr);
1039 static void devlink_notify(struct devlink *devlink, enum devlink_command cmd)
1041 struct sk_buff *msg;
1044 WARN_ON(cmd != DEVLINK_CMD_NEW && cmd != DEVLINK_CMD_DEL);
1045 WARN_ON(!xa_get_mark(&devlinks, devlink->index, DEVLINK_REGISTERED));
1047 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
1051 err = devlink_nl_fill(msg, devlink, cmd, 0, 0, 0);
1057 genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink),
1058 msg, 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
1061 static int devlink_nl_port_attrs_put(struct sk_buff *msg,
1062 struct devlink_port *devlink_port)
1064 struct devlink_port_attrs *attrs = &devlink_port->attrs;
1066 if (!devlink_port->attrs_set)
1069 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_LANES, attrs->lanes))
1072 if (nla_put_u8(msg, DEVLINK_ATTR_PORT_SPLITTABLE, attrs->splittable))
1074 if (nla_put_u16(msg, DEVLINK_ATTR_PORT_FLAVOUR, attrs->flavour))
1076 switch (devlink_port->attrs.flavour) {
1077 case DEVLINK_PORT_FLAVOUR_PCI_PF:
1078 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_CONTROLLER_NUMBER,
1079 attrs->pci_pf.controller) ||
1080 nla_put_u16(msg, DEVLINK_ATTR_PORT_PCI_PF_NUMBER, attrs->pci_pf.pf))
1082 if (nla_put_u8(msg, DEVLINK_ATTR_PORT_EXTERNAL, attrs->pci_pf.external))
1085 case DEVLINK_PORT_FLAVOUR_PCI_VF:
1086 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_CONTROLLER_NUMBER,
1087 attrs->pci_vf.controller) ||
1088 nla_put_u16(msg, DEVLINK_ATTR_PORT_PCI_PF_NUMBER, attrs->pci_vf.pf) ||
1089 nla_put_u16(msg, DEVLINK_ATTR_PORT_PCI_VF_NUMBER, attrs->pci_vf.vf))
1091 if (nla_put_u8(msg, DEVLINK_ATTR_PORT_EXTERNAL, attrs->pci_vf.external))
1094 case DEVLINK_PORT_FLAVOUR_PCI_SF:
1095 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_CONTROLLER_NUMBER,
1096 attrs->pci_sf.controller) ||
1097 nla_put_u16(msg, DEVLINK_ATTR_PORT_PCI_PF_NUMBER,
1098 attrs->pci_sf.pf) ||
1099 nla_put_u32(msg, DEVLINK_ATTR_PORT_PCI_SF_NUMBER,
1103 case DEVLINK_PORT_FLAVOUR_PHYSICAL:
1104 case DEVLINK_PORT_FLAVOUR_CPU:
1105 case DEVLINK_PORT_FLAVOUR_DSA:
1106 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_NUMBER,
1107 attrs->phys.port_number))
1111 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_SPLIT_GROUP,
1112 attrs->phys.port_number))
1114 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_SPLIT_SUBPORT_NUMBER,
1115 attrs->phys.split_subport_number))
1124 static int devlink_port_fn_hw_addr_fill(const struct devlink_ops *ops,
1125 struct devlink_port *port,
1126 struct sk_buff *msg,
1127 struct netlink_ext_ack *extack,
1130 u8 hw_addr[MAX_ADDR_LEN];
1134 if (!ops->port_function_hw_addr_get)
1137 err = ops->port_function_hw_addr_get(port, hw_addr, &hw_addr_len,
1140 if (err == -EOPNOTSUPP)
1144 err = nla_put(msg, DEVLINK_PORT_FUNCTION_ATTR_HW_ADDR, hw_addr_len, hw_addr);
1147 *msg_updated = true;
1151 static int devlink_nl_rate_fill(struct sk_buff *msg,
1152 struct devlink_rate *devlink_rate,
1153 enum devlink_command cmd, u32 portid, u32 seq,
1154 int flags, struct netlink_ext_ack *extack)
1156 struct devlink *devlink = devlink_rate->devlink;
1159 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
1163 if (devlink_nl_put_handle(msg, devlink))
1164 goto nla_put_failure;
1166 if (nla_put_u16(msg, DEVLINK_ATTR_RATE_TYPE, devlink_rate->type))
1167 goto nla_put_failure;
1169 if (devlink_rate_is_leaf(devlink_rate)) {
1170 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_INDEX,
1171 devlink_rate->devlink_port->index))
1172 goto nla_put_failure;
1173 } else if (devlink_rate_is_node(devlink_rate)) {
1174 if (nla_put_string(msg, DEVLINK_ATTR_RATE_NODE_NAME,
1175 devlink_rate->name))
1176 goto nla_put_failure;
1179 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_RATE_TX_SHARE,
1180 devlink_rate->tx_share, DEVLINK_ATTR_PAD))
1181 goto nla_put_failure;
1183 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_RATE_TX_MAX,
1184 devlink_rate->tx_max, DEVLINK_ATTR_PAD))
1185 goto nla_put_failure;
1187 if (devlink_rate->parent)
1188 if (nla_put_string(msg, DEVLINK_ATTR_RATE_PARENT_NODE_NAME,
1189 devlink_rate->parent->name))
1190 goto nla_put_failure;
1192 genlmsg_end(msg, hdr);
1196 genlmsg_cancel(msg, hdr);
1201 devlink_port_fn_state_valid(enum devlink_port_fn_state state)
1203 return state == DEVLINK_PORT_FN_STATE_INACTIVE ||
1204 state == DEVLINK_PORT_FN_STATE_ACTIVE;
1208 devlink_port_fn_opstate_valid(enum devlink_port_fn_opstate opstate)
1210 return opstate == DEVLINK_PORT_FN_OPSTATE_DETACHED ||
1211 opstate == DEVLINK_PORT_FN_OPSTATE_ATTACHED;
1214 static int devlink_port_fn_state_fill(const struct devlink_ops *ops,
1215 struct devlink_port *port,
1216 struct sk_buff *msg,
1217 struct netlink_ext_ack *extack,
1220 enum devlink_port_fn_opstate opstate;
1221 enum devlink_port_fn_state state;
1224 if (!ops->port_fn_state_get)
1227 err = ops->port_fn_state_get(port, &state, &opstate, extack);
1229 if (err == -EOPNOTSUPP)
1233 if (!devlink_port_fn_state_valid(state)) {
1235 NL_SET_ERR_MSG_MOD(extack, "Invalid state read from driver");
1238 if (!devlink_port_fn_opstate_valid(opstate)) {
1240 NL_SET_ERR_MSG_MOD(extack,
1241 "Invalid operational state read from driver");
1244 if (nla_put_u8(msg, DEVLINK_PORT_FN_ATTR_STATE, state) ||
1245 nla_put_u8(msg, DEVLINK_PORT_FN_ATTR_OPSTATE, opstate))
1247 *msg_updated = true;
1252 devlink_nl_port_function_attrs_put(struct sk_buff *msg, struct devlink_port *port,
1253 struct netlink_ext_ack *extack)
1255 const struct devlink_ops *ops;
1256 struct nlattr *function_attr;
1257 bool msg_updated = false;
1260 function_attr = nla_nest_start_noflag(msg, DEVLINK_ATTR_PORT_FUNCTION);
1264 ops = port->devlink->ops;
1265 err = devlink_port_fn_hw_addr_fill(ops, port, msg, extack,
1269 err = devlink_port_fn_state_fill(ops, port, msg, extack, &msg_updated);
1271 if (err || !msg_updated)
1272 nla_nest_cancel(msg, function_attr);
1274 nla_nest_end(msg, function_attr);
1278 static int devlink_nl_port_fill(struct sk_buff *msg,
1279 struct devlink_port *devlink_port,
1280 enum devlink_command cmd, u32 portid, u32 seq,
1281 int flags, struct netlink_ext_ack *extack)
1283 struct devlink *devlink = devlink_port->devlink;
1286 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
1290 if (devlink_nl_put_handle(msg, devlink))
1291 goto nla_put_failure;
1292 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_INDEX, devlink_port->index))
1293 goto nla_put_failure;
1295 /* Hold rtnl lock while accessing port's netdev attributes. */
1297 spin_lock_bh(&devlink_port->type_lock);
1298 if (nla_put_u16(msg, DEVLINK_ATTR_PORT_TYPE, devlink_port->type))
1299 goto nla_put_failure_type_locked;
1300 if (devlink_port->desired_type != DEVLINK_PORT_TYPE_NOTSET &&
1301 nla_put_u16(msg, DEVLINK_ATTR_PORT_DESIRED_TYPE,
1302 devlink_port->desired_type))
1303 goto nla_put_failure_type_locked;
1304 if (devlink_port->type == DEVLINK_PORT_TYPE_ETH) {
1305 struct net *net = devlink_net(devlink_port->devlink);
1306 struct net_device *netdev = devlink_port->type_dev;
1308 if (netdev && net_eq(net, dev_net(netdev)) &&
1309 (nla_put_u32(msg, DEVLINK_ATTR_PORT_NETDEV_IFINDEX,
1311 nla_put_string(msg, DEVLINK_ATTR_PORT_NETDEV_NAME,
1313 goto nla_put_failure_type_locked;
1315 if (devlink_port->type == DEVLINK_PORT_TYPE_IB) {
1316 struct ib_device *ibdev = devlink_port->type_dev;
1319 nla_put_string(msg, DEVLINK_ATTR_PORT_IBDEV_NAME,
1321 goto nla_put_failure_type_locked;
1323 spin_unlock_bh(&devlink_port->type_lock);
1325 if (devlink_nl_port_attrs_put(msg, devlink_port))
1326 goto nla_put_failure;
1327 if (devlink_nl_port_function_attrs_put(msg, devlink_port, extack))
1328 goto nla_put_failure;
1329 if (devlink_port->linecard &&
1330 nla_put_u32(msg, DEVLINK_ATTR_LINECARD_INDEX,
1331 devlink_port->linecard->index))
1332 goto nla_put_failure;
1334 genlmsg_end(msg, hdr);
1337 nla_put_failure_type_locked:
1338 spin_unlock_bh(&devlink_port->type_lock);
1341 genlmsg_cancel(msg, hdr);
1345 static void devlink_port_notify(struct devlink_port *devlink_port,
1346 enum devlink_command cmd)
1348 struct devlink *devlink = devlink_port->devlink;
1349 struct sk_buff *msg;
1352 WARN_ON(cmd != DEVLINK_CMD_PORT_NEW && cmd != DEVLINK_CMD_PORT_DEL);
1354 if (!xa_get_mark(&devlinks, devlink->index, DEVLINK_REGISTERED))
1357 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
1361 err = devlink_nl_port_fill(msg, devlink_port, cmd, 0, 0, 0, NULL);
1367 genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink), msg,
1368 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
1371 static void devlink_rate_notify(struct devlink_rate *devlink_rate,
1372 enum devlink_command cmd)
1374 struct devlink *devlink = devlink_rate->devlink;
1375 struct sk_buff *msg;
1378 WARN_ON(cmd != DEVLINK_CMD_RATE_NEW && cmd != DEVLINK_CMD_RATE_DEL);
1380 if (!xa_get_mark(&devlinks, devlink->index, DEVLINK_REGISTERED))
1383 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
1387 err = devlink_nl_rate_fill(msg, devlink_rate, cmd, 0, 0, 0, NULL);
1393 genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink), msg,
1394 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
1397 static int devlink_nl_cmd_rate_get_dumpit(struct sk_buff *msg,
1398 struct netlink_callback *cb)
1400 struct devlink_rate *devlink_rate;
1401 struct devlink *devlink;
1402 int start = cb->args[0];
1403 unsigned long index;
1407 devlinks_xa_for_each_registered_get(sock_net(msg->sk), index, devlink) {
1409 list_for_each_entry(devlink_rate, &devlink->rate_list, list) {
1410 enum devlink_command cmd = DEVLINK_CMD_RATE_NEW;
1411 u32 id = NETLINK_CB(cb->skb).portid;
1417 err = devlink_nl_rate_fill(msg, devlink_rate, cmd, id,
1421 devl_unlock(devlink);
1422 devlink_put(devlink);
1427 devl_unlock(devlink);
1428 devlink_put(devlink);
1431 if (err != -EMSGSIZE)
1438 static int devlink_nl_cmd_rate_get_doit(struct sk_buff *skb,
1439 struct genl_info *info)
1441 struct devlink_rate *devlink_rate = info->user_ptr[1];
1442 struct sk_buff *msg;
1445 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
1449 err = devlink_nl_rate_fill(msg, devlink_rate, DEVLINK_CMD_RATE_NEW,
1450 info->snd_portid, info->snd_seq, 0,
1457 return genlmsg_reply(msg, info);
1461 devlink_rate_is_parent_node(struct devlink_rate *devlink_rate,
1462 struct devlink_rate *parent)
1465 if (parent == devlink_rate)
1467 parent = parent->parent;
1472 static int devlink_nl_cmd_get_doit(struct sk_buff *skb, struct genl_info *info)
1474 struct devlink *devlink = info->user_ptr[0];
1475 struct sk_buff *msg;
1478 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
1482 err = devlink_nl_fill(msg, devlink, DEVLINK_CMD_NEW,
1483 info->snd_portid, info->snd_seq, 0);
1489 return genlmsg_reply(msg, info);
1492 static int devlink_nl_cmd_get_dumpit(struct sk_buff *msg,
1493 struct netlink_callback *cb)
1495 struct devlink *devlink;
1496 int start = cb->args[0];
1497 unsigned long index;
1501 devlinks_xa_for_each_registered_get(sock_net(msg->sk), index, devlink) {
1504 devlink_put(devlink);
1508 err = devlink_nl_fill(msg, devlink, DEVLINK_CMD_NEW,
1509 NETLINK_CB(cb->skb).portid,
1510 cb->nlh->nlmsg_seq, NLM_F_MULTI);
1511 devlink_put(devlink);
1521 static int devlink_nl_cmd_port_get_doit(struct sk_buff *skb,
1522 struct genl_info *info)
1524 struct devlink_port *devlink_port = info->user_ptr[1];
1525 struct sk_buff *msg;
1528 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
1532 err = devlink_nl_port_fill(msg, devlink_port, DEVLINK_CMD_PORT_NEW,
1533 info->snd_portid, info->snd_seq, 0,
1540 return genlmsg_reply(msg, info);
1543 static int devlink_nl_cmd_port_get_dumpit(struct sk_buff *msg,
1544 struct netlink_callback *cb)
1546 struct devlink *devlink;
1547 struct devlink_port *devlink_port;
1548 int start = cb->args[0];
1549 unsigned long index;
1553 devlinks_xa_for_each_registered_get(sock_net(msg->sk), index, devlink) {
1555 list_for_each_entry(devlink_port, &devlink->port_list, list) {
1560 err = devlink_nl_port_fill(msg, devlink_port,
1562 NETLINK_CB(cb->skb).portid,
1564 NLM_F_MULTI, cb->extack);
1566 devl_unlock(devlink);
1567 devlink_put(devlink);
1572 devl_unlock(devlink);
1573 devlink_put(devlink);
1580 static int devlink_port_type_set(struct devlink_port *devlink_port,
1581 enum devlink_port_type port_type)
1586 if (!devlink_port->devlink->ops->port_type_set)
1589 if (port_type == devlink_port->type)
1592 err = devlink_port->devlink->ops->port_type_set(devlink_port,
1597 devlink_port->desired_type = port_type;
1598 devlink_port_notify(devlink_port, DEVLINK_CMD_PORT_NEW);
1602 static int devlink_port_function_hw_addr_set(struct devlink_port *port,
1603 const struct nlattr *attr,
1604 struct netlink_ext_ack *extack)
1606 const struct devlink_ops *ops = port->devlink->ops;
1610 hw_addr = nla_data(attr);
1611 hw_addr_len = nla_len(attr);
1612 if (hw_addr_len > MAX_ADDR_LEN) {
1613 NL_SET_ERR_MSG_MOD(extack, "Port function hardware address too long");
1616 if (port->type == DEVLINK_PORT_TYPE_ETH) {
1617 if (hw_addr_len != ETH_ALEN) {
1618 NL_SET_ERR_MSG_MOD(extack, "Address must be 6 bytes for Ethernet device");
1621 if (!is_unicast_ether_addr(hw_addr)) {
1622 NL_SET_ERR_MSG_MOD(extack, "Non-unicast hardware address unsupported");
1627 if (!ops->port_function_hw_addr_set) {
1628 NL_SET_ERR_MSG_MOD(extack, "Port doesn't support function attributes");
1632 return ops->port_function_hw_addr_set(port, hw_addr, hw_addr_len,
1636 static int devlink_port_fn_state_set(struct devlink_port *port,
1637 const struct nlattr *attr,
1638 struct netlink_ext_ack *extack)
1640 enum devlink_port_fn_state state;
1641 const struct devlink_ops *ops;
1643 state = nla_get_u8(attr);
1644 ops = port->devlink->ops;
1645 if (!ops->port_fn_state_set) {
1646 NL_SET_ERR_MSG_MOD(extack,
1647 "Function does not support state setting");
1650 return ops->port_fn_state_set(port, state, extack);
1653 static int devlink_port_function_set(struct devlink_port *port,
1654 const struct nlattr *attr,
1655 struct netlink_ext_ack *extack)
1657 struct nlattr *tb[DEVLINK_PORT_FUNCTION_ATTR_MAX + 1];
1660 err = nla_parse_nested(tb, DEVLINK_PORT_FUNCTION_ATTR_MAX, attr,
1661 devlink_function_nl_policy, extack);
1663 NL_SET_ERR_MSG_MOD(extack, "Fail to parse port function attributes");
1667 attr = tb[DEVLINK_PORT_FUNCTION_ATTR_HW_ADDR];
1669 err = devlink_port_function_hw_addr_set(port, attr, extack);
1673 /* Keep this as the last function attribute set, so that when
1674 * multiple port function attributes are set along with state,
1675 * Those can be applied first before activating the state.
1677 attr = tb[DEVLINK_PORT_FN_ATTR_STATE];
1679 err = devlink_port_fn_state_set(port, attr, extack);
1682 devlink_port_notify(port, DEVLINK_CMD_PORT_NEW);
1686 static int devlink_nl_cmd_port_set_doit(struct sk_buff *skb,
1687 struct genl_info *info)
1689 struct devlink_port *devlink_port = info->user_ptr[1];
1692 if (info->attrs[DEVLINK_ATTR_PORT_TYPE]) {
1693 enum devlink_port_type port_type;
1695 port_type = nla_get_u16(info->attrs[DEVLINK_ATTR_PORT_TYPE]);
1696 err = devlink_port_type_set(devlink_port, port_type);
1701 if (info->attrs[DEVLINK_ATTR_PORT_FUNCTION]) {
1702 struct nlattr *attr = info->attrs[DEVLINK_ATTR_PORT_FUNCTION];
1703 struct netlink_ext_ack *extack = info->extack;
1705 err = devlink_port_function_set(devlink_port, attr, extack);
1713 static int devlink_nl_cmd_port_split_doit(struct sk_buff *skb,
1714 struct genl_info *info)
1716 struct devlink_port *devlink_port = info->user_ptr[1];
1717 struct devlink *devlink = info->user_ptr[0];
1720 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_PORT_SPLIT_COUNT))
1722 if (!devlink->ops->port_split)
1725 count = nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_SPLIT_COUNT]);
1727 if (!devlink_port->attrs.splittable) {
1728 /* Split ports cannot be split. */
1729 if (devlink_port->attrs.split)
1730 NL_SET_ERR_MSG_MOD(info->extack, "Port cannot be split further");
1732 NL_SET_ERR_MSG_MOD(info->extack, "Port cannot be split");
1736 if (count < 2 || !is_power_of_2(count) || count > devlink_port->attrs.lanes) {
1737 NL_SET_ERR_MSG_MOD(info->extack, "Invalid split count");
1741 return devlink->ops->port_split(devlink, devlink_port, count,
1745 static int devlink_nl_cmd_port_unsplit_doit(struct sk_buff *skb,
1746 struct genl_info *info)
1748 struct devlink_port *devlink_port = info->user_ptr[1];
1749 struct devlink *devlink = info->user_ptr[0];
1751 if (!devlink->ops->port_unsplit)
1753 return devlink->ops->port_unsplit(devlink, devlink_port, info->extack);
1756 static int devlink_port_new_notify(struct devlink *devlink,
1757 unsigned int port_index,
1758 struct genl_info *info)
1760 struct devlink_port *devlink_port;
1761 struct sk_buff *msg;
1764 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
1768 lockdep_assert_held(&devlink->lock);
1769 devlink_port = devlink_port_get_by_index(devlink, port_index);
1770 if (!devlink_port) {
1775 err = devlink_nl_port_fill(msg, devlink_port, DEVLINK_CMD_NEW,
1776 info->snd_portid, info->snd_seq, 0, NULL);
1780 return genlmsg_reply(msg, info);
1787 static int devlink_nl_cmd_port_new_doit(struct sk_buff *skb,
1788 struct genl_info *info)
1790 struct netlink_ext_ack *extack = info->extack;
1791 struct devlink_port_new_attrs new_attrs = {};
1792 struct devlink *devlink = info->user_ptr[0];
1793 unsigned int new_port_index;
1796 if (!devlink->ops->port_new || !devlink->ops->port_del)
1799 if (!info->attrs[DEVLINK_ATTR_PORT_FLAVOUR] ||
1800 !info->attrs[DEVLINK_ATTR_PORT_PCI_PF_NUMBER]) {
1801 NL_SET_ERR_MSG_MOD(extack, "Port flavour or PCI PF are not specified");
1804 new_attrs.flavour = nla_get_u16(info->attrs[DEVLINK_ATTR_PORT_FLAVOUR]);
1806 nla_get_u16(info->attrs[DEVLINK_ATTR_PORT_PCI_PF_NUMBER]);
1808 if (info->attrs[DEVLINK_ATTR_PORT_INDEX]) {
1809 /* Port index of the new port being created by driver. */
1810 new_attrs.port_index =
1811 nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_INDEX]);
1812 new_attrs.port_index_valid = true;
1814 if (info->attrs[DEVLINK_ATTR_PORT_CONTROLLER_NUMBER]) {
1815 new_attrs.controller =
1816 nla_get_u16(info->attrs[DEVLINK_ATTR_PORT_CONTROLLER_NUMBER]);
1817 new_attrs.controller_valid = true;
1819 if (new_attrs.flavour == DEVLINK_PORT_FLAVOUR_PCI_SF &&
1820 info->attrs[DEVLINK_ATTR_PORT_PCI_SF_NUMBER]) {
1821 new_attrs.sfnum = nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_PCI_SF_NUMBER]);
1822 new_attrs.sfnum_valid = true;
1825 err = devlink->ops->port_new(devlink, &new_attrs, extack,
1830 err = devlink_port_new_notify(devlink, new_port_index, info);
1831 if (err && err != -ENODEV) {
1832 /* Fail to send the response; destroy newly created port. */
1833 devlink->ops->port_del(devlink, new_port_index, extack);
1838 static int devlink_nl_cmd_port_del_doit(struct sk_buff *skb,
1839 struct genl_info *info)
1841 struct netlink_ext_ack *extack = info->extack;
1842 struct devlink *devlink = info->user_ptr[0];
1843 unsigned int port_index;
1845 if (!devlink->ops->port_del)
1848 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_PORT_INDEX)) {
1849 NL_SET_ERR_MSG_MOD(extack, "Port index is not specified");
1852 port_index = nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_INDEX]);
1854 return devlink->ops->port_del(devlink, port_index, extack);
1858 devlink_nl_rate_parent_node_set(struct devlink_rate *devlink_rate,
1859 struct genl_info *info,
1860 struct nlattr *nla_parent)
1862 struct devlink *devlink = devlink_rate->devlink;
1863 const char *parent_name = nla_data(nla_parent);
1864 const struct devlink_ops *ops = devlink->ops;
1865 size_t len = strlen(parent_name);
1866 struct devlink_rate *parent;
1867 int err = -EOPNOTSUPP;
1869 parent = devlink_rate->parent;
1870 if (parent && len) {
1871 NL_SET_ERR_MSG_MOD(info->extack, "Rate object already has parent.");
1873 } else if (parent && !len) {
1874 if (devlink_rate_is_leaf(devlink_rate))
1875 err = ops->rate_leaf_parent_set(devlink_rate, NULL,
1876 devlink_rate->priv, NULL,
1878 else if (devlink_rate_is_node(devlink_rate))
1879 err = ops->rate_node_parent_set(devlink_rate, NULL,
1880 devlink_rate->priv, NULL,
1885 refcount_dec(&parent->refcnt);
1886 devlink_rate->parent = NULL;
1887 } else if (!parent && len) {
1888 parent = devlink_rate_node_get_by_name(devlink, parent_name);
1892 if (parent == devlink_rate) {
1893 NL_SET_ERR_MSG_MOD(info->extack, "Parent to self is not allowed");
1897 if (devlink_rate_is_node(devlink_rate) &&
1898 devlink_rate_is_parent_node(devlink_rate, parent->parent)) {
1899 NL_SET_ERR_MSG_MOD(info->extack, "Node is already a parent of parent node.");
1903 if (devlink_rate_is_leaf(devlink_rate))
1904 err = ops->rate_leaf_parent_set(devlink_rate, parent,
1905 devlink_rate->priv, parent->priv,
1907 else if (devlink_rate_is_node(devlink_rate))
1908 err = ops->rate_node_parent_set(devlink_rate, parent,
1909 devlink_rate->priv, parent->priv,
1914 refcount_inc(&parent->refcnt);
1915 devlink_rate->parent = parent;
1921 static int devlink_nl_rate_set(struct devlink_rate *devlink_rate,
1922 const struct devlink_ops *ops,
1923 struct genl_info *info)
1925 struct nlattr *nla_parent, **attrs = info->attrs;
1926 int err = -EOPNOTSUPP;
1929 if (attrs[DEVLINK_ATTR_RATE_TX_SHARE]) {
1930 rate = nla_get_u64(attrs[DEVLINK_ATTR_RATE_TX_SHARE]);
1931 if (devlink_rate_is_leaf(devlink_rate))
1932 err = ops->rate_leaf_tx_share_set(devlink_rate, devlink_rate->priv,
1933 rate, info->extack);
1934 else if (devlink_rate_is_node(devlink_rate))
1935 err = ops->rate_node_tx_share_set(devlink_rate, devlink_rate->priv,
1936 rate, info->extack);
1939 devlink_rate->tx_share = rate;
1942 if (attrs[DEVLINK_ATTR_RATE_TX_MAX]) {
1943 rate = nla_get_u64(attrs[DEVLINK_ATTR_RATE_TX_MAX]);
1944 if (devlink_rate_is_leaf(devlink_rate))
1945 err = ops->rate_leaf_tx_max_set(devlink_rate, devlink_rate->priv,
1946 rate, info->extack);
1947 else if (devlink_rate_is_node(devlink_rate))
1948 err = ops->rate_node_tx_max_set(devlink_rate, devlink_rate->priv,
1949 rate, info->extack);
1952 devlink_rate->tx_max = rate;
1955 nla_parent = attrs[DEVLINK_ATTR_RATE_PARENT_NODE_NAME];
1957 err = devlink_nl_rate_parent_node_set(devlink_rate, info,
1966 static bool devlink_rate_set_ops_supported(const struct devlink_ops *ops,
1967 struct genl_info *info,
1968 enum devlink_rate_type type)
1970 struct nlattr **attrs = info->attrs;
1972 if (type == DEVLINK_RATE_TYPE_LEAF) {
1973 if (attrs[DEVLINK_ATTR_RATE_TX_SHARE] && !ops->rate_leaf_tx_share_set) {
1974 NL_SET_ERR_MSG_MOD(info->extack, "TX share set isn't supported for the leafs");
1977 if (attrs[DEVLINK_ATTR_RATE_TX_MAX] && !ops->rate_leaf_tx_max_set) {
1978 NL_SET_ERR_MSG_MOD(info->extack, "TX max set isn't supported for the leafs");
1981 if (attrs[DEVLINK_ATTR_RATE_PARENT_NODE_NAME] &&
1982 !ops->rate_leaf_parent_set) {
1983 NL_SET_ERR_MSG_MOD(info->extack, "Parent set isn't supported for the leafs");
1986 } else if (type == DEVLINK_RATE_TYPE_NODE) {
1987 if (attrs[DEVLINK_ATTR_RATE_TX_SHARE] && !ops->rate_node_tx_share_set) {
1988 NL_SET_ERR_MSG_MOD(info->extack, "TX share set isn't supported for the nodes");
1991 if (attrs[DEVLINK_ATTR_RATE_TX_MAX] && !ops->rate_node_tx_max_set) {
1992 NL_SET_ERR_MSG_MOD(info->extack, "TX max set isn't supported for the nodes");
1995 if (attrs[DEVLINK_ATTR_RATE_PARENT_NODE_NAME] &&
1996 !ops->rate_node_parent_set) {
1997 NL_SET_ERR_MSG_MOD(info->extack, "Parent set isn't supported for the nodes");
2001 WARN(1, "Unknown type of rate object");
2008 static int devlink_nl_cmd_rate_set_doit(struct sk_buff *skb,
2009 struct genl_info *info)
2011 struct devlink_rate *devlink_rate = info->user_ptr[1];
2012 struct devlink *devlink = devlink_rate->devlink;
2013 const struct devlink_ops *ops = devlink->ops;
2016 if (!ops || !devlink_rate_set_ops_supported(ops, info, devlink_rate->type))
2019 err = devlink_nl_rate_set(devlink_rate, ops, info);
2022 devlink_rate_notify(devlink_rate, DEVLINK_CMD_RATE_NEW);
2026 static int devlink_nl_cmd_rate_new_doit(struct sk_buff *skb,
2027 struct genl_info *info)
2029 struct devlink *devlink = info->user_ptr[0];
2030 struct devlink_rate *rate_node;
2031 const struct devlink_ops *ops;
2035 if (!ops || !ops->rate_node_new || !ops->rate_node_del) {
2036 NL_SET_ERR_MSG_MOD(info->extack, "Rate nodes aren't supported");
2040 if (!devlink_rate_set_ops_supported(ops, info, DEVLINK_RATE_TYPE_NODE))
2043 rate_node = devlink_rate_node_get_from_attrs(devlink, info->attrs);
2044 if (!IS_ERR(rate_node))
2046 else if (rate_node == ERR_PTR(-EINVAL))
2049 rate_node = kzalloc(sizeof(*rate_node), GFP_KERNEL);
2053 rate_node->devlink = devlink;
2054 rate_node->type = DEVLINK_RATE_TYPE_NODE;
2055 rate_node->name = nla_strdup(info->attrs[DEVLINK_ATTR_RATE_NODE_NAME], GFP_KERNEL);
2056 if (!rate_node->name) {
2061 err = ops->rate_node_new(rate_node, &rate_node->priv, info->extack);
2065 err = devlink_nl_rate_set(rate_node, ops, info);
2069 refcount_set(&rate_node->refcnt, 1);
2070 list_add(&rate_node->list, &devlink->rate_list);
2071 devlink_rate_notify(rate_node, DEVLINK_CMD_RATE_NEW);
2075 ops->rate_node_del(rate_node, rate_node->priv, info->extack);
2077 kfree(rate_node->name);
2083 static int devlink_nl_cmd_rate_del_doit(struct sk_buff *skb,
2084 struct genl_info *info)
2086 struct devlink_rate *rate_node = info->user_ptr[1];
2087 struct devlink *devlink = rate_node->devlink;
2088 const struct devlink_ops *ops = devlink->ops;
2091 if (refcount_read(&rate_node->refcnt) > 1) {
2092 NL_SET_ERR_MSG_MOD(info->extack, "Node has children. Cannot delete node.");
2096 devlink_rate_notify(rate_node, DEVLINK_CMD_RATE_DEL);
2097 err = ops->rate_node_del(rate_node, rate_node->priv, info->extack);
2098 if (rate_node->parent)
2099 refcount_dec(&rate_node->parent->refcnt);
2100 list_del(&rate_node->list);
2101 kfree(rate_node->name);
2106 struct devlink_linecard_type {
2111 static int devlink_nl_linecard_fill(struct sk_buff *msg,
2112 struct devlink *devlink,
2113 struct devlink_linecard *linecard,
2114 enum devlink_command cmd, u32 portid,
2116 struct netlink_ext_ack *extack)
2118 struct devlink_linecard_type *linecard_type;
2119 struct nlattr *attr;
2123 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
2127 if (devlink_nl_put_handle(msg, devlink))
2128 goto nla_put_failure;
2129 if (nla_put_u32(msg, DEVLINK_ATTR_LINECARD_INDEX, linecard->index))
2130 goto nla_put_failure;
2131 if (nla_put_u8(msg, DEVLINK_ATTR_LINECARD_STATE, linecard->state))
2132 goto nla_put_failure;
2133 if (linecard->type &&
2134 nla_put_string(msg, DEVLINK_ATTR_LINECARD_TYPE, linecard->type))
2135 goto nla_put_failure;
2137 if (linecard->types_count) {
2138 attr = nla_nest_start(msg,
2139 DEVLINK_ATTR_LINECARD_SUPPORTED_TYPES);
2141 goto nla_put_failure;
2142 for (i = 0; i < linecard->types_count; i++) {
2143 linecard_type = &linecard->types[i];
2144 if (nla_put_string(msg, DEVLINK_ATTR_LINECARD_TYPE,
2145 linecard_type->type)) {
2146 nla_nest_cancel(msg, attr);
2147 goto nla_put_failure;
2150 nla_nest_end(msg, attr);
2153 if (linecard->nested_devlink &&
2154 devlink_nl_put_nested_handle(msg, linecard->nested_devlink))
2155 goto nla_put_failure;
2157 genlmsg_end(msg, hdr);
2161 genlmsg_cancel(msg, hdr);
2165 static void devlink_linecard_notify(struct devlink_linecard *linecard,
2166 enum devlink_command cmd)
2168 struct devlink *devlink = linecard->devlink;
2169 struct sk_buff *msg;
2172 WARN_ON(cmd != DEVLINK_CMD_LINECARD_NEW &&
2173 cmd != DEVLINK_CMD_LINECARD_DEL);
2175 if (!xa_get_mark(&devlinks, devlink->index, DEVLINK_REGISTERED))
2178 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
2182 err = devlink_nl_linecard_fill(msg, devlink, linecard, cmd, 0, 0, 0,
2189 genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink),
2190 msg, 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
2193 static int devlink_nl_cmd_linecard_get_doit(struct sk_buff *skb,
2194 struct genl_info *info)
2196 struct devlink_linecard *linecard = info->user_ptr[1];
2197 struct devlink *devlink = linecard->devlink;
2198 struct sk_buff *msg;
2201 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
2205 mutex_lock(&linecard->state_lock);
2206 err = devlink_nl_linecard_fill(msg, devlink, linecard,
2207 DEVLINK_CMD_LINECARD_NEW,
2208 info->snd_portid, info->snd_seq, 0,
2210 mutex_unlock(&linecard->state_lock);
2216 return genlmsg_reply(msg, info);
2219 static int devlink_nl_cmd_linecard_get_dumpit(struct sk_buff *msg,
2220 struct netlink_callback *cb)
2222 struct devlink_linecard *linecard;
2223 struct devlink *devlink;
2224 int start = cb->args[0];
2225 unsigned long index;
2229 devlinks_xa_for_each_registered_get(sock_net(msg->sk), index, devlink) {
2230 mutex_lock(&devlink->linecards_lock);
2231 list_for_each_entry(linecard, &devlink->linecard_list, list) {
2236 mutex_lock(&linecard->state_lock);
2237 err = devlink_nl_linecard_fill(msg, devlink, linecard,
2238 DEVLINK_CMD_LINECARD_NEW,
2239 NETLINK_CB(cb->skb).portid,
2243 mutex_unlock(&linecard->state_lock);
2245 mutex_unlock(&devlink->linecards_lock);
2246 devlink_put(devlink);
2251 mutex_unlock(&devlink->linecards_lock);
2252 devlink_put(devlink);
2259 static struct devlink_linecard_type *
2260 devlink_linecard_type_lookup(struct devlink_linecard *linecard,
2263 struct devlink_linecard_type *linecard_type;
2266 for (i = 0; i < linecard->types_count; i++) {
2267 linecard_type = &linecard->types[i];
2268 if (!strcmp(type, linecard_type->type))
2269 return linecard_type;
2274 static int devlink_linecard_type_set(struct devlink_linecard *linecard,
2276 struct netlink_ext_ack *extack)
2278 const struct devlink_linecard_ops *ops = linecard->ops;
2279 struct devlink_linecard_type *linecard_type;
2282 mutex_lock(&linecard->state_lock);
2283 if (linecard->state == DEVLINK_LINECARD_STATE_PROVISIONING) {
2284 NL_SET_ERR_MSG_MOD(extack, "Line card is currently being provisioned");
2288 if (linecard->state == DEVLINK_LINECARD_STATE_UNPROVISIONING) {
2289 NL_SET_ERR_MSG_MOD(extack, "Line card is currently being unprovisioned");
2294 linecard_type = devlink_linecard_type_lookup(linecard, type);
2295 if (!linecard_type) {
2296 NL_SET_ERR_MSG_MOD(extack, "Unsupported line card type provided");
2301 if (linecard->state != DEVLINK_LINECARD_STATE_UNPROVISIONED &&
2302 linecard->state != DEVLINK_LINECARD_STATE_PROVISIONING_FAILED) {
2303 NL_SET_ERR_MSG_MOD(extack, "Line card already provisioned");
2305 /* Check if the line card is provisioned in the same
2306 * way the user asks. In case it is, make the operation
2307 * to return success.
2309 if (ops->same_provision &&
2310 ops->same_provision(linecard, linecard->priv,
2311 linecard_type->type,
2312 linecard_type->priv))
2317 linecard->state = DEVLINK_LINECARD_STATE_PROVISIONING;
2318 linecard->type = linecard_type->type;
2319 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_NEW);
2320 mutex_unlock(&linecard->state_lock);
2321 err = ops->provision(linecard, linecard->priv, linecard_type->type,
2322 linecard_type->priv, extack);
2324 /* Provisioning failed. Assume the linecard is unprovisioned
2325 * for future operations.
2327 mutex_lock(&linecard->state_lock);
2328 linecard->state = DEVLINK_LINECARD_STATE_UNPROVISIONED;
2329 linecard->type = NULL;
2330 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_NEW);
2331 mutex_unlock(&linecard->state_lock);
2336 mutex_unlock(&linecard->state_lock);
2340 static int devlink_linecard_type_unset(struct devlink_linecard *linecard,
2341 struct netlink_ext_ack *extack)
2345 mutex_lock(&linecard->state_lock);
2346 if (linecard->state == DEVLINK_LINECARD_STATE_PROVISIONING) {
2347 NL_SET_ERR_MSG_MOD(extack, "Line card is currently being provisioned");
2351 if (linecard->state == DEVLINK_LINECARD_STATE_UNPROVISIONING) {
2352 NL_SET_ERR_MSG_MOD(extack, "Line card is currently being unprovisioned");
2356 if (linecard->state == DEVLINK_LINECARD_STATE_PROVISIONING_FAILED) {
2357 linecard->state = DEVLINK_LINECARD_STATE_UNPROVISIONED;
2358 linecard->type = NULL;
2359 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_NEW);
2364 if (linecard->state == DEVLINK_LINECARD_STATE_UNPROVISIONED) {
2365 NL_SET_ERR_MSG_MOD(extack, "Line card is not provisioned");
2369 linecard->state = DEVLINK_LINECARD_STATE_UNPROVISIONING;
2370 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_NEW);
2371 mutex_unlock(&linecard->state_lock);
2372 err = linecard->ops->unprovision(linecard, linecard->priv,
2375 /* Unprovisioning failed. Assume the linecard is unprovisioned
2376 * for future operations.
2378 mutex_lock(&linecard->state_lock);
2379 linecard->state = DEVLINK_LINECARD_STATE_UNPROVISIONED;
2380 linecard->type = NULL;
2381 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_NEW);
2382 mutex_unlock(&linecard->state_lock);
2387 mutex_unlock(&linecard->state_lock);
2391 static int devlink_nl_cmd_linecard_set_doit(struct sk_buff *skb,
2392 struct genl_info *info)
2394 struct devlink_linecard *linecard = info->user_ptr[1];
2395 struct netlink_ext_ack *extack = info->extack;
2398 if (info->attrs[DEVLINK_ATTR_LINECARD_TYPE]) {
2401 type = nla_data(info->attrs[DEVLINK_ATTR_LINECARD_TYPE]);
2402 if (strcmp(type, "")) {
2403 err = devlink_linecard_type_set(linecard, type, extack);
2407 err = devlink_linecard_type_unset(linecard, extack);
2416 static int devlink_nl_sb_fill(struct sk_buff *msg, struct devlink *devlink,
2417 struct devlink_sb *devlink_sb,
2418 enum devlink_command cmd, u32 portid,
2423 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
2427 if (devlink_nl_put_handle(msg, devlink))
2428 goto nla_put_failure;
2429 if (nla_put_u32(msg, DEVLINK_ATTR_SB_INDEX, devlink_sb->index))
2430 goto nla_put_failure;
2431 if (nla_put_u32(msg, DEVLINK_ATTR_SB_SIZE, devlink_sb->size))
2432 goto nla_put_failure;
2433 if (nla_put_u16(msg, DEVLINK_ATTR_SB_INGRESS_POOL_COUNT,
2434 devlink_sb->ingress_pools_count))
2435 goto nla_put_failure;
2436 if (nla_put_u16(msg, DEVLINK_ATTR_SB_EGRESS_POOL_COUNT,
2437 devlink_sb->egress_pools_count))
2438 goto nla_put_failure;
2439 if (nla_put_u16(msg, DEVLINK_ATTR_SB_INGRESS_TC_COUNT,
2440 devlink_sb->ingress_tc_count))
2441 goto nla_put_failure;
2442 if (nla_put_u16(msg, DEVLINK_ATTR_SB_EGRESS_TC_COUNT,
2443 devlink_sb->egress_tc_count))
2444 goto nla_put_failure;
2446 genlmsg_end(msg, hdr);
2450 genlmsg_cancel(msg, hdr);
2454 static int devlink_nl_cmd_sb_get_doit(struct sk_buff *skb,
2455 struct genl_info *info)
2457 struct devlink *devlink = info->user_ptr[0];
2458 struct devlink_sb *devlink_sb;
2459 struct sk_buff *msg;
2462 devlink_sb = devlink_sb_get_from_info(devlink, info);
2463 if (IS_ERR(devlink_sb))
2464 return PTR_ERR(devlink_sb);
2466 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
2470 err = devlink_nl_sb_fill(msg, devlink, devlink_sb,
2472 info->snd_portid, info->snd_seq, 0);
2478 return genlmsg_reply(msg, info);
2481 static int devlink_nl_cmd_sb_get_dumpit(struct sk_buff *msg,
2482 struct netlink_callback *cb)
2484 struct devlink *devlink;
2485 struct devlink_sb *devlink_sb;
2486 int start = cb->args[0];
2487 unsigned long index;
2491 devlinks_xa_for_each_registered_get(sock_net(msg->sk), index, devlink) {
2493 list_for_each_entry(devlink_sb, &devlink->sb_list, list) {
2498 err = devlink_nl_sb_fill(msg, devlink, devlink_sb,
2500 NETLINK_CB(cb->skb).portid,
2504 devl_unlock(devlink);
2505 devlink_put(devlink);
2510 devl_unlock(devlink);
2511 devlink_put(devlink);
2518 static int devlink_nl_sb_pool_fill(struct sk_buff *msg, struct devlink *devlink,
2519 struct devlink_sb *devlink_sb,
2520 u16 pool_index, enum devlink_command cmd,
2521 u32 portid, u32 seq, int flags)
2523 struct devlink_sb_pool_info pool_info;
2527 err = devlink->ops->sb_pool_get(devlink, devlink_sb->index,
2528 pool_index, &pool_info);
2532 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
2536 if (devlink_nl_put_handle(msg, devlink))
2537 goto nla_put_failure;
2538 if (nla_put_u32(msg, DEVLINK_ATTR_SB_INDEX, devlink_sb->index))
2539 goto nla_put_failure;
2540 if (nla_put_u16(msg, DEVLINK_ATTR_SB_POOL_INDEX, pool_index))
2541 goto nla_put_failure;
2542 if (nla_put_u8(msg, DEVLINK_ATTR_SB_POOL_TYPE, pool_info.pool_type))
2543 goto nla_put_failure;
2544 if (nla_put_u32(msg, DEVLINK_ATTR_SB_POOL_SIZE, pool_info.size))
2545 goto nla_put_failure;
2546 if (nla_put_u8(msg, DEVLINK_ATTR_SB_POOL_THRESHOLD_TYPE,
2547 pool_info.threshold_type))
2548 goto nla_put_failure;
2549 if (nla_put_u32(msg, DEVLINK_ATTR_SB_POOL_CELL_SIZE,
2550 pool_info.cell_size))
2551 goto nla_put_failure;
2553 genlmsg_end(msg, hdr);
2557 genlmsg_cancel(msg, hdr);
2561 static int devlink_nl_cmd_sb_pool_get_doit(struct sk_buff *skb,
2562 struct genl_info *info)
2564 struct devlink *devlink = info->user_ptr[0];
2565 struct devlink_sb *devlink_sb;
2566 struct sk_buff *msg;
2570 devlink_sb = devlink_sb_get_from_info(devlink, info);
2571 if (IS_ERR(devlink_sb))
2572 return PTR_ERR(devlink_sb);
2574 err = devlink_sb_pool_index_get_from_info(devlink_sb, info,
2579 if (!devlink->ops->sb_pool_get)
2582 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
2586 err = devlink_nl_sb_pool_fill(msg, devlink, devlink_sb, pool_index,
2587 DEVLINK_CMD_SB_POOL_NEW,
2588 info->snd_portid, info->snd_seq, 0);
2594 return genlmsg_reply(msg, info);
2597 static int __sb_pool_get_dumpit(struct sk_buff *msg, int start, int *p_idx,
2598 struct devlink *devlink,
2599 struct devlink_sb *devlink_sb,
2600 u32 portid, u32 seq)
2602 u16 pool_count = devlink_sb_pool_count(devlink_sb);
2606 for (pool_index = 0; pool_index < pool_count; pool_index++) {
2607 if (*p_idx < start) {
2611 err = devlink_nl_sb_pool_fill(msg, devlink,
2614 DEVLINK_CMD_SB_POOL_NEW,
2615 portid, seq, NLM_F_MULTI);
2623 static int devlink_nl_cmd_sb_pool_get_dumpit(struct sk_buff *msg,
2624 struct netlink_callback *cb)
2626 struct devlink *devlink;
2627 struct devlink_sb *devlink_sb;
2628 int start = cb->args[0];
2629 unsigned long index;
2633 devlinks_xa_for_each_registered_get(sock_net(msg->sk), index, devlink) {
2634 if (!devlink->ops->sb_pool_get)
2638 list_for_each_entry(devlink_sb, &devlink->sb_list, list) {
2639 err = __sb_pool_get_dumpit(msg, start, &idx, devlink,
2641 NETLINK_CB(cb->skb).portid,
2642 cb->nlh->nlmsg_seq);
2643 if (err == -EOPNOTSUPP) {
2646 devl_unlock(devlink);
2647 devlink_put(devlink);
2651 devl_unlock(devlink);
2653 devlink_put(devlink);
2656 if (err != -EMSGSIZE)
2663 static int devlink_sb_pool_set(struct devlink *devlink, unsigned int sb_index,
2664 u16 pool_index, u32 size,
2665 enum devlink_sb_threshold_type threshold_type,
2666 struct netlink_ext_ack *extack)
2669 const struct devlink_ops *ops = devlink->ops;
2671 if (ops->sb_pool_set)
2672 return ops->sb_pool_set(devlink, sb_index, pool_index,
2673 size, threshold_type, extack);
2677 static int devlink_nl_cmd_sb_pool_set_doit(struct sk_buff *skb,
2678 struct genl_info *info)
2680 struct devlink *devlink = info->user_ptr[0];
2681 enum devlink_sb_threshold_type threshold_type;
2682 struct devlink_sb *devlink_sb;
2687 devlink_sb = devlink_sb_get_from_info(devlink, info);
2688 if (IS_ERR(devlink_sb))
2689 return PTR_ERR(devlink_sb);
2691 err = devlink_sb_pool_index_get_from_info(devlink_sb, info,
2696 err = devlink_sb_th_type_get_from_info(info, &threshold_type);
2700 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_SB_POOL_SIZE))
2703 size = nla_get_u32(info->attrs[DEVLINK_ATTR_SB_POOL_SIZE]);
2704 return devlink_sb_pool_set(devlink, devlink_sb->index,
2705 pool_index, size, threshold_type,
2709 static int devlink_nl_sb_port_pool_fill(struct sk_buff *msg,
2710 struct devlink *devlink,
2711 struct devlink_port *devlink_port,
2712 struct devlink_sb *devlink_sb,
2714 enum devlink_command cmd,
2715 u32 portid, u32 seq, int flags)
2717 const struct devlink_ops *ops = devlink->ops;
2722 err = ops->sb_port_pool_get(devlink_port, devlink_sb->index,
2723 pool_index, &threshold);
2727 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
2731 if (devlink_nl_put_handle(msg, devlink))
2732 goto nla_put_failure;
2733 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_INDEX, devlink_port->index))
2734 goto nla_put_failure;
2735 if (nla_put_u32(msg, DEVLINK_ATTR_SB_INDEX, devlink_sb->index))
2736 goto nla_put_failure;
2737 if (nla_put_u16(msg, DEVLINK_ATTR_SB_POOL_INDEX, pool_index))
2738 goto nla_put_failure;
2739 if (nla_put_u32(msg, DEVLINK_ATTR_SB_THRESHOLD, threshold))
2740 goto nla_put_failure;
2742 if (ops->sb_occ_port_pool_get) {
2746 err = ops->sb_occ_port_pool_get(devlink_port, devlink_sb->index,
2747 pool_index, &cur, &max);
2748 if (err && err != -EOPNOTSUPP)
2749 goto sb_occ_get_failure;
2751 if (nla_put_u32(msg, DEVLINK_ATTR_SB_OCC_CUR, cur))
2752 goto nla_put_failure;
2753 if (nla_put_u32(msg, DEVLINK_ATTR_SB_OCC_MAX, max))
2754 goto nla_put_failure;
2758 genlmsg_end(msg, hdr);
2764 genlmsg_cancel(msg, hdr);
2768 static int devlink_nl_cmd_sb_port_pool_get_doit(struct sk_buff *skb,
2769 struct genl_info *info)
2771 struct devlink_port *devlink_port = info->user_ptr[1];
2772 struct devlink *devlink = devlink_port->devlink;
2773 struct devlink_sb *devlink_sb;
2774 struct sk_buff *msg;
2778 devlink_sb = devlink_sb_get_from_info(devlink, info);
2779 if (IS_ERR(devlink_sb))
2780 return PTR_ERR(devlink_sb);
2782 err = devlink_sb_pool_index_get_from_info(devlink_sb, info,
2787 if (!devlink->ops->sb_port_pool_get)
2790 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
2794 err = devlink_nl_sb_port_pool_fill(msg, devlink, devlink_port,
2795 devlink_sb, pool_index,
2796 DEVLINK_CMD_SB_PORT_POOL_NEW,
2797 info->snd_portid, info->snd_seq, 0);
2803 return genlmsg_reply(msg, info);
2806 static int __sb_port_pool_get_dumpit(struct sk_buff *msg, int start, int *p_idx,
2807 struct devlink *devlink,
2808 struct devlink_sb *devlink_sb,
2809 u32 portid, u32 seq)
2811 struct devlink_port *devlink_port;
2812 u16 pool_count = devlink_sb_pool_count(devlink_sb);
2816 list_for_each_entry(devlink_port, &devlink->port_list, list) {
2817 for (pool_index = 0; pool_index < pool_count; pool_index++) {
2818 if (*p_idx < start) {
2822 err = devlink_nl_sb_port_pool_fill(msg, devlink,
2826 DEVLINK_CMD_SB_PORT_POOL_NEW,
2837 static int devlink_nl_cmd_sb_port_pool_get_dumpit(struct sk_buff *msg,
2838 struct netlink_callback *cb)
2840 struct devlink *devlink;
2841 struct devlink_sb *devlink_sb;
2842 int start = cb->args[0];
2843 unsigned long index;
2847 devlinks_xa_for_each_registered_get(sock_net(msg->sk), index, devlink) {
2848 if (!devlink->ops->sb_port_pool_get)
2852 list_for_each_entry(devlink_sb, &devlink->sb_list, list) {
2853 err = __sb_port_pool_get_dumpit(msg, start, &idx,
2854 devlink, devlink_sb,
2855 NETLINK_CB(cb->skb).portid,
2856 cb->nlh->nlmsg_seq);
2857 if (err == -EOPNOTSUPP) {
2860 devl_unlock(devlink);
2861 devlink_put(devlink);
2865 devl_unlock(devlink);
2867 devlink_put(devlink);
2870 if (err != -EMSGSIZE)
2877 static int devlink_sb_port_pool_set(struct devlink_port *devlink_port,
2878 unsigned int sb_index, u16 pool_index,
2880 struct netlink_ext_ack *extack)
2883 const struct devlink_ops *ops = devlink_port->devlink->ops;
2885 if (ops->sb_port_pool_set)
2886 return ops->sb_port_pool_set(devlink_port, sb_index,
2887 pool_index, threshold, extack);
2891 static int devlink_nl_cmd_sb_port_pool_set_doit(struct sk_buff *skb,
2892 struct genl_info *info)
2894 struct devlink_port *devlink_port = info->user_ptr[1];
2895 struct devlink *devlink = info->user_ptr[0];
2896 struct devlink_sb *devlink_sb;
2901 devlink_sb = devlink_sb_get_from_info(devlink, info);
2902 if (IS_ERR(devlink_sb))
2903 return PTR_ERR(devlink_sb);
2905 err = devlink_sb_pool_index_get_from_info(devlink_sb, info,
2910 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_SB_THRESHOLD))
2913 threshold = nla_get_u32(info->attrs[DEVLINK_ATTR_SB_THRESHOLD]);
2914 return devlink_sb_port_pool_set(devlink_port, devlink_sb->index,
2915 pool_index, threshold, info->extack);
2919 devlink_nl_sb_tc_pool_bind_fill(struct sk_buff *msg, struct devlink *devlink,
2920 struct devlink_port *devlink_port,
2921 struct devlink_sb *devlink_sb, u16 tc_index,
2922 enum devlink_sb_pool_type pool_type,
2923 enum devlink_command cmd,
2924 u32 portid, u32 seq, int flags)
2926 const struct devlink_ops *ops = devlink->ops;
2932 err = ops->sb_tc_pool_bind_get(devlink_port, devlink_sb->index,
2933 tc_index, pool_type,
2934 &pool_index, &threshold);
2938 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
2942 if (devlink_nl_put_handle(msg, devlink))
2943 goto nla_put_failure;
2944 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_INDEX, devlink_port->index))
2945 goto nla_put_failure;
2946 if (nla_put_u32(msg, DEVLINK_ATTR_SB_INDEX, devlink_sb->index))
2947 goto nla_put_failure;
2948 if (nla_put_u16(msg, DEVLINK_ATTR_SB_TC_INDEX, tc_index))
2949 goto nla_put_failure;
2950 if (nla_put_u8(msg, DEVLINK_ATTR_SB_POOL_TYPE, pool_type))
2951 goto nla_put_failure;
2952 if (nla_put_u16(msg, DEVLINK_ATTR_SB_POOL_INDEX, pool_index))
2953 goto nla_put_failure;
2954 if (nla_put_u32(msg, DEVLINK_ATTR_SB_THRESHOLD, threshold))
2955 goto nla_put_failure;
2957 if (ops->sb_occ_tc_port_bind_get) {
2961 err = ops->sb_occ_tc_port_bind_get(devlink_port,
2963 tc_index, pool_type,
2965 if (err && err != -EOPNOTSUPP)
2968 if (nla_put_u32(msg, DEVLINK_ATTR_SB_OCC_CUR, cur))
2969 goto nla_put_failure;
2970 if (nla_put_u32(msg, DEVLINK_ATTR_SB_OCC_MAX, max))
2971 goto nla_put_failure;
2975 genlmsg_end(msg, hdr);
2979 genlmsg_cancel(msg, hdr);
2983 static int devlink_nl_cmd_sb_tc_pool_bind_get_doit(struct sk_buff *skb,
2984 struct genl_info *info)
2986 struct devlink_port *devlink_port = info->user_ptr[1];
2987 struct devlink *devlink = devlink_port->devlink;
2988 struct devlink_sb *devlink_sb;
2989 struct sk_buff *msg;
2990 enum devlink_sb_pool_type pool_type;
2994 devlink_sb = devlink_sb_get_from_info(devlink, info);
2995 if (IS_ERR(devlink_sb))
2996 return PTR_ERR(devlink_sb);
2998 err = devlink_sb_pool_type_get_from_info(info, &pool_type);
3002 err = devlink_sb_tc_index_get_from_info(devlink_sb, info,
3003 pool_type, &tc_index);
3007 if (!devlink->ops->sb_tc_pool_bind_get)
3010 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
3014 err = devlink_nl_sb_tc_pool_bind_fill(msg, devlink, devlink_port,
3015 devlink_sb, tc_index, pool_type,
3016 DEVLINK_CMD_SB_TC_POOL_BIND_NEW,
3024 return genlmsg_reply(msg, info);
3027 static int __sb_tc_pool_bind_get_dumpit(struct sk_buff *msg,
3028 int start, int *p_idx,
3029 struct devlink *devlink,
3030 struct devlink_sb *devlink_sb,
3031 u32 portid, u32 seq)
3033 struct devlink_port *devlink_port;
3037 list_for_each_entry(devlink_port, &devlink->port_list, list) {
3039 tc_index < devlink_sb->ingress_tc_count; tc_index++) {
3040 if (*p_idx < start) {
3044 err = devlink_nl_sb_tc_pool_bind_fill(msg, devlink,
3048 DEVLINK_SB_POOL_TYPE_INGRESS,
3049 DEVLINK_CMD_SB_TC_POOL_BIND_NEW,
3057 tc_index < devlink_sb->egress_tc_count; tc_index++) {
3058 if (*p_idx < start) {
3062 err = devlink_nl_sb_tc_pool_bind_fill(msg, devlink,
3066 DEVLINK_SB_POOL_TYPE_EGRESS,
3067 DEVLINK_CMD_SB_TC_POOL_BIND_NEW,
3079 devlink_nl_cmd_sb_tc_pool_bind_get_dumpit(struct sk_buff *msg,
3080 struct netlink_callback *cb)
3082 struct devlink *devlink;
3083 struct devlink_sb *devlink_sb;
3084 int start = cb->args[0];
3085 unsigned long index;
3089 devlinks_xa_for_each_registered_get(sock_net(msg->sk), index, devlink) {
3090 if (!devlink->ops->sb_tc_pool_bind_get)
3094 list_for_each_entry(devlink_sb, &devlink->sb_list, list) {
3095 err = __sb_tc_pool_bind_get_dumpit(msg, start, &idx,
3098 NETLINK_CB(cb->skb).portid,
3099 cb->nlh->nlmsg_seq);
3100 if (err == -EOPNOTSUPP) {
3103 devl_unlock(devlink);
3104 devlink_put(devlink);
3108 devl_unlock(devlink);
3110 devlink_put(devlink);
3113 if (err != -EMSGSIZE)
3120 static int devlink_sb_tc_pool_bind_set(struct devlink_port *devlink_port,
3121 unsigned int sb_index, u16 tc_index,
3122 enum devlink_sb_pool_type pool_type,
3123 u16 pool_index, u32 threshold,
3124 struct netlink_ext_ack *extack)
3127 const struct devlink_ops *ops = devlink_port->devlink->ops;
3129 if (ops->sb_tc_pool_bind_set)
3130 return ops->sb_tc_pool_bind_set(devlink_port, sb_index,
3131 tc_index, pool_type,
3132 pool_index, threshold, extack);
3136 static int devlink_nl_cmd_sb_tc_pool_bind_set_doit(struct sk_buff *skb,
3137 struct genl_info *info)
3139 struct devlink_port *devlink_port = info->user_ptr[1];
3140 struct devlink *devlink = info->user_ptr[0];
3141 enum devlink_sb_pool_type pool_type;
3142 struct devlink_sb *devlink_sb;
3148 devlink_sb = devlink_sb_get_from_info(devlink, info);
3149 if (IS_ERR(devlink_sb))
3150 return PTR_ERR(devlink_sb);
3152 err = devlink_sb_pool_type_get_from_info(info, &pool_type);
3156 err = devlink_sb_tc_index_get_from_info(devlink_sb, info,
3157 pool_type, &tc_index);
3161 err = devlink_sb_pool_index_get_from_info(devlink_sb, info,
3166 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_SB_THRESHOLD))
3169 threshold = nla_get_u32(info->attrs[DEVLINK_ATTR_SB_THRESHOLD]);
3170 return devlink_sb_tc_pool_bind_set(devlink_port, devlink_sb->index,
3171 tc_index, pool_type,
3172 pool_index, threshold, info->extack);
3175 static int devlink_nl_cmd_sb_occ_snapshot_doit(struct sk_buff *skb,
3176 struct genl_info *info)
3178 struct devlink *devlink = info->user_ptr[0];
3179 const struct devlink_ops *ops = devlink->ops;
3180 struct devlink_sb *devlink_sb;
3182 devlink_sb = devlink_sb_get_from_info(devlink, info);
3183 if (IS_ERR(devlink_sb))
3184 return PTR_ERR(devlink_sb);
3186 if (ops->sb_occ_snapshot)
3187 return ops->sb_occ_snapshot(devlink, devlink_sb->index);
3191 static int devlink_nl_cmd_sb_occ_max_clear_doit(struct sk_buff *skb,
3192 struct genl_info *info)
3194 struct devlink *devlink = info->user_ptr[0];
3195 const struct devlink_ops *ops = devlink->ops;
3196 struct devlink_sb *devlink_sb;
3198 devlink_sb = devlink_sb_get_from_info(devlink, info);
3199 if (IS_ERR(devlink_sb))
3200 return PTR_ERR(devlink_sb);
3202 if (ops->sb_occ_max_clear)
3203 return ops->sb_occ_max_clear(devlink, devlink_sb->index);
3207 static int devlink_nl_eswitch_fill(struct sk_buff *msg, struct devlink *devlink,
3208 enum devlink_command cmd, u32 portid,
3211 const struct devlink_ops *ops = devlink->ops;
3212 enum devlink_eswitch_encap_mode encap_mode;
3218 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
3222 err = devlink_nl_put_handle(msg, devlink);
3224 goto nla_put_failure;
3226 if (ops->eswitch_mode_get) {
3227 err = ops->eswitch_mode_get(devlink, &mode);
3229 goto nla_put_failure;
3230 err = nla_put_u16(msg, DEVLINK_ATTR_ESWITCH_MODE, mode);
3232 goto nla_put_failure;
3235 if (ops->eswitch_inline_mode_get) {
3236 err = ops->eswitch_inline_mode_get(devlink, &inline_mode);
3238 goto nla_put_failure;
3239 err = nla_put_u8(msg, DEVLINK_ATTR_ESWITCH_INLINE_MODE,
3242 goto nla_put_failure;
3245 if (ops->eswitch_encap_mode_get) {
3246 err = ops->eswitch_encap_mode_get(devlink, &encap_mode);
3248 goto nla_put_failure;
3249 err = nla_put_u8(msg, DEVLINK_ATTR_ESWITCH_ENCAP_MODE, encap_mode);
3251 goto nla_put_failure;
3254 genlmsg_end(msg, hdr);
3258 genlmsg_cancel(msg, hdr);
3262 static int devlink_nl_cmd_eswitch_get_doit(struct sk_buff *skb,
3263 struct genl_info *info)
3265 struct devlink *devlink = info->user_ptr[0];
3266 struct sk_buff *msg;
3269 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
3273 err = devlink_nl_eswitch_fill(msg, devlink, DEVLINK_CMD_ESWITCH_GET,
3274 info->snd_portid, info->snd_seq, 0);
3281 return genlmsg_reply(msg, info);
3284 static int devlink_rate_nodes_check(struct devlink *devlink, u16 mode,
3285 struct netlink_ext_ack *extack)
3287 struct devlink_rate *devlink_rate;
3289 list_for_each_entry(devlink_rate, &devlink->rate_list, list)
3290 if (devlink_rate_is_node(devlink_rate)) {
3291 NL_SET_ERR_MSG_MOD(extack, "Rate node(s) exists.");
3297 static int devlink_nl_cmd_eswitch_set_doit(struct sk_buff *skb,
3298 struct genl_info *info)
3300 struct devlink *devlink = info->user_ptr[0];
3301 const struct devlink_ops *ops = devlink->ops;
3302 enum devlink_eswitch_encap_mode encap_mode;
3307 if (info->attrs[DEVLINK_ATTR_ESWITCH_MODE]) {
3308 if (!ops->eswitch_mode_set)
3310 mode = nla_get_u16(info->attrs[DEVLINK_ATTR_ESWITCH_MODE]);
3311 err = devlink_rate_nodes_check(devlink, mode, info->extack);
3314 err = ops->eswitch_mode_set(devlink, mode, info->extack);
3319 if (info->attrs[DEVLINK_ATTR_ESWITCH_INLINE_MODE]) {
3320 if (!ops->eswitch_inline_mode_set)
3322 inline_mode = nla_get_u8(
3323 info->attrs[DEVLINK_ATTR_ESWITCH_INLINE_MODE]);
3324 err = ops->eswitch_inline_mode_set(devlink, inline_mode,
3330 if (info->attrs[DEVLINK_ATTR_ESWITCH_ENCAP_MODE]) {
3331 if (!ops->eswitch_encap_mode_set)
3333 encap_mode = nla_get_u8(info->attrs[DEVLINK_ATTR_ESWITCH_ENCAP_MODE]);
3334 err = ops->eswitch_encap_mode_set(devlink, encap_mode,
3343 int devlink_dpipe_match_put(struct sk_buff *skb,
3344 struct devlink_dpipe_match *match)
3346 struct devlink_dpipe_header *header = match->header;
3347 struct devlink_dpipe_field *field = &header->fields[match->field_id];
3348 struct nlattr *match_attr;
3350 match_attr = nla_nest_start_noflag(skb, DEVLINK_ATTR_DPIPE_MATCH);
3354 if (nla_put_u32(skb, DEVLINK_ATTR_DPIPE_MATCH_TYPE, match->type) ||
3355 nla_put_u32(skb, DEVLINK_ATTR_DPIPE_HEADER_INDEX, match->header_index) ||
3356 nla_put_u32(skb, DEVLINK_ATTR_DPIPE_HEADER_ID, header->id) ||
3357 nla_put_u32(skb, DEVLINK_ATTR_DPIPE_FIELD_ID, field->id) ||
3358 nla_put_u8(skb, DEVLINK_ATTR_DPIPE_HEADER_GLOBAL, header->global))
3359 goto nla_put_failure;
3361 nla_nest_end(skb, match_attr);
3365 nla_nest_cancel(skb, match_attr);
3368 EXPORT_SYMBOL_GPL(devlink_dpipe_match_put);
3370 static int devlink_dpipe_matches_put(struct devlink_dpipe_table *table,
3371 struct sk_buff *skb)
3373 struct nlattr *matches_attr;
3375 matches_attr = nla_nest_start_noflag(skb,
3376 DEVLINK_ATTR_DPIPE_TABLE_MATCHES);
3380 if (table->table_ops->matches_dump(table->priv, skb))
3381 goto nla_put_failure;
3383 nla_nest_end(skb, matches_attr);
3387 nla_nest_cancel(skb, matches_attr);
3391 int devlink_dpipe_action_put(struct sk_buff *skb,
3392 struct devlink_dpipe_action *action)
3394 struct devlink_dpipe_header *header = action->header;
3395 struct devlink_dpipe_field *field = &header->fields[action->field_id];
3396 struct nlattr *action_attr;
3398 action_attr = nla_nest_start_noflag(skb, DEVLINK_ATTR_DPIPE_ACTION);
3402 if (nla_put_u32(skb, DEVLINK_ATTR_DPIPE_ACTION_TYPE, action->type) ||
3403 nla_put_u32(skb, DEVLINK_ATTR_DPIPE_HEADER_INDEX, action->header_index) ||
3404 nla_put_u32(skb, DEVLINK_ATTR_DPIPE_HEADER_ID, header->id) ||
3405 nla_put_u32(skb, DEVLINK_ATTR_DPIPE_FIELD_ID, field->id) ||
3406 nla_put_u8(skb, DEVLINK_ATTR_DPIPE_HEADER_GLOBAL, header->global))
3407 goto nla_put_failure;
3409 nla_nest_end(skb, action_attr);
3413 nla_nest_cancel(skb, action_attr);
3416 EXPORT_SYMBOL_GPL(devlink_dpipe_action_put);
3418 static int devlink_dpipe_actions_put(struct devlink_dpipe_table *table,
3419 struct sk_buff *skb)
3421 struct nlattr *actions_attr;
3423 actions_attr = nla_nest_start_noflag(skb,
3424 DEVLINK_ATTR_DPIPE_TABLE_ACTIONS);
3428 if (table->table_ops->actions_dump(table->priv, skb))
3429 goto nla_put_failure;
3431 nla_nest_end(skb, actions_attr);
3435 nla_nest_cancel(skb, actions_attr);
3439 static int devlink_dpipe_table_put(struct sk_buff *skb,
3440 struct devlink_dpipe_table *table)
3442 struct nlattr *table_attr;
3445 table_size = table->table_ops->size_get(table->priv);
3446 table_attr = nla_nest_start_noflag(skb, DEVLINK_ATTR_DPIPE_TABLE);
3450 if (nla_put_string(skb, DEVLINK_ATTR_DPIPE_TABLE_NAME, table->name) ||
3451 nla_put_u64_64bit(skb, DEVLINK_ATTR_DPIPE_TABLE_SIZE, table_size,
3453 goto nla_put_failure;
3454 if (nla_put_u8(skb, DEVLINK_ATTR_DPIPE_TABLE_COUNTERS_ENABLED,
3455 table->counters_enabled))
3456 goto nla_put_failure;
3458 if (table->resource_valid) {
3459 if (nla_put_u64_64bit(skb, DEVLINK_ATTR_DPIPE_TABLE_RESOURCE_ID,
3460 table->resource_id, DEVLINK_ATTR_PAD) ||
3461 nla_put_u64_64bit(skb, DEVLINK_ATTR_DPIPE_TABLE_RESOURCE_UNITS,
3462 table->resource_units, DEVLINK_ATTR_PAD))
3463 goto nla_put_failure;
3465 if (devlink_dpipe_matches_put(table, skb))
3466 goto nla_put_failure;
3468 if (devlink_dpipe_actions_put(table, skb))
3469 goto nla_put_failure;
3471 nla_nest_end(skb, table_attr);
3475 nla_nest_cancel(skb, table_attr);
3479 static int devlink_dpipe_send_and_alloc_skb(struct sk_buff **pskb,
3480 struct genl_info *info)
3485 err = genlmsg_reply(*pskb, info);
3489 *pskb = genlmsg_new(GENLMSG_DEFAULT_SIZE, GFP_KERNEL);
3495 static int devlink_dpipe_tables_fill(struct genl_info *info,
3496 enum devlink_command cmd, int flags,
3497 struct list_head *dpipe_tables,
3498 const char *table_name)
3500 struct devlink *devlink = info->user_ptr[0];
3501 struct devlink_dpipe_table *table;
3502 struct nlattr *tables_attr;
3503 struct sk_buff *skb = NULL;
3504 struct nlmsghdr *nlh;
3510 table = list_first_entry(dpipe_tables,
3511 struct devlink_dpipe_table, list);
3513 err = devlink_dpipe_send_and_alloc_skb(&skb, info);
3517 hdr = genlmsg_put(skb, info->snd_portid, info->snd_seq,
3518 &devlink_nl_family, NLM_F_MULTI, cmd);
3524 if (devlink_nl_put_handle(skb, devlink))
3525 goto nla_put_failure;
3526 tables_attr = nla_nest_start_noflag(skb, DEVLINK_ATTR_DPIPE_TABLES);
3528 goto nla_put_failure;
3532 list_for_each_entry_from(table, dpipe_tables, list) {
3534 err = devlink_dpipe_table_put(skb, table);
3542 if (!strcmp(table->name, table_name)) {
3543 err = devlink_dpipe_table_put(skb, table);
3551 nla_nest_end(skb, tables_attr);
3552 genlmsg_end(skb, hdr);
3557 nlh = nlmsg_put(skb, info->snd_portid, info->snd_seq,
3558 NLMSG_DONE, 0, flags | NLM_F_MULTI);
3560 err = devlink_dpipe_send_and_alloc_skb(&skb, info);
3566 return genlmsg_reply(skb, info);
3575 static int devlink_nl_cmd_dpipe_table_get(struct sk_buff *skb,
3576 struct genl_info *info)
3578 struct devlink *devlink = info->user_ptr[0];
3579 const char *table_name = NULL;
3581 if (info->attrs[DEVLINK_ATTR_DPIPE_TABLE_NAME])
3582 table_name = nla_data(info->attrs[DEVLINK_ATTR_DPIPE_TABLE_NAME]);
3584 return devlink_dpipe_tables_fill(info, DEVLINK_CMD_DPIPE_TABLE_GET, 0,
3585 &devlink->dpipe_table_list,
3589 static int devlink_dpipe_value_put(struct sk_buff *skb,
3590 struct devlink_dpipe_value *value)
3592 if (nla_put(skb, DEVLINK_ATTR_DPIPE_VALUE,
3593 value->value_size, value->value))
3596 if (nla_put(skb, DEVLINK_ATTR_DPIPE_VALUE_MASK,
3597 value->value_size, value->mask))
3599 if (value->mapping_valid)
3600 if (nla_put_u32(skb, DEVLINK_ATTR_DPIPE_VALUE_MAPPING,
3601 value->mapping_value))
3606 static int devlink_dpipe_action_value_put(struct sk_buff *skb,
3607 struct devlink_dpipe_value *value)
3611 if (devlink_dpipe_action_put(skb, value->action))
3613 if (devlink_dpipe_value_put(skb, value))
3618 static int devlink_dpipe_action_values_put(struct sk_buff *skb,
3619 struct devlink_dpipe_value *values,
3620 unsigned int values_count)
3622 struct nlattr *action_attr;
3626 for (i = 0; i < values_count; i++) {
3627 action_attr = nla_nest_start_noflag(skb,
3628 DEVLINK_ATTR_DPIPE_ACTION_VALUE);
3631 err = devlink_dpipe_action_value_put(skb, &values[i]);
3633 goto err_action_value_put;
3634 nla_nest_end(skb, action_attr);
3638 err_action_value_put:
3639 nla_nest_cancel(skb, action_attr);
3643 static int devlink_dpipe_match_value_put(struct sk_buff *skb,
3644 struct devlink_dpipe_value *value)
3648 if (devlink_dpipe_match_put(skb, value->match))
3650 if (devlink_dpipe_value_put(skb, value))
3655 static int devlink_dpipe_match_values_put(struct sk_buff *skb,
3656 struct devlink_dpipe_value *values,
3657 unsigned int values_count)
3659 struct nlattr *match_attr;
3663 for (i = 0; i < values_count; i++) {
3664 match_attr = nla_nest_start_noflag(skb,
3665 DEVLINK_ATTR_DPIPE_MATCH_VALUE);
3668 err = devlink_dpipe_match_value_put(skb, &values[i]);
3670 goto err_match_value_put;
3671 nla_nest_end(skb, match_attr);
3675 err_match_value_put:
3676 nla_nest_cancel(skb, match_attr);
3680 static int devlink_dpipe_entry_put(struct sk_buff *skb,
3681 struct devlink_dpipe_entry *entry)
3683 struct nlattr *entry_attr, *matches_attr, *actions_attr;
3686 entry_attr = nla_nest_start_noflag(skb, DEVLINK_ATTR_DPIPE_ENTRY);
3690 if (nla_put_u64_64bit(skb, DEVLINK_ATTR_DPIPE_ENTRY_INDEX, entry->index,
3692 goto nla_put_failure;
3693 if (entry->counter_valid)
3694 if (nla_put_u64_64bit(skb, DEVLINK_ATTR_DPIPE_ENTRY_COUNTER,
3695 entry->counter, DEVLINK_ATTR_PAD))
3696 goto nla_put_failure;
3698 matches_attr = nla_nest_start_noflag(skb,
3699 DEVLINK_ATTR_DPIPE_ENTRY_MATCH_VALUES);
3701 goto nla_put_failure;
3703 err = devlink_dpipe_match_values_put(skb, entry->match_values,
3704 entry->match_values_count);
3706 nla_nest_cancel(skb, matches_attr);
3707 goto err_match_values_put;
3709 nla_nest_end(skb, matches_attr);
3711 actions_attr = nla_nest_start_noflag(skb,
3712 DEVLINK_ATTR_DPIPE_ENTRY_ACTION_VALUES);
3714 goto nla_put_failure;
3716 err = devlink_dpipe_action_values_put(skb, entry->action_values,
3717 entry->action_values_count);
3719 nla_nest_cancel(skb, actions_attr);
3720 goto err_action_values_put;
3722 nla_nest_end(skb, actions_attr);
3724 nla_nest_end(skb, entry_attr);
3729 err_match_values_put:
3730 err_action_values_put:
3731 nla_nest_cancel(skb, entry_attr);
3735 static struct devlink_dpipe_table *
3736 devlink_dpipe_table_find(struct list_head *dpipe_tables,
3737 const char *table_name, struct devlink *devlink)
3739 struct devlink_dpipe_table *table;
3740 list_for_each_entry_rcu(table, dpipe_tables, list,
3741 lockdep_is_held(&devlink->lock)) {
3742 if (!strcmp(table->name, table_name))
3748 int devlink_dpipe_entry_ctx_prepare(struct devlink_dpipe_dump_ctx *dump_ctx)
3750 struct devlink *devlink;
3753 err = devlink_dpipe_send_and_alloc_skb(&dump_ctx->skb,
3758 dump_ctx->hdr = genlmsg_put(dump_ctx->skb,
3759 dump_ctx->info->snd_portid,
3760 dump_ctx->info->snd_seq,
3761 &devlink_nl_family, NLM_F_MULTI,
3764 goto nla_put_failure;
3766 devlink = dump_ctx->info->user_ptr[0];
3767 if (devlink_nl_put_handle(dump_ctx->skb, devlink))
3768 goto nla_put_failure;
3769 dump_ctx->nest = nla_nest_start_noflag(dump_ctx->skb,
3770 DEVLINK_ATTR_DPIPE_ENTRIES);
3771 if (!dump_ctx->nest)
3772 goto nla_put_failure;
3776 nlmsg_free(dump_ctx->skb);
3779 EXPORT_SYMBOL_GPL(devlink_dpipe_entry_ctx_prepare);
3781 int devlink_dpipe_entry_ctx_append(struct devlink_dpipe_dump_ctx *dump_ctx,
3782 struct devlink_dpipe_entry *entry)
3784 return devlink_dpipe_entry_put(dump_ctx->skb, entry);
3786 EXPORT_SYMBOL_GPL(devlink_dpipe_entry_ctx_append);
3788 int devlink_dpipe_entry_ctx_close(struct devlink_dpipe_dump_ctx *dump_ctx)
3790 nla_nest_end(dump_ctx->skb, dump_ctx->nest);
3791 genlmsg_end(dump_ctx->skb, dump_ctx->hdr);
3794 EXPORT_SYMBOL_GPL(devlink_dpipe_entry_ctx_close);
3796 void devlink_dpipe_entry_clear(struct devlink_dpipe_entry *entry)
3799 unsigned int value_count, value_index;
3800 struct devlink_dpipe_value *value;
3802 value = entry->action_values;
3803 value_count = entry->action_values_count;
3804 for (value_index = 0; value_index < value_count; value_index++) {
3805 kfree(value[value_index].value);
3806 kfree(value[value_index].mask);
3809 value = entry->match_values;
3810 value_count = entry->match_values_count;
3811 for (value_index = 0; value_index < value_count; value_index++) {
3812 kfree(value[value_index].value);
3813 kfree(value[value_index].mask);
3816 EXPORT_SYMBOL_GPL(devlink_dpipe_entry_clear);
3818 static int devlink_dpipe_entries_fill(struct genl_info *info,
3819 enum devlink_command cmd, int flags,
3820 struct devlink_dpipe_table *table)
3822 struct devlink_dpipe_dump_ctx dump_ctx;
3823 struct nlmsghdr *nlh;
3826 dump_ctx.skb = NULL;
3828 dump_ctx.info = info;
3830 err = table->table_ops->entries_dump(table->priv,
3831 table->counters_enabled,
3837 nlh = nlmsg_put(dump_ctx.skb, info->snd_portid, info->snd_seq,
3838 NLMSG_DONE, 0, flags | NLM_F_MULTI);
3840 err = devlink_dpipe_send_and_alloc_skb(&dump_ctx.skb, info);
3845 return genlmsg_reply(dump_ctx.skb, info);
3848 static int devlink_nl_cmd_dpipe_entries_get(struct sk_buff *skb,
3849 struct genl_info *info)
3851 struct devlink *devlink = info->user_ptr[0];
3852 struct devlink_dpipe_table *table;
3853 const char *table_name;
3855 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_DPIPE_TABLE_NAME))
3858 table_name = nla_data(info->attrs[DEVLINK_ATTR_DPIPE_TABLE_NAME]);
3859 table = devlink_dpipe_table_find(&devlink->dpipe_table_list,
3860 table_name, devlink);
3864 if (!table->table_ops->entries_dump)
3867 return devlink_dpipe_entries_fill(info, DEVLINK_CMD_DPIPE_ENTRIES_GET,
3871 static int devlink_dpipe_fields_put(struct sk_buff *skb,
3872 const struct devlink_dpipe_header *header)
3874 struct devlink_dpipe_field *field;
3875 struct nlattr *field_attr;
3878 for (i = 0; i < header->fields_count; i++) {
3879 field = &header->fields[i];
3880 field_attr = nla_nest_start_noflag(skb,
3881 DEVLINK_ATTR_DPIPE_FIELD);
3884 if (nla_put_string(skb, DEVLINK_ATTR_DPIPE_FIELD_NAME, field->name) ||
3885 nla_put_u32(skb, DEVLINK_ATTR_DPIPE_FIELD_ID, field->id) ||
3886 nla_put_u32(skb, DEVLINK_ATTR_DPIPE_FIELD_BITWIDTH, field->bitwidth) ||
3887 nla_put_u32(skb, DEVLINK_ATTR_DPIPE_FIELD_MAPPING_TYPE, field->mapping_type))
3888 goto nla_put_failure;
3889 nla_nest_end(skb, field_attr);
3894 nla_nest_cancel(skb, field_attr);
3898 static int devlink_dpipe_header_put(struct sk_buff *skb,
3899 struct devlink_dpipe_header *header)
3901 struct nlattr *fields_attr, *header_attr;
3904 header_attr = nla_nest_start_noflag(skb, DEVLINK_ATTR_DPIPE_HEADER);
3908 if (nla_put_string(skb, DEVLINK_ATTR_DPIPE_HEADER_NAME, header->name) ||
3909 nla_put_u32(skb, DEVLINK_ATTR_DPIPE_HEADER_ID, header->id) ||
3910 nla_put_u8(skb, DEVLINK_ATTR_DPIPE_HEADER_GLOBAL, header->global))
3911 goto nla_put_failure;
3913 fields_attr = nla_nest_start_noflag(skb,
3914 DEVLINK_ATTR_DPIPE_HEADER_FIELDS);
3916 goto nla_put_failure;
3918 err = devlink_dpipe_fields_put(skb, header);
3920 nla_nest_cancel(skb, fields_attr);
3921 goto nla_put_failure;
3923 nla_nest_end(skb, fields_attr);
3924 nla_nest_end(skb, header_attr);
3929 nla_nest_cancel(skb, header_attr);
3933 static int devlink_dpipe_headers_fill(struct genl_info *info,
3934 enum devlink_command cmd, int flags,
3935 struct devlink_dpipe_headers *
3938 struct devlink *devlink = info->user_ptr[0];
3939 struct nlattr *headers_attr;
3940 struct sk_buff *skb = NULL;
3941 struct nlmsghdr *nlh;
3948 err = devlink_dpipe_send_and_alloc_skb(&skb, info);
3952 hdr = genlmsg_put(skb, info->snd_portid, info->snd_seq,
3953 &devlink_nl_family, NLM_F_MULTI, cmd);
3959 if (devlink_nl_put_handle(skb, devlink))
3960 goto nla_put_failure;
3961 headers_attr = nla_nest_start_noflag(skb, DEVLINK_ATTR_DPIPE_HEADERS);
3963 goto nla_put_failure;
3966 for (; i < dpipe_headers->headers_count; i++) {
3967 err = devlink_dpipe_header_put(skb, dpipe_headers->headers[i]);
3975 nla_nest_end(skb, headers_attr);
3976 genlmsg_end(skb, hdr);
3977 if (i != dpipe_headers->headers_count)
3981 nlh = nlmsg_put(skb, info->snd_portid, info->snd_seq,
3982 NLMSG_DONE, 0, flags | NLM_F_MULTI);
3984 err = devlink_dpipe_send_and_alloc_skb(&skb, info);
3989 return genlmsg_reply(skb, info);
3998 static int devlink_nl_cmd_dpipe_headers_get(struct sk_buff *skb,
3999 struct genl_info *info)
4001 struct devlink *devlink = info->user_ptr[0];
4003 if (!devlink->dpipe_headers)
4005 return devlink_dpipe_headers_fill(info, DEVLINK_CMD_DPIPE_HEADERS_GET,
4006 0, devlink->dpipe_headers);
4009 static int devlink_dpipe_table_counters_set(struct devlink *devlink,
4010 const char *table_name,
4013 struct devlink_dpipe_table *table;
4015 table = devlink_dpipe_table_find(&devlink->dpipe_table_list,
4016 table_name, devlink);
4020 if (table->counter_control_extern)
4023 if (!(table->counters_enabled ^ enable))
4026 table->counters_enabled = enable;
4027 if (table->table_ops->counters_set_update)
4028 table->table_ops->counters_set_update(table->priv, enable);
4032 static int devlink_nl_cmd_dpipe_table_counters_set(struct sk_buff *skb,
4033 struct genl_info *info)
4035 struct devlink *devlink = info->user_ptr[0];
4036 const char *table_name;
4037 bool counters_enable;
4039 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_DPIPE_TABLE_NAME) ||
4040 GENL_REQ_ATTR_CHECK(info,
4041 DEVLINK_ATTR_DPIPE_TABLE_COUNTERS_ENABLED))
4044 table_name = nla_data(info->attrs[DEVLINK_ATTR_DPIPE_TABLE_NAME]);
4045 counters_enable = !!nla_get_u8(info->attrs[DEVLINK_ATTR_DPIPE_TABLE_COUNTERS_ENABLED]);
4047 return devlink_dpipe_table_counters_set(devlink, table_name,
4051 static struct devlink_resource *
4052 devlink_resource_find(struct devlink *devlink,
4053 struct devlink_resource *resource, u64 resource_id)
4055 struct list_head *resource_list;
4058 resource_list = &resource->resource_list;
4060 resource_list = &devlink->resource_list;
4062 list_for_each_entry(resource, resource_list, list) {
4063 struct devlink_resource *child_resource;
4065 if (resource->id == resource_id)
4068 child_resource = devlink_resource_find(devlink, resource,
4071 return child_resource;
4077 devlink_resource_validate_children(struct devlink_resource *resource)
4079 struct devlink_resource *child_resource;
4080 bool size_valid = true;
4083 if (list_empty(&resource->resource_list))
4086 list_for_each_entry(child_resource, &resource->resource_list, list)
4087 parts_size += child_resource->size_new;
4089 if (parts_size > resource->size_new)
4092 resource->size_valid = size_valid;
4096 devlink_resource_validate_size(struct devlink_resource *resource, u64 size,
4097 struct netlink_ext_ack *extack)
4102 if (size > resource->size_params.size_max) {
4103 NL_SET_ERR_MSG_MOD(extack, "Size larger than maximum");
4107 if (size < resource->size_params.size_min) {
4108 NL_SET_ERR_MSG_MOD(extack, "Size smaller than minimum");
4112 div64_u64_rem(size, resource->size_params.size_granularity, &reminder);
4114 NL_SET_ERR_MSG_MOD(extack, "Wrong granularity");
4121 static int devlink_nl_cmd_resource_set(struct sk_buff *skb,
4122 struct genl_info *info)
4124 struct devlink *devlink = info->user_ptr[0];
4125 struct devlink_resource *resource;
4130 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_RESOURCE_ID) ||
4131 GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_RESOURCE_SIZE))
4133 resource_id = nla_get_u64(info->attrs[DEVLINK_ATTR_RESOURCE_ID]);
4135 resource = devlink_resource_find(devlink, NULL, resource_id);
4139 size = nla_get_u64(info->attrs[DEVLINK_ATTR_RESOURCE_SIZE]);
4140 err = devlink_resource_validate_size(resource, size, info->extack);
4144 resource->size_new = size;
4145 devlink_resource_validate_children(resource);
4146 if (resource->parent)
4147 devlink_resource_validate_children(resource->parent);
4152 devlink_resource_size_params_put(struct devlink_resource *resource,
4153 struct sk_buff *skb)
4155 struct devlink_resource_size_params *size_params;
4157 size_params = &resource->size_params;
4158 if (nla_put_u64_64bit(skb, DEVLINK_ATTR_RESOURCE_SIZE_GRAN,
4159 size_params->size_granularity, DEVLINK_ATTR_PAD) ||
4160 nla_put_u64_64bit(skb, DEVLINK_ATTR_RESOURCE_SIZE_MAX,
4161 size_params->size_max, DEVLINK_ATTR_PAD) ||
4162 nla_put_u64_64bit(skb, DEVLINK_ATTR_RESOURCE_SIZE_MIN,
4163 size_params->size_min, DEVLINK_ATTR_PAD) ||
4164 nla_put_u8(skb, DEVLINK_ATTR_RESOURCE_UNIT, size_params->unit))
4169 static int devlink_resource_occ_put(struct devlink_resource *resource,
4170 struct sk_buff *skb)
4172 if (!resource->occ_get)
4174 return nla_put_u64_64bit(skb, DEVLINK_ATTR_RESOURCE_OCC,
4175 resource->occ_get(resource->occ_get_priv),
4179 static int devlink_resource_put(struct devlink *devlink, struct sk_buff *skb,
4180 struct devlink_resource *resource)
4182 struct devlink_resource *child_resource;
4183 struct nlattr *child_resource_attr;
4184 struct nlattr *resource_attr;
4186 resource_attr = nla_nest_start_noflag(skb, DEVLINK_ATTR_RESOURCE);
4190 if (nla_put_string(skb, DEVLINK_ATTR_RESOURCE_NAME, resource->name) ||
4191 nla_put_u64_64bit(skb, DEVLINK_ATTR_RESOURCE_SIZE, resource->size,
4192 DEVLINK_ATTR_PAD) ||
4193 nla_put_u64_64bit(skb, DEVLINK_ATTR_RESOURCE_ID, resource->id,
4195 goto nla_put_failure;
4196 if (resource->size != resource->size_new)
4197 nla_put_u64_64bit(skb, DEVLINK_ATTR_RESOURCE_SIZE_NEW,
4198 resource->size_new, DEVLINK_ATTR_PAD);
4199 if (devlink_resource_occ_put(resource, skb))
4200 goto nla_put_failure;
4201 if (devlink_resource_size_params_put(resource, skb))
4202 goto nla_put_failure;
4203 if (list_empty(&resource->resource_list))
4206 if (nla_put_u8(skb, DEVLINK_ATTR_RESOURCE_SIZE_VALID,
4207 resource->size_valid))
4208 goto nla_put_failure;
4210 child_resource_attr = nla_nest_start_noflag(skb,
4211 DEVLINK_ATTR_RESOURCE_LIST);
4212 if (!child_resource_attr)
4213 goto nla_put_failure;
4215 list_for_each_entry(child_resource, &resource->resource_list, list) {
4216 if (devlink_resource_put(devlink, skb, child_resource))
4217 goto resource_put_failure;
4220 nla_nest_end(skb, child_resource_attr);
4222 nla_nest_end(skb, resource_attr);
4225 resource_put_failure:
4226 nla_nest_cancel(skb, child_resource_attr);
4228 nla_nest_cancel(skb, resource_attr);
4232 static int devlink_resource_fill(struct genl_info *info,
4233 enum devlink_command cmd, int flags)
4235 struct devlink *devlink = info->user_ptr[0];
4236 struct devlink_resource *resource;
4237 struct nlattr *resources_attr;
4238 struct sk_buff *skb = NULL;
4239 struct nlmsghdr *nlh;
4245 resource = list_first_entry(&devlink->resource_list,
4246 struct devlink_resource, list);
4248 err = devlink_dpipe_send_and_alloc_skb(&skb, info);
4252 hdr = genlmsg_put(skb, info->snd_portid, info->snd_seq,
4253 &devlink_nl_family, NLM_F_MULTI, cmd);
4259 if (devlink_nl_put_handle(skb, devlink))
4260 goto nla_put_failure;
4262 resources_attr = nla_nest_start_noflag(skb,
4263 DEVLINK_ATTR_RESOURCE_LIST);
4264 if (!resources_attr)
4265 goto nla_put_failure;
4269 list_for_each_entry_from(resource, &devlink->resource_list, list) {
4270 err = devlink_resource_put(devlink, skb, resource);
4273 goto err_resource_put;
4279 nla_nest_end(skb, resources_attr);
4280 genlmsg_end(skb, hdr);
4284 nlh = nlmsg_put(skb, info->snd_portid, info->snd_seq,
4285 NLMSG_DONE, 0, flags | NLM_F_MULTI);
4287 err = devlink_dpipe_send_and_alloc_skb(&skb, info);
4292 return genlmsg_reply(skb, info);
4301 static int devlink_nl_cmd_resource_dump(struct sk_buff *skb,
4302 struct genl_info *info)
4304 struct devlink *devlink = info->user_ptr[0];
4306 if (list_empty(&devlink->resource_list))
4309 return devlink_resource_fill(info, DEVLINK_CMD_RESOURCE_DUMP, 0);
4313 devlink_resources_validate(struct devlink *devlink,
4314 struct devlink_resource *resource,
4315 struct genl_info *info)
4317 struct list_head *resource_list;
4321 resource_list = &resource->resource_list;
4323 resource_list = &devlink->resource_list;
4325 list_for_each_entry(resource, resource_list, list) {
4326 if (!resource->size_valid)
4328 err = devlink_resources_validate(devlink, resource, info);
4335 static struct net *devlink_netns_get(struct sk_buff *skb,
4336 struct genl_info *info)
4338 struct nlattr *netns_pid_attr = info->attrs[DEVLINK_ATTR_NETNS_PID];
4339 struct nlattr *netns_fd_attr = info->attrs[DEVLINK_ATTR_NETNS_FD];
4340 struct nlattr *netns_id_attr = info->attrs[DEVLINK_ATTR_NETNS_ID];
4343 if (!!netns_pid_attr + !!netns_fd_attr + !!netns_id_attr > 1) {
4344 NL_SET_ERR_MSG_MOD(info->extack, "multiple netns identifying attributes specified");
4345 return ERR_PTR(-EINVAL);
4348 if (netns_pid_attr) {
4349 net = get_net_ns_by_pid(nla_get_u32(netns_pid_attr));
4350 } else if (netns_fd_attr) {
4351 net = get_net_ns_by_fd(nla_get_u32(netns_fd_attr));
4352 } else if (netns_id_attr) {
4353 net = get_net_ns_by_id(sock_net(skb->sk),
4354 nla_get_u32(netns_id_attr));
4356 net = ERR_PTR(-EINVAL);
4359 net = ERR_PTR(-EINVAL);
4362 NL_SET_ERR_MSG_MOD(info->extack, "Unknown network namespace");
4363 return ERR_PTR(-EINVAL);
4365 if (!netlink_ns_capable(skb, net->user_ns, CAP_NET_ADMIN)) {
4367 return ERR_PTR(-EPERM);
4372 static void devlink_param_notify(struct devlink *devlink,
4373 unsigned int port_index,
4374 struct devlink_param_item *param_item,
4375 enum devlink_command cmd);
4377 static void devlink_ns_change_notify(struct devlink *devlink,
4378 struct net *dest_net, struct net *curr_net,
4381 struct devlink_param_item *param_item;
4382 enum devlink_command cmd;
4384 /* Userspace needs to be notified about devlink objects
4385 * removed from original and entering new network namespace.
4386 * The rest of the devlink objects are re-created during
4387 * reload process so the notifications are generated separatelly.
4390 if (!dest_net || net_eq(dest_net, curr_net))
4394 devlink_notify(devlink, DEVLINK_CMD_NEW);
4396 cmd = new ? DEVLINK_CMD_PARAM_NEW : DEVLINK_CMD_PARAM_DEL;
4397 list_for_each_entry(param_item, &devlink->param_list, list)
4398 devlink_param_notify(devlink, 0, param_item, cmd);
4401 devlink_notify(devlink, DEVLINK_CMD_DEL);
4404 static bool devlink_reload_supported(const struct devlink_ops *ops)
4406 return ops->reload_down && ops->reload_up;
4409 static void devlink_reload_failed_set(struct devlink *devlink,
4412 if (devlink->reload_failed == reload_failed)
4414 devlink->reload_failed = reload_failed;
4415 devlink_notify(devlink, DEVLINK_CMD_NEW);
4418 bool devlink_is_reload_failed(const struct devlink *devlink)
4420 return devlink->reload_failed;
4422 EXPORT_SYMBOL_GPL(devlink_is_reload_failed);
4425 __devlink_reload_stats_update(struct devlink *devlink, u32 *reload_stats,
4426 enum devlink_reload_limit limit, u32 actions_performed)
4428 unsigned long actions = actions_performed;
4432 for_each_set_bit(action, &actions, __DEVLINK_RELOAD_ACTION_MAX) {
4433 stat_idx = limit * __DEVLINK_RELOAD_ACTION_MAX + action;
4434 reload_stats[stat_idx]++;
4436 devlink_notify(devlink, DEVLINK_CMD_NEW);
4440 devlink_reload_stats_update(struct devlink *devlink, enum devlink_reload_limit limit,
4441 u32 actions_performed)
4443 __devlink_reload_stats_update(devlink, devlink->stats.reload_stats, limit,
4448 * devlink_remote_reload_actions_performed - Update devlink on reload actions
4449 * performed which are not a direct result of devlink reload call.
4451 * This should be called by a driver after performing reload actions in case it was not
4452 * a result of devlink reload call. For example fw_activate was performed as a result
4453 * of devlink reload triggered fw_activate on another host.
4454 * The motivation for this function is to keep data on reload actions performed on this
4455 * function whether it was done due to direct devlink reload call or not.
4458 * @limit: reload limit
4459 * @actions_performed: bitmask of actions performed
4461 void devlink_remote_reload_actions_performed(struct devlink *devlink,
4462 enum devlink_reload_limit limit,
4463 u32 actions_performed)
4465 if (WARN_ON(!actions_performed ||
4466 actions_performed & BIT(DEVLINK_RELOAD_ACTION_UNSPEC) ||
4467 actions_performed >= BIT(__DEVLINK_RELOAD_ACTION_MAX) ||
4468 limit > DEVLINK_RELOAD_LIMIT_MAX))
4471 __devlink_reload_stats_update(devlink, devlink->stats.remote_reload_stats, limit,
4474 EXPORT_SYMBOL_GPL(devlink_remote_reload_actions_performed);
4476 static int devlink_reload(struct devlink *devlink, struct net *dest_net,
4477 enum devlink_reload_action action, enum devlink_reload_limit limit,
4478 u32 *actions_performed, struct netlink_ext_ack *extack)
4480 u32 remote_reload_stats[DEVLINK_RELOAD_STATS_ARRAY_SIZE];
4481 struct net *curr_net;
4484 memcpy(remote_reload_stats, devlink->stats.remote_reload_stats,
4485 sizeof(remote_reload_stats));
4487 curr_net = devlink_net(devlink);
4488 devlink_ns_change_notify(devlink, dest_net, curr_net, false);
4489 err = devlink->ops->reload_down(devlink, !!dest_net, action, limit, extack);
4493 if (dest_net && !net_eq(dest_net, curr_net))
4494 write_pnet(&devlink->_net, dest_net);
4496 err = devlink->ops->reload_up(devlink, action, limit, actions_performed, extack);
4497 devlink_reload_failed_set(devlink, !!err);
4501 devlink_ns_change_notify(devlink, dest_net, curr_net, true);
4502 WARN_ON(!(*actions_performed & BIT(action)));
4503 /* Catch driver on updating the remote action within devlink reload */
4504 WARN_ON(memcmp(remote_reload_stats, devlink->stats.remote_reload_stats,
4505 sizeof(remote_reload_stats)));
4506 devlink_reload_stats_update(devlink, limit, *actions_performed);
4511 devlink_nl_reload_actions_performed_snd(struct devlink *devlink, u32 actions_performed,
4512 enum devlink_command cmd, struct genl_info *info)
4514 struct sk_buff *msg;
4517 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
4521 hdr = genlmsg_put(msg, info->snd_portid, info->snd_seq, &devlink_nl_family, 0, cmd);
4525 if (devlink_nl_put_handle(msg, devlink))
4526 goto nla_put_failure;
4528 if (nla_put_bitfield32(msg, DEVLINK_ATTR_RELOAD_ACTIONS_PERFORMED, actions_performed,
4530 goto nla_put_failure;
4531 genlmsg_end(msg, hdr);
4533 return genlmsg_reply(msg, info);
4536 genlmsg_cancel(msg, hdr);
4542 static int devlink_nl_cmd_reload(struct sk_buff *skb, struct genl_info *info)
4544 struct devlink *devlink = info->user_ptr[0];
4545 enum devlink_reload_action action;
4546 enum devlink_reload_limit limit;
4547 struct net *dest_net = NULL;
4548 u32 actions_performed;
4551 if (!(devlink->features & DEVLINK_F_RELOAD))
4554 err = devlink_resources_validate(devlink, NULL, info);
4556 NL_SET_ERR_MSG_MOD(info->extack, "resources size validation failed");
4560 if (info->attrs[DEVLINK_ATTR_RELOAD_ACTION])
4561 action = nla_get_u8(info->attrs[DEVLINK_ATTR_RELOAD_ACTION]);
4563 action = DEVLINK_RELOAD_ACTION_DRIVER_REINIT;
4565 if (!devlink_reload_action_is_supported(devlink, action)) {
4566 NL_SET_ERR_MSG_MOD(info->extack,
4567 "Requested reload action is not supported by the driver");
4571 limit = DEVLINK_RELOAD_LIMIT_UNSPEC;
4572 if (info->attrs[DEVLINK_ATTR_RELOAD_LIMITS]) {
4573 struct nla_bitfield32 limits;
4574 u32 limits_selected;
4576 limits = nla_get_bitfield32(info->attrs[DEVLINK_ATTR_RELOAD_LIMITS]);
4577 limits_selected = limits.value & limits.selector;
4578 if (!limits_selected) {
4579 NL_SET_ERR_MSG_MOD(info->extack, "Invalid limit selected");
4582 for (limit = 0 ; limit <= DEVLINK_RELOAD_LIMIT_MAX ; limit++)
4583 if (limits_selected & BIT(limit))
4585 /* UAPI enables multiselection, but currently it is not used */
4586 if (limits_selected != BIT(limit)) {
4587 NL_SET_ERR_MSG_MOD(info->extack,
4588 "Multiselection of limit is not supported");
4591 if (!devlink_reload_limit_is_supported(devlink, limit)) {
4592 NL_SET_ERR_MSG_MOD(info->extack,
4593 "Requested limit is not supported by the driver");
4596 if (devlink_reload_combination_is_invalid(action, limit)) {
4597 NL_SET_ERR_MSG_MOD(info->extack,
4598 "Requested limit is invalid for this action");
4602 if (info->attrs[DEVLINK_ATTR_NETNS_PID] ||
4603 info->attrs[DEVLINK_ATTR_NETNS_FD] ||
4604 info->attrs[DEVLINK_ATTR_NETNS_ID]) {
4605 dest_net = devlink_netns_get(skb, info);
4606 if (IS_ERR(dest_net))
4607 return PTR_ERR(dest_net);
4610 err = devlink_reload(devlink, dest_net, action, limit, &actions_performed, info->extack);
4617 /* For backward compatibility generate reply only if attributes used by user */
4618 if (!info->attrs[DEVLINK_ATTR_RELOAD_ACTION] && !info->attrs[DEVLINK_ATTR_RELOAD_LIMITS])
4621 return devlink_nl_reload_actions_performed_snd(devlink, actions_performed,
4622 DEVLINK_CMD_RELOAD, info);
4625 static int devlink_nl_flash_update_fill(struct sk_buff *msg,
4626 struct devlink *devlink,
4627 enum devlink_command cmd,
4628 struct devlink_flash_notify *params)
4632 hdr = genlmsg_put(msg, 0, 0, &devlink_nl_family, 0, cmd);
4636 if (devlink_nl_put_handle(msg, devlink))
4637 goto nla_put_failure;
4639 if (cmd != DEVLINK_CMD_FLASH_UPDATE_STATUS)
4642 if (params->status_msg &&
4643 nla_put_string(msg, DEVLINK_ATTR_FLASH_UPDATE_STATUS_MSG,
4644 params->status_msg))
4645 goto nla_put_failure;
4646 if (params->component &&
4647 nla_put_string(msg, DEVLINK_ATTR_FLASH_UPDATE_COMPONENT,
4649 goto nla_put_failure;
4650 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_FLASH_UPDATE_STATUS_DONE,
4651 params->done, DEVLINK_ATTR_PAD))
4652 goto nla_put_failure;
4653 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_FLASH_UPDATE_STATUS_TOTAL,
4654 params->total, DEVLINK_ATTR_PAD))
4655 goto nla_put_failure;
4656 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_FLASH_UPDATE_STATUS_TIMEOUT,
4657 params->timeout, DEVLINK_ATTR_PAD))
4658 goto nla_put_failure;
4661 genlmsg_end(msg, hdr);
4665 genlmsg_cancel(msg, hdr);
4669 static void __devlink_flash_update_notify(struct devlink *devlink,
4670 enum devlink_command cmd,
4671 struct devlink_flash_notify *params)
4673 struct sk_buff *msg;
4676 WARN_ON(cmd != DEVLINK_CMD_FLASH_UPDATE &&
4677 cmd != DEVLINK_CMD_FLASH_UPDATE_END &&
4678 cmd != DEVLINK_CMD_FLASH_UPDATE_STATUS);
4680 if (!xa_get_mark(&devlinks, devlink->index, DEVLINK_REGISTERED))
4683 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
4687 err = devlink_nl_flash_update_fill(msg, devlink, cmd, params);
4691 genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink),
4692 msg, 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
4699 static void devlink_flash_update_begin_notify(struct devlink *devlink)
4701 struct devlink_flash_notify params = {};
4703 __devlink_flash_update_notify(devlink,
4704 DEVLINK_CMD_FLASH_UPDATE,
4708 static void devlink_flash_update_end_notify(struct devlink *devlink)
4710 struct devlink_flash_notify params = {};
4712 __devlink_flash_update_notify(devlink,
4713 DEVLINK_CMD_FLASH_UPDATE_END,
4717 void devlink_flash_update_status_notify(struct devlink *devlink,
4718 const char *status_msg,
4719 const char *component,
4721 unsigned long total)
4723 struct devlink_flash_notify params = {
4724 .status_msg = status_msg,
4725 .component = component,
4730 __devlink_flash_update_notify(devlink,
4731 DEVLINK_CMD_FLASH_UPDATE_STATUS,
4734 EXPORT_SYMBOL_GPL(devlink_flash_update_status_notify);
4736 void devlink_flash_update_timeout_notify(struct devlink *devlink,
4737 const char *status_msg,
4738 const char *component,
4739 unsigned long timeout)
4741 struct devlink_flash_notify params = {
4742 .status_msg = status_msg,
4743 .component = component,
4747 __devlink_flash_update_notify(devlink,
4748 DEVLINK_CMD_FLASH_UPDATE_STATUS,
4751 EXPORT_SYMBOL_GPL(devlink_flash_update_timeout_notify);
4753 struct devlink_info_req {
4754 struct sk_buff *msg;
4755 void (*version_cb)(const char *version_name,
4756 enum devlink_info_version_type version_type,
4757 void *version_cb_priv);
4758 void *version_cb_priv;
4761 struct devlink_flash_component_lookup_ctx {
4762 const char *lookup_name;
4763 bool lookup_name_found;
4767 devlink_flash_component_lookup_cb(const char *version_name,
4768 enum devlink_info_version_type version_type,
4769 void *version_cb_priv)
4771 struct devlink_flash_component_lookup_ctx *lookup_ctx = version_cb_priv;
4773 if (version_type != DEVLINK_INFO_VERSION_TYPE_COMPONENT ||
4774 lookup_ctx->lookup_name_found)
4777 lookup_ctx->lookup_name_found =
4778 !strcmp(lookup_ctx->lookup_name, version_name);
4781 static int devlink_flash_component_get(struct devlink *devlink,
4782 struct nlattr *nla_component,
4783 const char **p_component,
4784 struct netlink_ext_ack *extack)
4786 struct devlink_flash_component_lookup_ctx lookup_ctx = {};
4787 struct devlink_info_req req = {};
4788 const char *component;
4794 component = nla_data(nla_component);
4796 if (!devlink->ops->info_get) {
4797 NL_SET_ERR_MSG_ATTR(extack, nla_component,
4798 "component update is not supported by this device");
4802 lookup_ctx.lookup_name = component;
4803 req.version_cb = devlink_flash_component_lookup_cb;
4804 req.version_cb_priv = &lookup_ctx;
4806 ret = devlink->ops->info_get(devlink, &req, NULL);
4810 if (!lookup_ctx.lookup_name_found) {
4811 NL_SET_ERR_MSG_ATTR(extack, nla_component,
4812 "selected component is not supported by this device");
4815 *p_component = component;
4819 static int devlink_nl_cmd_flash_update(struct sk_buff *skb,
4820 struct genl_info *info)
4822 struct nlattr *nla_overwrite_mask, *nla_file_name;
4823 struct devlink_flash_update_params params = {};
4824 struct devlink *devlink = info->user_ptr[0];
4825 const char *file_name;
4826 u32 supported_params;
4829 if (!devlink->ops->flash_update)
4832 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_FLASH_UPDATE_FILE_NAME))
4835 ret = devlink_flash_component_get(devlink,
4836 info->attrs[DEVLINK_ATTR_FLASH_UPDATE_COMPONENT],
4837 ¶ms.component, info->extack);
4841 supported_params = devlink->ops->supported_flash_update_params;
4843 nla_overwrite_mask = info->attrs[DEVLINK_ATTR_FLASH_UPDATE_OVERWRITE_MASK];
4844 if (nla_overwrite_mask) {
4845 struct nla_bitfield32 sections;
4847 if (!(supported_params & DEVLINK_SUPPORT_FLASH_UPDATE_OVERWRITE_MASK)) {
4848 NL_SET_ERR_MSG_ATTR(info->extack, nla_overwrite_mask,
4849 "overwrite settings are not supported by this device");
4852 sections = nla_get_bitfield32(nla_overwrite_mask);
4853 params.overwrite_mask = sections.value & sections.selector;
4856 nla_file_name = info->attrs[DEVLINK_ATTR_FLASH_UPDATE_FILE_NAME];
4857 file_name = nla_data(nla_file_name);
4858 ret = request_firmware(¶ms.fw, file_name, devlink->dev);
4860 NL_SET_ERR_MSG_ATTR(info->extack, nla_file_name, "failed to locate the requested firmware file");
4864 devlink_flash_update_begin_notify(devlink);
4865 ret = devlink->ops->flash_update(devlink, ¶ms, info->extack);
4866 devlink_flash_update_end_notify(devlink);
4868 release_firmware(params.fw);
4874 devlink_nl_selftests_fill(struct sk_buff *msg, struct devlink *devlink,
4875 u32 portid, u32 seq, int flags,
4876 struct netlink_ext_ack *extack)
4878 struct nlattr *selftests;
4883 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags,
4884 DEVLINK_CMD_SELFTESTS_GET);
4889 if (devlink_nl_put_handle(msg, devlink))
4890 goto err_cancel_msg;
4892 selftests = nla_nest_start(msg, DEVLINK_ATTR_SELFTESTS);
4894 goto err_cancel_msg;
4896 for (i = DEVLINK_ATTR_SELFTEST_ID_UNSPEC + 1;
4897 i <= DEVLINK_ATTR_SELFTEST_ID_MAX; i++) {
4898 if (devlink->ops->selftest_check(devlink, i, extack)) {
4899 err = nla_put_flag(msg, i);
4901 goto err_cancel_msg;
4905 nla_nest_end(msg, selftests);
4906 genlmsg_end(msg, hdr);
4910 genlmsg_cancel(msg, hdr);
4914 static int devlink_nl_cmd_selftests_get_doit(struct sk_buff *skb,
4915 struct genl_info *info)
4917 struct devlink *devlink = info->user_ptr[0];
4918 struct sk_buff *msg;
4921 if (!devlink->ops->selftest_check)
4924 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
4928 err = devlink_nl_selftests_fill(msg, devlink, info->snd_portid,
4929 info->snd_seq, 0, info->extack);
4935 return genlmsg_reply(msg, info);
4938 static int devlink_nl_cmd_selftests_get_dumpit(struct sk_buff *msg,
4939 struct netlink_callback *cb)
4941 struct devlink *devlink;
4942 int start = cb->args[0];
4943 unsigned long index;
4947 devlinks_xa_for_each_registered_get(sock_net(msg->sk), index, devlink) {
4948 if (idx < start || !devlink->ops->selftest_check)
4952 err = devlink_nl_selftests_fill(msg, devlink,
4953 NETLINK_CB(cb->skb).portid,
4954 cb->nlh->nlmsg_seq, NLM_F_MULTI,
4956 devl_unlock(devlink);
4958 devlink_put(devlink);
4963 devlink_put(devlink);
4966 if (err != -EMSGSIZE)
4973 static int devlink_selftest_result_put(struct sk_buff *skb, unsigned int id,
4974 enum devlink_selftest_status test_status)
4976 struct nlattr *result_attr;
4978 result_attr = nla_nest_start(skb, DEVLINK_ATTR_SELFTEST_RESULT);
4982 if (nla_put_u32(skb, DEVLINK_ATTR_SELFTEST_RESULT_ID, id) ||
4983 nla_put_u8(skb, DEVLINK_ATTR_SELFTEST_RESULT_STATUS,
4985 goto nla_put_failure;
4987 nla_nest_end(skb, result_attr);
4991 nla_nest_cancel(skb, result_attr);
4995 static int devlink_nl_cmd_selftests_run(struct sk_buff *skb,
4996 struct genl_info *info)
4998 struct nlattr *tb[DEVLINK_ATTR_SELFTEST_ID_MAX + 1];
4999 struct devlink *devlink = info->user_ptr[0];
5000 struct nlattr *attrs, *selftests;
5001 struct sk_buff *msg;
5006 if (!devlink->ops->selftest_run || !devlink->ops->selftest_check)
5009 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_SELFTESTS))
5012 attrs = info->attrs[DEVLINK_ATTR_SELFTESTS];
5014 err = nla_parse_nested(tb, DEVLINK_ATTR_SELFTEST_ID_MAX, attrs,
5015 devlink_selftest_nl_policy, info->extack);
5019 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
5024 hdr = genlmsg_put(msg, info->snd_portid, info->snd_seq,
5025 &devlink_nl_family, 0, DEVLINK_CMD_SELFTESTS_RUN);
5029 if (devlink_nl_put_handle(msg, devlink))
5030 goto genlmsg_cancel;
5032 selftests = nla_nest_start(msg, DEVLINK_ATTR_SELFTESTS);
5034 goto genlmsg_cancel;
5036 for (i = DEVLINK_ATTR_SELFTEST_ID_UNSPEC + 1;
5037 i <= DEVLINK_ATTR_SELFTEST_ID_MAX; i++) {
5038 enum devlink_selftest_status test_status;
5040 if (nla_get_flag(tb[i])) {
5041 if (!devlink->ops->selftest_check(devlink, i,
5043 if (devlink_selftest_result_put(msg, i,
5044 DEVLINK_SELFTEST_STATUS_SKIP))
5045 goto selftests_nest_cancel;
5049 test_status = devlink->ops->selftest_run(devlink, i,
5051 if (devlink_selftest_result_put(msg, i, test_status))
5052 goto selftests_nest_cancel;
5056 nla_nest_end(msg, selftests);
5057 genlmsg_end(msg, hdr);
5058 return genlmsg_reply(msg, info);
5060 selftests_nest_cancel:
5061 nla_nest_cancel(msg, selftests);
5063 genlmsg_cancel(msg, hdr);
5069 static const struct devlink_param devlink_param_generic[] = {
5071 .id = DEVLINK_PARAM_GENERIC_ID_INT_ERR_RESET,
5072 .name = DEVLINK_PARAM_GENERIC_INT_ERR_RESET_NAME,
5073 .type = DEVLINK_PARAM_GENERIC_INT_ERR_RESET_TYPE,
5076 .id = DEVLINK_PARAM_GENERIC_ID_MAX_MACS,
5077 .name = DEVLINK_PARAM_GENERIC_MAX_MACS_NAME,
5078 .type = DEVLINK_PARAM_GENERIC_MAX_MACS_TYPE,
5081 .id = DEVLINK_PARAM_GENERIC_ID_ENABLE_SRIOV,
5082 .name = DEVLINK_PARAM_GENERIC_ENABLE_SRIOV_NAME,
5083 .type = DEVLINK_PARAM_GENERIC_ENABLE_SRIOV_TYPE,
5086 .id = DEVLINK_PARAM_GENERIC_ID_REGION_SNAPSHOT,
5087 .name = DEVLINK_PARAM_GENERIC_REGION_SNAPSHOT_NAME,
5088 .type = DEVLINK_PARAM_GENERIC_REGION_SNAPSHOT_TYPE,
5091 .id = DEVLINK_PARAM_GENERIC_ID_IGNORE_ARI,
5092 .name = DEVLINK_PARAM_GENERIC_IGNORE_ARI_NAME,
5093 .type = DEVLINK_PARAM_GENERIC_IGNORE_ARI_TYPE,
5096 .id = DEVLINK_PARAM_GENERIC_ID_MSIX_VEC_PER_PF_MAX,
5097 .name = DEVLINK_PARAM_GENERIC_MSIX_VEC_PER_PF_MAX_NAME,
5098 .type = DEVLINK_PARAM_GENERIC_MSIX_VEC_PER_PF_MAX_TYPE,
5101 .id = DEVLINK_PARAM_GENERIC_ID_MSIX_VEC_PER_PF_MIN,
5102 .name = DEVLINK_PARAM_GENERIC_MSIX_VEC_PER_PF_MIN_NAME,
5103 .type = DEVLINK_PARAM_GENERIC_MSIX_VEC_PER_PF_MIN_TYPE,
5106 .id = DEVLINK_PARAM_GENERIC_ID_FW_LOAD_POLICY,
5107 .name = DEVLINK_PARAM_GENERIC_FW_LOAD_POLICY_NAME,
5108 .type = DEVLINK_PARAM_GENERIC_FW_LOAD_POLICY_TYPE,
5111 .id = DEVLINK_PARAM_GENERIC_ID_RESET_DEV_ON_DRV_PROBE,
5112 .name = DEVLINK_PARAM_GENERIC_RESET_DEV_ON_DRV_PROBE_NAME,
5113 .type = DEVLINK_PARAM_GENERIC_RESET_DEV_ON_DRV_PROBE_TYPE,
5116 .id = DEVLINK_PARAM_GENERIC_ID_ENABLE_ROCE,
5117 .name = DEVLINK_PARAM_GENERIC_ENABLE_ROCE_NAME,
5118 .type = DEVLINK_PARAM_GENERIC_ENABLE_ROCE_TYPE,
5121 .id = DEVLINK_PARAM_GENERIC_ID_ENABLE_REMOTE_DEV_RESET,
5122 .name = DEVLINK_PARAM_GENERIC_ENABLE_REMOTE_DEV_RESET_NAME,
5123 .type = DEVLINK_PARAM_GENERIC_ENABLE_REMOTE_DEV_RESET_TYPE,
5126 .id = DEVLINK_PARAM_GENERIC_ID_ENABLE_ETH,
5127 .name = DEVLINK_PARAM_GENERIC_ENABLE_ETH_NAME,
5128 .type = DEVLINK_PARAM_GENERIC_ENABLE_ETH_TYPE,
5131 .id = DEVLINK_PARAM_GENERIC_ID_ENABLE_RDMA,
5132 .name = DEVLINK_PARAM_GENERIC_ENABLE_RDMA_NAME,
5133 .type = DEVLINK_PARAM_GENERIC_ENABLE_RDMA_TYPE,
5136 .id = DEVLINK_PARAM_GENERIC_ID_ENABLE_VNET,
5137 .name = DEVLINK_PARAM_GENERIC_ENABLE_VNET_NAME,
5138 .type = DEVLINK_PARAM_GENERIC_ENABLE_VNET_TYPE,
5141 .id = DEVLINK_PARAM_GENERIC_ID_ENABLE_IWARP,
5142 .name = DEVLINK_PARAM_GENERIC_ENABLE_IWARP_NAME,
5143 .type = DEVLINK_PARAM_GENERIC_ENABLE_IWARP_TYPE,
5146 .id = DEVLINK_PARAM_GENERIC_ID_IO_EQ_SIZE,
5147 .name = DEVLINK_PARAM_GENERIC_IO_EQ_SIZE_NAME,
5148 .type = DEVLINK_PARAM_GENERIC_IO_EQ_SIZE_TYPE,
5151 .id = DEVLINK_PARAM_GENERIC_ID_EVENT_EQ_SIZE,
5152 .name = DEVLINK_PARAM_GENERIC_EVENT_EQ_SIZE_NAME,
5153 .type = DEVLINK_PARAM_GENERIC_EVENT_EQ_SIZE_TYPE,
5157 static int devlink_param_generic_verify(const struct devlink_param *param)
5159 /* verify it match generic parameter by id and name */
5160 if (param->id > DEVLINK_PARAM_GENERIC_ID_MAX)
5162 if (strcmp(param->name, devlink_param_generic[param->id].name))
5165 WARN_ON(param->type != devlink_param_generic[param->id].type);
5170 static int devlink_param_driver_verify(const struct devlink_param *param)
5174 if (param->id <= DEVLINK_PARAM_GENERIC_ID_MAX)
5176 /* verify no such name in generic params */
5177 for (i = 0; i <= DEVLINK_PARAM_GENERIC_ID_MAX; i++)
5178 if (!strcmp(param->name, devlink_param_generic[i].name))
5184 static struct devlink_param_item *
5185 devlink_param_find_by_name(struct list_head *param_list,
5186 const char *param_name)
5188 struct devlink_param_item *param_item;
5190 list_for_each_entry(param_item, param_list, list)
5191 if (!strcmp(param_item->param->name, param_name))
5196 static struct devlink_param_item *
5197 devlink_param_find_by_id(struct list_head *param_list, u32 param_id)
5199 struct devlink_param_item *param_item;
5201 list_for_each_entry(param_item, param_list, list)
5202 if (param_item->param->id == param_id)
5208 devlink_param_cmode_is_supported(const struct devlink_param *param,
5209 enum devlink_param_cmode cmode)
5211 return test_bit(cmode, ¶m->supported_cmodes);
5214 static int devlink_param_get(struct devlink *devlink,
5215 const struct devlink_param *param,
5216 struct devlink_param_gset_ctx *ctx)
5218 if (!param->get || devlink->reload_failed)
5220 return param->get(devlink, param->id, ctx);
5223 static int devlink_param_set(struct devlink *devlink,
5224 const struct devlink_param *param,
5225 struct devlink_param_gset_ctx *ctx)
5227 if (!param->set || devlink->reload_failed)
5229 return param->set(devlink, param->id, ctx);
5233 devlink_param_type_to_nla_type(enum devlink_param_type param_type)
5235 switch (param_type) {
5236 case DEVLINK_PARAM_TYPE_U8:
5238 case DEVLINK_PARAM_TYPE_U16:
5240 case DEVLINK_PARAM_TYPE_U32:
5242 case DEVLINK_PARAM_TYPE_STRING:
5244 case DEVLINK_PARAM_TYPE_BOOL:
5252 devlink_nl_param_value_fill_one(struct sk_buff *msg,
5253 enum devlink_param_type type,
5254 enum devlink_param_cmode cmode,
5255 union devlink_param_value val)
5257 struct nlattr *param_value_attr;
5259 param_value_attr = nla_nest_start_noflag(msg,
5260 DEVLINK_ATTR_PARAM_VALUE);
5261 if (!param_value_attr)
5262 goto nla_put_failure;
5264 if (nla_put_u8(msg, DEVLINK_ATTR_PARAM_VALUE_CMODE, cmode))
5265 goto value_nest_cancel;
5268 case DEVLINK_PARAM_TYPE_U8:
5269 if (nla_put_u8(msg, DEVLINK_ATTR_PARAM_VALUE_DATA, val.vu8))
5270 goto value_nest_cancel;
5272 case DEVLINK_PARAM_TYPE_U16:
5273 if (nla_put_u16(msg, DEVLINK_ATTR_PARAM_VALUE_DATA, val.vu16))
5274 goto value_nest_cancel;
5276 case DEVLINK_PARAM_TYPE_U32:
5277 if (nla_put_u32(msg, DEVLINK_ATTR_PARAM_VALUE_DATA, val.vu32))
5278 goto value_nest_cancel;
5280 case DEVLINK_PARAM_TYPE_STRING:
5281 if (nla_put_string(msg, DEVLINK_ATTR_PARAM_VALUE_DATA,
5283 goto value_nest_cancel;
5285 case DEVLINK_PARAM_TYPE_BOOL:
5287 nla_put_flag(msg, DEVLINK_ATTR_PARAM_VALUE_DATA))
5288 goto value_nest_cancel;
5292 nla_nest_end(msg, param_value_attr);
5296 nla_nest_cancel(msg, param_value_attr);
5301 static int devlink_nl_param_fill(struct sk_buff *msg, struct devlink *devlink,
5302 unsigned int port_index,
5303 struct devlink_param_item *param_item,
5304 enum devlink_command cmd,
5305 u32 portid, u32 seq, int flags)
5307 union devlink_param_value param_value[DEVLINK_PARAM_CMODE_MAX + 1];
5308 bool param_value_set[DEVLINK_PARAM_CMODE_MAX + 1] = {};
5309 const struct devlink_param *param = param_item->param;
5310 struct devlink_param_gset_ctx ctx;
5311 struct nlattr *param_values_list;
5312 struct nlattr *param_attr;
5318 /* Get value from driver part to driverinit configuration mode */
5319 for (i = 0; i <= DEVLINK_PARAM_CMODE_MAX; i++) {
5320 if (!devlink_param_cmode_is_supported(param, i))
5322 if (i == DEVLINK_PARAM_CMODE_DRIVERINIT) {
5323 if (!param_item->driverinit_value_valid)
5325 param_value[i] = param_item->driverinit_value;
5328 err = devlink_param_get(devlink, param, &ctx);
5331 param_value[i] = ctx.val;
5333 param_value_set[i] = true;
5336 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
5340 if (devlink_nl_put_handle(msg, devlink))
5341 goto genlmsg_cancel;
5343 if (cmd == DEVLINK_CMD_PORT_PARAM_GET ||
5344 cmd == DEVLINK_CMD_PORT_PARAM_NEW ||
5345 cmd == DEVLINK_CMD_PORT_PARAM_DEL)
5346 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_INDEX, port_index))
5347 goto genlmsg_cancel;
5349 param_attr = nla_nest_start_noflag(msg, DEVLINK_ATTR_PARAM);
5351 goto genlmsg_cancel;
5352 if (nla_put_string(msg, DEVLINK_ATTR_PARAM_NAME, param->name))
5353 goto param_nest_cancel;
5354 if (param->generic && nla_put_flag(msg, DEVLINK_ATTR_PARAM_GENERIC))
5355 goto param_nest_cancel;
5357 nla_type = devlink_param_type_to_nla_type(param->type);
5359 goto param_nest_cancel;
5360 if (nla_put_u8(msg, DEVLINK_ATTR_PARAM_TYPE, nla_type))
5361 goto param_nest_cancel;
5363 param_values_list = nla_nest_start_noflag(msg,
5364 DEVLINK_ATTR_PARAM_VALUES_LIST);
5365 if (!param_values_list)
5366 goto param_nest_cancel;
5368 for (i = 0; i <= DEVLINK_PARAM_CMODE_MAX; i++) {
5369 if (!param_value_set[i])
5371 err = devlink_nl_param_value_fill_one(msg, param->type,
5374 goto values_list_nest_cancel;
5377 nla_nest_end(msg, param_values_list);
5378 nla_nest_end(msg, param_attr);
5379 genlmsg_end(msg, hdr);
5382 values_list_nest_cancel:
5383 nla_nest_end(msg, param_values_list);
5385 nla_nest_cancel(msg, param_attr);
5387 genlmsg_cancel(msg, hdr);
5391 static void devlink_param_notify(struct devlink *devlink,
5392 unsigned int port_index,
5393 struct devlink_param_item *param_item,
5394 enum devlink_command cmd)
5396 struct sk_buff *msg;
5399 WARN_ON(cmd != DEVLINK_CMD_PARAM_NEW && cmd != DEVLINK_CMD_PARAM_DEL &&
5400 cmd != DEVLINK_CMD_PORT_PARAM_NEW &&
5401 cmd != DEVLINK_CMD_PORT_PARAM_DEL);
5402 ASSERT_DEVLINK_REGISTERED(devlink);
5404 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
5407 err = devlink_nl_param_fill(msg, devlink, port_index, param_item, cmd,
5414 genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink),
5415 msg, 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
5418 static int devlink_nl_cmd_param_get_dumpit(struct sk_buff *msg,
5419 struct netlink_callback *cb)
5421 struct devlink_param_item *param_item;
5422 struct devlink *devlink;
5423 int start = cb->args[0];
5424 unsigned long index;
5428 devlinks_xa_for_each_registered_get(sock_net(msg->sk), index, devlink) {
5430 list_for_each_entry(param_item, &devlink->param_list, list) {
5435 err = devlink_nl_param_fill(msg, devlink, 0, param_item,
5436 DEVLINK_CMD_PARAM_GET,
5437 NETLINK_CB(cb->skb).portid,
5440 if (err == -EOPNOTSUPP) {
5443 devl_unlock(devlink);
5444 devlink_put(devlink);
5449 devl_unlock(devlink);
5450 devlink_put(devlink);
5453 if (err != -EMSGSIZE)
5461 devlink_param_type_get_from_info(struct genl_info *info,
5462 enum devlink_param_type *param_type)
5464 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_PARAM_TYPE))
5467 switch (nla_get_u8(info->attrs[DEVLINK_ATTR_PARAM_TYPE])) {
5469 *param_type = DEVLINK_PARAM_TYPE_U8;
5472 *param_type = DEVLINK_PARAM_TYPE_U16;
5475 *param_type = DEVLINK_PARAM_TYPE_U32;
5478 *param_type = DEVLINK_PARAM_TYPE_STRING;
5481 *param_type = DEVLINK_PARAM_TYPE_BOOL;
5491 devlink_param_value_get_from_info(const struct devlink_param *param,
5492 struct genl_info *info,
5493 union devlink_param_value *value)
5495 struct nlattr *param_data;
5498 param_data = info->attrs[DEVLINK_ATTR_PARAM_VALUE_DATA];
5500 if (param->type != DEVLINK_PARAM_TYPE_BOOL && !param_data)
5503 switch (param->type) {
5504 case DEVLINK_PARAM_TYPE_U8:
5505 if (nla_len(param_data) != sizeof(u8))
5507 value->vu8 = nla_get_u8(param_data);
5509 case DEVLINK_PARAM_TYPE_U16:
5510 if (nla_len(param_data) != sizeof(u16))
5512 value->vu16 = nla_get_u16(param_data);
5514 case DEVLINK_PARAM_TYPE_U32:
5515 if (nla_len(param_data) != sizeof(u32))
5517 value->vu32 = nla_get_u32(param_data);
5519 case DEVLINK_PARAM_TYPE_STRING:
5520 len = strnlen(nla_data(param_data), nla_len(param_data));
5521 if (len == nla_len(param_data) ||
5522 len >= __DEVLINK_PARAM_MAX_STRING_VALUE)
5524 strcpy(value->vstr, nla_data(param_data));
5526 case DEVLINK_PARAM_TYPE_BOOL:
5527 if (param_data && nla_len(param_data))
5529 value->vbool = nla_get_flag(param_data);
5535 static struct devlink_param_item *
5536 devlink_param_get_from_info(struct list_head *param_list,
5537 struct genl_info *info)
5541 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_PARAM_NAME))
5544 param_name = nla_data(info->attrs[DEVLINK_ATTR_PARAM_NAME]);
5545 return devlink_param_find_by_name(param_list, param_name);
5548 static int devlink_nl_cmd_param_get_doit(struct sk_buff *skb,
5549 struct genl_info *info)
5551 struct devlink *devlink = info->user_ptr[0];
5552 struct devlink_param_item *param_item;
5553 struct sk_buff *msg;
5556 param_item = devlink_param_get_from_info(&devlink->param_list, info);
5560 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
5564 err = devlink_nl_param_fill(msg, devlink, 0, param_item,
5565 DEVLINK_CMD_PARAM_GET,
5566 info->snd_portid, info->snd_seq, 0);
5572 return genlmsg_reply(msg, info);
5575 static int __devlink_nl_cmd_param_set_doit(struct devlink *devlink,
5576 unsigned int port_index,
5577 struct list_head *param_list,
5578 struct genl_info *info,
5579 enum devlink_command cmd)
5581 enum devlink_param_type param_type;
5582 struct devlink_param_gset_ctx ctx;
5583 enum devlink_param_cmode cmode;
5584 struct devlink_param_item *param_item;
5585 const struct devlink_param *param;
5586 union devlink_param_value value;
5589 param_item = devlink_param_get_from_info(param_list, info);
5592 param = param_item->param;
5593 err = devlink_param_type_get_from_info(info, ¶m_type);
5596 if (param_type != param->type)
5598 err = devlink_param_value_get_from_info(param, info, &value);
5601 if (param->validate) {
5602 err = param->validate(devlink, param->id, value, info->extack);
5607 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_PARAM_VALUE_CMODE))
5609 cmode = nla_get_u8(info->attrs[DEVLINK_ATTR_PARAM_VALUE_CMODE]);
5610 if (!devlink_param_cmode_is_supported(param, cmode))
5613 if (cmode == DEVLINK_PARAM_CMODE_DRIVERINIT) {
5614 if (param->type == DEVLINK_PARAM_TYPE_STRING)
5615 strcpy(param_item->driverinit_value.vstr, value.vstr);
5617 param_item->driverinit_value = value;
5618 param_item->driverinit_value_valid = true;
5624 err = devlink_param_set(devlink, param, &ctx);
5629 devlink_param_notify(devlink, port_index, param_item, cmd);
5633 static int devlink_nl_cmd_param_set_doit(struct sk_buff *skb,
5634 struct genl_info *info)
5636 struct devlink *devlink = info->user_ptr[0];
5638 return __devlink_nl_cmd_param_set_doit(devlink, 0, &devlink->param_list,
5639 info, DEVLINK_CMD_PARAM_NEW);
5642 static int devlink_nl_cmd_port_param_get_dumpit(struct sk_buff *msg,
5643 struct netlink_callback *cb)
5645 NL_SET_ERR_MSG_MOD(cb->extack, "Port params are not supported");
5649 static int devlink_nl_cmd_port_param_get_doit(struct sk_buff *skb,
5650 struct genl_info *info)
5652 NL_SET_ERR_MSG_MOD(info->extack, "Port params are not supported");
5656 static int devlink_nl_cmd_port_param_set_doit(struct sk_buff *skb,
5657 struct genl_info *info)
5659 NL_SET_ERR_MSG_MOD(info->extack, "Port params are not supported");
5663 static int devlink_nl_region_snapshot_id_put(struct sk_buff *msg,
5664 struct devlink *devlink,
5665 struct devlink_snapshot *snapshot)
5667 struct nlattr *snap_attr;
5670 snap_attr = nla_nest_start_noflag(msg, DEVLINK_ATTR_REGION_SNAPSHOT);
5674 err = nla_put_u32(msg, DEVLINK_ATTR_REGION_SNAPSHOT_ID, snapshot->id);
5676 goto nla_put_failure;
5678 nla_nest_end(msg, snap_attr);
5682 nla_nest_cancel(msg, snap_attr);
5686 static int devlink_nl_region_snapshots_id_put(struct sk_buff *msg,
5687 struct devlink *devlink,
5688 struct devlink_region *region)
5690 struct devlink_snapshot *snapshot;
5691 struct nlattr *snapshots_attr;
5694 snapshots_attr = nla_nest_start_noflag(msg,
5695 DEVLINK_ATTR_REGION_SNAPSHOTS);
5696 if (!snapshots_attr)
5699 list_for_each_entry(snapshot, ®ion->snapshot_list, list) {
5700 err = devlink_nl_region_snapshot_id_put(msg, devlink, snapshot);
5702 goto nla_put_failure;
5705 nla_nest_end(msg, snapshots_attr);
5709 nla_nest_cancel(msg, snapshots_attr);
5713 static int devlink_nl_region_fill(struct sk_buff *msg, struct devlink *devlink,
5714 enum devlink_command cmd, u32 portid,
5716 struct devlink_region *region)
5721 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
5725 err = devlink_nl_put_handle(msg, devlink);
5727 goto nla_put_failure;
5730 err = nla_put_u32(msg, DEVLINK_ATTR_PORT_INDEX,
5731 region->port->index);
5733 goto nla_put_failure;
5736 err = nla_put_string(msg, DEVLINK_ATTR_REGION_NAME, region->ops->name);
5738 goto nla_put_failure;
5740 err = nla_put_u64_64bit(msg, DEVLINK_ATTR_REGION_SIZE,
5744 goto nla_put_failure;
5746 err = nla_put_u32(msg, DEVLINK_ATTR_REGION_MAX_SNAPSHOTS,
5747 region->max_snapshots);
5749 goto nla_put_failure;
5751 err = devlink_nl_region_snapshots_id_put(msg, devlink, region);
5753 goto nla_put_failure;
5755 genlmsg_end(msg, hdr);
5759 genlmsg_cancel(msg, hdr);
5763 static struct sk_buff *
5764 devlink_nl_region_notify_build(struct devlink_region *region,
5765 struct devlink_snapshot *snapshot,
5766 enum devlink_command cmd, u32 portid, u32 seq)
5768 struct devlink *devlink = region->devlink;
5769 struct sk_buff *msg;
5774 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
5776 return ERR_PTR(-ENOMEM);
5778 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, 0, cmd);
5784 err = devlink_nl_put_handle(msg, devlink);
5786 goto out_cancel_msg;
5789 err = nla_put_u32(msg, DEVLINK_ATTR_PORT_INDEX,
5790 region->port->index);
5792 goto out_cancel_msg;
5795 err = nla_put_string(msg, DEVLINK_ATTR_REGION_NAME,
5798 goto out_cancel_msg;
5801 err = nla_put_u32(msg, DEVLINK_ATTR_REGION_SNAPSHOT_ID,
5804 goto out_cancel_msg;
5806 err = nla_put_u64_64bit(msg, DEVLINK_ATTR_REGION_SIZE,
5807 region->size, DEVLINK_ATTR_PAD);
5809 goto out_cancel_msg;
5811 genlmsg_end(msg, hdr);
5816 genlmsg_cancel(msg, hdr);
5819 return ERR_PTR(err);
5822 static void devlink_nl_region_notify(struct devlink_region *region,
5823 struct devlink_snapshot *snapshot,
5824 enum devlink_command cmd)
5826 struct devlink *devlink = region->devlink;
5827 struct sk_buff *msg;
5829 WARN_ON(cmd != DEVLINK_CMD_REGION_NEW && cmd != DEVLINK_CMD_REGION_DEL);
5830 if (!xa_get_mark(&devlinks, devlink->index, DEVLINK_REGISTERED))
5833 msg = devlink_nl_region_notify_build(region, snapshot, cmd, 0, 0);
5837 genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink), msg,
5838 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
5842 * __devlink_snapshot_id_increment - Increment number of snapshots using an id
5843 * @devlink: devlink instance
5844 * @id: the snapshot id
5846 * Track when a new snapshot begins using an id. Load the count for the
5847 * given id from the snapshot xarray, increment it, and store it back.
5849 * Called when a new snapshot is created with the given id.
5851 * The id *must* have been previously allocated by
5852 * devlink_region_snapshot_id_get().
5854 * Returns 0 on success, or an error on failure.
5856 static int __devlink_snapshot_id_increment(struct devlink *devlink, u32 id)
5858 unsigned long count;
5862 xa_lock(&devlink->snapshot_ids);
5863 p = xa_load(&devlink->snapshot_ids, id);
5869 if (WARN_ON(!xa_is_value(p))) {
5874 count = xa_to_value(p);
5877 err = xa_err(__xa_store(&devlink->snapshot_ids, id, xa_mk_value(count),
5880 xa_unlock(&devlink->snapshot_ids);
5885 * __devlink_snapshot_id_decrement - Decrease number of snapshots using an id
5886 * @devlink: devlink instance
5887 * @id: the snapshot id
5889 * Track when a snapshot is deleted and stops using an id. Load the count
5890 * for the given id from the snapshot xarray, decrement it, and store it
5893 * If the count reaches zero, erase this id from the xarray, freeing it
5894 * up for future re-use by devlink_region_snapshot_id_get().
5896 * Called when a snapshot using the given id is deleted, and when the
5897 * initial allocator of the id is finished using it.
5899 static void __devlink_snapshot_id_decrement(struct devlink *devlink, u32 id)
5901 unsigned long count;
5904 xa_lock(&devlink->snapshot_ids);
5905 p = xa_load(&devlink->snapshot_ids, id);
5909 if (WARN_ON(!xa_is_value(p)))
5912 count = xa_to_value(p);
5916 __xa_store(&devlink->snapshot_ids, id, xa_mk_value(count),
5919 /* If this was the last user, we can erase this id */
5920 __xa_erase(&devlink->snapshot_ids, id);
5923 xa_unlock(&devlink->snapshot_ids);
5927 * __devlink_snapshot_id_insert - Insert a specific snapshot ID
5928 * @devlink: devlink instance
5929 * @id: the snapshot id
5931 * Mark the given snapshot id as used by inserting a zero value into the
5934 * This must be called while holding the devlink instance lock. Unlike
5935 * devlink_snapshot_id_get, the initial reference count is zero, not one.
5936 * It is expected that the id will immediately be used before
5937 * releasing the devlink instance lock.
5939 * Returns zero on success, or an error code if the snapshot id could not
5942 static int __devlink_snapshot_id_insert(struct devlink *devlink, u32 id)
5946 xa_lock(&devlink->snapshot_ids);
5947 if (xa_load(&devlink->snapshot_ids, id)) {
5948 xa_unlock(&devlink->snapshot_ids);
5951 err = xa_err(__xa_store(&devlink->snapshot_ids, id, xa_mk_value(0),
5953 xa_unlock(&devlink->snapshot_ids);
5958 * __devlink_region_snapshot_id_get - get snapshot ID
5959 * @devlink: devlink instance
5960 * @id: storage to return snapshot id
5962 * Allocates a new snapshot id. Returns zero on success, or a negative
5963 * error on failure. Must be called while holding the devlink instance
5966 * Snapshot IDs are tracked using an xarray which stores the number of
5967 * users of the snapshot id.
5969 * Note that the caller of this function counts as a 'user', in order to
5970 * avoid race conditions. The caller must release its hold on the
5971 * snapshot by using devlink_region_snapshot_id_put.
5973 static int __devlink_region_snapshot_id_get(struct devlink *devlink, u32 *id)
5975 return xa_alloc(&devlink->snapshot_ids, id, xa_mk_value(1),
5976 xa_limit_32b, GFP_KERNEL);
5980 * __devlink_region_snapshot_create - create a new snapshot
5981 * This will add a new snapshot of a region. The snapshot
5982 * will be stored on the region struct and can be accessed
5983 * from devlink. This is useful for future analyses of snapshots.
5984 * Multiple snapshots can be created on a region.
5985 * The @snapshot_id should be obtained using the getter function.
5987 * Must be called only while holding the region snapshot lock.
5989 * @region: devlink region of the snapshot
5990 * @data: snapshot data
5991 * @snapshot_id: snapshot id to be created
5994 __devlink_region_snapshot_create(struct devlink_region *region,
5995 u8 *data, u32 snapshot_id)
5997 struct devlink *devlink = region->devlink;
5998 struct devlink_snapshot *snapshot;
6001 lockdep_assert_held(®ion->snapshot_lock);
6003 /* check if region can hold one more snapshot */
6004 if (region->cur_snapshots == region->max_snapshots)
6007 if (devlink_region_snapshot_get_by_id(region, snapshot_id))
6010 snapshot = kzalloc(sizeof(*snapshot), GFP_KERNEL);
6014 err = __devlink_snapshot_id_increment(devlink, snapshot_id);
6016 goto err_snapshot_id_increment;
6018 snapshot->id = snapshot_id;
6019 snapshot->region = region;
6020 snapshot->data = data;
6022 list_add_tail(&snapshot->list, ®ion->snapshot_list);
6024 region->cur_snapshots++;
6026 devlink_nl_region_notify(region, snapshot, DEVLINK_CMD_REGION_NEW);
6029 err_snapshot_id_increment:
6034 static void devlink_region_snapshot_del(struct devlink_region *region,
6035 struct devlink_snapshot *snapshot)
6037 struct devlink *devlink = region->devlink;
6039 lockdep_assert_held(®ion->snapshot_lock);
6041 devlink_nl_region_notify(region, snapshot, DEVLINK_CMD_REGION_DEL);
6042 region->cur_snapshots--;
6043 list_del(&snapshot->list);
6044 region->ops->destructor(snapshot->data);
6045 __devlink_snapshot_id_decrement(devlink, snapshot->id);
6049 static int devlink_nl_cmd_region_get_doit(struct sk_buff *skb,
6050 struct genl_info *info)
6052 struct devlink *devlink = info->user_ptr[0];
6053 struct devlink_port *port = NULL;
6054 struct devlink_region *region;
6055 const char *region_name;
6056 struct sk_buff *msg;
6060 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_REGION_NAME))
6063 if (info->attrs[DEVLINK_ATTR_PORT_INDEX]) {
6064 index = nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_INDEX]);
6066 port = devlink_port_get_by_index(devlink, index);
6071 region_name = nla_data(info->attrs[DEVLINK_ATTR_REGION_NAME]);
6073 region = devlink_port_region_get_by_name(port, region_name);
6075 region = devlink_region_get_by_name(devlink, region_name);
6080 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
6084 err = devlink_nl_region_fill(msg, devlink, DEVLINK_CMD_REGION_GET,
6085 info->snd_portid, info->snd_seq, 0,
6092 return genlmsg_reply(msg, info);
6095 static int devlink_nl_cmd_region_get_port_dumpit(struct sk_buff *msg,
6096 struct netlink_callback *cb,
6097 struct devlink_port *port,
6101 struct devlink_region *region;
6104 list_for_each_entry(region, &port->region_list, list) {
6109 err = devlink_nl_region_fill(msg, port->devlink,
6110 DEVLINK_CMD_REGION_GET,
6111 NETLINK_CB(cb->skb).portid,
6113 NLM_F_MULTI, region);
6123 static int devlink_nl_cmd_region_get_devlink_dumpit(struct sk_buff *msg,
6124 struct netlink_callback *cb,
6125 struct devlink *devlink,
6129 struct devlink_region *region;
6130 struct devlink_port *port;
6134 list_for_each_entry(region, &devlink->region_list, list) {
6139 err = devlink_nl_region_fill(msg, devlink,
6140 DEVLINK_CMD_REGION_GET,
6141 NETLINK_CB(cb->skb).portid,
6143 NLM_F_MULTI, region);
6149 list_for_each_entry(port, &devlink->port_list, list) {
6150 err = devlink_nl_cmd_region_get_port_dumpit(msg, cb, port, idx,
6157 devl_unlock(devlink);
6161 static int devlink_nl_cmd_region_get_dumpit(struct sk_buff *msg,
6162 struct netlink_callback *cb)
6164 struct devlink *devlink;
6165 int start = cb->args[0];
6166 unsigned long index;
6170 devlinks_xa_for_each_registered_get(sock_net(msg->sk), index, devlink) {
6171 err = devlink_nl_cmd_region_get_devlink_dumpit(msg, cb, devlink,
6173 devlink_put(devlink);
6182 static int devlink_nl_cmd_region_del(struct sk_buff *skb,
6183 struct genl_info *info)
6185 struct devlink *devlink = info->user_ptr[0];
6186 struct devlink_snapshot *snapshot;
6187 struct devlink_port *port = NULL;
6188 struct devlink_region *region;
6189 const char *region_name;
6193 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_REGION_NAME) ||
6194 GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_REGION_SNAPSHOT_ID))
6197 region_name = nla_data(info->attrs[DEVLINK_ATTR_REGION_NAME]);
6198 snapshot_id = nla_get_u32(info->attrs[DEVLINK_ATTR_REGION_SNAPSHOT_ID]);
6200 if (info->attrs[DEVLINK_ATTR_PORT_INDEX]) {
6201 index = nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_INDEX]);
6203 port = devlink_port_get_by_index(devlink, index);
6209 region = devlink_port_region_get_by_name(port, region_name);
6211 region = devlink_region_get_by_name(devlink, region_name);
6216 mutex_lock(®ion->snapshot_lock);
6217 snapshot = devlink_region_snapshot_get_by_id(region, snapshot_id);
6219 mutex_unlock(®ion->snapshot_lock);
6223 devlink_region_snapshot_del(region, snapshot);
6224 mutex_unlock(®ion->snapshot_lock);
6229 devlink_nl_cmd_region_new(struct sk_buff *skb, struct genl_info *info)
6231 struct devlink *devlink = info->user_ptr[0];
6232 struct devlink_snapshot *snapshot;
6233 struct devlink_port *port = NULL;
6234 struct nlattr *snapshot_id_attr;
6235 struct devlink_region *region;
6236 const char *region_name;
6242 if (GENL_REQ_ATTR_CHECK(info, DEVLINK_ATTR_REGION_NAME)) {
6243 NL_SET_ERR_MSG_MOD(info->extack, "No region name provided");
6247 region_name = nla_data(info->attrs[DEVLINK_ATTR_REGION_NAME]);
6249 if (info->attrs[DEVLINK_ATTR_PORT_INDEX]) {
6250 index = nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_INDEX]);
6252 port = devlink_port_get_by_index(devlink, index);
6258 region = devlink_port_region_get_by_name(port, region_name);
6260 region = devlink_region_get_by_name(devlink, region_name);
6263 NL_SET_ERR_MSG_MOD(info->extack, "The requested region does not exist");
6267 if (!region->ops->snapshot) {
6268 NL_SET_ERR_MSG_MOD(info->extack, "The requested region does not support taking an immediate snapshot");
6272 mutex_lock(®ion->snapshot_lock);
6274 if (region->cur_snapshots == region->max_snapshots) {
6275 NL_SET_ERR_MSG_MOD(info->extack, "The region has reached the maximum number of stored snapshots");
6280 snapshot_id_attr = info->attrs[DEVLINK_ATTR_REGION_SNAPSHOT_ID];
6281 if (snapshot_id_attr) {
6282 snapshot_id = nla_get_u32(snapshot_id_attr);
6284 if (devlink_region_snapshot_get_by_id(region, snapshot_id)) {
6285 NL_SET_ERR_MSG_MOD(info->extack, "The requested snapshot id is already in use");
6290 err = __devlink_snapshot_id_insert(devlink, snapshot_id);
6294 err = __devlink_region_snapshot_id_get(devlink, &snapshot_id);
6296 NL_SET_ERR_MSG_MOD(info->extack, "Failed to allocate a new snapshot id");
6302 err = region->port_ops->snapshot(port, region->port_ops,
6303 info->extack, &data);
6305 err = region->ops->snapshot(devlink, region->ops,
6306 info->extack, &data);
6308 goto err_snapshot_capture;
6310 err = __devlink_region_snapshot_create(region, data, snapshot_id);
6312 goto err_snapshot_create;
6314 if (!snapshot_id_attr) {
6315 struct sk_buff *msg;
6317 snapshot = devlink_region_snapshot_get_by_id(region,
6319 if (WARN_ON(!snapshot)) {
6324 msg = devlink_nl_region_notify_build(region, snapshot,
6325 DEVLINK_CMD_REGION_NEW,
6328 err = PTR_ERR_OR_ZERO(msg);
6332 err = genlmsg_reply(msg, info);
6337 mutex_unlock(®ion->snapshot_lock);
6340 err_snapshot_create:
6341 region->ops->destructor(data);
6342 err_snapshot_capture:
6343 __devlink_snapshot_id_decrement(devlink, snapshot_id);
6344 mutex_unlock(®ion->snapshot_lock);
6348 devlink_region_snapshot_del(region, snapshot);
6350 mutex_unlock(®ion->snapshot_lock);
6354 static int devlink_nl_cmd_region_read_chunk_fill(struct sk_buff *msg,
6355 struct devlink *devlink,
6356 u8 *chunk, u32 chunk_size,
6359 struct nlattr *chunk_attr;
6362 chunk_attr = nla_nest_start_noflag(msg, DEVLINK_ATTR_REGION_CHUNK);
6366 err = nla_put(msg, DEVLINK_ATTR_REGION_CHUNK_DATA, chunk_size, chunk);
6368 goto nla_put_failure;
6370 err = nla_put_u64_64bit(msg, DEVLINK_ATTR_REGION_CHUNK_ADDR, addr,
6373 goto nla_put_failure;
6375 nla_nest_end(msg, chunk_attr);
6379 nla_nest_cancel(msg, chunk_attr);
6383 #define DEVLINK_REGION_READ_CHUNK_SIZE 256
6385 static int devlink_nl_region_read_snapshot_fill(struct sk_buff *skb,
6386 struct devlink *devlink,
6387 struct devlink_region *region,
6388 struct nlattr **attrs,
6393 struct devlink_snapshot *snapshot;
6394 u64 curr_offset = start_offset;
6398 *new_offset = start_offset;
6400 snapshot_id = nla_get_u32(attrs[DEVLINK_ATTR_REGION_SNAPSHOT_ID]);
6401 snapshot = devlink_region_snapshot_get_by_id(region, snapshot_id);
6405 while (curr_offset < end_offset) {
6409 if (end_offset - curr_offset < DEVLINK_REGION_READ_CHUNK_SIZE)
6410 data_size = end_offset - curr_offset;
6412 data_size = DEVLINK_REGION_READ_CHUNK_SIZE;
6414 data = &snapshot->data[curr_offset];
6415 err = devlink_nl_cmd_region_read_chunk_fill(skb, devlink,
6421 curr_offset += data_size;
6423 *new_offset = curr_offset;
6428 static int devlink_nl_cmd_region_read_dumpit(struct sk_buff *skb,
6429 struct netlink_callback *cb)
6431 const struct genl_dumpit_info *info = genl_dumpit_info(cb);
6432 u64 ret_offset, start_offset, end_offset = U64_MAX;
6433 struct nlattr **attrs = info->attrs;
6434 struct devlink_port *port = NULL;
6435 struct devlink_region *region;
6436 struct nlattr *chunks_attr;
6437 const char *region_name;
6438 struct devlink *devlink;
6443 start_offset = *((u64 *)&cb->args[0]);
6445 devlink = devlink_get_from_attrs(sock_net(cb->skb->sk), attrs);
6446 if (IS_ERR(devlink))
6447 return PTR_ERR(devlink);
6451 if (!attrs[DEVLINK_ATTR_REGION_NAME] ||
6452 !attrs[DEVLINK_ATTR_REGION_SNAPSHOT_ID]) {
6457 if (info->attrs[DEVLINK_ATTR_PORT_INDEX]) {
6458 index = nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_INDEX]);
6460 port = devlink_port_get_by_index(devlink, index);
6467 region_name = nla_data(attrs[DEVLINK_ATTR_REGION_NAME]);
6470 region = devlink_port_region_get_by_name(port, region_name);
6472 region = devlink_region_get_by_name(devlink, region_name);
6479 if (attrs[DEVLINK_ATTR_REGION_CHUNK_ADDR] &&
6480 attrs[DEVLINK_ATTR_REGION_CHUNK_LEN]) {
6483 nla_get_u64(attrs[DEVLINK_ATTR_REGION_CHUNK_ADDR]);
6485 end_offset = nla_get_u64(attrs[DEVLINK_ATTR_REGION_CHUNK_ADDR]);
6486 end_offset += nla_get_u64(attrs[DEVLINK_ATTR_REGION_CHUNK_LEN]);
6489 if (end_offset > region->size)
6490 end_offset = region->size;
6492 /* return 0 if there is no further data to read */
6493 if (start_offset == end_offset) {
6498 hdr = genlmsg_put(skb, NETLINK_CB(cb->skb).portid, cb->nlh->nlmsg_seq,
6499 &devlink_nl_family, NLM_F_ACK | NLM_F_MULTI,
6500 DEVLINK_CMD_REGION_READ);
6506 err = devlink_nl_put_handle(skb, devlink);
6508 goto nla_put_failure;
6511 err = nla_put_u32(skb, DEVLINK_ATTR_PORT_INDEX,
6512 region->port->index);
6514 goto nla_put_failure;
6517 err = nla_put_string(skb, DEVLINK_ATTR_REGION_NAME, region_name);
6519 goto nla_put_failure;
6521 chunks_attr = nla_nest_start_noflag(skb, DEVLINK_ATTR_REGION_CHUNKS);
6524 goto nla_put_failure;
6527 err = devlink_nl_region_read_snapshot_fill(skb, devlink,
6530 end_offset, &ret_offset);
6532 if (err && err != -EMSGSIZE)
6533 goto nla_put_failure;
6535 /* Check if there was any progress done to prevent infinite loop */
6536 if (ret_offset == start_offset) {
6538 goto nla_put_failure;
6541 *((u64 *)&cb->args[0]) = ret_offset;
6543 nla_nest_end(skb, chunks_attr);
6544 genlmsg_end(skb, hdr);
6545 devl_unlock(devlink);
6546 devlink_put(devlink);
6550 genlmsg_cancel(skb, hdr);
6552 devl_unlock(devlink);
6553 devlink_put(devlink);
6557 int devlink_info_driver_name_put(struct devlink_info_req *req, const char *name)
6561 return nla_put_string(req->msg, DEVLINK_ATTR_INFO_DRIVER_NAME, name);
6563 EXPORT_SYMBOL_GPL(devlink_info_driver_name_put);
6565 int devlink_info_serial_number_put(struct devlink_info_req *req, const char *sn)
6569 return nla_put_string(req->msg, DEVLINK_ATTR_INFO_SERIAL_NUMBER, sn);
6571 EXPORT_SYMBOL_GPL(devlink_info_serial_number_put);
6573 int devlink_info_board_serial_number_put(struct devlink_info_req *req,
6578 return nla_put_string(req->msg, DEVLINK_ATTR_INFO_BOARD_SERIAL_NUMBER,
6581 EXPORT_SYMBOL_GPL(devlink_info_board_serial_number_put);
6583 static int devlink_info_version_put(struct devlink_info_req *req, int attr,
6584 const char *version_name,
6585 const char *version_value,
6586 enum devlink_info_version_type version_type)
6588 struct nlattr *nest;
6591 if (req->version_cb)
6592 req->version_cb(version_name, version_type,
6593 req->version_cb_priv);
6598 nest = nla_nest_start_noflag(req->msg, attr);
6602 err = nla_put_string(req->msg, DEVLINK_ATTR_INFO_VERSION_NAME,
6605 goto nla_put_failure;
6607 err = nla_put_string(req->msg, DEVLINK_ATTR_INFO_VERSION_VALUE,
6610 goto nla_put_failure;
6612 nla_nest_end(req->msg, nest);
6617 nla_nest_cancel(req->msg, nest);
6621 int devlink_info_version_fixed_put(struct devlink_info_req *req,
6622 const char *version_name,
6623 const char *version_value)
6625 return devlink_info_version_put(req, DEVLINK_ATTR_INFO_VERSION_FIXED,
6626 version_name, version_value,
6627 DEVLINK_INFO_VERSION_TYPE_NONE);
6629 EXPORT_SYMBOL_GPL(devlink_info_version_fixed_put);
6631 int devlink_info_version_stored_put(struct devlink_info_req *req,
6632 const char *version_name,
6633 const char *version_value)
6635 return devlink_info_version_put(req, DEVLINK_ATTR_INFO_VERSION_STORED,
6636 version_name, version_value,
6637 DEVLINK_INFO_VERSION_TYPE_NONE);
6639 EXPORT_SYMBOL_GPL(devlink_info_version_stored_put);
6641 int devlink_info_version_stored_put_ext(struct devlink_info_req *req,
6642 const char *version_name,
6643 const char *version_value,
6644 enum devlink_info_version_type version_type)
6646 return devlink_info_version_put(req, DEVLINK_ATTR_INFO_VERSION_STORED,
6647 version_name, version_value,
6650 EXPORT_SYMBOL_GPL(devlink_info_version_stored_put_ext);
6652 int devlink_info_version_running_put(struct devlink_info_req *req,
6653 const char *version_name,
6654 const char *version_value)
6656 return devlink_info_version_put(req, DEVLINK_ATTR_INFO_VERSION_RUNNING,
6657 version_name, version_value,
6658 DEVLINK_INFO_VERSION_TYPE_NONE);
6660 EXPORT_SYMBOL_GPL(devlink_info_version_running_put);
6662 int devlink_info_version_running_put_ext(struct devlink_info_req *req,
6663 const char *version_name,
6664 const char *version_value,
6665 enum devlink_info_version_type version_type)
6667 return devlink_info_version_put(req, DEVLINK_ATTR_INFO_VERSION_RUNNING,
6668 version_name, version_value,
6671 EXPORT_SYMBOL_GPL(devlink_info_version_running_put_ext);
6674 devlink_nl_info_fill(struct sk_buff *msg, struct devlink *devlink,
6675 enum devlink_command cmd, u32 portid,
6676 u32 seq, int flags, struct netlink_ext_ack *extack)
6678 struct devlink_info_req req = {};
6682 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
6687 if (devlink_nl_put_handle(msg, devlink))
6688 goto err_cancel_msg;
6691 err = devlink->ops->info_get(devlink, &req, extack);
6693 goto err_cancel_msg;
6695 genlmsg_end(msg, hdr);
6699 genlmsg_cancel(msg, hdr);
6703 static int devlink_nl_cmd_info_get_doit(struct sk_buff *skb,
6704 struct genl_info *info)
6706 struct devlink *devlink = info->user_ptr[0];
6707 struct sk_buff *msg;
6710 if (!devlink->ops->info_get)
6713 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
6717 err = devlink_nl_info_fill(msg, devlink, DEVLINK_CMD_INFO_GET,
6718 info->snd_portid, info->snd_seq, 0,
6725 return genlmsg_reply(msg, info);
6728 static int devlink_nl_cmd_info_get_dumpit(struct sk_buff *msg,
6729 struct netlink_callback *cb)
6731 struct devlink *devlink;
6732 int start = cb->args[0];
6733 unsigned long index;
6737 devlinks_xa_for_each_registered_get(sock_net(msg->sk), index, devlink) {
6738 if (idx < start || !devlink->ops->info_get)
6742 err = devlink_nl_info_fill(msg, devlink, DEVLINK_CMD_INFO_GET,
6743 NETLINK_CB(cb->skb).portid,
6744 cb->nlh->nlmsg_seq, NLM_F_MULTI,
6746 devl_unlock(devlink);
6747 if (err == -EOPNOTSUPP)
6750 devlink_put(devlink);
6755 devlink_put(devlink);
6758 if (err != -EMSGSIZE)
6765 struct devlink_fmsg_item {
6766 struct list_head list;
6773 struct devlink_fmsg {
6774 struct list_head item_list;
6775 bool putting_binary; /* This flag forces enclosing of binary data
6776 * in an array brackets. It forces using
6777 * of designated API:
6778 * devlink_fmsg_binary_pair_nest_start()
6779 * devlink_fmsg_binary_pair_nest_end()
6783 static struct devlink_fmsg *devlink_fmsg_alloc(void)
6785 struct devlink_fmsg *fmsg;
6787 fmsg = kzalloc(sizeof(*fmsg), GFP_KERNEL);
6791 INIT_LIST_HEAD(&fmsg->item_list);
6796 static void devlink_fmsg_free(struct devlink_fmsg *fmsg)
6798 struct devlink_fmsg_item *item, *tmp;
6800 list_for_each_entry_safe(item, tmp, &fmsg->item_list, list) {
6801 list_del(&item->list);
6807 static int devlink_fmsg_nest_common(struct devlink_fmsg *fmsg,
6810 struct devlink_fmsg_item *item;
6812 item = kzalloc(sizeof(*item), GFP_KERNEL);
6816 item->attrtype = attrtype;
6817 list_add_tail(&item->list, &fmsg->item_list);
6822 int devlink_fmsg_obj_nest_start(struct devlink_fmsg *fmsg)
6824 if (fmsg->putting_binary)
6827 return devlink_fmsg_nest_common(fmsg, DEVLINK_ATTR_FMSG_OBJ_NEST_START);
6829 EXPORT_SYMBOL_GPL(devlink_fmsg_obj_nest_start);
6831 static int devlink_fmsg_nest_end(struct devlink_fmsg *fmsg)
6833 if (fmsg->putting_binary)
6836 return devlink_fmsg_nest_common(fmsg, DEVLINK_ATTR_FMSG_NEST_END);
6839 int devlink_fmsg_obj_nest_end(struct devlink_fmsg *fmsg)
6841 if (fmsg->putting_binary)
6844 return devlink_fmsg_nest_end(fmsg);
6846 EXPORT_SYMBOL_GPL(devlink_fmsg_obj_nest_end);
6848 #define DEVLINK_FMSG_MAX_SIZE (GENLMSG_DEFAULT_SIZE - GENL_HDRLEN - NLA_HDRLEN)
6850 static int devlink_fmsg_put_name(struct devlink_fmsg *fmsg, const char *name)
6852 struct devlink_fmsg_item *item;
6854 if (fmsg->putting_binary)
6857 if (strlen(name) + 1 > DEVLINK_FMSG_MAX_SIZE)
6860 item = kzalloc(sizeof(*item) + strlen(name) + 1, GFP_KERNEL);
6864 item->nla_type = NLA_NUL_STRING;
6865 item->len = strlen(name) + 1;
6866 item->attrtype = DEVLINK_ATTR_FMSG_OBJ_NAME;
6867 memcpy(&item->value, name, item->len);
6868 list_add_tail(&item->list, &fmsg->item_list);
6873 int devlink_fmsg_pair_nest_start(struct devlink_fmsg *fmsg, const char *name)
6877 if (fmsg->putting_binary)
6880 err = devlink_fmsg_nest_common(fmsg, DEVLINK_ATTR_FMSG_PAIR_NEST_START);
6884 err = devlink_fmsg_put_name(fmsg, name);
6890 EXPORT_SYMBOL_GPL(devlink_fmsg_pair_nest_start);
6892 int devlink_fmsg_pair_nest_end(struct devlink_fmsg *fmsg)
6894 if (fmsg->putting_binary)
6897 return devlink_fmsg_nest_end(fmsg);
6899 EXPORT_SYMBOL_GPL(devlink_fmsg_pair_nest_end);
6901 int devlink_fmsg_arr_pair_nest_start(struct devlink_fmsg *fmsg,
6906 if (fmsg->putting_binary)
6909 err = devlink_fmsg_pair_nest_start(fmsg, name);
6913 err = devlink_fmsg_nest_common(fmsg, DEVLINK_ATTR_FMSG_ARR_NEST_START);
6919 EXPORT_SYMBOL_GPL(devlink_fmsg_arr_pair_nest_start);
6921 int devlink_fmsg_arr_pair_nest_end(struct devlink_fmsg *fmsg)
6925 if (fmsg->putting_binary)
6928 err = devlink_fmsg_nest_end(fmsg);
6932 err = devlink_fmsg_nest_end(fmsg);
6938 EXPORT_SYMBOL_GPL(devlink_fmsg_arr_pair_nest_end);
6940 int devlink_fmsg_binary_pair_nest_start(struct devlink_fmsg *fmsg,
6945 err = devlink_fmsg_arr_pair_nest_start(fmsg, name);
6949 fmsg->putting_binary = true;
6952 EXPORT_SYMBOL_GPL(devlink_fmsg_binary_pair_nest_start);
6954 int devlink_fmsg_binary_pair_nest_end(struct devlink_fmsg *fmsg)
6956 if (!fmsg->putting_binary)
6959 fmsg->putting_binary = false;
6960 return devlink_fmsg_arr_pair_nest_end(fmsg);
6962 EXPORT_SYMBOL_GPL(devlink_fmsg_binary_pair_nest_end);
6964 static int devlink_fmsg_put_value(struct devlink_fmsg *fmsg,
6965 const void *value, u16 value_len,
6968 struct devlink_fmsg_item *item;
6970 if (value_len > DEVLINK_FMSG_MAX_SIZE)
6973 item = kzalloc(sizeof(*item) + value_len, GFP_KERNEL);
6977 item->nla_type = value_nla_type;
6978 item->len = value_len;
6979 item->attrtype = DEVLINK_ATTR_FMSG_OBJ_VALUE_DATA;
6980 memcpy(&item->value, value, item->len);
6981 list_add_tail(&item->list, &fmsg->item_list);
6986 static int devlink_fmsg_bool_put(struct devlink_fmsg *fmsg, bool value)
6988 if (fmsg->putting_binary)
6991 return devlink_fmsg_put_value(fmsg, &value, sizeof(value), NLA_FLAG);
6994 static int devlink_fmsg_u8_put(struct devlink_fmsg *fmsg, u8 value)
6996 if (fmsg->putting_binary)
6999 return devlink_fmsg_put_value(fmsg, &value, sizeof(value), NLA_U8);
7002 int devlink_fmsg_u32_put(struct devlink_fmsg *fmsg, u32 value)
7004 if (fmsg->putting_binary)
7007 return devlink_fmsg_put_value(fmsg, &value, sizeof(value), NLA_U32);
7009 EXPORT_SYMBOL_GPL(devlink_fmsg_u32_put);
7011 static int devlink_fmsg_u64_put(struct devlink_fmsg *fmsg, u64 value)
7013 if (fmsg->putting_binary)
7016 return devlink_fmsg_put_value(fmsg, &value, sizeof(value), NLA_U64);
7019 int devlink_fmsg_string_put(struct devlink_fmsg *fmsg, const char *value)
7021 if (fmsg->putting_binary)
7024 return devlink_fmsg_put_value(fmsg, value, strlen(value) + 1,
7027 EXPORT_SYMBOL_GPL(devlink_fmsg_string_put);
7029 int devlink_fmsg_binary_put(struct devlink_fmsg *fmsg, const void *value,
7032 if (!fmsg->putting_binary)
7035 return devlink_fmsg_put_value(fmsg, value, value_len, NLA_BINARY);
7037 EXPORT_SYMBOL_GPL(devlink_fmsg_binary_put);
7039 int devlink_fmsg_bool_pair_put(struct devlink_fmsg *fmsg, const char *name,
7044 err = devlink_fmsg_pair_nest_start(fmsg, name);
7048 err = devlink_fmsg_bool_put(fmsg, value);
7052 err = devlink_fmsg_pair_nest_end(fmsg);
7058 EXPORT_SYMBOL_GPL(devlink_fmsg_bool_pair_put);
7060 int devlink_fmsg_u8_pair_put(struct devlink_fmsg *fmsg, const char *name,
7065 err = devlink_fmsg_pair_nest_start(fmsg, name);
7069 err = devlink_fmsg_u8_put(fmsg, value);
7073 err = devlink_fmsg_pair_nest_end(fmsg);
7079 EXPORT_SYMBOL_GPL(devlink_fmsg_u8_pair_put);
7081 int devlink_fmsg_u32_pair_put(struct devlink_fmsg *fmsg, const char *name,
7086 err = devlink_fmsg_pair_nest_start(fmsg, name);
7090 err = devlink_fmsg_u32_put(fmsg, value);
7094 err = devlink_fmsg_pair_nest_end(fmsg);
7100 EXPORT_SYMBOL_GPL(devlink_fmsg_u32_pair_put);
7102 int devlink_fmsg_u64_pair_put(struct devlink_fmsg *fmsg, const char *name,
7107 err = devlink_fmsg_pair_nest_start(fmsg, name);
7111 err = devlink_fmsg_u64_put(fmsg, value);
7115 err = devlink_fmsg_pair_nest_end(fmsg);
7121 EXPORT_SYMBOL_GPL(devlink_fmsg_u64_pair_put);
7123 int devlink_fmsg_string_pair_put(struct devlink_fmsg *fmsg, const char *name,
7128 err = devlink_fmsg_pair_nest_start(fmsg, name);
7132 err = devlink_fmsg_string_put(fmsg, value);
7136 err = devlink_fmsg_pair_nest_end(fmsg);
7142 EXPORT_SYMBOL_GPL(devlink_fmsg_string_pair_put);
7144 int devlink_fmsg_binary_pair_put(struct devlink_fmsg *fmsg, const char *name,
7145 const void *value, u32 value_len)
7152 err = devlink_fmsg_binary_pair_nest_start(fmsg, name);
7156 for (offset = 0; offset < value_len; offset += data_size) {
7157 data_size = value_len - offset;
7158 if (data_size > DEVLINK_FMSG_MAX_SIZE)
7159 data_size = DEVLINK_FMSG_MAX_SIZE;
7160 err = devlink_fmsg_binary_put(fmsg, value + offset, data_size);
7163 /* Exit from loop with a break (instead of
7164 * return) to make sure putting_binary is turned off in
7165 * devlink_fmsg_binary_pair_nest_end
7169 end_err = devlink_fmsg_binary_pair_nest_end(fmsg);
7175 EXPORT_SYMBOL_GPL(devlink_fmsg_binary_pair_put);
7178 devlink_fmsg_item_fill_type(struct devlink_fmsg_item *msg, struct sk_buff *skb)
7180 switch (msg->nla_type) {
7185 case NLA_NUL_STRING:
7187 return nla_put_u8(skb, DEVLINK_ATTR_FMSG_OBJ_VALUE_TYPE,
7195 devlink_fmsg_item_fill_data(struct devlink_fmsg_item *msg, struct sk_buff *skb)
7197 int attrtype = DEVLINK_ATTR_FMSG_OBJ_VALUE_DATA;
7200 switch (msg->nla_type) {
7202 /* Always provide flag data, regardless of its value */
7203 tmp = *(bool *) msg->value;
7205 return nla_put_u8(skb, attrtype, tmp);
7207 return nla_put_u8(skb, attrtype, *(u8 *) msg->value);
7209 return nla_put_u32(skb, attrtype, *(u32 *) msg->value);
7211 return nla_put_u64_64bit(skb, attrtype, *(u64 *) msg->value,
7213 case NLA_NUL_STRING:
7214 return nla_put_string(skb, attrtype, (char *) &msg->value);
7216 return nla_put(skb, attrtype, msg->len, (void *) &msg->value);
7223 devlink_fmsg_prepare_skb(struct devlink_fmsg *fmsg, struct sk_buff *skb,
7226 struct devlink_fmsg_item *item;
7227 struct nlattr *fmsg_nlattr;
7231 fmsg_nlattr = nla_nest_start_noflag(skb, DEVLINK_ATTR_FMSG);
7235 list_for_each_entry(item, &fmsg->item_list, list) {
7241 switch (item->attrtype) {
7242 case DEVLINK_ATTR_FMSG_OBJ_NEST_START:
7243 case DEVLINK_ATTR_FMSG_PAIR_NEST_START:
7244 case DEVLINK_ATTR_FMSG_ARR_NEST_START:
7245 case DEVLINK_ATTR_FMSG_NEST_END:
7246 err = nla_put_flag(skb, item->attrtype);
7248 case DEVLINK_ATTR_FMSG_OBJ_VALUE_DATA:
7249 err = devlink_fmsg_item_fill_type(item, skb);
7252 err = devlink_fmsg_item_fill_data(item, skb);
7254 case DEVLINK_ATTR_FMSG_OBJ_NAME:
7255 err = nla_put_string(skb, item->attrtype,
7256 (char *) &item->value);
7268 nla_nest_end(skb, fmsg_nlattr);
7272 static int devlink_fmsg_snd(struct devlink_fmsg *fmsg,
7273 struct genl_info *info,
7274 enum devlink_command cmd, int flags)
7276 struct nlmsghdr *nlh;
7277 struct sk_buff *skb;
7284 int tmp_index = index;
7286 skb = genlmsg_new(GENLMSG_DEFAULT_SIZE, GFP_KERNEL);
7290 hdr = genlmsg_put(skb, info->snd_portid, info->snd_seq,
7291 &devlink_nl_family, flags | NLM_F_MULTI, cmd);
7294 goto nla_put_failure;
7297 err = devlink_fmsg_prepare_skb(fmsg, skb, &index);
7300 else if (err != -EMSGSIZE || tmp_index == index)
7301 goto nla_put_failure;
7303 genlmsg_end(skb, hdr);
7304 err = genlmsg_reply(skb, info);
7309 skb = genlmsg_new(GENLMSG_DEFAULT_SIZE, GFP_KERNEL);
7312 nlh = nlmsg_put(skb, info->snd_portid, info->snd_seq,
7313 NLMSG_DONE, 0, flags | NLM_F_MULTI);
7316 goto nla_put_failure;
7319 return genlmsg_reply(skb, info);
7326 static int devlink_fmsg_dumpit(struct devlink_fmsg *fmsg, struct sk_buff *skb,
7327 struct netlink_callback *cb,
7328 enum devlink_command cmd)
7330 int index = cb->args[0];
7331 int tmp_index = index;
7335 hdr = genlmsg_put(skb, NETLINK_CB(cb->skb).portid, cb->nlh->nlmsg_seq,
7336 &devlink_nl_family, NLM_F_ACK | NLM_F_MULTI, cmd);
7339 goto nla_put_failure;
7342 err = devlink_fmsg_prepare_skb(fmsg, skb, &index);
7343 if ((err && err != -EMSGSIZE) || tmp_index == index)
7344 goto nla_put_failure;
7346 cb->args[0] = index;
7347 genlmsg_end(skb, hdr);
7351 genlmsg_cancel(skb, hdr);
7355 struct devlink_health_reporter {
7356 struct list_head list;
7358 const struct devlink_health_reporter_ops *ops;
7359 struct devlink *devlink;
7360 struct devlink_port *devlink_port;
7361 struct devlink_fmsg *dump_fmsg;
7362 struct mutex dump_lock; /* lock parallel read/write from dump buffers */
7363 u64 graceful_period;
7371 u64 last_recovery_ts;
7372 refcount_t refcount;
7376 devlink_health_reporter_priv(struct devlink_health_reporter *reporter)
7378 return reporter->priv;
7380 EXPORT_SYMBOL_GPL(devlink_health_reporter_priv);
7382 static struct devlink_health_reporter *
7383 __devlink_health_reporter_find_by_name(struct list_head *reporter_list,
7384 struct mutex *list_lock,
7385 const char *reporter_name)
7387 struct devlink_health_reporter *reporter;
7389 lockdep_assert_held(list_lock);
7390 list_for_each_entry(reporter, reporter_list, list)
7391 if (!strcmp(reporter->ops->name, reporter_name))
7396 static struct devlink_health_reporter *
7397 devlink_health_reporter_find_by_name(struct devlink *devlink,
7398 const char *reporter_name)
7400 return __devlink_health_reporter_find_by_name(&devlink->reporter_list,
7401 &devlink->reporters_lock,
7405 static struct devlink_health_reporter *
7406 devlink_port_health_reporter_find_by_name(struct devlink_port *devlink_port,
7407 const char *reporter_name)
7409 return __devlink_health_reporter_find_by_name(&devlink_port->reporter_list,
7410 &devlink_port->reporters_lock,
7414 static struct devlink_health_reporter *
7415 __devlink_health_reporter_create(struct devlink *devlink,
7416 const struct devlink_health_reporter_ops *ops,
7417 u64 graceful_period, void *priv)
7419 struct devlink_health_reporter *reporter;
7421 if (WARN_ON(graceful_period && !ops->recover))
7422 return ERR_PTR(-EINVAL);
7424 reporter = kzalloc(sizeof(*reporter), GFP_KERNEL);
7426 return ERR_PTR(-ENOMEM);
7428 reporter->priv = priv;
7429 reporter->ops = ops;
7430 reporter->devlink = devlink;
7431 reporter->graceful_period = graceful_period;
7432 reporter->auto_recover = !!ops->recover;
7433 reporter->auto_dump = !!ops->dump;
7434 mutex_init(&reporter->dump_lock);
7435 refcount_set(&reporter->refcount, 1);
7440 * devlink_port_health_reporter_create - create devlink health reporter for
7441 * specified port instance
7443 * @port: devlink_port which should contain the new reporter
7445 * @graceful_period: to avoid recovery loops, in msecs
7448 struct devlink_health_reporter *
7449 devlink_port_health_reporter_create(struct devlink_port *port,
7450 const struct devlink_health_reporter_ops *ops,
7451 u64 graceful_period, void *priv)
7453 struct devlink_health_reporter *reporter;
7455 mutex_lock(&port->reporters_lock);
7456 if (__devlink_health_reporter_find_by_name(&port->reporter_list,
7457 &port->reporters_lock, ops->name)) {
7458 reporter = ERR_PTR(-EEXIST);
7462 reporter = __devlink_health_reporter_create(port->devlink, ops,
7463 graceful_period, priv);
7464 if (IS_ERR(reporter))
7467 reporter->devlink_port = port;
7468 list_add_tail(&reporter->list, &port->reporter_list);
7470 mutex_unlock(&port->reporters_lock);
7473 EXPORT_SYMBOL_GPL(devlink_port_health_reporter_create);
7476 * devlink_health_reporter_create - create devlink health reporter
7480 * @graceful_period: to avoid recovery loops, in msecs
7483 struct devlink_health_reporter *
7484 devlink_health_reporter_create(struct devlink *devlink,
7485 const struct devlink_health_reporter_ops *ops,
7486 u64 graceful_period, void *priv)
7488 struct devlink_health_reporter *reporter;
7490 mutex_lock(&devlink->reporters_lock);
7491 if (devlink_health_reporter_find_by_name(devlink, ops->name)) {
7492 reporter = ERR_PTR(-EEXIST);
7496 reporter = __devlink_health_reporter_create(devlink, ops,
7497 graceful_period, priv);
7498 if (IS_ERR(reporter))
7501 list_add_tail(&reporter->list, &devlink->reporter_list);
7503 mutex_unlock(&devlink->reporters_lock);
7506 EXPORT_SYMBOL_GPL(devlink_health_reporter_create);
7509 devlink_health_reporter_free(struct devlink_health_reporter *reporter)
7511 mutex_destroy(&reporter->dump_lock);
7512 if (reporter->dump_fmsg)
7513 devlink_fmsg_free(reporter->dump_fmsg);
7518 devlink_health_reporter_put(struct devlink_health_reporter *reporter)
7520 if (refcount_dec_and_test(&reporter->refcount))
7521 devlink_health_reporter_free(reporter);
7525 __devlink_health_reporter_destroy(struct devlink_health_reporter *reporter)
7527 list_del(&reporter->list);
7528 devlink_health_reporter_put(reporter);
7532 * devlink_health_reporter_destroy - destroy devlink health reporter
7534 * @reporter: devlink health reporter to destroy
7537 devlink_health_reporter_destroy(struct devlink_health_reporter *reporter)
7539 struct mutex *lock = &reporter->devlink->reporters_lock;
7542 __devlink_health_reporter_destroy(reporter);
7545 EXPORT_SYMBOL_GPL(devlink_health_reporter_destroy);
7548 * devlink_port_health_reporter_destroy - destroy devlink port health reporter
7550 * @reporter: devlink health reporter to destroy
7553 devlink_port_health_reporter_destroy(struct devlink_health_reporter *reporter)
7555 struct mutex *lock = &reporter->devlink_port->reporters_lock;
7558 __devlink_health_reporter_destroy(reporter);
7561 EXPORT_SYMBOL_GPL(devlink_port_health_reporter_destroy);
7564 devlink_nl_health_reporter_fill(struct sk_buff *msg,
7565 struct devlink_health_reporter *reporter,
7566 enum devlink_command cmd, u32 portid,
7569 struct devlink *devlink = reporter->devlink;
7570 struct nlattr *reporter_attr;
7573 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
7577 if (devlink_nl_put_handle(msg, devlink))
7578 goto genlmsg_cancel;
7580 if (reporter->devlink_port) {
7581 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_INDEX, reporter->devlink_port->index))
7582 goto genlmsg_cancel;
7584 reporter_attr = nla_nest_start_noflag(msg,
7585 DEVLINK_ATTR_HEALTH_REPORTER);
7587 goto genlmsg_cancel;
7588 if (nla_put_string(msg, DEVLINK_ATTR_HEALTH_REPORTER_NAME,
7589 reporter->ops->name))
7590 goto reporter_nest_cancel;
7591 if (nla_put_u8(msg, DEVLINK_ATTR_HEALTH_REPORTER_STATE,
7592 reporter->health_state))
7593 goto reporter_nest_cancel;
7594 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_HEALTH_REPORTER_ERR_COUNT,
7595 reporter->error_count, DEVLINK_ATTR_PAD))
7596 goto reporter_nest_cancel;
7597 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_HEALTH_REPORTER_RECOVER_COUNT,
7598 reporter->recovery_count, DEVLINK_ATTR_PAD))
7599 goto reporter_nest_cancel;
7600 if (reporter->ops->recover &&
7601 nla_put_u64_64bit(msg, DEVLINK_ATTR_HEALTH_REPORTER_GRACEFUL_PERIOD,
7602 reporter->graceful_period,
7604 goto reporter_nest_cancel;
7605 if (reporter->ops->recover &&
7606 nla_put_u8(msg, DEVLINK_ATTR_HEALTH_REPORTER_AUTO_RECOVER,
7607 reporter->auto_recover))
7608 goto reporter_nest_cancel;
7609 if (reporter->dump_fmsg &&
7610 nla_put_u64_64bit(msg, DEVLINK_ATTR_HEALTH_REPORTER_DUMP_TS,
7611 jiffies_to_msecs(reporter->dump_ts),
7613 goto reporter_nest_cancel;
7614 if (reporter->dump_fmsg &&
7615 nla_put_u64_64bit(msg, DEVLINK_ATTR_HEALTH_REPORTER_DUMP_TS_NS,
7616 reporter->dump_real_ts, DEVLINK_ATTR_PAD))
7617 goto reporter_nest_cancel;
7618 if (reporter->ops->dump &&
7619 nla_put_u8(msg, DEVLINK_ATTR_HEALTH_REPORTER_AUTO_DUMP,
7620 reporter->auto_dump))
7621 goto reporter_nest_cancel;
7623 nla_nest_end(msg, reporter_attr);
7624 genlmsg_end(msg, hdr);
7627 reporter_nest_cancel:
7628 nla_nest_end(msg, reporter_attr);
7630 genlmsg_cancel(msg, hdr);
7634 static void devlink_recover_notify(struct devlink_health_reporter *reporter,
7635 enum devlink_command cmd)
7637 struct devlink *devlink = reporter->devlink;
7638 struct sk_buff *msg;
7641 WARN_ON(cmd != DEVLINK_CMD_HEALTH_REPORTER_RECOVER);
7642 WARN_ON(!xa_get_mark(&devlinks, devlink->index, DEVLINK_REGISTERED));
7644 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
7648 err = devlink_nl_health_reporter_fill(msg, reporter, cmd, 0, 0, 0);
7654 genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink), msg,
7655 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
7659 devlink_health_reporter_recovery_done(struct devlink_health_reporter *reporter)
7661 reporter->recovery_count++;
7662 reporter->last_recovery_ts = jiffies;
7664 EXPORT_SYMBOL_GPL(devlink_health_reporter_recovery_done);
7667 devlink_health_reporter_recover(struct devlink_health_reporter *reporter,
7668 void *priv_ctx, struct netlink_ext_ack *extack)
7672 if (reporter->health_state == DEVLINK_HEALTH_REPORTER_STATE_HEALTHY)
7675 if (!reporter->ops->recover)
7678 err = reporter->ops->recover(reporter, priv_ctx, extack);
7682 devlink_health_reporter_recovery_done(reporter);
7683 reporter->health_state = DEVLINK_HEALTH_REPORTER_STATE_HEALTHY;
7684 devlink_recover_notify(reporter, DEVLINK_CMD_HEALTH_REPORTER_RECOVER);
7690 devlink_health_dump_clear(struct devlink_health_reporter *reporter)
7692 if (!reporter->dump_fmsg)
7694 devlink_fmsg_free(reporter->dump_fmsg);
7695 reporter->dump_fmsg = NULL;
7698 static int devlink_health_do_dump(struct devlink_health_reporter *reporter,
7700 struct netlink_ext_ack *extack)
7704 if (!reporter->ops->dump)
7707 if (reporter->dump_fmsg)
7710 reporter->dump_fmsg = devlink_fmsg_alloc();
7711 if (!reporter->dump_fmsg) {
7716 err = devlink_fmsg_obj_nest_start(reporter->dump_fmsg);
7720 err = reporter->ops->dump(reporter, reporter->dump_fmsg,
7725 err = devlink_fmsg_obj_nest_end(reporter->dump_fmsg);
7729 reporter->dump_ts = jiffies;
7730 reporter->dump_real_ts = ktime_get_real_ns();
7735 devlink_health_dump_clear(reporter);
7739 int devlink_health_report(struct devlink_health_reporter *reporter,
7740 const char *msg, void *priv_ctx)
7742 enum devlink_health_reporter_state prev_health_state;
7743 struct devlink *devlink = reporter->devlink;
7744 unsigned long recover_ts_threshold;
7747 /* write a log message of the current error */
7749 trace_devlink_health_report(devlink, reporter->ops->name, msg);
7750 reporter->error_count++;
7751 prev_health_state = reporter->health_state;
7752 reporter->health_state = DEVLINK_HEALTH_REPORTER_STATE_ERROR;
7753 devlink_recover_notify(reporter, DEVLINK_CMD_HEALTH_REPORTER_RECOVER);
7755 /* abort if the previous error wasn't recovered */
7756 recover_ts_threshold = reporter->last_recovery_ts +
7757 msecs_to_jiffies(reporter->graceful_period);
7758 if (reporter->auto_recover &&
7759 (prev_health_state != DEVLINK_HEALTH_REPORTER_STATE_HEALTHY ||
7760 (reporter->last_recovery_ts && reporter->recovery_count &&
7761 time_is_after_jiffies(recover_ts_threshold)))) {
7762 trace_devlink_health_recover_aborted(devlink,
7763 reporter->ops->name,
7764 reporter->health_state,
7766 reporter->last_recovery_ts);
7770 reporter->health_state = DEVLINK_HEALTH_REPORTER_STATE_ERROR;
7772 if (reporter->auto_dump) {
7773 mutex_lock(&reporter->dump_lock);
7774 /* store current dump of current error, for later analysis */
7775 devlink_health_do_dump(reporter, priv_ctx, NULL);
7776 mutex_unlock(&reporter->dump_lock);
7779 if (!reporter->auto_recover)
7783 ret = devlink_health_reporter_recover(reporter, priv_ctx, NULL);
7784 devl_unlock(devlink);
7788 EXPORT_SYMBOL_GPL(devlink_health_report);
7790 static struct devlink_health_reporter *
7791 devlink_health_reporter_get_from_attrs(struct devlink *devlink,
7792 struct nlattr **attrs)
7794 struct devlink_health_reporter *reporter;
7795 struct devlink_port *devlink_port;
7796 char *reporter_name;
7798 if (!attrs[DEVLINK_ATTR_HEALTH_REPORTER_NAME])
7801 reporter_name = nla_data(attrs[DEVLINK_ATTR_HEALTH_REPORTER_NAME]);
7802 devlink_port = devlink_port_get_from_attrs(devlink, attrs);
7803 if (IS_ERR(devlink_port)) {
7804 mutex_lock(&devlink->reporters_lock);
7805 reporter = devlink_health_reporter_find_by_name(devlink, reporter_name);
7807 refcount_inc(&reporter->refcount);
7808 mutex_unlock(&devlink->reporters_lock);
7810 mutex_lock(&devlink_port->reporters_lock);
7811 reporter = devlink_port_health_reporter_find_by_name(devlink_port, reporter_name);
7813 refcount_inc(&reporter->refcount);
7814 mutex_unlock(&devlink_port->reporters_lock);
7820 static struct devlink_health_reporter *
7821 devlink_health_reporter_get_from_info(struct devlink *devlink,
7822 struct genl_info *info)
7824 return devlink_health_reporter_get_from_attrs(devlink, info->attrs);
7827 static struct devlink_health_reporter *
7828 devlink_health_reporter_get_from_cb(struct netlink_callback *cb)
7830 const struct genl_dumpit_info *info = genl_dumpit_info(cb);
7831 struct devlink_health_reporter *reporter;
7832 struct nlattr **attrs = info->attrs;
7833 struct devlink *devlink;
7835 devlink = devlink_get_from_attrs(sock_net(cb->skb->sk), attrs);
7836 if (IS_ERR(devlink))
7839 reporter = devlink_health_reporter_get_from_attrs(devlink, attrs);
7840 devlink_put(devlink);
7845 devlink_health_reporter_state_update(struct devlink_health_reporter *reporter,
7846 enum devlink_health_reporter_state state)
7848 if (WARN_ON(state != DEVLINK_HEALTH_REPORTER_STATE_HEALTHY &&
7849 state != DEVLINK_HEALTH_REPORTER_STATE_ERROR))
7852 if (reporter->health_state == state)
7855 reporter->health_state = state;
7856 trace_devlink_health_reporter_state_update(reporter->devlink,
7857 reporter->ops->name, state);
7858 devlink_recover_notify(reporter, DEVLINK_CMD_HEALTH_REPORTER_RECOVER);
7860 EXPORT_SYMBOL_GPL(devlink_health_reporter_state_update);
7862 static int devlink_nl_cmd_health_reporter_get_doit(struct sk_buff *skb,
7863 struct genl_info *info)
7865 struct devlink *devlink = info->user_ptr[0];
7866 struct devlink_health_reporter *reporter;
7867 struct sk_buff *msg;
7870 reporter = devlink_health_reporter_get_from_info(devlink, info);
7874 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
7880 err = devlink_nl_health_reporter_fill(msg, reporter,
7881 DEVLINK_CMD_HEALTH_REPORTER_GET,
7882 info->snd_portid, info->snd_seq,
7889 err = genlmsg_reply(msg, info);
7891 devlink_health_reporter_put(reporter);
7896 devlink_nl_cmd_health_reporter_get_dumpit(struct sk_buff *msg,
7897 struct netlink_callback *cb)
7899 struct devlink_health_reporter *reporter;
7900 struct devlink_port *port;
7901 struct devlink *devlink;
7902 int start = cb->args[0];
7903 unsigned long index;
7907 devlinks_xa_for_each_registered_get(sock_net(msg->sk), index, devlink) {
7908 mutex_lock(&devlink->reporters_lock);
7909 list_for_each_entry(reporter, &devlink->reporter_list,
7915 err = devlink_nl_health_reporter_fill(
7916 msg, reporter, DEVLINK_CMD_HEALTH_REPORTER_GET,
7917 NETLINK_CB(cb->skb).portid, cb->nlh->nlmsg_seq,
7920 mutex_unlock(&devlink->reporters_lock);
7921 devlink_put(devlink);
7926 mutex_unlock(&devlink->reporters_lock);
7927 devlink_put(devlink);
7930 devlinks_xa_for_each_registered_get(sock_net(msg->sk), index, devlink) {
7932 list_for_each_entry(port, &devlink->port_list, list) {
7933 mutex_lock(&port->reporters_lock);
7934 list_for_each_entry(reporter, &port->reporter_list, list) {
7939 err = devlink_nl_health_reporter_fill(
7941 DEVLINK_CMD_HEALTH_REPORTER_GET,
7942 NETLINK_CB(cb->skb).portid,
7943 cb->nlh->nlmsg_seq, NLM_F_MULTI);
7945 mutex_unlock(&port->reporters_lock);
7946 devl_unlock(devlink);
7947 devlink_put(devlink);
7952 mutex_unlock(&port->reporters_lock);
7954 devl_unlock(devlink);
7955 devlink_put(devlink);
7963 devlink_nl_cmd_health_reporter_set_doit(struct sk_buff *skb,
7964 struct genl_info *info)
7966 struct devlink *devlink = info->user_ptr[0];
7967 struct devlink_health_reporter *reporter;
7970 reporter = devlink_health_reporter_get_from_info(devlink, info);
7974 if (!reporter->ops->recover &&
7975 (info->attrs[DEVLINK_ATTR_HEALTH_REPORTER_GRACEFUL_PERIOD] ||
7976 info->attrs[DEVLINK_ATTR_HEALTH_REPORTER_AUTO_RECOVER])) {
7980 if (!reporter->ops->dump &&
7981 info->attrs[DEVLINK_ATTR_HEALTH_REPORTER_AUTO_DUMP]) {
7986 if (info->attrs[DEVLINK_ATTR_HEALTH_REPORTER_GRACEFUL_PERIOD])
7987 reporter->graceful_period =
7988 nla_get_u64(info->attrs[DEVLINK_ATTR_HEALTH_REPORTER_GRACEFUL_PERIOD]);
7990 if (info->attrs[DEVLINK_ATTR_HEALTH_REPORTER_AUTO_RECOVER])
7991 reporter->auto_recover =
7992 nla_get_u8(info->attrs[DEVLINK_ATTR_HEALTH_REPORTER_AUTO_RECOVER]);
7994 if (info->attrs[DEVLINK_ATTR_HEALTH_REPORTER_AUTO_DUMP])
7995 reporter->auto_dump =
7996 nla_get_u8(info->attrs[DEVLINK_ATTR_HEALTH_REPORTER_AUTO_DUMP]);
7998 devlink_health_reporter_put(reporter);
8001 devlink_health_reporter_put(reporter);
8005 static int devlink_nl_cmd_health_reporter_recover_doit(struct sk_buff *skb,
8006 struct genl_info *info)
8008 struct devlink *devlink = info->user_ptr[0];
8009 struct devlink_health_reporter *reporter;
8012 reporter = devlink_health_reporter_get_from_info(devlink, info);
8016 err = devlink_health_reporter_recover(reporter, NULL, info->extack);
8018 devlink_health_reporter_put(reporter);
8022 static int devlink_nl_cmd_health_reporter_diagnose_doit(struct sk_buff *skb,
8023 struct genl_info *info)
8025 struct devlink *devlink = info->user_ptr[0];
8026 struct devlink_health_reporter *reporter;
8027 struct devlink_fmsg *fmsg;
8030 reporter = devlink_health_reporter_get_from_info(devlink, info);
8034 if (!reporter->ops->diagnose) {
8035 devlink_health_reporter_put(reporter);
8039 fmsg = devlink_fmsg_alloc();
8041 devlink_health_reporter_put(reporter);
8045 err = devlink_fmsg_obj_nest_start(fmsg);
8049 err = reporter->ops->diagnose(reporter, fmsg, info->extack);
8053 err = devlink_fmsg_obj_nest_end(fmsg);
8057 err = devlink_fmsg_snd(fmsg, info,
8058 DEVLINK_CMD_HEALTH_REPORTER_DIAGNOSE, 0);
8061 devlink_fmsg_free(fmsg);
8062 devlink_health_reporter_put(reporter);
8067 devlink_nl_cmd_health_reporter_dump_get_dumpit(struct sk_buff *skb,
8068 struct netlink_callback *cb)
8070 struct devlink_health_reporter *reporter;
8071 u64 start = cb->args[0];
8074 reporter = devlink_health_reporter_get_from_cb(cb);
8078 if (!reporter->ops->dump) {
8082 mutex_lock(&reporter->dump_lock);
8084 err = devlink_health_do_dump(reporter, NULL, cb->extack);
8087 cb->args[1] = reporter->dump_ts;
8089 if (!reporter->dump_fmsg || cb->args[1] != reporter->dump_ts) {
8090 NL_SET_ERR_MSG_MOD(cb->extack, "Dump trampled, please retry");
8095 err = devlink_fmsg_dumpit(reporter->dump_fmsg, skb, cb,
8096 DEVLINK_CMD_HEALTH_REPORTER_DUMP_GET);
8098 mutex_unlock(&reporter->dump_lock);
8100 devlink_health_reporter_put(reporter);
8105 devlink_nl_cmd_health_reporter_dump_clear_doit(struct sk_buff *skb,
8106 struct genl_info *info)
8108 struct devlink *devlink = info->user_ptr[0];
8109 struct devlink_health_reporter *reporter;
8111 reporter = devlink_health_reporter_get_from_info(devlink, info);
8115 if (!reporter->ops->dump) {
8116 devlink_health_reporter_put(reporter);
8120 mutex_lock(&reporter->dump_lock);
8121 devlink_health_dump_clear(reporter);
8122 mutex_unlock(&reporter->dump_lock);
8123 devlink_health_reporter_put(reporter);
8127 static int devlink_nl_cmd_health_reporter_test_doit(struct sk_buff *skb,
8128 struct genl_info *info)
8130 struct devlink *devlink = info->user_ptr[0];
8131 struct devlink_health_reporter *reporter;
8134 reporter = devlink_health_reporter_get_from_info(devlink, info);
8138 if (!reporter->ops->test) {
8139 devlink_health_reporter_put(reporter);
8143 err = reporter->ops->test(reporter, info->extack);
8145 devlink_health_reporter_put(reporter);
8149 struct devlink_stats {
8150 u64_stats_t rx_bytes;
8151 u64_stats_t rx_packets;
8152 struct u64_stats_sync syncp;
8156 * struct devlink_trap_policer_item - Packet trap policer attributes.
8157 * @policer: Immutable packet trap policer attributes.
8158 * @rate: Rate in packets / sec.
8159 * @burst: Burst size in packets.
8160 * @list: trap_policer_list member.
8162 * Describes packet trap policer attributes. Created by devlink during trap
8163 * policer registration.
8165 struct devlink_trap_policer_item {
8166 const struct devlink_trap_policer *policer;
8169 struct list_head list;
8173 * struct devlink_trap_group_item - Packet trap group attributes.
8174 * @group: Immutable packet trap group attributes.
8175 * @policer_item: Associated policer item. Can be NULL.
8176 * @list: trap_group_list member.
8177 * @stats: Trap group statistics.
8179 * Describes packet trap group attributes. Created by devlink during trap
8180 * group registration.
8182 struct devlink_trap_group_item {
8183 const struct devlink_trap_group *group;
8184 struct devlink_trap_policer_item *policer_item;
8185 struct list_head list;
8186 struct devlink_stats __percpu *stats;
8190 * struct devlink_trap_item - Packet trap attributes.
8191 * @trap: Immutable packet trap attributes.
8192 * @group_item: Associated group item.
8193 * @list: trap_list member.
8194 * @action: Trap action.
8195 * @stats: Trap statistics.
8196 * @priv: Driver private information.
8198 * Describes both mutable and immutable packet trap attributes. Created by
8199 * devlink during trap registration and used for all trap related operations.
8201 struct devlink_trap_item {
8202 const struct devlink_trap *trap;
8203 struct devlink_trap_group_item *group_item;
8204 struct list_head list;
8205 enum devlink_trap_action action;
8206 struct devlink_stats __percpu *stats;
8210 static struct devlink_trap_policer_item *
8211 devlink_trap_policer_item_lookup(struct devlink *devlink, u32 id)
8213 struct devlink_trap_policer_item *policer_item;
8215 list_for_each_entry(policer_item, &devlink->trap_policer_list, list) {
8216 if (policer_item->policer->id == id)
8217 return policer_item;
8223 static struct devlink_trap_item *
8224 devlink_trap_item_lookup(struct devlink *devlink, const char *name)
8226 struct devlink_trap_item *trap_item;
8228 list_for_each_entry(trap_item, &devlink->trap_list, list) {
8229 if (!strcmp(trap_item->trap->name, name))
8236 static struct devlink_trap_item *
8237 devlink_trap_item_get_from_info(struct devlink *devlink,
8238 struct genl_info *info)
8240 struct nlattr *attr;
8242 if (!info->attrs[DEVLINK_ATTR_TRAP_NAME])
8244 attr = info->attrs[DEVLINK_ATTR_TRAP_NAME];
8246 return devlink_trap_item_lookup(devlink, nla_data(attr));
8250 devlink_trap_action_get_from_info(struct genl_info *info,
8251 enum devlink_trap_action *p_trap_action)
8255 val = nla_get_u8(info->attrs[DEVLINK_ATTR_TRAP_ACTION]);
8257 case DEVLINK_TRAP_ACTION_DROP:
8258 case DEVLINK_TRAP_ACTION_TRAP:
8259 case DEVLINK_TRAP_ACTION_MIRROR:
8260 *p_trap_action = val;
8269 static int devlink_trap_metadata_put(struct sk_buff *msg,
8270 const struct devlink_trap *trap)
8272 struct nlattr *attr;
8274 attr = nla_nest_start(msg, DEVLINK_ATTR_TRAP_METADATA);
8278 if ((trap->metadata_cap & DEVLINK_TRAP_METADATA_TYPE_F_IN_PORT) &&
8279 nla_put_flag(msg, DEVLINK_ATTR_TRAP_METADATA_TYPE_IN_PORT))
8280 goto nla_put_failure;
8281 if ((trap->metadata_cap & DEVLINK_TRAP_METADATA_TYPE_F_FA_COOKIE) &&
8282 nla_put_flag(msg, DEVLINK_ATTR_TRAP_METADATA_TYPE_FA_COOKIE))
8283 goto nla_put_failure;
8285 nla_nest_end(msg, attr);
8290 nla_nest_cancel(msg, attr);
8294 static void devlink_trap_stats_read(struct devlink_stats __percpu *trap_stats,
8295 struct devlink_stats *stats)
8299 memset(stats, 0, sizeof(*stats));
8300 for_each_possible_cpu(i) {
8301 struct devlink_stats *cpu_stats;
8302 u64 rx_packets, rx_bytes;
8305 cpu_stats = per_cpu_ptr(trap_stats, i);
8307 start = u64_stats_fetch_begin_irq(&cpu_stats->syncp);
8308 rx_packets = u64_stats_read(&cpu_stats->rx_packets);
8309 rx_bytes = u64_stats_read(&cpu_stats->rx_bytes);
8310 } while (u64_stats_fetch_retry_irq(&cpu_stats->syncp, start));
8312 u64_stats_add(&stats->rx_packets, rx_packets);
8313 u64_stats_add(&stats->rx_bytes, rx_bytes);
8318 devlink_trap_group_stats_put(struct sk_buff *msg,
8319 struct devlink_stats __percpu *trap_stats)
8321 struct devlink_stats stats;
8322 struct nlattr *attr;
8324 devlink_trap_stats_read(trap_stats, &stats);
8326 attr = nla_nest_start(msg, DEVLINK_ATTR_STATS);
8330 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_STATS_RX_PACKETS,
8331 u64_stats_read(&stats.rx_packets),
8333 goto nla_put_failure;
8335 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_STATS_RX_BYTES,
8336 u64_stats_read(&stats.rx_bytes),
8338 goto nla_put_failure;
8340 nla_nest_end(msg, attr);
8345 nla_nest_cancel(msg, attr);
8349 static int devlink_trap_stats_put(struct sk_buff *msg, struct devlink *devlink,
8350 const struct devlink_trap_item *trap_item)
8352 struct devlink_stats stats;
8353 struct nlattr *attr;
8357 if (devlink->ops->trap_drop_counter_get) {
8358 err = devlink->ops->trap_drop_counter_get(devlink,
8365 devlink_trap_stats_read(trap_item->stats, &stats);
8367 attr = nla_nest_start(msg, DEVLINK_ATTR_STATS);
8371 if (devlink->ops->trap_drop_counter_get &&
8372 nla_put_u64_64bit(msg, DEVLINK_ATTR_STATS_RX_DROPPED, drops,
8374 goto nla_put_failure;
8376 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_STATS_RX_PACKETS,
8377 u64_stats_read(&stats.rx_packets),
8379 goto nla_put_failure;
8381 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_STATS_RX_BYTES,
8382 u64_stats_read(&stats.rx_bytes),
8384 goto nla_put_failure;
8386 nla_nest_end(msg, attr);
8391 nla_nest_cancel(msg, attr);
8395 static int devlink_nl_trap_fill(struct sk_buff *msg, struct devlink *devlink,
8396 const struct devlink_trap_item *trap_item,
8397 enum devlink_command cmd, u32 portid, u32 seq,
8400 struct devlink_trap_group_item *group_item = trap_item->group_item;
8404 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
8408 if (devlink_nl_put_handle(msg, devlink))
8409 goto nla_put_failure;
8411 if (nla_put_string(msg, DEVLINK_ATTR_TRAP_GROUP_NAME,
8412 group_item->group->name))
8413 goto nla_put_failure;
8415 if (nla_put_string(msg, DEVLINK_ATTR_TRAP_NAME, trap_item->trap->name))
8416 goto nla_put_failure;
8418 if (nla_put_u8(msg, DEVLINK_ATTR_TRAP_TYPE, trap_item->trap->type))
8419 goto nla_put_failure;
8421 if (trap_item->trap->generic &&
8422 nla_put_flag(msg, DEVLINK_ATTR_TRAP_GENERIC))
8423 goto nla_put_failure;
8425 if (nla_put_u8(msg, DEVLINK_ATTR_TRAP_ACTION, trap_item->action))
8426 goto nla_put_failure;
8428 err = devlink_trap_metadata_put(msg, trap_item->trap);
8430 goto nla_put_failure;
8432 err = devlink_trap_stats_put(msg, devlink, trap_item);
8434 goto nla_put_failure;
8436 genlmsg_end(msg, hdr);
8441 genlmsg_cancel(msg, hdr);
8445 static int devlink_nl_cmd_trap_get_doit(struct sk_buff *skb,
8446 struct genl_info *info)
8448 struct netlink_ext_ack *extack = info->extack;
8449 struct devlink *devlink = info->user_ptr[0];
8450 struct devlink_trap_item *trap_item;
8451 struct sk_buff *msg;
8454 if (list_empty(&devlink->trap_list))
8457 trap_item = devlink_trap_item_get_from_info(devlink, info);
8459 NL_SET_ERR_MSG_MOD(extack, "Device did not register this trap");
8463 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
8467 err = devlink_nl_trap_fill(msg, devlink, trap_item,
8468 DEVLINK_CMD_TRAP_NEW, info->snd_portid,
8473 return genlmsg_reply(msg, info);
8480 static int devlink_nl_cmd_trap_get_dumpit(struct sk_buff *msg,
8481 struct netlink_callback *cb)
8483 struct devlink_trap_item *trap_item;
8484 struct devlink *devlink;
8485 int start = cb->args[0];
8486 unsigned long index;
8490 devlinks_xa_for_each_registered_get(sock_net(msg->sk), index, devlink) {
8492 list_for_each_entry(trap_item, &devlink->trap_list, list) {
8497 err = devlink_nl_trap_fill(msg, devlink, trap_item,
8498 DEVLINK_CMD_TRAP_NEW,
8499 NETLINK_CB(cb->skb).portid,
8503 devl_unlock(devlink);
8504 devlink_put(devlink);
8509 devl_unlock(devlink);
8510 devlink_put(devlink);
8517 static int __devlink_trap_action_set(struct devlink *devlink,
8518 struct devlink_trap_item *trap_item,
8519 enum devlink_trap_action trap_action,
8520 struct netlink_ext_ack *extack)
8524 if (trap_item->action != trap_action &&
8525 trap_item->trap->type != DEVLINK_TRAP_TYPE_DROP) {
8526 NL_SET_ERR_MSG_MOD(extack, "Cannot change action of non-drop traps. Skipping");
8530 err = devlink->ops->trap_action_set(devlink, trap_item->trap,
8531 trap_action, extack);
8535 trap_item->action = trap_action;
8540 static int devlink_trap_action_set(struct devlink *devlink,
8541 struct devlink_trap_item *trap_item,
8542 struct genl_info *info)
8544 enum devlink_trap_action trap_action;
8547 if (!info->attrs[DEVLINK_ATTR_TRAP_ACTION])
8550 err = devlink_trap_action_get_from_info(info, &trap_action);
8552 NL_SET_ERR_MSG_MOD(info->extack, "Invalid trap action");
8556 return __devlink_trap_action_set(devlink, trap_item, trap_action,
8560 static int devlink_nl_cmd_trap_set_doit(struct sk_buff *skb,
8561 struct genl_info *info)
8563 struct netlink_ext_ack *extack = info->extack;
8564 struct devlink *devlink = info->user_ptr[0];
8565 struct devlink_trap_item *trap_item;
8567 if (list_empty(&devlink->trap_list))
8570 trap_item = devlink_trap_item_get_from_info(devlink, info);
8572 NL_SET_ERR_MSG_MOD(extack, "Device did not register this trap");
8576 return devlink_trap_action_set(devlink, trap_item, info);
8579 static struct devlink_trap_group_item *
8580 devlink_trap_group_item_lookup(struct devlink *devlink, const char *name)
8582 struct devlink_trap_group_item *group_item;
8584 list_for_each_entry(group_item, &devlink->trap_group_list, list) {
8585 if (!strcmp(group_item->group->name, name))
8592 static struct devlink_trap_group_item *
8593 devlink_trap_group_item_lookup_by_id(struct devlink *devlink, u16 id)
8595 struct devlink_trap_group_item *group_item;
8597 list_for_each_entry(group_item, &devlink->trap_group_list, list) {
8598 if (group_item->group->id == id)
8605 static struct devlink_trap_group_item *
8606 devlink_trap_group_item_get_from_info(struct devlink *devlink,
8607 struct genl_info *info)
8611 if (!info->attrs[DEVLINK_ATTR_TRAP_GROUP_NAME])
8613 name = nla_data(info->attrs[DEVLINK_ATTR_TRAP_GROUP_NAME]);
8615 return devlink_trap_group_item_lookup(devlink, name);
8619 devlink_nl_trap_group_fill(struct sk_buff *msg, struct devlink *devlink,
8620 const struct devlink_trap_group_item *group_item,
8621 enum devlink_command cmd, u32 portid, u32 seq,
8627 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
8631 if (devlink_nl_put_handle(msg, devlink))
8632 goto nla_put_failure;
8634 if (nla_put_string(msg, DEVLINK_ATTR_TRAP_GROUP_NAME,
8635 group_item->group->name))
8636 goto nla_put_failure;
8638 if (group_item->group->generic &&
8639 nla_put_flag(msg, DEVLINK_ATTR_TRAP_GENERIC))
8640 goto nla_put_failure;
8642 if (group_item->policer_item &&
8643 nla_put_u32(msg, DEVLINK_ATTR_TRAP_POLICER_ID,
8644 group_item->policer_item->policer->id))
8645 goto nla_put_failure;
8647 err = devlink_trap_group_stats_put(msg, group_item->stats);
8649 goto nla_put_failure;
8651 genlmsg_end(msg, hdr);
8656 genlmsg_cancel(msg, hdr);
8660 static int devlink_nl_cmd_trap_group_get_doit(struct sk_buff *skb,
8661 struct genl_info *info)
8663 struct netlink_ext_ack *extack = info->extack;
8664 struct devlink *devlink = info->user_ptr[0];
8665 struct devlink_trap_group_item *group_item;
8666 struct sk_buff *msg;
8669 if (list_empty(&devlink->trap_group_list))
8672 group_item = devlink_trap_group_item_get_from_info(devlink, info);
8674 NL_SET_ERR_MSG_MOD(extack, "Device did not register this trap group");
8678 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
8682 err = devlink_nl_trap_group_fill(msg, devlink, group_item,
8683 DEVLINK_CMD_TRAP_GROUP_NEW,
8684 info->snd_portid, info->snd_seq, 0);
8686 goto err_trap_group_fill;
8688 return genlmsg_reply(msg, info);
8690 err_trap_group_fill:
8695 static int devlink_nl_cmd_trap_group_get_dumpit(struct sk_buff *msg,
8696 struct netlink_callback *cb)
8698 enum devlink_command cmd = DEVLINK_CMD_TRAP_GROUP_NEW;
8699 struct devlink_trap_group_item *group_item;
8700 u32 portid = NETLINK_CB(cb->skb).portid;
8701 struct devlink *devlink;
8702 int start = cb->args[0];
8703 unsigned long index;
8707 devlinks_xa_for_each_registered_get(sock_net(msg->sk), index, devlink) {
8709 list_for_each_entry(group_item, &devlink->trap_group_list,
8715 err = devlink_nl_trap_group_fill(msg, devlink,
8721 devl_unlock(devlink);
8722 devlink_put(devlink);
8727 devl_unlock(devlink);
8728 devlink_put(devlink);
8736 __devlink_trap_group_action_set(struct devlink *devlink,
8737 struct devlink_trap_group_item *group_item,
8738 enum devlink_trap_action trap_action,
8739 struct netlink_ext_ack *extack)
8741 const char *group_name = group_item->group->name;
8742 struct devlink_trap_item *trap_item;
8745 if (devlink->ops->trap_group_action_set) {
8746 err = devlink->ops->trap_group_action_set(devlink, group_item->group,
8747 trap_action, extack);
8751 list_for_each_entry(trap_item, &devlink->trap_list, list) {
8752 if (strcmp(trap_item->group_item->group->name, group_name))
8754 if (trap_item->action != trap_action &&
8755 trap_item->trap->type != DEVLINK_TRAP_TYPE_DROP)
8757 trap_item->action = trap_action;
8763 list_for_each_entry(trap_item, &devlink->trap_list, list) {
8764 if (strcmp(trap_item->group_item->group->name, group_name))
8766 err = __devlink_trap_action_set(devlink, trap_item,
8767 trap_action, extack);
8776 devlink_trap_group_action_set(struct devlink *devlink,
8777 struct devlink_trap_group_item *group_item,
8778 struct genl_info *info, bool *p_modified)
8780 enum devlink_trap_action trap_action;
8783 if (!info->attrs[DEVLINK_ATTR_TRAP_ACTION])
8786 err = devlink_trap_action_get_from_info(info, &trap_action);
8788 NL_SET_ERR_MSG_MOD(info->extack, "Invalid trap action");
8792 err = __devlink_trap_group_action_set(devlink, group_item, trap_action,
8802 static int devlink_trap_group_set(struct devlink *devlink,
8803 struct devlink_trap_group_item *group_item,
8804 struct genl_info *info)
8806 struct devlink_trap_policer_item *policer_item;
8807 struct netlink_ext_ack *extack = info->extack;
8808 const struct devlink_trap_policer *policer;
8809 struct nlattr **attrs = info->attrs;
8812 if (!attrs[DEVLINK_ATTR_TRAP_POLICER_ID])
8815 if (!devlink->ops->trap_group_set)
8818 policer_item = group_item->policer_item;
8819 if (attrs[DEVLINK_ATTR_TRAP_POLICER_ID]) {
8822 policer_id = nla_get_u32(attrs[DEVLINK_ATTR_TRAP_POLICER_ID]);
8823 policer_item = devlink_trap_policer_item_lookup(devlink,
8825 if (policer_id && !policer_item) {
8826 NL_SET_ERR_MSG_MOD(extack, "Device did not register this trap policer");
8830 policer = policer_item ? policer_item->policer : NULL;
8832 err = devlink->ops->trap_group_set(devlink, group_item->group, policer,
8837 group_item->policer_item = policer_item;
8842 static int devlink_nl_cmd_trap_group_set_doit(struct sk_buff *skb,
8843 struct genl_info *info)
8845 struct netlink_ext_ack *extack = info->extack;
8846 struct devlink *devlink = info->user_ptr[0];
8847 struct devlink_trap_group_item *group_item;
8848 bool modified = false;
8851 if (list_empty(&devlink->trap_group_list))
8854 group_item = devlink_trap_group_item_get_from_info(devlink, info);
8856 NL_SET_ERR_MSG_MOD(extack, "Device did not register this trap group");
8860 err = devlink_trap_group_action_set(devlink, group_item, info,
8865 err = devlink_trap_group_set(devlink, group_item, info);
8867 goto err_trap_group_set;
8873 NL_SET_ERR_MSG_MOD(extack, "Trap group set failed, but some changes were committed already");
8877 static struct devlink_trap_policer_item *
8878 devlink_trap_policer_item_get_from_info(struct devlink *devlink,
8879 struct genl_info *info)
8883 if (!info->attrs[DEVLINK_ATTR_TRAP_POLICER_ID])
8885 id = nla_get_u32(info->attrs[DEVLINK_ATTR_TRAP_POLICER_ID]);
8887 return devlink_trap_policer_item_lookup(devlink, id);
8891 devlink_trap_policer_stats_put(struct sk_buff *msg, struct devlink *devlink,
8892 const struct devlink_trap_policer *policer)
8894 struct nlattr *attr;
8898 if (!devlink->ops->trap_policer_counter_get)
8901 err = devlink->ops->trap_policer_counter_get(devlink, policer, &drops);
8905 attr = nla_nest_start(msg, DEVLINK_ATTR_STATS);
8909 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_STATS_RX_DROPPED, drops,
8911 goto nla_put_failure;
8913 nla_nest_end(msg, attr);
8918 nla_nest_cancel(msg, attr);
8923 devlink_nl_trap_policer_fill(struct sk_buff *msg, struct devlink *devlink,
8924 const struct devlink_trap_policer_item *policer_item,
8925 enum devlink_command cmd, u32 portid, u32 seq,
8931 hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
8935 if (devlink_nl_put_handle(msg, devlink))
8936 goto nla_put_failure;
8938 if (nla_put_u32(msg, DEVLINK_ATTR_TRAP_POLICER_ID,
8939 policer_item->policer->id))
8940 goto nla_put_failure;
8942 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_TRAP_POLICER_RATE,
8943 policer_item->rate, DEVLINK_ATTR_PAD))
8944 goto nla_put_failure;
8946 if (nla_put_u64_64bit(msg, DEVLINK_ATTR_TRAP_POLICER_BURST,
8947 policer_item->burst, DEVLINK_ATTR_PAD))
8948 goto nla_put_failure;
8950 err = devlink_trap_policer_stats_put(msg, devlink,
8951 policer_item->policer);
8953 goto nla_put_failure;
8955 genlmsg_end(msg, hdr);
8960 genlmsg_cancel(msg, hdr);
8964 static int devlink_nl_cmd_trap_policer_get_doit(struct sk_buff *skb,
8965 struct genl_info *info)
8967 struct devlink_trap_policer_item *policer_item;
8968 struct netlink_ext_ack *extack = info->extack;
8969 struct devlink *devlink = info->user_ptr[0];
8970 struct sk_buff *msg;
8973 if (list_empty(&devlink->trap_policer_list))
8976 policer_item = devlink_trap_policer_item_get_from_info(devlink, info);
8977 if (!policer_item) {
8978 NL_SET_ERR_MSG_MOD(extack, "Device did not register this trap policer");
8982 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
8986 err = devlink_nl_trap_policer_fill(msg, devlink, policer_item,
8987 DEVLINK_CMD_TRAP_POLICER_NEW,
8988 info->snd_portid, info->snd_seq, 0);
8990 goto err_trap_policer_fill;
8992 return genlmsg_reply(msg, info);
8994 err_trap_policer_fill:
8999 static int devlink_nl_cmd_trap_policer_get_dumpit(struct sk_buff *msg,
9000 struct netlink_callback *cb)
9002 enum devlink_command cmd = DEVLINK_CMD_TRAP_POLICER_NEW;
9003 struct devlink_trap_policer_item *policer_item;
9004 u32 portid = NETLINK_CB(cb->skb).portid;
9005 struct devlink *devlink;
9006 int start = cb->args[0];
9007 unsigned long index;
9011 devlinks_xa_for_each_registered_get(sock_net(msg->sk), index, devlink) {
9013 list_for_each_entry(policer_item, &devlink->trap_policer_list,
9019 err = devlink_nl_trap_policer_fill(msg, devlink,
9025 devl_unlock(devlink);
9026 devlink_put(devlink);
9031 devl_unlock(devlink);
9032 devlink_put(devlink);
9040 devlink_trap_policer_set(struct devlink *devlink,
9041 struct devlink_trap_policer_item *policer_item,
9042 struct genl_info *info)
9044 struct netlink_ext_ack *extack = info->extack;
9045 struct nlattr **attrs = info->attrs;
9049 rate = policer_item->rate;
9050 burst = policer_item->burst;
9052 if (attrs[DEVLINK_ATTR_TRAP_POLICER_RATE])
9053 rate = nla_get_u64(attrs[DEVLINK_ATTR_TRAP_POLICER_RATE]);
9055 if (attrs[DEVLINK_ATTR_TRAP_POLICER_BURST])
9056 burst = nla_get_u64(attrs[DEVLINK_ATTR_TRAP_POLICER_BURST]);
9058 if (rate < policer_item->policer->min_rate) {
9059 NL_SET_ERR_MSG_MOD(extack, "Policer rate lower than limit");
9063 if (rate > policer_item->policer->max_rate) {
9064 NL_SET_ERR_MSG_MOD(extack, "Policer rate higher than limit");
9068 if (burst < policer_item->policer->min_burst) {
9069 NL_SET_ERR_MSG_MOD(extack, "Policer burst size lower than limit");
9073 if (burst > policer_item->policer->max_burst) {
9074 NL_SET_ERR_MSG_MOD(extack, "Policer burst size higher than limit");
9078 err = devlink->ops->trap_policer_set(devlink, policer_item->policer,
9079 rate, burst, info->extack);
9083 policer_item->rate = rate;
9084 policer_item->burst = burst;
9089 static int devlink_nl_cmd_trap_policer_set_doit(struct sk_buff *skb,
9090 struct genl_info *info)
9092 struct devlink_trap_policer_item *policer_item;
9093 struct netlink_ext_ack *extack = info->extack;
9094 struct devlink *devlink = info->user_ptr[0];
9096 if (list_empty(&devlink->trap_policer_list))
9099 if (!devlink->ops->trap_policer_set)
9102 policer_item = devlink_trap_policer_item_get_from_info(devlink, info);
9103 if (!policer_item) {
9104 NL_SET_ERR_MSG_MOD(extack, "Device did not register this trap policer");
9108 return devlink_trap_policer_set(devlink, policer_item, info);
9111 static const struct nla_policy devlink_nl_policy[DEVLINK_ATTR_MAX + 1] = {
9112 [DEVLINK_ATTR_UNSPEC] = { .strict_start_type =
9113 DEVLINK_ATTR_TRAP_POLICER_ID },
9114 [DEVLINK_ATTR_BUS_NAME] = { .type = NLA_NUL_STRING },
9115 [DEVLINK_ATTR_DEV_NAME] = { .type = NLA_NUL_STRING },
9116 [DEVLINK_ATTR_PORT_INDEX] = { .type = NLA_U32 },
9117 [DEVLINK_ATTR_PORT_TYPE] = NLA_POLICY_RANGE(NLA_U16, DEVLINK_PORT_TYPE_AUTO,
9118 DEVLINK_PORT_TYPE_IB),
9119 [DEVLINK_ATTR_PORT_SPLIT_COUNT] = { .type = NLA_U32 },
9120 [DEVLINK_ATTR_SB_INDEX] = { .type = NLA_U32 },
9121 [DEVLINK_ATTR_SB_POOL_INDEX] = { .type = NLA_U16 },
9122 [DEVLINK_ATTR_SB_POOL_TYPE] = { .type = NLA_U8 },
9123 [DEVLINK_ATTR_SB_POOL_SIZE] = { .type = NLA_U32 },
9124 [DEVLINK_ATTR_SB_POOL_THRESHOLD_TYPE] = { .type = NLA_U8 },
9125 [DEVLINK_ATTR_SB_THRESHOLD] = { .type = NLA_U32 },
9126 [DEVLINK_ATTR_SB_TC_INDEX] = { .type = NLA_U16 },
9127 [DEVLINK_ATTR_ESWITCH_MODE] = NLA_POLICY_RANGE(NLA_U16, DEVLINK_ESWITCH_MODE_LEGACY,
9128 DEVLINK_ESWITCH_MODE_SWITCHDEV),
9129 [DEVLINK_ATTR_ESWITCH_INLINE_MODE] = { .type = NLA_U8 },
9130 [DEVLINK_ATTR_ESWITCH_ENCAP_MODE] = { .type = NLA_U8 },
9131 [DEVLINK_ATTR_DPIPE_TABLE_NAME] = { .type = NLA_NUL_STRING },
9132 [DEVLINK_ATTR_DPIPE_TABLE_COUNTERS_ENABLED] = { .type = NLA_U8 },
9133 [DEVLINK_ATTR_RESOURCE_ID] = { .type = NLA_U64},
9134 [DEVLINK_ATTR_RESOURCE_SIZE] = { .type = NLA_U64},
9135 [DEVLINK_ATTR_PARAM_NAME] = { .type = NLA_NUL_STRING },
9136 [DEVLINK_ATTR_PARAM_TYPE] = { .type = NLA_U8 },
9137 [DEVLINK_ATTR_PARAM_VALUE_CMODE] = { .type = NLA_U8 },
9138 [DEVLINK_ATTR_REGION_NAME] = { .type = NLA_NUL_STRING },
9139 [DEVLINK_ATTR_REGION_SNAPSHOT_ID] = { .type = NLA_U32 },
9140 [DEVLINK_ATTR_REGION_CHUNK_ADDR] = { .type = NLA_U64 },
9141 [DEVLINK_ATTR_REGION_CHUNK_LEN] = { .type = NLA_U64 },
9142 [DEVLINK_ATTR_HEALTH_REPORTER_NAME] = { .type = NLA_NUL_STRING },
9143 [DEVLINK_ATTR_HEALTH_REPORTER_GRACEFUL_PERIOD] = { .type = NLA_U64 },
9144 [DEVLINK_ATTR_HEALTH_REPORTER_AUTO_RECOVER] = { .type = NLA_U8 },
9145 [DEVLINK_ATTR_FLASH_UPDATE_FILE_NAME] = { .type = NLA_NUL_STRING },
9146 [DEVLINK_ATTR_FLASH_UPDATE_COMPONENT] = { .type = NLA_NUL_STRING },
9147 [DEVLINK_ATTR_FLASH_UPDATE_OVERWRITE_MASK] =
9148 NLA_POLICY_BITFIELD32(DEVLINK_SUPPORTED_FLASH_OVERWRITE_SECTIONS),
9149 [DEVLINK_ATTR_TRAP_NAME] = { .type = NLA_NUL_STRING },
9150 [DEVLINK_ATTR_TRAP_ACTION] = { .type = NLA_U8 },
9151 [DEVLINK_ATTR_TRAP_GROUP_NAME] = { .type = NLA_NUL_STRING },
9152 [DEVLINK_ATTR_NETNS_PID] = { .type = NLA_U32 },
9153 [DEVLINK_ATTR_NETNS_FD] = { .type = NLA_U32 },
9154 [DEVLINK_ATTR_NETNS_ID] = { .type = NLA_U32 },
9155 [DEVLINK_ATTR_HEALTH_REPORTER_AUTO_DUMP] = { .type = NLA_U8 },
9156 [DEVLINK_ATTR_TRAP_POLICER_ID] = { .type = NLA_U32 },
9157 [DEVLINK_ATTR_TRAP_POLICER_RATE] = { .type = NLA_U64 },
9158 [DEVLINK_ATTR_TRAP_POLICER_BURST] = { .type = NLA_U64 },
9159 [DEVLINK_ATTR_PORT_FUNCTION] = { .type = NLA_NESTED },
9160 [DEVLINK_ATTR_RELOAD_ACTION] = NLA_POLICY_RANGE(NLA_U8, DEVLINK_RELOAD_ACTION_DRIVER_REINIT,
9161 DEVLINK_RELOAD_ACTION_MAX),
9162 [DEVLINK_ATTR_RELOAD_LIMITS] = NLA_POLICY_BITFIELD32(DEVLINK_RELOAD_LIMITS_VALID_MASK),
9163 [DEVLINK_ATTR_PORT_FLAVOUR] = { .type = NLA_U16 },
9164 [DEVLINK_ATTR_PORT_PCI_PF_NUMBER] = { .type = NLA_U16 },
9165 [DEVLINK_ATTR_PORT_PCI_SF_NUMBER] = { .type = NLA_U32 },
9166 [DEVLINK_ATTR_PORT_CONTROLLER_NUMBER] = { .type = NLA_U32 },
9167 [DEVLINK_ATTR_RATE_TYPE] = { .type = NLA_U16 },
9168 [DEVLINK_ATTR_RATE_TX_SHARE] = { .type = NLA_U64 },
9169 [DEVLINK_ATTR_RATE_TX_MAX] = { .type = NLA_U64 },
9170 [DEVLINK_ATTR_RATE_NODE_NAME] = { .type = NLA_NUL_STRING },
9171 [DEVLINK_ATTR_RATE_PARENT_NODE_NAME] = { .type = NLA_NUL_STRING },
9172 [DEVLINK_ATTR_LINECARD_INDEX] = { .type = NLA_U32 },
9173 [DEVLINK_ATTR_LINECARD_TYPE] = { .type = NLA_NUL_STRING },
9174 [DEVLINK_ATTR_SELFTESTS] = { .type = NLA_NESTED },
9177 static const struct genl_small_ops devlink_nl_ops[] = {
9179 .cmd = DEVLINK_CMD_GET,
9180 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9181 .doit = devlink_nl_cmd_get_doit,
9182 .dumpit = devlink_nl_cmd_get_dumpit,
9183 /* can be retrieved by unprivileged users */
9186 .cmd = DEVLINK_CMD_PORT_GET,
9187 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9188 .doit = devlink_nl_cmd_port_get_doit,
9189 .dumpit = devlink_nl_cmd_port_get_dumpit,
9190 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
9191 /* can be retrieved by unprivileged users */
9194 .cmd = DEVLINK_CMD_PORT_SET,
9195 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9196 .doit = devlink_nl_cmd_port_set_doit,
9197 .flags = GENL_ADMIN_PERM,
9198 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
9201 .cmd = DEVLINK_CMD_RATE_GET,
9202 .doit = devlink_nl_cmd_rate_get_doit,
9203 .dumpit = devlink_nl_cmd_rate_get_dumpit,
9204 .internal_flags = DEVLINK_NL_FLAG_NEED_RATE,
9205 /* can be retrieved by unprivileged users */
9208 .cmd = DEVLINK_CMD_RATE_SET,
9209 .doit = devlink_nl_cmd_rate_set_doit,
9210 .flags = GENL_ADMIN_PERM,
9211 .internal_flags = DEVLINK_NL_FLAG_NEED_RATE,
9214 .cmd = DEVLINK_CMD_RATE_NEW,
9215 .doit = devlink_nl_cmd_rate_new_doit,
9216 .flags = GENL_ADMIN_PERM,
9219 .cmd = DEVLINK_CMD_RATE_DEL,
9220 .doit = devlink_nl_cmd_rate_del_doit,
9221 .flags = GENL_ADMIN_PERM,
9222 .internal_flags = DEVLINK_NL_FLAG_NEED_RATE_NODE,
9225 .cmd = DEVLINK_CMD_PORT_SPLIT,
9226 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9227 .doit = devlink_nl_cmd_port_split_doit,
9228 .flags = GENL_ADMIN_PERM,
9229 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
9232 .cmd = DEVLINK_CMD_PORT_UNSPLIT,
9233 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9234 .doit = devlink_nl_cmd_port_unsplit_doit,
9235 .flags = GENL_ADMIN_PERM,
9236 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
9239 .cmd = DEVLINK_CMD_PORT_NEW,
9240 .doit = devlink_nl_cmd_port_new_doit,
9241 .flags = GENL_ADMIN_PERM,
9244 .cmd = DEVLINK_CMD_PORT_DEL,
9245 .doit = devlink_nl_cmd_port_del_doit,
9246 .flags = GENL_ADMIN_PERM,
9249 .cmd = DEVLINK_CMD_LINECARD_GET,
9250 .doit = devlink_nl_cmd_linecard_get_doit,
9251 .dumpit = devlink_nl_cmd_linecard_get_dumpit,
9252 .internal_flags = DEVLINK_NL_FLAG_NEED_LINECARD,
9253 /* can be retrieved by unprivileged users */
9256 .cmd = DEVLINK_CMD_LINECARD_SET,
9257 .doit = devlink_nl_cmd_linecard_set_doit,
9258 .flags = GENL_ADMIN_PERM,
9259 .internal_flags = DEVLINK_NL_FLAG_NEED_LINECARD,
9262 .cmd = DEVLINK_CMD_SB_GET,
9263 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9264 .doit = devlink_nl_cmd_sb_get_doit,
9265 .dumpit = devlink_nl_cmd_sb_get_dumpit,
9266 /* can be retrieved by unprivileged users */
9269 .cmd = DEVLINK_CMD_SB_POOL_GET,
9270 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9271 .doit = devlink_nl_cmd_sb_pool_get_doit,
9272 .dumpit = devlink_nl_cmd_sb_pool_get_dumpit,
9273 /* can be retrieved by unprivileged users */
9276 .cmd = DEVLINK_CMD_SB_POOL_SET,
9277 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9278 .doit = devlink_nl_cmd_sb_pool_set_doit,
9279 .flags = GENL_ADMIN_PERM,
9282 .cmd = DEVLINK_CMD_SB_PORT_POOL_GET,
9283 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9284 .doit = devlink_nl_cmd_sb_port_pool_get_doit,
9285 .dumpit = devlink_nl_cmd_sb_port_pool_get_dumpit,
9286 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
9287 /* can be retrieved by unprivileged users */
9290 .cmd = DEVLINK_CMD_SB_PORT_POOL_SET,
9291 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9292 .doit = devlink_nl_cmd_sb_port_pool_set_doit,
9293 .flags = GENL_ADMIN_PERM,
9294 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
9297 .cmd = DEVLINK_CMD_SB_TC_POOL_BIND_GET,
9298 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9299 .doit = devlink_nl_cmd_sb_tc_pool_bind_get_doit,
9300 .dumpit = devlink_nl_cmd_sb_tc_pool_bind_get_dumpit,
9301 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
9302 /* can be retrieved by unprivileged users */
9305 .cmd = DEVLINK_CMD_SB_TC_POOL_BIND_SET,
9306 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9307 .doit = devlink_nl_cmd_sb_tc_pool_bind_set_doit,
9308 .flags = GENL_ADMIN_PERM,
9309 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
9312 .cmd = DEVLINK_CMD_SB_OCC_SNAPSHOT,
9313 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9314 .doit = devlink_nl_cmd_sb_occ_snapshot_doit,
9315 .flags = GENL_ADMIN_PERM,
9318 .cmd = DEVLINK_CMD_SB_OCC_MAX_CLEAR,
9319 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9320 .doit = devlink_nl_cmd_sb_occ_max_clear_doit,
9321 .flags = GENL_ADMIN_PERM,
9324 .cmd = DEVLINK_CMD_ESWITCH_GET,
9325 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9326 .doit = devlink_nl_cmd_eswitch_get_doit,
9327 .flags = GENL_ADMIN_PERM,
9330 .cmd = DEVLINK_CMD_ESWITCH_SET,
9331 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9332 .doit = devlink_nl_cmd_eswitch_set_doit,
9333 .flags = GENL_ADMIN_PERM,
9336 .cmd = DEVLINK_CMD_DPIPE_TABLE_GET,
9337 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9338 .doit = devlink_nl_cmd_dpipe_table_get,
9339 /* can be retrieved by unprivileged users */
9342 .cmd = DEVLINK_CMD_DPIPE_ENTRIES_GET,
9343 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9344 .doit = devlink_nl_cmd_dpipe_entries_get,
9345 /* can be retrieved by unprivileged users */
9348 .cmd = DEVLINK_CMD_DPIPE_HEADERS_GET,
9349 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9350 .doit = devlink_nl_cmd_dpipe_headers_get,
9351 /* can be retrieved by unprivileged users */
9354 .cmd = DEVLINK_CMD_DPIPE_TABLE_COUNTERS_SET,
9355 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9356 .doit = devlink_nl_cmd_dpipe_table_counters_set,
9357 .flags = GENL_ADMIN_PERM,
9360 .cmd = DEVLINK_CMD_RESOURCE_SET,
9361 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9362 .doit = devlink_nl_cmd_resource_set,
9363 .flags = GENL_ADMIN_PERM,
9366 .cmd = DEVLINK_CMD_RESOURCE_DUMP,
9367 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9368 .doit = devlink_nl_cmd_resource_dump,
9369 /* can be retrieved by unprivileged users */
9372 .cmd = DEVLINK_CMD_RELOAD,
9373 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9374 .doit = devlink_nl_cmd_reload,
9375 .flags = GENL_ADMIN_PERM,
9378 .cmd = DEVLINK_CMD_PARAM_GET,
9379 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9380 .doit = devlink_nl_cmd_param_get_doit,
9381 .dumpit = devlink_nl_cmd_param_get_dumpit,
9382 /* can be retrieved by unprivileged users */
9385 .cmd = DEVLINK_CMD_PARAM_SET,
9386 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9387 .doit = devlink_nl_cmd_param_set_doit,
9388 .flags = GENL_ADMIN_PERM,
9391 .cmd = DEVLINK_CMD_PORT_PARAM_GET,
9392 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9393 .doit = devlink_nl_cmd_port_param_get_doit,
9394 .dumpit = devlink_nl_cmd_port_param_get_dumpit,
9395 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
9396 /* can be retrieved by unprivileged users */
9399 .cmd = DEVLINK_CMD_PORT_PARAM_SET,
9400 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9401 .doit = devlink_nl_cmd_port_param_set_doit,
9402 .flags = GENL_ADMIN_PERM,
9403 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
9406 .cmd = DEVLINK_CMD_REGION_GET,
9407 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9408 .doit = devlink_nl_cmd_region_get_doit,
9409 .dumpit = devlink_nl_cmd_region_get_dumpit,
9410 .flags = GENL_ADMIN_PERM,
9413 .cmd = DEVLINK_CMD_REGION_NEW,
9414 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9415 .doit = devlink_nl_cmd_region_new,
9416 .flags = GENL_ADMIN_PERM,
9419 .cmd = DEVLINK_CMD_REGION_DEL,
9420 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9421 .doit = devlink_nl_cmd_region_del,
9422 .flags = GENL_ADMIN_PERM,
9425 .cmd = DEVLINK_CMD_REGION_READ,
9426 .validate = GENL_DONT_VALIDATE_STRICT |
9427 GENL_DONT_VALIDATE_DUMP_STRICT,
9428 .dumpit = devlink_nl_cmd_region_read_dumpit,
9429 .flags = GENL_ADMIN_PERM,
9432 .cmd = DEVLINK_CMD_INFO_GET,
9433 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9434 .doit = devlink_nl_cmd_info_get_doit,
9435 .dumpit = devlink_nl_cmd_info_get_dumpit,
9436 /* can be retrieved by unprivileged users */
9439 .cmd = DEVLINK_CMD_HEALTH_REPORTER_GET,
9440 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9441 .doit = devlink_nl_cmd_health_reporter_get_doit,
9442 .dumpit = devlink_nl_cmd_health_reporter_get_dumpit,
9443 .internal_flags = DEVLINK_NL_FLAG_NEED_DEVLINK_OR_PORT,
9444 /* can be retrieved by unprivileged users */
9447 .cmd = DEVLINK_CMD_HEALTH_REPORTER_SET,
9448 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9449 .doit = devlink_nl_cmd_health_reporter_set_doit,
9450 .flags = GENL_ADMIN_PERM,
9451 .internal_flags = DEVLINK_NL_FLAG_NEED_DEVLINK_OR_PORT,
9454 .cmd = DEVLINK_CMD_HEALTH_REPORTER_RECOVER,
9455 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9456 .doit = devlink_nl_cmd_health_reporter_recover_doit,
9457 .flags = GENL_ADMIN_PERM,
9458 .internal_flags = DEVLINK_NL_FLAG_NEED_DEVLINK_OR_PORT,
9461 .cmd = DEVLINK_CMD_HEALTH_REPORTER_DIAGNOSE,
9462 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9463 .doit = devlink_nl_cmd_health_reporter_diagnose_doit,
9464 .flags = GENL_ADMIN_PERM,
9465 .internal_flags = DEVLINK_NL_FLAG_NEED_DEVLINK_OR_PORT,
9468 .cmd = DEVLINK_CMD_HEALTH_REPORTER_DUMP_GET,
9469 .validate = GENL_DONT_VALIDATE_STRICT |
9470 GENL_DONT_VALIDATE_DUMP_STRICT,
9471 .dumpit = devlink_nl_cmd_health_reporter_dump_get_dumpit,
9472 .flags = GENL_ADMIN_PERM,
9475 .cmd = DEVLINK_CMD_HEALTH_REPORTER_DUMP_CLEAR,
9476 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9477 .doit = devlink_nl_cmd_health_reporter_dump_clear_doit,
9478 .flags = GENL_ADMIN_PERM,
9479 .internal_flags = DEVLINK_NL_FLAG_NEED_DEVLINK_OR_PORT,
9482 .cmd = DEVLINK_CMD_HEALTH_REPORTER_TEST,
9483 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9484 .doit = devlink_nl_cmd_health_reporter_test_doit,
9485 .flags = GENL_ADMIN_PERM,
9486 .internal_flags = DEVLINK_NL_FLAG_NEED_DEVLINK_OR_PORT,
9489 .cmd = DEVLINK_CMD_FLASH_UPDATE,
9490 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
9491 .doit = devlink_nl_cmd_flash_update,
9492 .flags = GENL_ADMIN_PERM,
9495 .cmd = DEVLINK_CMD_TRAP_GET,
9496 .doit = devlink_nl_cmd_trap_get_doit,
9497 .dumpit = devlink_nl_cmd_trap_get_dumpit,
9498 /* can be retrieved by unprivileged users */
9501 .cmd = DEVLINK_CMD_TRAP_SET,
9502 .doit = devlink_nl_cmd_trap_set_doit,
9503 .flags = GENL_ADMIN_PERM,
9506 .cmd = DEVLINK_CMD_TRAP_GROUP_GET,
9507 .doit = devlink_nl_cmd_trap_group_get_doit,
9508 .dumpit = devlink_nl_cmd_trap_group_get_dumpit,
9509 /* can be retrieved by unprivileged users */
9512 .cmd = DEVLINK_CMD_TRAP_GROUP_SET,
9513 .doit = devlink_nl_cmd_trap_group_set_doit,
9514 .flags = GENL_ADMIN_PERM,
9517 .cmd = DEVLINK_CMD_TRAP_POLICER_GET,
9518 .doit = devlink_nl_cmd_trap_policer_get_doit,
9519 .dumpit = devlink_nl_cmd_trap_policer_get_dumpit,
9520 /* can be retrieved by unprivileged users */
9523 .cmd = DEVLINK_CMD_TRAP_POLICER_SET,
9524 .doit = devlink_nl_cmd_trap_policer_set_doit,
9525 .flags = GENL_ADMIN_PERM,
9528 .cmd = DEVLINK_CMD_SELFTESTS_GET,
9529 .doit = devlink_nl_cmd_selftests_get_doit,
9530 .dumpit = devlink_nl_cmd_selftests_get_dumpit
9531 /* can be retrieved by unprivileged users */
9534 .cmd = DEVLINK_CMD_SELFTESTS_RUN,
9535 .doit = devlink_nl_cmd_selftests_run,
9536 .flags = GENL_ADMIN_PERM,
9540 static struct genl_family devlink_nl_family __ro_after_init = {
9541 .name = DEVLINK_GENL_NAME,
9542 .version = DEVLINK_GENL_VERSION,
9543 .maxattr = DEVLINK_ATTR_MAX,
9544 .policy = devlink_nl_policy,
9546 .parallel_ops = true,
9547 .pre_doit = devlink_nl_pre_doit,
9548 .post_doit = devlink_nl_post_doit,
9549 .module = THIS_MODULE,
9550 .small_ops = devlink_nl_ops,
9551 .n_small_ops = ARRAY_SIZE(devlink_nl_ops),
9552 .resv_start_op = DEVLINK_CMD_SELFTESTS_RUN + 1,
9553 .mcgrps = devlink_nl_mcgrps,
9554 .n_mcgrps = ARRAY_SIZE(devlink_nl_mcgrps),
9557 static bool devlink_reload_actions_valid(const struct devlink_ops *ops)
9559 const struct devlink_reload_combination *comb;
9562 if (!devlink_reload_supported(ops)) {
9563 if (WARN_ON(ops->reload_actions))
9568 if (WARN_ON(!ops->reload_actions ||
9569 ops->reload_actions & BIT(DEVLINK_RELOAD_ACTION_UNSPEC) ||
9570 ops->reload_actions >= BIT(__DEVLINK_RELOAD_ACTION_MAX)))
9573 if (WARN_ON(ops->reload_limits & BIT(DEVLINK_RELOAD_LIMIT_UNSPEC) ||
9574 ops->reload_limits >= BIT(__DEVLINK_RELOAD_LIMIT_MAX)))
9577 for (i = 0; i < ARRAY_SIZE(devlink_reload_invalid_combinations); i++) {
9578 comb = &devlink_reload_invalid_combinations[i];
9579 if (ops->reload_actions == BIT(comb->action) &&
9580 ops->reload_limits == BIT(comb->limit))
9587 * devlink_set_features - Set devlink supported features
9590 * @features: devlink support features
9592 * This interface allows us to set reload ops separatelly from
9593 * the devlink_alloc.
9595 void devlink_set_features(struct devlink *devlink, u64 features)
9597 ASSERT_DEVLINK_NOT_REGISTERED(devlink);
9599 WARN_ON(features & DEVLINK_F_RELOAD &&
9600 !devlink_reload_supported(devlink->ops));
9601 devlink->features = features;
9603 EXPORT_SYMBOL_GPL(devlink_set_features);
9606 * devlink_alloc_ns - Allocate new devlink instance resources
9607 * in specific namespace
9610 * @priv_size: size of user private data
9611 * @net: net namespace
9612 * @dev: parent device
9614 * Allocate new devlink instance resources, including devlink index
9617 struct devlink *devlink_alloc_ns(const struct devlink_ops *ops,
9618 size_t priv_size, struct net *net,
9621 struct devlink *devlink;
9625 WARN_ON(!ops || !dev);
9626 if (!devlink_reload_actions_valid(ops))
9629 devlink = kzalloc(sizeof(*devlink) + priv_size, GFP_KERNEL);
9633 ret = xa_alloc_cyclic(&devlinks, &devlink->index, devlink, xa_limit_31b,
9634 &last_id, GFP_KERNEL);
9642 xa_init_flags(&devlink->snapshot_ids, XA_FLAGS_ALLOC);
9643 write_pnet(&devlink->_net, net);
9644 INIT_LIST_HEAD(&devlink->port_list);
9645 INIT_LIST_HEAD(&devlink->rate_list);
9646 INIT_LIST_HEAD(&devlink->linecard_list);
9647 INIT_LIST_HEAD(&devlink->sb_list);
9648 INIT_LIST_HEAD_RCU(&devlink->dpipe_table_list);
9649 INIT_LIST_HEAD(&devlink->resource_list);
9650 INIT_LIST_HEAD(&devlink->param_list);
9651 INIT_LIST_HEAD(&devlink->region_list);
9652 INIT_LIST_HEAD(&devlink->reporter_list);
9653 INIT_LIST_HEAD(&devlink->trap_list);
9654 INIT_LIST_HEAD(&devlink->trap_group_list);
9655 INIT_LIST_HEAD(&devlink->trap_policer_list);
9656 lockdep_register_key(&devlink->lock_key);
9657 mutex_init(&devlink->lock);
9658 lockdep_set_class(&devlink->lock, &devlink->lock_key);
9659 mutex_init(&devlink->reporters_lock);
9660 mutex_init(&devlink->linecards_lock);
9661 refcount_set(&devlink->refcount, 1);
9662 init_completion(&devlink->comp);
9666 EXPORT_SYMBOL_GPL(devlink_alloc_ns);
9669 devlink_trap_policer_notify(struct devlink *devlink,
9670 const struct devlink_trap_policer_item *policer_item,
9671 enum devlink_command cmd);
9673 devlink_trap_group_notify(struct devlink *devlink,
9674 const struct devlink_trap_group_item *group_item,
9675 enum devlink_command cmd);
9676 static void devlink_trap_notify(struct devlink *devlink,
9677 const struct devlink_trap_item *trap_item,
9678 enum devlink_command cmd);
9680 static void devlink_notify_register(struct devlink *devlink)
9682 struct devlink_trap_policer_item *policer_item;
9683 struct devlink_trap_group_item *group_item;
9684 struct devlink_param_item *param_item;
9685 struct devlink_trap_item *trap_item;
9686 struct devlink_port *devlink_port;
9687 struct devlink_linecard *linecard;
9688 struct devlink_rate *rate_node;
9689 struct devlink_region *region;
9691 devlink_notify(devlink, DEVLINK_CMD_NEW);
9692 list_for_each_entry(linecard, &devlink->linecard_list, list)
9693 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_NEW);
9695 list_for_each_entry(devlink_port, &devlink->port_list, list)
9696 devlink_port_notify(devlink_port, DEVLINK_CMD_PORT_NEW);
9698 list_for_each_entry(policer_item, &devlink->trap_policer_list, list)
9699 devlink_trap_policer_notify(devlink, policer_item,
9700 DEVLINK_CMD_TRAP_POLICER_NEW);
9702 list_for_each_entry(group_item, &devlink->trap_group_list, list)
9703 devlink_trap_group_notify(devlink, group_item,
9704 DEVLINK_CMD_TRAP_GROUP_NEW);
9706 list_for_each_entry(trap_item, &devlink->trap_list, list)
9707 devlink_trap_notify(devlink, trap_item, DEVLINK_CMD_TRAP_NEW);
9709 list_for_each_entry(rate_node, &devlink->rate_list, list)
9710 devlink_rate_notify(rate_node, DEVLINK_CMD_RATE_NEW);
9712 list_for_each_entry(region, &devlink->region_list, list)
9713 devlink_nl_region_notify(region, NULL, DEVLINK_CMD_REGION_NEW);
9715 list_for_each_entry(param_item, &devlink->param_list, list)
9716 devlink_param_notify(devlink, 0, param_item,
9717 DEVLINK_CMD_PARAM_NEW);
9720 static void devlink_notify_unregister(struct devlink *devlink)
9722 struct devlink_trap_policer_item *policer_item;
9723 struct devlink_trap_group_item *group_item;
9724 struct devlink_param_item *param_item;
9725 struct devlink_trap_item *trap_item;
9726 struct devlink_port *devlink_port;
9727 struct devlink_rate *rate_node;
9728 struct devlink_region *region;
9730 list_for_each_entry_reverse(param_item, &devlink->param_list, list)
9731 devlink_param_notify(devlink, 0, param_item,
9732 DEVLINK_CMD_PARAM_DEL);
9734 list_for_each_entry_reverse(region, &devlink->region_list, list)
9735 devlink_nl_region_notify(region, NULL, DEVLINK_CMD_REGION_DEL);
9737 list_for_each_entry_reverse(rate_node, &devlink->rate_list, list)
9738 devlink_rate_notify(rate_node, DEVLINK_CMD_RATE_DEL);
9740 list_for_each_entry_reverse(trap_item, &devlink->trap_list, list)
9741 devlink_trap_notify(devlink, trap_item, DEVLINK_CMD_TRAP_DEL);
9743 list_for_each_entry_reverse(group_item, &devlink->trap_group_list, list)
9744 devlink_trap_group_notify(devlink, group_item,
9745 DEVLINK_CMD_TRAP_GROUP_DEL);
9746 list_for_each_entry_reverse(policer_item, &devlink->trap_policer_list,
9748 devlink_trap_policer_notify(devlink, policer_item,
9749 DEVLINK_CMD_TRAP_POLICER_DEL);
9751 list_for_each_entry_reverse(devlink_port, &devlink->port_list, list)
9752 devlink_port_notify(devlink_port, DEVLINK_CMD_PORT_DEL);
9753 devlink_notify(devlink, DEVLINK_CMD_DEL);
9757 * devlink_register - Register devlink instance
9761 void devlink_register(struct devlink *devlink)
9763 ASSERT_DEVLINK_NOT_REGISTERED(devlink);
9764 /* Make sure that we are in .probe() routine */
9766 xa_set_mark(&devlinks, devlink->index, DEVLINK_REGISTERED);
9767 devlink_notify_register(devlink);
9769 EXPORT_SYMBOL_GPL(devlink_register);
9772 * devlink_unregister - Unregister devlink instance
9776 void devlink_unregister(struct devlink *devlink)
9778 ASSERT_DEVLINK_REGISTERED(devlink);
9779 /* Make sure that we are in .remove() routine */
9781 xa_set_mark(&devlinks, devlink->index, DEVLINK_UNREGISTERING);
9782 devlink_put(devlink);
9783 wait_for_completion(&devlink->comp);
9785 devlink_notify_unregister(devlink);
9786 xa_clear_mark(&devlinks, devlink->index, DEVLINK_REGISTERED);
9787 xa_clear_mark(&devlinks, devlink->index, DEVLINK_UNREGISTERING);
9789 EXPORT_SYMBOL_GPL(devlink_unregister);
9792 * devlink_free - Free devlink instance resources
9796 void devlink_free(struct devlink *devlink)
9798 ASSERT_DEVLINK_NOT_REGISTERED(devlink);
9800 mutex_destroy(&devlink->linecards_lock);
9801 mutex_destroy(&devlink->reporters_lock);
9802 mutex_destroy(&devlink->lock);
9803 lockdep_unregister_key(&devlink->lock_key);
9804 WARN_ON(!list_empty(&devlink->trap_policer_list));
9805 WARN_ON(!list_empty(&devlink->trap_group_list));
9806 WARN_ON(!list_empty(&devlink->trap_list));
9807 WARN_ON(!list_empty(&devlink->reporter_list));
9808 WARN_ON(!list_empty(&devlink->region_list));
9809 WARN_ON(!list_empty(&devlink->param_list));
9810 WARN_ON(!list_empty(&devlink->resource_list));
9811 WARN_ON(!list_empty(&devlink->dpipe_table_list));
9812 WARN_ON(!list_empty(&devlink->sb_list));
9813 WARN_ON(!list_empty(&devlink->rate_list));
9814 WARN_ON(!list_empty(&devlink->linecard_list));
9815 WARN_ON(!list_empty(&devlink->port_list));
9817 xa_destroy(&devlink->snapshot_ids);
9818 xa_erase(&devlinks, devlink->index);
9822 EXPORT_SYMBOL_GPL(devlink_free);
9824 static void devlink_port_type_warn(struct work_struct *work)
9826 WARN(true, "Type was not set for devlink port.");
9829 static bool devlink_port_type_should_warn(struct devlink_port *devlink_port)
9831 /* Ignore CPU and DSA flavours. */
9832 return devlink_port->attrs.flavour != DEVLINK_PORT_FLAVOUR_CPU &&
9833 devlink_port->attrs.flavour != DEVLINK_PORT_FLAVOUR_DSA &&
9834 devlink_port->attrs.flavour != DEVLINK_PORT_FLAVOUR_UNUSED;
9837 #define DEVLINK_PORT_TYPE_WARN_TIMEOUT (HZ * 3600)
9839 static void devlink_port_type_warn_schedule(struct devlink_port *devlink_port)
9841 if (!devlink_port_type_should_warn(devlink_port))
9843 /* Schedule a work to WARN in case driver does not set port
9844 * type within timeout.
9846 schedule_delayed_work(&devlink_port->type_warn_dw,
9847 DEVLINK_PORT_TYPE_WARN_TIMEOUT);
9850 static void devlink_port_type_warn_cancel(struct devlink_port *devlink_port)
9852 if (!devlink_port_type_should_warn(devlink_port))
9854 cancel_delayed_work_sync(&devlink_port->type_warn_dw);
9858 * devlink_port_init() - Init devlink port
9861 * @devlink_port: devlink port
9863 * Initialize essencial stuff that is needed for functions
9864 * that may be called before devlink port registration.
9865 * Call to this function is optional and not needed
9866 * in case the driver does not use such functions.
9868 void devlink_port_init(struct devlink *devlink,
9869 struct devlink_port *devlink_port)
9871 if (devlink_port->initialized)
9873 devlink_port->devlink = devlink;
9874 INIT_LIST_HEAD(&devlink_port->region_list);
9875 devlink_port->initialized = true;
9877 EXPORT_SYMBOL_GPL(devlink_port_init);
9880 * devlink_port_fini() - Deinitialize devlink port
9882 * @devlink_port: devlink port
9884 * Deinitialize essencial stuff that is in use for functions
9885 * that may be called after devlink port unregistration.
9886 * Call to this function is optional and not needed
9887 * in case the driver does not use such functions.
9889 void devlink_port_fini(struct devlink_port *devlink_port)
9891 WARN_ON(!list_empty(&devlink_port->region_list));
9893 EXPORT_SYMBOL_GPL(devlink_port_fini);
9896 * devl_port_register() - Register devlink port
9899 * @devlink_port: devlink port
9900 * @port_index: driver-specific numerical identifier of the port
9902 * Register devlink port with provided port index. User can use
9903 * any indexing, even hw-related one. devlink_port structure
9904 * is convenient to be embedded inside user driver private structure.
9905 * Note that the caller should take care of zeroing the devlink_port
9908 int devl_port_register(struct devlink *devlink,
9909 struct devlink_port *devlink_port,
9910 unsigned int port_index)
9912 devl_assert_locked(devlink);
9914 if (devlink_port_index_exists(devlink, port_index))
9917 ASSERT_DEVLINK_PORT_NOT_REGISTERED(devlink_port);
9919 devlink_port_init(devlink, devlink_port);
9920 devlink_port->registered = true;
9921 devlink_port->index = port_index;
9922 spin_lock_init(&devlink_port->type_lock);
9923 INIT_LIST_HEAD(&devlink_port->reporter_list);
9924 mutex_init(&devlink_port->reporters_lock);
9925 list_add_tail(&devlink_port->list, &devlink->port_list);
9927 INIT_DELAYED_WORK(&devlink_port->type_warn_dw, &devlink_port_type_warn);
9928 devlink_port_type_warn_schedule(devlink_port);
9929 devlink_port_notify(devlink_port, DEVLINK_CMD_PORT_NEW);
9932 EXPORT_SYMBOL_GPL(devl_port_register);
9935 * devlink_port_register - Register devlink port
9938 * @devlink_port: devlink port
9939 * @port_index: driver-specific numerical identifier of the port
9941 * Register devlink port with provided port index. User can use
9942 * any indexing, even hw-related one. devlink_port structure
9943 * is convenient to be embedded inside user driver private structure.
9944 * Note that the caller should take care of zeroing the devlink_port
9947 * Context: Takes and release devlink->lock <mutex>.
9949 int devlink_port_register(struct devlink *devlink,
9950 struct devlink_port *devlink_port,
9951 unsigned int port_index)
9956 err = devl_port_register(devlink, devlink_port, port_index);
9957 devl_unlock(devlink);
9960 EXPORT_SYMBOL_GPL(devlink_port_register);
9963 * devl_port_unregister() - Unregister devlink port
9965 * @devlink_port: devlink port
9967 void devl_port_unregister(struct devlink_port *devlink_port)
9969 lockdep_assert_held(&devlink_port->devlink->lock);
9971 devlink_port_type_warn_cancel(devlink_port);
9972 devlink_port_notify(devlink_port, DEVLINK_CMD_PORT_DEL);
9973 list_del(&devlink_port->list);
9974 WARN_ON(!list_empty(&devlink_port->reporter_list));
9975 mutex_destroy(&devlink_port->reporters_lock);
9976 devlink_port->registered = false;
9978 EXPORT_SYMBOL_GPL(devl_port_unregister);
9981 * devlink_port_unregister - Unregister devlink port
9983 * @devlink_port: devlink port
9985 * Context: Takes and release devlink->lock <mutex>.
9987 void devlink_port_unregister(struct devlink_port *devlink_port)
9989 struct devlink *devlink = devlink_port->devlink;
9992 devl_port_unregister(devlink_port);
9993 devl_unlock(devlink);
9995 EXPORT_SYMBOL_GPL(devlink_port_unregister);
9997 static void __devlink_port_type_set(struct devlink_port *devlink_port,
9998 enum devlink_port_type type,
10001 ASSERT_DEVLINK_PORT_REGISTERED(devlink_port);
10003 devlink_port_type_warn_cancel(devlink_port);
10004 spin_lock_bh(&devlink_port->type_lock);
10005 devlink_port->type = type;
10006 devlink_port->type_dev = type_dev;
10007 spin_unlock_bh(&devlink_port->type_lock);
10008 devlink_port_notify(devlink_port, DEVLINK_CMD_PORT_NEW);
10011 static void devlink_port_type_netdev_checks(struct devlink_port *devlink_port,
10012 struct net_device *netdev)
10014 const struct net_device_ops *ops = netdev->netdev_ops;
10016 /* If driver registers devlink port, it should set devlink port
10017 * attributes accordingly so the compat functions are called
10018 * and the original ops are not used.
10020 if (ops->ndo_get_phys_port_name) {
10021 /* Some drivers use the same set of ndos for netdevs
10022 * that have devlink_port registered and also for
10023 * those who don't. Make sure that ndo_get_phys_port_name
10024 * returns -EOPNOTSUPP here in case it is defined.
10027 char name[IFNAMSIZ];
10030 err = ops->ndo_get_phys_port_name(netdev, name, sizeof(name));
10031 WARN_ON(err != -EOPNOTSUPP);
10033 if (ops->ndo_get_port_parent_id) {
10034 /* Some drivers use the same set of ndos for netdevs
10035 * that have devlink_port registered and also for
10036 * those who don't. Make sure that ndo_get_port_parent_id
10037 * returns -EOPNOTSUPP here in case it is defined.
10040 struct netdev_phys_item_id ppid;
10043 err = ops->ndo_get_port_parent_id(netdev, &ppid);
10044 WARN_ON(err != -EOPNOTSUPP);
10049 * devlink_port_type_eth_set - Set port type to Ethernet
10051 * @devlink_port: devlink port
10052 * @netdev: related netdevice
10054 void devlink_port_type_eth_set(struct devlink_port *devlink_port,
10055 struct net_device *netdev)
10058 devlink_port_type_netdev_checks(devlink_port, netdev);
10060 dev_warn(devlink_port->devlink->dev,
10061 "devlink port type for port %d set to Ethernet without a software interface reference, device type not supported by the kernel?\n",
10062 devlink_port->index);
10064 __devlink_port_type_set(devlink_port, DEVLINK_PORT_TYPE_ETH, netdev);
10066 EXPORT_SYMBOL_GPL(devlink_port_type_eth_set);
10069 * devlink_port_type_ib_set - Set port type to InfiniBand
10071 * @devlink_port: devlink port
10072 * @ibdev: related IB device
10074 void devlink_port_type_ib_set(struct devlink_port *devlink_port,
10075 struct ib_device *ibdev)
10077 __devlink_port_type_set(devlink_port, DEVLINK_PORT_TYPE_IB, ibdev);
10079 EXPORT_SYMBOL_GPL(devlink_port_type_ib_set);
10082 * devlink_port_type_clear - Clear port type
10084 * @devlink_port: devlink port
10086 void devlink_port_type_clear(struct devlink_port *devlink_port)
10088 __devlink_port_type_set(devlink_port, DEVLINK_PORT_TYPE_NOTSET, NULL);
10089 devlink_port_type_warn_schedule(devlink_port);
10091 EXPORT_SYMBOL_GPL(devlink_port_type_clear);
10093 static int __devlink_port_attrs_set(struct devlink_port *devlink_port,
10094 enum devlink_port_flavour flavour)
10096 struct devlink_port_attrs *attrs = &devlink_port->attrs;
10098 devlink_port->attrs_set = true;
10099 attrs->flavour = flavour;
10100 if (attrs->switch_id.id_len) {
10101 devlink_port->switch_port = true;
10102 if (WARN_ON(attrs->switch_id.id_len > MAX_PHYS_ITEM_ID_LEN))
10103 attrs->switch_id.id_len = MAX_PHYS_ITEM_ID_LEN;
10105 devlink_port->switch_port = false;
10111 * devlink_port_attrs_set - Set port attributes
10113 * @devlink_port: devlink port
10114 * @attrs: devlink port attrs
10116 void devlink_port_attrs_set(struct devlink_port *devlink_port,
10117 struct devlink_port_attrs *attrs)
10121 ASSERT_DEVLINK_PORT_NOT_REGISTERED(devlink_port);
10123 devlink_port->attrs = *attrs;
10124 ret = __devlink_port_attrs_set(devlink_port, attrs->flavour);
10127 WARN_ON(attrs->splittable && attrs->split);
10129 EXPORT_SYMBOL_GPL(devlink_port_attrs_set);
10132 * devlink_port_attrs_pci_pf_set - Set PCI PF port attributes
10134 * @devlink_port: devlink port
10135 * @controller: associated controller number for the devlink port instance
10136 * @pf: associated PF for the devlink port instance
10137 * @external: indicates if the port is for an external controller
10139 void devlink_port_attrs_pci_pf_set(struct devlink_port *devlink_port, u32 controller,
10140 u16 pf, bool external)
10142 struct devlink_port_attrs *attrs = &devlink_port->attrs;
10145 ASSERT_DEVLINK_PORT_NOT_REGISTERED(devlink_port);
10147 ret = __devlink_port_attrs_set(devlink_port,
10148 DEVLINK_PORT_FLAVOUR_PCI_PF);
10151 attrs->pci_pf.controller = controller;
10152 attrs->pci_pf.pf = pf;
10153 attrs->pci_pf.external = external;
10155 EXPORT_SYMBOL_GPL(devlink_port_attrs_pci_pf_set);
10158 * devlink_port_attrs_pci_vf_set - Set PCI VF port attributes
10160 * @devlink_port: devlink port
10161 * @controller: associated controller number for the devlink port instance
10162 * @pf: associated PF for the devlink port instance
10163 * @vf: associated VF of a PF for the devlink port instance
10164 * @external: indicates if the port is for an external controller
10166 void devlink_port_attrs_pci_vf_set(struct devlink_port *devlink_port, u32 controller,
10167 u16 pf, u16 vf, bool external)
10169 struct devlink_port_attrs *attrs = &devlink_port->attrs;
10172 ASSERT_DEVLINK_PORT_NOT_REGISTERED(devlink_port);
10174 ret = __devlink_port_attrs_set(devlink_port,
10175 DEVLINK_PORT_FLAVOUR_PCI_VF);
10178 attrs->pci_vf.controller = controller;
10179 attrs->pci_vf.pf = pf;
10180 attrs->pci_vf.vf = vf;
10181 attrs->pci_vf.external = external;
10183 EXPORT_SYMBOL_GPL(devlink_port_attrs_pci_vf_set);
10186 * devlink_port_attrs_pci_sf_set - Set PCI SF port attributes
10188 * @devlink_port: devlink port
10189 * @controller: associated controller number for the devlink port instance
10190 * @pf: associated PF for the devlink port instance
10191 * @sf: associated SF of a PF for the devlink port instance
10192 * @external: indicates if the port is for an external controller
10194 void devlink_port_attrs_pci_sf_set(struct devlink_port *devlink_port, u32 controller,
10195 u16 pf, u32 sf, bool external)
10197 struct devlink_port_attrs *attrs = &devlink_port->attrs;
10200 ASSERT_DEVLINK_PORT_NOT_REGISTERED(devlink_port);
10202 ret = __devlink_port_attrs_set(devlink_port,
10203 DEVLINK_PORT_FLAVOUR_PCI_SF);
10206 attrs->pci_sf.controller = controller;
10207 attrs->pci_sf.pf = pf;
10208 attrs->pci_sf.sf = sf;
10209 attrs->pci_sf.external = external;
10211 EXPORT_SYMBOL_GPL(devlink_port_attrs_pci_sf_set);
10214 * devl_rate_leaf_create - create devlink rate leaf
10215 * @devlink_port: devlink port object to create rate object on
10216 * @priv: driver private data
10218 * Create devlink rate object of type leaf on provided @devlink_port.
10220 int devl_rate_leaf_create(struct devlink_port *devlink_port, void *priv)
10222 struct devlink *devlink = devlink_port->devlink;
10223 struct devlink_rate *devlink_rate;
10225 devl_assert_locked(devlink_port->devlink);
10227 if (WARN_ON(devlink_port->devlink_rate))
10230 devlink_rate = kzalloc(sizeof(*devlink_rate), GFP_KERNEL);
10234 devlink_rate->type = DEVLINK_RATE_TYPE_LEAF;
10235 devlink_rate->devlink = devlink;
10236 devlink_rate->devlink_port = devlink_port;
10237 devlink_rate->priv = priv;
10238 list_add_tail(&devlink_rate->list, &devlink->rate_list);
10239 devlink_port->devlink_rate = devlink_rate;
10240 devlink_rate_notify(devlink_rate, DEVLINK_CMD_RATE_NEW);
10244 EXPORT_SYMBOL_GPL(devl_rate_leaf_create);
10247 * devl_rate_leaf_destroy - destroy devlink rate leaf
10249 * @devlink_port: devlink port linked to the rate object
10251 * Destroy the devlink rate object of type leaf on provided @devlink_port.
10253 void devl_rate_leaf_destroy(struct devlink_port *devlink_port)
10255 struct devlink_rate *devlink_rate = devlink_port->devlink_rate;
10257 devl_assert_locked(devlink_port->devlink);
10261 devlink_rate_notify(devlink_rate, DEVLINK_CMD_RATE_DEL);
10262 if (devlink_rate->parent)
10263 refcount_dec(&devlink_rate->parent->refcnt);
10264 list_del(&devlink_rate->list);
10265 devlink_port->devlink_rate = NULL;
10266 kfree(devlink_rate);
10268 EXPORT_SYMBOL_GPL(devl_rate_leaf_destroy);
10271 * devl_rate_nodes_destroy - destroy all devlink rate nodes on device
10272 * @devlink: devlink instance
10274 * Unset parent for all rate objects and destroy all rate nodes
10275 * on specified device.
10277 void devl_rate_nodes_destroy(struct devlink *devlink)
10279 static struct devlink_rate *devlink_rate, *tmp;
10280 const struct devlink_ops *ops = devlink->ops;
10282 devl_assert_locked(devlink);
10284 list_for_each_entry(devlink_rate, &devlink->rate_list, list) {
10285 if (!devlink_rate->parent)
10288 refcount_dec(&devlink_rate->parent->refcnt);
10289 if (devlink_rate_is_leaf(devlink_rate))
10290 ops->rate_leaf_parent_set(devlink_rate, NULL, devlink_rate->priv,
10292 else if (devlink_rate_is_node(devlink_rate))
10293 ops->rate_node_parent_set(devlink_rate, NULL, devlink_rate->priv,
10296 list_for_each_entry_safe(devlink_rate, tmp, &devlink->rate_list, list) {
10297 if (devlink_rate_is_node(devlink_rate)) {
10298 ops->rate_node_del(devlink_rate, devlink_rate->priv, NULL);
10299 list_del(&devlink_rate->list);
10300 kfree(devlink_rate->name);
10301 kfree(devlink_rate);
10305 EXPORT_SYMBOL_GPL(devl_rate_nodes_destroy);
10308 * devlink_port_linecard_set - Link port with a linecard
10310 * @devlink_port: devlink port
10311 * @linecard: devlink linecard
10313 void devlink_port_linecard_set(struct devlink_port *devlink_port,
10314 struct devlink_linecard *linecard)
10316 ASSERT_DEVLINK_PORT_NOT_REGISTERED(devlink_port);
10318 devlink_port->linecard = linecard;
10320 EXPORT_SYMBOL_GPL(devlink_port_linecard_set);
10322 static int __devlink_port_phys_port_name_get(struct devlink_port *devlink_port,
10323 char *name, size_t len)
10325 struct devlink_port_attrs *attrs = &devlink_port->attrs;
10328 if (!devlink_port->attrs_set)
10329 return -EOPNOTSUPP;
10331 switch (attrs->flavour) {
10332 case DEVLINK_PORT_FLAVOUR_PHYSICAL:
10333 if (devlink_port->linecard)
10334 n = snprintf(name, len, "l%u",
10335 devlink_port->linecard->index);
10337 n += snprintf(name + n, len - n, "p%u",
10338 attrs->phys.port_number);
10339 if (n < len && attrs->split)
10340 n += snprintf(name + n, len - n, "s%u",
10341 attrs->phys.split_subport_number);
10343 case DEVLINK_PORT_FLAVOUR_CPU:
10344 case DEVLINK_PORT_FLAVOUR_DSA:
10345 case DEVLINK_PORT_FLAVOUR_UNUSED:
10346 /* As CPU and DSA ports do not have a netdevice associated
10347 * case should not ever happen.
10351 case DEVLINK_PORT_FLAVOUR_PCI_PF:
10352 if (attrs->pci_pf.external) {
10353 n = snprintf(name, len, "c%u", attrs->pci_pf.controller);
10359 n = snprintf(name, len, "pf%u", attrs->pci_pf.pf);
10361 case DEVLINK_PORT_FLAVOUR_PCI_VF:
10362 if (attrs->pci_vf.external) {
10363 n = snprintf(name, len, "c%u", attrs->pci_vf.controller);
10369 n = snprintf(name, len, "pf%uvf%u",
10370 attrs->pci_vf.pf, attrs->pci_vf.vf);
10372 case DEVLINK_PORT_FLAVOUR_PCI_SF:
10373 if (attrs->pci_sf.external) {
10374 n = snprintf(name, len, "c%u", attrs->pci_sf.controller);
10380 n = snprintf(name, len, "pf%usf%u", attrs->pci_sf.pf,
10383 case DEVLINK_PORT_FLAVOUR_VIRTUAL:
10384 return -EOPNOTSUPP;
10393 static int devlink_linecard_types_init(struct devlink_linecard *linecard)
10395 struct devlink_linecard_type *linecard_type;
10396 unsigned int count;
10399 count = linecard->ops->types_count(linecard, linecard->priv);
10400 linecard->types = kmalloc_array(count, sizeof(*linecard_type),
10402 if (!linecard->types)
10404 linecard->types_count = count;
10406 for (i = 0; i < count; i++) {
10407 linecard_type = &linecard->types[i];
10408 linecard->ops->types_get(linecard, linecard->priv, i,
10409 &linecard_type->type,
10410 &linecard_type->priv);
10415 static void devlink_linecard_types_fini(struct devlink_linecard *linecard)
10417 kfree(linecard->types);
10421 * devlink_linecard_create - Create devlink linecard
10423 * @devlink: devlink
10424 * @linecard_index: driver-specific numerical identifier of the linecard
10425 * @ops: linecards ops
10426 * @priv: user priv pointer
10428 * Create devlink linecard instance with provided linecard index.
10429 * Caller can use any indexing, even hw-related one.
10431 * Return: Line card structure or an ERR_PTR() encoded error code.
10433 struct devlink_linecard *
10434 devlink_linecard_create(struct devlink *devlink, unsigned int linecard_index,
10435 const struct devlink_linecard_ops *ops, void *priv)
10437 struct devlink_linecard *linecard;
10440 if (WARN_ON(!ops || !ops->provision || !ops->unprovision ||
10441 !ops->types_count || !ops->types_get))
10442 return ERR_PTR(-EINVAL);
10444 mutex_lock(&devlink->linecards_lock);
10445 if (devlink_linecard_index_exists(devlink, linecard_index)) {
10446 mutex_unlock(&devlink->linecards_lock);
10447 return ERR_PTR(-EEXIST);
10450 linecard = kzalloc(sizeof(*linecard), GFP_KERNEL);
10452 mutex_unlock(&devlink->linecards_lock);
10453 return ERR_PTR(-ENOMEM);
10456 linecard->devlink = devlink;
10457 linecard->index = linecard_index;
10458 linecard->ops = ops;
10459 linecard->priv = priv;
10460 linecard->state = DEVLINK_LINECARD_STATE_UNPROVISIONED;
10461 mutex_init(&linecard->state_lock);
10463 err = devlink_linecard_types_init(linecard);
10465 mutex_destroy(&linecard->state_lock);
10467 mutex_unlock(&devlink->linecards_lock);
10468 return ERR_PTR(err);
10471 list_add_tail(&linecard->list, &devlink->linecard_list);
10472 refcount_set(&linecard->refcount, 1);
10473 mutex_unlock(&devlink->linecards_lock);
10474 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_NEW);
10477 EXPORT_SYMBOL_GPL(devlink_linecard_create);
10480 * devlink_linecard_destroy - Destroy devlink linecard
10482 * @linecard: devlink linecard
10484 void devlink_linecard_destroy(struct devlink_linecard *linecard)
10486 struct devlink *devlink = linecard->devlink;
10488 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_DEL);
10489 mutex_lock(&devlink->linecards_lock);
10490 list_del(&linecard->list);
10491 devlink_linecard_types_fini(linecard);
10492 mutex_unlock(&devlink->linecards_lock);
10493 devlink_linecard_put(linecard);
10495 EXPORT_SYMBOL_GPL(devlink_linecard_destroy);
10498 * devlink_linecard_provision_set - Set provisioning on linecard
10500 * @linecard: devlink linecard
10501 * @type: linecard type
10503 * This is either called directly from the provision() op call or
10504 * as a result of the provision() op call asynchronously.
10506 void devlink_linecard_provision_set(struct devlink_linecard *linecard,
10509 mutex_lock(&linecard->state_lock);
10510 WARN_ON(linecard->type && strcmp(linecard->type, type));
10511 linecard->state = DEVLINK_LINECARD_STATE_PROVISIONED;
10512 linecard->type = type;
10513 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_NEW);
10514 mutex_unlock(&linecard->state_lock);
10516 EXPORT_SYMBOL_GPL(devlink_linecard_provision_set);
10519 * devlink_linecard_provision_clear - Clear provisioning on linecard
10521 * @linecard: devlink linecard
10523 * This is either called directly from the unprovision() op call or
10524 * as a result of the unprovision() op call asynchronously.
10526 void devlink_linecard_provision_clear(struct devlink_linecard *linecard)
10528 mutex_lock(&linecard->state_lock);
10529 WARN_ON(linecard->nested_devlink);
10530 linecard->state = DEVLINK_LINECARD_STATE_UNPROVISIONED;
10531 linecard->type = NULL;
10532 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_NEW);
10533 mutex_unlock(&linecard->state_lock);
10535 EXPORT_SYMBOL_GPL(devlink_linecard_provision_clear);
10538 * devlink_linecard_provision_fail - Fail provisioning on linecard
10540 * @linecard: devlink linecard
10542 * This is either called directly from the provision() op call or
10543 * as a result of the provision() op call asynchronously.
10545 void devlink_linecard_provision_fail(struct devlink_linecard *linecard)
10547 mutex_lock(&linecard->state_lock);
10548 WARN_ON(linecard->nested_devlink);
10549 linecard->state = DEVLINK_LINECARD_STATE_PROVISIONING_FAILED;
10550 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_NEW);
10551 mutex_unlock(&linecard->state_lock);
10553 EXPORT_SYMBOL_GPL(devlink_linecard_provision_fail);
10556 * devlink_linecard_activate - Set linecard active
10558 * @linecard: devlink linecard
10560 void devlink_linecard_activate(struct devlink_linecard *linecard)
10562 mutex_lock(&linecard->state_lock);
10563 WARN_ON(linecard->state != DEVLINK_LINECARD_STATE_PROVISIONED);
10564 linecard->state = DEVLINK_LINECARD_STATE_ACTIVE;
10565 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_NEW);
10566 mutex_unlock(&linecard->state_lock);
10568 EXPORT_SYMBOL_GPL(devlink_linecard_activate);
10571 * devlink_linecard_deactivate - Set linecard inactive
10573 * @linecard: devlink linecard
10575 void devlink_linecard_deactivate(struct devlink_linecard *linecard)
10577 mutex_lock(&linecard->state_lock);
10578 switch (linecard->state) {
10579 case DEVLINK_LINECARD_STATE_ACTIVE:
10580 linecard->state = DEVLINK_LINECARD_STATE_PROVISIONED;
10581 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_NEW);
10583 case DEVLINK_LINECARD_STATE_UNPROVISIONING:
10584 /* Line card is being deactivated as part
10585 * of unprovisioning flow.
10592 mutex_unlock(&linecard->state_lock);
10594 EXPORT_SYMBOL_GPL(devlink_linecard_deactivate);
10597 * devlink_linecard_nested_dl_set - Attach/detach nested devlink
10598 * instance to linecard.
10600 * @linecard: devlink linecard
10601 * @nested_devlink: devlink instance to attach or NULL to detach
10603 void devlink_linecard_nested_dl_set(struct devlink_linecard *linecard,
10604 struct devlink *nested_devlink)
10606 mutex_lock(&linecard->state_lock);
10607 linecard->nested_devlink = nested_devlink;
10608 devlink_linecard_notify(linecard, DEVLINK_CMD_LINECARD_NEW);
10609 mutex_unlock(&linecard->state_lock);
10611 EXPORT_SYMBOL_GPL(devlink_linecard_nested_dl_set);
10613 int devl_sb_register(struct devlink *devlink, unsigned int sb_index,
10614 u32 size, u16 ingress_pools_count,
10615 u16 egress_pools_count, u16 ingress_tc_count,
10616 u16 egress_tc_count)
10618 struct devlink_sb *devlink_sb;
10620 lockdep_assert_held(&devlink->lock);
10622 if (devlink_sb_index_exists(devlink, sb_index))
10625 devlink_sb = kzalloc(sizeof(*devlink_sb), GFP_KERNEL);
10628 devlink_sb->index = sb_index;
10629 devlink_sb->size = size;
10630 devlink_sb->ingress_pools_count = ingress_pools_count;
10631 devlink_sb->egress_pools_count = egress_pools_count;
10632 devlink_sb->ingress_tc_count = ingress_tc_count;
10633 devlink_sb->egress_tc_count = egress_tc_count;
10634 list_add_tail(&devlink_sb->list, &devlink->sb_list);
10637 EXPORT_SYMBOL_GPL(devl_sb_register);
10639 int devlink_sb_register(struct devlink *devlink, unsigned int sb_index,
10640 u32 size, u16 ingress_pools_count,
10641 u16 egress_pools_count, u16 ingress_tc_count,
10642 u16 egress_tc_count)
10646 devl_lock(devlink);
10647 err = devl_sb_register(devlink, sb_index, size, ingress_pools_count,
10648 egress_pools_count, ingress_tc_count,
10650 devl_unlock(devlink);
10653 EXPORT_SYMBOL_GPL(devlink_sb_register);
10655 void devl_sb_unregister(struct devlink *devlink, unsigned int sb_index)
10657 struct devlink_sb *devlink_sb;
10659 lockdep_assert_held(&devlink->lock);
10661 devlink_sb = devlink_sb_get_by_index(devlink, sb_index);
10662 WARN_ON(!devlink_sb);
10663 list_del(&devlink_sb->list);
10666 EXPORT_SYMBOL_GPL(devl_sb_unregister);
10668 void devlink_sb_unregister(struct devlink *devlink, unsigned int sb_index)
10670 devl_lock(devlink);
10671 devl_sb_unregister(devlink, sb_index);
10672 devl_unlock(devlink);
10674 EXPORT_SYMBOL_GPL(devlink_sb_unregister);
10677 * devl_dpipe_headers_register - register dpipe headers
10679 * @devlink: devlink
10680 * @dpipe_headers: dpipe header array
10682 * Register the headers supported by hardware.
10684 void devl_dpipe_headers_register(struct devlink *devlink,
10685 struct devlink_dpipe_headers *dpipe_headers)
10687 lockdep_assert_held(&devlink->lock);
10689 devlink->dpipe_headers = dpipe_headers;
10691 EXPORT_SYMBOL_GPL(devl_dpipe_headers_register);
10694 * devl_dpipe_headers_unregister - unregister dpipe headers
10696 * @devlink: devlink
10698 * Unregister the headers supported by hardware.
10700 void devl_dpipe_headers_unregister(struct devlink *devlink)
10702 lockdep_assert_held(&devlink->lock);
10704 devlink->dpipe_headers = NULL;
10706 EXPORT_SYMBOL_GPL(devl_dpipe_headers_unregister);
10709 * devlink_dpipe_table_counter_enabled - check if counter allocation
10711 * @devlink: devlink
10712 * @table_name: tables name
10714 * Used by driver to check if counter allocation is required.
10715 * After counter allocation is turned on the table entries
10716 * are updated to include counter statistics.
10718 * After that point on the driver must respect the counter
10719 * state so that each entry added to the table is added
10722 bool devlink_dpipe_table_counter_enabled(struct devlink *devlink,
10723 const char *table_name)
10725 struct devlink_dpipe_table *table;
10729 table = devlink_dpipe_table_find(&devlink->dpipe_table_list,
10730 table_name, devlink);
10733 enabled = table->counters_enabled;
10737 EXPORT_SYMBOL_GPL(devlink_dpipe_table_counter_enabled);
10740 * devl_dpipe_table_register - register dpipe table
10742 * @devlink: devlink
10743 * @table_name: table name
10744 * @table_ops: table ops
10746 * @counter_control_extern: external control for counters
10748 int devl_dpipe_table_register(struct devlink *devlink,
10749 const char *table_name,
10750 struct devlink_dpipe_table_ops *table_ops,
10751 void *priv, bool counter_control_extern)
10753 struct devlink_dpipe_table *table;
10755 lockdep_assert_held(&devlink->lock);
10757 if (WARN_ON(!table_ops->size_get))
10760 if (devlink_dpipe_table_find(&devlink->dpipe_table_list, table_name,
10764 table = kzalloc(sizeof(*table), GFP_KERNEL);
10768 table->name = table_name;
10769 table->table_ops = table_ops;
10770 table->priv = priv;
10771 table->counter_control_extern = counter_control_extern;
10773 list_add_tail_rcu(&table->list, &devlink->dpipe_table_list);
10777 EXPORT_SYMBOL_GPL(devl_dpipe_table_register);
10780 * devl_dpipe_table_unregister - unregister dpipe table
10782 * @devlink: devlink
10783 * @table_name: table name
10785 void devl_dpipe_table_unregister(struct devlink *devlink,
10786 const char *table_name)
10788 struct devlink_dpipe_table *table;
10790 lockdep_assert_held(&devlink->lock);
10792 table = devlink_dpipe_table_find(&devlink->dpipe_table_list,
10793 table_name, devlink);
10796 list_del_rcu(&table->list);
10797 kfree_rcu(table, rcu);
10799 EXPORT_SYMBOL_GPL(devl_dpipe_table_unregister);
10802 * devl_resource_register - devlink resource register
10804 * @devlink: devlink
10805 * @resource_name: resource's name
10806 * @resource_size: resource's size
10807 * @resource_id: resource's id
10808 * @parent_resource_id: resource's parent id
10809 * @size_params: size parameters
10811 * Generic resources should reuse the same names across drivers.
10812 * Please see the generic resources list at:
10813 * Documentation/networking/devlink/devlink-resource.rst
10815 int devl_resource_register(struct devlink *devlink,
10816 const char *resource_name,
10819 u64 parent_resource_id,
10820 const struct devlink_resource_size_params *size_params)
10822 struct devlink_resource *resource;
10823 struct list_head *resource_list;
10824 bool top_hierarchy;
10826 lockdep_assert_held(&devlink->lock);
10828 top_hierarchy = parent_resource_id == DEVLINK_RESOURCE_ID_PARENT_TOP;
10830 resource = devlink_resource_find(devlink, NULL, resource_id);
10834 resource = kzalloc(sizeof(*resource), GFP_KERNEL);
10838 if (top_hierarchy) {
10839 resource_list = &devlink->resource_list;
10841 struct devlink_resource *parent_resource;
10843 parent_resource = devlink_resource_find(devlink, NULL,
10844 parent_resource_id);
10845 if (parent_resource) {
10846 resource_list = &parent_resource->resource_list;
10847 resource->parent = parent_resource;
10854 resource->name = resource_name;
10855 resource->size = resource_size;
10856 resource->size_new = resource_size;
10857 resource->id = resource_id;
10858 resource->size_valid = true;
10859 memcpy(&resource->size_params, size_params,
10860 sizeof(resource->size_params));
10861 INIT_LIST_HEAD(&resource->resource_list);
10862 list_add_tail(&resource->list, resource_list);
10866 EXPORT_SYMBOL_GPL(devl_resource_register);
10869 * devlink_resource_register - devlink resource register
10871 * @devlink: devlink
10872 * @resource_name: resource's name
10873 * @resource_size: resource's size
10874 * @resource_id: resource's id
10875 * @parent_resource_id: resource's parent id
10876 * @size_params: size parameters
10878 * Generic resources should reuse the same names across drivers.
10879 * Please see the generic resources list at:
10880 * Documentation/networking/devlink/devlink-resource.rst
10882 * Context: Takes and release devlink->lock <mutex>.
10884 int devlink_resource_register(struct devlink *devlink,
10885 const char *resource_name,
10888 u64 parent_resource_id,
10889 const struct devlink_resource_size_params *size_params)
10893 devl_lock(devlink);
10894 err = devl_resource_register(devlink, resource_name, resource_size,
10895 resource_id, parent_resource_id, size_params);
10896 devl_unlock(devlink);
10899 EXPORT_SYMBOL_GPL(devlink_resource_register);
10901 static void devlink_resource_unregister(struct devlink *devlink,
10902 struct devlink_resource *resource)
10904 struct devlink_resource *tmp, *child_resource;
10906 list_for_each_entry_safe(child_resource, tmp, &resource->resource_list,
10908 devlink_resource_unregister(devlink, child_resource);
10909 list_del(&child_resource->list);
10910 kfree(child_resource);
10915 * devl_resources_unregister - free all resources
10917 * @devlink: devlink
10919 void devl_resources_unregister(struct devlink *devlink)
10921 struct devlink_resource *tmp, *child_resource;
10923 lockdep_assert_held(&devlink->lock);
10925 list_for_each_entry_safe(child_resource, tmp, &devlink->resource_list,
10927 devlink_resource_unregister(devlink, child_resource);
10928 list_del(&child_resource->list);
10929 kfree(child_resource);
10932 EXPORT_SYMBOL_GPL(devl_resources_unregister);
10935 * devlink_resources_unregister - free all resources
10937 * @devlink: devlink
10939 * Context: Takes and release devlink->lock <mutex>.
10941 void devlink_resources_unregister(struct devlink *devlink)
10943 devl_lock(devlink);
10944 devl_resources_unregister(devlink);
10945 devl_unlock(devlink);
10947 EXPORT_SYMBOL_GPL(devlink_resources_unregister);
10950 * devl_resource_size_get - get and update size
10952 * @devlink: devlink
10953 * @resource_id: the requested resource id
10954 * @p_resource_size: ptr to update
10956 int devl_resource_size_get(struct devlink *devlink,
10958 u64 *p_resource_size)
10960 struct devlink_resource *resource;
10962 lockdep_assert_held(&devlink->lock);
10964 resource = devlink_resource_find(devlink, NULL, resource_id);
10967 *p_resource_size = resource->size_new;
10968 resource->size = resource->size_new;
10971 EXPORT_SYMBOL_GPL(devl_resource_size_get);
10974 * devl_dpipe_table_resource_set - set the resource id
10976 * @devlink: devlink
10977 * @table_name: table name
10978 * @resource_id: resource id
10979 * @resource_units: number of resource's units consumed per table's entry
10981 int devl_dpipe_table_resource_set(struct devlink *devlink,
10982 const char *table_name, u64 resource_id,
10983 u64 resource_units)
10985 struct devlink_dpipe_table *table;
10987 table = devlink_dpipe_table_find(&devlink->dpipe_table_list,
10988 table_name, devlink);
10992 table->resource_id = resource_id;
10993 table->resource_units = resource_units;
10994 table->resource_valid = true;
10997 EXPORT_SYMBOL_GPL(devl_dpipe_table_resource_set);
11000 * devl_resource_occ_get_register - register occupancy getter
11002 * @devlink: devlink
11003 * @resource_id: resource id
11004 * @occ_get: occupancy getter callback
11005 * @occ_get_priv: occupancy getter callback priv
11007 void devl_resource_occ_get_register(struct devlink *devlink,
11009 devlink_resource_occ_get_t *occ_get,
11010 void *occ_get_priv)
11012 struct devlink_resource *resource;
11014 lockdep_assert_held(&devlink->lock);
11016 resource = devlink_resource_find(devlink, NULL, resource_id);
11017 if (WARN_ON(!resource))
11019 WARN_ON(resource->occ_get);
11021 resource->occ_get = occ_get;
11022 resource->occ_get_priv = occ_get_priv;
11024 EXPORT_SYMBOL_GPL(devl_resource_occ_get_register);
11027 * devlink_resource_occ_get_register - register occupancy getter
11029 * @devlink: devlink
11030 * @resource_id: resource id
11031 * @occ_get: occupancy getter callback
11032 * @occ_get_priv: occupancy getter callback priv
11034 * Context: Takes and release devlink->lock <mutex>.
11036 void devlink_resource_occ_get_register(struct devlink *devlink,
11038 devlink_resource_occ_get_t *occ_get,
11039 void *occ_get_priv)
11041 devl_lock(devlink);
11042 devl_resource_occ_get_register(devlink, resource_id,
11043 occ_get, occ_get_priv);
11044 devl_unlock(devlink);
11046 EXPORT_SYMBOL_GPL(devlink_resource_occ_get_register);
11049 * devl_resource_occ_get_unregister - unregister occupancy getter
11051 * @devlink: devlink
11052 * @resource_id: resource id
11054 void devl_resource_occ_get_unregister(struct devlink *devlink,
11057 struct devlink_resource *resource;
11059 lockdep_assert_held(&devlink->lock);
11061 resource = devlink_resource_find(devlink, NULL, resource_id);
11062 if (WARN_ON(!resource))
11064 WARN_ON(!resource->occ_get);
11066 resource->occ_get = NULL;
11067 resource->occ_get_priv = NULL;
11069 EXPORT_SYMBOL_GPL(devl_resource_occ_get_unregister);
11072 * devlink_resource_occ_get_unregister - unregister occupancy getter
11074 * @devlink: devlink
11075 * @resource_id: resource id
11077 * Context: Takes and release devlink->lock <mutex>.
11079 void devlink_resource_occ_get_unregister(struct devlink *devlink,
11082 devl_lock(devlink);
11083 devl_resource_occ_get_unregister(devlink, resource_id);
11084 devl_unlock(devlink);
11086 EXPORT_SYMBOL_GPL(devlink_resource_occ_get_unregister);
11088 static int devlink_param_verify(const struct devlink_param *param)
11090 if (!param || !param->name || !param->supported_cmodes)
11092 if (param->generic)
11093 return devlink_param_generic_verify(param);
11095 return devlink_param_driver_verify(param);
11099 * devlink_params_register - register configuration parameters
11101 * @devlink: devlink
11102 * @params: configuration parameters array
11103 * @params_count: number of parameters provided
11105 * Register the configuration parameters supported by the driver.
11107 int devlink_params_register(struct devlink *devlink,
11108 const struct devlink_param *params,
11109 size_t params_count)
11111 const struct devlink_param *param = params;
11114 ASSERT_DEVLINK_NOT_REGISTERED(devlink);
11116 for (i = 0; i < params_count; i++, param++) {
11117 err = devlink_param_register(devlink, param);
11127 for (param--; i > 0; i--, param--)
11128 devlink_param_unregister(devlink, param);
11131 EXPORT_SYMBOL_GPL(devlink_params_register);
11134 * devlink_params_unregister - unregister configuration parameters
11135 * @devlink: devlink
11136 * @params: configuration parameters to unregister
11137 * @params_count: number of parameters provided
11139 void devlink_params_unregister(struct devlink *devlink,
11140 const struct devlink_param *params,
11141 size_t params_count)
11143 const struct devlink_param *param = params;
11146 ASSERT_DEVLINK_NOT_REGISTERED(devlink);
11148 for (i = 0; i < params_count; i++, param++)
11149 devlink_param_unregister(devlink, param);
11151 EXPORT_SYMBOL_GPL(devlink_params_unregister);
11154 * devlink_param_register - register one configuration parameter
11156 * @devlink: devlink
11157 * @param: one configuration parameter
11159 * Register the configuration parameter supported by the driver.
11160 * Return: returns 0 on successful registration or error code otherwise.
11162 int devlink_param_register(struct devlink *devlink,
11163 const struct devlink_param *param)
11165 struct devlink_param_item *param_item;
11167 ASSERT_DEVLINK_NOT_REGISTERED(devlink);
11169 WARN_ON(devlink_param_verify(param));
11170 WARN_ON(devlink_param_find_by_name(&devlink->param_list, param->name));
11172 if (param->supported_cmodes == BIT(DEVLINK_PARAM_CMODE_DRIVERINIT))
11173 WARN_ON(param->get || param->set);
11175 WARN_ON(!param->get || !param->set);
11177 param_item = kzalloc(sizeof(*param_item), GFP_KERNEL);
11181 param_item->param = param;
11183 list_add_tail(¶m_item->list, &devlink->param_list);
11186 EXPORT_SYMBOL_GPL(devlink_param_register);
11189 * devlink_param_unregister - unregister one configuration parameter
11190 * @devlink: devlink
11191 * @param: configuration parameter to unregister
11193 void devlink_param_unregister(struct devlink *devlink,
11194 const struct devlink_param *param)
11196 struct devlink_param_item *param_item;
11198 ASSERT_DEVLINK_NOT_REGISTERED(devlink);
11201 devlink_param_find_by_name(&devlink->param_list, param->name);
11202 WARN_ON(!param_item);
11203 list_del(¶m_item->list);
11206 EXPORT_SYMBOL_GPL(devlink_param_unregister);
11209 * devlink_param_driverinit_value_get - get configuration parameter
11210 * value for driver initializing
11212 * @devlink: devlink
11213 * @param_id: parameter ID
11214 * @init_val: value of parameter in driverinit configuration mode
11216 * This function should be used by the driver to get driverinit
11217 * configuration for initialization after reload command.
11219 int devlink_param_driverinit_value_get(struct devlink *devlink, u32 param_id,
11220 union devlink_param_value *init_val)
11222 struct devlink_param_item *param_item;
11224 if (!devlink_reload_supported(devlink->ops))
11225 return -EOPNOTSUPP;
11227 param_item = devlink_param_find_by_id(&devlink->param_list, param_id);
11231 if (!param_item->driverinit_value_valid ||
11232 !devlink_param_cmode_is_supported(param_item->param,
11233 DEVLINK_PARAM_CMODE_DRIVERINIT))
11234 return -EOPNOTSUPP;
11236 if (param_item->param->type == DEVLINK_PARAM_TYPE_STRING)
11237 strcpy(init_val->vstr, param_item->driverinit_value.vstr);
11239 *init_val = param_item->driverinit_value;
11243 EXPORT_SYMBOL_GPL(devlink_param_driverinit_value_get);
11246 * devlink_param_driverinit_value_set - set value of configuration
11247 * parameter for driverinit
11248 * configuration mode
11250 * @devlink: devlink
11251 * @param_id: parameter ID
11252 * @init_val: value of parameter to set for driverinit configuration mode
11254 * This function should be used by the driver to set driverinit
11255 * configuration mode default value.
11257 int devlink_param_driverinit_value_set(struct devlink *devlink, u32 param_id,
11258 union devlink_param_value init_val)
11260 struct devlink_param_item *param_item;
11262 ASSERT_DEVLINK_NOT_REGISTERED(devlink);
11264 param_item = devlink_param_find_by_id(&devlink->param_list, param_id);
11268 if (!devlink_param_cmode_is_supported(param_item->param,
11269 DEVLINK_PARAM_CMODE_DRIVERINIT))
11270 return -EOPNOTSUPP;
11272 if (param_item->param->type == DEVLINK_PARAM_TYPE_STRING)
11273 strcpy(param_item->driverinit_value.vstr, init_val.vstr);
11275 param_item->driverinit_value = init_val;
11276 param_item->driverinit_value_valid = true;
11279 EXPORT_SYMBOL_GPL(devlink_param_driverinit_value_set);
11282 * devlink_param_value_changed - notify devlink on a parameter's value
11283 * change. Should be called by the driver
11284 * right after the change.
11286 * @devlink: devlink
11287 * @param_id: parameter ID
11289 * This function should be used by the driver to notify devlink on value
11290 * change, excluding driverinit configuration mode.
11291 * For driverinit configuration mode driver should use the function
11293 void devlink_param_value_changed(struct devlink *devlink, u32 param_id)
11295 struct devlink_param_item *param_item;
11297 param_item = devlink_param_find_by_id(&devlink->param_list, param_id);
11298 WARN_ON(!param_item);
11300 devlink_param_notify(devlink, 0, param_item, DEVLINK_CMD_PARAM_NEW);
11302 EXPORT_SYMBOL_GPL(devlink_param_value_changed);
11305 * devl_region_create - create a new address region
11307 * @devlink: devlink
11308 * @ops: region operations and name
11309 * @region_max_snapshots: Maximum supported number of snapshots for region
11310 * @region_size: size of region
11312 struct devlink_region *devl_region_create(struct devlink *devlink,
11313 const struct devlink_region_ops *ops,
11314 u32 region_max_snapshots,
11317 struct devlink_region *region;
11319 devl_assert_locked(devlink);
11321 if (WARN_ON(!ops) || WARN_ON(!ops->destructor))
11322 return ERR_PTR(-EINVAL);
11324 if (devlink_region_get_by_name(devlink, ops->name))
11325 return ERR_PTR(-EEXIST);
11327 region = kzalloc(sizeof(*region), GFP_KERNEL);
11329 return ERR_PTR(-ENOMEM);
11331 region->devlink = devlink;
11332 region->max_snapshots = region_max_snapshots;
11334 region->size = region_size;
11335 INIT_LIST_HEAD(®ion->snapshot_list);
11336 mutex_init(®ion->snapshot_lock);
11337 list_add_tail(®ion->list, &devlink->region_list);
11338 devlink_nl_region_notify(region, NULL, DEVLINK_CMD_REGION_NEW);
11342 EXPORT_SYMBOL_GPL(devl_region_create);
11345 * devlink_region_create - create a new address region
11347 * @devlink: devlink
11348 * @ops: region operations and name
11349 * @region_max_snapshots: Maximum supported number of snapshots for region
11350 * @region_size: size of region
11352 * Context: Takes and release devlink->lock <mutex>.
11354 struct devlink_region *
11355 devlink_region_create(struct devlink *devlink,
11356 const struct devlink_region_ops *ops,
11357 u32 region_max_snapshots, u64 region_size)
11359 struct devlink_region *region;
11361 devl_lock(devlink);
11362 region = devl_region_create(devlink, ops, region_max_snapshots,
11364 devl_unlock(devlink);
11367 EXPORT_SYMBOL_GPL(devlink_region_create);
11370 * devlink_port_region_create - create a new address region for a port
11372 * @port: devlink port
11373 * @ops: region operations and name
11374 * @region_max_snapshots: Maximum supported number of snapshots for region
11375 * @region_size: size of region
11377 * Context: Takes and release devlink->lock <mutex>.
11379 struct devlink_region *
11380 devlink_port_region_create(struct devlink_port *port,
11381 const struct devlink_port_region_ops *ops,
11382 u32 region_max_snapshots, u64 region_size)
11384 struct devlink *devlink = port->devlink;
11385 struct devlink_region *region;
11388 ASSERT_DEVLINK_PORT_INITIALIZED(port);
11390 if (WARN_ON(!ops) || WARN_ON(!ops->destructor))
11391 return ERR_PTR(-EINVAL);
11393 devl_lock(devlink);
11395 if (devlink_port_region_get_by_name(port, ops->name)) {
11400 region = kzalloc(sizeof(*region), GFP_KERNEL);
11406 region->devlink = devlink;
11407 region->port = port;
11408 region->max_snapshots = region_max_snapshots;
11409 region->port_ops = ops;
11410 region->size = region_size;
11411 INIT_LIST_HEAD(®ion->snapshot_list);
11412 mutex_init(®ion->snapshot_lock);
11413 list_add_tail(®ion->list, &port->region_list);
11414 devlink_nl_region_notify(region, NULL, DEVLINK_CMD_REGION_NEW);
11416 devl_unlock(devlink);
11420 devl_unlock(devlink);
11421 return ERR_PTR(err);
11423 EXPORT_SYMBOL_GPL(devlink_port_region_create);
11426 * devl_region_destroy - destroy address region
11428 * @region: devlink region to destroy
11430 void devl_region_destroy(struct devlink_region *region)
11432 struct devlink *devlink = region->devlink;
11433 struct devlink_snapshot *snapshot, *ts;
11435 devl_assert_locked(devlink);
11437 /* Free all snapshots of region */
11438 list_for_each_entry_safe(snapshot, ts, ®ion->snapshot_list, list)
11439 devlink_region_snapshot_del(region, snapshot);
11441 list_del(®ion->list);
11442 mutex_destroy(®ion->snapshot_lock);
11444 devlink_nl_region_notify(region, NULL, DEVLINK_CMD_REGION_DEL);
11447 EXPORT_SYMBOL_GPL(devl_region_destroy);
11450 * devlink_region_destroy - destroy address region
11452 * @region: devlink region to destroy
11454 * Context: Takes and release devlink->lock <mutex>.
11456 void devlink_region_destroy(struct devlink_region *region)
11458 struct devlink *devlink = region->devlink;
11460 devl_lock(devlink);
11461 devl_region_destroy(region);
11462 devl_unlock(devlink);
11464 EXPORT_SYMBOL_GPL(devlink_region_destroy);
11467 * devlink_region_snapshot_id_get - get snapshot ID
11469 * This callback should be called when adding a new snapshot,
11470 * Driver should use the same id for multiple snapshots taken
11471 * on multiple regions at the same time/by the same trigger.
11473 * The caller of this function must use devlink_region_snapshot_id_put
11474 * when finished creating regions using this id.
11476 * Returns zero on success, or a negative error code on failure.
11478 * @devlink: devlink
11479 * @id: storage to return id
11481 int devlink_region_snapshot_id_get(struct devlink *devlink, u32 *id)
11483 return __devlink_region_snapshot_id_get(devlink, id);
11485 EXPORT_SYMBOL_GPL(devlink_region_snapshot_id_get);
11488 * devlink_region_snapshot_id_put - put snapshot ID reference
11490 * This should be called by a driver after finishing creating snapshots
11491 * with an id. Doing so ensures that the ID can later be released in the
11492 * event that all snapshots using it have been destroyed.
11494 * @devlink: devlink
11495 * @id: id to release reference on
11497 void devlink_region_snapshot_id_put(struct devlink *devlink, u32 id)
11499 __devlink_snapshot_id_decrement(devlink, id);
11501 EXPORT_SYMBOL_GPL(devlink_region_snapshot_id_put);
11504 * devlink_region_snapshot_create - create a new snapshot
11505 * This will add a new snapshot of a region. The snapshot
11506 * will be stored on the region struct and can be accessed
11507 * from devlink. This is useful for future analyses of snapshots.
11508 * Multiple snapshots can be created on a region.
11509 * The @snapshot_id should be obtained using the getter function.
11511 * @region: devlink region of the snapshot
11512 * @data: snapshot data
11513 * @snapshot_id: snapshot id to be created
11515 int devlink_region_snapshot_create(struct devlink_region *region,
11516 u8 *data, u32 snapshot_id)
11520 mutex_lock(®ion->snapshot_lock);
11521 err = __devlink_region_snapshot_create(region, data, snapshot_id);
11522 mutex_unlock(®ion->snapshot_lock);
11525 EXPORT_SYMBOL_GPL(devlink_region_snapshot_create);
11527 #define DEVLINK_TRAP(_id, _type) \
11529 .type = DEVLINK_TRAP_TYPE_##_type, \
11530 .id = DEVLINK_TRAP_GENERIC_ID_##_id, \
11531 .name = DEVLINK_TRAP_GENERIC_NAME_##_id, \
11534 static const struct devlink_trap devlink_trap_generic[] = {
11535 DEVLINK_TRAP(SMAC_MC, DROP),
11536 DEVLINK_TRAP(VLAN_TAG_MISMATCH, DROP),
11537 DEVLINK_TRAP(INGRESS_VLAN_FILTER, DROP),
11538 DEVLINK_TRAP(INGRESS_STP_FILTER, DROP),
11539 DEVLINK_TRAP(EMPTY_TX_LIST, DROP),
11540 DEVLINK_TRAP(PORT_LOOPBACK_FILTER, DROP),
11541 DEVLINK_TRAP(BLACKHOLE_ROUTE, DROP),
11542 DEVLINK_TRAP(TTL_ERROR, EXCEPTION),
11543 DEVLINK_TRAP(TAIL_DROP, DROP),
11544 DEVLINK_TRAP(NON_IP_PACKET, DROP),
11545 DEVLINK_TRAP(UC_DIP_MC_DMAC, DROP),
11546 DEVLINK_TRAP(DIP_LB, DROP),
11547 DEVLINK_TRAP(SIP_MC, DROP),
11548 DEVLINK_TRAP(SIP_LB, DROP),
11549 DEVLINK_TRAP(CORRUPTED_IP_HDR, DROP),
11550 DEVLINK_TRAP(IPV4_SIP_BC, DROP),
11551 DEVLINK_TRAP(IPV6_MC_DIP_RESERVED_SCOPE, DROP),
11552 DEVLINK_TRAP(IPV6_MC_DIP_INTERFACE_LOCAL_SCOPE, DROP),
11553 DEVLINK_TRAP(MTU_ERROR, EXCEPTION),
11554 DEVLINK_TRAP(UNRESOLVED_NEIGH, EXCEPTION),
11555 DEVLINK_TRAP(RPF, EXCEPTION),
11556 DEVLINK_TRAP(REJECT_ROUTE, EXCEPTION),
11557 DEVLINK_TRAP(IPV4_LPM_UNICAST_MISS, EXCEPTION),
11558 DEVLINK_TRAP(IPV6_LPM_UNICAST_MISS, EXCEPTION),
11559 DEVLINK_TRAP(NON_ROUTABLE, DROP),
11560 DEVLINK_TRAP(DECAP_ERROR, EXCEPTION),
11561 DEVLINK_TRAP(OVERLAY_SMAC_MC, DROP),
11562 DEVLINK_TRAP(INGRESS_FLOW_ACTION_DROP, DROP),
11563 DEVLINK_TRAP(EGRESS_FLOW_ACTION_DROP, DROP),
11564 DEVLINK_TRAP(STP, CONTROL),
11565 DEVLINK_TRAP(LACP, CONTROL),
11566 DEVLINK_TRAP(LLDP, CONTROL),
11567 DEVLINK_TRAP(IGMP_QUERY, CONTROL),
11568 DEVLINK_TRAP(IGMP_V1_REPORT, CONTROL),
11569 DEVLINK_TRAP(IGMP_V2_REPORT, CONTROL),
11570 DEVLINK_TRAP(IGMP_V3_REPORT, CONTROL),
11571 DEVLINK_TRAP(IGMP_V2_LEAVE, CONTROL),
11572 DEVLINK_TRAP(MLD_QUERY, CONTROL),
11573 DEVLINK_TRAP(MLD_V1_REPORT, CONTROL),
11574 DEVLINK_TRAP(MLD_V2_REPORT, CONTROL),
11575 DEVLINK_TRAP(MLD_V1_DONE, CONTROL),
11576 DEVLINK_TRAP(IPV4_DHCP, CONTROL),
11577 DEVLINK_TRAP(IPV6_DHCP, CONTROL),
11578 DEVLINK_TRAP(ARP_REQUEST, CONTROL),
11579 DEVLINK_TRAP(ARP_RESPONSE, CONTROL),
11580 DEVLINK_TRAP(ARP_OVERLAY, CONTROL),
11581 DEVLINK_TRAP(IPV6_NEIGH_SOLICIT, CONTROL),
11582 DEVLINK_TRAP(IPV6_NEIGH_ADVERT, CONTROL),
11583 DEVLINK_TRAP(IPV4_BFD, CONTROL),
11584 DEVLINK_TRAP(IPV6_BFD, CONTROL),
11585 DEVLINK_TRAP(IPV4_OSPF, CONTROL),
11586 DEVLINK_TRAP(IPV6_OSPF, CONTROL),
11587 DEVLINK_TRAP(IPV4_BGP, CONTROL),
11588 DEVLINK_TRAP(IPV6_BGP, CONTROL),
11589 DEVLINK_TRAP(IPV4_VRRP, CONTROL),
11590 DEVLINK_TRAP(IPV6_VRRP, CONTROL),
11591 DEVLINK_TRAP(IPV4_PIM, CONTROL),
11592 DEVLINK_TRAP(IPV6_PIM, CONTROL),
11593 DEVLINK_TRAP(UC_LB, CONTROL),
11594 DEVLINK_TRAP(LOCAL_ROUTE, CONTROL),
11595 DEVLINK_TRAP(EXTERNAL_ROUTE, CONTROL),
11596 DEVLINK_TRAP(IPV6_UC_DIP_LINK_LOCAL_SCOPE, CONTROL),
11597 DEVLINK_TRAP(IPV6_DIP_ALL_NODES, CONTROL),
11598 DEVLINK_TRAP(IPV6_DIP_ALL_ROUTERS, CONTROL),
11599 DEVLINK_TRAP(IPV6_ROUTER_SOLICIT, CONTROL),
11600 DEVLINK_TRAP(IPV6_ROUTER_ADVERT, CONTROL),
11601 DEVLINK_TRAP(IPV6_REDIRECT, CONTROL),
11602 DEVLINK_TRAP(IPV4_ROUTER_ALERT, CONTROL),
11603 DEVLINK_TRAP(IPV6_ROUTER_ALERT, CONTROL),
11604 DEVLINK_TRAP(PTP_EVENT, CONTROL),
11605 DEVLINK_TRAP(PTP_GENERAL, CONTROL),
11606 DEVLINK_TRAP(FLOW_ACTION_SAMPLE, CONTROL),
11607 DEVLINK_TRAP(FLOW_ACTION_TRAP, CONTROL),
11608 DEVLINK_TRAP(EARLY_DROP, DROP),
11609 DEVLINK_TRAP(VXLAN_PARSING, DROP),
11610 DEVLINK_TRAP(LLC_SNAP_PARSING, DROP),
11611 DEVLINK_TRAP(VLAN_PARSING, DROP),
11612 DEVLINK_TRAP(PPPOE_PPP_PARSING, DROP),
11613 DEVLINK_TRAP(MPLS_PARSING, DROP),
11614 DEVLINK_TRAP(ARP_PARSING, DROP),
11615 DEVLINK_TRAP(IP_1_PARSING, DROP),
11616 DEVLINK_TRAP(IP_N_PARSING, DROP),
11617 DEVLINK_TRAP(GRE_PARSING, DROP),
11618 DEVLINK_TRAP(UDP_PARSING, DROP),
11619 DEVLINK_TRAP(TCP_PARSING, DROP),
11620 DEVLINK_TRAP(IPSEC_PARSING, DROP),
11621 DEVLINK_TRAP(SCTP_PARSING, DROP),
11622 DEVLINK_TRAP(DCCP_PARSING, DROP),
11623 DEVLINK_TRAP(GTP_PARSING, DROP),
11624 DEVLINK_TRAP(ESP_PARSING, DROP),
11625 DEVLINK_TRAP(BLACKHOLE_NEXTHOP, DROP),
11626 DEVLINK_TRAP(DMAC_FILTER, DROP),
11629 #define DEVLINK_TRAP_GROUP(_id) \
11631 .id = DEVLINK_TRAP_GROUP_GENERIC_ID_##_id, \
11632 .name = DEVLINK_TRAP_GROUP_GENERIC_NAME_##_id, \
11635 static const struct devlink_trap_group devlink_trap_group_generic[] = {
11636 DEVLINK_TRAP_GROUP(L2_DROPS),
11637 DEVLINK_TRAP_GROUP(L3_DROPS),
11638 DEVLINK_TRAP_GROUP(L3_EXCEPTIONS),
11639 DEVLINK_TRAP_GROUP(BUFFER_DROPS),
11640 DEVLINK_TRAP_GROUP(TUNNEL_DROPS),
11641 DEVLINK_TRAP_GROUP(ACL_DROPS),
11642 DEVLINK_TRAP_GROUP(STP),
11643 DEVLINK_TRAP_GROUP(LACP),
11644 DEVLINK_TRAP_GROUP(LLDP),
11645 DEVLINK_TRAP_GROUP(MC_SNOOPING),
11646 DEVLINK_TRAP_GROUP(DHCP),
11647 DEVLINK_TRAP_GROUP(NEIGH_DISCOVERY),
11648 DEVLINK_TRAP_GROUP(BFD),
11649 DEVLINK_TRAP_GROUP(OSPF),
11650 DEVLINK_TRAP_GROUP(BGP),
11651 DEVLINK_TRAP_GROUP(VRRP),
11652 DEVLINK_TRAP_GROUP(PIM),
11653 DEVLINK_TRAP_GROUP(UC_LB),
11654 DEVLINK_TRAP_GROUP(LOCAL_DELIVERY),
11655 DEVLINK_TRAP_GROUP(EXTERNAL_DELIVERY),
11656 DEVLINK_TRAP_GROUP(IPV6),
11657 DEVLINK_TRAP_GROUP(PTP_EVENT),
11658 DEVLINK_TRAP_GROUP(PTP_GENERAL),
11659 DEVLINK_TRAP_GROUP(ACL_SAMPLE),
11660 DEVLINK_TRAP_GROUP(ACL_TRAP),
11661 DEVLINK_TRAP_GROUP(PARSER_ERROR_DROPS),
11664 static int devlink_trap_generic_verify(const struct devlink_trap *trap)
11666 if (trap->id > DEVLINK_TRAP_GENERIC_ID_MAX)
11669 if (strcmp(trap->name, devlink_trap_generic[trap->id].name))
11672 if (trap->type != devlink_trap_generic[trap->id].type)
11678 static int devlink_trap_driver_verify(const struct devlink_trap *trap)
11682 if (trap->id <= DEVLINK_TRAP_GENERIC_ID_MAX)
11685 for (i = 0; i < ARRAY_SIZE(devlink_trap_generic); i++) {
11686 if (!strcmp(trap->name, devlink_trap_generic[i].name))
11693 static int devlink_trap_verify(const struct devlink_trap *trap)
11695 if (!trap || !trap->name)
11699 return devlink_trap_generic_verify(trap);
11701 return devlink_trap_driver_verify(trap);
11705 devlink_trap_group_generic_verify(const struct devlink_trap_group *group)
11707 if (group->id > DEVLINK_TRAP_GROUP_GENERIC_ID_MAX)
11710 if (strcmp(group->name, devlink_trap_group_generic[group->id].name))
11717 devlink_trap_group_driver_verify(const struct devlink_trap_group *group)
11721 if (group->id <= DEVLINK_TRAP_GROUP_GENERIC_ID_MAX)
11724 for (i = 0; i < ARRAY_SIZE(devlink_trap_group_generic); i++) {
11725 if (!strcmp(group->name, devlink_trap_group_generic[i].name))
11732 static int devlink_trap_group_verify(const struct devlink_trap_group *group)
11734 if (group->generic)
11735 return devlink_trap_group_generic_verify(group);
11737 return devlink_trap_group_driver_verify(group);
11741 devlink_trap_group_notify(struct devlink *devlink,
11742 const struct devlink_trap_group_item *group_item,
11743 enum devlink_command cmd)
11745 struct sk_buff *msg;
11748 WARN_ON_ONCE(cmd != DEVLINK_CMD_TRAP_GROUP_NEW &&
11749 cmd != DEVLINK_CMD_TRAP_GROUP_DEL);
11750 if (!xa_get_mark(&devlinks, devlink->index, DEVLINK_REGISTERED))
11753 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
11757 err = devlink_nl_trap_group_fill(msg, devlink, group_item, cmd, 0, 0,
11764 genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink),
11765 msg, 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
11769 devlink_trap_item_group_link(struct devlink *devlink,
11770 struct devlink_trap_item *trap_item)
11772 u16 group_id = trap_item->trap->init_group_id;
11773 struct devlink_trap_group_item *group_item;
11775 group_item = devlink_trap_group_item_lookup_by_id(devlink, group_id);
11776 if (WARN_ON_ONCE(!group_item))
11779 trap_item->group_item = group_item;
11784 static void devlink_trap_notify(struct devlink *devlink,
11785 const struct devlink_trap_item *trap_item,
11786 enum devlink_command cmd)
11788 struct sk_buff *msg;
11791 WARN_ON_ONCE(cmd != DEVLINK_CMD_TRAP_NEW &&
11792 cmd != DEVLINK_CMD_TRAP_DEL);
11793 if (!xa_get_mark(&devlinks, devlink->index, DEVLINK_REGISTERED))
11796 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
11800 err = devlink_nl_trap_fill(msg, devlink, trap_item, cmd, 0, 0, 0);
11806 genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink),
11807 msg, 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
11811 devlink_trap_register(struct devlink *devlink,
11812 const struct devlink_trap *trap, void *priv)
11814 struct devlink_trap_item *trap_item;
11817 if (devlink_trap_item_lookup(devlink, trap->name))
11820 trap_item = kzalloc(sizeof(*trap_item), GFP_KERNEL);
11824 trap_item->stats = netdev_alloc_pcpu_stats(struct devlink_stats);
11825 if (!trap_item->stats) {
11827 goto err_stats_alloc;
11830 trap_item->trap = trap;
11831 trap_item->action = trap->init_action;
11832 trap_item->priv = priv;
11834 err = devlink_trap_item_group_link(devlink, trap_item);
11836 goto err_group_link;
11838 err = devlink->ops->trap_init(devlink, trap, trap_item);
11840 goto err_trap_init;
11842 list_add_tail(&trap_item->list, &devlink->trap_list);
11843 devlink_trap_notify(devlink, trap_item, DEVLINK_CMD_TRAP_NEW);
11849 free_percpu(trap_item->stats);
11855 static void devlink_trap_unregister(struct devlink *devlink,
11856 const struct devlink_trap *trap)
11858 struct devlink_trap_item *trap_item;
11860 trap_item = devlink_trap_item_lookup(devlink, trap->name);
11861 if (WARN_ON_ONCE(!trap_item))
11864 devlink_trap_notify(devlink, trap_item, DEVLINK_CMD_TRAP_DEL);
11865 list_del(&trap_item->list);
11866 if (devlink->ops->trap_fini)
11867 devlink->ops->trap_fini(devlink, trap, trap_item);
11868 free_percpu(trap_item->stats);
11872 static void devlink_trap_disable(struct devlink *devlink,
11873 const struct devlink_trap *trap)
11875 struct devlink_trap_item *trap_item;
11877 trap_item = devlink_trap_item_lookup(devlink, trap->name);
11878 if (WARN_ON_ONCE(!trap_item))
11881 devlink->ops->trap_action_set(devlink, trap, DEVLINK_TRAP_ACTION_DROP,
11883 trap_item->action = DEVLINK_TRAP_ACTION_DROP;
11887 * devl_traps_register - Register packet traps with devlink.
11888 * @devlink: devlink.
11889 * @traps: Packet traps.
11890 * @traps_count: Count of provided packet traps.
11891 * @priv: Driver private information.
11893 * Return: Non-zero value on failure.
11895 int devl_traps_register(struct devlink *devlink,
11896 const struct devlink_trap *traps,
11897 size_t traps_count, void *priv)
11901 if (!devlink->ops->trap_init || !devlink->ops->trap_action_set)
11904 devl_assert_locked(devlink);
11905 for (i = 0; i < traps_count; i++) {
11906 const struct devlink_trap *trap = &traps[i];
11908 err = devlink_trap_verify(trap);
11910 goto err_trap_verify;
11912 err = devlink_trap_register(devlink, trap, priv);
11914 goto err_trap_register;
11921 for (i--; i >= 0; i--)
11922 devlink_trap_unregister(devlink, &traps[i]);
11925 EXPORT_SYMBOL_GPL(devl_traps_register);
11928 * devlink_traps_register - Register packet traps with devlink.
11929 * @devlink: devlink.
11930 * @traps: Packet traps.
11931 * @traps_count: Count of provided packet traps.
11932 * @priv: Driver private information.
11934 * Context: Takes and release devlink->lock <mutex>.
11936 * Return: Non-zero value on failure.
11938 int devlink_traps_register(struct devlink *devlink,
11939 const struct devlink_trap *traps,
11940 size_t traps_count, void *priv)
11944 devl_lock(devlink);
11945 err = devl_traps_register(devlink, traps, traps_count, priv);
11946 devl_unlock(devlink);
11949 EXPORT_SYMBOL_GPL(devlink_traps_register);
11952 * devl_traps_unregister - Unregister packet traps from devlink.
11953 * @devlink: devlink.
11954 * @traps: Packet traps.
11955 * @traps_count: Count of provided packet traps.
11957 void devl_traps_unregister(struct devlink *devlink,
11958 const struct devlink_trap *traps,
11959 size_t traps_count)
11963 devl_assert_locked(devlink);
11964 /* Make sure we do not have any packets in-flight while unregistering
11965 * traps by disabling all of them and waiting for a grace period.
11967 for (i = traps_count - 1; i >= 0; i--)
11968 devlink_trap_disable(devlink, &traps[i]);
11970 for (i = traps_count - 1; i >= 0; i--)
11971 devlink_trap_unregister(devlink, &traps[i]);
11973 EXPORT_SYMBOL_GPL(devl_traps_unregister);
11976 * devlink_traps_unregister - Unregister packet traps from devlink.
11977 * @devlink: devlink.
11978 * @traps: Packet traps.
11979 * @traps_count: Count of provided packet traps.
11981 * Context: Takes and release devlink->lock <mutex>.
11983 void devlink_traps_unregister(struct devlink *devlink,
11984 const struct devlink_trap *traps,
11985 size_t traps_count)
11987 devl_lock(devlink);
11988 devl_traps_unregister(devlink, traps, traps_count);
11989 devl_unlock(devlink);
11991 EXPORT_SYMBOL_GPL(devlink_traps_unregister);
11994 devlink_trap_stats_update(struct devlink_stats __percpu *trap_stats,
11997 struct devlink_stats *stats;
11999 stats = this_cpu_ptr(trap_stats);
12000 u64_stats_update_begin(&stats->syncp);
12001 u64_stats_add(&stats->rx_bytes, skb_len);
12002 u64_stats_inc(&stats->rx_packets);
12003 u64_stats_update_end(&stats->syncp);
12007 devlink_trap_report_metadata_set(struct devlink_trap_metadata *metadata,
12008 const struct devlink_trap_item *trap_item,
12009 struct devlink_port *in_devlink_port,
12010 const struct flow_action_cookie *fa_cookie)
12012 metadata->trap_name = trap_item->trap->name;
12013 metadata->trap_group_name = trap_item->group_item->group->name;
12014 metadata->fa_cookie = fa_cookie;
12015 metadata->trap_type = trap_item->trap->type;
12017 spin_lock(&in_devlink_port->type_lock);
12018 if (in_devlink_port->type == DEVLINK_PORT_TYPE_ETH)
12019 metadata->input_dev = in_devlink_port->type_dev;
12020 spin_unlock(&in_devlink_port->type_lock);
12024 * devlink_trap_report - Report trapped packet to drop monitor.
12025 * @devlink: devlink.
12026 * @skb: Trapped packet.
12027 * @trap_ctx: Trap context.
12028 * @in_devlink_port: Input devlink port.
12029 * @fa_cookie: Flow action cookie. Could be NULL.
12031 void devlink_trap_report(struct devlink *devlink, struct sk_buff *skb,
12032 void *trap_ctx, struct devlink_port *in_devlink_port,
12033 const struct flow_action_cookie *fa_cookie)
12036 struct devlink_trap_item *trap_item = trap_ctx;
12038 devlink_trap_stats_update(trap_item->stats, skb->len);
12039 devlink_trap_stats_update(trap_item->group_item->stats, skb->len);
12041 if (trace_devlink_trap_report_enabled()) {
12042 struct devlink_trap_metadata metadata = {};
12044 devlink_trap_report_metadata_set(&metadata, trap_item,
12045 in_devlink_port, fa_cookie);
12046 trace_devlink_trap_report(devlink, skb, &metadata);
12049 EXPORT_SYMBOL_GPL(devlink_trap_report);
12052 * devlink_trap_ctx_priv - Trap context to driver private information.
12053 * @trap_ctx: Trap context.
12055 * Return: Driver private information passed during registration.
12057 void *devlink_trap_ctx_priv(void *trap_ctx)
12059 struct devlink_trap_item *trap_item = trap_ctx;
12061 return trap_item->priv;
12063 EXPORT_SYMBOL_GPL(devlink_trap_ctx_priv);
12066 devlink_trap_group_item_policer_link(struct devlink *devlink,
12067 struct devlink_trap_group_item *group_item)
12069 u32 policer_id = group_item->group->init_policer_id;
12070 struct devlink_trap_policer_item *policer_item;
12072 if (policer_id == 0)
12075 policer_item = devlink_trap_policer_item_lookup(devlink, policer_id);
12076 if (WARN_ON_ONCE(!policer_item))
12079 group_item->policer_item = policer_item;
12085 devlink_trap_group_register(struct devlink *devlink,
12086 const struct devlink_trap_group *group)
12088 struct devlink_trap_group_item *group_item;
12091 if (devlink_trap_group_item_lookup(devlink, group->name))
12094 group_item = kzalloc(sizeof(*group_item), GFP_KERNEL);
12098 group_item->stats = netdev_alloc_pcpu_stats(struct devlink_stats);
12099 if (!group_item->stats) {
12101 goto err_stats_alloc;
12104 group_item->group = group;
12106 err = devlink_trap_group_item_policer_link(devlink, group_item);
12108 goto err_policer_link;
12110 if (devlink->ops->trap_group_init) {
12111 err = devlink->ops->trap_group_init(devlink, group);
12113 goto err_group_init;
12116 list_add_tail(&group_item->list, &devlink->trap_group_list);
12117 devlink_trap_group_notify(devlink, group_item,
12118 DEVLINK_CMD_TRAP_GROUP_NEW);
12124 free_percpu(group_item->stats);
12131 devlink_trap_group_unregister(struct devlink *devlink,
12132 const struct devlink_trap_group *group)
12134 struct devlink_trap_group_item *group_item;
12136 group_item = devlink_trap_group_item_lookup(devlink, group->name);
12137 if (WARN_ON_ONCE(!group_item))
12140 devlink_trap_group_notify(devlink, group_item,
12141 DEVLINK_CMD_TRAP_GROUP_DEL);
12142 list_del(&group_item->list);
12143 free_percpu(group_item->stats);
12148 * devl_trap_groups_register - Register packet trap groups with devlink.
12149 * @devlink: devlink.
12150 * @groups: Packet trap groups.
12151 * @groups_count: Count of provided packet trap groups.
12153 * Return: Non-zero value on failure.
12155 int devl_trap_groups_register(struct devlink *devlink,
12156 const struct devlink_trap_group *groups,
12157 size_t groups_count)
12161 devl_assert_locked(devlink);
12162 for (i = 0; i < groups_count; i++) {
12163 const struct devlink_trap_group *group = &groups[i];
12165 err = devlink_trap_group_verify(group);
12167 goto err_trap_group_verify;
12169 err = devlink_trap_group_register(devlink, group);
12171 goto err_trap_group_register;
12176 err_trap_group_register:
12177 err_trap_group_verify:
12178 for (i--; i >= 0; i--)
12179 devlink_trap_group_unregister(devlink, &groups[i]);
12182 EXPORT_SYMBOL_GPL(devl_trap_groups_register);
12185 * devlink_trap_groups_register - Register packet trap groups with devlink.
12186 * @devlink: devlink.
12187 * @groups: Packet trap groups.
12188 * @groups_count: Count of provided packet trap groups.
12190 * Context: Takes and release devlink->lock <mutex>.
12192 * Return: Non-zero value on failure.
12194 int devlink_trap_groups_register(struct devlink *devlink,
12195 const struct devlink_trap_group *groups,
12196 size_t groups_count)
12200 devl_lock(devlink);
12201 err = devl_trap_groups_register(devlink, groups, groups_count);
12202 devl_unlock(devlink);
12205 EXPORT_SYMBOL_GPL(devlink_trap_groups_register);
12208 * devl_trap_groups_unregister - Unregister packet trap groups from devlink.
12209 * @devlink: devlink.
12210 * @groups: Packet trap groups.
12211 * @groups_count: Count of provided packet trap groups.
12213 void devl_trap_groups_unregister(struct devlink *devlink,
12214 const struct devlink_trap_group *groups,
12215 size_t groups_count)
12219 devl_assert_locked(devlink);
12220 for (i = groups_count - 1; i >= 0; i--)
12221 devlink_trap_group_unregister(devlink, &groups[i]);
12223 EXPORT_SYMBOL_GPL(devl_trap_groups_unregister);
12226 * devlink_trap_groups_unregister - Unregister packet trap groups from devlink.
12227 * @devlink: devlink.
12228 * @groups: Packet trap groups.
12229 * @groups_count: Count of provided packet trap groups.
12231 * Context: Takes and release devlink->lock <mutex>.
12233 void devlink_trap_groups_unregister(struct devlink *devlink,
12234 const struct devlink_trap_group *groups,
12235 size_t groups_count)
12237 devl_lock(devlink);
12238 devl_trap_groups_unregister(devlink, groups, groups_count);
12239 devl_unlock(devlink);
12241 EXPORT_SYMBOL_GPL(devlink_trap_groups_unregister);
12244 devlink_trap_policer_notify(struct devlink *devlink,
12245 const struct devlink_trap_policer_item *policer_item,
12246 enum devlink_command cmd)
12248 struct sk_buff *msg;
12251 WARN_ON_ONCE(cmd != DEVLINK_CMD_TRAP_POLICER_NEW &&
12252 cmd != DEVLINK_CMD_TRAP_POLICER_DEL);
12253 if (!xa_get_mark(&devlinks, devlink->index, DEVLINK_REGISTERED))
12256 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
12260 err = devlink_nl_trap_policer_fill(msg, devlink, policer_item, cmd, 0,
12267 genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink),
12268 msg, 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
12272 devlink_trap_policer_register(struct devlink *devlink,
12273 const struct devlink_trap_policer *policer)
12275 struct devlink_trap_policer_item *policer_item;
12278 if (devlink_trap_policer_item_lookup(devlink, policer->id))
12281 policer_item = kzalloc(sizeof(*policer_item), GFP_KERNEL);
12285 policer_item->policer = policer;
12286 policer_item->rate = policer->init_rate;
12287 policer_item->burst = policer->init_burst;
12289 if (devlink->ops->trap_policer_init) {
12290 err = devlink->ops->trap_policer_init(devlink, policer);
12292 goto err_policer_init;
12295 list_add_tail(&policer_item->list, &devlink->trap_policer_list);
12296 devlink_trap_policer_notify(devlink, policer_item,
12297 DEVLINK_CMD_TRAP_POLICER_NEW);
12302 kfree(policer_item);
12307 devlink_trap_policer_unregister(struct devlink *devlink,
12308 const struct devlink_trap_policer *policer)
12310 struct devlink_trap_policer_item *policer_item;
12312 policer_item = devlink_trap_policer_item_lookup(devlink, policer->id);
12313 if (WARN_ON_ONCE(!policer_item))
12316 devlink_trap_policer_notify(devlink, policer_item,
12317 DEVLINK_CMD_TRAP_POLICER_DEL);
12318 list_del(&policer_item->list);
12319 if (devlink->ops->trap_policer_fini)
12320 devlink->ops->trap_policer_fini(devlink, policer);
12321 kfree(policer_item);
12325 * devl_trap_policers_register - Register packet trap policers with devlink.
12326 * @devlink: devlink.
12327 * @policers: Packet trap policers.
12328 * @policers_count: Count of provided packet trap policers.
12330 * Return: Non-zero value on failure.
12333 devl_trap_policers_register(struct devlink *devlink,
12334 const struct devlink_trap_policer *policers,
12335 size_t policers_count)
12339 devl_assert_locked(devlink);
12340 for (i = 0; i < policers_count; i++) {
12341 const struct devlink_trap_policer *policer = &policers[i];
12343 if (WARN_ON(policer->id == 0 ||
12344 policer->max_rate < policer->min_rate ||
12345 policer->max_burst < policer->min_burst)) {
12347 goto err_trap_policer_verify;
12350 err = devlink_trap_policer_register(devlink, policer);
12352 goto err_trap_policer_register;
12356 err_trap_policer_register:
12357 err_trap_policer_verify:
12358 for (i--; i >= 0; i--)
12359 devlink_trap_policer_unregister(devlink, &policers[i]);
12362 EXPORT_SYMBOL_GPL(devl_trap_policers_register);
12365 * devl_trap_policers_unregister - Unregister packet trap policers from devlink.
12366 * @devlink: devlink.
12367 * @policers: Packet trap policers.
12368 * @policers_count: Count of provided packet trap policers.
12371 devl_trap_policers_unregister(struct devlink *devlink,
12372 const struct devlink_trap_policer *policers,
12373 size_t policers_count)
12377 devl_assert_locked(devlink);
12378 for (i = policers_count - 1; i >= 0; i--)
12379 devlink_trap_policer_unregister(devlink, &policers[i]);
12381 EXPORT_SYMBOL_GPL(devl_trap_policers_unregister);
12383 static void __devlink_compat_running_version(struct devlink *devlink,
12384 char *buf, size_t len)
12386 struct devlink_info_req req = {};
12387 const struct nlattr *nlattr;
12388 struct sk_buff *msg;
12391 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
12396 err = devlink->ops->info_get(devlink, &req, NULL);
12400 nla_for_each_attr(nlattr, (void *)msg->data, msg->len, rem) {
12401 const struct nlattr *kv;
12404 if (nla_type(nlattr) != DEVLINK_ATTR_INFO_VERSION_RUNNING)
12407 nla_for_each_nested(kv, nlattr, rem_kv) {
12408 if (nla_type(kv) != DEVLINK_ATTR_INFO_VERSION_VALUE)
12411 strlcat(buf, nla_data(kv), len);
12412 strlcat(buf, " ", len);
12419 static struct devlink_port *netdev_to_devlink_port(struct net_device *dev)
12421 if (!dev->netdev_ops->ndo_get_devlink_port)
12424 return dev->netdev_ops->ndo_get_devlink_port(dev);
12427 void devlink_compat_running_version(struct devlink *devlink,
12428 char *buf, size_t len)
12430 if (!devlink->ops->info_get)
12433 devl_lock(devlink);
12434 __devlink_compat_running_version(devlink, buf, len);
12435 devl_unlock(devlink);
12438 int devlink_compat_flash_update(struct devlink *devlink, const char *file_name)
12440 struct devlink_flash_update_params params = {};
12443 if (!devlink->ops->flash_update)
12444 return -EOPNOTSUPP;
12446 ret = request_firmware(¶ms.fw, file_name, devlink->dev);
12450 devl_lock(devlink);
12451 devlink_flash_update_begin_notify(devlink);
12452 ret = devlink->ops->flash_update(devlink, ¶ms, NULL);
12453 devlink_flash_update_end_notify(devlink);
12454 devl_unlock(devlink);
12456 release_firmware(params.fw);
12461 int devlink_compat_phys_port_name_get(struct net_device *dev,
12462 char *name, size_t len)
12464 struct devlink_port *devlink_port;
12466 /* RTNL mutex is held here which ensures that devlink_port
12467 * instance cannot disappear in the middle. No need to take
12468 * any devlink lock as only permanent values are accessed.
12472 devlink_port = netdev_to_devlink_port(dev);
12474 return -EOPNOTSUPP;
12476 return __devlink_port_phys_port_name_get(devlink_port, name, len);
12479 int devlink_compat_switch_id_get(struct net_device *dev,
12480 struct netdev_phys_item_id *ppid)
12482 struct devlink_port *devlink_port;
12484 /* Caller must hold RTNL mutex or reference to dev, which ensures that
12485 * devlink_port instance cannot disappear in the middle. No need to take
12486 * any devlink lock as only permanent values are accessed.
12488 devlink_port = netdev_to_devlink_port(dev);
12489 if (!devlink_port || !devlink_port->switch_port)
12490 return -EOPNOTSUPP;
12492 memcpy(ppid, &devlink_port->attrs.switch_id, sizeof(*ppid));
12497 static void __net_exit devlink_pernet_pre_exit(struct net *net)
12499 struct devlink *devlink;
12500 u32 actions_performed;
12501 unsigned long index;
12504 /* In case network namespace is getting destroyed, reload
12505 * all devlink instances from this namespace into init_net.
12507 devlinks_xa_for_each_registered_get(net, index, devlink) {
12508 WARN_ON(!(devlink->features & DEVLINK_F_RELOAD));
12509 mutex_lock(&devlink->lock);
12510 err = devlink_reload(devlink, &init_net,
12511 DEVLINK_RELOAD_ACTION_DRIVER_REINIT,
12512 DEVLINK_RELOAD_LIMIT_UNSPEC,
12513 &actions_performed, NULL);
12514 mutex_unlock(&devlink->lock);
12515 if (err && err != -EOPNOTSUPP)
12516 pr_warn("Failed to reload devlink instance into init_net\n");
12517 devlink_put(devlink);
12521 static struct pernet_operations devlink_pernet_ops __net_initdata = {
12522 .pre_exit = devlink_pernet_pre_exit,
12525 static int __init devlink_init(void)
12529 err = genl_register_family(&devlink_nl_family);
12532 err = register_pernet_subsys(&devlink_pernet_ops);
12539 subsys_initcall(devlink_init);