Merge tag '5.15-rc-ksmbd-part2' of git://git.samba.org/ksmbd
[linux-2.6-microblaze.git] / net / core / devlink.c
1 // SPDX-License-Identifier: GPL-2.0-or-later
2 /*
3  * net/core/devlink.c - Network physical/parent device Netlink interface
4  *
5  * Heavily inspired by net/wireless/
6  * Copyright (c) 2016 Mellanox Technologies. All rights reserved.
7  * Copyright (c) 2016 Jiri Pirko <jiri@mellanox.com>
8  */
9
10 #include <linux/kernel.h>
11 #include <linux/module.h>
12 #include <linux/types.h>
13 #include <linux/slab.h>
14 #include <linux/gfp.h>
15 #include <linux/device.h>
16 #include <linux/list.h>
17 #include <linux/netdevice.h>
18 #include <linux/spinlock.h>
19 #include <linux/refcount.h>
20 #include <linux/workqueue.h>
21 #include <linux/u64_stats_sync.h>
22 #include <linux/timekeeping.h>
23 #include <rdma/ib_verbs.h>
24 #include <net/netlink.h>
25 #include <net/genetlink.h>
26 #include <net/rtnetlink.h>
27 #include <net/net_namespace.h>
28 #include <net/sock.h>
29 #include <net/devlink.h>
30 #define CREATE_TRACE_POINTS
31 #include <trace/events/devlink.h>
32
33 static struct devlink_dpipe_field devlink_dpipe_fields_ethernet[] = {
34         {
35                 .name = "destination mac",
36                 .id = DEVLINK_DPIPE_FIELD_ETHERNET_DST_MAC,
37                 .bitwidth = 48,
38         },
39 };
40
41 struct devlink_dpipe_header devlink_dpipe_header_ethernet = {
42         .name = "ethernet",
43         .id = DEVLINK_DPIPE_HEADER_ETHERNET,
44         .fields = devlink_dpipe_fields_ethernet,
45         .fields_count = ARRAY_SIZE(devlink_dpipe_fields_ethernet),
46         .global = true,
47 };
48 EXPORT_SYMBOL(devlink_dpipe_header_ethernet);
49
50 static struct devlink_dpipe_field devlink_dpipe_fields_ipv4[] = {
51         {
52                 .name = "destination ip",
53                 .id = DEVLINK_DPIPE_FIELD_IPV4_DST_IP,
54                 .bitwidth = 32,
55         },
56 };
57
58 struct devlink_dpipe_header devlink_dpipe_header_ipv4 = {
59         .name = "ipv4",
60         .id = DEVLINK_DPIPE_HEADER_IPV4,
61         .fields = devlink_dpipe_fields_ipv4,
62         .fields_count = ARRAY_SIZE(devlink_dpipe_fields_ipv4),
63         .global = true,
64 };
65 EXPORT_SYMBOL(devlink_dpipe_header_ipv4);
66
67 static struct devlink_dpipe_field devlink_dpipe_fields_ipv6[] = {
68         {
69                 .name = "destination ip",
70                 .id = DEVLINK_DPIPE_FIELD_IPV6_DST_IP,
71                 .bitwidth = 128,
72         },
73 };
74
75 struct devlink_dpipe_header devlink_dpipe_header_ipv6 = {
76         .name = "ipv6",
77         .id = DEVLINK_DPIPE_HEADER_IPV6,
78         .fields = devlink_dpipe_fields_ipv6,
79         .fields_count = ARRAY_SIZE(devlink_dpipe_fields_ipv6),
80         .global = true,
81 };
82 EXPORT_SYMBOL(devlink_dpipe_header_ipv6);
83
84 EXPORT_TRACEPOINT_SYMBOL_GPL(devlink_hwmsg);
85 EXPORT_TRACEPOINT_SYMBOL_GPL(devlink_hwerr);
86 EXPORT_TRACEPOINT_SYMBOL_GPL(devlink_trap_report);
87
88 static const struct nla_policy devlink_function_nl_policy[DEVLINK_PORT_FUNCTION_ATTR_MAX + 1] = {
89         [DEVLINK_PORT_FUNCTION_ATTR_HW_ADDR] = { .type = NLA_BINARY },
90         [DEVLINK_PORT_FN_ATTR_STATE] =
91                 NLA_POLICY_RANGE(NLA_U8, DEVLINK_PORT_FN_STATE_INACTIVE,
92                                  DEVLINK_PORT_FN_STATE_ACTIVE),
93 };
94
95 static DEFINE_XARRAY_FLAGS(devlinks, XA_FLAGS_ALLOC);
96 #define DEVLINK_REGISTERED XA_MARK_1
97
98 /* devlink_mutex
99  *
100  * An overall lock guarding every operation coming from userspace.
101  * It also guards devlink devices list and it is taken when
102  * driver registers/unregisters it.
103  */
104 static DEFINE_MUTEX(devlink_mutex);
105
106 struct net *devlink_net(const struct devlink *devlink)
107 {
108         return read_pnet(&devlink->_net);
109 }
110 EXPORT_SYMBOL_GPL(devlink_net);
111
112 static void devlink_put(struct devlink *devlink)
113 {
114         if (refcount_dec_and_test(&devlink->refcount))
115                 complete(&devlink->comp);
116 }
117
118 static bool __must_check devlink_try_get(struct devlink *devlink)
119 {
120         return refcount_inc_not_zero(&devlink->refcount);
121 }
122
123 static struct devlink *devlink_get_from_attrs(struct net *net,
124                                               struct nlattr **attrs)
125 {
126         struct devlink *devlink;
127         unsigned long index;
128         bool found = false;
129         char *busname;
130         char *devname;
131
132         if (!attrs[DEVLINK_ATTR_BUS_NAME] || !attrs[DEVLINK_ATTR_DEV_NAME])
133                 return ERR_PTR(-EINVAL);
134
135         busname = nla_data(attrs[DEVLINK_ATTR_BUS_NAME]);
136         devname = nla_data(attrs[DEVLINK_ATTR_DEV_NAME]);
137
138         lockdep_assert_held(&devlink_mutex);
139
140         xa_for_each_marked(&devlinks, index, devlink, DEVLINK_REGISTERED) {
141                 if (strcmp(devlink->dev->bus->name, busname) == 0 &&
142                     strcmp(dev_name(devlink->dev), devname) == 0 &&
143                     net_eq(devlink_net(devlink), net)) {
144                         found = true;
145                         break;
146                 }
147         }
148
149         if (!found || !devlink_try_get(devlink))
150                 devlink = ERR_PTR(-ENODEV);
151
152         return devlink;
153 }
154
155 static struct devlink_port *devlink_port_get_by_index(struct devlink *devlink,
156                                                       unsigned int port_index)
157 {
158         struct devlink_port *devlink_port;
159
160         list_for_each_entry(devlink_port, &devlink->port_list, list) {
161                 if (devlink_port->index == port_index)
162                         return devlink_port;
163         }
164         return NULL;
165 }
166
167 static bool devlink_port_index_exists(struct devlink *devlink,
168                                       unsigned int port_index)
169 {
170         return devlink_port_get_by_index(devlink, port_index);
171 }
172
173 static struct devlink_port *devlink_port_get_from_attrs(struct devlink *devlink,
174                                                         struct nlattr **attrs)
175 {
176         if (attrs[DEVLINK_ATTR_PORT_INDEX]) {
177                 u32 port_index = nla_get_u32(attrs[DEVLINK_ATTR_PORT_INDEX]);
178                 struct devlink_port *devlink_port;
179
180                 devlink_port = devlink_port_get_by_index(devlink, port_index);
181                 if (!devlink_port)
182                         return ERR_PTR(-ENODEV);
183                 return devlink_port;
184         }
185         return ERR_PTR(-EINVAL);
186 }
187
188 static struct devlink_port *devlink_port_get_from_info(struct devlink *devlink,
189                                                        struct genl_info *info)
190 {
191         return devlink_port_get_from_attrs(devlink, info->attrs);
192 }
193
194 static inline bool
195 devlink_rate_is_leaf(struct devlink_rate *devlink_rate)
196 {
197         return devlink_rate->type == DEVLINK_RATE_TYPE_LEAF;
198 }
199
200 static inline bool
201 devlink_rate_is_node(struct devlink_rate *devlink_rate)
202 {
203         return devlink_rate->type == DEVLINK_RATE_TYPE_NODE;
204 }
205
206 static struct devlink_rate *
207 devlink_rate_leaf_get_from_info(struct devlink *devlink, struct genl_info *info)
208 {
209         struct devlink_rate *devlink_rate;
210         struct devlink_port *devlink_port;
211
212         devlink_port = devlink_port_get_from_attrs(devlink, info->attrs);
213         if (IS_ERR(devlink_port))
214                 return ERR_CAST(devlink_port);
215         devlink_rate = devlink_port->devlink_rate;
216         return devlink_rate ?: ERR_PTR(-ENODEV);
217 }
218
219 static struct devlink_rate *
220 devlink_rate_node_get_by_name(struct devlink *devlink, const char *node_name)
221 {
222         static struct devlink_rate *devlink_rate;
223
224         list_for_each_entry(devlink_rate, &devlink->rate_list, list) {
225                 if (devlink_rate_is_node(devlink_rate) &&
226                     !strcmp(node_name, devlink_rate->name))
227                         return devlink_rate;
228         }
229         return ERR_PTR(-ENODEV);
230 }
231
232 static struct devlink_rate *
233 devlink_rate_node_get_from_attrs(struct devlink *devlink, struct nlattr **attrs)
234 {
235         const char *rate_node_name;
236         size_t len;
237
238         if (!attrs[DEVLINK_ATTR_RATE_NODE_NAME])
239                 return ERR_PTR(-EINVAL);
240         rate_node_name = nla_data(attrs[DEVLINK_ATTR_RATE_NODE_NAME]);
241         len = strlen(rate_node_name);
242         /* Name cannot be empty or decimal number */
243         if (!len || strspn(rate_node_name, "0123456789") == len)
244                 return ERR_PTR(-EINVAL);
245
246         return devlink_rate_node_get_by_name(devlink, rate_node_name);
247 }
248
249 static struct devlink_rate *
250 devlink_rate_node_get_from_info(struct devlink *devlink, struct genl_info *info)
251 {
252         return devlink_rate_node_get_from_attrs(devlink, info->attrs);
253 }
254
255 static struct devlink_rate *
256 devlink_rate_get_from_info(struct devlink *devlink, struct genl_info *info)
257 {
258         struct nlattr **attrs = info->attrs;
259
260         if (attrs[DEVLINK_ATTR_PORT_INDEX])
261                 return devlink_rate_leaf_get_from_info(devlink, info);
262         else if (attrs[DEVLINK_ATTR_RATE_NODE_NAME])
263                 return devlink_rate_node_get_from_info(devlink, info);
264         else
265                 return ERR_PTR(-EINVAL);
266 }
267
268 struct devlink_sb {
269         struct list_head list;
270         unsigned int index;
271         u32 size;
272         u16 ingress_pools_count;
273         u16 egress_pools_count;
274         u16 ingress_tc_count;
275         u16 egress_tc_count;
276 };
277
278 static u16 devlink_sb_pool_count(struct devlink_sb *devlink_sb)
279 {
280         return devlink_sb->ingress_pools_count + devlink_sb->egress_pools_count;
281 }
282
283 static struct devlink_sb *devlink_sb_get_by_index(struct devlink *devlink,
284                                                   unsigned int sb_index)
285 {
286         struct devlink_sb *devlink_sb;
287
288         list_for_each_entry(devlink_sb, &devlink->sb_list, list) {
289                 if (devlink_sb->index == sb_index)
290                         return devlink_sb;
291         }
292         return NULL;
293 }
294
295 static bool devlink_sb_index_exists(struct devlink *devlink,
296                                     unsigned int sb_index)
297 {
298         return devlink_sb_get_by_index(devlink, sb_index);
299 }
300
301 static struct devlink_sb *devlink_sb_get_from_attrs(struct devlink *devlink,
302                                                     struct nlattr **attrs)
303 {
304         if (attrs[DEVLINK_ATTR_SB_INDEX]) {
305                 u32 sb_index = nla_get_u32(attrs[DEVLINK_ATTR_SB_INDEX]);
306                 struct devlink_sb *devlink_sb;
307
308                 devlink_sb = devlink_sb_get_by_index(devlink, sb_index);
309                 if (!devlink_sb)
310                         return ERR_PTR(-ENODEV);
311                 return devlink_sb;
312         }
313         return ERR_PTR(-EINVAL);
314 }
315
316 static struct devlink_sb *devlink_sb_get_from_info(struct devlink *devlink,
317                                                    struct genl_info *info)
318 {
319         return devlink_sb_get_from_attrs(devlink, info->attrs);
320 }
321
322 static int devlink_sb_pool_index_get_from_attrs(struct devlink_sb *devlink_sb,
323                                                 struct nlattr **attrs,
324                                                 u16 *p_pool_index)
325 {
326         u16 val;
327
328         if (!attrs[DEVLINK_ATTR_SB_POOL_INDEX])
329                 return -EINVAL;
330
331         val = nla_get_u16(attrs[DEVLINK_ATTR_SB_POOL_INDEX]);
332         if (val >= devlink_sb_pool_count(devlink_sb))
333                 return -EINVAL;
334         *p_pool_index = val;
335         return 0;
336 }
337
338 static int devlink_sb_pool_index_get_from_info(struct devlink_sb *devlink_sb,
339                                                struct genl_info *info,
340                                                u16 *p_pool_index)
341 {
342         return devlink_sb_pool_index_get_from_attrs(devlink_sb, info->attrs,
343                                                     p_pool_index);
344 }
345
346 static int
347 devlink_sb_pool_type_get_from_attrs(struct nlattr **attrs,
348                                     enum devlink_sb_pool_type *p_pool_type)
349 {
350         u8 val;
351
352         if (!attrs[DEVLINK_ATTR_SB_POOL_TYPE])
353                 return -EINVAL;
354
355         val = nla_get_u8(attrs[DEVLINK_ATTR_SB_POOL_TYPE]);
356         if (val != DEVLINK_SB_POOL_TYPE_INGRESS &&
357             val != DEVLINK_SB_POOL_TYPE_EGRESS)
358                 return -EINVAL;
359         *p_pool_type = val;
360         return 0;
361 }
362
363 static int
364 devlink_sb_pool_type_get_from_info(struct genl_info *info,
365                                    enum devlink_sb_pool_type *p_pool_type)
366 {
367         return devlink_sb_pool_type_get_from_attrs(info->attrs, p_pool_type);
368 }
369
370 static int
371 devlink_sb_th_type_get_from_attrs(struct nlattr **attrs,
372                                   enum devlink_sb_threshold_type *p_th_type)
373 {
374         u8 val;
375
376         if (!attrs[DEVLINK_ATTR_SB_POOL_THRESHOLD_TYPE])
377                 return -EINVAL;
378
379         val = nla_get_u8(attrs[DEVLINK_ATTR_SB_POOL_THRESHOLD_TYPE]);
380         if (val != DEVLINK_SB_THRESHOLD_TYPE_STATIC &&
381             val != DEVLINK_SB_THRESHOLD_TYPE_DYNAMIC)
382                 return -EINVAL;
383         *p_th_type = val;
384         return 0;
385 }
386
387 static int
388 devlink_sb_th_type_get_from_info(struct genl_info *info,
389                                  enum devlink_sb_threshold_type *p_th_type)
390 {
391         return devlink_sb_th_type_get_from_attrs(info->attrs, p_th_type);
392 }
393
394 static int
395 devlink_sb_tc_index_get_from_attrs(struct devlink_sb *devlink_sb,
396                                    struct nlattr **attrs,
397                                    enum devlink_sb_pool_type pool_type,
398                                    u16 *p_tc_index)
399 {
400         u16 val;
401
402         if (!attrs[DEVLINK_ATTR_SB_TC_INDEX])
403                 return -EINVAL;
404
405         val = nla_get_u16(attrs[DEVLINK_ATTR_SB_TC_INDEX]);
406         if (pool_type == DEVLINK_SB_POOL_TYPE_INGRESS &&
407             val >= devlink_sb->ingress_tc_count)
408                 return -EINVAL;
409         if (pool_type == DEVLINK_SB_POOL_TYPE_EGRESS &&
410             val >= devlink_sb->egress_tc_count)
411                 return -EINVAL;
412         *p_tc_index = val;
413         return 0;
414 }
415
416 static int
417 devlink_sb_tc_index_get_from_info(struct devlink_sb *devlink_sb,
418                                   struct genl_info *info,
419                                   enum devlink_sb_pool_type pool_type,
420                                   u16 *p_tc_index)
421 {
422         return devlink_sb_tc_index_get_from_attrs(devlink_sb, info->attrs,
423                                                   pool_type, p_tc_index);
424 }
425
426 struct devlink_region {
427         struct devlink *devlink;
428         struct devlink_port *port;
429         struct list_head list;
430         union {
431                 const struct devlink_region_ops *ops;
432                 const struct devlink_port_region_ops *port_ops;
433         };
434         struct list_head snapshot_list;
435         u32 max_snapshots;
436         u32 cur_snapshots;
437         u64 size;
438 };
439
440 struct devlink_snapshot {
441         struct list_head list;
442         struct devlink_region *region;
443         u8 *data;
444         u32 id;
445 };
446
447 static struct devlink_region *
448 devlink_region_get_by_name(struct devlink *devlink, const char *region_name)
449 {
450         struct devlink_region *region;
451
452         list_for_each_entry(region, &devlink->region_list, list)
453                 if (!strcmp(region->ops->name, region_name))
454                         return region;
455
456         return NULL;
457 }
458
459 static struct devlink_region *
460 devlink_port_region_get_by_name(struct devlink_port *port,
461                                 const char *region_name)
462 {
463         struct devlink_region *region;
464
465         list_for_each_entry(region, &port->region_list, list)
466                 if (!strcmp(region->ops->name, region_name))
467                         return region;
468
469         return NULL;
470 }
471
472 static struct devlink_snapshot *
473 devlink_region_snapshot_get_by_id(struct devlink_region *region, u32 id)
474 {
475         struct devlink_snapshot *snapshot;
476
477         list_for_each_entry(snapshot, &region->snapshot_list, list)
478                 if (snapshot->id == id)
479                         return snapshot;
480
481         return NULL;
482 }
483
484 #define DEVLINK_NL_FLAG_NEED_PORT               BIT(0)
485 #define DEVLINK_NL_FLAG_NEED_DEVLINK_OR_PORT    BIT(1)
486 #define DEVLINK_NL_FLAG_NEED_RATE               BIT(2)
487 #define DEVLINK_NL_FLAG_NEED_RATE_NODE          BIT(3)
488
489 /* The per devlink instance lock is taken by default in the pre-doit
490  * operation, yet several commands do not require this. The global
491  * devlink lock is taken and protects from disruption by user-calls.
492  */
493 #define DEVLINK_NL_FLAG_NO_LOCK                 BIT(4)
494
495 static int devlink_nl_pre_doit(const struct genl_ops *ops,
496                                struct sk_buff *skb, struct genl_info *info)
497 {
498         struct devlink_port *devlink_port;
499         struct devlink *devlink;
500         int err;
501
502         mutex_lock(&devlink_mutex);
503         devlink = devlink_get_from_attrs(genl_info_net(info), info->attrs);
504         if (IS_ERR(devlink)) {
505                 mutex_unlock(&devlink_mutex);
506                 return PTR_ERR(devlink);
507         }
508         if (~ops->internal_flags & DEVLINK_NL_FLAG_NO_LOCK)
509                 mutex_lock(&devlink->lock);
510         info->user_ptr[0] = devlink;
511         if (ops->internal_flags & DEVLINK_NL_FLAG_NEED_PORT) {
512                 devlink_port = devlink_port_get_from_info(devlink, info);
513                 if (IS_ERR(devlink_port)) {
514                         err = PTR_ERR(devlink_port);
515                         goto unlock;
516                 }
517                 info->user_ptr[1] = devlink_port;
518         } else if (ops->internal_flags & DEVLINK_NL_FLAG_NEED_DEVLINK_OR_PORT) {
519                 devlink_port = devlink_port_get_from_info(devlink, info);
520                 if (!IS_ERR(devlink_port))
521                         info->user_ptr[1] = devlink_port;
522         } else if (ops->internal_flags & DEVLINK_NL_FLAG_NEED_RATE) {
523                 struct devlink_rate *devlink_rate;
524
525                 devlink_rate = devlink_rate_get_from_info(devlink, info);
526                 if (IS_ERR(devlink_rate)) {
527                         err = PTR_ERR(devlink_rate);
528                         goto unlock;
529                 }
530                 info->user_ptr[1] = devlink_rate;
531         } else if (ops->internal_flags & DEVLINK_NL_FLAG_NEED_RATE_NODE) {
532                 struct devlink_rate *rate_node;
533
534                 rate_node = devlink_rate_node_get_from_info(devlink, info);
535                 if (IS_ERR(rate_node)) {
536                         err = PTR_ERR(rate_node);
537                         goto unlock;
538                 }
539                 info->user_ptr[1] = rate_node;
540         }
541         return 0;
542
543 unlock:
544         if (~ops->internal_flags & DEVLINK_NL_FLAG_NO_LOCK)
545                 mutex_unlock(&devlink->lock);
546         devlink_put(devlink);
547         mutex_unlock(&devlink_mutex);
548         return err;
549 }
550
551 static void devlink_nl_post_doit(const struct genl_ops *ops,
552                                  struct sk_buff *skb, struct genl_info *info)
553 {
554         struct devlink *devlink;
555
556         devlink = info->user_ptr[0];
557         if (~ops->internal_flags & DEVLINK_NL_FLAG_NO_LOCK)
558                 mutex_unlock(&devlink->lock);
559         devlink_put(devlink);
560         mutex_unlock(&devlink_mutex);
561 }
562
563 static struct genl_family devlink_nl_family;
564
565 enum devlink_multicast_groups {
566         DEVLINK_MCGRP_CONFIG,
567 };
568
569 static const struct genl_multicast_group devlink_nl_mcgrps[] = {
570         [DEVLINK_MCGRP_CONFIG] = { .name = DEVLINK_GENL_MCGRP_CONFIG_NAME },
571 };
572
573 static int devlink_nl_put_handle(struct sk_buff *msg, struct devlink *devlink)
574 {
575         if (nla_put_string(msg, DEVLINK_ATTR_BUS_NAME, devlink->dev->bus->name))
576                 return -EMSGSIZE;
577         if (nla_put_string(msg, DEVLINK_ATTR_DEV_NAME, dev_name(devlink->dev)))
578                 return -EMSGSIZE;
579         return 0;
580 }
581
582 struct devlink_reload_combination {
583         enum devlink_reload_action action;
584         enum devlink_reload_limit limit;
585 };
586
587 static const struct devlink_reload_combination devlink_reload_invalid_combinations[] = {
588         {
589                 /* can't reinitialize driver with no down time */
590                 .action = DEVLINK_RELOAD_ACTION_DRIVER_REINIT,
591                 .limit = DEVLINK_RELOAD_LIMIT_NO_RESET,
592         },
593 };
594
595 static bool
596 devlink_reload_combination_is_invalid(enum devlink_reload_action action,
597                                       enum devlink_reload_limit limit)
598 {
599         int i;
600
601         for (i = 0; i < ARRAY_SIZE(devlink_reload_invalid_combinations); i++)
602                 if (devlink_reload_invalid_combinations[i].action == action &&
603                     devlink_reload_invalid_combinations[i].limit == limit)
604                         return true;
605         return false;
606 }
607
608 static bool
609 devlink_reload_action_is_supported(struct devlink *devlink, enum devlink_reload_action action)
610 {
611         return test_bit(action, &devlink->ops->reload_actions);
612 }
613
614 static bool
615 devlink_reload_limit_is_supported(struct devlink *devlink, enum devlink_reload_limit limit)
616 {
617         return test_bit(limit, &devlink->ops->reload_limits);
618 }
619
620 static int devlink_reload_stat_put(struct sk_buff *msg,
621                                    enum devlink_reload_limit limit, u32 value)
622 {
623         struct nlattr *reload_stats_entry;
624
625         reload_stats_entry = nla_nest_start(msg, DEVLINK_ATTR_RELOAD_STATS_ENTRY);
626         if (!reload_stats_entry)
627                 return -EMSGSIZE;
628
629         if (nla_put_u8(msg, DEVLINK_ATTR_RELOAD_STATS_LIMIT, limit) ||
630             nla_put_u32(msg, DEVLINK_ATTR_RELOAD_STATS_VALUE, value))
631                 goto nla_put_failure;
632         nla_nest_end(msg, reload_stats_entry);
633         return 0;
634
635 nla_put_failure:
636         nla_nest_cancel(msg, reload_stats_entry);
637         return -EMSGSIZE;
638 }
639
640 static int devlink_reload_stats_put(struct sk_buff *msg, struct devlink *devlink, bool is_remote)
641 {
642         struct nlattr *reload_stats_attr, *act_info, *act_stats;
643         int i, j, stat_idx;
644         u32 value;
645
646         if (!is_remote)
647                 reload_stats_attr = nla_nest_start(msg, DEVLINK_ATTR_RELOAD_STATS);
648         else
649                 reload_stats_attr = nla_nest_start(msg, DEVLINK_ATTR_REMOTE_RELOAD_STATS);
650
651         if (!reload_stats_attr)
652                 return -EMSGSIZE;
653
654         for (i = 0; i <= DEVLINK_RELOAD_ACTION_MAX; i++) {
655                 if ((!is_remote &&
656                      !devlink_reload_action_is_supported(devlink, i)) ||
657                     i == DEVLINK_RELOAD_ACTION_UNSPEC)
658                         continue;
659                 act_info = nla_nest_start(msg, DEVLINK_ATTR_RELOAD_ACTION_INFO);
660                 if (!act_info)
661                         goto nla_put_failure;
662
663                 if (nla_put_u8(msg, DEVLINK_ATTR_RELOAD_ACTION, i))
664                         goto action_info_nest_cancel;
665                 act_stats = nla_nest_start(msg, DEVLINK_ATTR_RELOAD_ACTION_STATS);
666                 if (!act_stats)
667                         goto action_info_nest_cancel;
668
669                 for (j = 0; j <= DEVLINK_RELOAD_LIMIT_MAX; j++) {
670                         /* Remote stats are shown even if not locally supported.
671                          * Stats of actions with unspecified limit are shown
672                          * though drivers don't need to register unspecified
673                          * limit.
674                          */
675                         if ((!is_remote && j != DEVLINK_RELOAD_LIMIT_UNSPEC &&
676                              !devlink_reload_limit_is_supported(devlink, j)) ||
677                             devlink_reload_combination_is_invalid(i, j))
678                                 continue;
679
680                         stat_idx = j * __DEVLINK_RELOAD_ACTION_MAX + i;
681                         if (!is_remote)
682                                 value = devlink->stats.reload_stats[stat_idx];
683                         else
684                                 value = devlink->stats.remote_reload_stats[stat_idx];
685                         if (devlink_reload_stat_put(msg, j, value))
686                                 goto action_stats_nest_cancel;
687                 }
688                 nla_nest_end(msg, act_stats);
689                 nla_nest_end(msg, act_info);
690         }
691         nla_nest_end(msg, reload_stats_attr);
692         return 0;
693
694 action_stats_nest_cancel:
695         nla_nest_cancel(msg, act_stats);
696 action_info_nest_cancel:
697         nla_nest_cancel(msg, act_info);
698 nla_put_failure:
699         nla_nest_cancel(msg, reload_stats_attr);
700         return -EMSGSIZE;
701 }
702
703 static int devlink_nl_fill(struct sk_buff *msg, struct devlink *devlink,
704                            enum devlink_command cmd, u32 portid,
705                            u32 seq, int flags)
706 {
707         struct nlattr *dev_stats;
708         void *hdr;
709
710         hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
711         if (!hdr)
712                 return -EMSGSIZE;
713
714         if (devlink_nl_put_handle(msg, devlink))
715                 goto nla_put_failure;
716         if (nla_put_u8(msg, DEVLINK_ATTR_RELOAD_FAILED, devlink->reload_failed))
717                 goto nla_put_failure;
718
719         dev_stats = nla_nest_start(msg, DEVLINK_ATTR_DEV_STATS);
720         if (!dev_stats)
721                 goto nla_put_failure;
722
723         if (devlink_reload_stats_put(msg, devlink, false))
724                 goto dev_stats_nest_cancel;
725         if (devlink_reload_stats_put(msg, devlink, true))
726                 goto dev_stats_nest_cancel;
727
728         nla_nest_end(msg, dev_stats);
729         genlmsg_end(msg, hdr);
730         return 0;
731
732 dev_stats_nest_cancel:
733         nla_nest_cancel(msg, dev_stats);
734 nla_put_failure:
735         genlmsg_cancel(msg, hdr);
736         return -EMSGSIZE;
737 }
738
739 static void devlink_notify(struct devlink *devlink, enum devlink_command cmd)
740 {
741         struct sk_buff *msg;
742         int err;
743
744         WARN_ON(cmd != DEVLINK_CMD_NEW && cmd != DEVLINK_CMD_DEL);
745
746         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
747         if (!msg)
748                 return;
749
750         err = devlink_nl_fill(msg, devlink, cmd, 0, 0, 0);
751         if (err) {
752                 nlmsg_free(msg);
753                 return;
754         }
755
756         genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink),
757                                 msg, 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
758 }
759
760 static int devlink_nl_port_attrs_put(struct sk_buff *msg,
761                                      struct devlink_port *devlink_port)
762 {
763         struct devlink_port_attrs *attrs = &devlink_port->attrs;
764
765         if (!devlink_port->attrs_set)
766                 return 0;
767         if (attrs->lanes) {
768                 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_LANES, attrs->lanes))
769                         return -EMSGSIZE;
770         }
771         if (nla_put_u8(msg, DEVLINK_ATTR_PORT_SPLITTABLE, attrs->splittable))
772                 return -EMSGSIZE;
773         if (nla_put_u16(msg, DEVLINK_ATTR_PORT_FLAVOUR, attrs->flavour))
774                 return -EMSGSIZE;
775         switch (devlink_port->attrs.flavour) {
776         case DEVLINK_PORT_FLAVOUR_PCI_PF:
777                 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_CONTROLLER_NUMBER,
778                                 attrs->pci_pf.controller) ||
779                     nla_put_u16(msg, DEVLINK_ATTR_PORT_PCI_PF_NUMBER, attrs->pci_pf.pf))
780                         return -EMSGSIZE;
781                 if (nla_put_u8(msg, DEVLINK_ATTR_PORT_EXTERNAL, attrs->pci_pf.external))
782                         return -EMSGSIZE;
783                 break;
784         case DEVLINK_PORT_FLAVOUR_PCI_VF:
785                 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_CONTROLLER_NUMBER,
786                                 attrs->pci_vf.controller) ||
787                     nla_put_u16(msg, DEVLINK_ATTR_PORT_PCI_PF_NUMBER, attrs->pci_vf.pf) ||
788                     nla_put_u16(msg, DEVLINK_ATTR_PORT_PCI_VF_NUMBER, attrs->pci_vf.vf))
789                         return -EMSGSIZE;
790                 if (nla_put_u8(msg, DEVLINK_ATTR_PORT_EXTERNAL, attrs->pci_vf.external))
791                         return -EMSGSIZE;
792                 break;
793         case DEVLINK_PORT_FLAVOUR_PCI_SF:
794                 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_CONTROLLER_NUMBER,
795                                 attrs->pci_sf.controller) ||
796                     nla_put_u16(msg, DEVLINK_ATTR_PORT_PCI_PF_NUMBER,
797                                 attrs->pci_sf.pf) ||
798                     nla_put_u32(msg, DEVLINK_ATTR_PORT_PCI_SF_NUMBER,
799                                 attrs->pci_sf.sf))
800                         return -EMSGSIZE;
801                 break;
802         case DEVLINK_PORT_FLAVOUR_PHYSICAL:
803         case DEVLINK_PORT_FLAVOUR_CPU:
804         case DEVLINK_PORT_FLAVOUR_DSA:
805                 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_NUMBER,
806                                 attrs->phys.port_number))
807                         return -EMSGSIZE;
808                 if (!attrs->split)
809                         return 0;
810                 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_SPLIT_GROUP,
811                                 attrs->phys.port_number))
812                         return -EMSGSIZE;
813                 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_SPLIT_SUBPORT_NUMBER,
814                                 attrs->phys.split_subport_number))
815                         return -EMSGSIZE;
816                 break;
817         default:
818                 break;
819         }
820         return 0;
821 }
822
823 static int devlink_port_fn_hw_addr_fill(const struct devlink_ops *ops,
824                                         struct devlink_port *port,
825                                         struct sk_buff *msg,
826                                         struct netlink_ext_ack *extack,
827                                         bool *msg_updated)
828 {
829         u8 hw_addr[MAX_ADDR_LEN];
830         int hw_addr_len;
831         int err;
832
833         if (!ops->port_function_hw_addr_get)
834                 return 0;
835
836         err = ops->port_function_hw_addr_get(port, hw_addr, &hw_addr_len,
837                                              extack);
838         if (err) {
839                 if (err == -EOPNOTSUPP)
840                         return 0;
841                 return err;
842         }
843         err = nla_put(msg, DEVLINK_PORT_FUNCTION_ATTR_HW_ADDR, hw_addr_len, hw_addr);
844         if (err)
845                 return err;
846         *msg_updated = true;
847         return 0;
848 }
849
850 static int devlink_nl_rate_fill(struct sk_buff *msg,
851                                 struct devlink_rate *devlink_rate,
852                                 enum devlink_command cmd, u32 portid, u32 seq,
853                                 int flags, struct netlink_ext_ack *extack)
854 {
855         struct devlink *devlink = devlink_rate->devlink;
856         void *hdr;
857
858         hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
859         if (!hdr)
860                 return -EMSGSIZE;
861
862         if (devlink_nl_put_handle(msg, devlink))
863                 goto nla_put_failure;
864
865         if (nla_put_u16(msg, DEVLINK_ATTR_RATE_TYPE, devlink_rate->type))
866                 goto nla_put_failure;
867
868         if (devlink_rate_is_leaf(devlink_rate)) {
869                 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_INDEX,
870                                 devlink_rate->devlink_port->index))
871                         goto nla_put_failure;
872         } else if (devlink_rate_is_node(devlink_rate)) {
873                 if (nla_put_string(msg, DEVLINK_ATTR_RATE_NODE_NAME,
874                                    devlink_rate->name))
875                         goto nla_put_failure;
876         }
877
878         if (nla_put_u64_64bit(msg, DEVLINK_ATTR_RATE_TX_SHARE,
879                               devlink_rate->tx_share, DEVLINK_ATTR_PAD))
880                 goto nla_put_failure;
881
882         if (nla_put_u64_64bit(msg, DEVLINK_ATTR_RATE_TX_MAX,
883                               devlink_rate->tx_max, DEVLINK_ATTR_PAD))
884                 goto nla_put_failure;
885
886         if (devlink_rate->parent)
887                 if (nla_put_string(msg, DEVLINK_ATTR_RATE_PARENT_NODE_NAME,
888                                    devlink_rate->parent->name))
889                         goto nla_put_failure;
890
891         genlmsg_end(msg, hdr);
892         return 0;
893
894 nla_put_failure:
895         genlmsg_cancel(msg, hdr);
896         return -EMSGSIZE;
897 }
898
899 static bool
900 devlink_port_fn_state_valid(enum devlink_port_fn_state state)
901 {
902         return state == DEVLINK_PORT_FN_STATE_INACTIVE ||
903                state == DEVLINK_PORT_FN_STATE_ACTIVE;
904 }
905
906 static bool
907 devlink_port_fn_opstate_valid(enum devlink_port_fn_opstate opstate)
908 {
909         return opstate == DEVLINK_PORT_FN_OPSTATE_DETACHED ||
910                opstate == DEVLINK_PORT_FN_OPSTATE_ATTACHED;
911 }
912
913 static int devlink_port_fn_state_fill(const struct devlink_ops *ops,
914                                       struct devlink_port *port,
915                                       struct sk_buff *msg,
916                                       struct netlink_ext_ack *extack,
917                                       bool *msg_updated)
918 {
919         enum devlink_port_fn_opstate opstate;
920         enum devlink_port_fn_state state;
921         int err;
922
923         if (!ops->port_fn_state_get)
924                 return 0;
925
926         err = ops->port_fn_state_get(port, &state, &opstate, extack);
927         if (err) {
928                 if (err == -EOPNOTSUPP)
929                         return 0;
930                 return err;
931         }
932         if (!devlink_port_fn_state_valid(state)) {
933                 WARN_ON_ONCE(1);
934                 NL_SET_ERR_MSG_MOD(extack, "Invalid state read from driver");
935                 return -EINVAL;
936         }
937         if (!devlink_port_fn_opstate_valid(opstate)) {
938                 WARN_ON_ONCE(1);
939                 NL_SET_ERR_MSG_MOD(extack,
940                                    "Invalid operational state read from driver");
941                 return -EINVAL;
942         }
943         if (nla_put_u8(msg, DEVLINK_PORT_FN_ATTR_STATE, state) ||
944             nla_put_u8(msg, DEVLINK_PORT_FN_ATTR_OPSTATE, opstate))
945                 return -EMSGSIZE;
946         *msg_updated = true;
947         return 0;
948 }
949
950 static int
951 devlink_nl_port_function_attrs_put(struct sk_buff *msg, struct devlink_port *port,
952                                    struct netlink_ext_ack *extack)
953 {
954         const struct devlink_ops *ops;
955         struct nlattr *function_attr;
956         bool msg_updated = false;
957         int err;
958
959         function_attr = nla_nest_start_noflag(msg, DEVLINK_ATTR_PORT_FUNCTION);
960         if (!function_attr)
961                 return -EMSGSIZE;
962
963         ops = port->devlink->ops;
964         err = devlink_port_fn_hw_addr_fill(ops, port, msg, extack,
965                                            &msg_updated);
966         if (err)
967                 goto out;
968         err = devlink_port_fn_state_fill(ops, port, msg, extack, &msg_updated);
969 out:
970         if (err || !msg_updated)
971                 nla_nest_cancel(msg, function_attr);
972         else
973                 nla_nest_end(msg, function_attr);
974         return err;
975 }
976
977 static int devlink_nl_port_fill(struct sk_buff *msg,
978                                 struct devlink_port *devlink_port,
979                                 enum devlink_command cmd, u32 portid, u32 seq,
980                                 int flags, struct netlink_ext_ack *extack)
981 {
982         struct devlink *devlink = devlink_port->devlink;
983         void *hdr;
984
985         hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
986         if (!hdr)
987                 return -EMSGSIZE;
988
989         if (devlink_nl_put_handle(msg, devlink))
990                 goto nla_put_failure;
991         if (nla_put_u32(msg, DEVLINK_ATTR_PORT_INDEX, devlink_port->index))
992                 goto nla_put_failure;
993
994         /* Hold rtnl lock while accessing port's netdev attributes. */
995         rtnl_lock();
996         spin_lock_bh(&devlink_port->type_lock);
997         if (nla_put_u16(msg, DEVLINK_ATTR_PORT_TYPE, devlink_port->type))
998                 goto nla_put_failure_type_locked;
999         if (devlink_port->desired_type != DEVLINK_PORT_TYPE_NOTSET &&
1000             nla_put_u16(msg, DEVLINK_ATTR_PORT_DESIRED_TYPE,
1001                         devlink_port->desired_type))
1002                 goto nla_put_failure_type_locked;
1003         if (devlink_port->type == DEVLINK_PORT_TYPE_ETH) {
1004                 struct net *net = devlink_net(devlink_port->devlink);
1005                 struct net_device *netdev = devlink_port->type_dev;
1006
1007                 if (netdev && net_eq(net, dev_net(netdev)) &&
1008                     (nla_put_u32(msg, DEVLINK_ATTR_PORT_NETDEV_IFINDEX,
1009                                  netdev->ifindex) ||
1010                      nla_put_string(msg, DEVLINK_ATTR_PORT_NETDEV_NAME,
1011                                     netdev->name)))
1012                         goto nla_put_failure_type_locked;
1013         }
1014         if (devlink_port->type == DEVLINK_PORT_TYPE_IB) {
1015                 struct ib_device *ibdev = devlink_port->type_dev;
1016
1017                 if (ibdev &&
1018                     nla_put_string(msg, DEVLINK_ATTR_PORT_IBDEV_NAME,
1019                                    ibdev->name))
1020                         goto nla_put_failure_type_locked;
1021         }
1022         spin_unlock_bh(&devlink_port->type_lock);
1023         rtnl_unlock();
1024         if (devlink_nl_port_attrs_put(msg, devlink_port))
1025                 goto nla_put_failure;
1026         if (devlink_nl_port_function_attrs_put(msg, devlink_port, extack))
1027                 goto nla_put_failure;
1028
1029         genlmsg_end(msg, hdr);
1030         return 0;
1031
1032 nla_put_failure_type_locked:
1033         spin_unlock_bh(&devlink_port->type_lock);
1034         rtnl_unlock();
1035 nla_put_failure:
1036         genlmsg_cancel(msg, hdr);
1037         return -EMSGSIZE;
1038 }
1039
1040 static void devlink_port_notify(struct devlink_port *devlink_port,
1041                                 enum devlink_command cmd)
1042 {
1043         struct sk_buff *msg;
1044         int err;
1045
1046         WARN_ON(cmd != DEVLINK_CMD_PORT_NEW && cmd != DEVLINK_CMD_PORT_DEL);
1047
1048         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
1049         if (!msg)
1050                 return;
1051
1052         err = devlink_nl_port_fill(msg, devlink_port, cmd, 0, 0, 0, NULL);
1053         if (err) {
1054                 nlmsg_free(msg);
1055                 return;
1056         }
1057
1058         genlmsg_multicast_netns(&devlink_nl_family,
1059                                 devlink_net(devlink_port->devlink), msg, 0,
1060                                 DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
1061 }
1062
1063 static void devlink_rate_notify(struct devlink_rate *devlink_rate,
1064                                 enum devlink_command cmd)
1065 {
1066         struct sk_buff *msg;
1067         int err;
1068
1069         WARN_ON(cmd != DEVLINK_CMD_RATE_NEW && cmd != DEVLINK_CMD_RATE_DEL);
1070
1071         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
1072         if (!msg)
1073                 return;
1074
1075         err = devlink_nl_rate_fill(msg, devlink_rate, cmd, 0, 0, 0, NULL);
1076         if (err) {
1077                 nlmsg_free(msg);
1078                 return;
1079         }
1080
1081         genlmsg_multicast_netns(&devlink_nl_family,
1082                                 devlink_net(devlink_rate->devlink), msg, 0,
1083                                 DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
1084 }
1085
1086 static int devlink_nl_cmd_rate_get_dumpit(struct sk_buff *msg,
1087                                           struct netlink_callback *cb)
1088 {
1089         struct devlink_rate *devlink_rate;
1090         struct devlink *devlink;
1091         int start = cb->args[0];
1092         unsigned long index;
1093         int idx = 0;
1094         int err = 0;
1095
1096         mutex_lock(&devlink_mutex);
1097         xa_for_each_marked(&devlinks, index, devlink, DEVLINK_REGISTERED) {
1098                 if (!devlink_try_get(devlink))
1099                         continue;
1100
1101                 if (!net_eq(devlink_net(devlink), sock_net(msg->sk)))
1102                         goto retry;
1103
1104                 mutex_lock(&devlink->lock);
1105                 list_for_each_entry(devlink_rate, &devlink->rate_list, list) {
1106                         enum devlink_command cmd = DEVLINK_CMD_RATE_NEW;
1107                         u32 id = NETLINK_CB(cb->skb).portid;
1108
1109                         if (idx < start) {
1110                                 idx++;
1111                                 continue;
1112                         }
1113                         err = devlink_nl_rate_fill(msg, devlink_rate, cmd, id,
1114                                                    cb->nlh->nlmsg_seq,
1115                                                    NLM_F_MULTI, NULL);
1116                         if (err) {
1117                                 mutex_unlock(&devlink->lock);
1118                                 devlink_put(devlink);
1119                                 goto out;
1120                         }
1121                         idx++;
1122                 }
1123                 mutex_unlock(&devlink->lock);
1124 retry:
1125                 devlink_put(devlink);
1126         }
1127 out:
1128         mutex_unlock(&devlink_mutex);
1129         if (err != -EMSGSIZE)
1130                 return err;
1131
1132         cb->args[0] = idx;
1133         return msg->len;
1134 }
1135
1136 static int devlink_nl_cmd_rate_get_doit(struct sk_buff *skb,
1137                                         struct genl_info *info)
1138 {
1139         struct devlink_rate *devlink_rate = info->user_ptr[1];
1140         struct sk_buff *msg;
1141         int err;
1142
1143         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
1144         if (!msg)
1145                 return -ENOMEM;
1146
1147         err = devlink_nl_rate_fill(msg, devlink_rate, DEVLINK_CMD_RATE_NEW,
1148                                    info->snd_portid, info->snd_seq, 0,
1149                                    info->extack);
1150         if (err) {
1151                 nlmsg_free(msg);
1152                 return err;
1153         }
1154
1155         return genlmsg_reply(msg, info);
1156 }
1157
1158 static bool
1159 devlink_rate_is_parent_node(struct devlink_rate *devlink_rate,
1160                             struct devlink_rate *parent)
1161 {
1162         while (parent) {
1163                 if (parent == devlink_rate)
1164                         return true;
1165                 parent = parent->parent;
1166         }
1167         return false;
1168 }
1169
1170 static int devlink_nl_cmd_get_doit(struct sk_buff *skb, struct genl_info *info)
1171 {
1172         struct devlink *devlink = info->user_ptr[0];
1173         struct sk_buff *msg;
1174         int err;
1175
1176         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
1177         if (!msg)
1178                 return -ENOMEM;
1179
1180         err = devlink_nl_fill(msg, devlink, DEVLINK_CMD_NEW,
1181                               info->snd_portid, info->snd_seq, 0);
1182         if (err) {
1183                 nlmsg_free(msg);
1184                 return err;
1185         }
1186
1187         return genlmsg_reply(msg, info);
1188 }
1189
1190 static int devlink_nl_cmd_get_dumpit(struct sk_buff *msg,
1191                                      struct netlink_callback *cb)
1192 {
1193         struct devlink *devlink;
1194         int start = cb->args[0];
1195         unsigned long index;
1196         int idx = 0;
1197         int err;
1198
1199         mutex_lock(&devlink_mutex);
1200         xa_for_each_marked(&devlinks, index, devlink, DEVLINK_REGISTERED) {
1201                 if (!devlink_try_get(devlink))
1202                         continue;
1203
1204                 if (!net_eq(devlink_net(devlink), sock_net(msg->sk))) {
1205                         devlink_put(devlink);
1206                         continue;
1207                 }
1208
1209                 if (idx < start) {
1210                         idx++;
1211                         devlink_put(devlink);
1212                         continue;
1213                 }
1214
1215                 err = devlink_nl_fill(msg, devlink, DEVLINK_CMD_NEW,
1216                                       NETLINK_CB(cb->skb).portid,
1217                                       cb->nlh->nlmsg_seq, NLM_F_MULTI);
1218                 devlink_put(devlink);
1219                 if (err)
1220                         goto out;
1221                 idx++;
1222         }
1223 out:
1224         mutex_unlock(&devlink_mutex);
1225
1226         cb->args[0] = idx;
1227         return msg->len;
1228 }
1229
1230 static int devlink_nl_cmd_port_get_doit(struct sk_buff *skb,
1231                                         struct genl_info *info)
1232 {
1233         struct devlink_port *devlink_port = info->user_ptr[1];
1234         struct sk_buff *msg;
1235         int err;
1236
1237         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
1238         if (!msg)
1239                 return -ENOMEM;
1240
1241         err = devlink_nl_port_fill(msg, devlink_port, DEVLINK_CMD_PORT_NEW,
1242                                    info->snd_portid, info->snd_seq, 0,
1243                                    info->extack);
1244         if (err) {
1245                 nlmsg_free(msg);
1246                 return err;
1247         }
1248
1249         return genlmsg_reply(msg, info);
1250 }
1251
1252 static int devlink_nl_cmd_port_get_dumpit(struct sk_buff *msg,
1253                                           struct netlink_callback *cb)
1254 {
1255         struct devlink *devlink;
1256         struct devlink_port *devlink_port;
1257         int start = cb->args[0];
1258         unsigned long index;
1259         int idx = 0;
1260         int err;
1261
1262         mutex_lock(&devlink_mutex);
1263         xa_for_each_marked(&devlinks, index, devlink, DEVLINK_REGISTERED) {
1264                 if (!devlink_try_get(devlink))
1265                         continue;
1266
1267                 if (!net_eq(devlink_net(devlink), sock_net(msg->sk)))
1268                         goto retry;
1269
1270                 mutex_lock(&devlink->lock);
1271                 list_for_each_entry(devlink_port, &devlink->port_list, list) {
1272                         if (idx < start) {
1273                                 idx++;
1274                                 continue;
1275                         }
1276                         err = devlink_nl_port_fill(msg, devlink_port,
1277                                                    DEVLINK_CMD_NEW,
1278                                                    NETLINK_CB(cb->skb).portid,
1279                                                    cb->nlh->nlmsg_seq,
1280                                                    NLM_F_MULTI, cb->extack);
1281                         if (err) {
1282                                 mutex_unlock(&devlink->lock);
1283                                 devlink_put(devlink);
1284                                 goto out;
1285                         }
1286                         idx++;
1287                 }
1288                 mutex_unlock(&devlink->lock);
1289 retry:
1290                 devlink_put(devlink);
1291         }
1292 out:
1293         mutex_unlock(&devlink_mutex);
1294
1295         cb->args[0] = idx;
1296         return msg->len;
1297 }
1298
1299 static int devlink_port_type_set(struct devlink_port *devlink_port,
1300                                  enum devlink_port_type port_type)
1301
1302 {
1303         int err;
1304
1305         if (!devlink_port->devlink->ops->port_type_set)
1306                 return -EOPNOTSUPP;
1307
1308         if (port_type == devlink_port->type)
1309                 return 0;
1310
1311         err = devlink_port->devlink->ops->port_type_set(devlink_port,
1312                                                         port_type);
1313         if (err)
1314                 return err;
1315
1316         devlink_port->desired_type = port_type;
1317         devlink_port_notify(devlink_port, DEVLINK_CMD_PORT_NEW);
1318         return 0;
1319 }
1320
1321 static int devlink_port_function_hw_addr_set(struct devlink_port *port,
1322                                              const struct nlattr *attr,
1323                                              struct netlink_ext_ack *extack)
1324 {
1325         const struct devlink_ops *ops = port->devlink->ops;
1326         const u8 *hw_addr;
1327         int hw_addr_len;
1328
1329         hw_addr = nla_data(attr);
1330         hw_addr_len = nla_len(attr);
1331         if (hw_addr_len > MAX_ADDR_LEN) {
1332                 NL_SET_ERR_MSG_MOD(extack, "Port function hardware address too long");
1333                 return -EINVAL;
1334         }
1335         if (port->type == DEVLINK_PORT_TYPE_ETH) {
1336                 if (hw_addr_len != ETH_ALEN) {
1337                         NL_SET_ERR_MSG_MOD(extack, "Address must be 6 bytes for Ethernet device");
1338                         return -EINVAL;
1339                 }
1340                 if (!is_unicast_ether_addr(hw_addr)) {
1341                         NL_SET_ERR_MSG_MOD(extack, "Non-unicast hardware address unsupported");
1342                         return -EINVAL;
1343                 }
1344         }
1345
1346         if (!ops->port_function_hw_addr_set) {
1347                 NL_SET_ERR_MSG_MOD(extack, "Port doesn't support function attributes");
1348                 return -EOPNOTSUPP;
1349         }
1350
1351         return ops->port_function_hw_addr_set(port, hw_addr, hw_addr_len,
1352                                               extack);
1353 }
1354
1355 static int devlink_port_fn_state_set(struct devlink_port *port,
1356                                      const struct nlattr *attr,
1357                                      struct netlink_ext_ack *extack)
1358 {
1359         enum devlink_port_fn_state state;
1360         const struct devlink_ops *ops;
1361
1362         state = nla_get_u8(attr);
1363         ops = port->devlink->ops;
1364         if (!ops->port_fn_state_set) {
1365                 NL_SET_ERR_MSG_MOD(extack,
1366                                    "Function does not support state setting");
1367                 return -EOPNOTSUPP;
1368         }
1369         return ops->port_fn_state_set(port, state, extack);
1370 }
1371
1372 static int devlink_port_function_set(struct devlink_port *port,
1373                                      const struct nlattr *attr,
1374                                      struct netlink_ext_ack *extack)
1375 {
1376         struct nlattr *tb[DEVLINK_PORT_FUNCTION_ATTR_MAX + 1];
1377         int err;
1378
1379         err = nla_parse_nested(tb, DEVLINK_PORT_FUNCTION_ATTR_MAX, attr,
1380                                devlink_function_nl_policy, extack);
1381         if (err < 0) {
1382                 NL_SET_ERR_MSG_MOD(extack, "Fail to parse port function attributes");
1383                 return err;
1384         }
1385
1386         attr = tb[DEVLINK_PORT_FUNCTION_ATTR_HW_ADDR];
1387         if (attr) {
1388                 err = devlink_port_function_hw_addr_set(port, attr, extack);
1389                 if (err)
1390                         return err;
1391         }
1392         /* Keep this as the last function attribute set, so that when
1393          * multiple port function attributes are set along with state,
1394          * Those can be applied first before activating the state.
1395          */
1396         attr = tb[DEVLINK_PORT_FN_ATTR_STATE];
1397         if (attr)
1398                 err = devlink_port_fn_state_set(port, attr, extack);
1399
1400         if (!err)
1401                 devlink_port_notify(port, DEVLINK_CMD_PORT_NEW);
1402         return err;
1403 }
1404
1405 static int devlink_nl_cmd_port_set_doit(struct sk_buff *skb,
1406                                         struct genl_info *info)
1407 {
1408         struct devlink_port *devlink_port = info->user_ptr[1];
1409         int err;
1410
1411         if (info->attrs[DEVLINK_ATTR_PORT_TYPE]) {
1412                 enum devlink_port_type port_type;
1413
1414                 port_type = nla_get_u16(info->attrs[DEVLINK_ATTR_PORT_TYPE]);
1415                 err = devlink_port_type_set(devlink_port, port_type);
1416                 if (err)
1417                         return err;
1418         }
1419
1420         if (info->attrs[DEVLINK_ATTR_PORT_FUNCTION]) {
1421                 struct nlattr *attr = info->attrs[DEVLINK_ATTR_PORT_FUNCTION];
1422                 struct netlink_ext_ack *extack = info->extack;
1423
1424                 err = devlink_port_function_set(devlink_port, attr, extack);
1425                 if (err)
1426                         return err;
1427         }
1428
1429         return 0;
1430 }
1431
1432 static int devlink_port_split(struct devlink *devlink, u32 port_index,
1433                               u32 count, struct netlink_ext_ack *extack)
1434
1435 {
1436         if (devlink->ops->port_split)
1437                 return devlink->ops->port_split(devlink, port_index, count,
1438                                                 extack);
1439         return -EOPNOTSUPP;
1440 }
1441
1442 static int devlink_nl_cmd_port_split_doit(struct sk_buff *skb,
1443                                           struct genl_info *info)
1444 {
1445         struct devlink *devlink = info->user_ptr[0];
1446         struct devlink_port *devlink_port;
1447         u32 port_index;
1448         u32 count;
1449
1450         if (!info->attrs[DEVLINK_ATTR_PORT_INDEX] ||
1451             !info->attrs[DEVLINK_ATTR_PORT_SPLIT_COUNT])
1452                 return -EINVAL;
1453
1454         devlink_port = devlink_port_get_from_info(devlink, info);
1455         port_index = nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_INDEX]);
1456         count = nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_SPLIT_COUNT]);
1457
1458         if (IS_ERR(devlink_port))
1459                 return -EINVAL;
1460
1461         if (!devlink_port->attrs.splittable) {
1462                 /* Split ports cannot be split. */
1463                 if (devlink_port->attrs.split)
1464                         NL_SET_ERR_MSG_MOD(info->extack, "Port cannot be split further");
1465                 else
1466                         NL_SET_ERR_MSG_MOD(info->extack, "Port cannot be split");
1467                 return -EINVAL;
1468         }
1469
1470         if (count < 2 || !is_power_of_2(count) || count > devlink_port->attrs.lanes) {
1471                 NL_SET_ERR_MSG_MOD(info->extack, "Invalid split count");
1472                 return -EINVAL;
1473         }
1474
1475         return devlink_port_split(devlink, port_index, count, info->extack);
1476 }
1477
1478 static int devlink_port_unsplit(struct devlink *devlink, u32 port_index,
1479                                 struct netlink_ext_ack *extack)
1480
1481 {
1482         if (devlink->ops->port_unsplit)
1483                 return devlink->ops->port_unsplit(devlink, port_index, extack);
1484         return -EOPNOTSUPP;
1485 }
1486
1487 static int devlink_nl_cmd_port_unsplit_doit(struct sk_buff *skb,
1488                                             struct genl_info *info)
1489 {
1490         struct devlink *devlink = info->user_ptr[0];
1491         u32 port_index;
1492
1493         if (!info->attrs[DEVLINK_ATTR_PORT_INDEX])
1494                 return -EINVAL;
1495
1496         port_index = nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_INDEX]);
1497         return devlink_port_unsplit(devlink, port_index, info->extack);
1498 }
1499
1500 static int devlink_port_new_notifiy(struct devlink *devlink,
1501                                     unsigned int port_index,
1502                                     struct genl_info *info)
1503 {
1504         struct devlink_port *devlink_port;
1505         struct sk_buff *msg;
1506         int err;
1507
1508         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
1509         if (!msg)
1510                 return -ENOMEM;
1511
1512         mutex_lock(&devlink->lock);
1513         devlink_port = devlink_port_get_by_index(devlink, port_index);
1514         if (!devlink_port) {
1515                 err = -ENODEV;
1516                 goto out;
1517         }
1518
1519         err = devlink_nl_port_fill(msg, devlink_port, DEVLINK_CMD_NEW,
1520                                    info->snd_portid, info->snd_seq, 0, NULL);
1521         if (err)
1522                 goto out;
1523
1524         err = genlmsg_reply(msg, info);
1525         mutex_unlock(&devlink->lock);
1526         return err;
1527
1528 out:
1529         mutex_unlock(&devlink->lock);
1530         nlmsg_free(msg);
1531         return err;
1532 }
1533
1534 static int devlink_nl_cmd_port_new_doit(struct sk_buff *skb,
1535                                         struct genl_info *info)
1536 {
1537         struct netlink_ext_ack *extack = info->extack;
1538         struct devlink_port_new_attrs new_attrs = {};
1539         struct devlink *devlink = info->user_ptr[0];
1540         unsigned int new_port_index;
1541         int err;
1542
1543         if (!devlink->ops->port_new || !devlink->ops->port_del)
1544                 return -EOPNOTSUPP;
1545
1546         if (!info->attrs[DEVLINK_ATTR_PORT_FLAVOUR] ||
1547             !info->attrs[DEVLINK_ATTR_PORT_PCI_PF_NUMBER]) {
1548                 NL_SET_ERR_MSG_MOD(extack, "Port flavour or PCI PF are not specified");
1549                 return -EINVAL;
1550         }
1551         new_attrs.flavour = nla_get_u16(info->attrs[DEVLINK_ATTR_PORT_FLAVOUR]);
1552         new_attrs.pfnum =
1553                 nla_get_u16(info->attrs[DEVLINK_ATTR_PORT_PCI_PF_NUMBER]);
1554
1555         if (info->attrs[DEVLINK_ATTR_PORT_INDEX]) {
1556                 /* Port index of the new port being created by driver. */
1557                 new_attrs.port_index =
1558                         nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_INDEX]);
1559                 new_attrs.port_index_valid = true;
1560         }
1561         if (info->attrs[DEVLINK_ATTR_PORT_CONTROLLER_NUMBER]) {
1562                 new_attrs.controller =
1563                         nla_get_u16(info->attrs[DEVLINK_ATTR_PORT_CONTROLLER_NUMBER]);
1564                 new_attrs.controller_valid = true;
1565         }
1566         if (new_attrs.flavour == DEVLINK_PORT_FLAVOUR_PCI_SF &&
1567             info->attrs[DEVLINK_ATTR_PORT_PCI_SF_NUMBER]) {
1568                 new_attrs.sfnum = nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_PCI_SF_NUMBER]);
1569                 new_attrs.sfnum_valid = true;
1570         }
1571
1572         err = devlink->ops->port_new(devlink, &new_attrs, extack,
1573                                      &new_port_index);
1574         if (err)
1575                 return err;
1576
1577         err = devlink_port_new_notifiy(devlink, new_port_index, info);
1578         if (err && err != -ENODEV) {
1579                 /* Fail to send the response; destroy newly created port. */
1580                 devlink->ops->port_del(devlink, new_port_index, extack);
1581         }
1582         return err;
1583 }
1584
1585 static int devlink_nl_cmd_port_del_doit(struct sk_buff *skb,
1586                                         struct genl_info *info)
1587 {
1588         struct netlink_ext_ack *extack = info->extack;
1589         struct devlink *devlink = info->user_ptr[0];
1590         unsigned int port_index;
1591
1592         if (!devlink->ops->port_del)
1593                 return -EOPNOTSUPP;
1594
1595         if (!info->attrs[DEVLINK_ATTR_PORT_INDEX]) {
1596                 NL_SET_ERR_MSG_MOD(extack, "Port index is not specified");
1597                 return -EINVAL;
1598         }
1599         port_index = nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_INDEX]);
1600
1601         return devlink->ops->port_del(devlink, port_index, extack);
1602 }
1603
1604 static int
1605 devlink_nl_rate_parent_node_set(struct devlink_rate *devlink_rate,
1606                                 struct genl_info *info,
1607                                 struct nlattr *nla_parent)
1608 {
1609         struct devlink *devlink = devlink_rate->devlink;
1610         const char *parent_name = nla_data(nla_parent);
1611         const struct devlink_ops *ops = devlink->ops;
1612         size_t len = strlen(parent_name);
1613         struct devlink_rate *parent;
1614         int err = -EOPNOTSUPP;
1615
1616         parent = devlink_rate->parent;
1617         if (parent && len) {
1618                 NL_SET_ERR_MSG_MOD(info->extack, "Rate object already has parent.");
1619                 return -EBUSY;
1620         } else if (parent && !len) {
1621                 if (devlink_rate_is_leaf(devlink_rate))
1622                         err = ops->rate_leaf_parent_set(devlink_rate, NULL,
1623                                                         devlink_rate->priv, NULL,
1624                                                         info->extack);
1625                 else if (devlink_rate_is_node(devlink_rate))
1626                         err = ops->rate_node_parent_set(devlink_rate, NULL,
1627                                                         devlink_rate->priv, NULL,
1628                                                         info->extack);
1629                 if (err)
1630                         return err;
1631
1632                 refcount_dec(&parent->refcnt);
1633                 devlink_rate->parent = NULL;
1634         } else if (!parent && len) {
1635                 parent = devlink_rate_node_get_by_name(devlink, parent_name);
1636                 if (IS_ERR(parent))
1637                         return -ENODEV;
1638
1639                 if (parent == devlink_rate) {
1640                         NL_SET_ERR_MSG_MOD(info->extack, "Parent to self is not allowed");
1641                         return -EINVAL;
1642                 }
1643
1644                 if (devlink_rate_is_node(devlink_rate) &&
1645                     devlink_rate_is_parent_node(devlink_rate, parent->parent)) {
1646                         NL_SET_ERR_MSG_MOD(info->extack, "Node is already a parent of parent node.");
1647                         return -EEXIST;
1648                 }
1649
1650                 if (devlink_rate_is_leaf(devlink_rate))
1651                         err = ops->rate_leaf_parent_set(devlink_rate, parent,
1652                                                         devlink_rate->priv, parent->priv,
1653                                                         info->extack);
1654                 else if (devlink_rate_is_node(devlink_rate))
1655                         err = ops->rate_node_parent_set(devlink_rate, parent,
1656                                                         devlink_rate->priv, parent->priv,
1657                                                         info->extack);
1658                 if (err)
1659                         return err;
1660
1661                 refcount_inc(&parent->refcnt);
1662                 devlink_rate->parent = parent;
1663         }
1664
1665         return 0;
1666 }
1667
1668 static int devlink_nl_rate_set(struct devlink_rate *devlink_rate,
1669                                const struct devlink_ops *ops,
1670                                struct genl_info *info)
1671 {
1672         struct nlattr *nla_parent, **attrs = info->attrs;
1673         int err = -EOPNOTSUPP;
1674         u64 rate;
1675
1676         if (attrs[DEVLINK_ATTR_RATE_TX_SHARE]) {
1677                 rate = nla_get_u64(attrs[DEVLINK_ATTR_RATE_TX_SHARE]);
1678                 if (devlink_rate_is_leaf(devlink_rate))
1679                         err = ops->rate_leaf_tx_share_set(devlink_rate, devlink_rate->priv,
1680                                                           rate, info->extack);
1681                 else if (devlink_rate_is_node(devlink_rate))
1682                         err = ops->rate_node_tx_share_set(devlink_rate, devlink_rate->priv,
1683                                                           rate, info->extack);
1684                 if (err)
1685                         return err;
1686                 devlink_rate->tx_share = rate;
1687         }
1688
1689         if (attrs[DEVLINK_ATTR_RATE_TX_MAX]) {
1690                 rate = nla_get_u64(attrs[DEVLINK_ATTR_RATE_TX_MAX]);
1691                 if (devlink_rate_is_leaf(devlink_rate))
1692                         err = ops->rate_leaf_tx_max_set(devlink_rate, devlink_rate->priv,
1693                                                         rate, info->extack);
1694                 else if (devlink_rate_is_node(devlink_rate))
1695                         err = ops->rate_node_tx_max_set(devlink_rate, devlink_rate->priv,
1696                                                         rate, info->extack);
1697                 if (err)
1698                         return err;
1699                 devlink_rate->tx_max = rate;
1700         }
1701
1702         nla_parent = attrs[DEVLINK_ATTR_RATE_PARENT_NODE_NAME];
1703         if (nla_parent) {
1704                 err = devlink_nl_rate_parent_node_set(devlink_rate, info,
1705                                                       nla_parent);
1706                 if (err)
1707                         return err;
1708         }
1709
1710         return 0;
1711 }
1712
1713 static bool devlink_rate_set_ops_supported(const struct devlink_ops *ops,
1714                                            struct genl_info *info,
1715                                            enum devlink_rate_type type)
1716 {
1717         struct nlattr **attrs = info->attrs;
1718
1719         if (type == DEVLINK_RATE_TYPE_LEAF) {
1720                 if (attrs[DEVLINK_ATTR_RATE_TX_SHARE] && !ops->rate_leaf_tx_share_set) {
1721                         NL_SET_ERR_MSG_MOD(info->extack, "TX share set isn't supported for the leafs");
1722                         return false;
1723                 }
1724                 if (attrs[DEVLINK_ATTR_RATE_TX_MAX] && !ops->rate_leaf_tx_max_set) {
1725                         NL_SET_ERR_MSG_MOD(info->extack, "TX max set isn't supported for the leafs");
1726                         return false;
1727                 }
1728                 if (attrs[DEVLINK_ATTR_RATE_PARENT_NODE_NAME] &&
1729                     !ops->rate_leaf_parent_set) {
1730                         NL_SET_ERR_MSG_MOD(info->extack, "Parent set isn't supported for the leafs");
1731                         return false;
1732                 }
1733         } else if (type == DEVLINK_RATE_TYPE_NODE) {
1734                 if (attrs[DEVLINK_ATTR_RATE_TX_SHARE] && !ops->rate_node_tx_share_set) {
1735                         NL_SET_ERR_MSG_MOD(info->extack, "TX share set isn't supported for the nodes");
1736                         return false;
1737                 }
1738                 if (attrs[DEVLINK_ATTR_RATE_TX_MAX] && !ops->rate_node_tx_max_set) {
1739                         NL_SET_ERR_MSG_MOD(info->extack, "TX max set isn't supported for the nodes");
1740                         return false;
1741                 }
1742                 if (attrs[DEVLINK_ATTR_RATE_PARENT_NODE_NAME] &&
1743                     !ops->rate_node_parent_set) {
1744                         NL_SET_ERR_MSG_MOD(info->extack, "Parent set isn't supported for the nodes");
1745                         return false;
1746                 }
1747         } else {
1748                 WARN(1, "Unknown type of rate object");
1749                 return false;
1750         }
1751
1752         return true;
1753 }
1754
1755 static int devlink_nl_cmd_rate_set_doit(struct sk_buff *skb,
1756                                         struct genl_info *info)
1757 {
1758         struct devlink_rate *devlink_rate = info->user_ptr[1];
1759         struct devlink *devlink = devlink_rate->devlink;
1760         const struct devlink_ops *ops = devlink->ops;
1761         int err;
1762
1763         if (!ops || !devlink_rate_set_ops_supported(ops, info, devlink_rate->type))
1764                 return -EOPNOTSUPP;
1765
1766         err = devlink_nl_rate_set(devlink_rate, ops, info);
1767
1768         if (!err)
1769                 devlink_rate_notify(devlink_rate, DEVLINK_CMD_RATE_NEW);
1770         return err;
1771 }
1772
1773 static int devlink_nl_cmd_rate_new_doit(struct sk_buff *skb,
1774                                         struct genl_info *info)
1775 {
1776         struct devlink *devlink = info->user_ptr[0];
1777         struct devlink_rate *rate_node;
1778         const struct devlink_ops *ops;
1779         int err;
1780
1781         ops = devlink->ops;
1782         if (!ops || !ops->rate_node_new || !ops->rate_node_del) {
1783                 NL_SET_ERR_MSG_MOD(info->extack, "Rate nodes aren't supported");
1784                 return -EOPNOTSUPP;
1785         }
1786
1787         if (!devlink_rate_set_ops_supported(ops, info, DEVLINK_RATE_TYPE_NODE))
1788                 return -EOPNOTSUPP;
1789
1790         rate_node = devlink_rate_node_get_from_attrs(devlink, info->attrs);
1791         if (!IS_ERR(rate_node))
1792                 return -EEXIST;
1793         else if (rate_node == ERR_PTR(-EINVAL))
1794                 return -EINVAL;
1795
1796         rate_node = kzalloc(sizeof(*rate_node), GFP_KERNEL);
1797         if (!rate_node)
1798                 return -ENOMEM;
1799
1800         rate_node->devlink = devlink;
1801         rate_node->type = DEVLINK_RATE_TYPE_NODE;
1802         rate_node->name = nla_strdup(info->attrs[DEVLINK_ATTR_RATE_NODE_NAME], GFP_KERNEL);
1803         if (!rate_node->name) {
1804                 err = -ENOMEM;
1805                 goto err_strdup;
1806         }
1807
1808         err = ops->rate_node_new(rate_node, &rate_node->priv, info->extack);
1809         if (err)
1810                 goto err_node_new;
1811
1812         err = devlink_nl_rate_set(rate_node, ops, info);
1813         if (err)
1814                 goto err_rate_set;
1815
1816         refcount_set(&rate_node->refcnt, 1);
1817         list_add(&rate_node->list, &devlink->rate_list);
1818         devlink_rate_notify(rate_node, DEVLINK_CMD_RATE_NEW);
1819         return 0;
1820
1821 err_rate_set:
1822         ops->rate_node_del(rate_node, rate_node->priv, info->extack);
1823 err_node_new:
1824         kfree(rate_node->name);
1825 err_strdup:
1826         kfree(rate_node);
1827         return err;
1828 }
1829
1830 static int devlink_nl_cmd_rate_del_doit(struct sk_buff *skb,
1831                                         struct genl_info *info)
1832 {
1833         struct devlink_rate *rate_node = info->user_ptr[1];
1834         struct devlink *devlink = rate_node->devlink;
1835         const struct devlink_ops *ops = devlink->ops;
1836         int err;
1837
1838         if (refcount_read(&rate_node->refcnt) > 1) {
1839                 NL_SET_ERR_MSG_MOD(info->extack, "Node has children. Cannot delete node.");
1840                 return -EBUSY;
1841         }
1842
1843         devlink_rate_notify(rate_node, DEVLINK_CMD_RATE_DEL);
1844         err = ops->rate_node_del(rate_node, rate_node->priv, info->extack);
1845         if (rate_node->parent)
1846                 refcount_dec(&rate_node->parent->refcnt);
1847         list_del(&rate_node->list);
1848         kfree(rate_node->name);
1849         kfree(rate_node);
1850         return err;
1851 }
1852
1853 static int devlink_nl_sb_fill(struct sk_buff *msg, struct devlink *devlink,
1854                               struct devlink_sb *devlink_sb,
1855                               enum devlink_command cmd, u32 portid,
1856                               u32 seq, int flags)
1857 {
1858         void *hdr;
1859
1860         hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
1861         if (!hdr)
1862                 return -EMSGSIZE;
1863
1864         if (devlink_nl_put_handle(msg, devlink))
1865                 goto nla_put_failure;
1866         if (nla_put_u32(msg, DEVLINK_ATTR_SB_INDEX, devlink_sb->index))
1867                 goto nla_put_failure;
1868         if (nla_put_u32(msg, DEVLINK_ATTR_SB_SIZE, devlink_sb->size))
1869                 goto nla_put_failure;
1870         if (nla_put_u16(msg, DEVLINK_ATTR_SB_INGRESS_POOL_COUNT,
1871                         devlink_sb->ingress_pools_count))
1872                 goto nla_put_failure;
1873         if (nla_put_u16(msg, DEVLINK_ATTR_SB_EGRESS_POOL_COUNT,
1874                         devlink_sb->egress_pools_count))
1875                 goto nla_put_failure;
1876         if (nla_put_u16(msg, DEVLINK_ATTR_SB_INGRESS_TC_COUNT,
1877                         devlink_sb->ingress_tc_count))
1878                 goto nla_put_failure;
1879         if (nla_put_u16(msg, DEVLINK_ATTR_SB_EGRESS_TC_COUNT,
1880                         devlink_sb->egress_tc_count))
1881                 goto nla_put_failure;
1882
1883         genlmsg_end(msg, hdr);
1884         return 0;
1885
1886 nla_put_failure:
1887         genlmsg_cancel(msg, hdr);
1888         return -EMSGSIZE;
1889 }
1890
1891 static int devlink_nl_cmd_sb_get_doit(struct sk_buff *skb,
1892                                       struct genl_info *info)
1893 {
1894         struct devlink *devlink = info->user_ptr[0];
1895         struct devlink_sb *devlink_sb;
1896         struct sk_buff *msg;
1897         int err;
1898
1899         devlink_sb = devlink_sb_get_from_info(devlink, info);
1900         if (IS_ERR(devlink_sb))
1901                 return PTR_ERR(devlink_sb);
1902
1903         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
1904         if (!msg)
1905                 return -ENOMEM;
1906
1907         err = devlink_nl_sb_fill(msg, devlink, devlink_sb,
1908                                  DEVLINK_CMD_SB_NEW,
1909                                  info->snd_portid, info->snd_seq, 0);
1910         if (err) {
1911                 nlmsg_free(msg);
1912                 return err;
1913         }
1914
1915         return genlmsg_reply(msg, info);
1916 }
1917
1918 static int devlink_nl_cmd_sb_get_dumpit(struct sk_buff *msg,
1919                                         struct netlink_callback *cb)
1920 {
1921         struct devlink *devlink;
1922         struct devlink_sb *devlink_sb;
1923         int start = cb->args[0];
1924         unsigned long index;
1925         int idx = 0;
1926         int err;
1927
1928         mutex_lock(&devlink_mutex);
1929         xa_for_each_marked(&devlinks, index, devlink, DEVLINK_REGISTERED) {
1930                 if (!devlink_try_get(devlink))
1931                         continue;
1932
1933                 if (!net_eq(devlink_net(devlink), sock_net(msg->sk)))
1934                         goto retry;
1935
1936                 mutex_lock(&devlink->lock);
1937                 list_for_each_entry(devlink_sb, &devlink->sb_list, list) {
1938                         if (idx < start) {
1939                                 idx++;
1940                                 continue;
1941                         }
1942                         err = devlink_nl_sb_fill(msg, devlink, devlink_sb,
1943                                                  DEVLINK_CMD_SB_NEW,
1944                                                  NETLINK_CB(cb->skb).portid,
1945                                                  cb->nlh->nlmsg_seq,
1946                                                  NLM_F_MULTI);
1947                         if (err) {
1948                                 mutex_unlock(&devlink->lock);
1949                                 devlink_put(devlink);
1950                                 goto out;
1951                         }
1952                         idx++;
1953                 }
1954                 mutex_unlock(&devlink->lock);
1955 retry:
1956                 devlink_put(devlink);
1957         }
1958 out:
1959         mutex_unlock(&devlink_mutex);
1960
1961         cb->args[0] = idx;
1962         return msg->len;
1963 }
1964
1965 static int devlink_nl_sb_pool_fill(struct sk_buff *msg, struct devlink *devlink,
1966                                    struct devlink_sb *devlink_sb,
1967                                    u16 pool_index, enum devlink_command cmd,
1968                                    u32 portid, u32 seq, int flags)
1969 {
1970         struct devlink_sb_pool_info pool_info;
1971         void *hdr;
1972         int err;
1973
1974         err = devlink->ops->sb_pool_get(devlink, devlink_sb->index,
1975                                         pool_index, &pool_info);
1976         if (err)
1977                 return err;
1978
1979         hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
1980         if (!hdr)
1981                 return -EMSGSIZE;
1982
1983         if (devlink_nl_put_handle(msg, devlink))
1984                 goto nla_put_failure;
1985         if (nla_put_u32(msg, DEVLINK_ATTR_SB_INDEX, devlink_sb->index))
1986                 goto nla_put_failure;
1987         if (nla_put_u16(msg, DEVLINK_ATTR_SB_POOL_INDEX, pool_index))
1988                 goto nla_put_failure;
1989         if (nla_put_u8(msg, DEVLINK_ATTR_SB_POOL_TYPE, pool_info.pool_type))
1990                 goto nla_put_failure;
1991         if (nla_put_u32(msg, DEVLINK_ATTR_SB_POOL_SIZE, pool_info.size))
1992                 goto nla_put_failure;
1993         if (nla_put_u8(msg, DEVLINK_ATTR_SB_POOL_THRESHOLD_TYPE,
1994                        pool_info.threshold_type))
1995                 goto nla_put_failure;
1996         if (nla_put_u32(msg, DEVLINK_ATTR_SB_POOL_CELL_SIZE,
1997                         pool_info.cell_size))
1998                 goto nla_put_failure;
1999
2000         genlmsg_end(msg, hdr);
2001         return 0;
2002
2003 nla_put_failure:
2004         genlmsg_cancel(msg, hdr);
2005         return -EMSGSIZE;
2006 }
2007
2008 static int devlink_nl_cmd_sb_pool_get_doit(struct sk_buff *skb,
2009                                            struct genl_info *info)
2010 {
2011         struct devlink *devlink = info->user_ptr[0];
2012         struct devlink_sb *devlink_sb;
2013         struct sk_buff *msg;
2014         u16 pool_index;
2015         int err;
2016
2017         devlink_sb = devlink_sb_get_from_info(devlink, info);
2018         if (IS_ERR(devlink_sb))
2019                 return PTR_ERR(devlink_sb);
2020
2021         err = devlink_sb_pool_index_get_from_info(devlink_sb, info,
2022                                                   &pool_index);
2023         if (err)
2024                 return err;
2025
2026         if (!devlink->ops->sb_pool_get)
2027                 return -EOPNOTSUPP;
2028
2029         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
2030         if (!msg)
2031                 return -ENOMEM;
2032
2033         err = devlink_nl_sb_pool_fill(msg, devlink, devlink_sb, pool_index,
2034                                       DEVLINK_CMD_SB_POOL_NEW,
2035                                       info->snd_portid, info->snd_seq, 0);
2036         if (err) {
2037                 nlmsg_free(msg);
2038                 return err;
2039         }
2040
2041         return genlmsg_reply(msg, info);
2042 }
2043
2044 static int __sb_pool_get_dumpit(struct sk_buff *msg, int start, int *p_idx,
2045                                 struct devlink *devlink,
2046                                 struct devlink_sb *devlink_sb,
2047                                 u32 portid, u32 seq)
2048 {
2049         u16 pool_count = devlink_sb_pool_count(devlink_sb);
2050         u16 pool_index;
2051         int err;
2052
2053         for (pool_index = 0; pool_index < pool_count; pool_index++) {
2054                 if (*p_idx < start) {
2055                         (*p_idx)++;
2056                         continue;
2057                 }
2058                 err = devlink_nl_sb_pool_fill(msg, devlink,
2059                                               devlink_sb,
2060                                               pool_index,
2061                                               DEVLINK_CMD_SB_POOL_NEW,
2062                                               portid, seq, NLM_F_MULTI);
2063                 if (err)
2064                         return err;
2065                 (*p_idx)++;
2066         }
2067         return 0;
2068 }
2069
2070 static int devlink_nl_cmd_sb_pool_get_dumpit(struct sk_buff *msg,
2071                                              struct netlink_callback *cb)
2072 {
2073         struct devlink *devlink;
2074         struct devlink_sb *devlink_sb;
2075         int start = cb->args[0];
2076         unsigned long index;
2077         int idx = 0;
2078         int err = 0;
2079
2080         mutex_lock(&devlink_mutex);
2081         xa_for_each_marked(&devlinks, index, devlink, DEVLINK_REGISTERED) {
2082                 if (!devlink_try_get(devlink))
2083                         continue;
2084
2085                 if (!net_eq(devlink_net(devlink), sock_net(msg->sk)) ||
2086                     !devlink->ops->sb_pool_get)
2087                         goto retry;
2088
2089                 mutex_lock(&devlink->lock);
2090                 list_for_each_entry(devlink_sb, &devlink->sb_list, list) {
2091                         err = __sb_pool_get_dumpit(msg, start, &idx, devlink,
2092                                                    devlink_sb,
2093                                                    NETLINK_CB(cb->skb).portid,
2094                                                    cb->nlh->nlmsg_seq);
2095                         if (err == -EOPNOTSUPP) {
2096                                 err = 0;
2097                         } else if (err) {
2098                                 mutex_unlock(&devlink->lock);
2099                                 devlink_put(devlink);
2100                                 goto out;
2101                         }
2102                 }
2103                 mutex_unlock(&devlink->lock);
2104 retry:
2105                 devlink_put(devlink);
2106         }
2107 out:
2108         mutex_unlock(&devlink_mutex);
2109
2110         if (err != -EMSGSIZE)
2111                 return err;
2112
2113         cb->args[0] = idx;
2114         return msg->len;
2115 }
2116
2117 static int devlink_sb_pool_set(struct devlink *devlink, unsigned int sb_index,
2118                                u16 pool_index, u32 size,
2119                                enum devlink_sb_threshold_type threshold_type,
2120                                struct netlink_ext_ack *extack)
2121
2122 {
2123         const struct devlink_ops *ops = devlink->ops;
2124
2125         if (ops->sb_pool_set)
2126                 return ops->sb_pool_set(devlink, sb_index, pool_index,
2127                                         size, threshold_type, extack);
2128         return -EOPNOTSUPP;
2129 }
2130
2131 static int devlink_nl_cmd_sb_pool_set_doit(struct sk_buff *skb,
2132                                            struct genl_info *info)
2133 {
2134         struct devlink *devlink = info->user_ptr[0];
2135         enum devlink_sb_threshold_type threshold_type;
2136         struct devlink_sb *devlink_sb;
2137         u16 pool_index;
2138         u32 size;
2139         int err;
2140
2141         devlink_sb = devlink_sb_get_from_info(devlink, info);
2142         if (IS_ERR(devlink_sb))
2143                 return PTR_ERR(devlink_sb);
2144
2145         err = devlink_sb_pool_index_get_from_info(devlink_sb, info,
2146                                                   &pool_index);
2147         if (err)
2148                 return err;
2149
2150         err = devlink_sb_th_type_get_from_info(info, &threshold_type);
2151         if (err)
2152                 return err;
2153
2154         if (!info->attrs[DEVLINK_ATTR_SB_POOL_SIZE])
2155                 return -EINVAL;
2156
2157         size = nla_get_u32(info->attrs[DEVLINK_ATTR_SB_POOL_SIZE]);
2158         return devlink_sb_pool_set(devlink, devlink_sb->index,
2159                                    pool_index, size, threshold_type,
2160                                    info->extack);
2161 }
2162
2163 static int devlink_nl_sb_port_pool_fill(struct sk_buff *msg,
2164                                         struct devlink *devlink,
2165                                         struct devlink_port *devlink_port,
2166                                         struct devlink_sb *devlink_sb,
2167                                         u16 pool_index,
2168                                         enum devlink_command cmd,
2169                                         u32 portid, u32 seq, int flags)
2170 {
2171         const struct devlink_ops *ops = devlink->ops;
2172         u32 threshold;
2173         void *hdr;
2174         int err;
2175
2176         err = ops->sb_port_pool_get(devlink_port, devlink_sb->index,
2177                                     pool_index, &threshold);
2178         if (err)
2179                 return err;
2180
2181         hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
2182         if (!hdr)
2183                 return -EMSGSIZE;
2184
2185         if (devlink_nl_put_handle(msg, devlink))
2186                 goto nla_put_failure;
2187         if (nla_put_u32(msg, DEVLINK_ATTR_PORT_INDEX, devlink_port->index))
2188                 goto nla_put_failure;
2189         if (nla_put_u32(msg, DEVLINK_ATTR_SB_INDEX, devlink_sb->index))
2190                 goto nla_put_failure;
2191         if (nla_put_u16(msg, DEVLINK_ATTR_SB_POOL_INDEX, pool_index))
2192                 goto nla_put_failure;
2193         if (nla_put_u32(msg, DEVLINK_ATTR_SB_THRESHOLD, threshold))
2194                 goto nla_put_failure;
2195
2196         if (ops->sb_occ_port_pool_get) {
2197                 u32 cur;
2198                 u32 max;
2199
2200                 err = ops->sb_occ_port_pool_get(devlink_port, devlink_sb->index,
2201                                                 pool_index, &cur, &max);
2202                 if (err && err != -EOPNOTSUPP)
2203                         goto sb_occ_get_failure;
2204                 if (!err) {
2205                         if (nla_put_u32(msg, DEVLINK_ATTR_SB_OCC_CUR, cur))
2206                                 goto nla_put_failure;
2207                         if (nla_put_u32(msg, DEVLINK_ATTR_SB_OCC_MAX, max))
2208                                 goto nla_put_failure;
2209                 }
2210         }
2211
2212         genlmsg_end(msg, hdr);
2213         return 0;
2214
2215 nla_put_failure:
2216         err = -EMSGSIZE;
2217 sb_occ_get_failure:
2218         genlmsg_cancel(msg, hdr);
2219         return err;
2220 }
2221
2222 static int devlink_nl_cmd_sb_port_pool_get_doit(struct sk_buff *skb,
2223                                                 struct genl_info *info)
2224 {
2225         struct devlink_port *devlink_port = info->user_ptr[1];
2226         struct devlink *devlink = devlink_port->devlink;
2227         struct devlink_sb *devlink_sb;
2228         struct sk_buff *msg;
2229         u16 pool_index;
2230         int err;
2231
2232         devlink_sb = devlink_sb_get_from_info(devlink, info);
2233         if (IS_ERR(devlink_sb))
2234                 return PTR_ERR(devlink_sb);
2235
2236         err = devlink_sb_pool_index_get_from_info(devlink_sb, info,
2237                                                   &pool_index);
2238         if (err)
2239                 return err;
2240
2241         if (!devlink->ops->sb_port_pool_get)
2242                 return -EOPNOTSUPP;
2243
2244         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
2245         if (!msg)
2246                 return -ENOMEM;
2247
2248         err = devlink_nl_sb_port_pool_fill(msg, devlink, devlink_port,
2249                                            devlink_sb, pool_index,
2250                                            DEVLINK_CMD_SB_PORT_POOL_NEW,
2251                                            info->snd_portid, info->snd_seq, 0);
2252         if (err) {
2253                 nlmsg_free(msg);
2254                 return err;
2255         }
2256
2257         return genlmsg_reply(msg, info);
2258 }
2259
2260 static int __sb_port_pool_get_dumpit(struct sk_buff *msg, int start, int *p_idx,
2261                                      struct devlink *devlink,
2262                                      struct devlink_sb *devlink_sb,
2263                                      u32 portid, u32 seq)
2264 {
2265         struct devlink_port *devlink_port;
2266         u16 pool_count = devlink_sb_pool_count(devlink_sb);
2267         u16 pool_index;
2268         int err;
2269
2270         list_for_each_entry(devlink_port, &devlink->port_list, list) {
2271                 for (pool_index = 0; pool_index < pool_count; pool_index++) {
2272                         if (*p_idx < start) {
2273                                 (*p_idx)++;
2274                                 continue;
2275                         }
2276                         err = devlink_nl_sb_port_pool_fill(msg, devlink,
2277                                                            devlink_port,
2278                                                            devlink_sb,
2279                                                            pool_index,
2280                                                            DEVLINK_CMD_SB_PORT_POOL_NEW,
2281                                                            portid, seq,
2282                                                            NLM_F_MULTI);
2283                         if (err)
2284                                 return err;
2285                         (*p_idx)++;
2286                 }
2287         }
2288         return 0;
2289 }
2290
2291 static int devlink_nl_cmd_sb_port_pool_get_dumpit(struct sk_buff *msg,
2292                                                   struct netlink_callback *cb)
2293 {
2294         struct devlink *devlink;
2295         struct devlink_sb *devlink_sb;
2296         int start = cb->args[0];
2297         unsigned long index;
2298         int idx = 0;
2299         int err = 0;
2300
2301         mutex_lock(&devlink_mutex);
2302         xa_for_each_marked(&devlinks, index, devlink, DEVLINK_REGISTERED) {
2303                 if (!devlink_try_get(devlink))
2304                         continue;
2305
2306                 if (!net_eq(devlink_net(devlink), sock_net(msg->sk)) ||
2307                     !devlink->ops->sb_port_pool_get)
2308                         goto retry;
2309
2310                 mutex_lock(&devlink->lock);
2311                 list_for_each_entry(devlink_sb, &devlink->sb_list, list) {
2312                         err = __sb_port_pool_get_dumpit(msg, start, &idx,
2313                                                         devlink, devlink_sb,
2314                                                         NETLINK_CB(cb->skb).portid,
2315                                                         cb->nlh->nlmsg_seq);
2316                         if (err == -EOPNOTSUPP) {
2317                                 err = 0;
2318                         } else if (err) {
2319                                 mutex_unlock(&devlink->lock);
2320                                 devlink_put(devlink);
2321                                 goto out;
2322                         }
2323                 }
2324                 mutex_unlock(&devlink->lock);
2325 retry:
2326                 devlink_put(devlink);
2327         }
2328 out:
2329         mutex_unlock(&devlink_mutex);
2330
2331         if (err != -EMSGSIZE)
2332                 return err;
2333
2334         cb->args[0] = idx;
2335         return msg->len;
2336 }
2337
2338 static int devlink_sb_port_pool_set(struct devlink_port *devlink_port,
2339                                     unsigned int sb_index, u16 pool_index,
2340                                     u32 threshold,
2341                                     struct netlink_ext_ack *extack)
2342
2343 {
2344         const struct devlink_ops *ops = devlink_port->devlink->ops;
2345
2346         if (ops->sb_port_pool_set)
2347                 return ops->sb_port_pool_set(devlink_port, sb_index,
2348                                              pool_index, threshold, extack);
2349         return -EOPNOTSUPP;
2350 }
2351
2352 static int devlink_nl_cmd_sb_port_pool_set_doit(struct sk_buff *skb,
2353                                                 struct genl_info *info)
2354 {
2355         struct devlink_port *devlink_port = info->user_ptr[1];
2356         struct devlink *devlink = info->user_ptr[0];
2357         struct devlink_sb *devlink_sb;
2358         u16 pool_index;
2359         u32 threshold;
2360         int err;
2361
2362         devlink_sb = devlink_sb_get_from_info(devlink, info);
2363         if (IS_ERR(devlink_sb))
2364                 return PTR_ERR(devlink_sb);
2365
2366         err = devlink_sb_pool_index_get_from_info(devlink_sb, info,
2367                                                   &pool_index);
2368         if (err)
2369                 return err;
2370
2371         if (!info->attrs[DEVLINK_ATTR_SB_THRESHOLD])
2372                 return -EINVAL;
2373
2374         threshold = nla_get_u32(info->attrs[DEVLINK_ATTR_SB_THRESHOLD]);
2375         return devlink_sb_port_pool_set(devlink_port, devlink_sb->index,
2376                                         pool_index, threshold, info->extack);
2377 }
2378
2379 static int
2380 devlink_nl_sb_tc_pool_bind_fill(struct sk_buff *msg, struct devlink *devlink,
2381                                 struct devlink_port *devlink_port,
2382                                 struct devlink_sb *devlink_sb, u16 tc_index,
2383                                 enum devlink_sb_pool_type pool_type,
2384                                 enum devlink_command cmd,
2385                                 u32 portid, u32 seq, int flags)
2386 {
2387         const struct devlink_ops *ops = devlink->ops;
2388         u16 pool_index;
2389         u32 threshold;
2390         void *hdr;
2391         int err;
2392
2393         err = ops->sb_tc_pool_bind_get(devlink_port, devlink_sb->index,
2394                                        tc_index, pool_type,
2395                                        &pool_index, &threshold);
2396         if (err)
2397                 return err;
2398
2399         hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
2400         if (!hdr)
2401                 return -EMSGSIZE;
2402
2403         if (devlink_nl_put_handle(msg, devlink))
2404                 goto nla_put_failure;
2405         if (nla_put_u32(msg, DEVLINK_ATTR_PORT_INDEX, devlink_port->index))
2406                 goto nla_put_failure;
2407         if (nla_put_u32(msg, DEVLINK_ATTR_SB_INDEX, devlink_sb->index))
2408                 goto nla_put_failure;
2409         if (nla_put_u16(msg, DEVLINK_ATTR_SB_TC_INDEX, tc_index))
2410                 goto nla_put_failure;
2411         if (nla_put_u8(msg, DEVLINK_ATTR_SB_POOL_TYPE, pool_type))
2412                 goto nla_put_failure;
2413         if (nla_put_u16(msg, DEVLINK_ATTR_SB_POOL_INDEX, pool_index))
2414                 goto nla_put_failure;
2415         if (nla_put_u32(msg, DEVLINK_ATTR_SB_THRESHOLD, threshold))
2416                 goto nla_put_failure;
2417
2418         if (ops->sb_occ_tc_port_bind_get) {
2419                 u32 cur;
2420                 u32 max;
2421
2422                 err = ops->sb_occ_tc_port_bind_get(devlink_port,
2423                                                    devlink_sb->index,
2424                                                    tc_index, pool_type,
2425                                                    &cur, &max);
2426                 if (err && err != -EOPNOTSUPP)
2427                         return err;
2428                 if (!err) {
2429                         if (nla_put_u32(msg, DEVLINK_ATTR_SB_OCC_CUR, cur))
2430                                 goto nla_put_failure;
2431                         if (nla_put_u32(msg, DEVLINK_ATTR_SB_OCC_MAX, max))
2432                                 goto nla_put_failure;
2433                 }
2434         }
2435
2436         genlmsg_end(msg, hdr);
2437         return 0;
2438
2439 nla_put_failure:
2440         genlmsg_cancel(msg, hdr);
2441         return -EMSGSIZE;
2442 }
2443
2444 static int devlink_nl_cmd_sb_tc_pool_bind_get_doit(struct sk_buff *skb,
2445                                                    struct genl_info *info)
2446 {
2447         struct devlink_port *devlink_port = info->user_ptr[1];
2448         struct devlink *devlink = devlink_port->devlink;
2449         struct devlink_sb *devlink_sb;
2450         struct sk_buff *msg;
2451         enum devlink_sb_pool_type pool_type;
2452         u16 tc_index;
2453         int err;
2454
2455         devlink_sb = devlink_sb_get_from_info(devlink, info);
2456         if (IS_ERR(devlink_sb))
2457                 return PTR_ERR(devlink_sb);
2458
2459         err = devlink_sb_pool_type_get_from_info(info, &pool_type);
2460         if (err)
2461                 return err;
2462
2463         err = devlink_sb_tc_index_get_from_info(devlink_sb, info,
2464                                                 pool_type, &tc_index);
2465         if (err)
2466                 return err;
2467
2468         if (!devlink->ops->sb_tc_pool_bind_get)
2469                 return -EOPNOTSUPP;
2470
2471         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
2472         if (!msg)
2473                 return -ENOMEM;
2474
2475         err = devlink_nl_sb_tc_pool_bind_fill(msg, devlink, devlink_port,
2476                                               devlink_sb, tc_index, pool_type,
2477                                               DEVLINK_CMD_SB_TC_POOL_BIND_NEW,
2478                                               info->snd_portid,
2479                                               info->snd_seq, 0);
2480         if (err) {
2481                 nlmsg_free(msg);
2482                 return err;
2483         }
2484
2485         return genlmsg_reply(msg, info);
2486 }
2487
2488 static int __sb_tc_pool_bind_get_dumpit(struct sk_buff *msg,
2489                                         int start, int *p_idx,
2490                                         struct devlink *devlink,
2491                                         struct devlink_sb *devlink_sb,
2492                                         u32 portid, u32 seq)
2493 {
2494         struct devlink_port *devlink_port;
2495         u16 tc_index;
2496         int err;
2497
2498         list_for_each_entry(devlink_port, &devlink->port_list, list) {
2499                 for (tc_index = 0;
2500                      tc_index < devlink_sb->ingress_tc_count; tc_index++) {
2501                         if (*p_idx < start) {
2502                                 (*p_idx)++;
2503                                 continue;
2504                         }
2505                         err = devlink_nl_sb_tc_pool_bind_fill(msg, devlink,
2506                                                               devlink_port,
2507                                                               devlink_sb,
2508                                                               tc_index,
2509                                                               DEVLINK_SB_POOL_TYPE_INGRESS,
2510                                                               DEVLINK_CMD_SB_TC_POOL_BIND_NEW,
2511                                                               portid, seq,
2512                                                               NLM_F_MULTI);
2513                         if (err)
2514                                 return err;
2515                         (*p_idx)++;
2516                 }
2517                 for (tc_index = 0;
2518                      tc_index < devlink_sb->egress_tc_count; tc_index++) {
2519                         if (*p_idx < start) {
2520                                 (*p_idx)++;
2521                                 continue;
2522                         }
2523                         err = devlink_nl_sb_tc_pool_bind_fill(msg, devlink,
2524                                                               devlink_port,
2525                                                               devlink_sb,
2526                                                               tc_index,
2527                                                               DEVLINK_SB_POOL_TYPE_EGRESS,
2528                                                               DEVLINK_CMD_SB_TC_POOL_BIND_NEW,
2529                                                               portid, seq,
2530                                                               NLM_F_MULTI);
2531                         if (err)
2532                                 return err;
2533                         (*p_idx)++;
2534                 }
2535         }
2536         return 0;
2537 }
2538
2539 static int
2540 devlink_nl_cmd_sb_tc_pool_bind_get_dumpit(struct sk_buff *msg,
2541                                           struct netlink_callback *cb)
2542 {
2543         struct devlink *devlink;
2544         struct devlink_sb *devlink_sb;
2545         int start = cb->args[0];
2546         unsigned long index;
2547         int idx = 0;
2548         int err = 0;
2549
2550         mutex_lock(&devlink_mutex);
2551         xa_for_each_marked(&devlinks, index, devlink, DEVLINK_REGISTERED) {
2552                 if (!devlink_try_get(devlink))
2553                         continue;
2554
2555                 if (!net_eq(devlink_net(devlink), sock_net(msg->sk)) ||
2556                     !devlink->ops->sb_tc_pool_bind_get)
2557                         goto retry;
2558
2559                 mutex_lock(&devlink->lock);
2560                 list_for_each_entry(devlink_sb, &devlink->sb_list, list) {
2561                         err = __sb_tc_pool_bind_get_dumpit(msg, start, &idx,
2562                                                            devlink,
2563                                                            devlink_sb,
2564                                                            NETLINK_CB(cb->skb).portid,
2565                                                            cb->nlh->nlmsg_seq);
2566                         if (err == -EOPNOTSUPP) {
2567                                 err = 0;
2568                         } else if (err) {
2569                                 mutex_unlock(&devlink->lock);
2570                                 devlink_put(devlink);
2571                                 goto out;
2572                         }
2573                 }
2574                 mutex_unlock(&devlink->lock);
2575 retry:
2576                 devlink_put(devlink);
2577         }
2578 out:
2579         mutex_unlock(&devlink_mutex);
2580
2581         if (err != -EMSGSIZE)
2582                 return err;
2583
2584         cb->args[0] = idx;
2585         return msg->len;
2586 }
2587
2588 static int devlink_sb_tc_pool_bind_set(struct devlink_port *devlink_port,
2589                                        unsigned int sb_index, u16 tc_index,
2590                                        enum devlink_sb_pool_type pool_type,
2591                                        u16 pool_index, u32 threshold,
2592                                        struct netlink_ext_ack *extack)
2593
2594 {
2595         const struct devlink_ops *ops = devlink_port->devlink->ops;
2596
2597         if (ops->sb_tc_pool_bind_set)
2598                 return ops->sb_tc_pool_bind_set(devlink_port, sb_index,
2599                                                 tc_index, pool_type,
2600                                                 pool_index, threshold, extack);
2601         return -EOPNOTSUPP;
2602 }
2603
2604 static int devlink_nl_cmd_sb_tc_pool_bind_set_doit(struct sk_buff *skb,
2605                                                    struct genl_info *info)
2606 {
2607         struct devlink_port *devlink_port = info->user_ptr[1];
2608         struct devlink *devlink = info->user_ptr[0];
2609         enum devlink_sb_pool_type pool_type;
2610         struct devlink_sb *devlink_sb;
2611         u16 tc_index;
2612         u16 pool_index;
2613         u32 threshold;
2614         int err;
2615
2616         devlink_sb = devlink_sb_get_from_info(devlink, info);
2617         if (IS_ERR(devlink_sb))
2618                 return PTR_ERR(devlink_sb);
2619
2620         err = devlink_sb_pool_type_get_from_info(info, &pool_type);
2621         if (err)
2622                 return err;
2623
2624         err = devlink_sb_tc_index_get_from_info(devlink_sb, info,
2625                                                 pool_type, &tc_index);
2626         if (err)
2627                 return err;
2628
2629         err = devlink_sb_pool_index_get_from_info(devlink_sb, info,
2630                                                   &pool_index);
2631         if (err)
2632                 return err;
2633
2634         if (!info->attrs[DEVLINK_ATTR_SB_THRESHOLD])
2635                 return -EINVAL;
2636
2637         threshold = nla_get_u32(info->attrs[DEVLINK_ATTR_SB_THRESHOLD]);
2638         return devlink_sb_tc_pool_bind_set(devlink_port, devlink_sb->index,
2639                                            tc_index, pool_type,
2640                                            pool_index, threshold, info->extack);
2641 }
2642
2643 static int devlink_nl_cmd_sb_occ_snapshot_doit(struct sk_buff *skb,
2644                                                struct genl_info *info)
2645 {
2646         struct devlink *devlink = info->user_ptr[0];
2647         const struct devlink_ops *ops = devlink->ops;
2648         struct devlink_sb *devlink_sb;
2649
2650         devlink_sb = devlink_sb_get_from_info(devlink, info);
2651         if (IS_ERR(devlink_sb))
2652                 return PTR_ERR(devlink_sb);
2653
2654         if (ops->sb_occ_snapshot)
2655                 return ops->sb_occ_snapshot(devlink, devlink_sb->index);
2656         return -EOPNOTSUPP;
2657 }
2658
2659 static int devlink_nl_cmd_sb_occ_max_clear_doit(struct sk_buff *skb,
2660                                                 struct genl_info *info)
2661 {
2662         struct devlink *devlink = info->user_ptr[0];
2663         const struct devlink_ops *ops = devlink->ops;
2664         struct devlink_sb *devlink_sb;
2665
2666         devlink_sb = devlink_sb_get_from_info(devlink, info);
2667         if (IS_ERR(devlink_sb))
2668                 return PTR_ERR(devlink_sb);
2669
2670         if (ops->sb_occ_max_clear)
2671                 return ops->sb_occ_max_clear(devlink, devlink_sb->index);
2672         return -EOPNOTSUPP;
2673 }
2674
2675 static int devlink_nl_eswitch_fill(struct sk_buff *msg, struct devlink *devlink,
2676                                    enum devlink_command cmd, u32 portid,
2677                                    u32 seq, int flags)
2678 {
2679         const struct devlink_ops *ops = devlink->ops;
2680         enum devlink_eswitch_encap_mode encap_mode;
2681         u8 inline_mode;
2682         void *hdr;
2683         int err = 0;
2684         u16 mode;
2685
2686         hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
2687         if (!hdr)
2688                 return -EMSGSIZE;
2689
2690         err = devlink_nl_put_handle(msg, devlink);
2691         if (err)
2692                 goto nla_put_failure;
2693
2694         if (ops->eswitch_mode_get) {
2695                 err = ops->eswitch_mode_get(devlink, &mode);
2696                 if (err)
2697                         goto nla_put_failure;
2698                 err = nla_put_u16(msg, DEVLINK_ATTR_ESWITCH_MODE, mode);
2699                 if (err)
2700                         goto nla_put_failure;
2701         }
2702
2703         if (ops->eswitch_inline_mode_get) {
2704                 err = ops->eswitch_inline_mode_get(devlink, &inline_mode);
2705                 if (err)
2706                         goto nla_put_failure;
2707                 err = nla_put_u8(msg, DEVLINK_ATTR_ESWITCH_INLINE_MODE,
2708                                  inline_mode);
2709                 if (err)
2710                         goto nla_put_failure;
2711         }
2712
2713         if (ops->eswitch_encap_mode_get) {
2714                 err = ops->eswitch_encap_mode_get(devlink, &encap_mode);
2715                 if (err)
2716                         goto nla_put_failure;
2717                 err = nla_put_u8(msg, DEVLINK_ATTR_ESWITCH_ENCAP_MODE, encap_mode);
2718                 if (err)
2719                         goto nla_put_failure;
2720         }
2721
2722         genlmsg_end(msg, hdr);
2723         return 0;
2724
2725 nla_put_failure:
2726         genlmsg_cancel(msg, hdr);
2727         return err;
2728 }
2729
2730 static int devlink_nl_cmd_eswitch_get_doit(struct sk_buff *skb,
2731                                            struct genl_info *info)
2732 {
2733         struct devlink *devlink = info->user_ptr[0];
2734         struct sk_buff *msg;
2735         int err;
2736
2737         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
2738         if (!msg)
2739                 return -ENOMEM;
2740
2741         err = devlink_nl_eswitch_fill(msg, devlink, DEVLINK_CMD_ESWITCH_GET,
2742                                       info->snd_portid, info->snd_seq, 0);
2743
2744         if (err) {
2745                 nlmsg_free(msg);
2746                 return err;
2747         }
2748
2749         return genlmsg_reply(msg, info);
2750 }
2751
2752 static int devlink_rate_nodes_check(struct devlink *devlink, u16 mode,
2753                                     struct netlink_ext_ack *extack)
2754 {
2755         struct devlink_rate *devlink_rate;
2756
2757         /* Take the lock to sync with devlink_rate_nodes_destroy() */
2758         mutex_lock(&devlink->lock);
2759         list_for_each_entry(devlink_rate, &devlink->rate_list, list)
2760                 if (devlink_rate_is_node(devlink_rate)) {
2761                         mutex_unlock(&devlink->lock);
2762                         NL_SET_ERR_MSG_MOD(extack, "Rate node(s) exists.");
2763                         return -EBUSY;
2764                 }
2765         mutex_unlock(&devlink->lock);
2766         return 0;
2767 }
2768
2769 static int devlink_nl_cmd_eswitch_set_doit(struct sk_buff *skb,
2770                                            struct genl_info *info)
2771 {
2772         struct devlink *devlink = info->user_ptr[0];
2773         const struct devlink_ops *ops = devlink->ops;
2774         enum devlink_eswitch_encap_mode encap_mode;
2775         u8 inline_mode;
2776         int err = 0;
2777         u16 mode;
2778
2779         if (info->attrs[DEVLINK_ATTR_ESWITCH_MODE]) {
2780                 if (!ops->eswitch_mode_set)
2781                         return -EOPNOTSUPP;
2782                 mode = nla_get_u16(info->attrs[DEVLINK_ATTR_ESWITCH_MODE]);
2783                 err = devlink_rate_nodes_check(devlink, mode, info->extack);
2784                 if (err)
2785                         return err;
2786                 err = ops->eswitch_mode_set(devlink, mode, info->extack);
2787                 if (err)
2788                         return err;
2789         }
2790
2791         if (info->attrs[DEVLINK_ATTR_ESWITCH_INLINE_MODE]) {
2792                 if (!ops->eswitch_inline_mode_set)
2793                         return -EOPNOTSUPP;
2794                 inline_mode = nla_get_u8(
2795                                 info->attrs[DEVLINK_ATTR_ESWITCH_INLINE_MODE]);
2796                 err = ops->eswitch_inline_mode_set(devlink, inline_mode,
2797                                                    info->extack);
2798                 if (err)
2799                         return err;
2800         }
2801
2802         if (info->attrs[DEVLINK_ATTR_ESWITCH_ENCAP_MODE]) {
2803                 if (!ops->eswitch_encap_mode_set)
2804                         return -EOPNOTSUPP;
2805                 encap_mode = nla_get_u8(info->attrs[DEVLINK_ATTR_ESWITCH_ENCAP_MODE]);
2806                 err = ops->eswitch_encap_mode_set(devlink, encap_mode,
2807                                                   info->extack);
2808                 if (err)
2809                         return err;
2810         }
2811
2812         return 0;
2813 }
2814
2815 int devlink_dpipe_match_put(struct sk_buff *skb,
2816                             struct devlink_dpipe_match *match)
2817 {
2818         struct devlink_dpipe_header *header = match->header;
2819         struct devlink_dpipe_field *field = &header->fields[match->field_id];
2820         struct nlattr *match_attr;
2821
2822         match_attr = nla_nest_start_noflag(skb, DEVLINK_ATTR_DPIPE_MATCH);
2823         if (!match_attr)
2824                 return -EMSGSIZE;
2825
2826         if (nla_put_u32(skb, DEVLINK_ATTR_DPIPE_MATCH_TYPE, match->type) ||
2827             nla_put_u32(skb, DEVLINK_ATTR_DPIPE_HEADER_INDEX, match->header_index) ||
2828             nla_put_u32(skb, DEVLINK_ATTR_DPIPE_HEADER_ID, header->id) ||
2829             nla_put_u32(skb, DEVLINK_ATTR_DPIPE_FIELD_ID, field->id) ||
2830             nla_put_u8(skb, DEVLINK_ATTR_DPIPE_HEADER_GLOBAL, header->global))
2831                 goto nla_put_failure;
2832
2833         nla_nest_end(skb, match_attr);
2834         return 0;
2835
2836 nla_put_failure:
2837         nla_nest_cancel(skb, match_attr);
2838         return -EMSGSIZE;
2839 }
2840 EXPORT_SYMBOL_GPL(devlink_dpipe_match_put);
2841
2842 static int devlink_dpipe_matches_put(struct devlink_dpipe_table *table,
2843                                      struct sk_buff *skb)
2844 {
2845         struct nlattr *matches_attr;
2846
2847         matches_attr = nla_nest_start_noflag(skb,
2848                                              DEVLINK_ATTR_DPIPE_TABLE_MATCHES);
2849         if (!matches_attr)
2850                 return -EMSGSIZE;
2851
2852         if (table->table_ops->matches_dump(table->priv, skb))
2853                 goto nla_put_failure;
2854
2855         nla_nest_end(skb, matches_attr);
2856         return 0;
2857
2858 nla_put_failure:
2859         nla_nest_cancel(skb, matches_attr);
2860         return -EMSGSIZE;
2861 }
2862
2863 int devlink_dpipe_action_put(struct sk_buff *skb,
2864                              struct devlink_dpipe_action *action)
2865 {
2866         struct devlink_dpipe_header *header = action->header;
2867         struct devlink_dpipe_field *field = &header->fields[action->field_id];
2868         struct nlattr *action_attr;
2869
2870         action_attr = nla_nest_start_noflag(skb, DEVLINK_ATTR_DPIPE_ACTION);
2871         if (!action_attr)
2872                 return -EMSGSIZE;
2873
2874         if (nla_put_u32(skb, DEVLINK_ATTR_DPIPE_ACTION_TYPE, action->type) ||
2875             nla_put_u32(skb, DEVLINK_ATTR_DPIPE_HEADER_INDEX, action->header_index) ||
2876             nla_put_u32(skb, DEVLINK_ATTR_DPIPE_HEADER_ID, header->id) ||
2877             nla_put_u32(skb, DEVLINK_ATTR_DPIPE_FIELD_ID, field->id) ||
2878             nla_put_u8(skb, DEVLINK_ATTR_DPIPE_HEADER_GLOBAL, header->global))
2879                 goto nla_put_failure;
2880
2881         nla_nest_end(skb, action_attr);
2882         return 0;
2883
2884 nla_put_failure:
2885         nla_nest_cancel(skb, action_attr);
2886         return -EMSGSIZE;
2887 }
2888 EXPORT_SYMBOL_GPL(devlink_dpipe_action_put);
2889
2890 static int devlink_dpipe_actions_put(struct devlink_dpipe_table *table,
2891                                      struct sk_buff *skb)
2892 {
2893         struct nlattr *actions_attr;
2894
2895         actions_attr = nla_nest_start_noflag(skb,
2896                                              DEVLINK_ATTR_DPIPE_TABLE_ACTIONS);
2897         if (!actions_attr)
2898                 return -EMSGSIZE;
2899
2900         if (table->table_ops->actions_dump(table->priv, skb))
2901                 goto nla_put_failure;
2902
2903         nla_nest_end(skb, actions_attr);
2904         return 0;
2905
2906 nla_put_failure:
2907         nla_nest_cancel(skb, actions_attr);
2908         return -EMSGSIZE;
2909 }
2910
2911 static int devlink_dpipe_table_put(struct sk_buff *skb,
2912                                    struct devlink_dpipe_table *table)
2913 {
2914         struct nlattr *table_attr;
2915         u64 table_size;
2916
2917         table_size = table->table_ops->size_get(table->priv);
2918         table_attr = nla_nest_start_noflag(skb, DEVLINK_ATTR_DPIPE_TABLE);
2919         if (!table_attr)
2920                 return -EMSGSIZE;
2921
2922         if (nla_put_string(skb, DEVLINK_ATTR_DPIPE_TABLE_NAME, table->name) ||
2923             nla_put_u64_64bit(skb, DEVLINK_ATTR_DPIPE_TABLE_SIZE, table_size,
2924                               DEVLINK_ATTR_PAD))
2925                 goto nla_put_failure;
2926         if (nla_put_u8(skb, DEVLINK_ATTR_DPIPE_TABLE_COUNTERS_ENABLED,
2927                        table->counters_enabled))
2928                 goto nla_put_failure;
2929
2930         if (table->resource_valid) {
2931                 if (nla_put_u64_64bit(skb, DEVLINK_ATTR_DPIPE_TABLE_RESOURCE_ID,
2932                                       table->resource_id, DEVLINK_ATTR_PAD) ||
2933                     nla_put_u64_64bit(skb, DEVLINK_ATTR_DPIPE_TABLE_RESOURCE_UNITS,
2934                                       table->resource_units, DEVLINK_ATTR_PAD))
2935                         goto nla_put_failure;
2936         }
2937         if (devlink_dpipe_matches_put(table, skb))
2938                 goto nla_put_failure;
2939
2940         if (devlink_dpipe_actions_put(table, skb))
2941                 goto nla_put_failure;
2942
2943         nla_nest_end(skb, table_attr);
2944         return 0;
2945
2946 nla_put_failure:
2947         nla_nest_cancel(skb, table_attr);
2948         return -EMSGSIZE;
2949 }
2950
2951 static int devlink_dpipe_send_and_alloc_skb(struct sk_buff **pskb,
2952                                             struct genl_info *info)
2953 {
2954         int err;
2955
2956         if (*pskb) {
2957                 err = genlmsg_reply(*pskb, info);
2958                 if (err)
2959                         return err;
2960         }
2961         *pskb = genlmsg_new(GENLMSG_DEFAULT_SIZE, GFP_KERNEL);
2962         if (!*pskb)
2963                 return -ENOMEM;
2964         return 0;
2965 }
2966
2967 static int devlink_dpipe_tables_fill(struct genl_info *info,
2968                                      enum devlink_command cmd, int flags,
2969                                      struct list_head *dpipe_tables,
2970                                      const char *table_name)
2971 {
2972         struct devlink *devlink = info->user_ptr[0];
2973         struct devlink_dpipe_table *table;
2974         struct nlattr *tables_attr;
2975         struct sk_buff *skb = NULL;
2976         struct nlmsghdr *nlh;
2977         bool incomplete;
2978         void *hdr;
2979         int i;
2980         int err;
2981
2982         table = list_first_entry(dpipe_tables,
2983                                  struct devlink_dpipe_table, list);
2984 start_again:
2985         err = devlink_dpipe_send_and_alloc_skb(&skb, info);
2986         if (err)
2987                 return err;
2988
2989         hdr = genlmsg_put(skb, info->snd_portid, info->snd_seq,
2990                           &devlink_nl_family, NLM_F_MULTI, cmd);
2991         if (!hdr) {
2992                 nlmsg_free(skb);
2993                 return -EMSGSIZE;
2994         }
2995
2996         if (devlink_nl_put_handle(skb, devlink))
2997                 goto nla_put_failure;
2998         tables_attr = nla_nest_start_noflag(skb, DEVLINK_ATTR_DPIPE_TABLES);
2999         if (!tables_attr)
3000                 goto nla_put_failure;
3001
3002         i = 0;
3003         incomplete = false;
3004         list_for_each_entry_from(table, dpipe_tables, list) {
3005                 if (!table_name) {
3006                         err = devlink_dpipe_table_put(skb, table);
3007                         if (err) {
3008                                 if (!i)
3009                                         goto err_table_put;
3010                                 incomplete = true;
3011                                 break;
3012                         }
3013                 } else {
3014                         if (!strcmp(table->name, table_name)) {
3015                                 err = devlink_dpipe_table_put(skb, table);
3016                                 if (err)
3017                                         break;
3018                         }
3019                 }
3020                 i++;
3021         }
3022
3023         nla_nest_end(skb, tables_attr);
3024         genlmsg_end(skb, hdr);
3025         if (incomplete)
3026                 goto start_again;
3027
3028 send_done:
3029         nlh = nlmsg_put(skb, info->snd_portid, info->snd_seq,
3030                         NLMSG_DONE, 0, flags | NLM_F_MULTI);
3031         if (!nlh) {
3032                 err = devlink_dpipe_send_and_alloc_skb(&skb, info);
3033                 if (err)
3034                         return err;
3035                 goto send_done;
3036         }
3037
3038         return genlmsg_reply(skb, info);
3039
3040 nla_put_failure:
3041         err = -EMSGSIZE;
3042 err_table_put:
3043         nlmsg_free(skb);
3044         return err;
3045 }
3046
3047 static int devlink_nl_cmd_dpipe_table_get(struct sk_buff *skb,
3048                                           struct genl_info *info)
3049 {
3050         struct devlink *devlink = info->user_ptr[0];
3051         const char *table_name =  NULL;
3052
3053         if (info->attrs[DEVLINK_ATTR_DPIPE_TABLE_NAME])
3054                 table_name = nla_data(info->attrs[DEVLINK_ATTR_DPIPE_TABLE_NAME]);
3055
3056         return devlink_dpipe_tables_fill(info, DEVLINK_CMD_DPIPE_TABLE_GET, 0,
3057                                          &devlink->dpipe_table_list,
3058                                          table_name);
3059 }
3060
3061 static int devlink_dpipe_value_put(struct sk_buff *skb,
3062                                    struct devlink_dpipe_value *value)
3063 {
3064         if (nla_put(skb, DEVLINK_ATTR_DPIPE_VALUE,
3065                     value->value_size, value->value))
3066                 return -EMSGSIZE;
3067         if (value->mask)
3068                 if (nla_put(skb, DEVLINK_ATTR_DPIPE_VALUE_MASK,
3069                             value->value_size, value->mask))
3070                         return -EMSGSIZE;
3071         if (value->mapping_valid)
3072                 if (nla_put_u32(skb, DEVLINK_ATTR_DPIPE_VALUE_MAPPING,
3073                                 value->mapping_value))
3074                         return -EMSGSIZE;
3075         return 0;
3076 }
3077
3078 static int devlink_dpipe_action_value_put(struct sk_buff *skb,
3079                                           struct devlink_dpipe_value *value)
3080 {
3081         if (!value->action)
3082                 return -EINVAL;
3083         if (devlink_dpipe_action_put(skb, value->action))
3084                 return -EMSGSIZE;
3085         if (devlink_dpipe_value_put(skb, value))
3086                 return -EMSGSIZE;
3087         return 0;
3088 }
3089
3090 static int devlink_dpipe_action_values_put(struct sk_buff *skb,
3091                                            struct devlink_dpipe_value *values,
3092                                            unsigned int values_count)
3093 {
3094         struct nlattr *action_attr;
3095         int i;
3096         int err;
3097
3098         for (i = 0; i < values_count; i++) {
3099                 action_attr = nla_nest_start_noflag(skb,
3100                                                     DEVLINK_ATTR_DPIPE_ACTION_VALUE);
3101                 if (!action_attr)
3102                         return -EMSGSIZE;
3103                 err = devlink_dpipe_action_value_put(skb, &values[i]);
3104                 if (err)
3105                         goto err_action_value_put;
3106                 nla_nest_end(skb, action_attr);
3107         }
3108         return 0;
3109
3110 err_action_value_put:
3111         nla_nest_cancel(skb, action_attr);
3112         return err;
3113 }
3114
3115 static int devlink_dpipe_match_value_put(struct sk_buff *skb,
3116                                          struct devlink_dpipe_value *value)
3117 {
3118         if (!value->match)
3119                 return -EINVAL;
3120         if (devlink_dpipe_match_put(skb, value->match))
3121                 return -EMSGSIZE;
3122         if (devlink_dpipe_value_put(skb, value))
3123                 return -EMSGSIZE;
3124         return 0;
3125 }
3126
3127 static int devlink_dpipe_match_values_put(struct sk_buff *skb,
3128                                           struct devlink_dpipe_value *values,
3129                                           unsigned int values_count)
3130 {
3131         struct nlattr *match_attr;
3132         int i;
3133         int err;
3134
3135         for (i = 0; i < values_count; i++) {
3136                 match_attr = nla_nest_start_noflag(skb,
3137                                                    DEVLINK_ATTR_DPIPE_MATCH_VALUE);
3138                 if (!match_attr)
3139                         return -EMSGSIZE;
3140                 err = devlink_dpipe_match_value_put(skb, &values[i]);
3141                 if (err)
3142                         goto err_match_value_put;
3143                 nla_nest_end(skb, match_attr);
3144         }
3145         return 0;
3146
3147 err_match_value_put:
3148         nla_nest_cancel(skb, match_attr);
3149         return err;
3150 }
3151
3152 static int devlink_dpipe_entry_put(struct sk_buff *skb,
3153                                    struct devlink_dpipe_entry *entry)
3154 {
3155         struct nlattr *entry_attr, *matches_attr, *actions_attr;
3156         int err;
3157
3158         entry_attr = nla_nest_start_noflag(skb, DEVLINK_ATTR_DPIPE_ENTRY);
3159         if (!entry_attr)
3160                 return  -EMSGSIZE;
3161
3162         if (nla_put_u64_64bit(skb, DEVLINK_ATTR_DPIPE_ENTRY_INDEX, entry->index,
3163                               DEVLINK_ATTR_PAD))
3164                 goto nla_put_failure;
3165         if (entry->counter_valid)
3166                 if (nla_put_u64_64bit(skb, DEVLINK_ATTR_DPIPE_ENTRY_COUNTER,
3167                                       entry->counter, DEVLINK_ATTR_PAD))
3168                         goto nla_put_failure;
3169
3170         matches_attr = nla_nest_start_noflag(skb,
3171                                              DEVLINK_ATTR_DPIPE_ENTRY_MATCH_VALUES);
3172         if (!matches_attr)
3173                 goto nla_put_failure;
3174
3175         err = devlink_dpipe_match_values_put(skb, entry->match_values,
3176                                              entry->match_values_count);
3177         if (err) {
3178                 nla_nest_cancel(skb, matches_attr);
3179                 goto err_match_values_put;
3180         }
3181         nla_nest_end(skb, matches_attr);
3182
3183         actions_attr = nla_nest_start_noflag(skb,
3184                                              DEVLINK_ATTR_DPIPE_ENTRY_ACTION_VALUES);
3185         if (!actions_attr)
3186                 goto nla_put_failure;
3187
3188         err = devlink_dpipe_action_values_put(skb, entry->action_values,
3189                                               entry->action_values_count);
3190         if (err) {
3191                 nla_nest_cancel(skb, actions_attr);
3192                 goto err_action_values_put;
3193         }
3194         nla_nest_end(skb, actions_attr);
3195
3196         nla_nest_end(skb, entry_attr);
3197         return 0;
3198
3199 nla_put_failure:
3200         err = -EMSGSIZE;
3201 err_match_values_put:
3202 err_action_values_put:
3203         nla_nest_cancel(skb, entry_attr);
3204         return err;
3205 }
3206
3207 static struct devlink_dpipe_table *
3208 devlink_dpipe_table_find(struct list_head *dpipe_tables,
3209                          const char *table_name, struct devlink *devlink)
3210 {
3211         struct devlink_dpipe_table *table;
3212         list_for_each_entry_rcu(table, dpipe_tables, list,
3213                                 lockdep_is_held(&devlink->lock)) {
3214                 if (!strcmp(table->name, table_name))
3215                         return table;
3216         }
3217         return NULL;
3218 }
3219
3220 int devlink_dpipe_entry_ctx_prepare(struct devlink_dpipe_dump_ctx *dump_ctx)
3221 {
3222         struct devlink *devlink;
3223         int err;
3224
3225         err = devlink_dpipe_send_and_alloc_skb(&dump_ctx->skb,
3226                                                dump_ctx->info);
3227         if (err)
3228                 return err;
3229
3230         dump_ctx->hdr = genlmsg_put(dump_ctx->skb,
3231                                     dump_ctx->info->snd_portid,
3232                                     dump_ctx->info->snd_seq,
3233                                     &devlink_nl_family, NLM_F_MULTI,
3234                                     dump_ctx->cmd);
3235         if (!dump_ctx->hdr)
3236                 goto nla_put_failure;
3237
3238         devlink = dump_ctx->info->user_ptr[0];
3239         if (devlink_nl_put_handle(dump_ctx->skb, devlink))
3240                 goto nla_put_failure;
3241         dump_ctx->nest = nla_nest_start_noflag(dump_ctx->skb,
3242                                                DEVLINK_ATTR_DPIPE_ENTRIES);
3243         if (!dump_ctx->nest)
3244                 goto nla_put_failure;
3245         return 0;
3246
3247 nla_put_failure:
3248         nlmsg_free(dump_ctx->skb);
3249         return -EMSGSIZE;
3250 }
3251 EXPORT_SYMBOL_GPL(devlink_dpipe_entry_ctx_prepare);
3252
3253 int devlink_dpipe_entry_ctx_append(struct devlink_dpipe_dump_ctx *dump_ctx,
3254                                    struct devlink_dpipe_entry *entry)
3255 {
3256         return devlink_dpipe_entry_put(dump_ctx->skb, entry);
3257 }
3258 EXPORT_SYMBOL_GPL(devlink_dpipe_entry_ctx_append);
3259
3260 int devlink_dpipe_entry_ctx_close(struct devlink_dpipe_dump_ctx *dump_ctx)
3261 {
3262         nla_nest_end(dump_ctx->skb, dump_ctx->nest);
3263         genlmsg_end(dump_ctx->skb, dump_ctx->hdr);
3264         return 0;
3265 }
3266 EXPORT_SYMBOL_GPL(devlink_dpipe_entry_ctx_close);
3267
3268 void devlink_dpipe_entry_clear(struct devlink_dpipe_entry *entry)
3269
3270 {
3271         unsigned int value_count, value_index;
3272         struct devlink_dpipe_value *value;
3273
3274         value = entry->action_values;
3275         value_count = entry->action_values_count;
3276         for (value_index = 0; value_index < value_count; value_index++) {
3277                 kfree(value[value_index].value);
3278                 kfree(value[value_index].mask);
3279         }
3280
3281         value = entry->match_values;
3282         value_count = entry->match_values_count;
3283         for (value_index = 0; value_index < value_count; value_index++) {
3284                 kfree(value[value_index].value);
3285                 kfree(value[value_index].mask);
3286         }
3287 }
3288 EXPORT_SYMBOL(devlink_dpipe_entry_clear);
3289
3290 static int devlink_dpipe_entries_fill(struct genl_info *info,
3291                                       enum devlink_command cmd, int flags,
3292                                       struct devlink_dpipe_table *table)
3293 {
3294         struct devlink_dpipe_dump_ctx dump_ctx;
3295         struct nlmsghdr *nlh;
3296         int err;
3297
3298         dump_ctx.skb = NULL;
3299         dump_ctx.cmd = cmd;
3300         dump_ctx.info = info;
3301
3302         err = table->table_ops->entries_dump(table->priv,
3303                                              table->counters_enabled,
3304                                              &dump_ctx);
3305         if (err)
3306                 return err;
3307
3308 send_done:
3309         nlh = nlmsg_put(dump_ctx.skb, info->snd_portid, info->snd_seq,
3310                         NLMSG_DONE, 0, flags | NLM_F_MULTI);
3311         if (!nlh) {
3312                 err = devlink_dpipe_send_and_alloc_skb(&dump_ctx.skb, info);
3313                 if (err)
3314                         return err;
3315                 goto send_done;
3316         }
3317         return genlmsg_reply(dump_ctx.skb, info);
3318 }
3319
3320 static int devlink_nl_cmd_dpipe_entries_get(struct sk_buff *skb,
3321                                             struct genl_info *info)
3322 {
3323         struct devlink *devlink = info->user_ptr[0];
3324         struct devlink_dpipe_table *table;
3325         const char *table_name;
3326
3327         if (!info->attrs[DEVLINK_ATTR_DPIPE_TABLE_NAME])
3328                 return -EINVAL;
3329
3330         table_name = nla_data(info->attrs[DEVLINK_ATTR_DPIPE_TABLE_NAME]);
3331         table = devlink_dpipe_table_find(&devlink->dpipe_table_list,
3332                                          table_name, devlink);
3333         if (!table)
3334                 return -EINVAL;
3335
3336         if (!table->table_ops->entries_dump)
3337                 return -EINVAL;
3338
3339         return devlink_dpipe_entries_fill(info, DEVLINK_CMD_DPIPE_ENTRIES_GET,
3340                                           0, table);
3341 }
3342
3343 static int devlink_dpipe_fields_put(struct sk_buff *skb,
3344                                     const struct devlink_dpipe_header *header)
3345 {
3346         struct devlink_dpipe_field *field;
3347         struct nlattr *field_attr;
3348         int i;
3349
3350         for (i = 0; i < header->fields_count; i++) {
3351                 field = &header->fields[i];
3352                 field_attr = nla_nest_start_noflag(skb,
3353                                                    DEVLINK_ATTR_DPIPE_FIELD);
3354                 if (!field_attr)
3355                         return -EMSGSIZE;
3356                 if (nla_put_string(skb, DEVLINK_ATTR_DPIPE_FIELD_NAME, field->name) ||
3357                     nla_put_u32(skb, DEVLINK_ATTR_DPIPE_FIELD_ID, field->id) ||
3358                     nla_put_u32(skb, DEVLINK_ATTR_DPIPE_FIELD_BITWIDTH, field->bitwidth) ||
3359                     nla_put_u32(skb, DEVLINK_ATTR_DPIPE_FIELD_MAPPING_TYPE, field->mapping_type))
3360                         goto nla_put_failure;
3361                 nla_nest_end(skb, field_attr);
3362         }
3363         return 0;
3364
3365 nla_put_failure:
3366         nla_nest_cancel(skb, field_attr);
3367         return -EMSGSIZE;
3368 }
3369
3370 static int devlink_dpipe_header_put(struct sk_buff *skb,
3371                                     struct devlink_dpipe_header *header)
3372 {
3373         struct nlattr *fields_attr, *header_attr;
3374         int err;
3375
3376         header_attr = nla_nest_start_noflag(skb, DEVLINK_ATTR_DPIPE_HEADER);
3377         if (!header_attr)
3378                 return -EMSGSIZE;
3379
3380         if (nla_put_string(skb, DEVLINK_ATTR_DPIPE_HEADER_NAME, header->name) ||
3381             nla_put_u32(skb, DEVLINK_ATTR_DPIPE_HEADER_ID, header->id) ||
3382             nla_put_u8(skb, DEVLINK_ATTR_DPIPE_HEADER_GLOBAL, header->global))
3383                 goto nla_put_failure;
3384
3385         fields_attr = nla_nest_start_noflag(skb,
3386                                             DEVLINK_ATTR_DPIPE_HEADER_FIELDS);
3387         if (!fields_attr)
3388                 goto nla_put_failure;
3389
3390         err = devlink_dpipe_fields_put(skb, header);
3391         if (err) {
3392                 nla_nest_cancel(skb, fields_attr);
3393                 goto nla_put_failure;
3394         }
3395         nla_nest_end(skb, fields_attr);
3396         nla_nest_end(skb, header_attr);
3397         return 0;
3398
3399 nla_put_failure:
3400         err = -EMSGSIZE;
3401         nla_nest_cancel(skb, header_attr);
3402         return err;
3403 }
3404
3405 static int devlink_dpipe_headers_fill(struct genl_info *info,
3406                                       enum devlink_command cmd, int flags,
3407                                       struct devlink_dpipe_headers *
3408                                       dpipe_headers)
3409 {
3410         struct devlink *devlink = info->user_ptr[0];
3411         struct nlattr *headers_attr;
3412         struct sk_buff *skb = NULL;
3413         struct nlmsghdr *nlh;
3414         void *hdr;
3415         int i, j;
3416         int err;
3417
3418         i = 0;
3419 start_again:
3420         err = devlink_dpipe_send_and_alloc_skb(&skb, info);
3421         if (err)
3422                 return err;
3423
3424         hdr = genlmsg_put(skb, info->snd_portid, info->snd_seq,
3425                           &devlink_nl_family, NLM_F_MULTI, cmd);
3426         if (!hdr) {
3427                 nlmsg_free(skb);
3428                 return -EMSGSIZE;
3429         }
3430
3431         if (devlink_nl_put_handle(skb, devlink))
3432                 goto nla_put_failure;
3433         headers_attr = nla_nest_start_noflag(skb, DEVLINK_ATTR_DPIPE_HEADERS);
3434         if (!headers_attr)
3435                 goto nla_put_failure;
3436
3437         j = 0;
3438         for (; i < dpipe_headers->headers_count; i++) {
3439                 err = devlink_dpipe_header_put(skb, dpipe_headers->headers[i]);
3440                 if (err) {
3441                         if (!j)
3442                                 goto err_table_put;
3443                         break;
3444                 }
3445                 j++;
3446         }
3447         nla_nest_end(skb, headers_attr);
3448         genlmsg_end(skb, hdr);
3449         if (i != dpipe_headers->headers_count)
3450                 goto start_again;
3451
3452 send_done:
3453         nlh = nlmsg_put(skb, info->snd_portid, info->snd_seq,
3454                         NLMSG_DONE, 0, flags | NLM_F_MULTI);
3455         if (!nlh) {
3456                 err = devlink_dpipe_send_and_alloc_skb(&skb, info);
3457                 if (err)
3458                         return err;
3459                 goto send_done;
3460         }
3461         return genlmsg_reply(skb, info);
3462
3463 nla_put_failure:
3464         err = -EMSGSIZE;
3465 err_table_put:
3466         nlmsg_free(skb);
3467         return err;
3468 }
3469
3470 static int devlink_nl_cmd_dpipe_headers_get(struct sk_buff *skb,
3471                                             struct genl_info *info)
3472 {
3473         struct devlink *devlink = info->user_ptr[0];
3474
3475         if (!devlink->dpipe_headers)
3476                 return -EOPNOTSUPP;
3477         return devlink_dpipe_headers_fill(info, DEVLINK_CMD_DPIPE_HEADERS_GET,
3478                                           0, devlink->dpipe_headers);
3479 }
3480
3481 static int devlink_dpipe_table_counters_set(struct devlink *devlink,
3482                                             const char *table_name,
3483                                             bool enable)
3484 {
3485         struct devlink_dpipe_table *table;
3486
3487         table = devlink_dpipe_table_find(&devlink->dpipe_table_list,
3488                                          table_name, devlink);
3489         if (!table)
3490                 return -EINVAL;
3491
3492         if (table->counter_control_extern)
3493                 return -EOPNOTSUPP;
3494
3495         if (!(table->counters_enabled ^ enable))
3496                 return 0;
3497
3498         table->counters_enabled = enable;
3499         if (table->table_ops->counters_set_update)
3500                 table->table_ops->counters_set_update(table->priv, enable);
3501         return 0;
3502 }
3503
3504 static int devlink_nl_cmd_dpipe_table_counters_set(struct sk_buff *skb,
3505                                                    struct genl_info *info)
3506 {
3507         struct devlink *devlink = info->user_ptr[0];
3508         const char *table_name;
3509         bool counters_enable;
3510
3511         if (!info->attrs[DEVLINK_ATTR_DPIPE_TABLE_NAME] ||
3512             !info->attrs[DEVLINK_ATTR_DPIPE_TABLE_COUNTERS_ENABLED])
3513                 return -EINVAL;
3514
3515         table_name = nla_data(info->attrs[DEVLINK_ATTR_DPIPE_TABLE_NAME]);
3516         counters_enable = !!nla_get_u8(info->attrs[DEVLINK_ATTR_DPIPE_TABLE_COUNTERS_ENABLED]);
3517
3518         return devlink_dpipe_table_counters_set(devlink, table_name,
3519                                                 counters_enable);
3520 }
3521
3522 static struct devlink_resource *
3523 devlink_resource_find(struct devlink *devlink,
3524                       struct devlink_resource *resource, u64 resource_id)
3525 {
3526         struct list_head *resource_list;
3527
3528         if (resource)
3529                 resource_list = &resource->resource_list;
3530         else
3531                 resource_list = &devlink->resource_list;
3532
3533         list_for_each_entry(resource, resource_list, list) {
3534                 struct devlink_resource *child_resource;
3535
3536                 if (resource->id == resource_id)
3537                         return resource;
3538
3539                 child_resource = devlink_resource_find(devlink, resource,
3540                                                        resource_id);
3541                 if (child_resource)
3542                         return child_resource;
3543         }
3544         return NULL;
3545 }
3546
3547 static void
3548 devlink_resource_validate_children(struct devlink_resource *resource)
3549 {
3550         struct devlink_resource *child_resource;
3551         bool size_valid = true;
3552         u64 parts_size = 0;
3553
3554         if (list_empty(&resource->resource_list))
3555                 goto out;
3556
3557         list_for_each_entry(child_resource, &resource->resource_list, list)
3558                 parts_size += child_resource->size_new;
3559
3560         if (parts_size > resource->size_new)
3561                 size_valid = false;
3562 out:
3563         resource->size_valid = size_valid;
3564 }
3565
3566 static int
3567 devlink_resource_validate_size(struct devlink_resource *resource, u64 size,
3568                                struct netlink_ext_ack *extack)
3569 {
3570         u64 reminder;
3571         int err = 0;
3572
3573         if (size > resource->size_params.size_max) {
3574                 NL_SET_ERR_MSG_MOD(extack, "Size larger than maximum");
3575                 err = -EINVAL;
3576         }
3577
3578         if (size < resource->size_params.size_min) {
3579                 NL_SET_ERR_MSG_MOD(extack, "Size smaller than minimum");
3580                 err = -EINVAL;
3581         }
3582
3583         div64_u64_rem(size, resource->size_params.size_granularity, &reminder);
3584         if (reminder) {
3585                 NL_SET_ERR_MSG_MOD(extack, "Wrong granularity");
3586                 err = -EINVAL;
3587         }
3588
3589         return err;
3590 }
3591
3592 static int devlink_nl_cmd_resource_set(struct sk_buff *skb,
3593                                        struct genl_info *info)
3594 {
3595         struct devlink *devlink = info->user_ptr[0];
3596         struct devlink_resource *resource;
3597         u64 resource_id;
3598         u64 size;
3599         int err;
3600
3601         if (!info->attrs[DEVLINK_ATTR_RESOURCE_ID] ||
3602             !info->attrs[DEVLINK_ATTR_RESOURCE_SIZE])
3603                 return -EINVAL;
3604         resource_id = nla_get_u64(info->attrs[DEVLINK_ATTR_RESOURCE_ID]);
3605
3606         resource = devlink_resource_find(devlink, NULL, resource_id);
3607         if (!resource)
3608                 return -EINVAL;
3609
3610         size = nla_get_u64(info->attrs[DEVLINK_ATTR_RESOURCE_SIZE]);
3611         err = devlink_resource_validate_size(resource, size, info->extack);
3612         if (err)
3613                 return err;
3614
3615         resource->size_new = size;
3616         devlink_resource_validate_children(resource);
3617         if (resource->parent)
3618                 devlink_resource_validate_children(resource->parent);
3619         return 0;
3620 }
3621
3622 static int
3623 devlink_resource_size_params_put(struct devlink_resource *resource,
3624                                  struct sk_buff *skb)
3625 {
3626         struct devlink_resource_size_params *size_params;
3627
3628         size_params = &resource->size_params;
3629         if (nla_put_u64_64bit(skb, DEVLINK_ATTR_RESOURCE_SIZE_GRAN,
3630                               size_params->size_granularity, DEVLINK_ATTR_PAD) ||
3631             nla_put_u64_64bit(skb, DEVLINK_ATTR_RESOURCE_SIZE_MAX,
3632                               size_params->size_max, DEVLINK_ATTR_PAD) ||
3633             nla_put_u64_64bit(skb, DEVLINK_ATTR_RESOURCE_SIZE_MIN,
3634                               size_params->size_min, DEVLINK_ATTR_PAD) ||
3635             nla_put_u8(skb, DEVLINK_ATTR_RESOURCE_UNIT, size_params->unit))
3636                 return -EMSGSIZE;
3637         return 0;
3638 }
3639
3640 static int devlink_resource_occ_put(struct devlink_resource *resource,
3641                                     struct sk_buff *skb)
3642 {
3643         if (!resource->occ_get)
3644                 return 0;
3645         return nla_put_u64_64bit(skb, DEVLINK_ATTR_RESOURCE_OCC,
3646                                  resource->occ_get(resource->occ_get_priv),
3647                                  DEVLINK_ATTR_PAD);
3648 }
3649
3650 static int devlink_resource_put(struct devlink *devlink, struct sk_buff *skb,
3651                                 struct devlink_resource *resource)
3652 {
3653         struct devlink_resource *child_resource;
3654         struct nlattr *child_resource_attr;
3655         struct nlattr *resource_attr;
3656
3657         resource_attr = nla_nest_start_noflag(skb, DEVLINK_ATTR_RESOURCE);
3658         if (!resource_attr)
3659                 return -EMSGSIZE;
3660
3661         if (nla_put_string(skb, DEVLINK_ATTR_RESOURCE_NAME, resource->name) ||
3662             nla_put_u64_64bit(skb, DEVLINK_ATTR_RESOURCE_SIZE, resource->size,
3663                               DEVLINK_ATTR_PAD) ||
3664             nla_put_u64_64bit(skb, DEVLINK_ATTR_RESOURCE_ID, resource->id,
3665                               DEVLINK_ATTR_PAD))
3666                 goto nla_put_failure;
3667         if (resource->size != resource->size_new)
3668                 nla_put_u64_64bit(skb, DEVLINK_ATTR_RESOURCE_SIZE_NEW,
3669                                   resource->size_new, DEVLINK_ATTR_PAD);
3670         if (devlink_resource_occ_put(resource, skb))
3671                 goto nla_put_failure;
3672         if (devlink_resource_size_params_put(resource, skb))
3673                 goto nla_put_failure;
3674         if (list_empty(&resource->resource_list))
3675                 goto out;
3676
3677         if (nla_put_u8(skb, DEVLINK_ATTR_RESOURCE_SIZE_VALID,
3678                        resource->size_valid))
3679                 goto nla_put_failure;
3680
3681         child_resource_attr = nla_nest_start_noflag(skb,
3682                                                     DEVLINK_ATTR_RESOURCE_LIST);
3683         if (!child_resource_attr)
3684                 goto nla_put_failure;
3685
3686         list_for_each_entry(child_resource, &resource->resource_list, list) {
3687                 if (devlink_resource_put(devlink, skb, child_resource))
3688                         goto resource_put_failure;
3689         }
3690
3691         nla_nest_end(skb, child_resource_attr);
3692 out:
3693         nla_nest_end(skb, resource_attr);
3694         return 0;
3695
3696 resource_put_failure:
3697         nla_nest_cancel(skb, child_resource_attr);
3698 nla_put_failure:
3699         nla_nest_cancel(skb, resource_attr);
3700         return -EMSGSIZE;
3701 }
3702
3703 static int devlink_resource_fill(struct genl_info *info,
3704                                  enum devlink_command cmd, int flags)
3705 {
3706         struct devlink *devlink = info->user_ptr[0];
3707         struct devlink_resource *resource;
3708         struct nlattr *resources_attr;
3709         struct sk_buff *skb = NULL;
3710         struct nlmsghdr *nlh;
3711         bool incomplete;
3712         void *hdr;
3713         int i;
3714         int err;
3715
3716         resource = list_first_entry(&devlink->resource_list,
3717                                     struct devlink_resource, list);
3718 start_again:
3719         err = devlink_dpipe_send_and_alloc_skb(&skb, info);
3720         if (err)
3721                 return err;
3722
3723         hdr = genlmsg_put(skb, info->snd_portid, info->snd_seq,
3724                           &devlink_nl_family, NLM_F_MULTI, cmd);
3725         if (!hdr) {
3726                 nlmsg_free(skb);
3727                 return -EMSGSIZE;
3728         }
3729
3730         if (devlink_nl_put_handle(skb, devlink))
3731                 goto nla_put_failure;
3732
3733         resources_attr = nla_nest_start_noflag(skb,
3734                                                DEVLINK_ATTR_RESOURCE_LIST);
3735         if (!resources_attr)
3736                 goto nla_put_failure;
3737
3738         incomplete = false;
3739         i = 0;
3740         list_for_each_entry_from(resource, &devlink->resource_list, list) {
3741                 err = devlink_resource_put(devlink, skb, resource);
3742                 if (err) {
3743                         if (!i)
3744                                 goto err_resource_put;
3745                         incomplete = true;
3746                         break;
3747                 }
3748                 i++;
3749         }
3750         nla_nest_end(skb, resources_attr);
3751         genlmsg_end(skb, hdr);
3752         if (incomplete)
3753                 goto start_again;
3754 send_done:
3755         nlh = nlmsg_put(skb, info->snd_portid, info->snd_seq,
3756                         NLMSG_DONE, 0, flags | NLM_F_MULTI);
3757         if (!nlh) {
3758                 err = devlink_dpipe_send_and_alloc_skb(&skb, info);
3759                 if (err)
3760                         return err;
3761                 goto send_done;
3762         }
3763         return genlmsg_reply(skb, info);
3764
3765 nla_put_failure:
3766         err = -EMSGSIZE;
3767 err_resource_put:
3768         nlmsg_free(skb);
3769         return err;
3770 }
3771
3772 static int devlink_nl_cmd_resource_dump(struct sk_buff *skb,
3773                                         struct genl_info *info)
3774 {
3775         struct devlink *devlink = info->user_ptr[0];
3776
3777         if (list_empty(&devlink->resource_list))
3778                 return -EOPNOTSUPP;
3779
3780         return devlink_resource_fill(info, DEVLINK_CMD_RESOURCE_DUMP, 0);
3781 }
3782
3783 static int
3784 devlink_resources_validate(struct devlink *devlink,
3785                            struct devlink_resource *resource,
3786                            struct genl_info *info)
3787 {
3788         struct list_head *resource_list;
3789         int err = 0;
3790
3791         if (resource)
3792                 resource_list = &resource->resource_list;
3793         else
3794                 resource_list = &devlink->resource_list;
3795
3796         list_for_each_entry(resource, resource_list, list) {
3797                 if (!resource->size_valid)
3798                         return -EINVAL;
3799                 err = devlink_resources_validate(devlink, resource, info);
3800                 if (err)
3801                         return err;
3802         }
3803         return err;
3804 }
3805
3806 static struct net *devlink_netns_get(struct sk_buff *skb,
3807                                      struct genl_info *info)
3808 {
3809         struct nlattr *netns_pid_attr = info->attrs[DEVLINK_ATTR_NETNS_PID];
3810         struct nlattr *netns_fd_attr = info->attrs[DEVLINK_ATTR_NETNS_FD];
3811         struct nlattr *netns_id_attr = info->attrs[DEVLINK_ATTR_NETNS_ID];
3812         struct net *net;
3813
3814         if (!!netns_pid_attr + !!netns_fd_attr + !!netns_id_attr > 1) {
3815                 NL_SET_ERR_MSG_MOD(info->extack, "multiple netns identifying attributes specified");
3816                 return ERR_PTR(-EINVAL);
3817         }
3818
3819         if (netns_pid_attr) {
3820                 net = get_net_ns_by_pid(nla_get_u32(netns_pid_attr));
3821         } else if (netns_fd_attr) {
3822                 net = get_net_ns_by_fd(nla_get_u32(netns_fd_attr));
3823         } else if (netns_id_attr) {
3824                 net = get_net_ns_by_id(sock_net(skb->sk),
3825                                        nla_get_u32(netns_id_attr));
3826                 if (!net)
3827                         net = ERR_PTR(-EINVAL);
3828         } else {
3829                 WARN_ON(1);
3830                 net = ERR_PTR(-EINVAL);
3831         }
3832         if (IS_ERR(net)) {
3833                 NL_SET_ERR_MSG_MOD(info->extack, "Unknown network namespace");
3834                 return ERR_PTR(-EINVAL);
3835         }
3836         if (!netlink_ns_capable(skb, net->user_ns, CAP_NET_ADMIN)) {
3837                 put_net(net);
3838                 return ERR_PTR(-EPERM);
3839         }
3840         return net;
3841 }
3842
3843 static void devlink_param_notify(struct devlink *devlink,
3844                                  unsigned int port_index,
3845                                  struct devlink_param_item *param_item,
3846                                  enum devlink_command cmd);
3847
3848 static void devlink_ns_change_notify(struct devlink *devlink,
3849                                      struct net *dest_net, struct net *curr_net,
3850                                      bool new)
3851 {
3852         struct devlink_param_item *param_item;
3853         enum devlink_command cmd;
3854
3855         /* Userspace needs to be notified about devlink objects
3856          * removed from original and entering new network namespace.
3857          * The rest of the devlink objects are re-created during
3858          * reload process so the notifications are generated separatelly.
3859          */
3860
3861         if (!dest_net || net_eq(dest_net, curr_net))
3862                 return;
3863
3864         if (new)
3865                 devlink_notify(devlink, DEVLINK_CMD_NEW);
3866
3867         cmd = new ? DEVLINK_CMD_PARAM_NEW : DEVLINK_CMD_PARAM_DEL;
3868         list_for_each_entry(param_item, &devlink->param_list, list)
3869                 devlink_param_notify(devlink, 0, param_item, cmd);
3870
3871         if (!new)
3872                 devlink_notify(devlink, DEVLINK_CMD_DEL);
3873 }
3874
3875 static bool devlink_reload_supported(const struct devlink_ops *ops)
3876 {
3877         return ops->reload_down && ops->reload_up;
3878 }
3879
3880 static void devlink_reload_failed_set(struct devlink *devlink,
3881                                       bool reload_failed)
3882 {
3883         if (devlink->reload_failed == reload_failed)
3884                 return;
3885         devlink->reload_failed = reload_failed;
3886         devlink_notify(devlink, DEVLINK_CMD_NEW);
3887 }
3888
3889 bool devlink_is_reload_failed(const struct devlink *devlink)
3890 {
3891         return devlink->reload_failed;
3892 }
3893 EXPORT_SYMBOL_GPL(devlink_is_reload_failed);
3894
3895 static void
3896 __devlink_reload_stats_update(struct devlink *devlink, u32 *reload_stats,
3897                               enum devlink_reload_limit limit, u32 actions_performed)
3898 {
3899         unsigned long actions = actions_performed;
3900         int stat_idx;
3901         int action;
3902
3903         for_each_set_bit(action, &actions, __DEVLINK_RELOAD_ACTION_MAX) {
3904                 stat_idx = limit * __DEVLINK_RELOAD_ACTION_MAX + action;
3905                 reload_stats[stat_idx]++;
3906         }
3907         devlink_notify(devlink, DEVLINK_CMD_NEW);
3908 }
3909
3910 static void
3911 devlink_reload_stats_update(struct devlink *devlink, enum devlink_reload_limit limit,
3912                             u32 actions_performed)
3913 {
3914         __devlink_reload_stats_update(devlink, devlink->stats.reload_stats, limit,
3915                                       actions_performed);
3916 }
3917
3918 /**
3919  *      devlink_remote_reload_actions_performed - Update devlink on reload actions
3920  *        performed which are not a direct result of devlink reload call.
3921  *
3922  *      This should be called by a driver after performing reload actions in case it was not
3923  *      a result of devlink reload call. For example fw_activate was performed as a result
3924  *      of devlink reload triggered fw_activate on another host.
3925  *      The motivation for this function is to keep data on reload actions performed on this
3926  *      function whether it was done due to direct devlink reload call or not.
3927  *
3928  *      @devlink: devlink
3929  *      @limit: reload limit
3930  *      @actions_performed: bitmask of actions performed
3931  */
3932 void devlink_remote_reload_actions_performed(struct devlink *devlink,
3933                                              enum devlink_reload_limit limit,
3934                                              u32 actions_performed)
3935 {
3936         if (WARN_ON(!actions_performed ||
3937                     actions_performed & BIT(DEVLINK_RELOAD_ACTION_UNSPEC) ||
3938                     actions_performed >= BIT(__DEVLINK_RELOAD_ACTION_MAX) ||
3939                     limit > DEVLINK_RELOAD_LIMIT_MAX))
3940                 return;
3941
3942         __devlink_reload_stats_update(devlink, devlink->stats.remote_reload_stats, limit,
3943                                       actions_performed);
3944 }
3945 EXPORT_SYMBOL_GPL(devlink_remote_reload_actions_performed);
3946
3947 static int devlink_reload(struct devlink *devlink, struct net *dest_net,
3948                           enum devlink_reload_action action, enum devlink_reload_limit limit,
3949                           u32 *actions_performed, struct netlink_ext_ack *extack)
3950 {
3951         u32 remote_reload_stats[DEVLINK_RELOAD_STATS_ARRAY_SIZE];
3952         struct net *curr_net;
3953         int err;
3954
3955         if (!devlink->reload_enabled)
3956                 return -EOPNOTSUPP;
3957
3958         memcpy(remote_reload_stats, devlink->stats.remote_reload_stats,
3959                sizeof(remote_reload_stats));
3960
3961         curr_net = devlink_net(devlink);
3962         devlink_ns_change_notify(devlink, dest_net, curr_net, false);
3963         err = devlink->ops->reload_down(devlink, !!dest_net, action, limit, extack);
3964         if (err)
3965                 return err;
3966
3967         if (dest_net && !net_eq(dest_net, curr_net))
3968                 write_pnet(&devlink->_net, dest_net);
3969
3970         err = devlink->ops->reload_up(devlink, action, limit, actions_performed, extack);
3971         devlink_reload_failed_set(devlink, !!err);
3972         if (err)
3973                 return err;
3974
3975         devlink_ns_change_notify(devlink, dest_net, curr_net, true);
3976         WARN_ON(!(*actions_performed & BIT(action)));
3977         /* Catch driver on updating the remote action within devlink reload */
3978         WARN_ON(memcmp(remote_reload_stats, devlink->stats.remote_reload_stats,
3979                        sizeof(remote_reload_stats)));
3980         devlink_reload_stats_update(devlink, limit, *actions_performed);
3981         return 0;
3982 }
3983
3984 static int
3985 devlink_nl_reload_actions_performed_snd(struct devlink *devlink, u32 actions_performed,
3986                                         enum devlink_command cmd, struct genl_info *info)
3987 {
3988         struct sk_buff *msg;
3989         void *hdr;
3990
3991         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
3992         if (!msg)
3993                 return -ENOMEM;
3994
3995         hdr = genlmsg_put(msg, info->snd_portid, info->snd_seq, &devlink_nl_family, 0, cmd);
3996         if (!hdr)
3997                 goto free_msg;
3998
3999         if (devlink_nl_put_handle(msg, devlink))
4000                 goto nla_put_failure;
4001
4002         if (nla_put_bitfield32(msg, DEVLINK_ATTR_RELOAD_ACTIONS_PERFORMED, actions_performed,
4003                                actions_performed))
4004                 goto nla_put_failure;
4005         genlmsg_end(msg, hdr);
4006
4007         return genlmsg_reply(msg, info);
4008
4009 nla_put_failure:
4010         genlmsg_cancel(msg, hdr);
4011 free_msg:
4012         nlmsg_free(msg);
4013         return -EMSGSIZE;
4014 }
4015
4016 static int devlink_nl_cmd_reload(struct sk_buff *skb, struct genl_info *info)
4017 {
4018         struct devlink *devlink = info->user_ptr[0];
4019         enum devlink_reload_action action;
4020         enum devlink_reload_limit limit;
4021         struct net *dest_net = NULL;
4022         u32 actions_performed;
4023         int err;
4024
4025         if (!devlink_reload_supported(devlink->ops))
4026                 return -EOPNOTSUPP;
4027
4028         err = devlink_resources_validate(devlink, NULL, info);
4029         if (err) {
4030                 NL_SET_ERR_MSG_MOD(info->extack, "resources size validation failed");
4031                 return err;
4032         }
4033
4034         if (info->attrs[DEVLINK_ATTR_NETNS_PID] ||
4035             info->attrs[DEVLINK_ATTR_NETNS_FD] ||
4036             info->attrs[DEVLINK_ATTR_NETNS_ID]) {
4037                 dest_net = devlink_netns_get(skb, info);
4038                 if (IS_ERR(dest_net))
4039                         return PTR_ERR(dest_net);
4040         }
4041
4042         if (info->attrs[DEVLINK_ATTR_RELOAD_ACTION])
4043                 action = nla_get_u8(info->attrs[DEVLINK_ATTR_RELOAD_ACTION]);
4044         else
4045                 action = DEVLINK_RELOAD_ACTION_DRIVER_REINIT;
4046
4047         if (!devlink_reload_action_is_supported(devlink, action)) {
4048                 NL_SET_ERR_MSG_MOD(info->extack,
4049                                    "Requested reload action is not supported by the driver");
4050                 return -EOPNOTSUPP;
4051         }
4052
4053         limit = DEVLINK_RELOAD_LIMIT_UNSPEC;
4054         if (info->attrs[DEVLINK_ATTR_RELOAD_LIMITS]) {
4055                 struct nla_bitfield32 limits;
4056                 u32 limits_selected;
4057
4058                 limits = nla_get_bitfield32(info->attrs[DEVLINK_ATTR_RELOAD_LIMITS]);
4059                 limits_selected = limits.value & limits.selector;
4060                 if (!limits_selected) {
4061                         NL_SET_ERR_MSG_MOD(info->extack, "Invalid limit selected");
4062                         return -EINVAL;
4063                 }
4064                 for (limit = 0 ; limit <= DEVLINK_RELOAD_LIMIT_MAX ; limit++)
4065                         if (limits_selected & BIT(limit))
4066                                 break;
4067                 /* UAPI enables multiselection, but currently it is not used */
4068                 if (limits_selected != BIT(limit)) {
4069                         NL_SET_ERR_MSG_MOD(info->extack,
4070                                            "Multiselection of limit is not supported");
4071                         return -EOPNOTSUPP;
4072                 }
4073                 if (!devlink_reload_limit_is_supported(devlink, limit)) {
4074                         NL_SET_ERR_MSG_MOD(info->extack,
4075                                            "Requested limit is not supported by the driver");
4076                         return -EOPNOTSUPP;
4077                 }
4078                 if (devlink_reload_combination_is_invalid(action, limit)) {
4079                         NL_SET_ERR_MSG_MOD(info->extack,
4080                                            "Requested limit is invalid for this action");
4081                         return -EINVAL;
4082                 }
4083         }
4084         err = devlink_reload(devlink, dest_net, action, limit, &actions_performed, info->extack);
4085
4086         if (dest_net)
4087                 put_net(dest_net);
4088
4089         if (err)
4090                 return err;
4091         /* For backward compatibility generate reply only if attributes used by user */
4092         if (!info->attrs[DEVLINK_ATTR_RELOAD_ACTION] && !info->attrs[DEVLINK_ATTR_RELOAD_LIMITS])
4093                 return 0;
4094
4095         return devlink_nl_reload_actions_performed_snd(devlink, actions_performed,
4096                                                        DEVLINK_CMD_RELOAD, info);
4097 }
4098
4099 static int devlink_nl_flash_update_fill(struct sk_buff *msg,
4100                                         struct devlink *devlink,
4101                                         enum devlink_command cmd,
4102                                         struct devlink_flash_notify *params)
4103 {
4104         void *hdr;
4105
4106         hdr = genlmsg_put(msg, 0, 0, &devlink_nl_family, 0, cmd);
4107         if (!hdr)
4108                 return -EMSGSIZE;
4109
4110         if (devlink_nl_put_handle(msg, devlink))
4111                 goto nla_put_failure;
4112
4113         if (cmd != DEVLINK_CMD_FLASH_UPDATE_STATUS)
4114                 goto out;
4115
4116         if (params->status_msg &&
4117             nla_put_string(msg, DEVLINK_ATTR_FLASH_UPDATE_STATUS_MSG,
4118                            params->status_msg))
4119                 goto nla_put_failure;
4120         if (params->component &&
4121             nla_put_string(msg, DEVLINK_ATTR_FLASH_UPDATE_COMPONENT,
4122                            params->component))
4123                 goto nla_put_failure;
4124         if (nla_put_u64_64bit(msg, DEVLINK_ATTR_FLASH_UPDATE_STATUS_DONE,
4125                               params->done, DEVLINK_ATTR_PAD))
4126                 goto nla_put_failure;
4127         if (nla_put_u64_64bit(msg, DEVLINK_ATTR_FLASH_UPDATE_STATUS_TOTAL,
4128                               params->total, DEVLINK_ATTR_PAD))
4129                 goto nla_put_failure;
4130         if (nla_put_u64_64bit(msg, DEVLINK_ATTR_FLASH_UPDATE_STATUS_TIMEOUT,
4131                               params->timeout, DEVLINK_ATTR_PAD))
4132                 goto nla_put_failure;
4133
4134 out:
4135         genlmsg_end(msg, hdr);
4136         return 0;
4137
4138 nla_put_failure:
4139         genlmsg_cancel(msg, hdr);
4140         return -EMSGSIZE;
4141 }
4142
4143 static void __devlink_flash_update_notify(struct devlink *devlink,
4144                                           enum devlink_command cmd,
4145                                           struct devlink_flash_notify *params)
4146 {
4147         struct sk_buff *msg;
4148         int err;
4149
4150         WARN_ON(cmd != DEVLINK_CMD_FLASH_UPDATE &&
4151                 cmd != DEVLINK_CMD_FLASH_UPDATE_END &&
4152                 cmd != DEVLINK_CMD_FLASH_UPDATE_STATUS);
4153
4154         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
4155         if (!msg)
4156                 return;
4157
4158         err = devlink_nl_flash_update_fill(msg, devlink, cmd, params);
4159         if (err)
4160                 goto out_free_msg;
4161
4162         genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink),
4163                                 msg, 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
4164         return;
4165
4166 out_free_msg:
4167         nlmsg_free(msg);
4168 }
4169
4170 static void devlink_flash_update_begin_notify(struct devlink *devlink)
4171 {
4172         struct devlink_flash_notify params = {};
4173
4174         __devlink_flash_update_notify(devlink,
4175                                       DEVLINK_CMD_FLASH_UPDATE,
4176                                       &params);
4177 }
4178
4179 static void devlink_flash_update_end_notify(struct devlink *devlink)
4180 {
4181         struct devlink_flash_notify params = {};
4182
4183         __devlink_flash_update_notify(devlink,
4184                                       DEVLINK_CMD_FLASH_UPDATE_END,
4185                                       &params);
4186 }
4187
4188 void devlink_flash_update_status_notify(struct devlink *devlink,
4189                                         const char *status_msg,
4190                                         const char *component,
4191                                         unsigned long done,
4192                                         unsigned long total)
4193 {
4194         struct devlink_flash_notify params = {
4195                 .status_msg = status_msg,
4196                 .component = component,
4197                 .done = done,
4198                 .total = total,
4199         };
4200
4201         __devlink_flash_update_notify(devlink,
4202                                       DEVLINK_CMD_FLASH_UPDATE_STATUS,
4203                                       &params);
4204 }
4205 EXPORT_SYMBOL_GPL(devlink_flash_update_status_notify);
4206
4207 void devlink_flash_update_timeout_notify(struct devlink *devlink,
4208                                          const char *status_msg,
4209                                          const char *component,
4210                                          unsigned long timeout)
4211 {
4212         struct devlink_flash_notify params = {
4213                 .status_msg = status_msg,
4214                 .component = component,
4215                 .timeout = timeout,
4216         };
4217
4218         __devlink_flash_update_notify(devlink,
4219                                       DEVLINK_CMD_FLASH_UPDATE_STATUS,
4220                                       &params);
4221 }
4222 EXPORT_SYMBOL_GPL(devlink_flash_update_timeout_notify);
4223
4224 static int devlink_nl_cmd_flash_update(struct sk_buff *skb,
4225                                        struct genl_info *info)
4226 {
4227         struct nlattr *nla_component, *nla_overwrite_mask, *nla_file_name;
4228         struct devlink_flash_update_params params = {};
4229         struct devlink *devlink = info->user_ptr[0];
4230         const char *file_name;
4231         u32 supported_params;
4232         int ret;
4233
4234         if (!devlink->ops->flash_update)
4235                 return -EOPNOTSUPP;
4236
4237         if (!info->attrs[DEVLINK_ATTR_FLASH_UPDATE_FILE_NAME])
4238                 return -EINVAL;
4239
4240         supported_params = devlink->ops->supported_flash_update_params;
4241
4242         nla_component = info->attrs[DEVLINK_ATTR_FLASH_UPDATE_COMPONENT];
4243         if (nla_component) {
4244                 if (!(supported_params & DEVLINK_SUPPORT_FLASH_UPDATE_COMPONENT)) {
4245                         NL_SET_ERR_MSG_ATTR(info->extack, nla_component,
4246                                             "component update is not supported by this device");
4247                         return -EOPNOTSUPP;
4248                 }
4249                 params.component = nla_data(nla_component);
4250         }
4251
4252         nla_overwrite_mask = info->attrs[DEVLINK_ATTR_FLASH_UPDATE_OVERWRITE_MASK];
4253         if (nla_overwrite_mask) {
4254                 struct nla_bitfield32 sections;
4255
4256                 if (!(supported_params & DEVLINK_SUPPORT_FLASH_UPDATE_OVERWRITE_MASK)) {
4257                         NL_SET_ERR_MSG_ATTR(info->extack, nla_overwrite_mask,
4258                                             "overwrite settings are not supported by this device");
4259                         return -EOPNOTSUPP;
4260                 }
4261                 sections = nla_get_bitfield32(nla_overwrite_mask);
4262                 params.overwrite_mask = sections.value & sections.selector;
4263         }
4264
4265         nla_file_name = info->attrs[DEVLINK_ATTR_FLASH_UPDATE_FILE_NAME];
4266         file_name = nla_data(nla_file_name);
4267         ret = request_firmware(&params.fw, file_name, devlink->dev);
4268         if (ret) {
4269                 NL_SET_ERR_MSG_ATTR(info->extack, nla_file_name, "failed to locate the requested firmware file");
4270                 return ret;
4271         }
4272
4273         devlink_flash_update_begin_notify(devlink);
4274         ret = devlink->ops->flash_update(devlink, &params, info->extack);
4275         devlink_flash_update_end_notify(devlink);
4276
4277         release_firmware(params.fw);
4278
4279         return ret;
4280 }
4281
4282 static const struct devlink_param devlink_param_generic[] = {
4283         {
4284                 .id = DEVLINK_PARAM_GENERIC_ID_INT_ERR_RESET,
4285                 .name = DEVLINK_PARAM_GENERIC_INT_ERR_RESET_NAME,
4286                 .type = DEVLINK_PARAM_GENERIC_INT_ERR_RESET_TYPE,
4287         },
4288         {
4289                 .id = DEVLINK_PARAM_GENERIC_ID_MAX_MACS,
4290                 .name = DEVLINK_PARAM_GENERIC_MAX_MACS_NAME,
4291                 .type = DEVLINK_PARAM_GENERIC_MAX_MACS_TYPE,
4292         },
4293         {
4294                 .id = DEVLINK_PARAM_GENERIC_ID_ENABLE_SRIOV,
4295                 .name = DEVLINK_PARAM_GENERIC_ENABLE_SRIOV_NAME,
4296                 .type = DEVLINK_PARAM_GENERIC_ENABLE_SRIOV_TYPE,
4297         },
4298         {
4299                 .id = DEVLINK_PARAM_GENERIC_ID_REGION_SNAPSHOT,
4300                 .name = DEVLINK_PARAM_GENERIC_REGION_SNAPSHOT_NAME,
4301                 .type = DEVLINK_PARAM_GENERIC_REGION_SNAPSHOT_TYPE,
4302         },
4303         {
4304                 .id = DEVLINK_PARAM_GENERIC_ID_IGNORE_ARI,
4305                 .name = DEVLINK_PARAM_GENERIC_IGNORE_ARI_NAME,
4306                 .type = DEVLINK_PARAM_GENERIC_IGNORE_ARI_TYPE,
4307         },
4308         {
4309                 .id = DEVLINK_PARAM_GENERIC_ID_MSIX_VEC_PER_PF_MAX,
4310                 .name = DEVLINK_PARAM_GENERIC_MSIX_VEC_PER_PF_MAX_NAME,
4311                 .type = DEVLINK_PARAM_GENERIC_MSIX_VEC_PER_PF_MAX_TYPE,
4312         },
4313         {
4314                 .id = DEVLINK_PARAM_GENERIC_ID_MSIX_VEC_PER_PF_MIN,
4315                 .name = DEVLINK_PARAM_GENERIC_MSIX_VEC_PER_PF_MIN_NAME,
4316                 .type = DEVLINK_PARAM_GENERIC_MSIX_VEC_PER_PF_MIN_TYPE,
4317         },
4318         {
4319                 .id = DEVLINK_PARAM_GENERIC_ID_FW_LOAD_POLICY,
4320                 .name = DEVLINK_PARAM_GENERIC_FW_LOAD_POLICY_NAME,
4321                 .type = DEVLINK_PARAM_GENERIC_FW_LOAD_POLICY_TYPE,
4322         },
4323         {
4324                 .id = DEVLINK_PARAM_GENERIC_ID_RESET_DEV_ON_DRV_PROBE,
4325                 .name = DEVLINK_PARAM_GENERIC_RESET_DEV_ON_DRV_PROBE_NAME,
4326                 .type = DEVLINK_PARAM_GENERIC_RESET_DEV_ON_DRV_PROBE_TYPE,
4327         },
4328         {
4329                 .id = DEVLINK_PARAM_GENERIC_ID_ENABLE_ROCE,
4330                 .name = DEVLINK_PARAM_GENERIC_ENABLE_ROCE_NAME,
4331                 .type = DEVLINK_PARAM_GENERIC_ENABLE_ROCE_TYPE,
4332         },
4333         {
4334                 .id = DEVLINK_PARAM_GENERIC_ID_ENABLE_REMOTE_DEV_RESET,
4335                 .name = DEVLINK_PARAM_GENERIC_ENABLE_REMOTE_DEV_RESET_NAME,
4336                 .type = DEVLINK_PARAM_GENERIC_ENABLE_REMOTE_DEV_RESET_TYPE,
4337         },
4338         {
4339                 .id = DEVLINK_PARAM_GENERIC_ID_ENABLE_ETH,
4340                 .name = DEVLINK_PARAM_GENERIC_ENABLE_ETH_NAME,
4341                 .type = DEVLINK_PARAM_GENERIC_ENABLE_ETH_TYPE,
4342         },
4343         {
4344                 .id = DEVLINK_PARAM_GENERIC_ID_ENABLE_RDMA,
4345                 .name = DEVLINK_PARAM_GENERIC_ENABLE_RDMA_NAME,
4346                 .type = DEVLINK_PARAM_GENERIC_ENABLE_RDMA_TYPE,
4347         },
4348         {
4349                 .id = DEVLINK_PARAM_GENERIC_ID_ENABLE_VNET,
4350                 .name = DEVLINK_PARAM_GENERIC_ENABLE_VNET_NAME,
4351                 .type = DEVLINK_PARAM_GENERIC_ENABLE_VNET_TYPE,
4352         },
4353 };
4354
4355 static int devlink_param_generic_verify(const struct devlink_param *param)
4356 {
4357         /* verify it match generic parameter by id and name */
4358         if (param->id > DEVLINK_PARAM_GENERIC_ID_MAX)
4359                 return -EINVAL;
4360         if (strcmp(param->name, devlink_param_generic[param->id].name))
4361                 return -ENOENT;
4362
4363         WARN_ON(param->type != devlink_param_generic[param->id].type);
4364
4365         return 0;
4366 }
4367
4368 static int devlink_param_driver_verify(const struct devlink_param *param)
4369 {
4370         int i;
4371
4372         if (param->id <= DEVLINK_PARAM_GENERIC_ID_MAX)
4373                 return -EINVAL;
4374         /* verify no such name in generic params */
4375         for (i = 0; i <= DEVLINK_PARAM_GENERIC_ID_MAX; i++)
4376                 if (!strcmp(param->name, devlink_param_generic[i].name))
4377                         return -EEXIST;
4378
4379         return 0;
4380 }
4381
4382 static struct devlink_param_item *
4383 devlink_param_find_by_name(struct list_head *param_list,
4384                            const char *param_name)
4385 {
4386         struct devlink_param_item *param_item;
4387
4388         list_for_each_entry(param_item, param_list, list)
4389                 if (!strcmp(param_item->param->name, param_name))
4390                         return param_item;
4391         return NULL;
4392 }
4393
4394 static struct devlink_param_item *
4395 devlink_param_find_by_id(struct list_head *param_list, u32 param_id)
4396 {
4397         struct devlink_param_item *param_item;
4398
4399         list_for_each_entry(param_item, param_list, list)
4400                 if (param_item->param->id == param_id)
4401                         return param_item;
4402         return NULL;
4403 }
4404
4405 static bool
4406 devlink_param_cmode_is_supported(const struct devlink_param *param,
4407                                  enum devlink_param_cmode cmode)
4408 {
4409         return test_bit(cmode, &param->supported_cmodes);
4410 }
4411
4412 static int devlink_param_get(struct devlink *devlink,
4413                              const struct devlink_param *param,
4414                              struct devlink_param_gset_ctx *ctx)
4415 {
4416         if (!param->get)
4417                 return -EOPNOTSUPP;
4418         return param->get(devlink, param->id, ctx);
4419 }
4420
4421 static int devlink_param_set(struct devlink *devlink,
4422                              const struct devlink_param *param,
4423                              struct devlink_param_gset_ctx *ctx)
4424 {
4425         if (!param->set)
4426                 return -EOPNOTSUPP;
4427         return param->set(devlink, param->id, ctx);
4428 }
4429
4430 static int
4431 devlink_param_type_to_nla_type(enum devlink_param_type param_type)
4432 {
4433         switch (param_type) {
4434         case DEVLINK_PARAM_TYPE_U8:
4435                 return NLA_U8;
4436         case DEVLINK_PARAM_TYPE_U16:
4437                 return NLA_U16;
4438         case DEVLINK_PARAM_TYPE_U32:
4439                 return NLA_U32;
4440         case DEVLINK_PARAM_TYPE_STRING:
4441                 return NLA_STRING;
4442         case DEVLINK_PARAM_TYPE_BOOL:
4443                 return NLA_FLAG;
4444         default:
4445                 return -EINVAL;
4446         }
4447 }
4448
4449 static int
4450 devlink_nl_param_value_fill_one(struct sk_buff *msg,
4451                                 enum devlink_param_type type,
4452                                 enum devlink_param_cmode cmode,
4453                                 union devlink_param_value val)
4454 {
4455         struct nlattr *param_value_attr;
4456
4457         param_value_attr = nla_nest_start_noflag(msg,
4458                                                  DEVLINK_ATTR_PARAM_VALUE);
4459         if (!param_value_attr)
4460                 goto nla_put_failure;
4461
4462         if (nla_put_u8(msg, DEVLINK_ATTR_PARAM_VALUE_CMODE, cmode))
4463                 goto value_nest_cancel;
4464
4465         switch (type) {
4466         case DEVLINK_PARAM_TYPE_U8:
4467                 if (nla_put_u8(msg, DEVLINK_ATTR_PARAM_VALUE_DATA, val.vu8))
4468                         goto value_nest_cancel;
4469                 break;
4470         case DEVLINK_PARAM_TYPE_U16:
4471                 if (nla_put_u16(msg, DEVLINK_ATTR_PARAM_VALUE_DATA, val.vu16))
4472                         goto value_nest_cancel;
4473                 break;
4474         case DEVLINK_PARAM_TYPE_U32:
4475                 if (nla_put_u32(msg, DEVLINK_ATTR_PARAM_VALUE_DATA, val.vu32))
4476                         goto value_nest_cancel;
4477                 break;
4478         case DEVLINK_PARAM_TYPE_STRING:
4479                 if (nla_put_string(msg, DEVLINK_ATTR_PARAM_VALUE_DATA,
4480                                    val.vstr))
4481                         goto value_nest_cancel;
4482                 break;
4483         case DEVLINK_PARAM_TYPE_BOOL:
4484                 if (val.vbool &&
4485                     nla_put_flag(msg, DEVLINK_ATTR_PARAM_VALUE_DATA))
4486                         goto value_nest_cancel;
4487                 break;
4488         }
4489
4490         nla_nest_end(msg, param_value_attr);
4491         return 0;
4492
4493 value_nest_cancel:
4494         nla_nest_cancel(msg, param_value_attr);
4495 nla_put_failure:
4496         return -EMSGSIZE;
4497 }
4498
4499 static int devlink_nl_param_fill(struct sk_buff *msg, struct devlink *devlink,
4500                                  unsigned int port_index,
4501                                  struct devlink_param_item *param_item,
4502                                  enum devlink_command cmd,
4503                                  u32 portid, u32 seq, int flags)
4504 {
4505         union devlink_param_value param_value[DEVLINK_PARAM_CMODE_MAX + 1];
4506         bool param_value_set[DEVLINK_PARAM_CMODE_MAX + 1] = {};
4507         const struct devlink_param *param = param_item->param;
4508         struct devlink_param_gset_ctx ctx;
4509         struct nlattr *param_values_list;
4510         struct nlattr *param_attr;
4511         int nla_type;
4512         void *hdr;
4513         int err;
4514         int i;
4515
4516         /* Get value from driver part to driverinit configuration mode */
4517         for (i = 0; i <= DEVLINK_PARAM_CMODE_MAX; i++) {
4518                 if (!devlink_param_cmode_is_supported(param, i))
4519                         continue;
4520                 if (i == DEVLINK_PARAM_CMODE_DRIVERINIT) {
4521                         if (!param_item->driverinit_value_valid)
4522                                 return -EOPNOTSUPP;
4523                         param_value[i] = param_item->driverinit_value;
4524                 } else {
4525                         if (!param_item->published)
4526                                 continue;
4527                         ctx.cmode = i;
4528                         err = devlink_param_get(devlink, param, &ctx);
4529                         if (err)
4530                                 return err;
4531                         param_value[i] = ctx.val;
4532                 }
4533                 param_value_set[i] = true;
4534         }
4535
4536         hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
4537         if (!hdr)
4538                 return -EMSGSIZE;
4539
4540         if (devlink_nl_put_handle(msg, devlink))
4541                 goto genlmsg_cancel;
4542
4543         if (cmd == DEVLINK_CMD_PORT_PARAM_GET ||
4544             cmd == DEVLINK_CMD_PORT_PARAM_NEW ||
4545             cmd == DEVLINK_CMD_PORT_PARAM_DEL)
4546                 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_INDEX, port_index))
4547                         goto genlmsg_cancel;
4548
4549         param_attr = nla_nest_start_noflag(msg, DEVLINK_ATTR_PARAM);
4550         if (!param_attr)
4551                 goto genlmsg_cancel;
4552         if (nla_put_string(msg, DEVLINK_ATTR_PARAM_NAME, param->name))
4553                 goto param_nest_cancel;
4554         if (param->generic && nla_put_flag(msg, DEVLINK_ATTR_PARAM_GENERIC))
4555                 goto param_nest_cancel;
4556
4557         nla_type = devlink_param_type_to_nla_type(param->type);
4558         if (nla_type < 0)
4559                 goto param_nest_cancel;
4560         if (nla_put_u8(msg, DEVLINK_ATTR_PARAM_TYPE, nla_type))
4561                 goto param_nest_cancel;
4562
4563         param_values_list = nla_nest_start_noflag(msg,
4564                                                   DEVLINK_ATTR_PARAM_VALUES_LIST);
4565         if (!param_values_list)
4566                 goto param_nest_cancel;
4567
4568         for (i = 0; i <= DEVLINK_PARAM_CMODE_MAX; i++) {
4569                 if (!param_value_set[i])
4570                         continue;
4571                 err = devlink_nl_param_value_fill_one(msg, param->type,
4572                                                       i, param_value[i]);
4573                 if (err)
4574                         goto values_list_nest_cancel;
4575         }
4576
4577         nla_nest_end(msg, param_values_list);
4578         nla_nest_end(msg, param_attr);
4579         genlmsg_end(msg, hdr);
4580         return 0;
4581
4582 values_list_nest_cancel:
4583         nla_nest_end(msg, param_values_list);
4584 param_nest_cancel:
4585         nla_nest_cancel(msg, param_attr);
4586 genlmsg_cancel:
4587         genlmsg_cancel(msg, hdr);
4588         return -EMSGSIZE;
4589 }
4590
4591 static void devlink_param_notify(struct devlink *devlink,
4592                                  unsigned int port_index,
4593                                  struct devlink_param_item *param_item,
4594                                  enum devlink_command cmd)
4595 {
4596         struct sk_buff *msg;
4597         int err;
4598
4599         WARN_ON(cmd != DEVLINK_CMD_PARAM_NEW && cmd != DEVLINK_CMD_PARAM_DEL &&
4600                 cmd != DEVLINK_CMD_PORT_PARAM_NEW &&
4601                 cmd != DEVLINK_CMD_PORT_PARAM_DEL);
4602
4603         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
4604         if (!msg)
4605                 return;
4606         err = devlink_nl_param_fill(msg, devlink, port_index, param_item, cmd,
4607                                     0, 0, 0);
4608         if (err) {
4609                 nlmsg_free(msg);
4610                 return;
4611         }
4612
4613         genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink),
4614                                 msg, 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
4615 }
4616
4617 static int devlink_nl_cmd_param_get_dumpit(struct sk_buff *msg,
4618                                            struct netlink_callback *cb)
4619 {
4620         struct devlink_param_item *param_item;
4621         struct devlink *devlink;
4622         int start = cb->args[0];
4623         unsigned long index;
4624         int idx = 0;
4625         int err = 0;
4626
4627         mutex_lock(&devlink_mutex);
4628         xa_for_each_marked(&devlinks, index, devlink, DEVLINK_REGISTERED) {
4629                 if (!devlink_try_get(devlink))
4630                         continue;
4631
4632                 if (!net_eq(devlink_net(devlink), sock_net(msg->sk)))
4633                         goto retry;
4634
4635                 mutex_lock(&devlink->lock);
4636                 list_for_each_entry(param_item, &devlink->param_list, list) {
4637                         if (idx < start) {
4638                                 idx++;
4639                                 continue;
4640                         }
4641                         err = devlink_nl_param_fill(msg, devlink, 0, param_item,
4642                                                     DEVLINK_CMD_PARAM_GET,
4643                                                     NETLINK_CB(cb->skb).portid,
4644                                                     cb->nlh->nlmsg_seq,
4645                                                     NLM_F_MULTI);
4646                         if (err == -EOPNOTSUPP) {
4647                                 err = 0;
4648                         } else if (err) {
4649                                 mutex_unlock(&devlink->lock);
4650                                 devlink_put(devlink);
4651                                 goto out;
4652                         }
4653                         idx++;
4654                 }
4655                 mutex_unlock(&devlink->lock);
4656 retry:
4657                 devlink_put(devlink);
4658         }
4659 out:
4660         mutex_unlock(&devlink_mutex);
4661
4662         if (err != -EMSGSIZE)
4663                 return err;
4664
4665         cb->args[0] = idx;
4666         return msg->len;
4667 }
4668
4669 static int
4670 devlink_param_type_get_from_info(struct genl_info *info,
4671                                  enum devlink_param_type *param_type)
4672 {
4673         if (!info->attrs[DEVLINK_ATTR_PARAM_TYPE])
4674                 return -EINVAL;
4675
4676         switch (nla_get_u8(info->attrs[DEVLINK_ATTR_PARAM_TYPE])) {
4677         case NLA_U8:
4678                 *param_type = DEVLINK_PARAM_TYPE_U8;
4679                 break;
4680         case NLA_U16:
4681                 *param_type = DEVLINK_PARAM_TYPE_U16;
4682                 break;
4683         case NLA_U32:
4684                 *param_type = DEVLINK_PARAM_TYPE_U32;
4685                 break;
4686         case NLA_STRING:
4687                 *param_type = DEVLINK_PARAM_TYPE_STRING;
4688                 break;
4689         case NLA_FLAG:
4690                 *param_type = DEVLINK_PARAM_TYPE_BOOL;
4691                 break;
4692         default:
4693                 return -EINVAL;
4694         }
4695
4696         return 0;
4697 }
4698
4699 static int
4700 devlink_param_value_get_from_info(const struct devlink_param *param,
4701                                   struct genl_info *info,
4702                                   union devlink_param_value *value)
4703 {
4704         struct nlattr *param_data;
4705         int len;
4706
4707         param_data = info->attrs[DEVLINK_ATTR_PARAM_VALUE_DATA];
4708
4709         if (param->type != DEVLINK_PARAM_TYPE_BOOL && !param_data)
4710                 return -EINVAL;
4711
4712         switch (param->type) {
4713         case DEVLINK_PARAM_TYPE_U8:
4714                 if (nla_len(param_data) != sizeof(u8))
4715                         return -EINVAL;
4716                 value->vu8 = nla_get_u8(param_data);
4717                 break;
4718         case DEVLINK_PARAM_TYPE_U16:
4719                 if (nla_len(param_data) != sizeof(u16))
4720                         return -EINVAL;
4721                 value->vu16 = nla_get_u16(param_data);
4722                 break;
4723         case DEVLINK_PARAM_TYPE_U32:
4724                 if (nla_len(param_data) != sizeof(u32))
4725                         return -EINVAL;
4726                 value->vu32 = nla_get_u32(param_data);
4727                 break;
4728         case DEVLINK_PARAM_TYPE_STRING:
4729                 len = strnlen(nla_data(param_data), nla_len(param_data));
4730                 if (len == nla_len(param_data) ||
4731                     len >= __DEVLINK_PARAM_MAX_STRING_VALUE)
4732                         return -EINVAL;
4733                 strcpy(value->vstr, nla_data(param_data));
4734                 break;
4735         case DEVLINK_PARAM_TYPE_BOOL:
4736                 if (param_data && nla_len(param_data))
4737                         return -EINVAL;
4738                 value->vbool = nla_get_flag(param_data);
4739                 break;
4740         }
4741         return 0;
4742 }
4743
4744 static struct devlink_param_item *
4745 devlink_param_get_from_info(struct list_head *param_list,
4746                             struct genl_info *info)
4747 {
4748         char *param_name;
4749
4750         if (!info->attrs[DEVLINK_ATTR_PARAM_NAME])
4751                 return NULL;
4752
4753         param_name = nla_data(info->attrs[DEVLINK_ATTR_PARAM_NAME]);
4754         return devlink_param_find_by_name(param_list, param_name);
4755 }
4756
4757 static int devlink_nl_cmd_param_get_doit(struct sk_buff *skb,
4758                                          struct genl_info *info)
4759 {
4760         struct devlink *devlink = info->user_ptr[0];
4761         struct devlink_param_item *param_item;
4762         struct sk_buff *msg;
4763         int err;
4764
4765         param_item = devlink_param_get_from_info(&devlink->param_list, info);
4766         if (!param_item)
4767                 return -EINVAL;
4768
4769         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
4770         if (!msg)
4771                 return -ENOMEM;
4772
4773         err = devlink_nl_param_fill(msg, devlink, 0, param_item,
4774                                     DEVLINK_CMD_PARAM_GET,
4775                                     info->snd_portid, info->snd_seq, 0);
4776         if (err) {
4777                 nlmsg_free(msg);
4778                 return err;
4779         }
4780
4781         return genlmsg_reply(msg, info);
4782 }
4783
4784 static int __devlink_nl_cmd_param_set_doit(struct devlink *devlink,
4785                                            unsigned int port_index,
4786                                            struct list_head *param_list,
4787                                            struct genl_info *info,
4788                                            enum devlink_command cmd)
4789 {
4790         enum devlink_param_type param_type;
4791         struct devlink_param_gset_ctx ctx;
4792         enum devlink_param_cmode cmode;
4793         struct devlink_param_item *param_item;
4794         const struct devlink_param *param;
4795         union devlink_param_value value;
4796         int err = 0;
4797
4798         param_item = devlink_param_get_from_info(param_list, info);
4799         if (!param_item)
4800                 return -EINVAL;
4801         param = param_item->param;
4802         err = devlink_param_type_get_from_info(info, &param_type);
4803         if (err)
4804                 return err;
4805         if (param_type != param->type)
4806                 return -EINVAL;
4807         err = devlink_param_value_get_from_info(param, info, &value);
4808         if (err)
4809                 return err;
4810         if (param->validate) {
4811                 err = param->validate(devlink, param->id, value, info->extack);
4812                 if (err)
4813                         return err;
4814         }
4815
4816         if (!info->attrs[DEVLINK_ATTR_PARAM_VALUE_CMODE])
4817                 return -EINVAL;
4818         cmode = nla_get_u8(info->attrs[DEVLINK_ATTR_PARAM_VALUE_CMODE]);
4819         if (!devlink_param_cmode_is_supported(param, cmode))
4820                 return -EOPNOTSUPP;
4821
4822         if (cmode == DEVLINK_PARAM_CMODE_DRIVERINIT) {
4823                 if (param->type == DEVLINK_PARAM_TYPE_STRING)
4824                         strcpy(param_item->driverinit_value.vstr, value.vstr);
4825                 else
4826                         param_item->driverinit_value = value;
4827                 param_item->driverinit_value_valid = true;
4828         } else {
4829                 if (!param->set)
4830                         return -EOPNOTSUPP;
4831                 ctx.val = value;
4832                 ctx.cmode = cmode;
4833                 err = devlink_param_set(devlink, param, &ctx);
4834                 if (err)
4835                         return err;
4836         }
4837
4838         devlink_param_notify(devlink, port_index, param_item, cmd);
4839         return 0;
4840 }
4841
4842 static int devlink_nl_cmd_param_set_doit(struct sk_buff *skb,
4843                                          struct genl_info *info)
4844 {
4845         struct devlink *devlink = info->user_ptr[0];
4846
4847         return __devlink_nl_cmd_param_set_doit(devlink, 0, &devlink->param_list,
4848                                                info, DEVLINK_CMD_PARAM_NEW);
4849 }
4850
4851 static int devlink_param_register_one(struct devlink *devlink,
4852                                       unsigned int port_index,
4853                                       struct list_head *param_list,
4854                                       const struct devlink_param *param,
4855                                       enum devlink_command cmd)
4856 {
4857         struct devlink_param_item *param_item;
4858
4859         if (devlink_param_find_by_name(param_list, param->name))
4860                 return -EEXIST;
4861
4862         if (param->supported_cmodes == BIT(DEVLINK_PARAM_CMODE_DRIVERINIT))
4863                 WARN_ON(param->get || param->set);
4864         else
4865                 WARN_ON(!param->get || !param->set);
4866
4867         param_item = kzalloc(sizeof(*param_item), GFP_KERNEL);
4868         if (!param_item)
4869                 return -ENOMEM;
4870         param_item->param = param;
4871
4872         list_add_tail(&param_item->list, param_list);
4873         devlink_param_notify(devlink, port_index, param_item, cmd);
4874         return 0;
4875 }
4876
4877 static void devlink_param_unregister_one(struct devlink *devlink,
4878                                          unsigned int port_index,
4879                                          struct list_head *param_list,
4880                                          const struct devlink_param *param,
4881                                          enum devlink_command cmd)
4882 {
4883         struct devlink_param_item *param_item;
4884
4885         param_item = devlink_param_find_by_name(param_list, param->name);
4886         WARN_ON(!param_item);
4887         devlink_param_notify(devlink, port_index, param_item, cmd);
4888         list_del(&param_item->list);
4889         kfree(param_item);
4890 }
4891
4892 static int devlink_nl_cmd_port_param_get_dumpit(struct sk_buff *msg,
4893                                                 struct netlink_callback *cb)
4894 {
4895         struct devlink_param_item *param_item;
4896         struct devlink_port *devlink_port;
4897         struct devlink *devlink;
4898         int start = cb->args[0];
4899         unsigned long index;
4900         int idx = 0;
4901         int err = 0;
4902
4903         mutex_lock(&devlink_mutex);
4904         xa_for_each_marked(&devlinks, index, devlink, DEVLINK_REGISTERED) {
4905                 if (!devlink_try_get(devlink))
4906                         continue;
4907
4908                 if (!net_eq(devlink_net(devlink), sock_net(msg->sk)))
4909                         goto retry;
4910
4911                 mutex_lock(&devlink->lock);
4912                 list_for_each_entry(devlink_port, &devlink->port_list, list) {
4913                         list_for_each_entry(param_item,
4914                                             &devlink_port->param_list, list) {
4915                                 if (idx < start) {
4916                                         idx++;
4917                                         continue;
4918                                 }
4919                                 err = devlink_nl_param_fill(msg,
4920                                                 devlink_port->devlink,
4921                                                 devlink_port->index, param_item,
4922                                                 DEVLINK_CMD_PORT_PARAM_GET,
4923                                                 NETLINK_CB(cb->skb).portid,
4924                                                 cb->nlh->nlmsg_seq,
4925                                                 NLM_F_MULTI);
4926                                 if (err == -EOPNOTSUPP) {
4927                                         err = 0;
4928                                 } else if (err) {
4929                                         mutex_unlock(&devlink->lock);
4930                                         devlink_put(devlink);
4931                                         goto out;
4932                                 }
4933                                 idx++;
4934                         }
4935                 }
4936                 mutex_unlock(&devlink->lock);
4937 retry:
4938                 devlink_put(devlink);
4939         }
4940 out:
4941         mutex_unlock(&devlink_mutex);
4942
4943         if (err != -EMSGSIZE)
4944                 return err;
4945
4946         cb->args[0] = idx;
4947         return msg->len;
4948 }
4949
4950 static int devlink_nl_cmd_port_param_get_doit(struct sk_buff *skb,
4951                                               struct genl_info *info)
4952 {
4953         struct devlink_port *devlink_port = info->user_ptr[1];
4954         struct devlink_param_item *param_item;
4955         struct sk_buff *msg;
4956         int err;
4957
4958         param_item = devlink_param_get_from_info(&devlink_port->param_list,
4959                                                  info);
4960         if (!param_item)
4961                 return -EINVAL;
4962
4963         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
4964         if (!msg)
4965                 return -ENOMEM;
4966
4967         err = devlink_nl_param_fill(msg, devlink_port->devlink,
4968                                     devlink_port->index, param_item,
4969                                     DEVLINK_CMD_PORT_PARAM_GET,
4970                                     info->snd_portid, info->snd_seq, 0);
4971         if (err) {
4972                 nlmsg_free(msg);
4973                 return err;
4974         }
4975
4976         return genlmsg_reply(msg, info);
4977 }
4978
4979 static int devlink_nl_cmd_port_param_set_doit(struct sk_buff *skb,
4980                                               struct genl_info *info)
4981 {
4982         struct devlink_port *devlink_port = info->user_ptr[1];
4983
4984         return __devlink_nl_cmd_param_set_doit(devlink_port->devlink,
4985                                                devlink_port->index,
4986                                                &devlink_port->param_list, info,
4987                                                DEVLINK_CMD_PORT_PARAM_NEW);
4988 }
4989
4990 static int devlink_nl_region_snapshot_id_put(struct sk_buff *msg,
4991                                              struct devlink *devlink,
4992                                              struct devlink_snapshot *snapshot)
4993 {
4994         struct nlattr *snap_attr;
4995         int err;
4996
4997         snap_attr = nla_nest_start_noflag(msg, DEVLINK_ATTR_REGION_SNAPSHOT);
4998         if (!snap_attr)
4999                 return -EINVAL;
5000
5001         err = nla_put_u32(msg, DEVLINK_ATTR_REGION_SNAPSHOT_ID, snapshot->id);
5002         if (err)
5003                 goto nla_put_failure;
5004
5005         nla_nest_end(msg, snap_attr);
5006         return 0;
5007
5008 nla_put_failure:
5009         nla_nest_cancel(msg, snap_attr);
5010         return err;
5011 }
5012
5013 static int devlink_nl_region_snapshots_id_put(struct sk_buff *msg,
5014                                               struct devlink *devlink,
5015                                               struct devlink_region *region)
5016 {
5017         struct devlink_snapshot *snapshot;
5018         struct nlattr *snapshots_attr;
5019         int err;
5020
5021         snapshots_attr = nla_nest_start_noflag(msg,
5022                                                DEVLINK_ATTR_REGION_SNAPSHOTS);
5023         if (!snapshots_attr)
5024                 return -EINVAL;
5025
5026         list_for_each_entry(snapshot, &region->snapshot_list, list) {
5027                 err = devlink_nl_region_snapshot_id_put(msg, devlink, snapshot);
5028                 if (err)
5029                         goto nla_put_failure;
5030         }
5031
5032         nla_nest_end(msg, snapshots_attr);
5033         return 0;
5034
5035 nla_put_failure:
5036         nla_nest_cancel(msg, snapshots_attr);
5037         return err;
5038 }
5039
5040 static int devlink_nl_region_fill(struct sk_buff *msg, struct devlink *devlink,
5041                                   enum devlink_command cmd, u32 portid,
5042                                   u32 seq, int flags,
5043                                   struct devlink_region *region)
5044 {
5045         void *hdr;
5046         int err;
5047
5048         hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
5049         if (!hdr)
5050                 return -EMSGSIZE;
5051
5052         err = devlink_nl_put_handle(msg, devlink);
5053         if (err)
5054                 goto nla_put_failure;
5055
5056         if (region->port) {
5057                 err = nla_put_u32(msg, DEVLINK_ATTR_PORT_INDEX,
5058                                   region->port->index);
5059                 if (err)
5060                         goto nla_put_failure;
5061         }
5062
5063         err = nla_put_string(msg, DEVLINK_ATTR_REGION_NAME, region->ops->name);
5064         if (err)
5065                 goto nla_put_failure;
5066
5067         err = nla_put_u64_64bit(msg, DEVLINK_ATTR_REGION_SIZE,
5068                                 region->size,
5069                                 DEVLINK_ATTR_PAD);
5070         if (err)
5071                 goto nla_put_failure;
5072
5073         err = devlink_nl_region_snapshots_id_put(msg, devlink, region);
5074         if (err)
5075                 goto nla_put_failure;
5076
5077         genlmsg_end(msg, hdr);
5078         return 0;
5079
5080 nla_put_failure:
5081         genlmsg_cancel(msg, hdr);
5082         return err;
5083 }
5084
5085 static struct sk_buff *
5086 devlink_nl_region_notify_build(struct devlink_region *region,
5087                                struct devlink_snapshot *snapshot,
5088                                enum devlink_command cmd, u32 portid, u32 seq)
5089 {
5090         struct devlink *devlink = region->devlink;
5091         struct sk_buff *msg;
5092         void *hdr;
5093         int err;
5094
5095
5096         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
5097         if (!msg)
5098                 return ERR_PTR(-ENOMEM);
5099
5100         hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, 0, cmd);
5101         if (!hdr) {
5102                 err = -EMSGSIZE;
5103                 goto out_free_msg;
5104         }
5105
5106         err = devlink_nl_put_handle(msg, devlink);
5107         if (err)
5108                 goto out_cancel_msg;
5109
5110         if (region->port) {
5111                 err = nla_put_u32(msg, DEVLINK_ATTR_PORT_INDEX,
5112                                   region->port->index);
5113                 if (err)
5114                         goto out_cancel_msg;
5115         }
5116
5117         err = nla_put_string(msg, DEVLINK_ATTR_REGION_NAME,
5118                              region->ops->name);
5119         if (err)
5120                 goto out_cancel_msg;
5121
5122         if (snapshot) {
5123                 err = nla_put_u32(msg, DEVLINK_ATTR_REGION_SNAPSHOT_ID,
5124                                   snapshot->id);
5125                 if (err)
5126                         goto out_cancel_msg;
5127         } else {
5128                 err = nla_put_u64_64bit(msg, DEVLINK_ATTR_REGION_SIZE,
5129                                         region->size, DEVLINK_ATTR_PAD);
5130                 if (err)
5131                         goto out_cancel_msg;
5132         }
5133         genlmsg_end(msg, hdr);
5134
5135         return msg;
5136
5137 out_cancel_msg:
5138         genlmsg_cancel(msg, hdr);
5139 out_free_msg:
5140         nlmsg_free(msg);
5141         return ERR_PTR(err);
5142 }
5143
5144 static void devlink_nl_region_notify(struct devlink_region *region,
5145                                      struct devlink_snapshot *snapshot,
5146                                      enum devlink_command cmd)
5147 {
5148         struct sk_buff *msg;
5149
5150         WARN_ON(cmd != DEVLINK_CMD_REGION_NEW && cmd != DEVLINK_CMD_REGION_DEL);
5151
5152         msg = devlink_nl_region_notify_build(region, snapshot, cmd, 0, 0);
5153         if (IS_ERR(msg))
5154                 return;
5155
5156         genlmsg_multicast_netns(&devlink_nl_family,
5157                                 devlink_net(region->devlink), msg, 0,
5158                                 DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
5159 }
5160
5161 /**
5162  * __devlink_snapshot_id_increment - Increment number of snapshots using an id
5163  *      @devlink: devlink instance
5164  *      @id: the snapshot id
5165  *
5166  *      Track when a new snapshot begins using an id. Load the count for the
5167  *      given id from the snapshot xarray, increment it, and store it back.
5168  *
5169  *      Called when a new snapshot is created with the given id.
5170  *
5171  *      The id *must* have been previously allocated by
5172  *      devlink_region_snapshot_id_get().
5173  *
5174  *      Returns 0 on success, or an error on failure.
5175  */
5176 static int __devlink_snapshot_id_increment(struct devlink *devlink, u32 id)
5177 {
5178         unsigned long count;
5179         void *p;
5180
5181         lockdep_assert_held(&devlink->lock);
5182
5183         p = xa_load(&devlink->snapshot_ids, id);
5184         if (WARN_ON(!p))
5185                 return -EINVAL;
5186
5187         if (WARN_ON(!xa_is_value(p)))
5188                 return -EINVAL;
5189
5190         count = xa_to_value(p);
5191         count++;
5192
5193         return xa_err(xa_store(&devlink->snapshot_ids, id, xa_mk_value(count),
5194                                GFP_KERNEL));
5195 }
5196
5197 /**
5198  * __devlink_snapshot_id_decrement - Decrease number of snapshots using an id
5199  *      @devlink: devlink instance
5200  *      @id: the snapshot id
5201  *
5202  *      Track when a snapshot is deleted and stops using an id. Load the count
5203  *      for the given id from the snapshot xarray, decrement it, and store it
5204  *      back.
5205  *
5206  *      If the count reaches zero, erase this id from the xarray, freeing it
5207  *      up for future re-use by devlink_region_snapshot_id_get().
5208  *
5209  *      Called when a snapshot using the given id is deleted, and when the
5210  *      initial allocator of the id is finished using it.
5211  */
5212 static void __devlink_snapshot_id_decrement(struct devlink *devlink, u32 id)
5213 {
5214         unsigned long count;
5215         void *p;
5216
5217         lockdep_assert_held(&devlink->lock);
5218
5219         p = xa_load(&devlink->snapshot_ids, id);
5220         if (WARN_ON(!p))
5221                 return;
5222
5223         if (WARN_ON(!xa_is_value(p)))
5224                 return;
5225
5226         count = xa_to_value(p);
5227
5228         if (count > 1) {
5229                 count--;
5230                 xa_store(&devlink->snapshot_ids, id, xa_mk_value(count),
5231                          GFP_KERNEL);
5232         } else {
5233                 /* If this was the last user, we can erase this id */
5234                 xa_erase(&devlink->snapshot_ids, id);
5235         }
5236 }
5237
5238 /**
5239  *      __devlink_snapshot_id_insert - Insert a specific snapshot ID
5240  *      @devlink: devlink instance
5241  *      @id: the snapshot id
5242  *
5243  *      Mark the given snapshot id as used by inserting a zero value into the
5244  *      snapshot xarray.
5245  *
5246  *      This must be called while holding the devlink instance lock. Unlike
5247  *      devlink_snapshot_id_get, the initial reference count is zero, not one.
5248  *      It is expected that the id will immediately be used before
5249  *      releasing the devlink instance lock.
5250  *
5251  *      Returns zero on success, or an error code if the snapshot id could not
5252  *      be inserted.
5253  */
5254 static int __devlink_snapshot_id_insert(struct devlink *devlink, u32 id)
5255 {
5256         lockdep_assert_held(&devlink->lock);
5257
5258         if (xa_load(&devlink->snapshot_ids, id))
5259                 return -EEXIST;
5260
5261         return xa_err(xa_store(&devlink->snapshot_ids, id, xa_mk_value(0),
5262                                GFP_KERNEL));
5263 }
5264
5265 /**
5266  *      __devlink_region_snapshot_id_get - get snapshot ID
5267  *      @devlink: devlink instance
5268  *      @id: storage to return snapshot id
5269  *
5270  *      Allocates a new snapshot id. Returns zero on success, or a negative
5271  *      error on failure. Must be called while holding the devlink instance
5272  *      lock.
5273  *
5274  *      Snapshot IDs are tracked using an xarray which stores the number of
5275  *      users of the snapshot id.
5276  *
5277  *      Note that the caller of this function counts as a 'user', in order to
5278  *      avoid race conditions. The caller must release its hold on the
5279  *      snapshot by using devlink_region_snapshot_id_put.
5280  */
5281 static int __devlink_region_snapshot_id_get(struct devlink *devlink, u32 *id)
5282 {
5283         lockdep_assert_held(&devlink->lock);
5284
5285         return xa_alloc(&devlink->snapshot_ids, id, xa_mk_value(1),
5286                         xa_limit_32b, GFP_KERNEL);
5287 }
5288
5289 /**
5290  *      __devlink_region_snapshot_create - create a new snapshot
5291  *      This will add a new snapshot of a region. The snapshot
5292  *      will be stored on the region struct and can be accessed
5293  *      from devlink. This is useful for future analyses of snapshots.
5294  *      Multiple snapshots can be created on a region.
5295  *      The @snapshot_id should be obtained using the getter function.
5296  *
5297  *      Must be called only while holding the devlink instance lock.
5298  *
5299  *      @region: devlink region of the snapshot
5300  *      @data: snapshot data
5301  *      @snapshot_id: snapshot id to be created
5302  */
5303 static int
5304 __devlink_region_snapshot_create(struct devlink_region *region,
5305                                  u8 *data, u32 snapshot_id)
5306 {
5307         struct devlink *devlink = region->devlink;
5308         struct devlink_snapshot *snapshot;
5309         int err;
5310
5311         lockdep_assert_held(&devlink->lock);
5312
5313         /* check if region can hold one more snapshot */
5314         if (region->cur_snapshots == region->max_snapshots)
5315                 return -ENOSPC;
5316
5317         if (devlink_region_snapshot_get_by_id(region, snapshot_id))
5318                 return -EEXIST;
5319
5320         snapshot = kzalloc(sizeof(*snapshot), GFP_KERNEL);
5321         if (!snapshot)
5322                 return -ENOMEM;
5323
5324         err = __devlink_snapshot_id_increment(devlink, snapshot_id);
5325         if (err)
5326                 goto err_snapshot_id_increment;
5327
5328         snapshot->id = snapshot_id;
5329         snapshot->region = region;
5330         snapshot->data = data;
5331
5332         list_add_tail(&snapshot->list, &region->snapshot_list);
5333
5334         region->cur_snapshots++;
5335
5336         devlink_nl_region_notify(region, snapshot, DEVLINK_CMD_REGION_NEW);
5337         return 0;
5338
5339 err_snapshot_id_increment:
5340         kfree(snapshot);
5341         return err;
5342 }
5343
5344 static void devlink_region_snapshot_del(struct devlink_region *region,
5345                                         struct devlink_snapshot *snapshot)
5346 {
5347         struct devlink *devlink = region->devlink;
5348
5349         lockdep_assert_held(&devlink->lock);
5350
5351         devlink_nl_region_notify(region, snapshot, DEVLINK_CMD_REGION_DEL);
5352         region->cur_snapshots--;
5353         list_del(&snapshot->list);
5354         region->ops->destructor(snapshot->data);
5355         __devlink_snapshot_id_decrement(devlink, snapshot->id);
5356         kfree(snapshot);
5357 }
5358
5359 static int devlink_nl_cmd_region_get_doit(struct sk_buff *skb,
5360                                           struct genl_info *info)
5361 {
5362         struct devlink *devlink = info->user_ptr[0];
5363         struct devlink_port *port = NULL;
5364         struct devlink_region *region;
5365         const char *region_name;
5366         struct sk_buff *msg;
5367         unsigned int index;
5368         int err;
5369
5370         if (!info->attrs[DEVLINK_ATTR_REGION_NAME])
5371                 return -EINVAL;
5372
5373         if (info->attrs[DEVLINK_ATTR_PORT_INDEX]) {
5374                 index = nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_INDEX]);
5375
5376                 port = devlink_port_get_by_index(devlink, index);
5377                 if (!port)
5378                         return -ENODEV;
5379         }
5380
5381         region_name = nla_data(info->attrs[DEVLINK_ATTR_REGION_NAME]);
5382         if (port)
5383                 region = devlink_port_region_get_by_name(port, region_name);
5384         else
5385                 region = devlink_region_get_by_name(devlink, region_name);
5386
5387         if (!region)
5388                 return -EINVAL;
5389
5390         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
5391         if (!msg)
5392                 return -ENOMEM;
5393
5394         err = devlink_nl_region_fill(msg, devlink, DEVLINK_CMD_REGION_GET,
5395                                      info->snd_portid, info->snd_seq, 0,
5396                                      region);
5397         if (err) {
5398                 nlmsg_free(msg);
5399                 return err;
5400         }
5401
5402         return genlmsg_reply(msg, info);
5403 }
5404
5405 static int devlink_nl_cmd_region_get_port_dumpit(struct sk_buff *msg,
5406                                                  struct netlink_callback *cb,
5407                                                  struct devlink_port *port,
5408                                                  int *idx,
5409                                                  int start)
5410 {
5411         struct devlink_region *region;
5412         int err = 0;
5413
5414         list_for_each_entry(region, &port->region_list, list) {
5415                 if (*idx < start) {
5416                         (*idx)++;
5417                         continue;
5418                 }
5419                 err = devlink_nl_region_fill(msg, port->devlink,
5420                                              DEVLINK_CMD_REGION_GET,
5421                                              NETLINK_CB(cb->skb).portid,
5422                                              cb->nlh->nlmsg_seq,
5423                                              NLM_F_MULTI, region);
5424                 if (err)
5425                         goto out;
5426                 (*idx)++;
5427         }
5428
5429 out:
5430         return err;
5431 }
5432
5433 static int devlink_nl_cmd_region_get_devlink_dumpit(struct sk_buff *msg,
5434                                                     struct netlink_callback *cb,
5435                                                     struct devlink *devlink,
5436                                                     int *idx,
5437                                                     int start)
5438 {
5439         struct devlink_region *region;
5440         struct devlink_port *port;
5441         int err = 0;
5442
5443         mutex_lock(&devlink->lock);
5444         list_for_each_entry(region, &devlink->region_list, list) {
5445                 if (*idx < start) {
5446                         (*idx)++;
5447                         continue;
5448                 }
5449                 err = devlink_nl_region_fill(msg, devlink,
5450                                              DEVLINK_CMD_REGION_GET,
5451                                              NETLINK_CB(cb->skb).portid,
5452                                              cb->nlh->nlmsg_seq,
5453                                              NLM_F_MULTI, region);
5454                 if (err)
5455                         goto out;
5456                 (*idx)++;
5457         }
5458
5459         list_for_each_entry(port, &devlink->port_list, list) {
5460                 err = devlink_nl_cmd_region_get_port_dumpit(msg, cb, port, idx,
5461                                                             start);
5462                 if (err)
5463                         goto out;
5464         }
5465
5466 out:
5467         mutex_unlock(&devlink->lock);
5468         return err;
5469 }
5470
5471 static int devlink_nl_cmd_region_get_dumpit(struct sk_buff *msg,
5472                                             struct netlink_callback *cb)
5473 {
5474         struct devlink *devlink;
5475         int start = cb->args[0];
5476         unsigned long index;
5477         int idx = 0;
5478         int err = 0;
5479
5480         mutex_lock(&devlink_mutex);
5481         xa_for_each_marked(&devlinks, index, devlink, DEVLINK_REGISTERED) {
5482                 if (!devlink_try_get(devlink))
5483                         continue;
5484
5485                 if (!net_eq(devlink_net(devlink), sock_net(msg->sk)))
5486                         goto retry;
5487
5488                 err = devlink_nl_cmd_region_get_devlink_dumpit(msg, cb, devlink,
5489                                                                &idx, start);
5490 retry:
5491                 devlink_put(devlink);
5492                 if (err)
5493                         goto out;
5494         }
5495 out:
5496         mutex_unlock(&devlink_mutex);
5497         cb->args[0] = idx;
5498         return msg->len;
5499 }
5500
5501 static int devlink_nl_cmd_region_del(struct sk_buff *skb,
5502                                      struct genl_info *info)
5503 {
5504         struct devlink *devlink = info->user_ptr[0];
5505         struct devlink_snapshot *snapshot;
5506         struct devlink_port *port = NULL;
5507         struct devlink_region *region;
5508         const char *region_name;
5509         unsigned int index;
5510         u32 snapshot_id;
5511
5512         if (!info->attrs[DEVLINK_ATTR_REGION_NAME] ||
5513             !info->attrs[DEVLINK_ATTR_REGION_SNAPSHOT_ID])
5514                 return -EINVAL;
5515
5516         region_name = nla_data(info->attrs[DEVLINK_ATTR_REGION_NAME]);
5517         snapshot_id = nla_get_u32(info->attrs[DEVLINK_ATTR_REGION_SNAPSHOT_ID]);
5518
5519         if (info->attrs[DEVLINK_ATTR_PORT_INDEX]) {
5520                 index = nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_INDEX]);
5521
5522                 port = devlink_port_get_by_index(devlink, index);
5523                 if (!port)
5524                         return -ENODEV;
5525         }
5526
5527         if (port)
5528                 region = devlink_port_region_get_by_name(port, region_name);
5529         else
5530                 region = devlink_region_get_by_name(devlink, region_name);
5531
5532         if (!region)
5533                 return -EINVAL;
5534
5535         snapshot = devlink_region_snapshot_get_by_id(region, snapshot_id);
5536         if (!snapshot)
5537                 return -EINVAL;
5538
5539         devlink_region_snapshot_del(region, snapshot);
5540         return 0;
5541 }
5542
5543 static int
5544 devlink_nl_cmd_region_new(struct sk_buff *skb, struct genl_info *info)
5545 {
5546         struct devlink *devlink = info->user_ptr[0];
5547         struct devlink_snapshot *snapshot;
5548         struct devlink_port *port = NULL;
5549         struct nlattr *snapshot_id_attr;
5550         struct devlink_region *region;
5551         const char *region_name;
5552         unsigned int index;
5553         u32 snapshot_id;
5554         u8 *data;
5555         int err;
5556
5557         if (!info->attrs[DEVLINK_ATTR_REGION_NAME]) {
5558                 NL_SET_ERR_MSG_MOD(info->extack, "No region name provided");
5559                 return -EINVAL;
5560         }
5561
5562         region_name = nla_data(info->attrs[DEVLINK_ATTR_REGION_NAME]);
5563
5564         if (info->attrs[DEVLINK_ATTR_PORT_INDEX]) {
5565                 index = nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_INDEX]);
5566
5567                 port = devlink_port_get_by_index(devlink, index);
5568                 if (!port)
5569                         return -ENODEV;
5570         }
5571
5572         if (port)
5573                 region = devlink_port_region_get_by_name(port, region_name);
5574         else
5575                 region = devlink_region_get_by_name(devlink, region_name);
5576
5577         if (!region) {
5578                 NL_SET_ERR_MSG_MOD(info->extack, "The requested region does not exist");
5579                 return -EINVAL;
5580         }
5581
5582         if (!region->ops->snapshot) {
5583                 NL_SET_ERR_MSG_MOD(info->extack, "The requested region does not support taking an immediate snapshot");
5584                 return -EOPNOTSUPP;
5585         }
5586
5587         if (region->cur_snapshots == region->max_snapshots) {
5588                 NL_SET_ERR_MSG_MOD(info->extack, "The region has reached the maximum number of stored snapshots");
5589                 return -ENOSPC;
5590         }
5591
5592         snapshot_id_attr = info->attrs[DEVLINK_ATTR_REGION_SNAPSHOT_ID];
5593         if (snapshot_id_attr) {
5594                 snapshot_id = nla_get_u32(snapshot_id_attr);
5595
5596                 if (devlink_region_snapshot_get_by_id(region, snapshot_id)) {
5597                         NL_SET_ERR_MSG_MOD(info->extack, "The requested snapshot id is already in use");
5598                         return -EEXIST;
5599                 }
5600
5601                 err = __devlink_snapshot_id_insert(devlink, snapshot_id);
5602                 if (err)
5603                         return err;
5604         } else {
5605                 err = __devlink_region_snapshot_id_get(devlink, &snapshot_id);
5606                 if (err) {
5607                         NL_SET_ERR_MSG_MOD(info->extack, "Failed to allocate a new snapshot id");
5608                         return err;
5609                 }
5610         }
5611
5612         if (port)
5613                 err = region->port_ops->snapshot(port, region->port_ops,
5614                                                  info->extack, &data);
5615         else
5616                 err = region->ops->snapshot(devlink, region->ops,
5617                                             info->extack, &data);
5618         if (err)
5619                 goto err_snapshot_capture;
5620
5621         err = __devlink_region_snapshot_create(region, data, snapshot_id);
5622         if (err)
5623                 goto err_snapshot_create;
5624
5625         if (!snapshot_id_attr) {
5626                 struct sk_buff *msg;
5627
5628                 snapshot = devlink_region_snapshot_get_by_id(region,
5629                                                              snapshot_id);
5630                 if (WARN_ON(!snapshot))
5631                         return -EINVAL;
5632
5633                 msg = devlink_nl_region_notify_build(region, snapshot,
5634                                                      DEVLINK_CMD_REGION_NEW,
5635                                                      info->snd_portid,
5636                                                      info->snd_seq);
5637                 err = PTR_ERR_OR_ZERO(msg);
5638                 if (err)
5639                         goto err_notify;
5640
5641                 err = genlmsg_reply(msg, info);
5642                 if (err)
5643                         goto err_notify;
5644         }
5645
5646         return 0;
5647
5648 err_snapshot_create:
5649         region->ops->destructor(data);
5650 err_snapshot_capture:
5651         __devlink_snapshot_id_decrement(devlink, snapshot_id);
5652         return err;
5653
5654 err_notify:
5655         devlink_region_snapshot_del(region, snapshot);
5656         return err;
5657 }
5658
5659 static int devlink_nl_cmd_region_read_chunk_fill(struct sk_buff *msg,
5660                                                  struct devlink *devlink,
5661                                                  u8 *chunk, u32 chunk_size,
5662                                                  u64 addr)
5663 {
5664         struct nlattr *chunk_attr;
5665         int err;
5666
5667         chunk_attr = nla_nest_start_noflag(msg, DEVLINK_ATTR_REGION_CHUNK);
5668         if (!chunk_attr)
5669                 return -EINVAL;
5670
5671         err = nla_put(msg, DEVLINK_ATTR_REGION_CHUNK_DATA, chunk_size, chunk);
5672         if (err)
5673                 goto nla_put_failure;
5674
5675         err = nla_put_u64_64bit(msg, DEVLINK_ATTR_REGION_CHUNK_ADDR, addr,
5676                                 DEVLINK_ATTR_PAD);
5677         if (err)
5678                 goto nla_put_failure;
5679
5680         nla_nest_end(msg, chunk_attr);
5681         return 0;
5682
5683 nla_put_failure:
5684         nla_nest_cancel(msg, chunk_attr);
5685         return err;
5686 }
5687
5688 #define DEVLINK_REGION_READ_CHUNK_SIZE 256
5689
5690 static int devlink_nl_region_read_snapshot_fill(struct sk_buff *skb,
5691                                                 struct devlink *devlink,
5692                                                 struct devlink_region *region,
5693                                                 struct nlattr **attrs,
5694                                                 u64 start_offset,
5695                                                 u64 end_offset,
5696                                                 u64 *new_offset)
5697 {
5698         struct devlink_snapshot *snapshot;
5699         u64 curr_offset = start_offset;
5700         u32 snapshot_id;
5701         int err = 0;
5702
5703         *new_offset = start_offset;
5704
5705         snapshot_id = nla_get_u32(attrs[DEVLINK_ATTR_REGION_SNAPSHOT_ID]);
5706         snapshot = devlink_region_snapshot_get_by_id(region, snapshot_id);
5707         if (!snapshot)
5708                 return -EINVAL;
5709
5710         while (curr_offset < end_offset) {
5711                 u32 data_size;
5712                 u8 *data;
5713
5714                 if (end_offset - curr_offset < DEVLINK_REGION_READ_CHUNK_SIZE)
5715                         data_size = end_offset - curr_offset;
5716                 else
5717                         data_size = DEVLINK_REGION_READ_CHUNK_SIZE;
5718
5719                 data = &snapshot->data[curr_offset];
5720                 err = devlink_nl_cmd_region_read_chunk_fill(skb, devlink,
5721                                                             data, data_size,
5722                                                             curr_offset);
5723                 if (err)
5724                         break;
5725
5726                 curr_offset += data_size;
5727         }
5728         *new_offset = curr_offset;
5729
5730         return err;
5731 }
5732
5733 static int devlink_nl_cmd_region_read_dumpit(struct sk_buff *skb,
5734                                              struct netlink_callback *cb)
5735 {
5736         const struct genl_dumpit_info *info = genl_dumpit_info(cb);
5737         u64 ret_offset, start_offset, end_offset = U64_MAX;
5738         struct nlattr **attrs = info->attrs;
5739         struct devlink_port *port = NULL;
5740         struct devlink_region *region;
5741         struct nlattr *chunks_attr;
5742         const char *region_name;
5743         struct devlink *devlink;
5744         unsigned int index;
5745         void *hdr;
5746         int err;
5747
5748         start_offset = *((u64 *)&cb->args[0]);
5749
5750         mutex_lock(&devlink_mutex);
5751         devlink = devlink_get_from_attrs(sock_net(cb->skb->sk), attrs);
5752         if (IS_ERR(devlink)) {
5753                 err = PTR_ERR(devlink);
5754                 goto out_dev;
5755         }
5756
5757         mutex_lock(&devlink->lock);
5758
5759         if (!attrs[DEVLINK_ATTR_REGION_NAME] ||
5760             !attrs[DEVLINK_ATTR_REGION_SNAPSHOT_ID]) {
5761                 err = -EINVAL;
5762                 goto out_unlock;
5763         }
5764
5765         if (info->attrs[DEVLINK_ATTR_PORT_INDEX]) {
5766                 index = nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_INDEX]);
5767
5768                 port = devlink_port_get_by_index(devlink, index);
5769                 if (!port) {
5770                         err = -ENODEV;
5771                         goto out_unlock;
5772                 }
5773         }
5774
5775         region_name = nla_data(attrs[DEVLINK_ATTR_REGION_NAME]);
5776
5777         if (port)
5778                 region = devlink_port_region_get_by_name(port, region_name);
5779         else
5780                 region = devlink_region_get_by_name(devlink, region_name);
5781
5782         if (!region) {
5783                 err = -EINVAL;
5784                 goto out_unlock;
5785         }
5786
5787         if (attrs[DEVLINK_ATTR_REGION_CHUNK_ADDR] &&
5788             attrs[DEVLINK_ATTR_REGION_CHUNK_LEN]) {
5789                 if (!start_offset)
5790                         start_offset =
5791                                 nla_get_u64(attrs[DEVLINK_ATTR_REGION_CHUNK_ADDR]);
5792
5793                 end_offset = nla_get_u64(attrs[DEVLINK_ATTR_REGION_CHUNK_ADDR]);
5794                 end_offset += nla_get_u64(attrs[DEVLINK_ATTR_REGION_CHUNK_LEN]);
5795         }
5796
5797         if (end_offset > region->size)
5798                 end_offset = region->size;
5799
5800         /* return 0 if there is no further data to read */
5801         if (start_offset == end_offset) {
5802                 err = 0;
5803                 goto out_unlock;
5804         }
5805
5806         hdr = genlmsg_put(skb, NETLINK_CB(cb->skb).portid, cb->nlh->nlmsg_seq,
5807                           &devlink_nl_family, NLM_F_ACK | NLM_F_MULTI,
5808                           DEVLINK_CMD_REGION_READ);
5809         if (!hdr) {
5810                 err = -EMSGSIZE;
5811                 goto out_unlock;
5812         }
5813
5814         err = devlink_nl_put_handle(skb, devlink);
5815         if (err)
5816                 goto nla_put_failure;
5817
5818         if (region->port) {
5819                 err = nla_put_u32(skb, DEVLINK_ATTR_PORT_INDEX,
5820                                   region->port->index);
5821                 if (err)
5822                         goto nla_put_failure;
5823         }
5824
5825         err = nla_put_string(skb, DEVLINK_ATTR_REGION_NAME, region_name);
5826         if (err)
5827                 goto nla_put_failure;
5828
5829         chunks_attr = nla_nest_start_noflag(skb, DEVLINK_ATTR_REGION_CHUNKS);
5830         if (!chunks_attr) {
5831                 err = -EMSGSIZE;
5832                 goto nla_put_failure;
5833         }
5834
5835         err = devlink_nl_region_read_snapshot_fill(skb, devlink,
5836                                                    region, attrs,
5837                                                    start_offset,
5838                                                    end_offset, &ret_offset);
5839
5840         if (err && err != -EMSGSIZE)
5841                 goto nla_put_failure;
5842
5843         /* Check if there was any progress done to prevent infinite loop */
5844         if (ret_offset == start_offset) {
5845                 err = -EINVAL;
5846                 goto nla_put_failure;
5847         }
5848
5849         *((u64 *)&cb->args[0]) = ret_offset;
5850
5851         nla_nest_end(skb, chunks_attr);
5852         genlmsg_end(skb, hdr);
5853         mutex_unlock(&devlink->lock);
5854         devlink_put(devlink);
5855         mutex_unlock(&devlink_mutex);
5856
5857         return skb->len;
5858
5859 nla_put_failure:
5860         genlmsg_cancel(skb, hdr);
5861 out_unlock:
5862         mutex_unlock(&devlink->lock);
5863         devlink_put(devlink);
5864 out_dev:
5865         mutex_unlock(&devlink_mutex);
5866         return err;
5867 }
5868
5869 struct devlink_info_req {
5870         struct sk_buff *msg;
5871 };
5872
5873 int devlink_info_driver_name_put(struct devlink_info_req *req, const char *name)
5874 {
5875         return nla_put_string(req->msg, DEVLINK_ATTR_INFO_DRIVER_NAME, name);
5876 }
5877 EXPORT_SYMBOL_GPL(devlink_info_driver_name_put);
5878
5879 int devlink_info_serial_number_put(struct devlink_info_req *req, const char *sn)
5880 {
5881         return nla_put_string(req->msg, DEVLINK_ATTR_INFO_SERIAL_NUMBER, sn);
5882 }
5883 EXPORT_SYMBOL_GPL(devlink_info_serial_number_put);
5884
5885 int devlink_info_board_serial_number_put(struct devlink_info_req *req,
5886                                          const char *bsn)
5887 {
5888         return nla_put_string(req->msg, DEVLINK_ATTR_INFO_BOARD_SERIAL_NUMBER,
5889                               bsn);
5890 }
5891 EXPORT_SYMBOL_GPL(devlink_info_board_serial_number_put);
5892
5893 static int devlink_info_version_put(struct devlink_info_req *req, int attr,
5894                                     const char *version_name,
5895                                     const char *version_value)
5896 {
5897         struct nlattr *nest;
5898         int err;
5899
5900         nest = nla_nest_start_noflag(req->msg, attr);
5901         if (!nest)
5902                 return -EMSGSIZE;
5903
5904         err = nla_put_string(req->msg, DEVLINK_ATTR_INFO_VERSION_NAME,
5905                              version_name);
5906         if (err)
5907                 goto nla_put_failure;
5908
5909         err = nla_put_string(req->msg, DEVLINK_ATTR_INFO_VERSION_VALUE,
5910                              version_value);
5911         if (err)
5912                 goto nla_put_failure;
5913
5914         nla_nest_end(req->msg, nest);
5915
5916         return 0;
5917
5918 nla_put_failure:
5919         nla_nest_cancel(req->msg, nest);
5920         return err;
5921 }
5922
5923 int devlink_info_version_fixed_put(struct devlink_info_req *req,
5924                                    const char *version_name,
5925                                    const char *version_value)
5926 {
5927         return devlink_info_version_put(req, DEVLINK_ATTR_INFO_VERSION_FIXED,
5928                                         version_name, version_value);
5929 }
5930 EXPORT_SYMBOL_GPL(devlink_info_version_fixed_put);
5931
5932 int devlink_info_version_stored_put(struct devlink_info_req *req,
5933                                     const char *version_name,
5934                                     const char *version_value)
5935 {
5936         return devlink_info_version_put(req, DEVLINK_ATTR_INFO_VERSION_STORED,
5937                                         version_name, version_value);
5938 }
5939 EXPORT_SYMBOL_GPL(devlink_info_version_stored_put);
5940
5941 int devlink_info_version_running_put(struct devlink_info_req *req,
5942                                      const char *version_name,
5943                                      const char *version_value)
5944 {
5945         return devlink_info_version_put(req, DEVLINK_ATTR_INFO_VERSION_RUNNING,
5946                                         version_name, version_value);
5947 }
5948 EXPORT_SYMBOL_GPL(devlink_info_version_running_put);
5949
5950 static int
5951 devlink_nl_info_fill(struct sk_buff *msg, struct devlink *devlink,
5952                      enum devlink_command cmd, u32 portid,
5953                      u32 seq, int flags, struct netlink_ext_ack *extack)
5954 {
5955         struct devlink_info_req req;
5956         void *hdr;
5957         int err;
5958
5959         hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
5960         if (!hdr)
5961                 return -EMSGSIZE;
5962
5963         err = -EMSGSIZE;
5964         if (devlink_nl_put_handle(msg, devlink))
5965                 goto err_cancel_msg;
5966
5967         req.msg = msg;
5968         err = devlink->ops->info_get(devlink, &req, extack);
5969         if (err)
5970                 goto err_cancel_msg;
5971
5972         genlmsg_end(msg, hdr);
5973         return 0;
5974
5975 err_cancel_msg:
5976         genlmsg_cancel(msg, hdr);
5977         return err;
5978 }
5979
5980 static int devlink_nl_cmd_info_get_doit(struct sk_buff *skb,
5981                                         struct genl_info *info)
5982 {
5983         struct devlink *devlink = info->user_ptr[0];
5984         struct sk_buff *msg;
5985         int err;
5986
5987         if (!devlink->ops->info_get)
5988                 return -EOPNOTSUPP;
5989
5990         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
5991         if (!msg)
5992                 return -ENOMEM;
5993
5994         err = devlink_nl_info_fill(msg, devlink, DEVLINK_CMD_INFO_GET,
5995                                    info->snd_portid, info->snd_seq, 0,
5996                                    info->extack);
5997         if (err) {
5998                 nlmsg_free(msg);
5999                 return err;
6000         }
6001
6002         return genlmsg_reply(msg, info);
6003 }
6004
6005 static int devlink_nl_cmd_info_get_dumpit(struct sk_buff *msg,
6006                                           struct netlink_callback *cb)
6007 {
6008         struct devlink *devlink;
6009         int start = cb->args[0];
6010         unsigned long index;
6011         int idx = 0;
6012         int err = 0;
6013
6014         mutex_lock(&devlink_mutex);
6015         xa_for_each_marked(&devlinks, index, devlink, DEVLINK_REGISTERED) {
6016                 if (!devlink_try_get(devlink))
6017                         continue;
6018
6019                 if (!net_eq(devlink_net(devlink), sock_net(msg->sk)))
6020                         goto retry;
6021
6022                 if (idx < start || !devlink->ops->info_get)
6023                         goto inc;
6024
6025                 mutex_lock(&devlink->lock);
6026                 err = devlink_nl_info_fill(msg, devlink, DEVLINK_CMD_INFO_GET,
6027                                            NETLINK_CB(cb->skb).portid,
6028                                            cb->nlh->nlmsg_seq, NLM_F_MULTI,
6029                                            cb->extack);
6030                 mutex_unlock(&devlink->lock);
6031                 if (err == -EOPNOTSUPP)
6032                         err = 0;
6033                 else if (err) {
6034                         devlink_put(devlink);
6035                         break;
6036                 }
6037 inc:
6038                 idx++;
6039 retry:
6040                 devlink_put(devlink);
6041         }
6042         mutex_unlock(&devlink_mutex);
6043
6044         if (err != -EMSGSIZE)
6045                 return err;
6046
6047         cb->args[0] = idx;
6048         return msg->len;
6049 }
6050
6051 struct devlink_fmsg_item {
6052         struct list_head list;
6053         int attrtype;
6054         u8 nla_type;
6055         u16 len;
6056         int value[];
6057 };
6058
6059 struct devlink_fmsg {
6060         struct list_head item_list;
6061         bool putting_binary; /* This flag forces enclosing of binary data
6062                               * in an array brackets. It forces using
6063                               * of designated API:
6064                               * devlink_fmsg_binary_pair_nest_start()
6065                               * devlink_fmsg_binary_pair_nest_end()
6066                               */
6067 };
6068
6069 static struct devlink_fmsg *devlink_fmsg_alloc(void)
6070 {
6071         struct devlink_fmsg *fmsg;
6072
6073         fmsg = kzalloc(sizeof(*fmsg), GFP_KERNEL);
6074         if (!fmsg)
6075                 return NULL;
6076
6077         INIT_LIST_HEAD(&fmsg->item_list);
6078
6079         return fmsg;
6080 }
6081
6082 static void devlink_fmsg_free(struct devlink_fmsg *fmsg)
6083 {
6084         struct devlink_fmsg_item *item, *tmp;
6085
6086         list_for_each_entry_safe(item, tmp, &fmsg->item_list, list) {
6087                 list_del(&item->list);
6088                 kfree(item);
6089         }
6090         kfree(fmsg);
6091 }
6092
6093 static int devlink_fmsg_nest_common(struct devlink_fmsg *fmsg,
6094                                     int attrtype)
6095 {
6096         struct devlink_fmsg_item *item;
6097
6098         item = kzalloc(sizeof(*item), GFP_KERNEL);
6099         if (!item)
6100                 return -ENOMEM;
6101
6102         item->attrtype = attrtype;
6103         list_add_tail(&item->list, &fmsg->item_list);
6104
6105         return 0;
6106 }
6107
6108 int devlink_fmsg_obj_nest_start(struct devlink_fmsg *fmsg)
6109 {
6110         if (fmsg->putting_binary)
6111                 return -EINVAL;
6112
6113         return devlink_fmsg_nest_common(fmsg, DEVLINK_ATTR_FMSG_OBJ_NEST_START);
6114 }
6115 EXPORT_SYMBOL_GPL(devlink_fmsg_obj_nest_start);
6116
6117 static int devlink_fmsg_nest_end(struct devlink_fmsg *fmsg)
6118 {
6119         if (fmsg->putting_binary)
6120                 return -EINVAL;
6121
6122         return devlink_fmsg_nest_common(fmsg, DEVLINK_ATTR_FMSG_NEST_END);
6123 }
6124
6125 int devlink_fmsg_obj_nest_end(struct devlink_fmsg *fmsg)
6126 {
6127         if (fmsg->putting_binary)
6128                 return -EINVAL;
6129
6130         return devlink_fmsg_nest_end(fmsg);
6131 }
6132 EXPORT_SYMBOL_GPL(devlink_fmsg_obj_nest_end);
6133
6134 #define DEVLINK_FMSG_MAX_SIZE (GENLMSG_DEFAULT_SIZE - GENL_HDRLEN - NLA_HDRLEN)
6135
6136 static int devlink_fmsg_put_name(struct devlink_fmsg *fmsg, const char *name)
6137 {
6138         struct devlink_fmsg_item *item;
6139
6140         if (fmsg->putting_binary)
6141                 return -EINVAL;
6142
6143         if (strlen(name) + 1 > DEVLINK_FMSG_MAX_SIZE)
6144                 return -EMSGSIZE;
6145
6146         item = kzalloc(sizeof(*item) + strlen(name) + 1, GFP_KERNEL);
6147         if (!item)
6148                 return -ENOMEM;
6149
6150         item->nla_type = NLA_NUL_STRING;
6151         item->len = strlen(name) + 1;
6152         item->attrtype = DEVLINK_ATTR_FMSG_OBJ_NAME;
6153         memcpy(&item->value, name, item->len);
6154         list_add_tail(&item->list, &fmsg->item_list);
6155
6156         return 0;
6157 }
6158
6159 int devlink_fmsg_pair_nest_start(struct devlink_fmsg *fmsg, const char *name)
6160 {
6161         int err;
6162
6163         if (fmsg->putting_binary)
6164                 return -EINVAL;
6165
6166         err = devlink_fmsg_nest_common(fmsg, DEVLINK_ATTR_FMSG_PAIR_NEST_START);
6167         if (err)
6168                 return err;
6169
6170         err = devlink_fmsg_put_name(fmsg, name);
6171         if (err)
6172                 return err;
6173
6174         return 0;
6175 }
6176 EXPORT_SYMBOL_GPL(devlink_fmsg_pair_nest_start);
6177
6178 int devlink_fmsg_pair_nest_end(struct devlink_fmsg *fmsg)
6179 {
6180         if (fmsg->putting_binary)
6181                 return -EINVAL;
6182
6183         return devlink_fmsg_nest_end(fmsg);
6184 }
6185 EXPORT_SYMBOL_GPL(devlink_fmsg_pair_nest_end);
6186
6187 int devlink_fmsg_arr_pair_nest_start(struct devlink_fmsg *fmsg,
6188                                      const char *name)
6189 {
6190         int err;
6191
6192         if (fmsg->putting_binary)
6193                 return -EINVAL;
6194
6195         err = devlink_fmsg_pair_nest_start(fmsg, name);
6196         if (err)
6197                 return err;
6198
6199         err = devlink_fmsg_nest_common(fmsg, DEVLINK_ATTR_FMSG_ARR_NEST_START);
6200         if (err)
6201                 return err;
6202
6203         return 0;
6204 }
6205 EXPORT_SYMBOL_GPL(devlink_fmsg_arr_pair_nest_start);
6206
6207 int devlink_fmsg_arr_pair_nest_end(struct devlink_fmsg *fmsg)
6208 {
6209         int err;
6210
6211         if (fmsg->putting_binary)
6212                 return -EINVAL;
6213
6214         err = devlink_fmsg_nest_end(fmsg);
6215         if (err)
6216                 return err;
6217
6218         err = devlink_fmsg_nest_end(fmsg);
6219         if (err)
6220                 return err;
6221
6222         return 0;
6223 }
6224 EXPORT_SYMBOL_GPL(devlink_fmsg_arr_pair_nest_end);
6225
6226 int devlink_fmsg_binary_pair_nest_start(struct devlink_fmsg *fmsg,
6227                                         const char *name)
6228 {
6229         int err;
6230
6231         err = devlink_fmsg_arr_pair_nest_start(fmsg, name);
6232         if (err)
6233                 return err;
6234
6235         fmsg->putting_binary = true;
6236         return err;
6237 }
6238 EXPORT_SYMBOL_GPL(devlink_fmsg_binary_pair_nest_start);
6239
6240 int devlink_fmsg_binary_pair_nest_end(struct devlink_fmsg *fmsg)
6241 {
6242         if (!fmsg->putting_binary)
6243                 return -EINVAL;
6244
6245         fmsg->putting_binary = false;
6246         return devlink_fmsg_arr_pair_nest_end(fmsg);
6247 }
6248 EXPORT_SYMBOL_GPL(devlink_fmsg_binary_pair_nest_end);
6249
6250 static int devlink_fmsg_put_value(struct devlink_fmsg *fmsg,
6251                                   const void *value, u16 value_len,
6252                                   u8 value_nla_type)
6253 {
6254         struct devlink_fmsg_item *item;
6255
6256         if (value_len > DEVLINK_FMSG_MAX_SIZE)
6257                 return -EMSGSIZE;
6258
6259         item = kzalloc(sizeof(*item) + value_len, GFP_KERNEL);
6260         if (!item)
6261                 return -ENOMEM;
6262
6263         item->nla_type = value_nla_type;
6264         item->len = value_len;
6265         item->attrtype = DEVLINK_ATTR_FMSG_OBJ_VALUE_DATA;
6266         memcpy(&item->value, value, item->len);
6267         list_add_tail(&item->list, &fmsg->item_list);
6268
6269         return 0;
6270 }
6271
6272 int devlink_fmsg_bool_put(struct devlink_fmsg *fmsg, bool value)
6273 {
6274         if (fmsg->putting_binary)
6275                 return -EINVAL;
6276
6277         return devlink_fmsg_put_value(fmsg, &value, sizeof(value), NLA_FLAG);
6278 }
6279 EXPORT_SYMBOL_GPL(devlink_fmsg_bool_put);
6280
6281 int devlink_fmsg_u8_put(struct devlink_fmsg *fmsg, u8 value)
6282 {
6283         if (fmsg->putting_binary)
6284                 return -EINVAL;
6285
6286         return devlink_fmsg_put_value(fmsg, &value, sizeof(value), NLA_U8);
6287 }
6288 EXPORT_SYMBOL_GPL(devlink_fmsg_u8_put);
6289
6290 int devlink_fmsg_u32_put(struct devlink_fmsg *fmsg, u32 value)
6291 {
6292         if (fmsg->putting_binary)
6293                 return -EINVAL;
6294
6295         return devlink_fmsg_put_value(fmsg, &value, sizeof(value), NLA_U32);
6296 }
6297 EXPORT_SYMBOL_GPL(devlink_fmsg_u32_put);
6298
6299 int devlink_fmsg_u64_put(struct devlink_fmsg *fmsg, u64 value)
6300 {
6301         if (fmsg->putting_binary)
6302                 return -EINVAL;
6303
6304         return devlink_fmsg_put_value(fmsg, &value, sizeof(value), NLA_U64);
6305 }
6306 EXPORT_SYMBOL_GPL(devlink_fmsg_u64_put);
6307
6308 int devlink_fmsg_string_put(struct devlink_fmsg *fmsg, const char *value)
6309 {
6310         if (fmsg->putting_binary)
6311                 return -EINVAL;
6312
6313         return devlink_fmsg_put_value(fmsg, value, strlen(value) + 1,
6314                                       NLA_NUL_STRING);
6315 }
6316 EXPORT_SYMBOL_GPL(devlink_fmsg_string_put);
6317
6318 int devlink_fmsg_binary_put(struct devlink_fmsg *fmsg, const void *value,
6319                             u16 value_len)
6320 {
6321         if (!fmsg->putting_binary)
6322                 return -EINVAL;
6323
6324         return devlink_fmsg_put_value(fmsg, value, value_len, NLA_BINARY);
6325 }
6326 EXPORT_SYMBOL_GPL(devlink_fmsg_binary_put);
6327
6328 int devlink_fmsg_bool_pair_put(struct devlink_fmsg *fmsg, const char *name,
6329                                bool value)
6330 {
6331         int err;
6332
6333         err = devlink_fmsg_pair_nest_start(fmsg, name);
6334         if (err)
6335                 return err;
6336
6337         err = devlink_fmsg_bool_put(fmsg, value);
6338         if (err)
6339                 return err;
6340
6341         err = devlink_fmsg_pair_nest_end(fmsg);
6342         if (err)
6343                 return err;
6344
6345         return 0;
6346 }
6347 EXPORT_SYMBOL_GPL(devlink_fmsg_bool_pair_put);
6348
6349 int devlink_fmsg_u8_pair_put(struct devlink_fmsg *fmsg, const char *name,
6350                              u8 value)
6351 {
6352         int err;
6353
6354         err = devlink_fmsg_pair_nest_start(fmsg, name);
6355         if (err)
6356                 return err;
6357
6358         err = devlink_fmsg_u8_put(fmsg, value);
6359         if (err)
6360                 return err;
6361
6362         err = devlink_fmsg_pair_nest_end(fmsg);
6363         if (err)
6364                 return err;
6365
6366         return 0;
6367 }
6368 EXPORT_SYMBOL_GPL(devlink_fmsg_u8_pair_put);
6369
6370 int devlink_fmsg_u32_pair_put(struct devlink_fmsg *fmsg, const char *name,
6371                               u32 value)
6372 {
6373         int err;
6374
6375         err = devlink_fmsg_pair_nest_start(fmsg, name);
6376         if (err)
6377                 return err;
6378
6379         err = devlink_fmsg_u32_put(fmsg, value);
6380         if (err)
6381                 return err;
6382
6383         err = devlink_fmsg_pair_nest_end(fmsg);
6384         if (err)
6385                 return err;
6386
6387         return 0;
6388 }
6389 EXPORT_SYMBOL_GPL(devlink_fmsg_u32_pair_put);
6390
6391 int devlink_fmsg_u64_pair_put(struct devlink_fmsg *fmsg, const char *name,
6392                               u64 value)
6393 {
6394         int err;
6395
6396         err = devlink_fmsg_pair_nest_start(fmsg, name);
6397         if (err)
6398                 return err;
6399
6400         err = devlink_fmsg_u64_put(fmsg, value);
6401         if (err)
6402                 return err;
6403
6404         err = devlink_fmsg_pair_nest_end(fmsg);
6405         if (err)
6406                 return err;
6407
6408         return 0;
6409 }
6410 EXPORT_SYMBOL_GPL(devlink_fmsg_u64_pair_put);
6411
6412 int devlink_fmsg_string_pair_put(struct devlink_fmsg *fmsg, const char *name,
6413                                  const char *value)
6414 {
6415         int err;
6416
6417         err = devlink_fmsg_pair_nest_start(fmsg, name);
6418         if (err)
6419                 return err;
6420
6421         err = devlink_fmsg_string_put(fmsg, value);
6422         if (err)
6423                 return err;
6424
6425         err = devlink_fmsg_pair_nest_end(fmsg);
6426         if (err)
6427                 return err;
6428
6429         return 0;
6430 }
6431 EXPORT_SYMBOL_GPL(devlink_fmsg_string_pair_put);
6432
6433 int devlink_fmsg_binary_pair_put(struct devlink_fmsg *fmsg, const char *name,
6434                                  const void *value, u32 value_len)
6435 {
6436         u32 data_size;
6437         int end_err;
6438         u32 offset;
6439         int err;
6440
6441         err = devlink_fmsg_binary_pair_nest_start(fmsg, name);
6442         if (err)
6443                 return err;
6444
6445         for (offset = 0; offset < value_len; offset += data_size) {
6446                 data_size = value_len - offset;
6447                 if (data_size > DEVLINK_FMSG_MAX_SIZE)
6448                         data_size = DEVLINK_FMSG_MAX_SIZE;
6449                 err = devlink_fmsg_binary_put(fmsg, value + offset, data_size);
6450                 if (err)
6451                         break;
6452                 /* Exit from loop with a break (instead of
6453                  * return) to make sure putting_binary is turned off in
6454                  * devlink_fmsg_binary_pair_nest_end
6455                  */
6456         }
6457
6458         end_err = devlink_fmsg_binary_pair_nest_end(fmsg);
6459         if (end_err)
6460                 err = end_err;
6461
6462         return err;
6463 }
6464 EXPORT_SYMBOL_GPL(devlink_fmsg_binary_pair_put);
6465
6466 static int
6467 devlink_fmsg_item_fill_type(struct devlink_fmsg_item *msg, struct sk_buff *skb)
6468 {
6469         switch (msg->nla_type) {
6470         case NLA_FLAG:
6471         case NLA_U8:
6472         case NLA_U32:
6473         case NLA_U64:
6474         case NLA_NUL_STRING:
6475         case NLA_BINARY:
6476                 return nla_put_u8(skb, DEVLINK_ATTR_FMSG_OBJ_VALUE_TYPE,
6477                                   msg->nla_type);
6478         default:
6479                 return -EINVAL;
6480         }
6481 }
6482
6483 static int
6484 devlink_fmsg_item_fill_data(struct devlink_fmsg_item *msg, struct sk_buff *skb)
6485 {
6486         int attrtype = DEVLINK_ATTR_FMSG_OBJ_VALUE_DATA;
6487         u8 tmp;
6488
6489         switch (msg->nla_type) {
6490         case NLA_FLAG:
6491                 /* Always provide flag data, regardless of its value */
6492                 tmp = *(bool *) msg->value;
6493
6494                 return nla_put_u8(skb, attrtype, tmp);
6495         case NLA_U8:
6496                 return nla_put_u8(skb, attrtype, *(u8 *) msg->value);
6497         case NLA_U32:
6498                 return nla_put_u32(skb, attrtype, *(u32 *) msg->value);
6499         case NLA_U64:
6500                 return nla_put_u64_64bit(skb, attrtype, *(u64 *) msg->value,
6501                                          DEVLINK_ATTR_PAD);
6502         case NLA_NUL_STRING:
6503                 return nla_put_string(skb, attrtype, (char *) &msg->value);
6504         case NLA_BINARY:
6505                 return nla_put(skb, attrtype, msg->len, (void *) &msg->value);
6506         default:
6507                 return -EINVAL;
6508         }
6509 }
6510
6511 static int
6512 devlink_fmsg_prepare_skb(struct devlink_fmsg *fmsg, struct sk_buff *skb,
6513                          int *start)
6514 {
6515         struct devlink_fmsg_item *item;
6516         struct nlattr *fmsg_nlattr;
6517         int i = 0;
6518         int err;
6519
6520         fmsg_nlattr = nla_nest_start_noflag(skb, DEVLINK_ATTR_FMSG);
6521         if (!fmsg_nlattr)
6522                 return -EMSGSIZE;
6523
6524         list_for_each_entry(item, &fmsg->item_list, list) {
6525                 if (i < *start) {
6526                         i++;
6527                         continue;
6528                 }
6529
6530                 switch (item->attrtype) {
6531                 case DEVLINK_ATTR_FMSG_OBJ_NEST_START:
6532                 case DEVLINK_ATTR_FMSG_PAIR_NEST_START:
6533                 case DEVLINK_ATTR_FMSG_ARR_NEST_START:
6534                 case DEVLINK_ATTR_FMSG_NEST_END:
6535                         err = nla_put_flag(skb, item->attrtype);
6536                         break;
6537                 case DEVLINK_ATTR_FMSG_OBJ_VALUE_DATA:
6538                         err = devlink_fmsg_item_fill_type(item, skb);
6539                         if (err)
6540                                 break;
6541                         err = devlink_fmsg_item_fill_data(item, skb);
6542                         break;
6543                 case DEVLINK_ATTR_FMSG_OBJ_NAME:
6544                         err = nla_put_string(skb, item->attrtype,
6545                                              (char *) &item->value);
6546                         break;
6547                 default:
6548                         err = -EINVAL;
6549                         break;
6550                 }
6551                 if (!err)
6552                         *start = ++i;
6553                 else
6554                         break;
6555         }
6556
6557         nla_nest_end(skb, fmsg_nlattr);
6558         return err;
6559 }
6560
6561 static int devlink_fmsg_snd(struct devlink_fmsg *fmsg,
6562                             struct genl_info *info,
6563                             enum devlink_command cmd, int flags)
6564 {
6565         struct nlmsghdr *nlh;
6566         struct sk_buff *skb;
6567         bool last = false;
6568         int index = 0;
6569         void *hdr;
6570         int err;
6571
6572         while (!last) {
6573                 int tmp_index = index;
6574
6575                 skb = genlmsg_new(GENLMSG_DEFAULT_SIZE, GFP_KERNEL);
6576                 if (!skb)
6577                         return -ENOMEM;
6578
6579                 hdr = genlmsg_put(skb, info->snd_portid, info->snd_seq,
6580                                   &devlink_nl_family, flags | NLM_F_MULTI, cmd);
6581                 if (!hdr) {
6582                         err = -EMSGSIZE;
6583                         goto nla_put_failure;
6584                 }
6585
6586                 err = devlink_fmsg_prepare_skb(fmsg, skb, &index);
6587                 if (!err)
6588                         last = true;
6589                 else if (err != -EMSGSIZE || tmp_index == index)
6590                         goto nla_put_failure;
6591
6592                 genlmsg_end(skb, hdr);
6593                 err = genlmsg_reply(skb, info);
6594                 if (err)
6595                         return err;
6596         }
6597
6598         skb = genlmsg_new(GENLMSG_DEFAULT_SIZE, GFP_KERNEL);
6599         if (!skb)
6600                 return -ENOMEM;
6601         nlh = nlmsg_put(skb, info->snd_portid, info->snd_seq,
6602                         NLMSG_DONE, 0, flags | NLM_F_MULTI);
6603         if (!nlh) {
6604                 err = -EMSGSIZE;
6605                 goto nla_put_failure;
6606         }
6607
6608         return genlmsg_reply(skb, info);
6609
6610 nla_put_failure:
6611         nlmsg_free(skb);
6612         return err;
6613 }
6614
6615 static int devlink_fmsg_dumpit(struct devlink_fmsg *fmsg, struct sk_buff *skb,
6616                                struct netlink_callback *cb,
6617                                enum devlink_command cmd)
6618 {
6619         int index = cb->args[0];
6620         int tmp_index = index;
6621         void *hdr;
6622         int err;
6623
6624         hdr = genlmsg_put(skb, NETLINK_CB(cb->skb).portid, cb->nlh->nlmsg_seq,
6625                           &devlink_nl_family, NLM_F_ACK | NLM_F_MULTI, cmd);
6626         if (!hdr) {
6627                 err = -EMSGSIZE;
6628                 goto nla_put_failure;
6629         }
6630
6631         err = devlink_fmsg_prepare_skb(fmsg, skb, &index);
6632         if ((err && err != -EMSGSIZE) || tmp_index == index)
6633                 goto nla_put_failure;
6634
6635         cb->args[0] = index;
6636         genlmsg_end(skb, hdr);
6637         return skb->len;
6638
6639 nla_put_failure:
6640         genlmsg_cancel(skb, hdr);
6641         return err;
6642 }
6643
6644 struct devlink_health_reporter {
6645         struct list_head list;
6646         void *priv;
6647         const struct devlink_health_reporter_ops *ops;
6648         struct devlink *devlink;
6649         struct devlink_port *devlink_port;
6650         struct devlink_fmsg *dump_fmsg;
6651         struct mutex dump_lock; /* lock parallel read/write from dump buffers */
6652         u64 graceful_period;
6653         bool auto_recover;
6654         bool auto_dump;
6655         u8 health_state;
6656         u64 dump_ts;
6657         u64 dump_real_ts;
6658         u64 error_count;
6659         u64 recovery_count;
6660         u64 last_recovery_ts;
6661         refcount_t refcount;
6662 };
6663
6664 void *
6665 devlink_health_reporter_priv(struct devlink_health_reporter *reporter)
6666 {
6667         return reporter->priv;
6668 }
6669 EXPORT_SYMBOL_GPL(devlink_health_reporter_priv);
6670
6671 static struct devlink_health_reporter *
6672 __devlink_health_reporter_find_by_name(struct list_head *reporter_list,
6673                                        struct mutex *list_lock,
6674                                        const char *reporter_name)
6675 {
6676         struct devlink_health_reporter *reporter;
6677
6678         lockdep_assert_held(list_lock);
6679         list_for_each_entry(reporter, reporter_list, list)
6680                 if (!strcmp(reporter->ops->name, reporter_name))
6681                         return reporter;
6682         return NULL;
6683 }
6684
6685 static struct devlink_health_reporter *
6686 devlink_health_reporter_find_by_name(struct devlink *devlink,
6687                                      const char *reporter_name)
6688 {
6689         return __devlink_health_reporter_find_by_name(&devlink->reporter_list,
6690                                                       &devlink->reporters_lock,
6691                                                       reporter_name);
6692 }
6693
6694 static struct devlink_health_reporter *
6695 devlink_port_health_reporter_find_by_name(struct devlink_port *devlink_port,
6696                                           const char *reporter_name)
6697 {
6698         return __devlink_health_reporter_find_by_name(&devlink_port->reporter_list,
6699                                                       &devlink_port->reporters_lock,
6700                                                       reporter_name);
6701 }
6702
6703 static struct devlink_health_reporter *
6704 __devlink_health_reporter_create(struct devlink *devlink,
6705                                  const struct devlink_health_reporter_ops *ops,
6706                                  u64 graceful_period, void *priv)
6707 {
6708         struct devlink_health_reporter *reporter;
6709
6710         if (WARN_ON(graceful_period && !ops->recover))
6711                 return ERR_PTR(-EINVAL);
6712
6713         reporter = kzalloc(sizeof(*reporter), GFP_KERNEL);
6714         if (!reporter)
6715                 return ERR_PTR(-ENOMEM);
6716
6717         reporter->priv = priv;
6718         reporter->ops = ops;
6719         reporter->devlink = devlink;
6720         reporter->graceful_period = graceful_period;
6721         reporter->auto_recover = !!ops->recover;
6722         reporter->auto_dump = !!ops->dump;
6723         mutex_init(&reporter->dump_lock);
6724         refcount_set(&reporter->refcount, 1);
6725         return reporter;
6726 }
6727
6728 /**
6729  *      devlink_port_health_reporter_create - create devlink health reporter for
6730  *                                            specified port instance
6731  *
6732  *      @port: devlink_port which should contain the new reporter
6733  *      @ops: ops
6734  *      @graceful_period: to avoid recovery loops, in msecs
6735  *      @priv: priv
6736  */
6737 struct devlink_health_reporter *
6738 devlink_port_health_reporter_create(struct devlink_port *port,
6739                                     const struct devlink_health_reporter_ops *ops,
6740                                     u64 graceful_period, void *priv)
6741 {
6742         struct devlink_health_reporter *reporter;
6743
6744         mutex_lock(&port->reporters_lock);
6745         if (__devlink_health_reporter_find_by_name(&port->reporter_list,
6746                                                    &port->reporters_lock, ops->name)) {
6747                 reporter = ERR_PTR(-EEXIST);
6748                 goto unlock;
6749         }
6750
6751         reporter = __devlink_health_reporter_create(port->devlink, ops,
6752                                                     graceful_period, priv);
6753         if (IS_ERR(reporter))
6754                 goto unlock;
6755
6756         reporter->devlink_port = port;
6757         list_add_tail(&reporter->list, &port->reporter_list);
6758 unlock:
6759         mutex_unlock(&port->reporters_lock);
6760         return reporter;
6761 }
6762 EXPORT_SYMBOL_GPL(devlink_port_health_reporter_create);
6763
6764 /**
6765  *      devlink_health_reporter_create - create devlink health reporter
6766  *
6767  *      @devlink: devlink
6768  *      @ops: ops
6769  *      @graceful_period: to avoid recovery loops, in msecs
6770  *      @priv: priv
6771  */
6772 struct devlink_health_reporter *
6773 devlink_health_reporter_create(struct devlink *devlink,
6774                                const struct devlink_health_reporter_ops *ops,
6775                                u64 graceful_period, void *priv)
6776 {
6777         struct devlink_health_reporter *reporter;
6778
6779         mutex_lock(&devlink->reporters_lock);
6780         if (devlink_health_reporter_find_by_name(devlink, ops->name)) {
6781                 reporter = ERR_PTR(-EEXIST);
6782                 goto unlock;
6783         }
6784
6785         reporter = __devlink_health_reporter_create(devlink, ops,
6786                                                     graceful_period, priv);
6787         if (IS_ERR(reporter))
6788                 goto unlock;
6789
6790         list_add_tail(&reporter->list, &devlink->reporter_list);
6791 unlock:
6792         mutex_unlock(&devlink->reporters_lock);
6793         return reporter;
6794 }
6795 EXPORT_SYMBOL_GPL(devlink_health_reporter_create);
6796
6797 static void
6798 devlink_health_reporter_free(struct devlink_health_reporter *reporter)
6799 {
6800         mutex_destroy(&reporter->dump_lock);
6801         if (reporter->dump_fmsg)
6802                 devlink_fmsg_free(reporter->dump_fmsg);
6803         kfree(reporter);
6804 }
6805
6806 static void
6807 devlink_health_reporter_put(struct devlink_health_reporter *reporter)
6808 {
6809         if (refcount_dec_and_test(&reporter->refcount))
6810                 devlink_health_reporter_free(reporter);
6811 }
6812
6813 static void
6814 __devlink_health_reporter_destroy(struct devlink_health_reporter *reporter)
6815 {
6816         list_del(&reporter->list);
6817         devlink_health_reporter_put(reporter);
6818 }
6819
6820 /**
6821  *      devlink_health_reporter_destroy - destroy devlink health reporter
6822  *
6823  *      @reporter: devlink health reporter to destroy
6824  */
6825 void
6826 devlink_health_reporter_destroy(struct devlink_health_reporter *reporter)
6827 {
6828         struct mutex *lock = &reporter->devlink->reporters_lock;
6829
6830         mutex_lock(lock);
6831         __devlink_health_reporter_destroy(reporter);
6832         mutex_unlock(lock);
6833 }
6834 EXPORT_SYMBOL_GPL(devlink_health_reporter_destroy);
6835
6836 /**
6837  *      devlink_port_health_reporter_destroy - destroy devlink port health reporter
6838  *
6839  *      @reporter: devlink health reporter to destroy
6840  */
6841 void
6842 devlink_port_health_reporter_destroy(struct devlink_health_reporter *reporter)
6843 {
6844         struct mutex *lock = &reporter->devlink_port->reporters_lock;
6845
6846         mutex_lock(lock);
6847         __devlink_health_reporter_destroy(reporter);
6848         mutex_unlock(lock);
6849 }
6850 EXPORT_SYMBOL_GPL(devlink_port_health_reporter_destroy);
6851
6852 static int
6853 devlink_nl_health_reporter_fill(struct sk_buff *msg,
6854                                 struct devlink_health_reporter *reporter,
6855                                 enum devlink_command cmd, u32 portid,
6856                                 u32 seq, int flags)
6857 {
6858         struct devlink *devlink = reporter->devlink;
6859         struct nlattr *reporter_attr;
6860         void *hdr;
6861
6862         hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
6863         if (!hdr)
6864                 return -EMSGSIZE;
6865
6866         if (devlink_nl_put_handle(msg, devlink))
6867                 goto genlmsg_cancel;
6868
6869         if (reporter->devlink_port) {
6870                 if (nla_put_u32(msg, DEVLINK_ATTR_PORT_INDEX, reporter->devlink_port->index))
6871                         goto genlmsg_cancel;
6872         }
6873         reporter_attr = nla_nest_start_noflag(msg,
6874                                               DEVLINK_ATTR_HEALTH_REPORTER);
6875         if (!reporter_attr)
6876                 goto genlmsg_cancel;
6877         if (nla_put_string(msg, DEVLINK_ATTR_HEALTH_REPORTER_NAME,
6878                            reporter->ops->name))
6879                 goto reporter_nest_cancel;
6880         if (nla_put_u8(msg, DEVLINK_ATTR_HEALTH_REPORTER_STATE,
6881                        reporter->health_state))
6882                 goto reporter_nest_cancel;
6883         if (nla_put_u64_64bit(msg, DEVLINK_ATTR_HEALTH_REPORTER_ERR_COUNT,
6884                               reporter->error_count, DEVLINK_ATTR_PAD))
6885                 goto reporter_nest_cancel;
6886         if (nla_put_u64_64bit(msg, DEVLINK_ATTR_HEALTH_REPORTER_RECOVER_COUNT,
6887                               reporter->recovery_count, DEVLINK_ATTR_PAD))
6888                 goto reporter_nest_cancel;
6889         if (reporter->ops->recover &&
6890             nla_put_u64_64bit(msg, DEVLINK_ATTR_HEALTH_REPORTER_GRACEFUL_PERIOD,
6891                               reporter->graceful_period,
6892                               DEVLINK_ATTR_PAD))
6893                 goto reporter_nest_cancel;
6894         if (reporter->ops->recover &&
6895             nla_put_u8(msg, DEVLINK_ATTR_HEALTH_REPORTER_AUTO_RECOVER,
6896                        reporter->auto_recover))
6897                 goto reporter_nest_cancel;
6898         if (reporter->dump_fmsg &&
6899             nla_put_u64_64bit(msg, DEVLINK_ATTR_HEALTH_REPORTER_DUMP_TS,
6900                               jiffies_to_msecs(reporter->dump_ts),
6901                               DEVLINK_ATTR_PAD))
6902                 goto reporter_nest_cancel;
6903         if (reporter->dump_fmsg &&
6904             nla_put_u64_64bit(msg, DEVLINK_ATTR_HEALTH_REPORTER_DUMP_TS_NS,
6905                               reporter->dump_real_ts, DEVLINK_ATTR_PAD))
6906                 goto reporter_nest_cancel;
6907         if (reporter->ops->dump &&
6908             nla_put_u8(msg, DEVLINK_ATTR_HEALTH_REPORTER_AUTO_DUMP,
6909                        reporter->auto_dump))
6910                 goto reporter_nest_cancel;
6911
6912         nla_nest_end(msg, reporter_attr);
6913         genlmsg_end(msg, hdr);
6914         return 0;
6915
6916 reporter_nest_cancel:
6917         nla_nest_end(msg, reporter_attr);
6918 genlmsg_cancel:
6919         genlmsg_cancel(msg, hdr);
6920         return -EMSGSIZE;
6921 }
6922
6923 static void devlink_recover_notify(struct devlink_health_reporter *reporter,
6924                                    enum devlink_command cmd)
6925 {
6926         struct sk_buff *msg;
6927         int err;
6928
6929         WARN_ON(cmd != DEVLINK_CMD_HEALTH_REPORTER_RECOVER);
6930
6931         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
6932         if (!msg)
6933                 return;
6934
6935         err = devlink_nl_health_reporter_fill(msg, reporter, cmd, 0, 0, 0);
6936         if (err) {
6937                 nlmsg_free(msg);
6938                 return;
6939         }
6940
6941         genlmsg_multicast_netns(&devlink_nl_family,
6942                                 devlink_net(reporter->devlink),
6943                                 msg, 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
6944 }
6945
6946 void
6947 devlink_health_reporter_recovery_done(struct devlink_health_reporter *reporter)
6948 {
6949         reporter->recovery_count++;
6950         reporter->last_recovery_ts = jiffies;
6951 }
6952 EXPORT_SYMBOL_GPL(devlink_health_reporter_recovery_done);
6953
6954 static int
6955 devlink_health_reporter_recover(struct devlink_health_reporter *reporter,
6956                                 void *priv_ctx, struct netlink_ext_ack *extack)
6957 {
6958         int err;
6959
6960         if (reporter->health_state == DEVLINK_HEALTH_REPORTER_STATE_HEALTHY)
6961                 return 0;
6962
6963         if (!reporter->ops->recover)
6964                 return -EOPNOTSUPP;
6965
6966         err = reporter->ops->recover(reporter, priv_ctx, extack);
6967         if (err)
6968                 return err;
6969
6970         devlink_health_reporter_recovery_done(reporter);
6971         reporter->health_state = DEVLINK_HEALTH_REPORTER_STATE_HEALTHY;
6972         devlink_recover_notify(reporter, DEVLINK_CMD_HEALTH_REPORTER_RECOVER);
6973
6974         return 0;
6975 }
6976
6977 static void
6978 devlink_health_dump_clear(struct devlink_health_reporter *reporter)
6979 {
6980         if (!reporter->dump_fmsg)
6981                 return;
6982         devlink_fmsg_free(reporter->dump_fmsg);
6983         reporter->dump_fmsg = NULL;
6984 }
6985
6986 static int devlink_health_do_dump(struct devlink_health_reporter *reporter,
6987                                   void *priv_ctx,
6988                                   struct netlink_ext_ack *extack)
6989 {
6990         int err;
6991
6992         if (!reporter->ops->dump)
6993                 return 0;
6994
6995         if (reporter->dump_fmsg)
6996                 return 0;
6997
6998         reporter->dump_fmsg = devlink_fmsg_alloc();
6999         if (!reporter->dump_fmsg) {
7000                 err = -ENOMEM;
7001                 return err;
7002         }
7003
7004         err = devlink_fmsg_obj_nest_start(reporter->dump_fmsg);
7005         if (err)
7006                 goto dump_err;
7007
7008         err = reporter->ops->dump(reporter, reporter->dump_fmsg,
7009                                   priv_ctx, extack);
7010         if (err)
7011                 goto dump_err;
7012
7013         err = devlink_fmsg_obj_nest_end(reporter->dump_fmsg);
7014         if (err)
7015                 goto dump_err;
7016
7017         reporter->dump_ts = jiffies;
7018         reporter->dump_real_ts = ktime_get_real_ns();
7019
7020         return 0;
7021
7022 dump_err:
7023         devlink_health_dump_clear(reporter);
7024         return err;
7025 }
7026
7027 int devlink_health_report(struct devlink_health_reporter *reporter,
7028                           const char *msg, void *priv_ctx)
7029 {
7030         enum devlink_health_reporter_state prev_health_state;
7031         struct devlink *devlink = reporter->devlink;
7032         unsigned long recover_ts_threshold;
7033
7034         /* write a log message of the current error */
7035         WARN_ON(!msg);
7036         trace_devlink_health_report(devlink, reporter->ops->name, msg);
7037         reporter->error_count++;
7038         prev_health_state = reporter->health_state;
7039         reporter->health_state = DEVLINK_HEALTH_REPORTER_STATE_ERROR;
7040         devlink_recover_notify(reporter, DEVLINK_CMD_HEALTH_REPORTER_RECOVER);
7041
7042         /* abort if the previous error wasn't recovered */
7043         recover_ts_threshold = reporter->last_recovery_ts +
7044                                msecs_to_jiffies(reporter->graceful_period);
7045         if (reporter->auto_recover &&
7046             (prev_health_state != DEVLINK_HEALTH_REPORTER_STATE_HEALTHY ||
7047              (reporter->last_recovery_ts && reporter->recovery_count &&
7048               time_is_after_jiffies(recover_ts_threshold)))) {
7049                 trace_devlink_health_recover_aborted(devlink,
7050                                                      reporter->ops->name,
7051                                                      reporter->health_state,
7052                                                      jiffies -
7053                                                      reporter->last_recovery_ts);
7054                 return -ECANCELED;
7055         }
7056
7057         reporter->health_state = DEVLINK_HEALTH_REPORTER_STATE_ERROR;
7058
7059         if (reporter->auto_dump) {
7060                 mutex_lock(&reporter->dump_lock);
7061                 /* store current dump of current error, for later analysis */
7062                 devlink_health_do_dump(reporter, priv_ctx, NULL);
7063                 mutex_unlock(&reporter->dump_lock);
7064         }
7065
7066         if (reporter->auto_recover)
7067                 return devlink_health_reporter_recover(reporter,
7068                                                        priv_ctx, NULL);
7069
7070         return 0;
7071 }
7072 EXPORT_SYMBOL_GPL(devlink_health_report);
7073
7074 static struct devlink_health_reporter *
7075 devlink_health_reporter_get_from_attrs(struct devlink *devlink,
7076                                        struct nlattr **attrs)
7077 {
7078         struct devlink_health_reporter *reporter;
7079         struct devlink_port *devlink_port;
7080         char *reporter_name;
7081
7082         if (!attrs[DEVLINK_ATTR_HEALTH_REPORTER_NAME])
7083                 return NULL;
7084
7085         reporter_name = nla_data(attrs[DEVLINK_ATTR_HEALTH_REPORTER_NAME]);
7086         devlink_port = devlink_port_get_from_attrs(devlink, attrs);
7087         if (IS_ERR(devlink_port)) {
7088                 mutex_lock(&devlink->reporters_lock);
7089                 reporter = devlink_health_reporter_find_by_name(devlink, reporter_name);
7090                 if (reporter)
7091                         refcount_inc(&reporter->refcount);
7092                 mutex_unlock(&devlink->reporters_lock);
7093         } else {
7094                 mutex_lock(&devlink_port->reporters_lock);
7095                 reporter = devlink_port_health_reporter_find_by_name(devlink_port, reporter_name);
7096                 if (reporter)
7097                         refcount_inc(&reporter->refcount);
7098                 mutex_unlock(&devlink_port->reporters_lock);
7099         }
7100
7101         return reporter;
7102 }
7103
7104 static struct devlink_health_reporter *
7105 devlink_health_reporter_get_from_info(struct devlink *devlink,
7106                                       struct genl_info *info)
7107 {
7108         return devlink_health_reporter_get_from_attrs(devlink, info->attrs);
7109 }
7110
7111 static struct devlink_health_reporter *
7112 devlink_health_reporter_get_from_cb(struct netlink_callback *cb)
7113 {
7114         const struct genl_dumpit_info *info = genl_dumpit_info(cb);
7115         struct devlink_health_reporter *reporter;
7116         struct nlattr **attrs = info->attrs;
7117         struct devlink *devlink;
7118
7119         mutex_lock(&devlink_mutex);
7120         devlink = devlink_get_from_attrs(sock_net(cb->skb->sk), attrs);
7121         if (IS_ERR(devlink))
7122                 goto unlock;
7123
7124         reporter = devlink_health_reporter_get_from_attrs(devlink, attrs);
7125         devlink_put(devlink);
7126         mutex_unlock(&devlink_mutex);
7127         return reporter;
7128 unlock:
7129         mutex_unlock(&devlink_mutex);
7130         return NULL;
7131 }
7132
7133 void
7134 devlink_health_reporter_state_update(struct devlink_health_reporter *reporter,
7135                                      enum devlink_health_reporter_state state)
7136 {
7137         if (WARN_ON(state != DEVLINK_HEALTH_REPORTER_STATE_HEALTHY &&
7138                     state != DEVLINK_HEALTH_REPORTER_STATE_ERROR))
7139                 return;
7140
7141         if (reporter->health_state == state)
7142                 return;
7143
7144         reporter->health_state = state;
7145         trace_devlink_health_reporter_state_update(reporter->devlink,
7146                                                    reporter->ops->name, state);
7147         devlink_recover_notify(reporter, DEVLINK_CMD_HEALTH_REPORTER_RECOVER);
7148 }
7149 EXPORT_SYMBOL_GPL(devlink_health_reporter_state_update);
7150
7151 static int devlink_nl_cmd_health_reporter_get_doit(struct sk_buff *skb,
7152                                                    struct genl_info *info)
7153 {
7154         struct devlink *devlink = info->user_ptr[0];
7155         struct devlink_health_reporter *reporter;
7156         struct sk_buff *msg;
7157         int err;
7158
7159         reporter = devlink_health_reporter_get_from_info(devlink, info);
7160         if (!reporter)
7161                 return -EINVAL;
7162
7163         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
7164         if (!msg) {
7165                 err = -ENOMEM;
7166                 goto out;
7167         }
7168
7169         err = devlink_nl_health_reporter_fill(msg, reporter,
7170                                               DEVLINK_CMD_HEALTH_REPORTER_GET,
7171                                               info->snd_portid, info->snd_seq,
7172                                               0);
7173         if (err) {
7174                 nlmsg_free(msg);
7175                 goto out;
7176         }
7177
7178         err = genlmsg_reply(msg, info);
7179 out:
7180         devlink_health_reporter_put(reporter);
7181         return err;
7182 }
7183
7184 static int
7185 devlink_nl_cmd_health_reporter_get_dumpit(struct sk_buff *msg,
7186                                           struct netlink_callback *cb)
7187 {
7188         struct devlink_health_reporter *reporter;
7189         struct devlink_port *port;
7190         struct devlink *devlink;
7191         int start = cb->args[0];
7192         unsigned long index;
7193         int idx = 0;
7194         int err;
7195
7196         mutex_lock(&devlink_mutex);
7197         xa_for_each_marked(&devlinks, index, devlink, DEVLINK_REGISTERED) {
7198                 if (!devlink_try_get(devlink))
7199                         continue;
7200
7201                 if (!net_eq(devlink_net(devlink), sock_net(msg->sk)))
7202                         goto retry_rep;
7203
7204                 mutex_lock(&devlink->reporters_lock);
7205                 list_for_each_entry(reporter, &devlink->reporter_list,
7206                                     list) {
7207                         if (idx < start) {
7208                                 idx++;
7209                                 continue;
7210                         }
7211                         err = devlink_nl_health_reporter_fill(
7212                                 msg, reporter, DEVLINK_CMD_HEALTH_REPORTER_GET,
7213                                 NETLINK_CB(cb->skb).portid, cb->nlh->nlmsg_seq,
7214                                 NLM_F_MULTI);
7215                         if (err) {
7216                                 mutex_unlock(&devlink->reporters_lock);
7217                                 devlink_put(devlink);
7218                                 goto out;
7219                         }
7220                         idx++;
7221                 }
7222                 mutex_unlock(&devlink->reporters_lock);
7223 retry_rep:
7224                 devlink_put(devlink);
7225         }
7226
7227         xa_for_each_marked(&devlinks, index, devlink, DEVLINK_REGISTERED) {
7228                 if (!devlink_try_get(devlink))
7229                         continue;
7230
7231                 if (!net_eq(devlink_net(devlink), sock_net(msg->sk)))
7232                         goto retry_port;
7233
7234                 mutex_lock(&devlink->lock);
7235                 list_for_each_entry(port, &devlink->port_list, list) {
7236                         mutex_lock(&port->reporters_lock);
7237                         list_for_each_entry(reporter, &port->reporter_list, list) {
7238                                 if (idx < start) {
7239                                         idx++;
7240                                         continue;
7241                                 }
7242                                 err = devlink_nl_health_reporter_fill(
7243                                         msg, reporter,
7244                                         DEVLINK_CMD_HEALTH_REPORTER_GET,
7245                                         NETLINK_CB(cb->skb).portid,
7246                                         cb->nlh->nlmsg_seq, NLM_F_MULTI);
7247                                 if (err) {
7248                                         mutex_unlock(&port->reporters_lock);
7249                                         mutex_unlock(&devlink->lock);
7250                                         devlink_put(devlink);
7251                                         goto out;
7252                                 }
7253                                 idx++;
7254                         }
7255                         mutex_unlock(&port->reporters_lock);
7256                 }
7257                 mutex_unlock(&devlink->lock);
7258 retry_port:
7259                 devlink_put(devlink);
7260         }
7261 out:
7262         mutex_unlock(&devlink_mutex);
7263
7264         cb->args[0] = idx;
7265         return msg->len;
7266 }
7267
7268 static int
7269 devlink_nl_cmd_health_reporter_set_doit(struct sk_buff *skb,
7270                                         struct genl_info *info)
7271 {
7272         struct devlink *devlink = info->user_ptr[0];
7273         struct devlink_health_reporter *reporter;
7274         int err;
7275
7276         reporter = devlink_health_reporter_get_from_info(devlink, info);
7277         if (!reporter)
7278                 return -EINVAL;
7279
7280         if (!reporter->ops->recover &&
7281             (info->attrs[DEVLINK_ATTR_HEALTH_REPORTER_GRACEFUL_PERIOD] ||
7282              info->attrs[DEVLINK_ATTR_HEALTH_REPORTER_AUTO_RECOVER])) {
7283                 err = -EOPNOTSUPP;
7284                 goto out;
7285         }
7286         if (!reporter->ops->dump &&
7287             info->attrs[DEVLINK_ATTR_HEALTH_REPORTER_AUTO_DUMP]) {
7288                 err = -EOPNOTSUPP;
7289                 goto out;
7290         }
7291
7292         if (info->attrs[DEVLINK_ATTR_HEALTH_REPORTER_GRACEFUL_PERIOD])
7293                 reporter->graceful_period =
7294                         nla_get_u64(info->attrs[DEVLINK_ATTR_HEALTH_REPORTER_GRACEFUL_PERIOD]);
7295
7296         if (info->attrs[DEVLINK_ATTR_HEALTH_REPORTER_AUTO_RECOVER])
7297                 reporter->auto_recover =
7298                         nla_get_u8(info->attrs[DEVLINK_ATTR_HEALTH_REPORTER_AUTO_RECOVER]);
7299
7300         if (info->attrs[DEVLINK_ATTR_HEALTH_REPORTER_AUTO_DUMP])
7301                 reporter->auto_dump =
7302                 nla_get_u8(info->attrs[DEVLINK_ATTR_HEALTH_REPORTER_AUTO_DUMP]);
7303
7304         devlink_health_reporter_put(reporter);
7305         return 0;
7306 out:
7307         devlink_health_reporter_put(reporter);
7308         return err;
7309 }
7310
7311 static int devlink_nl_cmd_health_reporter_recover_doit(struct sk_buff *skb,
7312                                                        struct genl_info *info)
7313 {
7314         struct devlink *devlink = info->user_ptr[0];
7315         struct devlink_health_reporter *reporter;
7316         int err;
7317
7318         reporter = devlink_health_reporter_get_from_info(devlink, info);
7319         if (!reporter)
7320                 return -EINVAL;
7321
7322         err = devlink_health_reporter_recover(reporter, NULL, info->extack);
7323
7324         devlink_health_reporter_put(reporter);
7325         return err;
7326 }
7327
7328 static int devlink_nl_cmd_health_reporter_diagnose_doit(struct sk_buff *skb,
7329                                                         struct genl_info *info)
7330 {
7331         struct devlink *devlink = info->user_ptr[0];
7332         struct devlink_health_reporter *reporter;
7333         struct devlink_fmsg *fmsg;
7334         int err;
7335
7336         reporter = devlink_health_reporter_get_from_info(devlink, info);
7337         if (!reporter)
7338                 return -EINVAL;
7339
7340         if (!reporter->ops->diagnose) {
7341                 devlink_health_reporter_put(reporter);
7342                 return -EOPNOTSUPP;
7343         }
7344
7345         fmsg = devlink_fmsg_alloc();
7346         if (!fmsg) {
7347                 devlink_health_reporter_put(reporter);
7348                 return -ENOMEM;
7349         }
7350
7351         err = devlink_fmsg_obj_nest_start(fmsg);
7352         if (err)
7353                 goto out;
7354
7355         err = reporter->ops->diagnose(reporter, fmsg, info->extack);
7356         if (err)
7357                 goto out;
7358
7359         err = devlink_fmsg_obj_nest_end(fmsg);
7360         if (err)
7361                 goto out;
7362
7363         err = devlink_fmsg_snd(fmsg, info,
7364                                DEVLINK_CMD_HEALTH_REPORTER_DIAGNOSE, 0);
7365
7366 out:
7367         devlink_fmsg_free(fmsg);
7368         devlink_health_reporter_put(reporter);
7369         return err;
7370 }
7371
7372 static int
7373 devlink_nl_cmd_health_reporter_dump_get_dumpit(struct sk_buff *skb,
7374                                                struct netlink_callback *cb)
7375 {
7376         struct devlink_health_reporter *reporter;
7377         u64 start = cb->args[0];
7378         int err;
7379
7380         reporter = devlink_health_reporter_get_from_cb(cb);
7381         if (!reporter)
7382                 return -EINVAL;
7383
7384         if (!reporter->ops->dump) {
7385                 err = -EOPNOTSUPP;
7386                 goto out;
7387         }
7388         mutex_lock(&reporter->dump_lock);
7389         if (!start) {
7390                 err = devlink_health_do_dump(reporter, NULL, cb->extack);
7391                 if (err)
7392                         goto unlock;
7393                 cb->args[1] = reporter->dump_ts;
7394         }
7395         if (!reporter->dump_fmsg || cb->args[1] != reporter->dump_ts) {
7396                 NL_SET_ERR_MSG_MOD(cb->extack, "Dump trampled, please retry");
7397                 err = -EAGAIN;
7398                 goto unlock;
7399         }
7400
7401         err = devlink_fmsg_dumpit(reporter->dump_fmsg, skb, cb,
7402                                   DEVLINK_CMD_HEALTH_REPORTER_DUMP_GET);
7403 unlock:
7404         mutex_unlock(&reporter->dump_lock);
7405 out:
7406         devlink_health_reporter_put(reporter);
7407         return err;
7408 }
7409
7410 static int
7411 devlink_nl_cmd_health_reporter_dump_clear_doit(struct sk_buff *skb,
7412                                                struct genl_info *info)
7413 {
7414         struct devlink *devlink = info->user_ptr[0];
7415         struct devlink_health_reporter *reporter;
7416
7417         reporter = devlink_health_reporter_get_from_info(devlink, info);
7418         if (!reporter)
7419                 return -EINVAL;
7420
7421         if (!reporter->ops->dump) {
7422                 devlink_health_reporter_put(reporter);
7423                 return -EOPNOTSUPP;
7424         }
7425
7426         mutex_lock(&reporter->dump_lock);
7427         devlink_health_dump_clear(reporter);
7428         mutex_unlock(&reporter->dump_lock);
7429         devlink_health_reporter_put(reporter);
7430         return 0;
7431 }
7432
7433 static int devlink_nl_cmd_health_reporter_test_doit(struct sk_buff *skb,
7434                                                     struct genl_info *info)
7435 {
7436         struct devlink *devlink = info->user_ptr[0];
7437         struct devlink_health_reporter *reporter;
7438         int err;
7439
7440         reporter = devlink_health_reporter_get_from_info(devlink, info);
7441         if (!reporter)
7442                 return -EINVAL;
7443
7444         if (!reporter->ops->test) {
7445                 devlink_health_reporter_put(reporter);
7446                 return -EOPNOTSUPP;
7447         }
7448
7449         err = reporter->ops->test(reporter, info->extack);
7450
7451         devlink_health_reporter_put(reporter);
7452         return err;
7453 }
7454
7455 struct devlink_stats {
7456         u64 rx_bytes;
7457         u64 rx_packets;
7458         struct u64_stats_sync syncp;
7459 };
7460
7461 /**
7462  * struct devlink_trap_policer_item - Packet trap policer attributes.
7463  * @policer: Immutable packet trap policer attributes.
7464  * @rate: Rate in packets / sec.
7465  * @burst: Burst size in packets.
7466  * @list: trap_policer_list member.
7467  *
7468  * Describes packet trap policer attributes. Created by devlink during trap
7469  * policer registration.
7470  */
7471 struct devlink_trap_policer_item {
7472         const struct devlink_trap_policer *policer;
7473         u64 rate;
7474         u64 burst;
7475         struct list_head list;
7476 };
7477
7478 /**
7479  * struct devlink_trap_group_item - Packet trap group attributes.
7480  * @group: Immutable packet trap group attributes.
7481  * @policer_item: Associated policer item. Can be NULL.
7482  * @list: trap_group_list member.
7483  * @stats: Trap group statistics.
7484  *
7485  * Describes packet trap group attributes. Created by devlink during trap
7486  * group registration.
7487  */
7488 struct devlink_trap_group_item {
7489         const struct devlink_trap_group *group;
7490         struct devlink_trap_policer_item *policer_item;
7491         struct list_head list;
7492         struct devlink_stats __percpu *stats;
7493 };
7494
7495 /**
7496  * struct devlink_trap_item - Packet trap attributes.
7497  * @trap: Immutable packet trap attributes.
7498  * @group_item: Associated group item.
7499  * @list: trap_list member.
7500  * @action: Trap action.
7501  * @stats: Trap statistics.
7502  * @priv: Driver private information.
7503  *
7504  * Describes both mutable and immutable packet trap attributes. Created by
7505  * devlink during trap registration and used for all trap related operations.
7506  */
7507 struct devlink_trap_item {
7508         const struct devlink_trap *trap;
7509         struct devlink_trap_group_item *group_item;
7510         struct list_head list;
7511         enum devlink_trap_action action;
7512         struct devlink_stats __percpu *stats;
7513         void *priv;
7514 };
7515
7516 static struct devlink_trap_policer_item *
7517 devlink_trap_policer_item_lookup(struct devlink *devlink, u32 id)
7518 {
7519         struct devlink_trap_policer_item *policer_item;
7520
7521         list_for_each_entry(policer_item, &devlink->trap_policer_list, list) {
7522                 if (policer_item->policer->id == id)
7523                         return policer_item;
7524         }
7525
7526         return NULL;
7527 }
7528
7529 static struct devlink_trap_item *
7530 devlink_trap_item_lookup(struct devlink *devlink, const char *name)
7531 {
7532         struct devlink_trap_item *trap_item;
7533
7534         list_for_each_entry(trap_item, &devlink->trap_list, list) {
7535                 if (!strcmp(trap_item->trap->name, name))
7536                         return trap_item;
7537         }
7538
7539         return NULL;
7540 }
7541
7542 static struct devlink_trap_item *
7543 devlink_trap_item_get_from_info(struct devlink *devlink,
7544                                 struct genl_info *info)
7545 {
7546         struct nlattr *attr;
7547
7548         if (!info->attrs[DEVLINK_ATTR_TRAP_NAME])
7549                 return NULL;
7550         attr = info->attrs[DEVLINK_ATTR_TRAP_NAME];
7551
7552         return devlink_trap_item_lookup(devlink, nla_data(attr));
7553 }
7554
7555 static int
7556 devlink_trap_action_get_from_info(struct genl_info *info,
7557                                   enum devlink_trap_action *p_trap_action)
7558 {
7559         u8 val;
7560
7561         val = nla_get_u8(info->attrs[DEVLINK_ATTR_TRAP_ACTION]);
7562         switch (val) {
7563         case DEVLINK_TRAP_ACTION_DROP:
7564         case DEVLINK_TRAP_ACTION_TRAP:
7565         case DEVLINK_TRAP_ACTION_MIRROR:
7566                 *p_trap_action = val;
7567                 break;
7568         default:
7569                 return -EINVAL;
7570         }
7571
7572         return 0;
7573 }
7574
7575 static int devlink_trap_metadata_put(struct sk_buff *msg,
7576                                      const struct devlink_trap *trap)
7577 {
7578         struct nlattr *attr;
7579
7580         attr = nla_nest_start(msg, DEVLINK_ATTR_TRAP_METADATA);
7581         if (!attr)
7582                 return -EMSGSIZE;
7583
7584         if ((trap->metadata_cap & DEVLINK_TRAP_METADATA_TYPE_F_IN_PORT) &&
7585             nla_put_flag(msg, DEVLINK_ATTR_TRAP_METADATA_TYPE_IN_PORT))
7586                 goto nla_put_failure;
7587         if ((trap->metadata_cap & DEVLINK_TRAP_METADATA_TYPE_F_FA_COOKIE) &&
7588             nla_put_flag(msg, DEVLINK_ATTR_TRAP_METADATA_TYPE_FA_COOKIE))
7589                 goto nla_put_failure;
7590
7591         nla_nest_end(msg, attr);
7592
7593         return 0;
7594
7595 nla_put_failure:
7596         nla_nest_cancel(msg, attr);
7597         return -EMSGSIZE;
7598 }
7599
7600 static void devlink_trap_stats_read(struct devlink_stats __percpu *trap_stats,
7601                                     struct devlink_stats *stats)
7602 {
7603         int i;
7604
7605         memset(stats, 0, sizeof(*stats));
7606         for_each_possible_cpu(i) {
7607                 struct devlink_stats *cpu_stats;
7608                 u64 rx_packets, rx_bytes;
7609                 unsigned int start;
7610
7611                 cpu_stats = per_cpu_ptr(trap_stats, i);
7612                 do {
7613                         start = u64_stats_fetch_begin_irq(&cpu_stats->syncp);
7614                         rx_packets = cpu_stats->rx_packets;
7615                         rx_bytes = cpu_stats->rx_bytes;
7616                 } while (u64_stats_fetch_retry_irq(&cpu_stats->syncp, start));
7617
7618                 stats->rx_packets += rx_packets;
7619                 stats->rx_bytes += rx_bytes;
7620         }
7621 }
7622
7623 static int
7624 devlink_trap_group_stats_put(struct sk_buff *msg,
7625                              struct devlink_stats __percpu *trap_stats)
7626 {
7627         struct devlink_stats stats;
7628         struct nlattr *attr;
7629
7630         devlink_trap_stats_read(trap_stats, &stats);
7631
7632         attr = nla_nest_start(msg, DEVLINK_ATTR_STATS);
7633         if (!attr)
7634                 return -EMSGSIZE;
7635
7636         if (nla_put_u64_64bit(msg, DEVLINK_ATTR_STATS_RX_PACKETS,
7637                               stats.rx_packets, DEVLINK_ATTR_PAD))
7638                 goto nla_put_failure;
7639
7640         if (nla_put_u64_64bit(msg, DEVLINK_ATTR_STATS_RX_BYTES,
7641                               stats.rx_bytes, DEVLINK_ATTR_PAD))
7642                 goto nla_put_failure;
7643
7644         nla_nest_end(msg, attr);
7645
7646         return 0;
7647
7648 nla_put_failure:
7649         nla_nest_cancel(msg, attr);
7650         return -EMSGSIZE;
7651 }
7652
7653 static int devlink_trap_stats_put(struct sk_buff *msg, struct devlink *devlink,
7654                                   const struct devlink_trap_item *trap_item)
7655 {
7656         struct devlink_stats stats;
7657         struct nlattr *attr;
7658         u64 drops = 0;
7659         int err;
7660
7661         if (devlink->ops->trap_drop_counter_get) {
7662                 err = devlink->ops->trap_drop_counter_get(devlink,
7663                                                           trap_item->trap,
7664                                                           &drops);
7665                 if (err)
7666                         return err;
7667         }
7668
7669         devlink_trap_stats_read(trap_item->stats, &stats);
7670
7671         attr = nla_nest_start(msg, DEVLINK_ATTR_STATS);
7672         if (!attr)
7673                 return -EMSGSIZE;
7674
7675         if (devlink->ops->trap_drop_counter_get &&
7676             nla_put_u64_64bit(msg, DEVLINK_ATTR_STATS_RX_DROPPED, drops,
7677                               DEVLINK_ATTR_PAD))
7678                 goto nla_put_failure;
7679
7680         if (nla_put_u64_64bit(msg, DEVLINK_ATTR_STATS_RX_PACKETS,
7681                               stats.rx_packets, DEVLINK_ATTR_PAD))
7682                 goto nla_put_failure;
7683
7684         if (nla_put_u64_64bit(msg, DEVLINK_ATTR_STATS_RX_BYTES,
7685                               stats.rx_bytes, DEVLINK_ATTR_PAD))
7686                 goto nla_put_failure;
7687
7688         nla_nest_end(msg, attr);
7689
7690         return 0;
7691
7692 nla_put_failure:
7693         nla_nest_cancel(msg, attr);
7694         return -EMSGSIZE;
7695 }
7696
7697 static int devlink_nl_trap_fill(struct sk_buff *msg, struct devlink *devlink,
7698                                 const struct devlink_trap_item *trap_item,
7699                                 enum devlink_command cmd, u32 portid, u32 seq,
7700                                 int flags)
7701 {
7702         struct devlink_trap_group_item *group_item = trap_item->group_item;
7703         void *hdr;
7704         int err;
7705
7706         hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
7707         if (!hdr)
7708                 return -EMSGSIZE;
7709
7710         if (devlink_nl_put_handle(msg, devlink))
7711                 goto nla_put_failure;
7712
7713         if (nla_put_string(msg, DEVLINK_ATTR_TRAP_GROUP_NAME,
7714                            group_item->group->name))
7715                 goto nla_put_failure;
7716
7717         if (nla_put_string(msg, DEVLINK_ATTR_TRAP_NAME, trap_item->trap->name))
7718                 goto nla_put_failure;
7719
7720         if (nla_put_u8(msg, DEVLINK_ATTR_TRAP_TYPE, trap_item->trap->type))
7721                 goto nla_put_failure;
7722
7723         if (trap_item->trap->generic &&
7724             nla_put_flag(msg, DEVLINK_ATTR_TRAP_GENERIC))
7725                 goto nla_put_failure;
7726
7727         if (nla_put_u8(msg, DEVLINK_ATTR_TRAP_ACTION, trap_item->action))
7728                 goto nla_put_failure;
7729
7730         err = devlink_trap_metadata_put(msg, trap_item->trap);
7731         if (err)
7732                 goto nla_put_failure;
7733
7734         err = devlink_trap_stats_put(msg, devlink, trap_item);
7735         if (err)
7736                 goto nla_put_failure;
7737
7738         genlmsg_end(msg, hdr);
7739
7740         return 0;
7741
7742 nla_put_failure:
7743         genlmsg_cancel(msg, hdr);
7744         return -EMSGSIZE;
7745 }
7746
7747 static int devlink_nl_cmd_trap_get_doit(struct sk_buff *skb,
7748                                         struct genl_info *info)
7749 {
7750         struct netlink_ext_ack *extack = info->extack;
7751         struct devlink *devlink = info->user_ptr[0];
7752         struct devlink_trap_item *trap_item;
7753         struct sk_buff *msg;
7754         int err;
7755
7756         if (list_empty(&devlink->trap_list))
7757                 return -EOPNOTSUPP;
7758
7759         trap_item = devlink_trap_item_get_from_info(devlink, info);
7760         if (!trap_item) {
7761                 NL_SET_ERR_MSG_MOD(extack, "Device did not register this trap");
7762                 return -ENOENT;
7763         }
7764
7765         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
7766         if (!msg)
7767                 return -ENOMEM;
7768
7769         err = devlink_nl_trap_fill(msg, devlink, trap_item,
7770                                    DEVLINK_CMD_TRAP_NEW, info->snd_portid,
7771                                    info->snd_seq, 0);
7772         if (err)
7773                 goto err_trap_fill;
7774
7775         return genlmsg_reply(msg, info);
7776
7777 err_trap_fill:
7778         nlmsg_free(msg);
7779         return err;
7780 }
7781
7782 static int devlink_nl_cmd_trap_get_dumpit(struct sk_buff *msg,
7783                                           struct netlink_callback *cb)
7784 {
7785         struct devlink_trap_item *trap_item;
7786         struct devlink *devlink;
7787         int start = cb->args[0];
7788         unsigned long index;
7789         int idx = 0;
7790         int err;
7791
7792         mutex_lock(&devlink_mutex);
7793         xa_for_each_marked(&devlinks, index, devlink, DEVLINK_REGISTERED) {
7794                 if (!devlink_try_get(devlink))
7795                         continue;
7796
7797                 if (!net_eq(devlink_net(devlink), sock_net(msg->sk)))
7798                         goto retry;
7799
7800                 mutex_lock(&devlink->lock);
7801                 list_for_each_entry(trap_item, &devlink->trap_list, list) {
7802                         if (idx < start) {
7803                                 idx++;
7804                                 continue;
7805                         }
7806                         err = devlink_nl_trap_fill(msg, devlink, trap_item,
7807                                                    DEVLINK_CMD_TRAP_NEW,
7808                                                    NETLINK_CB(cb->skb).portid,
7809                                                    cb->nlh->nlmsg_seq,
7810                                                    NLM_F_MULTI);
7811                         if (err) {
7812                                 mutex_unlock(&devlink->lock);
7813                                 devlink_put(devlink);
7814                                 goto out;
7815                         }
7816                         idx++;
7817                 }
7818                 mutex_unlock(&devlink->lock);
7819 retry:
7820                 devlink_put(devlink);
7821         }
7822 out:
7823         mutex_unlock(&devlink_mutex);
7824
7825         cb->args[0] = idx;
7826         return msg->len;
7827 }
7828
7829 static int __devlink_trap_action_set(struct devlink *devlink,
7830                                      struct devlink_trap_item *trap_item,
7831                                      enum devlink_trap_action trap_action,
7832                                      struct netlink_ext_ack *extack)
7833 {
7834         int err;
7835
7836         if (trap_item->action != trap_action &&
7837             trap_item->trap->type != DEVLINK_TRAP_TYPE_DROP) {
7838                 NL_SET_ERR_MSG_MOD(extack, "Cannot change action of non-drop traps. Skipping");
7839                 return 0;
7840         }
7841
7842         err = devlink->ops->trap_action_set(devlink, trap_item->trap,
7843                                             trap_action, extack);
7844         if (err)
7845                 return err;
7846
7847         trap_item->action = trap_action;
7848
7849         return 0;
7850 }
7851
7852 static int devlink_trap_action_set(struct devlink *devlink,
7853                                    struct devlink_trap_item *trap_item,
7854                                    struct genl_info *info)
7855 {
7856         enum devlink_trap_action trap_action;
7857         int err;
7858
7859         if (!info->attrs[DEVLINK_ATTR_TRAP_ACTION])
7860                 return 0;
7861
7862         err = devlink_trap_action_get_from_info(info, &trap_action);
7863         if (err) {
7864                 NL_SET_ERR_MSG_MOD(info->extack, "Invalid trap action");
7865                 return -EINVAL;
7866         }
7867
7868         return __devlink_trap_action_set(devlink, trap_item, trap_action,
7869                                          info->extack);
7870 }
7871
7872 static int devlink_nl_cmd_trap_set_doit(struct sk_buff *skb,
7873                                         struct genl_info *info)
7874 {
7875         struct netlink_ext_ack *extack = info->extack;
7876         struct devlink *devlink = info->user_ptr[0];
7877         struct devlink_trap_item *trap_item;
7878
7879         if (list_empty(&devlink->trap_list))
7880                 return -EOPNOTSUPP;
7881
7882         trap_item = devlink_trap_item_get_from_info(devlink, info);
7883         if (!trap_item) {
7884                 NL_SET_ERR_MSG_MOD(extack, "Device did not register this trap");
7885                 return -ENOENT;
7886         }
7887
7888         return devlink_trap_action_set(devlink, trap_item, info);
7889 }
7890
7891 static struct devlink_trap_group_item *
7892 devlink_trap_group_item_lookup(struct devlink *devlink, const char *name)
7893 {
7894         struct devlink_trap_group_item *group_item;
7895
7896         list_for_each_entry(group_item, &devlink->trap_group_list, list) {
7897                 if (!strcmp(group_item->group->name, name))
7898                         return group_item;
7899         }
7900
7901         return NULL;
7902 }
7903
7904 static struct devlink_trap_group_item *
7905 devlink_trap_group_item_lookup_by_id(struct devlink *devlink, u16 id)
7906 {
7907         struct devlink_trap_group_item *group_item;
7908
7909         list_for_each_entry(group_item, &devlink->trap_group_list, list) {
7910                 if (group_item->group->id == id)
7911                         return group_item;
7912         }
7913
7914         return NULL;
7915 }
7916
7917 static struct devlink_trap_group_item *
7918 devlink_trap_group_item_get_from_info(struct devlink *devlink,
7919                                       struct genl_info *info)
7920 {
7921         char *name;
7922
7923         if (!info->attrs[DEVLINK_ATTR_TRAP_GROUP_NAME])
7924                 return NULL;
7925         name = nla_data(info->attrs[DEVLINK_ATTR_TRAP_GROUP_NAME]);
7926
7927         return devlink_trap_group_item_lookup(devlink, name);
7928 }
7929
7930 static int
7931 devlink_nl_trap_group_fill(struct sk_buff *msg, struct devlink *devlink,
7932                            const struct devlink_trap_group_item *group_item,
7933                            enum devlink_command cmd, u32 portid, u32 seq,
7934                            int flags)
7935 {
7936         void *hdr;
7937         int err;
7938
7939         hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
7940         if (!hdr)
7941                 return -EMSGSIZE;
7942
7943         if (devlink_nl_put_handle(msg, devlink))
7944                 goto nla_put_failure;
7945
7946         if (nla_put_string(msg, DEVLINK_ATTR_TRAP_GROUP_NAME,
7947                            group_item->group->name))
7948                 goto nla_put_failure;
7949
7950         if (group_item->group->generic &&
7951             nla_put_flag(msg, DEVLINK_ATTR_TRAP_GENERIC))
7952                 goto nla_put_failure;
7953
7954         if (group_item->policer_item &&
7955             nla_put_u32(msg, DEVLINK_ATTR_TRAP_POLICER_ID,
7956                         group_item->policer_item->policer->id))
7957                 goto nla_put_failure;
7958
7959         err = devlink_trap_group_stats_put(msg, group_item->stats);
7960         if (err)
7961                 goto nla_put_failure;
7962
7963         genlmsg_end(msg, hdr);
7964
7965         return 0;
7966
7967 nla_put_failure:
7968         genlmsg_cancel(msg, hdr);
7969         return -EMSGSIZE;
7970 }
7971
7972 static int devlink_nl_cmd_trap_group_get_doit(struct sk_buff *skb,
7973                                               struct genl_info *info)
7974 {
7975         struct netlink_ext_ack *extack = info->extack;
7976         struct devlink *devlink = info->user_ptr[0];
7977         struct devlink_trap_group_item *group_item;
7978         struct sk_buff *msg;
7979         int err;
7980
7981         if (list_empty(&devlink->trap_group_list))
7982                 return -EOPNOTSUPP;
7983
7984         group_item = devlink_trap_group_item_get_from_info(devlink, info);
7985         if (!group_item) {
7986                 NL_SET_ERR_MSG_MOD(extack, "Device did not register this trap group");
7987                 return -ENOENT;
7988         }
7989
7990         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
7991         if (!msg)
7992                 return -ENOMEM;
7993
7994         err = devlink_nl_trap_group_fill(msg, devlink, group_item,
7995                                          DEVLINK_CMD_TRAP_GROUP_NEW,
7996                                          info->snd_portid, info->snd_seq, 0);
7997         if (err)
7998                 goto err_trap_group_fill;
7999
8000         return genlmsg_reply(msg, info);
8001
8002 err_trap_group_fill:
8003         nlmsg_free(msg);
8004         return err;
8005 }
8006
8007 static int devlink_nl_cmd_trap_group_get_dumpit(struct sk_buff *msg,
8008                                                 struct netlink_callback *cb)
8009 {
8010         enum devlink_command cmd = DEVLINK_CMD_TRAP_GROUP_NEW;
8011         struct devlink_trap_group_item *group_item;
8012         u32 portid = NETLINK_CB(cb->skb).portid;
8013         struct devlink *devlink;
8014         int start = cb->args[0];
8015         unsigned long index;
8016         int idx = 0;
8017         int err;
8018
8019         mutex_lock(&devlink_mutex);
8020         xa_for_each_marked(&devlinks, index, devlink, DEVLINK_REGISTERED) {
8021                 if (!devlink_try_get(devlink))
8022                         continue;
8023
8024                 if (!net_eq(devlink_net(devlink), sock_net(msg->sk)))
8025                         goto retry;
8026
8027                 mutex_lock(&devlink->lock);
8028                 list_for_each_entry(group_item, &devlink->trap_group_list,
8029                                     list) {
8030                         if (idx < start) {
8031                                 idx++;
8032                                 continue;
8033                         }
8034                         err = devlink_nl_trap_group_fill(msg, devlink,
8035                                                          group_item, cmd,
8036                                                          portid,
8037                                                          cb->nlh->nlmsg_seq,
8038                                                          NLM_F_MULTI);
8039                         if (err) {
8040                                 mutex_unlock(&devlink->lock);
8041                                 devlink_put(devlink);
8042                                 goto out;
8043                         }
8044                         idx++;
8045                 }
8046                 mutex_unlock(&devlink->lock);
8047 retry:
8048                 devlink_put(devlink);
8049         }
8050 out:
8051         mutex_unlock(&devlink_mutex);
8052
8053         cb->args[0] = idx;
8054         return msg->len;
8055 }
8056
8057 static int
8058 __devlink_trap_group_action_set(struct devlink *devlink,
8059                                 struct devlink_trap_group_item *group_item,
8060                                 enum devlink_trap_action trap_action,
8061                                 struct netlink_ext_ack *extack)
8062 {
8063         const char *group_name = group_item->group->name;
8064         struct devlink_trap_item *trap_item;
8065         int err;
8066
8067         if (devlink->ops->trap_group_action_set) {
8068                 err = devlink->ops->trap_group_action_set(devlink, group_item->group,
8069                                                           trap_action, extack);
8070                 if (err)
8071                         return err;
8072
8073                 list_for_each_entry(trap_item, &devlink->trap_list, list) {
8074                         if (strcmp(trap_item->group_item->group->name, group_name))
8075                                 continue;
8076                         if (trap_item->action != trap_action &&
8077                             trap_item->trap->type != DEVLINK_TRAP_TYPE_DROP)
8078                                 continue;
8079                         trap_item->action = trap_action;
8080                 }
8081
8082                 return 0;
8083         }
8084
8085         list_for_each_entry(trap_item, &devlink->trap_list, list) {
8086                 if (strcmp(trap_item->group_item->group->name, group_name))
8087                         continue;
8088                 err = __devlink_trap_action_set(devlink, trap_item,
8089                                                 trap_action, extack);
8090                 if (err)
8091                         return err;
8092         }
8093
8094         return 0;
8095 }
8096
8097 static int
8098 devlink_trap_group_action_set(struct devlink *devlink,
8099                               struct devlink_trap_group_item *group_item,
8100                               struct genl_info *info, bool *p_modified)
8101 {
8102         enum devlink_trap_action trap_action;
8103         int err;
8104
8105         if (!info->attrs[DEVLINK_ATTR_TRAP_ACTION])
8106                 return 0;
8107
8108         err = devlink_trap_action_get_from_info(info, &trap_action);
8109         if (err) {
8110                 NL_SET_ERR_MSG_MOD(info->extack, "Invalid trap action");
8111                 return -EINVAL;
8112         }
8113
8114         err = __devlink_trap_group_action_set(devlink, group_item, trap_action,
8115                                               info->extack);
8116         if (err)
8117                 return err;
8118
8119         *p_modified = true;
8120
8121         return 0;
8122 }
8123
8124 static int devlink_trap_group_set(struct devlink *devlink,
8125                                   struct devlink_trap_group_item *group_item,
8126                                   struct genl_info *info)
8127 {
8128         struct devlink_trap_policer_item *policer_item;
8129         struct netlink_ext_ack *extack = info->extack;
8130         const struct devlink_trap_policer *policer;
8131         struct nlattr **attrs = info->attrs;
8132         int err;
8133
8134         if (!attrs[DEVLINK_ATTR_TRAP_POLICER_ID])
8135                 return 0;
8136
8137         if (!devlink->ops->trap_group_set)
8138                 return -EOPNOTSUPP;
8139
8140         policer_item = group_item->policer_item;
8141         if (attrs[DEVLINK_ATTR_TRAP_POLICER_ID]) {
8142                 u32 policer_id;
8143
8144                 policer_id = nla_get_u32(attrs[DEVLINK_ATTR_TRAP_POLICER_ID]);
8145                 policer_item = devlink_trap_policer_item_lookup(devlink,
8146                                                                 policer_id);
8147                 if (policer_id && !policer_item) {
8148                         NL_SET_ERR_MSG_MOD(extack, "Device did not register this trap policer");
8149                         return -ENOENT;
8150                 }
8151         }
8152         policer = policer_item ? policer_item->policer : NULL;
8153
8154         err = devlink->ops->trap_group_set(devlink, group_item->group, policer,
8155                                            extack);
8156         if (err)
8157                 return err;
8158
8159         group_item->policer_item = policer_item;
8160
8161         return 0;
8162 }
8163
8164 static int devlink_nl_cmd_trap_group_set_doit(struct sk_buff *skb,
8165                                               struct genl_info *info)
8166 {
8167         struct netlink_ext_ack *extack = info->extack;
8168         struct devlink *devlink = info->user_ptr[0];
8169         struct devlink_trap_group_item *group_item;
8170         bool modified = false;
8171         int err;
8172
8173         if (list_empty(&devlink->trap_group_list))
8174                 return -EOPNOTSUPP;
8175
8176         group_item = devlink_trap_group_item_get_from_info(devlink, info);
8177         if (!group_item) {
8178                 NL_SET_ERR_MSG_MOD(extack, "Device did not register this trap group");
8179                 return -ENOENT;
8180         }
8181
8182         err = devlink_trap_group_action_set(devlink, group_item, info,
8183                                             &modified);
8184         if (err)
8185                 return err;
8186
8187         err = devlink_trap_group_set(devlink, group_item, info);
8188         if (err)
8189                 goto err_trap_group_set;
8190
8191         return 0;
8192
8193 err_trap_group_set:
8194         if (modified)
8195                 NL_SET_ERR_MSG_MOD(extack, "Trap group set failed, but some changes were committed already");
8196         return err;
8197 }
8198
8199 static struct devlink_trap_policer_item *
8200 devlink_trap_policer_item_get_from_info(struct devlink *devlink,
8201                                         struct genl_info *info)
8202 {
8203         u32 id;
8204
8205         if (!info->attrs[DEVLINK_ATTR_TRAP_POLICER_ID])
8206                 return NULL;
8207         id = nla_get_u32(info->attrs[DEVLINK_ATTR_TRAP_POLICER_ID]);
8208
8209         return devlink_trap_policer_item_lookup(devlink, id);
8210 }
8211
8212 static int
8213 devlink_trap_policer_stats_put(struct sk_buff *msg, struct devlink *devlink,
8214                                const struct devlink_trap_policer *policer)
8215 {
8216         struct nlattr *attr;
8217         u64 drops;
8218         int err;
8219
8220         if (!devlink->ops->trap_policer_counter_get)
8221                 return 0;
8222
8223         err = devlink->ops->trap_policer_counter_get(devlink, policer, &drops);
8224         if (err)
8225                 return err;
8226
8227         attr = nla_nest_start(msg, DEVLINK_ATTR_STATS);
8228         if (!attr)
8229                 return -EMSGSIZE;
8230
8231         if (nla_put_u64_64bit(msg, DEVLINK_ATTR_STATS_RX_DROPPED, drops,
8232                               DEVLINK_ATTR_PAD))
8233                 goto nla_put_failure;
8234
8235         nla_nest_end(msg, attr);
8236
8237         return 0;
8238
8239 nla_put_failure:
8240         nla_nest_cancel(msg, attr);
8241         return -EMSGSIZE;
8242 }
8243
8244 static int
8245 devlink_nl_trap_policer_fill(struct sk_buff *msg, struct devlink *devlink,
8246                              const struct devlink_trap_policer_item *policer_item,
8247                              enum devlink_command cmd, u32 portid, u32 seq,
8248                              int flags)
8249 {
8250         void *hdr;
8251         int err;
8252
8253         hdr = genlmsg_put(msg, portid, seq, &devlink_nl_family, flags, cmd);
8254         if (!hdr)
8255                 return -EMSGSIZE;
8256
8257         if (devlink_nl_put_handle(msg, devlink))
8258                 goto nla_put_failure;
8259
8260         if (nla_put_u32(msg, DEVLINK_ATTR_TRAP_POLICER_ID,
8261                         policer_item->policer->id))
8262                 goto nla_put_failure;
8263
8264         if (nla_put_u64_64bit(msg, DEVLINK_ATTR_TRAP_POLICER_RATE,
8265                               policer_item->rate, DEVLINK_ATTR_PAD))
8266                 goto nla_put_failure;
8267
8268         if (nla_put_u64_64bit(msg, DEVLINK_ATTR_TRAP_POLICER_BURST,
8269                               policer_item->burst, DEVLINK_ATTR_PAD))
8270                 goto nla_put_failure;
8271
8272         err = devlink_trap_policer_stats_put(msg, devlink,
8273                                              policer_item->policer);
8274         if (err)
8275                 goto nla_put_failure;
8276
8277         genlmsg_end(msg, hdr);
8278
8279         return 0;
8280
8281 nla_put_failure:
8282         genlmsg_cancel(msg, hdr);
8283         return -EMSGSIZE;
8284 }
8285
8286 static int devlink_nl_cmd_trap_policer_get_doit(struct sk_buff *skb,
8287                                                 struct genl_info *info)
8288 {
8289         struct devlink_trap_policer_item *policer_item;
8290         struct netlink_ext_ack *extack = info->extack;
8291         struct devlink *devlink = info->user_ptr[0];
8292         struct sk_buff *msg;
8293         int err;
8294
8295         if (list_empty(&devlink->trap_policer_list))
8296                 return -EOPNOTSUPP;
8297
8298         policer_item = devlink_trap_policer_item_get_from_info(devlink, info);
8299         if (!policer_item) {
8300                 NL_SET_ERR_MSG_MOD(extack, "Device did not register this trap policer");
8301                 return -ENOENT;
8302         }
8303
8304         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
8305         if (!msg)
8306                 return -ENOMEM;
8307
8308         err = devlink_nl_trap_policer_fill(msg, devlink, policer_item,
8309                                            DEVLINK_CMD_TRAP_POLICER_NEW,
8310                                            info->snd_portid, info->snd_seq, 0);
8311         if (err)
8312                 goto err_trap_policer_fill;
8313
8314         return genlmsg_reply(msg, info);
8315
8316 err_trap_policer_fill:
8317         nlmsg_free(msg);
8318         return err;
8319 }
8320
8321 static int devlink_nl_cmd_trap_policer_get_dumpit(struct sk_buff *msg,
8322                                                   struct netlink_callback *cb)
8323 {
8324         enum devlink_command cmd = DEVLINK_CMD_TRAP_POLICER_NEW;
8325         struct devlink_trap_policer_item *policer_item;
8326         u32 portid = NETLINK_CB(cb->skb).portid;
8327         struct devlink *devlink;
8328         int start = cb->args[0];
8329         unsigned long index;
8330         int idx = 0;
8331         int err;
8332
8333         mutex_lock(&devlink_mutex);
8334         xa_for_each_marked(&devlinks, index, devlink, DEVLINK_REGISTERED) {
8335                 if (!devlink_try_get(devlink))
8336                         continue;
8337
8338                 if (!net_eq(devlink_net(devlink), sock_net(msg->sk)))
8339                         goto retry;
8340
8341                 mutex_lock(&devlink->lock);
8342                 list_for_each_entry(policer_item, &devlink->trap_policer_list,
8343                                     list) {
8344                         if (idx < start) {
8345                                 idx++;
8346                                 continue;
8347                         }
8348                         err = devlink_nl_trap_policer_fill(msg, devlink,
8349                                                            policer_item, cmd,
8350                                                            portid,
8351                                                            cb->nlh->nlmsg_seq,
8352                                                            NLM_F_MULTI);
8353                         if (err) {
8354                                 mutex_unlock(&devlink->lock);
8355                                 devlink_put(devlink);
8356                                 goto out;
8357                         }
8358                         idx++;
8359                 }
8360                 mutex_unlock(&devlink->lock);
8361 retry:
8362                 devlink_put(devlink);
8363         }
8364 out:
8365         mutex_unlock(&devlink_mutex);
8366
8367         cb->args[0] = idx;
8368         return msg->len;
8369 }
8370
8371 static int
8372 devlink_trap_policer_set(struct devlink *devlink,
8373                          struct devlink_trap_policer_item *policer_item,
8374                          struct genl_info *info)
8375 {
8376         struct netlink_ext_ack *extack = info->extack;
8377         struct nlattr **attrs = info->attrs;
8378         u64 rate, burst;
8379         int err;
8380
8381         rate = policer_item->rate;
8382         burst = policer_item->burst;
8383
8384         if (attrs[DEVLINK_ATTR_TRAP_POLICER_RATE])
8385                 rate = nla_get_u64(attrs[DEVLINK_ATTR_TRAP_POLICER_RATE]);
8386
8387         if (attrs[DEVLINK_ATTR_TRAP_POLICER_BURST])
8388                 burst = nla_get_u64(attrs[DEVLINK_ATTR_TRAP_POLICER_BURST]);
8389
8390         if (rate < policer_item->policer->min_rate) {
8391                 NL_SET_ERR_MSG_MOD(extack, "Policer rate lower than limit");
8392                 return -EINVAL;
8393         }
8394
8395         if (rate > policer_item->policer->max_rate) {
8396                 NL_SET_ERR_MSG_MOD(extack, "Policer rate higher than limit");
8397                 return -EINVAL;
8398         }
8399
8400         if (burst < policer_item->policer->min_burst) {
8401                 NL_SET_ERR_MSG_MOD(extack, "Policer burst size lower than limit");
8402                 return -EINVAL;
8403         }
8404
8405         if (burst > policer_item->policer->max_burst) {
8406                 NL_SET_ERR_MSG_MOD(extack, "Policer burst size higher than limit");
8407                 return -EINVAL;
8408         }
8409
8410         err = devlink->ops->trap_policer_set(devlink, policer_item->policer,
8411                                              rate, burst, info->extack);
8412         if (err)
8413                 return err;
8414
8415         policer_item->rate = rate;
8416         policer_item->burst = burst;
8417
8418         return 0;
8419 }
8420
8421 static int devlink_nl_cmd_trap_policer_set_doit(struct sk_buff *skb,
8422                                                 struct genl_info *info)
8423 {
8424         struct devlink_trap_policer_item *policer_item;
8425         struct netlink_ext_ack *extack = info->extack;
8426         struct devlink *devlink = info->user_ptr[0];
8427
8428         if (list_empty(&devlink->trap_policer_list))
8429                 return -EOPNOTSUPP;
8430
8431         if (!devlink->ops->trap_policer_set)
8432                 return -EOPNOTSUPP;
8433
8434         policer_item = devlink_trap_policer_item_get_from_info(devlink, info);
8435         if (!policer_item) {
8436                 NL_SET_ERR_MSG_MOD(extack, "Device did not register this trap policer");
8437                 return -ENOENT;
8438         }
8439
8440         return devlink_trap_policer_set(devlink, policer_item, info);
8441 }
8442
8443 static const struct nla_policy devlink_nl_policy[DEVLINK_ATTR_MAX + 1] = {
8444         [DEVLINK_ATTR_UNSPEC] = { .strict_start_type =
8445                 DEVLINK_ATTR_TRAP_POLICER_ID },
8446         [DEVLINK_ATTR_BUS_NAME] = { .type = NLA_NUL_STRING },
8447         [DEVLINK_ATTR_DEV_NAME] = { .type = NLA_NUL_STRING },
8448         [DEVLINK_ATTR_PORT_INDEX] = { .type = NLA_U32 },
8449         [DEVLINK_ATTR_PORT_TYPE] = NLA_POLICY_RANGE(NLA_U16, DEVLINK_PORT_TYPE_AUTO,
8450                                                     DEVLINK_PORT_TYPE_IB),
8451         [DEVLINK_ATTR_PORT_SPLIT_COUNT] = { .type = NLA_U32 },
8452         [DEVLINK_ATTR_SB_INDEX] = { .type = NLA_U32 },
8453         [DEVLINK_ATTR_SB_POOL_INDEX] = { .type = NLA_U16 },
8454         [DEVLINK_ATTR_SB_POOL_TYPE] = { .type = NLA_U8 },
8455         [DEVLINK_ATTR_SB_POOL_SIZE] = { .type = NLA_U32 },
8456         [DEVLINK_ATTR_SB_POOL_THRESHOLD_TYPE] = { .type = NLA_U8 },
8457         [DEVLINK_ATTR_SB_THRESHOLD] = { .type = NLA_U32 },
8458         [DEVLINK_ATTR_SB_TC_INDEX] = { .type = NLA_U16 },
8459         [DEVLINK_ATTR_ESWITCH_MODE] = NLA_POLICY_RANGE(NLA_U16, DEVLINK_ESWITCH_MODE_LEGACY,
8460                                                        DEVLINK_ESWITCH_MODE_SWITCHDEV),
8461         [DEVLINK_ATTR_ESWITCH_INLINE_MODE] = { .type = NLA_U8 },
8462         [DEVLINK_ATTR_ESWITCH_ENCAP_MODE] = { .type = NLA_U8 },
8463         [DEVLINK_ATTR_DPIPE_TABLE_NAME] = { .type = NLA_NUL_STRING },
8464         [DEVLINK_ATTR_DPIPE_TABLE_COUNTERS_ENABLED] = { .type = NLA_U8 },
8465         [DEVLINK_ATTR_RESOURCE_ID] = { .type = NLA_U64},
8466         [DEVLINK_ATTR_RESOURCE_SIZE] = { .type = NLA_U64},
8467         [DEVLINK_ATTR_PARAM_NAME] = { .type = NLA_NUL_STRING },
8468         [DEVLINK_ATTR_PARAM_TYPE] = { .type = NLA_U8 },
8469         [DEVLINK_ATTR_PARAM_VALUE_CMODE] = { .type = NLA_U8 },
8470         [DEVLINK_ATTR_REGION_NAME] = { .type = NLA_NUL_STRING },
8471         [DEVLINK_ATTR_REGION_SNAPSHOT_ID] = { .type = NLA_U32 },
8472         [DEVLINK_ATTR_REGION_CHUNK_ADDR] = { .type = NLA_U64 },
8473         [DEVLINK_ATTR_REGION_CHUNK_LEN] = { .type = NLA_U64 },
8474         [DEVLINK_ATTR_HEALTH_REPORTER_NAME] = { .type = NLA_NUL_STRING },
8475         [DEVLINK_ATTR_HEALTH_REPORTER_GRACEFUL_PERIOD] = { .type = NLA_U64 },
8476         [DEVLINK_ATTR_HEALTH_REPORTER_AUTO_RECOVER] = { .type = NLA_U8 },
8477         [DEVLINK_ATTR_FLASH_UPDATE_FILE_NAME] = { .type = NLA_NUL_STRING },
8478         [DEVLINK_ATTR_FLASH_UPDATE_COMPONENT] = { .type = NLA_NUL_STRING },
8479         [DEVLINK_ATTR_FLASH_UPDATE_OVERWRITE_MASK] =
8480                 NLA_POLICY_BITFIELD32(DEVLINK_SUPPORTED_FLASH_OVERWRITE_SECTIONS),
8481         [DEVLINK_ATTR_TRAP_NAME] = { .type = NLA_NUL_STRING },
8482         [DEVLINK_ATTR_TRAP_ACTION] = { .type = NLA_U8 },
8483         [DEVLINK_ATTR_TRAP_GROUP_NAME] = { .type = NLA_NUL_STRING },
8484         [DEVLINK_ATTR_NETNS_PID] = { .type = NLA_U32 },
8485         [DEVLINK_ATTR_NETNS_FD] = { .type = NLA_U32 },
8486         [DEVLINK_ATTR_NETNS_ID] = { .type = NLA_U32 },
8487         [DEVLINK_ATTR_HEALTH_REPORTER_AUTO_DUMP] = { .type = NLA_U8 },
8488         [DEVLINK_ATTR_TRAP_POLICER_ID] = { .type = NLA_U32 },
8489         [DEVLINK_ATTR_TRAP_POLICER_RATE] = { .type = NLA_U64 },
8490         [DEVLINK_ATTR_TRAP_POLICER_BURST] = { .type = NLA_U64 },
8491         [DEVLINK_ATTR_PORT_FUNCTION] = { .type = NLA_NESTED },
8492         [DEVLINK_ATTR_RELOAD_ACTION] = NLA_POLICY_RANGE(NLA_U8, DEVLINK_RELOAD_ACTION_DRIVER_REINIT,
8493                                                         DEVLINK_RELOAD_ACTION_MAX),
8494         [DEVLINK_ATTR_RELOAD_LIMITS] = NLA_POLICY_BITFIELD32(DEVLINK_RELOAD_LIMITS_VALID_MASK),
8495         [DEVLINK_ATTR_PORT_FLAVOUR] = { .type = NLA_U16 },
8496         [DEVLINK_ATTR_PORT_PCI_PF_NUMBER] = { .type = NLA_U16 },
8497         [DEVLINK_ATTR_PORT_PCI_SF_NUMBER] = { .type = NLA_U32 },
8498         [DEVLINK_ATTR_PORT_CONTROLLER_NUMBER] = { .type = NLA_U32 },
8499         [DEVLINK_ATTR_RATE_TYPE] = { .type = NLA_U16 },
8500         [DEVLINK_ATTR_RATE_TX_SHARE] = { .type = NLA_U64 },
8501         [DEVLINK_ATTR_RATE_TX_MAX] = { .type = NLA_U64 },
8502         [DEVLINK_ATTR_RATE_NODE_NAME] = { .type = NLA_NUL_STRING },
8503         [DEVLINK_ATTR_RATE_PARENT_NODE_NAME] = { .type = NLA_NUL_STRING },
8504 };
8505
8506 static const struct genl_small_ops devlink_nl_ops[] = {
8507         {
8508                 .cmd = DEVLINK_CMD_GET,
8509                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8510                 .doit = devlink_nl_cmd_get_doit,
8511                 .dumpit = devlink_nl_cmd_get_dumpit,
8512                 /* can be retrieved by unprivileged users */
8513         },
8514         {
8515                 .cmd = DEVLINK_CMD_PORT_GET,
8516                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8517                 .doit = devlink_nl_cmd_port_get_doit,
8518                 .dumpit = devlink_nl_cmd_port_get_dumpit,
8519                 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
8520                 /* can be retrieved by unprivileged users */
8521         },
8522         {
8523                 .cmd = DEVLINK_CMD_PORT_SET,
8524                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8525                 .doit = devlink_nl_cmd_port_set_doit,
8526                 .flags = GENL_ADMIN_PERM,
8527                 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
8528         },
8529         {
8530                 .cmd = DEVLINK_CMD_RATE_GET,
8531                 .doit = devlink_nl_cmd_rate_get_doit,
8532                 .dumpit = devlink_nl_cmd_rate_get_dumpit,
8533                 .internal_flags = DEVLINK_NL_FLAG_NEED_RATE,
8534                 /* can be retrieved by unprivileged users */
8535         },
8536         {
8537                 .cmd = DEVLINK_CMD_RATE_SET,
8538                 .doit = devlink_nl_cmd_rate_set_doit,
8539                 .flags = GENL_ADMIN_PERM,
8540                 .internal_flags = DEVLINK_NL_FLAG_NEED_RATE,
8541         },
8542         {
8543                 .cmd = DEVLINK_CMD_RATE_NEW,
8544                 .doit = devlink_nl_cmd_rate_new_doit,
8545                 .flags = GENL_ADMIN_PERM,
8546         },
8547         {
8548                 .cmd = DEVLINK_CMD_RATE_DEL,
8549                 .doit = devlink_nl_cmd_rate_del_doit,
8550                 .flags = GENL_ADMIN_PERM,
8551                 .internal_flags = DEVLINK_NL_FLAG_NEED_RATE_NODE,
8552         },
8553         {
8554                 .cmd = DEVLINK_CMD_PORT_SPLIT,
8555                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8556                 .doit = devlink_nl_cmd_port_split_doit,
8557                 .flags = GENL_ADMIN_PERM,
8558                 .internal_flags = DEVLINK_NL_FLAG_NO_LOCK,
8559         },
8560         {
8561                 .cmd = DEVLINK_CMD_PORT_UNSPLIT,
8562                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8563                 .doit = devlink_nl_cmd_port_unsplit_doit,
8564                 .flags = GENL_ADMIN_PERM,
8565                 .internal_flags = DEVLINK_NL_FLAG_NO_LOCK,
8566         },
8567         {
8568                 .cmd = DEVLINK_CMD_PORT_NEW,
8569                 .doit = devlink_nl_cmd_port_new_doit,
8570                 .flags = GENL_ADMIN_PERM,
8571                 .internal_flags = DEVLINK_NL_FLAG_NO_LOCK,
8572         },
8573         {
8574                 .cmd = DEVLINK_CMD_PORT_DEL,
8575                 .doit = devlink_nl_cmd_port_del_doit,
8576                 .flags = GENL_ADMIN_PERM,
8577                 .internal_flags = DEVLINK_NL_FLAG_NO_LOCK,
8578         },
8579         {
8580                 .cmd = DEVLINK_CMD_SB_GET,
8581                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8582                 .doit = devlink_nl_cmd_sb_get_doit,
8583                 .dumpit = devlink_nl_cmd_sb_get_dumpit,
8584                 /* can be retrieved by unprivileged users */
8585         },
8586         {
8587                 .cmd = DEVLINK_CMD_SB_POOL_GET,
8588                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8589                 .doit = devlink_nl_cmd_sb_pool_get_doit,
8590                 .dumpit = devlink_nl_cmd_sb_pool_get_dumpit,
8591                 /* can be retrieved by unprivileged users */
8592         },
8593         {
8594                 .cmd = DEVLINK_CMD_SB_POOL_SET,
8595                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8596                 .doit = devlink_nl_cmd_sb_pool_set_doit,
8597                 .flags = GENL_ADMIN_PERM,
8598         },
8599         {
8600                 .cmd = DEVLINK_CMD_SB_PORT_POOL_GET,
8601                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8602                 .doit = devlink_nl_cmd_sb_port_pool_get_doit,
8603                 .dumpit = devlink_nl_cmd_sb_port_pool_get_dumpit,
8604                 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
8605                 /* can be retrieved by unprivileged users */
8606         },
8607         {
8608                 .cmd = DEVLINK_CMD_SB_PORT_POOL_SET,
8609                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8610                 .doit = devlink_nl_cmd_sb_port_pool_set_doit,
8611                 .flags = GENL_ADMIN_PERM,
8612                 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
8613         },
8614         {
8615                 .cmd = DEVLINK_CMD_SB_TC_POOL_BIND_GET,
8616                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8617                 .doit = devlink_nl_cmd_sb_tc_pool_bind_get_doit,
8618                 .dumpit = devlink_nl_cmd_sb_tc_pool_bind_get_dumpit,
8619                 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
8620                 /* can be retrieved by unprivileged users */
8621         },
8622         {
8623                 .cmd = DEVLINK_CMD_SB_TC_POOL_BIND_SET,
8624                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8625                 .doit = devlink_nl_cmd_sb_tc_pool_bind_set_doit,
8626                 .flags = GENL_ADMIN_PERM,
8627                 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
8628         },
8629         {
8630                 .cmd = DEVLINK_CMD_SB_OCC_SNAPSHOT,
8631                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8632                 .doit = devlink_nl_cmd_sb_occ_snapshot_doit,
8633                 .flags = GENL_ADMIN_PERM,
8634         },
8635         {
8636                 .cmd = DEVLINK_CMD_SB_OCC_MAX_CLEAR,
8637                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8638                 .doit = devlink_nl_cmd_sb_occ_max_clear_doit,
8639                 .flags = GENL_ADMIN_PERM,
8640         },
8641         {
8642                 .cmd = DEVLINK_CMD_ESWITCH_GET,
8643                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8644                 .doit = devlink_nl_cmd_eswitch_get_doit,
8645                 .flags = GENL_ADMIN_PERM,
8646                 .internal_flags = DEVLINK_NL_FLAG_NO_LOCK,
8647         },
8648         {
8649                 .cmd = DEVLINK_CMD_ESWITCH_SET,
8650                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8651                 .doit = devlink_nl_cmd_eswitch_set_doit,
8652                 .flags = GENL_ADMIN_PERM,
8653                 .internal_flags = DEVLINK_NL_FLAG_NO_LOCK,
8654         },
8655         {
8656                 .cmd = DEVLINK_CMD_DPIPE_TABLE_GET,
8657                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8658                 .doit = devlink_nl_cmd_dpipe_table_get,
8659                 /* can be retrieved by unprivileged users */
8660         },
8661         {
8662                 .cmd = DEVLINK_CMD_DPIPE_ENTRIES_GET,
8663                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8664                 .doit = devlink_nl_cmd_dpipe_entries_get,
8665                 /* can be retrieved by unprivileged users */
8666         },
8667         {
8668                 .cmd = DEVLINK_CMD_DPIPE_HEADERS_GET,
8669                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8670                 .doit = devlink_nl_cmd_dpipe_headers_get,
8671                 /* can be retrieved by unprivileged users */
8672         },
8673         {
8674                 .cmd = DEVLINK_CMD_DPIPE_TABLE_COUNTERS_SET,
8675                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8676                 .doit = devlink_nl_cmd_dpipe_table_counters_set,
8677                 .flags = GENL_ADMIN_PERM,
8678         },
8679         {
8680                 .cmd = DEVLINK_CMD_RESOURCE_SET,
8681                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8682                 .doit = devlink_nl_cmd_resource_set,
8683                 .flags = GENL_ADMIN_PERM,
8684         },
8685         {
8686                 .cmd = DEVLINK_CMD_RESOURCE_DUMP,
8687                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8688                 .doit = devlink_nl_cmd_resource_dump,
8689                 /* can be retrieved by unprivileged users */
8690         },
8691         {
8692                 .cmd = DEVLINK_CMD_RELOAD,
8693                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8694                 .doit = devlink_nl_cmd_reload,
8695                 .flags = GENL_ADMIN_PERM,
8696                 .internal_flags = DEVLINK_NL_FLAG_NO_LOCK,
8697         },
8698         {
8699                 .cmd = DEVLINK_CMD_PARAM_GET,
8700                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8701                 .doit = devlink_nl_cmd_param_get_doit,
8702                 .dumpit = devlink_nl_cmd_param_get_dumpit,
8703                 /* can be retrieved by unprivileged users */
8704         },
8705         {
8706                 .cmd = DEVLINK_CMD_PARAM_SET,
8707                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8708                 .doit = devlink_nl_cmd_param_set_doit,
8709                 .flags = GENL_ADMIN_PERM,
8710         },
8711         {
8712                 .cmd = DEVLINK_CMD_PORT_PARAM_GET,
8713                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8714                 .doit = devlink_nl_cmd_port_param_get_doit,
8715                 .dumpit = devlink_nl_cmd_port_param_get_dumpit,
8716                 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
8717                 /* can be retrieved by unprivileged users */
8718         },
8719         {
8720                 .cmd = DEVLINK_CMD_PORT_PARAM_SET,
8721                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8722                 .doit = devlink_nl_cmd_port_param_set_doit,
8723                 .flags = GENL_ADMIN_PERM,
8724                 .internal_flags = DEVLINK_NL_FLAG_NEED_PORT,
8725         },
8726         {
8727                 .cmd = DEVLINK_CMD_REGION_GET,
8728                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8729                 .doit = devlink_nl_cmd_region_get_doit,
8730                 .dumpit = devlink_nl_cmd_region_get_dumpit,
8731                 .flags = GENL_ADMIN_PERM,
8732         },
8733         {
8734                 .cmd = DEVLINK_CMD_REGION_NEW,
8735                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8736                 .doit = devlink_nl_cmd_region_new,
8737                 .flags = GENL_ADMIN_PERM,
8738         },
8739         {
8740                 .cmd = DEVLINK_CMD_REGION_DEL,
8741                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8742                 .doit = devlink_nl_cmd_region_del,
8743                 .flags = GENL_ADMIN_PERM,
8744         },
8745         {
8746                 .cmd = DEVLINK_CMD_REGION_READ,
8747                 .validate = GENL_DONT_VALIDATE_STRICT |
8748                             GENL_DONT_VALIDATE_DUMP_STRICT,
8749                 .dumpit = devlink_nl_cmd_region_read_dumpit,
8750                 .flags = GENL_ADMIN_PERM,
8751         },
8752         {
8753                 .cmd = DEVLINK_CMD_INFO_GET,
8754                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8755                 .doit = devlink_nl_cmd_info_get_doit,
8756                 .dumpit = devlink_nl_cmd_info_get_dumpit,
8757                 /* can be retrieved by unprivileged users */
8758         },
8759         {
8760                 .cmd = DEVLINK_CMD_HEALTH_REPORTER_GET,
8761                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8762                 .doit = devlink_nl_cmd_health_reporter_get_doit,
8763                 .dumpit = devlink_nl_cmd_health_reporter_get_dumpit,
8764                 .internal_flags = DEVLINK_NL_FLAG_NEED_DEVLINK_OR_PORT |
8765                                   DEVLINK_NL_FLAG_NO_LOCK,
8766                 /* can be retrieved by unprivileged users */
8767         },
8768         {
8769                 .cmd = DEVLINK_CMD_HEALTH_REPORTER_SET,
8770                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8771                 .doit = devlink_nl_cmd_health_reporter_set_doit,
8772                 .flags = GENL_ADMIN_PERM,
8773                 .internal_flags = DEVLINK_NL_FLAG_NEED_DEVLINK_OR_PORT |
8774                                   DEVLINK_NL_FLAG_NO_LOCK,
8775         },
8776         {
8777                 .cmd = DEVLINK_CMD_HEALTH_REPORTER_RECOVER,
8778                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8779                 .doit = devlink_nl_cmd_health_reporter_recover_doit,
8780                 .flags = GENL_ADMIN_PERM,
8781                 .internal_flags = DEVLINK_NL_FLAG_NEED_DEVLINK_OR_PORT |
8782                                   DEVLINK_NL_FLAG_NO_LOCK,
8783         },
8784         {
8785                 .cmd = DEVLINK_CMD_HEALTH_REPORTER_DIAGNOSE,
8786                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8787                 .doit = devlink_nl_cmd_health_reporter_diagnose_doit,
8788                 .flags = GENL_ADMIN_PERM,
8789                 .internal_flags = DEVLINK_NL_FLAG_NEED_DEVLINK_OR_PORT |
8790                                   DEVLINK_NL_FLAG_NO_LOCK,
8791         },
8792         {
8793                 .cmd = DEVLINK_CMD_HEALTH_REPORTER_DUMP_GET,
8794                 .validate = GENL_DONT_VALIDATE_STRICT |
8795                             GENL_DONT_VALIDATE_DUMP_STRICT,
8796                 .dumpit = devlink_nl_cmd_health_reporter_dump_get_dumpit,
8797                 .flags = GENL_ADMIN_PERM,
8798                 .internal_flags = DEVLINK_NL_FLAG_NEED_DEVLINK_OR_PORT |
8799                                   DEVLINK_NL_FLAG_NO_LOCK,
8800         },
8801         {
8802                 .cmd = DEVLINK_CMD_HEALTH_REPORTER_DUMP_CLEAR,
8803                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8804                 .doit = devlink_nl_cmd_health_reporter_dump_clear_doit,
8805                 .flags = GENL_ADMIN_PERM,
8806                 .internal_flags = DEVLINK_NL_FLAG_NEED_DEVLINK_OR_PORT |
8807                                   DEVLINK_NL_FLAG_NO_LOCK,
8808         },
8809         {
8810                 .cmd = DEVLINK_CMD_HEALTH_REPORTER_TEST,
8811                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8812                 .doit = devlink_nl_cmd_health_reporter_test_doit,
8813                 .flags = GENL_ADMIN_PERM,
8814                 .internal_flags = DEVLINK_NL_FLAG_NEED_DEVLINK_OR_PORT |
8815                                   DEVLINK_NL_FLAG_NO_LOCK,
8816         },
8817         {
8818                 .cmd = DEVLINK_CMD_FLASH_UPDATE,
8819                 .validate = GENL_DONT_VALIDATE_STRICT | GENL_DONT_VALIDATE_DUMP,
8820                 .doit = devlink_nl_cmd_flash_update,
8821                 .flags = GENL_ADMIN_PERM,
8822         },
8823         {
8824                 .cmd = DEVLINK_CMD_TRAP_GET,
8825                 .doit = devlink_nl_cmd_trap_get_doit,
8826                 .dumpit = devlink_nl_cmd_trap_get_dumpit,
8827                 /* can be retrieved by unprivileged users */
8828         },
8829         {
8830                 .cmd = DEVLINK_CMD_TRAP_SET,
8831                 .doit = devlink_nl_cmd_trap_set_doit,
8832                 .flags = GENL_ADMIN_PERM,
8833         },
8834         {
8835                 .cmd = DEVLINK_CMD_TRAP_GROUP_GET,
8836                 .doit = devlink_nl_cmd_trap_group_get_doit,
8837                 .dumpit = devlink_nl_cmd_trap_group_get_dumpit,
8838                 /* can be retrieved by unprivileged users */
8839         },
8840         {
8841                 .cmd = DEVLINK_CMD_TRAP_GROUP_SET,
8842                 .doit = devlink_nl_cmd_trap_group_set_doit,
8843                 .flags = GENL_ADMIN_PERM,
8844         },
8845         {
8846                 .cmd = DEVLINK_CMD_TRAP_POLICER_GET,
8847                 .doit = devlink_nl_cmd_trap_policer_get_doit,
8848                 .dumpit = devlink_nl_cmd_trap_policer_get_dumpit,
8849                 /* can be retrieved by unprivileged users */
8850         },
8851         {
8852                 .cmd = DEVLINK_CMD_TRAP_POLICER_SET,
8853                 .doit = devlink_nl_cmd_trap_policer_set_doit,
8854                 .flags = GENL_ADMIN_PERM,
8855         },
8856 };
8857
8858 static struct genl_family devlink_nl_family __ro_after_init = {
8859         .name           = DEVLINK_GENL_NAME,
8860         .version        = DEVLINK_GENL_VERSION,
8861         .maxattr        = DEVLINK_ATTR_MAX,
8862         .policy = devlink_nl_policy,
8863         .netnsok        = true,
8864         .pre_doit       = devlink_nl_pre_doit,
8865         .post_doit      = devlink_nl_post_doit,
8866         .module         = THIS_MODULE,
8867         .small_ops      = devlink_nl_ops,
8868         .n_small_ops    = ARRAY_SIZE(devlink_nl_ops),
8869         .mcgrps         = devlink_nl_mcgrps,
8870         .n_mcgrps       = ARRAY_SIZE(devlink_nl_mcgrps),
8871 };
8872
8873 static bool devlink_reload_actions_valid(const struct devlink_ops *ops)
8874 {
8875         const struct devlink_reload_combination *comb;
8876         int i;
8877
8878         if (!devlink_reload_supported(ops)) {
8879                 if (WARN_ON(ops->reload_actions))
8880                         return false;
8881                 return true;
8882         }
8883
8884         if (WARN_ON(!ops->reload_actions ||
8885                     ops->reload_actions & BIT(DEVLINK_RELOAD_ACTION_UNSPEC) ||
8886                     ops->reload_actions >= BIT(__DEVLINK_RELOAD_ACTION_MAX)))
8887                 return false;
8888
8889         if (WARN_ON(ops->reload_limits & BIT(DEVLINK_RELOAD_LIMIT_UNSPEC) ||
8890                     ops->reload_limits >= BIT(__DEVLINK_RELOAD_LIMIT_MAX)))
8891                 return false;
8892
8893         for (i = 0; i < ARRAY_SIZE(devlink_reload_invalid_combinations); i++)  {
8894                 comb = &devlink_reload_invalid_combinations[i];
8895                 if (ops->reload_actions == BIT(comb->action) &&
8896                     ops->reload_limits == BIT(comb->limit))
8897                         return false;
8898         }
8899         return true;
8900 }
8901
8902 /**
8903  *      devlink_alloc_ns - Allocate new devlink instance resources
8904  *      in specific namespace
8905  *
8906  *      @ops: ops
8907  *      @priv_size: size of user private data
8908  *      @net: net namespace
8909  *      @dev: parent device
8910  *
8911  *      Allocate new devlink instance resources, including devlink index
8912  *      and name.
8913  */
8914 struct devlink *devlink_alloc_ns(const struct devlink_ops *ops,
8915                                  size_t priv_size, struct net *net,
8916                                  struct device *dev)
8917 {
8918         struct devlink *devlink;
8919         static u32 last_id;
8920         int ret;
8921
8922         WARN_ON(!ops || !dev);
8923         if (!devlink_reload_actions_valid(ops))
8924                 return NULL;
8925
8926         devlink = kzalloc(sizeof(*devlink) + priv_size, GFP_KERNEL);
8927         if (!devlink)
8928                 return NULL;
8929
8930         ret = xa_alloc_cyclic(&devlinks, &devlink->index, devlink, xa_limit_31b,
8931                               &last_id, GFP_KERNEL);
8932         if (ret < 0) {
8933                 kfree(devlink);
8934                 return NULL;
8935         }
8936
8937         devlink->dev = dev;
8938         devlink->ops = ops;
8939         xa_init_flags(&devlink->snapshot_ids, XA_FLAGS_ALLOC);
8940         write_pnet(&devlink->_net, net);
8941         INIT_LIST_HEAD(&devlink->port_list);
8942         INIT_LIST_HEAD(&devlink->rate_list);
8943         INIT_LIST_HEAD(&devlink->sb_list);
8944         INIT_LIST_HEAD_RCU(&devlink->dpipe_table_list);
8945         INIT_LIST_HEAD(&devlink->resource_list);
8946         INIT_LIST_HEAD(&devlink->param_list);
8947         INIT_LIST_HEAD(&devlink->region_list);
8948         INIT_LIST_HEAD(&devlink->reporter_list);
8949         INIT_LIST_HEAD(&devlink->trap_list);
8950         INIT_LIST_HEAD(&devlink->trap_group_list);
8951         INIT_LIST_HEAD(&devlink->trap_policer_list);
8952         mutex_init(&devlink->lock);
8953         mutex_init(&devlink->reporters_lock);
8954         refcount_set(&devlink->refcount, 1);
8955         init_completion(&devlink->comp);
8956
8957         return devlink;
8958 }
8959 EXPORT_SYMBOL_GPL(devlink_alloc_ns);
8960
8961 /**
8962  *      devlink_register - Register devlink instance
8963  *
8964  *      @devlink: devlink
8965  */
8966 int devlink_register(struct devlink *devlink)
8967 {
8968         mutex_lock(&devlink_mutex);
8969         xa_set_mark(&devlinks, devlink->index, DEVLINK_REGISTERED);
8970         devlink_notify(devlink, DEVLINK_CMD_NEW);
8971         mutex_unlock(&devlink_mutex);
8972         return 0;
8973 }
8974 EXPORT_SYMBOL_GPL(devlink_register);
8975
8976 /**
8977  *      devlink_unregister - Unregister devlink instance
8978  *
8979  *      @devlink: devlink
8980  */
8981 void devlink_unregister(struct devlink *devlink)
8982 {
8983         devlink_put(devlink);
8984         wait_for_completion(&devlink->comp);
8985
8986         mutex_lock(&devlink_mutex);
8987         WARN_ON(devlink_reload_supported(devlink->ops) &&
8988                 devlink->reload_enabled);
8989         devlink_notify(devlink, DEVLINK_CMD_DEL);
8990         xa_clear_mark(&devlinks, devlink->index, DEVLINK_REGISTERED);
8991         mutex_unlock(&devlink_mutex);
8992 }
8993 EXPORT_SYMBOL_GPL(devlink_unregister);
8994
8995 /**
8996  *      devlink_reload_enable - Enable reload of devlink instance
8997  *
8998  *      @devlink: devlink
8999  *
9000  *      Should be called at end of device initialization
9001  *      process when reload operation is supported.
9002  */
9003 void devlink_reload_enable(struct devlink *devlink)
9004 {
9005         mutex_lock(&devlink_mutex);
9006         devlink->reload_enabled = true;
9007         mutex_unlock(&devlink_mutex);
9008 }
9009 EXPORT_SYMBOL_GPL(devlink_reload_enable);
9010
9011 /**
9012  *      devlink_reload_disable - Disable reload of devlink instance
9013  *
9014  *      @devlink: devlink
9015  *
9016  *      Should be called at the beginning of device cleanup
9017  *      process when reload operation is supported.
9018  */
9019 void devlink_reload_disable(struct devlink *devlink)
9020 {
9021         mutex_lock(&devlink_mutex);
9022         /* Mutex is taken which ensures that no reload operation is in
9023          * progress while setting up forbidded flag.
9024          */
9025         devlink->reload_enabled = false;
9026         mutex_unlock(&devlink_mutex);
9027 }
9028 EXPORT_SYMBOL_GPL(devlink_reload_disable);
9029
9030 /**
9031  *      devlink_free - Free devlink instance resources
9032  *
9033  *      @devlink: devlink
9034  */
9035 void devlink_free(struct devlink *devlink)
9036 {
9037         mutex_destroy(&devlink->reporters_lock);
9038         mutex_destroy(&devlink->lock);
9039         WARN_ON(!list_empty(&devlink->trap_policer_list));
9040         WARN_ON(!list_empty(&devlink->trap_group_list));
9041         WARN_ON(!list_empty(&devlink->trap_list));
9042         WARN_ON(!list_empty(&devlink->reporter_list));
9043         WARN_ON(!list_empty(&devlink->region_list));
9044         WARN_ON(!list_empty(&devlink->param_list));
9045         WARN_ON(!list_empty(&devlink->resource_list));
9046         WARN_ON(!list_empty(&devlink->dpipe_table_list));
9047         WARN_ON(!list_empty(&devlink->sb_list));
9048         WARN_ON(!list_empty(&devlink->rate_list));
9049         WARN_ON(!list_empty(&devlink->port_list));
9050
9051         xa_destroy(&devlink->snapshot_ids);
9052         xa_erase(&devlinks, devlink->index);
9053
9054         kfree(devlink);
9055 }
9056 EXPORT_SYMBOL_GPL(devlink_free);
9057
9058 static void devlink_port_type_warn(struct work_struct *work)
9059 {
9060         WARN(true, "Type was not set for devlink port.");
9061 }
9062
9063 static bool devlink_port_type_should_warn(struct devlink_port *devlink_port)
9064 {
9065         /* Ignore CPU and DSA flavours. */
9066         return devlink_port->attrs.flavour != DEVLINK_PORT_FLAVOUR_CPU &&
9067                devlink_port->attrs.flavour != DEVLINK_PORT_FLAVOUR_DSA &&
9068                devlink_port->attrs.flavour != DEVLINK_PORT_FLAVOUR_UNUSED;
9069 }
9070
9071 #define DEVLINK_PORT_TYPE_WARN_TIMEOUT (HZ * 3600)
9072
9073 static void devlink_port_type_warn_schedule(struct devlink_port *devlink_port)
9074 {
9075         if (!devlink_port_type_should_warn(devlink_port))
9076                 return;
9077         /* Schedule a work to WARN in case driver does not set port
9078          * type within timeout.
9079          */
9080         schedule_delayed_work(&devlink_port->type_warn_dw,
9081                               DEVLINK_PORT_TYPE_WARN_TIMEOUT);
9082 }
9083
9084 static void devlink_port_type_warn_cancel(struct devlink_port *devlink_port)
9085 {
9086         if (!devlink_port_type_should_warn(devlink_port))
9087                 return;
9088         cancel_delayed_work_sync(&devlink_port->type_warn_dw);
9089 }
9090
9091 /**
9092  *      devlink_port_register - Register devlink port
9093  *
9094  *      @devlink: devlink
9095  *      @devlink_port: devlink port
9096  *      @port_index: driver-specific numerical identifier of the port
9097  *
9098  *      Register devlink port with provided port index. User can use
9099  *      any indexing, even hw-related one. devlink_port structure
9100  *      is convenient to be embedded inside user driver private structure.
9101  *      Note that the caller should take care of zeroing the devlink_port
9102  *      structure.
9103  */
9104 int devlink_port_register(struct devlink *devlink,
9105                           struct devlink_port *devlink_port,
9106                           unsigned int port_index)
9107 {
9108         mutex_lock(&devlink->lock);
9109         if (devlink_port_index_exists(devlink, port_index)) {
9110                 mutex_unlock(&devlink->lock);
9111                 return -EEXIST;
9112         }
9113
9114         WARN_ON(devlink_port->devlink);
9115         devlink_port->devlink = devlink;
9116         devlink_port->index = port_index;
9117         spin_lock_init(&devlink_port->type_lock);
9118         INIT_LIST_HEAD(&devlink_port->reporter_list);
9119         mutex_init(&devlink_port->reporters_lock);
9120         list_add_tail(&devlink_port->list, &devlink->port_list);
9121         INIT_LIST_HEAD(&devlink_port->param_list);
9122         INIT_LIST_HEAD(&devlink_port->region_list);
9123         mutex_unlock(&devlink->lock);
9124         INIT_DELAYED_WORK(&devlink_port->type_warn_dw, &devlink_port_type_warn);
9125         devlink_port_type_warn_schedule(devlink_port);
9126         devlink_port_notify(devlink_port, DEVLINK_CMD_PORT_NEW);
9127         return 0;
9128 }
9129 EXPORT_SYMBOL_GPL(devlink_port_register);
9130
9131 /**
9132  *      devlink_port_unregister - Unregister devlink port
9133  *
9134  *      @devlink_port: devlink port
9135  */
9136 void devlink_port_unregister(struct devlink_port *devlink_port)
9137 {
9138         struct devlink *devlink = devlink_port->devlink;
9139
9140         devlink_port_type_warn_cancel(devlink_port);
9141         devlink_port_notify(devlink_port, DEVLINK_CMD_PORT_DEL);
9142         mutex_lock(&devlink->lock);
9143         list_del(&devlink_port->list);
9144         mutex_unlock(&devlink->lock);
9145         WARN_ON(!list_empty(&devlink_port->reporter_list));
9146         WARN_ON(!list_empty(&devlink_port->region_list));
9147         mutex_destroy(&devlink_port->reporters_lock);
9148 }
9149 EXPORT_SYMBOL_GPL(devlink_port_unregister);
9150
9151 static void __devlink_port_type_set(struct devlink_port *devlink_port,
9152                                     enum devlink_port_type type,
9153                                     void *type_dev)
9154 {
9155         if (WARN_ON(!devlink_port->devlink))
9156                 return;
9157         devlink_port_type_warn_cancel(devlink_port);
9158         spin_lock_bh(&devlink_port->type_lock);
9159         devlink_port->type = type;
9160         devlink_port->type_dev = type_dev;
9161         spin_unlock_bh(&devlink_port->type_lock);
9162         devlink_port_notify(devlink_port, DEVLINK_CMD_PORT_NEW);
9163 }
9164
9165 static void devlink_port_type_netdev_checks(struct devlink_port *devlink_port,
9166                                             struct net_device *netdev)
9167 {
9168         const struct net_device_ops *ops = netdev->netdev_ops;
9169
9170         /* If driver registers devlink port, it should set devlink port
9171          * attributes accordingly so the compat functions are called
9172          * and the original ops are not used.
9173          */
9174         if (ops->ndo_get_phys_port_name) {
9175                 /* Some drivers use the same set of ndos for netdevs
9176                  * that have devlink_port registered and also for
9177                  * those who don't. Make sure that ndo_get_phys_port_name
9178                  * returns -EOPNOTSUPP here in case it is defined.
9179                  * Warn if not.
9180                  */
9181                 char name[IFNAMSIZ];
9182                 int err;
9183
9184                 err = ops->ndo_get_phys_port_name(netdev, name, sizeof(name));
9185                 WARN_ON(err != -EOPNOTSUPP);
9186         }
9187         if (ops->ndo_get_port_parent_id) {
9188                 /* Some drivers use the same set of ndos for netdevs
9189                  * that have devlink_port registered and also for
9190                  * those who don't. Make sure that ndo_get_port_parent_id
9191                  * returns -EOPNOTSUPP here in case it is defined.
9192                  * Warn if not.
9193                  */
9194                 struct netdev_phys_item_id ppid;
9195                 int err;
9196
9197                 err = ops->ndo_get_port_parent_id(netdev, &ppid);
9198                 WARN_ON(err != -EOPNOTSUPP);
9199         }
9200 }
9201
9202 /**
9203  *      devlink_port_type_eth_set - Set port type to Ethernet
9204  *
9205  *      @devlink_port: devlink port
9206  *      @netdev: related netdevice
9207  */
9208 void devlink_port_type_eth_set(struct devlink_port *devlink_port,
9209                                struct net_device *netdev)
9210 {
9211         if (netdev)
9212                 devlink_port_type_netdev_checks(devlink_port, netdev);
9213         else
9214                 dev_warn(devlink_port->devlink->dev,
9215                          "devlink port type for port %d set to Ethernet without a software interface reference, device type not supported by the kernel?\n",
9216                          devlink_port->index);
9217
9218         __devlink_port_type_set(devlink_port, DEVLINK_PORT_TYPE_ETH, netdev);
9219 }
9220 EXPORT_SYMBOL_GPL(devlink_port_type_eth_set);
9221
9222 /**
9223  *      devlink_port_type_ib_set - Set port type to InfiniBand
9224  *
9225  *      @devlink_port: devlink port
9226  *      @ibdev: related IB device
9227  */
9228 void devlink_port_type_ib_set(struct devlink_port *devlink_port,
9229                               struct ib_device *ibdev)
9230 {
9231         __devlink_port_type_set(devlink_port, DEVLINK_PORT_TYPE_IB, ibdev);
9232 }
9233 EXPORT_SYMBOL_GPL(devlink_port_type_ib_set);
9234
9235 /**
9236  *      devlink_port_type_clear - Clear port type
9237  *
9238  *      @devlink_port: devlink port
9239  */
9240 void devlink_port_type_clear(struct devlink_port *devlink_port)
9241 {
9242         __devlink_port_type_set(devlink_port, DEVLINK_PORT_TYPE_NOTSET, NULL);
9243         devlink_port_type_warn_schedule(devlink_port);
9244 }
9245 EXPORT_SYMBOL_GPL(devlink_port_type_clear);
9246
9247 static int __devlink_port_attrs_set(struct devlink_port *devlink_port,
9248                                     enum devlink_port_flavour flavour)
9249 {
9250         struct devlink_port_attrs *attrs = &devlink_port->attrs;
9251
9252         devlink_port->attrs_set = true;
9253         attrs->flavour = flavour;
9254         if (attrs->switch_id.id_len) {
9255                 devlink_port->switch_port = true;
9256                 if (WARN_ON(attrs->switch_id.id_len > MAX_PHYS_ITEM_ID_LEN))
9257                         attrs->switch_id.id_len = MAX_PHYS_ITEM_ID_LEN;
9258         } else {
9259                 devlink_port->switch_port = false;
9260         }
9261         return 0;
9262 }
9263
9264 /**
9265  *      devlink_port_attrs_set - Set port attributes
9266  *
9267  *      @devlink_port: devlink port
9268  *      @attrs: devlink port attrs
9269  */
9270 void devlink_port_attrs_set(struct devlink_port *devlink_port,
9271                             struct devlink_port_attrs *attrs)
9272 {
9273         int ret;
9274
9275         if (WARN_ON(devlink_port->devlink))
9276                 return;
9277         devlink_port->attrs = *attrs;
9278         ret = __devlink_port_attrs_set(devlink_port, attrs->flavour);
9279         if (ret)
9280                 return;
9281         WARN_ON(attrs->splittable && attrs->split);
9282 }
9283 EXPORT_SYMBOL_GPL(devlink_port_attrs_set);
9284
9285 /**
9286  *      devlink_port_attrs_pci_pf_set - Set PCI PF port attributes
9287  *
9288  *      @devlink_port: devlink port
9289  *      @controller: associated controller number for the devlink port instance
9290  *      @pf: associated PF for the devlink port instance
9291  *      @external: indicates if the port is for an external controller
9292  */
9293 void devlink_port_attrs_pci_pf_set(struct devlink_port *devlink_port, u32 controller,
9294                                    u16 pf, bool external)
9295 {
9296         struct devlink_port_attrs *attrs = &devlink_port->attrs;
9297         int ret;
9298
9299         if (WARN_ON(devlink_port->devlink))
9300                 return;
9301         ret = __devlink_port_attrs_set(devlink_port,
9302                                        DEVLINK_PORT_FLAVOUR_PCI_PF);
9303         if (ret)
9304                 return;
9305         attrs->pci_pf.controller = controller;
9306         attrs->pci_pf.pf = pf;
9307         attrs->pci_pf.external = external;
9308 }
9309 EXPORT_SYMBOL_GPL(devlink_port_attrs_pci_pf_set);
9310
9311 /**
9312  *      devlink_port_attrs_pci_vf_set - Set PCI VF port attributes
9313  *
9314  *      @devlink_port: devlink port
9315  *      @controller: associated controller number for the devlink port instance
9316  *      @pf: associated PF for the devlink port instance
9317  *      @vf: associated VF of a PF for the devlink port instance
9318  *      @external: indicates if the port is for an external controller
9319  */
9320 void devlink_port_attrs_pci_vf_set(struct devlink_port *devlink_port, u32 controller,
9321                                    u16 pf, u16 vf, bool external)
9322 {
9323         struct devlink_port_attrs *attrs = &devlink_port->attrs;
9324         int ret;
9325
9326         if (WARN_ON(devlink_port->devlink))
9327                 return;
9328         ret = __devlink_port_attrs_set(devlink_port,
9329                                        DEVLINK_PORT_FLAVOUR_PCI_VF);
9330         if (ret)
9331                 return;
9332         attrs->pci_vf.controller = controller;
9333         attrs->pci_vf.pf = pf;
9334         attrs->pci_vf.vf = vf;
9335         attrs->pci_vf.external = external;
9336 }
9337 EXPORT_SYMBOL_GPL(devlink_port_attrs_pci_vf_set);
9338
9339 /**
9340  *      devlink_port_attrs_pci_sf_set - Set PCI SF port attributes
9341  *
9342  *      @devlink_port: devlink port
9343  *      @controller: associated controller number for the devlink port instance
9344  *      @pf: associated PF for the devlink port instance
9345  *      @sf: associated SF of a PF for the devlink port instance
9346  *      @external: indicates if the port is for an external controller
9347  */
9348 void devlink_port_attrs_pci_sf_set(struct devlink_port *devlink_port, u32 controller,
9349                                    u16 pf, u32 sf, bool external)
9350 {
9351         struct devlink_port_attrs *attrs = &devlink_port->attrs;
9352         int ret;
9353
9354         if (WARN_ON(devlink_port->devlink))
9355                 return;
9356         ret = __devlink_port_attrs_set(devlink_port,
9357                                        DEVLINK_PORT_FLAVOUR_PCI_SF);
9358         if (ret)
9359                 return;
9360         attrs->pci_sf.controller = controller;
9361         attrs->pci_sf.pf = pf;
9362         attrs->pci_sf.sf = sf;
9363         attrs->pci_sf.external = external;
9364 }
9365 EXPORT_SYMBOL_GPL(devlink_port_attrs_pci_sf_set);
9366
9367 /**
9368  * devlink_rate_leaf_create - create devlink rate leaf
9369  *
9370  * @devlink_port: devlink port object to create rate object on
9371  * @priv: driver private data
9372  *
9373  * Create devlink rate object of type leaf on provided @devlink_port.
9374  * Throws call trace if @devlink_port already has a devlink rate object.
9375  *
9376  * Context: Takes and release devlink->lock <mutex>.
9377  *
9378  * Return: -ENOMEM if failed to allocate rate object, 0 otherwise.
9379  */
9380 int
9381 devlink_rate_leaf_create(struct devlink_port *devlink_port, void *priv)
9382 {
9383         struct devlink *devlink = devlink_port->devlink;
9384         struct devlink_rate *devlink_rate;
9385
9386         devlink_rate = kzalloc(sizeof(*devlink_rate), GFP_KERNEL);
9387         if (!devlink_rate)
9388                 return -ENOMEM;
9389
9390         mutex_lock(&devlink->lock);
9391         WARN_ON(devlink_port->devlink_rate);
9392         devlink_rate->type = DEVLINK_RATE_TYPE_LEAF;
9393         devlink_rate->devlink = devlink;
9394         devlink_rate->devlink_port = devlink_port;
9395         devlink_rate->priv = priv;
9396         list_add_tail(&devlink_rate->list, &devlink->rate_list);
9397         devlink_port->devlink_rate = devlink_rate;
9398         devlink_rate_notify(devlink_rate, DEVLINK_CMD_RATE_NEW);
9399         mutex_unlock(&devlink->lock);
9400
9401         return 0;
9402 }
9403 EXPORT_SYMBOL_GPL(devlink_rate_leaf_create);
9404
9405 /**
9406  * devlink_rate_leaf_destroy - destroy devlink rate leaf
9407  *
9408  * @devlink_port: devlink port linked to the rate object
9409  *
9410  * Context: Takes and release devlink->lock <mutex>.
9411  */
9412 void devlink_rate_leaf_destroy(struct devlink_port *devlink_port)
9413 {
9414         struct devlink_rate *devlink_rate = devlink_port->devlink_rate;
9415         struct devlink *devlink = devlink_port->devlink;
9416
9417         if (!devlink_rate)
9418                 return;
9419
9420         mutex_lock(&devlink->lock);
9421         devlink_rate_notify(devlink_rate, DEVLINK_CMD_RATE_DEL);
9422         if (devlink_rate->parent)
9423                 refcount_dec(&devlink_rate->parent->refcnt);
9424         list_del(&devlink_rate->list);
9425         devlink_port->devlink_rate = NULL;
9426         mutex_unlock(&devlink->lock);
9427         kfree(devlink_rate);
9428 }
9429 EXPORT_SYMBOL_GPL(devlink_rate_leaf_destroy);
9430
9431 /**
9432  * devlink_rate_nodes_destroy - destroy all devlink rate nodes on device
9433  *
9434  * @devlink: devlink instance
9435  *
9436  * Unset parent for all rate objects and destroy all rate nodes
9437  * on specified device.
9438  *
9439  * Context: Takes and release devlink->lock <mutex>.
9440  */
9441 void devlink_rate_nodes_destroy(struct devlink *devlink)
9442 {
9443         static struct devlink_rate *devlink_rate, *tmp;
9444         const struct devlink_ops *ops = devlink->ops;
9445
9446         mutex_lock(&devlink->lock);
9447         list_for_each_entry(devlink_rate, &devlink->rate_list, list) {
9448                 if (!devlink_rate->parent)
9449                         continue;
9450
9451                 refcount_dec(&devlink_rate->parent->refcnt);
9452                 if (devlink_rate_is_leaf(devlink_rate))
9453                         ops->rate_leaf_parent_set(devlink_rate, NULL, devlink_rate->priv,
9454                                                   NULL, NULL);
9455                 else if (devlink_rate_is_node(devlink_rate))
9456                         ops->rate_node_parent_set(devlink_rate, NULL, devlink_rate->priv,
9457                                                   NULL, NULL);
9458         }
9459         list_for_each_entry_safe(devlink_rate, tmp, &devlink->rate_list, list) {
9460                 if (devlink_rate_is_node(devlink_rate)) {
9461                         ops->rate_node_del(devlink_rate, devlink_rate->priv, NULL);
9462                         list_del(&devlink_rate->list);
9463                         kfree(devlink_rate->name);
9464                         kfree(devlink_rate);
9465                 }
9466         }
9467         mutex_unlock(&devlink->lock);
9468 }
9469 EXPORT_SYMBOL_GPL(devlink_rate_nodes_destroy);
9470
9471 static int __devlink_port_phys_port_name_get(struct devlink_port *devlink_port,
9472                                              char *name, size_t len)
9473 {
9474         struct devlink_port_attrs *attrs = &devlink_port->attrs;
9475         int n = 0;
9476
9477         if (!devlink_port->attrs_set)
9478                 return -EOPNOTSUPP;
9479
9480         switch (attrs->flavour) {
9481         case DEVLINK_PORT_FLAVOUR_PHYSICAL:
9482                 n = snprintf(name, len, "p%u", attrs->phys.port_number);
9483                 if (n < len && attrs->split)
9484                         n += snprintf(name + n, len - n, "s%u",
9485                                       attrs->phys.split_subport_number);
9486                 break;
9487         case DEVLINK_PORT_FLAVOUR_CPU:
9488         case DEVLINK_PORT_FLAVOUR_DSA:
9489         case DEVLINK_PORT_FLAVOUR_UNUSED:
9490                 /* As CPU and DSA ports do not have a netdevice associated
9491                  * case should not ever happen.
9492                  */
9493                 WARN_ON(1);
9494                 return -EINVAL;
9495         case DEVLINK_PORT_FLAVOUR_PCI_PF:
9496                 if (attrs->pci_pf.external) {
9497                         n = snprintf(name, len, "c%u", attrs->pci_pf.controller);
9498                         if (n >= len)
9499                                 return -EINVAL;
9500                         len -= n;
9501                         name += n;
9502                 }
9503                 n = snprintf(name, len, "pf%u", attrs->pci_pf.pf);
9504                 break;
9505         case DEVLINK_PORT_FLAVOUR_PCI_VF:
9506                 if (attrs->pci_vf.external) {
9507                         n = snprintf(name, len, "c%u", attrs->pci_vf.controller);
9508                         if (n >= len)
9509                                 return -EINVAL;
9510                         len -= n;
9511                         name += n;
9512                 }
9513                 n = snprintf(name, len, "pf%uvf%u",
9514                              attrs->pci_vf.pf, attrs->pci_vf.vf);
9515                 break;
9516         case DEVLINK_PORT_FLAVOUR_PCI_SF:
9517                 if (attrs->pci_sf.external) {
9518                         n = snprintf(name, len, "c%u", attrs->pci_sf.controller);
9519                         if (n >= len)
9520                                 return -EINVAL;
9521                         len -= n;
9522                         name += n;
9523                 }
9524                 n = snprintf(name, len, "pf%usf%u", attrs->pci_sf.pf,
9525                              attrs->pci_sf.sf);
9526                 break;
9527         case DEVLINK_PORT_FLAVOUR_VIRTUAL:
9528                 return -EOPNOTSUPP;
9529         }
9530
9531         if (n >= len)
9532                 return -EINVAL;
9533
9534         return 0;
9535 }
9536
9537 int devlink_sb_register(struct devlink *devlink, unsigned int sb_index,
9538                         u32 size, u16 ingress_pools_count,
9539                         u16 egress_pools_count, u16 ingress_tc_count,
9540                         u16 egress_tc_count)
9541 {
9542         struct devlink_sb *devlink_sb;
9543         int err = 0;
9544
9545         mutex_lock(&devlink->lock);
9546         if (devlink_sb_index_exists(devlink, sb_index)) {
9547                 err = -EEXIST;
9548                 goto unlock;
9549         }
9550
9551         devlink_sb = kzalloc(sizeof(*devlink_sb), GFP_KERNEL);
9552         if (!devlink_sb) {
9553                 err = -ENOMEM;
9554                 goto unlock;
9555         }
9556         devlink_sb->index = sb_index;
9557         devlink_sb->size = size;
9558         devlink_sb->ingress_pools_count = ingress_pools_count;
9559         devlink_sb->egress_pools_count = egress_pools_count;
9560         devlink_sb->ingress_tc_count = ingress_tc_count;
9561         devlink_sb->egress_tc_count = egress_tc_count;
9562         list_add_tail(&devlink_sb->list, &devlink->sb_list);
9563 unlock:
9564         mutex_unlock(&devlink->lock);
9565         return err;
9566 }
9567 EXPORT_SYMBOL_GPL(devlink_sb_register);
9568
9569 void devlink_sb_unregister(struct devlink *devlink, unsigned int sb_index)
9570 {
9571         struct devlink_sb *devlink_sb;
9572
9573         mutex_lock(&devlink->lock);
9574         devlink_sb = devlink_sb_get_by_index(devlink, sb_index);
9575         WARN_ON(!devlink_sb);
9576         list_del(&devlink_sb->list);
9577         mutex_unlock(&devlink->lock);
9578         kfree(devlink_sb);
9579 }
9580 EXPORT_SYMBOL_GPL(devlink_sb_unregister);
9581
9582 /**
9583  *      devlink_dpipe_headers_register - register dpipe headers
9584  *
9585  *      @devlink: devlink
9586  *      @dpipe_headers: dpipe header array
9587  *
9588  *      Register the headers supported by hardware.
9589  */
9590 int devlink_dpipe_headers_register(struct devlink *devlink,
9591                                    struct devlink_dpipe_headers *dpipe_headers)
9592 {
9593         mutex_lock(&devlink->lock);
9594         devlink->dpipe_headers = dpipe_headers;
9595         mutex_unlock(&devlink->lock);
9596         return 0;
9597 }
9598 EXPORT_SYMBOL_GPL(devlink_dpipe_headers_register);
9599
9600 /**
9601  *      devlink_dpipe_headers_unregister - unregister dpipe headers
9602  *
9603  *      @devlink: devlink
9604  *
9605  *      Unregister the headers supported by hardware.
9606  */
9607 void devlink_dpipe_headers_unregister(struct devlink *devlink)
9608 {
9609         mutex_lock(&devlink->lock);
9610         devlink->dpipe_headers = NULL;
9611         mutex_unlock(&devlink->lock);
9612 }
9613 EXPORT_SYMBOL_GPL(devlink_dpipe_headers_unregister);
9614
9615 /**
9616  *      devlink_dpipe_table_counter_enabled - check if counter allocation
9617  *                                            required
9618  *      @devlink: devlink
9619  *      @table_name: tables name
9620  *
9621  *      Used by driver to check if counter allocation is required.
9622  *      After counter allocation is turned on the table entries
9623  *      are updated to include counter statistics.
9624  *
9625  *      After that point on the driver must respect the counter
9626  *      state so that each entry added to the table is added
9627  *      with a counter.
9628  */
9629 bool devlink_dpipe_table_counter_enabled(struct devlink *devlink,
9630                                          const char *table_name)
9631 {
9632         struct devlink_dpipe_table *table;
9633         bool enabled;
9634
9635         rcu_read_lock();
9636         table = devlink_dpipe_table_find(&devlink->dpipe_table_list,
9637                                          table_name, devlink);
9638         enabled = false;
9639         if (table)
9640                 enabled = table->counters_enabled;
9641         rcu_read_unlock();
9642         return enabled;
9643 }
9644 EXPORT_SYMBOL_GPL(devlink_dpipe_table_counter_enabled);
9645
9646 /**
9647  *      devlink_dpipe_table_register - register dpipe table
9648  *
9649  *      @devlink: devlink
9650  *      @table_name: table name
9651  *      @table_ops: table ops
9652  *      @priv: priv
9653  *      @counter_control_extern: external control for counters
9654  */
9655 int devlink_dpipe_table_register(struct devlink *devlink,
9656                                  const char *table_name,
9657                                  struct devlink_dpipe_table_ops *table_ops,
9658                                  void *priv, bool counter_control_extern)
9659 {
9660         struct devlink_dpipe_table *table;
9661         int err = 0;
9662
9663         if (WARN_ON(!table_ops->size_get))
9664                 return -EINVAL;
9665
9666         mutex_lock(&devlink->lock);
9667
9668         if (devlink_dpipe_table_find(&devlink->dpipe_table_list, table_name,
9669                                      devlink)) {
9670                 err = -EEXIST;
9671                 goto unlock;
9672         }
9673
9674         table = kzalloc(sizeof(*table), GFP_KERNEL);
9675         if (!table) {
9676                 err = -ENOMEM;
9677                 goto unlock;
9678         }
9679
9680         table->name = table_name;
9681         table->table_ops = table_ops;
9682         table->priv = priv;
9683         table->counter_control_extern = counter_control_extern;
9684
9685         list_add_tail_rcu(&table->list, &devlink->dpipe_table_list);
9686 unlock:
9687         mutex_unlock(&devlink->lock);
9688         return err;
9689 }
9690 EXPORT_SYMBOL_GPL(devlink_dpipe_table_register);
9691
9692 /**
9693  *      devlink_dpipe_table_unregister - unregister dpipe table
9694  *
9695  *      @devlink: devlink
9696  *      @table_name: table name
9697  */
9698 void devlink_dpipe_table_unregister(struct devlink *devlink,
9699                                     const char *table_name)
9700 {
9701         struct devlink_dpipe_table *table;
9702
9703         mutex_lock(&devlink->lock);
9704         table = devlink_dpipe_table_find(&devlink->dpipe_table_list,
9705                                          table_name, devlink);
9706         if (!table)
9707                 goto unlock;
9708         list_del_rcu(&table->list);
9709         mutex_unlock(&devlink->lock);
9710         kfree_rcu(table, rcu);
9711         return;
9712 unlock:
9713         mutex_unlock(&devlink->lock);
9714 }
9715 EXPORT_SYMBOL_GPL(devlink_dpipe_table_unregister);
9716
9717 /**
9718  *      devlink_resource_register - devlink resource register
9719  *
9720  *      @devlink: devlink
9721  *      @resource_name: resource's name
9722  *      @resource_size: resource's size
9723  *      @resource_id: resource's id
9724  *      @parent_resource_id: resource's parent id
9725  *      @size_params: size parameters
9726  *
9727  *      Generic resources should reuse the same names across drivers.
9728  *      Please see the generic resources list at:
9729  *      Documentation/networking/devlink/devlink-resource.rst
9730  */
9731 int devlink_resource_register(struct devlink *devlink,
9732                               const char *resource_name,
9733                               u64 resource_size,
9734                               u64 resource_id,
9735                               u64 parent_resource_id,
9736                               const struct devlink_resource_size_params *size_params)
9737 {
9738         struct devlink_resource *resource;
9739         struct list_head *resource_list;
9740         bool top_hierarchy;
9741         int err = 0;
9742
9743         top_hierarchy = parent_resource_id == DEVLINK_RESOURCE_ID_PARENT_TOP;
9744
9745         mutex_lock(&devlink->lock);
9746         resource = devlink_resource_find(devlink, NULL, resource_id);
9747         if (resource) {
9748                 err = -EINVAL;
9749                 goto out;
9750         }
9751
9752         resource = kzalloc(sizeof(*resource), GFP_KERNEL);
9753         if (!resource) {
9754                 err = -ENOMEM;
9755                 goto out;
9756         }
9757
9758         if (top_hierarchy) {
9759                 resource_list = &devlink->resource_list;
9760         } else {
9761                 struct devlink_resource *parent_resource;
9762
9763                 parent_resource = devlink_resource_find(devlink, NULL,
9764                                                         parent_resource_id);
9765                 if (parent_resource) {
9766                         resource_list = &parent_resource->resource_list;
9767                         resource->parent = parent_resource;
9768                 } else {
9769                         kfree(resource);
9770                         err = -EINVAL;
9771                         goto out;
9772                 }
9773         }
9774
9775         resource->name = resource_name;
9776         resource->size = resource_size;
9777         resource->size_new = resource_size;
9778         resource->id = resource_id;
9779         resource->size_valid = true;
9780         memcpy(&resource->size_params, size_params,
9781                sizeof(resource->size_params));
9782         INIT_LIST_HEAD(&resource->resource_list);
9783         list_add_tail(&resource->list, resource_list);
9784 out:
9785         mutex_unlock(&devlink->lock);
9786         return err;
9787 }
9788 EXPORT_SYMBOL_GPL(devlink_resource_register);
9789
9790 /**
9791  *      devlink_resources_unregister - free all resources
9792  *
9793  *      @devlink: devlink
9794  *      @resource: resource
9795  */
9796 void devlink_resources_unregister(struct devlink *devlink,
9797                                   struct devlink_resource *resource)
9798 {
9799         struct devlink_resource *tmp, *child_resource;
9800         struct list_head *resource_list;
9801
9802         if (resource)
9803                 resource_list = &resource->resource_list;
9804         else
9805                 resource_list = &devlink->resource_list;
9806
9807         if (!resource)
9808                 mutex_lock(&devlink->lock);
9809
9810         list_for_each_entry_safe(child_resource, tmp, resource_list, list) {
9811                 devlink_resources_unregister(devlink, child_resource);
9812                 list_del(&child_resource->list);
9813                 kfree(child_resource);
9814         }
9815
9816         if (!resource)
9817                 mutex_unlock(&devlink->lock);
9818 }
9819 EXPORT_SYMBOL_GPL(devlink_resources_unregister);
9820
9821 /**
9822  *      devlink_resource_size_get - get and update size
9823  *
9824  *      @devlink: devlink
9825  *      @resource_id: the requested resource id
9826  *      @p_resource_size: ptr to update
9827  */
9828 int devlink_resource_size_get(struct devlink *devlink,
9829                               u64 resource_id,
9830                               u64 *p_resource_size)
9831 {
9832         struct devlink_resource *resource;
9833         int err = 0;
9834
9835         mutex_lock(&devlink->lock);
9836         resource = devlink_resource_find(devlink, NULL, resource_id);
9837         if (!resource) {
9838                 err = -EINVAL;
9839                 goto out;
9840         }
9841         *p_resource_size = resource->size_new;
9842         resource->size = resource->size_new;
9843 out:
9844         mutex_unlock(&devlink->lock);
9845         return err;
9846 }
9847 EXPORT_SYMBOL_GPL(devlink_resource_size_get);
9848
9849 /**
9850  *      devlink_dpipe_table_resource_set - set the resource id
9851  *
9852  *      @devlink: devlink
9853  *      @table_name: table name
9854  *      @resource_id: resource id
9855  *      @resource_units: number of resource's units consumed per table's entry
9856  */
9857 int devlink_dpipe_table_resource_set(struct devlink *devlink,
9858                                      const char *table_name, u64 resource_id,
9859                                      u64 resource_units)
9860 {
9861         struct devlink_dpipe_table *table;
9862         int err = 0;
9863
9864         mutex_lock(&devlink->lock);
9865         table = devlink_dpipe_table_find(&devlink->dpipe_table_list,
9866                                          table_name, devlink);
9867         if (!table) {
9868                 err = -EINVAL;
9869                 goto out;
9870         }
9871         table->resource_id = resource_id;
9872         table->resource_units = resource_units;
9873         table->resource_valid = true;
9874 out:
9875         mutex_unlock(&devlink->lock);
9876         return err;
9877 }
9878 EXPORT_SYMBOL_GPL(devlink_dpipe_table_resource_set);
9879
9880 /**
9881  *      devlink_resource_occ_get_register - register occupancy getter
9882  *
9883  *      @devlink: devlink
9884  *      @resource_id: resource id
9885  *      @occ_get: occupancy getter callback
9886  *      @occ_get_priv: occupancy getter callback priv
9887  */
9888 void devlink_resource_occ_get_register(struct devlink *devlink,
9889                                        u64 resource_id,
9890                                        devlink_resource_occ_get_t *occ_get,
9891                                        void *occ_get_priv)
9892 {
9893         struct devlink_resource *resource;
9894
9895         mutex_lock(&devlink->lock);
9896         resource = devlink_resource_find(devlink, NULL, resource_id);
9897         if (WARN_ON(!resource))
9898                 goto out;
9899         WARN_ON(resource->occ_get);
9900
9901         resource->occ_get = occ_get;
9902         resource->occ_get_priv = occ_get_priv;
9903 out:
9904         mutex_unlock(&devlink->lock);
9905 }
9906 EXPORT_SYMBOL_GPL(devlink_resource_occ_get_register);
9907
9908 /**
9909  *      devlink_resource_occ_get_unregister - unregister occupancy getter
9910  *
9911  *      @devlink: devlink
9912  *      @resource_id: resource id
9913  */
9914 void devlink_resource_occ_get_unregister(struct devlink *devlink,
9915                                          u64 resource_id)
9916 {
9917         struct devlink_resource *resource;
9918
9919         mutex_lock(&devlink->lock);
9920         resource = devlink_resource_find(devlink, NULL, resource_id);
9921         if (WARN_ON(!resource))
9922                 goto out;
9923         WARN_ON(!resource->occ_get);
9924
9925         resource->occ_get = NULL;
9926         resource->occ_get_priv = NULL;
9927 out:
9928         mutex_unlock(&devlink->lock);
9929 }
9930 EXPORT_SYMBOL_GPL(devlink_resource_occ_get_unregister);
9931
9932 static int devlink_param_verify(const struct devlink_param *param)
9933 {
9934         if (!param || !param->name || !param->supported_cmodes)
9935                 return -EINVAL;
9936         if (param->generic)
9937                 return devlink_param_generic_verify(param);
9938         else
9939                 return devlink_param_driver_verify(param);
9940 }
9941
9942 static int __devlink_param_register_one(struct devlink *devlink,
9943                                         unsigned int port_index,
9944                                         struct list_head *param_list,
9945                                         const struct devlink_param *param,
9946                                         enum devlink_command reg_cmd)
9947 {
9948         int err;
9949
9950         err = devlink_param_verify(param);
9951         if (err)
9952                 return err;
9953
9954         return devlink_param_register_one(devlink, port_index,
9955                                           param_list, param, reg_cmd);
9956 }
9957
9958 static int __devlink_params_register(struct devlink *devlink,
9959                                      unsigned int port_index,
9960                                      struct list_head *param_list,
9961                                      const struct devlink_param *params,
9962                                      size_t params_count,
9963                                      enum devlink_command reg_cmd,
9964                                      enum devlink_command unreg_cmd)
9965 {
9966         const struct devlink_param *param = params;
9967         int i;
9968         int err;
9969
9970         mutex_lock(&devlink->lock);
9971         for (i = 0; i < params_count; i++, param++) {
9972                 err = __devlink_param_register_one(devlink, port_index,
9973                                                    param_list, param, reg_cmd);
9974                 if (err)
9975                         goto rollback;
9976         }
9977
9978         mutex_unlock(&devlink->lock);
9979         return 0;
9980
9981 rollback:
9982         if (!i)
9983                 goto unlock;
9984         for (param--; i > 0; i--, param--)
9985                 devlink_param_unregister_one(devlink, port_index, param_list,
9986                                              param, unreg_cmd);
9987 unlock:
9988         mutex_unlock(&devlink->lock);
9989         return err;
9990 }
9991
9992 static void __devlink_params_unregister(struct devlink *devlink,
9993                                         unsigned int port_index,
9994                                         struct list_head *param_list,
9995                                         const struct devlink_param *params,
9996                                         size_t params_count,
9997                                         enum devlink_command cmd)
9998 {
9999         const struct devlink_param *param = params;
10000         int i;
10001
10002         mutex_lock(&devlink->lock);
10003         for (i = 0; i < params_count; i++, param++)
10004                 devlink_param_unregister_one(devlink, 0, param_list, param,
10005                                              cmd);
10006         mutex_unlock(&devlink->lock);
10007 }
10008
10009 /**
10010  *      devlink_params_register - register configuration parameters
10011  *
10012  *      @devlink: devlink
10013  *      @params: configuration parameters array
10014  *      @params_count: number of parameters provided
10015  *
10016  *      Register the configuration parameters supported by the driver.
10017  */
10018 int devlink_params_register(struct devlink *devlink,
10019                             const struct devlink_param *params,
10020                             size_t params_count)
10021 {
10022         return __devlink_params_register(devlink, 0, &devlink->param_list,
10023                                          params, params_count,
10024                                          DEVLINK_CMD_PARAM_NEW,
10025                                          DEVLINK_CMD_PARAM_DEL);
10026 }
10027 EXPORT_SYMBOL_GPL(devlink_params_register);
10028
10029 /**
10030  *      devlink_params_unregister - unregister configuration parameters
10031  *      @devlink: devlink
10032  *      @params: configuration parameters to unregister
10033  *      @params_count: number of parameters provided
10034  */
10035 void devlink_params_unregister(struct devlink *devlink,
10036                                const struct devlink_param *params,
10037                                size_t params_count)
10038 {
10039         return __devlink_params_unregister(devlink, 0, &devlink->param_list,
10040                                            params, params_count,
10041                                            DEVLINK_CMD_PARAM_DEL);
10042 }
10043 EXPORT_SYMBOL_GPL(devlink_params_unregister);
10044
10045 /**
10046  * devlink_param_register - register one configuration parameter
10047  *
10048  * @devlink: devlink
10049  * @param: one configuration parameter
10050  *
10051  * Register the configuration parameter supported by the driver.
10052  * Return: returns 0 on successful registration or error code otherwise.
10053  */
10054 int devlink_param_register(struct devlink *devlink,
10055                            const struct devlink_param *param)
10056 {
10057         int err;
10058
10059         mutex_lock(&devlink->lock);
10060         err = __devlink_param_register_one(devlink, 0, &devlink->param_list,
10061                                            param, DEVLINK_CMD_PARAM_NEW);
10062         mutex_unlock(&devlink->lock);
10063         return err;
10064 }
10065 EXPORT_SYMBOL_GPL(devlink_param_register);
10066
10067 /**
10068  * devlink_param_unregister - unregister one configuration parameter
10069  * @devlink: devlink
10070  * @param: configuration parameter to unregister
10071  */
10072 void devlink_param_unregister(struct devlink *devlink,
10073                               const struct devlink_param *param)
10074 {
10075         mutex_lock(&devlink->lock);
10076         devlink_param_unregister_one(devlink, 0, &devlink->param_list, param,
10077                                      DEVLINK_CMD_PARAM_DEL);
10078         mutex_unlock(&devlink->lock);
10079 }
10080 EXPORT_SYMBOL_GPL(devlink_param_unregister);
10081
10082 /**
10083  *      devlink_params_publish - publish configuration parameters
10084  *
10085  *      @devlink: devlink
10086  *
10087  *      Publish previously registered configuration parameters.
10088  */
10089 void devlink_params_publish(struct devlink *devlink)
10090 {
10091         struct devlink_param_item *param_item;
10092
10093         list_for_each_entry(param_item, &devlink->param_list, list) {
10094                 if (param_item->published)
10095                         continue;
10096                 param_item->published = true;
10097                 devlink_param_notify(devlink, 0, param_item,
10098                                      DEVLINK_CMD_PARAM_NEW);
10099         }
10100 }
10101 EXPORT_SYMBOL_GPL(devlink_params_publish);
10102
10103 /**
10104  *      devlink_params_unpublish - unpublish configuration parameters
10105  *
10106  *      @devlink: devlink
10107  *
10108  *      Unpublish previously registered configuration parameters.
10109  */
10110 void devlink_params_unpublish(struct devlink *devlink)
10111 {
10112         struct devlink_param_item *param_item;
10113
10114         list_for_each_entry(param_item, &devlink->param_list, list) {
10115                 if (!param_item->published)
10116                         continue;
10117                 param_item->published = false;
10118                 devlink_param_notify(devlink, 0, param_item,
10119                                      DEVLINK_CMD_PARAM_DEL);
10120         }
10121 }
10122 EXPORT_SYMBOL_GPL(devlink_params_unpublish);
10123
10124 /**
10125  * devlink_param_publish - publish one configuration parameter
10126  *
10127  * @devlink: devlink
10128  * @param: one configuration parameter
10129  *
10130  * Publish previously registered configuration parameter.
10131  */
10132 void devlink_param_publish(struct devlink *devlink,
10133                            const struct devlink_param *param)
10134 {
10135         struct devlink_param_item *param_item;
10136
10137         list_for_each_entry(param_item, &devlink->param_list, list) {
10138                 if (param_item->param != param || param_item->published)
10139                         continue;
10140                 param_item->published = true;
10141                 devlink_param_notify(devlink, 0, param_item,
10142                                      DEVLINK_CMD_PARAM_NEW);
10143                 break;
10144         }
10145 }
10146 EXPORT_SYMBOL_GPL(devlink_param_publish);
10147
10148 /**
10149  * devlink_param_unpublish - unpublish one configuration parameter
10150  *
10151  * @devlink: devlink
10152  * @param: one configuration parameter
10153  *
10154  * Unpublish previously registered configuration parameter.
10155  */
10156 void devlink_param_unpublish(struct devlink *devlink,
10157                              const struct devlink_param *param)
10158 {
10159         struct devlink_param_item *param_item;
10160
10161         list_for_each_entry(param_item, &devlink->param_list, list) {
10162                 if (param_item->param != param || !param_item->published)
10163                         continue;
10164                 param_item->published = false;
10165                 devlink_param_notify(devlink, 0, param_item,
10166                                      DEVLINK_CMD_PARAM_DEL);
10167                 break;
10168         }
10169 }
10170 EXPORT_SYMBOL_GPL(devlink_param_unpublish);
10171
10172 /**
10173  *      devlink_port_params_register - register port configuration parameters
10174  *
10175  *      @devlink_port: devlink port
10176  *      @params: configuration parameters array
10177  *      @params_count: number of parameters provided
10178  *
10179  *      Register the configuration parameters supported by the port.
10180  */
10181 int devlink_port_params_register(struct devlink_port *devlink_port,
10182                                  const struct devlink_param *params,
10183                                  size_t params_count)
10184 {
10185         return __devlink_params_register(devlink_port->devlink,
10186                                          devlink_port->index,
10187                                          &devlink_port->param_list, params,
10188                                          params_count,
10189                                          DEVLINK_CMD_PORT_PARAM_NEW,
10190                                          DEVLINK_CMD_PORT_PARAM_DEL);
10191 }
10192 EXPORT_SYMBOL_GPL(devlink_port_params_register);
10193
10194 /**
10195  *      devlink_port_params_unregister - unregister port configuration
10196  *      parameters
10197  *
10198  *      @devlink_port: devlink port
10199  *      @params: configuration parameters array
10200  *      @params_count: number of parameters provided
10201  */
10202 void devlink_port_params_unregister(struct devlink_port *devlink_port,
10203                                     const struct devlink_param *params,
10204                                     size_t params_count)
10205 {
10206         return __devlink_params_unregister(devlink_port->devlink,
10207                                            devlink_port->index,
10208                                            &devlink_port->param_list,
10209                                            params, params_count,
10210                                            DEVLINK_CMD_PORT_PARAM_DEL);
10211 }
10212 EXPORT_SYMBOL_GPL(devlink_port_params_unregister);
10213
10214 static int
10215 __devlink_param_driverinit_value_get(struct list_head *param_list, u32 param_id,
10216                                      union devlink_param_value *init_val)
10217 {
10218         struct devlink_param_item *param_item;
10219
10220         param_item = devlink_param_find_by_id(param_list, param_id);
10221         if (!param_item)
10222                 return -EINVAL;
10223
10224         if (!param_item->driverinit_value_valid ||
10225             !devlink_param_cmode_is_supported(param_item->param,
10226                                               DEVLINK_PARAM_CMODE_DRIVERINIT))
10227                 return -EOPNOTSUPP;
10228
10229         if (param_item->param->type == DEVLINK_PARAM_TYPE_STRING)
10230                 strcpy(init_val->vstr, param_item->driverinit_value.vstr);
10231         else
10232                 *init_val = param_item->driverinit_value;
10233
10234         return 0;
10235 }
10236
10237 static int
10238 __devlink_param_driverinit_value_set(struct devlink *devlink,
10239                                      unsigned int port_index,
10240                                      struct list_head *param_list, u32 param_id,
10241                                      union devlink_param_value init_val,
10242                                      enum devlink_command cmd)
10243 {
10244         struct devlink_param_item *param_item;
10245
10246         param_item = devlink_param_find_by_id(param_list, param_id);
10247         if (!param_item)
10248                 return -EINVAL;
10249
10250         if (!devlink_param_cmode_is_supported(param_item->param,
10251                                               DEVLINK_PARAM_CMODE_DRIVERINIT))
10252                 return -EOPNOTSUPP;
10253
10254         if (param_item->param->type == DEVLINK_PARAM_TYPE_STRING)
10255                 strcpy(param_item->driverinit_value.vstr, init_val.vstr);
10256         else
10257                 param_item->driverinit_value = init_val;
10258         param_item->driverinit_value_valid = true;
10259
10260         devlink_param_notify(devlink, port_index, param_item, cmd);
10261         return 0;
10262 }
10263
10264 /**
10265  *      devlink_param_driverinit_value_get - get configuration parameter
10266  *                                           value for driver initializing
10267  *
10268  *      @devlink: devlink
10269  *      @param_id: parameter ID
10270  *      @init_val: value of parameter in driverinit configuration mode
10271  *
10272  *      This function should be used by the driver to get driverinit
10273  *      configuration for initialization after reload command.
10274  */
10275 int devlink_param_driverinit_value_get(struct devlink *devlink, u32 param_id,
10276                                        union devlink_param_value *init_val)
10277 {
10278         if (!devlink_reload_supported(devlink->ops))
10279                 return -EOPNOTSUPP;
10280
10281         return __devlink_param_driverinit_value_get(&devlink->param_list,
10282                                                     param_id, init_val);
10283 }
10284 EXPORT_SYMBOL_GPL(devlink_param_driverinit_value_get);
10285
10286 /**
10287  *      devlink_param_driverinit_value_set - set value of configuration
10288  *                                           parameter for driverinit
10289  *                                           configuration mode
10290  *
10291  *      @devlink: devlink
10292  *      @param_id: parameter ID
10293  *      @init_val: value of parameter to set for driverinit configuration mode
10294  *
10295  *      This function should be used by the driver to set driverinit
10296  *      configuration mode default value.
10297  */
10298 int devlink_param_driverinit_value_set(struct devlink *devlink, u32 param_id,
10299                                        union devlink_param_value init_val)
10300 {
10301         return __devlink_param_driverinit_value_set(devlink, 0,
10302                                                     &devlink->param_list,
10303                                                     param_id, init_val,
10304                                                     DEVLINK_CMD_PARAM_NEW);
10305 }
10306 EXPORT_SYMBOL_GPL(devlink_param_driverinit_value_set);
10307
10308 /**
10309  *      devlink_port_param_driverinit_value_get - get configuration parameter
10310  *                                              value for driver initializing
10311  *
10312  *      @devlink_port: devlink_port
10313  *      @param_id: parameter ID
10314  *      @init_val: value of parameter in driverinit configuration mode
10315  *
10316  *      This function should be used by the driver to get driverinit
10317  *      configuration for initialization after reload command.
10318  */
10319 int devlink_port_param_driverinit_value_get(struct devlink_port *devlink_port,
10320                                             u32 param_id,
10321                                             union devlink_param_value *init_val)
10322 {
10323         struct devlink *devlink = devlink_port->devlink;
10324
10325         if (!devlink_reload_supported(devlink->ops))
10326                 return -EOPNOTSUPP;
10327
10328         return __devlink_param_driverinit_value_get(&devlink_port->param_list,
10329                                                     param_id, init_val);
10330 }
10331 EXPORT_SYMBOL_GPL(devlink_port_param_driverinit_value_get);
10332
10333 /**
10334  *     devlink_port_param_driverinit_value_set - set value of configuration
10335  *                                               parameter for driverinit
10336  *                                               configuration mode
10337  *
10338  *     @devlink_port: devlink_port
10339  *     @param_id: parameter ID
10340  *     @init_val: value of parameter to set for driverinit configuration mode
10341  *
10342  *     This function should be used by the driver to set driverinit
10343  *     configuration mode default value.
10344  */
10345 int devlink_port_param_driverinit_value_set(struct devlink_port *devlink_port,
10346                                             u32 param_id,
10347                                             union devlink_param_value init_val)
10348 {
10349         return __devlink_param_driverinit_value_set(devlink_port->devlink,
10350                                                     devlink_port->index,
10351                                                     &devlink_port->param_list,
10352                                                     param_id, init_val,
10353                                                     DEVLINK_CMD_PORT_PARAM_NEW);
10354 }
10355 EXPORT_SYMBOL_GPL(devlink_port_param_driverinit_value_set);
10356
10357 /**
10358  *      devlink_param_value_changed - notify devlink on a parameter's value
10359  *                                    change. Should be called by the driver
10360  *                                    right after the change.
10361  *
10362  *      @devlink: devlink
10363  *      @param_id: parameter ID
10364  *
10365  *      This function should be used by the driver to notify devlink on value
10366  *      change, excluding driverinit configuration mode.
10367  *      For driverinit configuration mode driver should use the function
10368  */
10369 void devlink_param_value_changed(struct devlink *devlink, u32 param_id)
10370 {
10371         struct devlink_param_item *param_item;
10372
10373         param_item = devlink_param_find_by_id(&devlink->param_list, param_id);
10374         WARN_ON(!param_item);
10375
10376         devlink_param_notify(devlink, 0, param_item, DEVLINK_CMD_PARAM_NEW);
10377 }
10378 EXPORT_SYMBOL_GPL(devlink_param_value_changed);
10379
10380 /**
10381  *     devlink_port_param_value_changed - notify devlink on a parameter's value
10382  *                                      change. Should be called by the driver
10383  *                                      right after the change.
10384  *
10385  *     @devlink_port: devlink_port
10386  *     @param_id: parameter ID
10387  *
10388  *     This function should be used by the driver to notify devlink on value
10389  *     change, excluding driverinit configuration mode.
10390  *     For driverinit configuration mode driver should use the function
10391  *     devlink_port_param_driverinit_value_set() instead.
10392  */
10393 void devlink_port_param_value_changed(struct devlink_port *devlink_port,
10394                                       u32 param_id)
10395 {
10396         struct devlink_param_item *param_item;
10397
10398         param_item = devlink_param_find_by_id(&devlink_port->param_list,
10399                                               param_id);
10400         WARN_ON(!param_item);
10401
10402         devlink_param_notify(devlink_port->devlink, devlink_port->index,
10403                              param_item, DEVLINK_CMD_PORT_PARAM_NEW);
10404 }
10405 EXPORT_SYMBOL_GPL(devlink_port_param_value_changed);
10406
10407 /**
10408  *      devlink_param_value_str_fill - Safely fill-up the string preventing
10409  *                                     from overflow of the preallocated buffer
10410  *
10411  *      @dst_val: destination devlink_param_value
10412  *      @src: source buffer
10413  */
10414 void devlink_param_value_str_fill(union devlink_param_value *dst_val,
10415                                   const char *src)
10416 {
10417         size_t len;
10418
10419         len = strlcpy(dst_val->vstr, src, __DEVLINK_PARAM_MAX_STRING_VALUE);
10420         WARN_ON(len >= __DEVLINK_PARAM_MAX_STRING_VALUE);
10421 }
10422 EXPORT_SYMBOL_GPL(devlink_param_value_str_fill);
10423
10424 /**
10425  *      devlink_region_create - create a new address region
10426  *
10427  *      @devlink: devlink
10428  *      @ops: region operations and name
10429  *      @region_max_snapshots: Maximum supported number of snapshots for region
10430  *      @region_size: size of region
10431  */
10432 struct devlink_region *
10433 devlink_region_create(struct devlink *devlink,
10434                       const struct devlink_region_ops *ops,
10435                       u32 region_max_snapshots, u64 region_size)
10436 {
10437         struct devlink_region *region;
10438         int err = 0;
10439
10440         if (WARN_ON(!ops) || WARN_ON(!ops->destructor))
10441                 return ERR_PTR(-EINVAL);
10442
10443         mutex_lock(&devlink->lock);
10444
10445         if (devlink_region_get_by_name(devlink, ops->name)) {
10446                 err = -EEXIST;
10447                 goto unlock;
10448         }
10449
10450         region = kzalloc(sizeof(*region), GFP_KERNEL);
10451         if (!region) {
10452                 err = -ENOMEM;
10453                 goto unlock;
10454         }
10455
10456         region->devlink = devlink;
10457         region->max_snapshots = region_max_snapshots;
10458         region->ops = ops;
10459         region->size = region_size;
10460         INIT_LIST_HEAD(&region->snapshot_list);
10461         list_add_tail(&region->list, &devlink->region_list);
10462         devlink_nl_region_notify(region, NULL, DEVLINK_CMD_REGION_NEW);
10463
10464         mutex_unlock(&devlink->lock);
10465         return region;
10466
10467 unlock:
10468         mutex_unlock(&devlink->lock);
10469         return ERR_PTR(err);
10470 }
10471 EXPORT_SYMBOL_GPL(devlink_region_create);
10472
10473 /**
10474  *      devlink_port_region_create - create a new address region for a port
10475  *
10476  *      @port: devlink port
10477  *      @ops: region operations and name
10478  *      @region_max_snapshots: Maximum supported number of snapshots for region
10479  *      @region_size: size of region
10480  */
10481 struct devlink_region *
10482 devlink_port_region_create(struct devlink_port *port,
10483                            const struct devlink_port_region_ops *ops,
10484                            u32 region_max_snapshots, u64 region_size)
10485 {
10486         struct devlink *devlink = port->devlink;
10487         struct devlink_region *region;
10488         int err = 0;
10489
10490         if (WARN_ON(!ops) || WARN_ON(!ops->destructor))
10491                 return ERR_PTR(-EINVAL);
10492
10493         mutex_lock(&devlink->lock);
10494
10495         if (devlink_port_region_get_by_name(port, ops->name)) {
10496                 err = -EEXIST;
10497                 goto unlock;
10498         }
10499
10500         region = kzalloc(sizeof(*region), GFP_KERNEL);
10501         if (!region) {
10502                 err = -ENOMEM;
10503                 goto unlock;
10504         }
10505
10506         region->devlink = devlink;
10507         region->port = port;
10508         region->max_snapshots = region_max_snapshots;
10509         region->port_ops = ops;
10510         region->size = region_size;
10511         INIT_LIST_HEAD(&region->snapshot_list);
10512         list_add_tail(&region->list, &port->region_list);
10513         devlink_nl_region_notify(region, NULL, DEVLINK_CMD_REGION_NEW);
10514
10515         mutex_unlock(&devlink->lock);
10516         return region;
10517
10518 unlock:
10519         mutex_unlock(&devlink->lock);
10520         return ERR_PTR(err);
10521 }
10522 EXPORT_SYMBOL_GPL(devlink_port_region_create);
10523
10524 /**
10525  *      devlink_region_destroy - destroy address region
10526  *
10527  *      @region: devlink region to destroy
10528  */
10529 void devlink_region_destroy(struct devlink_region *region)
10530 {
10531         struct devlink *devlink = region->devlink;
10532         struct devlink_snapshot *snapshot, *ts;
10533
10534         mutex_lock(&devlink->lock);
10535
10536         /* Free all snapshots of region */
10537         list_for_each_entry_safe(snapshot, ts, &region->snapshot_list, list)
10538                 devlink_region_snapshot_del(region, snapshot);
10539
10540         list_del(&region->list);
10541
10542         devlink_nl_region_notify(region, NULL, DEVLINK_CMD_REGION_DEL);
10543         mutex_unlock(&devlink->lock);
10544         kfree(region);
10545 }
10546 EXPORT_SYMBOL_GPL(devlink_region_destroy);
10547
10548 /**
10549  *      devlink_region_snapshot_id_get - get snapshot ID
10550  *
10551  *      This callback should be called when adding a new snapshot,
10552  *      Driver should use the same id for multiple snapshots taken
10553  *      on multiple regions at the same time/by the same trigger.
10554  *
10555  *      The caller of this function must use devlink_region_snapshot_id_put
10556  *      when finished creating regions using this id.
10557  *
10558  *      Returns zero on success, or a negative error code on failure.
10559  *
10560  *      @devlink: devlink
10561  *      @id: storage to return id
10562  */
10563 int devlink_region_snapshot_id_get(struct devlink *devlink, u32 *id)
10564 {
10565         int err;
10566
10567         mutex_lock(&devlink->lock);
10568         err = __devlink_region_snapshot_id_get(devlink, id);
10569         mutex_unlock(&devlink->lock);
10570
10571         return err;
10572 }
10573 EXPORT_SYMBOL_GPL(devlink_region_snapshot_id_get);
10574
10575 /**
10576  *      devlink_region_snapshot_id_put - put snapshot ID reference
10577  *
10578  *      This should be called by a driver after finishing creating snapshots
10579  *      with an id. Doing so ensures that the ID can later be released in the
10580  *      event that all snapshots using it have been destroyed.
10581  *
10582  *      @devlink: devlink
10583  *      @id: id to release reference on
10584  */
10585 void devlink_region_snapshot_id_put(struct devlink *devlink, u32 id)
10586 {
10587         mutex_lock(&devlink->lock);
10588         __devlink_snapshot_id_decrement(devlink, id);
10589         mutex_unlock(&devlink->lock);
10590 }
10591 EXPORT_SYMBOL_GPL(devlink_region_snapshot_id_put);
10592
10593 /**
10594  *      devlink_region_snapshot_create - create a new snapshot
10595  *      This will add a new snapshot of a region. The snapshot
10596  *      will be stored on the region struct and can be accessed
10597  *      from devlink. This is useful for future analyses of snapshots.
10598  *      Multiple snapshots can be created on a region.
10599  *      The @snapshot_id should be obtained using the getter function.
10600  *
10601  *      @region: devlink region of the snapshot
10602  *      @data: snapshot data
10603  *      @snapshot_id: snapshot id to be created
10604  */
10605 int devlink_region_snapshot_create(struct devlink_region *region,
10606                                    u8 *data, u32 snapshot_id)
10607 {
10608         struct devlink *devlink = region->devlink;
10609         int err;
10610
10611         mutex_lock(&devlink->lock);
10612         err = __devlink_region_snapshot_create(region, data, snapshot_id);
10613         mutex_unlock(&devlink->lock);
10614
10615         return err;
10616 }
10617 EXPORT_SYMBOL_GPL(devlink_region_snapshot_create);
10618
10619 #define DEVLINK_TRAP(_id, _type)                                              \
10620         {                                                                     \
10621                 .type = DEVLINK_TRAP_TYPE_##_type,                            \
10622                 .id = DEVLINK_TRAP_GENERIC_ID_##_id,                          \
10623                 .name = DEVLINK_TRAP_GENERIC_NAME_##_id,                      \
10624         }
10625
10626 static const struct devlink_trap devlink_trap_generic[] = {
10627         DEVLINK_TRAP(SMAC_MC, DROP),
10628         DEVLINK_TRAP(VLAN_TAG_MISMATCH, DROP),
10629         DEVLINK_TRAP(INGRESS_VLAN_FILTER, DROP),
10630         DEVLINK_TRAP(INGRESS_STP_FILTER, DROP),
10631         DEVLINK_TRAP(EMPTY_TX_LIST, DROP),
10632         DEVLINK_TRAP(PORT_LOOPBACK_FILTER, DROP),
10633         DEVLINK_TRAP(BLACKHOLE_ROUTE, DROP),
10634         DEVLINK_TRAP(TTL_ERROR, EXCEPTION),
10635         DEVLINK_TRAP(TAIL_DROP, DROP),
10636         DEVLINK_TRAP(NON_IP_PACKET, DROP),
10637         DEVLINK_TRAP(UC_DIP_MC_DMAC, DROP),
10638         DEVLINK_TRAP(DIP_LB, DROP),
10639         DEVLINK_TRAP(SIP_MC, DROP),
10640         DEVLINK_TRAP(SIP_LB, DROP),
10641         DEVLINK_TRAP(CORRUPTED_IP_HDR, DROP),
10642         DEVLINK_TRAP(IPV4_SIP_BC, DROP),
10643         DEVLINK_TRAP(IPV6_MC_DIP_RESERVED_SCOPE, DROP),
10644         DEVLINK_TRAP(IPV6_MC_DIP_INTERFACE_LOCAL_SCOPE, DROP),
10645         DEVLINK_TRAP(MTU_ERROR, EXCEPTION),
10646         DEVLINK_TRAP(UNRESOLVED_NEIGH, EXCEPTION),
10647         DEVLINK_TRAP(RPF, EXCEPTION),
10648         DEVLINK_TRAP(REJECT_ROUTE, EXCEPTION),
10649         DEVLINK_TRAP(IPV4_LPM_UNICAST_MISS, EXCEPTION),
10650         DEVLINK_TRAP(IPV6_LPM_UNICAST_MISS, EXCEPTION),
10651         DEVLINK_TRAP(NON_ROUTABLE, DROP),
10652         DEVLINK_TRAP(DECAP_ERROR, EXCEPTION),
10653         DEVLINK_TRAP(OVERLAY_SMAC_MC, DROP),
10654         DEVLINK_TRAP(INGRESS_FLOW_ACTION_DROP, DROP),
10655         DEVLINK_TRAP(EGRESS_FLOW_ACTION_DROP, DROP),
10656         DEVLINK_TRAP(STP, CONTROL),
10657         DEVLINK_TRAP(LACP, CONTROL),
10658         DEVLINK_TRAP(LLDP, CONTROL),
10659         DEVLINK_TRAP(IGMP_QUERY, CONTROL),
10660         DEVLINK_TRAP(IGMP_V1_REPORT, CONTROL),
10661         DEVLINK_TRAP(IGMP_V2_REPORT, CONTROL),
10662         DEVLINK_TRAP(IGMP_V3_REPORT, CONTROL),
10663         DEVLINK_TRAP(IGMP_V2_LEAVE, CONTROL),
10664         DEVLINK_TRAP(MLD_QUERY, CONTROL),
10665         DEVLINK_TRAP(MLD_V1_REPORT, CONTROL),
10666         DEVLINK_TRAP(MLD_V2_REPORT, CONTROL),
10667         DEVLINK_TRAP(MLD_V1_DONE, CONTROL),
10668         DEVLINK_TRAP(IPV4_DHCP, CONTROL),
10669         DEVLINK_TRAP(IPV6_DHCP, CONTROL),
10670         DEVLINK_TRAP(ARP_REQUEST, CONTROL),
10671         DEVLINK_TRAP(ARP_RESPONSE, CONTROL),
10672         DEVLINK_TRAP(ARP_OVERLAY, CONTROL),
10673         DEVLINK_TRAP(IPV6_NEIGH_SOLICIT, CONTROL),
10674         DEVLINK_TRAP(IPV6_NEIGH_ADVERT, CONTROL),
10675         DEVLINK_TRAP(IPV4_BFD, CONTROL),
10676         DEVLINK_TRAP(IPV6_BFD, CONTROL),
10677         DEVLINK_TRAP(IPV4_OSPF, CONTROL),
10678         DEVLINK_TRAP(IPV6_OSPF, CONTROL),
10679         DEVLINK_TRAP(IPV4_BGP, CONTROL),
10680         DEVLINK_TRAP(IPV6_BGP, CONTROL),
10681         DEVLINK_TRAP(IPV4_VRRP, CONTROL),
10682         DEVLINK_TRAP(IPV6_VRRP, CONTROL),
10683         DEVLINK_TRAP(IPV4_PIM, CONTROL),
10684         DEVLINK_TRAP(IPV6_PIM, CONTROL),
10685         DEVLINK_TRAP(UC_LB, CONTROL),
10686         DEVLINK_TRAP(LOCAL_ROUTE, CONTROL),
10687         DEVLINK_TRAP(EXTERNAL_ROUTE, CONTROL),
10688         DEVLINK_TRAP(IPV6_UC_DIP_LINK_LOCAL_SCOPE, CONTROL),
10689         DEVLINK_TRAP(IPV6_DIP_ALL_NODES, CONTROL),
10690         DEVLINK_TRAP(IPV6_DIP_ALL_ROUTERS, CONTROL),
10691         DEVLINK_TRAP(IPV6_ROUTER_SOLICIT, CONTROL),
10692         DEVLINK_TRAP(IPV6_ROUTER_ADVERT, CONTROL),
10693         DEVLINK_TRAP(IPV6_REDIRECT, CONTROL),
10694         DEVLINK_TRAP(IPV4_ROUTER_ALERT, CONTROL),
10695         DEVLINK_TRAP(IPV6_ROUTER_ALERT, CONTROL),
10696         DEVLINK_TRAP(PTP_EVENT, CONTROL),
10697         DEVLINK_TRAP(PTP_GENERAL, CONTROL),
10698         DEVLINK_TRAP(FLOW_ACTION_SAMPLE, CONTROL),
10699         DEVLINK_TRAP(FLOW_ACTION_TRAP, CONTROL),
10700         DEVLINK_TRAP(EARLY_DROP, DROP),
10701         DEVLINK_TRAP(VXLAN_PARSING, DROP),
10702         DEVLINK_TRAP(LLC_SNAP_PARSING, DROP),
10703         DEVLINK_TRAP(VLAN_PARSING, DROP),
10704         DEVLINK_TRAP(PPPOE_PPP_PARSING, DROP),
10705         DEVLINK_TRAP(MPLS_PARSING, DROP),
10706         DEVLINK_TRAP(ARP_PARSING, DROP),
10707         DEVLINK_TRAP(IP_1_PARSING, DROP),
10708         DEVLINK_TRAP(IP_N_PARSING, DROP),
10709         DEVLINK_TRAP(GRE_PARSING, DROP),
10710         DEVLINK_TRAP(UDP_PARSING, DROP),
10711         DEVLINK_TRAP(TCP_PARSING, DROP),
10712         DEVLINK_TRAP(IPSEC_PARSING, DROP),
10713         DEVLINK_TRAP(SCTP_PARSING, DROP),
10714         DEVLINK_TRAP(DCCP_PARSING, DROP),
10715         DEVLINK_TRAP(GTP_PARSING, DROP),
10716         DEVLINK_TRAP(ESP_PARSING, DROP),
10717         DEVLINK_TRAP(BLACKHOLE_NEXTHOP, DROP),
10718         DEVLINK_TRAP(DMAC_FILTER, DROP),
10719 };
10720
10721 #define DEVLINK_TRAP_GROUP(_id)                                               \
10722         {                                                                     \
10723                 .id = DEVLINK_TRAP_GROUP_GENERIC_ID_##_id,                    \
10724                 .name = DEVLINK_TRAP_GROUP_GENERIC_NAME_##_id,                \
10725         }
10726
10727 static const struct devlink_trap_group devlink_trap_group_generic[] = {
10728         DEVLINK_TRAP_GROUP(L2_DROPS),
10729         DEVLINK_TRAP_GROUP(L3_DROPS),
10730         DEVLINK_TRAP_GROUP(L3_EXCEPTIONS),
10731         DEVLINK_TRAP_GROUP(BUFFER_DROPS),
10732         DEVLINK_TRAP_GROUP(TUNNEL_DROPS),
10733         DEVLINK_TRAP_GROUP(ACL_DROPS),
10734         DEVLINK_TRAP_GROUP(STP),
10735         DEVLINK_TRAP_GROUP(LACP),
10736         DEVLINK_TRAP_GROUP(LLDP),
10737         DEVLINK_TRAP_GROUP(MC_SNOOPING),
10738         DEVLINK_TRAP_GROUP(DHCP),
10739         DEVLINK_TRAP_GROUP(NEIGH_DISCOVERY),
10740         DEVLINK_TRAP_GROUP(BFD),
10741         DEVLINK_TRAP_GROUP(OSPF),
10742         DEVLINK_TRAP_GROUP(BGP),
10743         DEVLINK_TRAP_GROUP(VRRP),
10744         DEVLINK_TRAP_GROUP(PIM),
10745         DEVLINK_TRAP_GROUP(UC_LB),
10746         DEVLINK_TRAP_GROUP(LOCAL_DELIVERY),
10747         DEVLINK_TRAP_GROUP(EXTERNAL_DELIVERY),
10748         DEVLINK_TRAP_GROUP(IPV6),
10749         DEVLINK_TRAP_GROUP(PTP_EVENT),
10750         DEVLINK_TRAP_GROUP(PTP_GENERAL),
10751         DEVLINK_TRAP_GROUP(ACL_SAMPLE),
10752         DEVLINK_TRAP_GROUP(ACL_TRAP),
10753         DEVLINK_TRAP_GROUP(PARSER_ERROR_DROPS),
10754 };
10755
10756 static int devlink_trap_generic_verify(const struct devlink_trap *trap)
10757 {
10758         if (trap->id > DEVLINK_TRAP_GENERIC_ID_MAX)
10759                 return -EINVAL;
10760
10761         if (strcmp(trap->name, devlink_trap_generic[trap->id].name))
10762                 return -EINVAL;
10763
10764         if (trap->type != devlink_trap_generic[trap->id].type)
10765                 return -EINVAL;
10766
10767         return 0;
10768 }
10769
10770 static int devlink_trap_driver_verify(const struct devlink_trap *trap)
10771 {
10772         int i;
10773
10774         if (trap->id <= DEVLINK_TRAP_GENERIC_ID_MAX)
10775                 return -EINVAL;
10776
10777         for (i = 0; i < ARRAY_SIZE(devlink_trap_generic); i++) {
10778                 if (!strcmp(trap->name, devlink_trap_generic[i].name))
10779                         return -EEXIST;
10780         }
10781
10782         return 0;
10783 }
10784
10785 static int devlink_trap_verify(const struct devlink_trap *trap)
10786 {
10787         if (!trap || !trap->name)
10788                 return -EINVAL;
10789
10790         if (trap->generic)
10791                 return devlink_trap_generic_verify(trap);
10792         else
10793                 return devlink_trap_driver_verify(trap);
10794 }
10795
10796 static int
10797 devlink_trap_group_generic_verify(const struct devlink_trap_group *group)
10798 {
10799         if (group->id > DEVLINK_TRAP_GROUP_GENERIC_ID_MAX)
10800                 return -EINVAL;
10801
10802         if (strcmp(group->name, devlink_trap_group_generic[group->id].name))
10803                 return -EINVAL;
10804
10805         return 0;
10806 }
10807
10808 static int
10809 devlink_trap_group_driver_verify(const struct devlink_trap_group *group)
10810 {
10811         int i;
10812
10813         if (group->id <= DEVLINK_TRAP_GROUP_GENERIC_ID_MAX)
10814                 return -EINVAL;
10815
10816         for (i = 0; i < ARRAY_SIZE(devlink_trap_group_generic); i++) {
10817                 if (!strcmp(group->name, devlink_trap_group_generic[i].name))
10818                         return -EEXIST;
10819         }
10820
10821         return 0;
10822 }
10823
10824 static int devlink_trap_group_verify(const struct devlink_trap_group *group)
10825 {
10826         if (group->generic)
10827                 return devlink_trap_group_generic_verify(group);
10828         else
10829                 return devlink_trap_group_driver_verify(group);
10830 }
10831
10832 static void
10833 devlink_trap_group_notify(struct devlink *devlink,
10834                           const struct devlink_trap_group_item *group_item,
10835                           enum devlink_command cmd)
10836 {
10837         struct sk_buff *msg;
10838         int err;
10839
10840         WARN_ON_ONCE(cmd != DEVLINK_CMD_TRAP_GROUP_NEW &&
10841                      cmd != DEVLINK_CMD_TRAP_GROUP_DEL);
10842
10843         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
10844         if (!msg)
10845                 return;
10846
10847         err = devlink_nl_trap_group_fill(msg, devlink, group_item, cmd, 0, 0,
10848                                          0);
10849         if (err) {
10850                 nlmsg_free(msg);
10851                 return;
10852         }
10853
10854         genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink),
10855                                 msg, 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
10856 }
10857
10858 static int
10859 devlink_trap_item_group_link(struct devlink *devlink,
10860                              struct devlink_trap_item *trap_item)
10861 {
10862         u16 group_id = trap_item->trap->init_group_id;
10863         struct devlink_trap_group_item *group_item;
10864
10865         group_item = devlink_trap_group_item_lookup_by_id(devlink, group_id);
10866         if (WARN_ON_ONCE(!group_item))
10867                 return -EINVAL;
10868
10869         trap_item->group_item = group_item;
10870
10871         return 0;
10872 }
10873
10874 static void devlink_trap_notify(struct devlink *devlink,
10875                                 const struct devlink_trap_item *trap_item,
10876                                 enum devlink_command cmd)
10877 {
10878         struct sk_buff *msg;
10879         int err;
10880
10881         WARN_ON_ONCE(cmd != DEVLINK_CMD_TRAP_NEW &&
10882                      cmd != DEVLINK_CMD_TRAP_DEL);
10883
10884         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
10885         if (!msg)
10886                 return;
10887
10888         err = devlink_nl_trap_fill(msg, devlink, trap_item, cmd, 0, 0, 0);
10889         if (err) {
10890                 nlmsg_free(msg);
10891                 return;
10892         }
10893
10894         genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink),
10895                                 msg, 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
10896 }
10897
10898 static int
10899 devlink_trap_register(struct devlink *devlink,
10900                       const struct devlink_trap *trap, void *priv)
10901 {
10902         struct devlink_trap_item *trap_item;
10903         int err;
10904
10905         if (devlink_trap_item_lookup(devlink, trap->name))
10906                 return -EEXIST;
10907
10908         trap_item = kzalloc(sizeof(*trap_item), GFP_KERNEL);
10909         if (!trap_item)
10910                 return -ENOMEM;
10911
10912         trap_item->stats = netdev_alloc_pcpu_stats(struct devlink_stats);
10913         if (!trap_item->stats) {
10914                 err = -ENOMEM;
10915                 goto err_stats_alloc;
10916         }
10917
10918         trap_item->trap = trap;
10919         trap_item->action = trap->init_action;
10920         trap_item->priv = priv;
10921
10922         err = devlink_trap_item_group_link(devlink, trap_item);
10923         if (err)
10924                 goto err_group_link;
10925
10926         err = devlink->ops->trap_init(devlink, trap, trap_item);
10927         if (err)
10928                 goto err_trap_init;
10929
10930         list_add_tail(&trap_item->list, &devlink->trap_list);
10931         devlink_trap_notify(devlink, trap_item, DEVLINK_CMD_TRAP_NEW);
10932
10933         return 0;
10934
10935 err_trap_init:
10936 err_group_link:
10937         free_percpu(trap_item->stats);
10938 err_stats_alloc:
10939         kfree(trap_item);
10940         return err;
10941 }
10942
10943 static void devlink_trap_unregister(struct devlink *devlink,
10944                                     const struct devlink_trap *trap)
10945 {
10946         struct devlink_trap_item *trap_item;
10947
10948         trap_item = devlink_trap_item_lookup(devlink, trap->name);
10949         if (WARN_ON_ONCE(!trap_item))
10950                 return;
10951
10952         devlink_trap_notify(devlink, trap_item, DEVLINK_CMD_TRAP_DEL);
10953         list_del(&trap_item->list);
10954         if (devlink->ops->trap_fini)
10955                 devlink->ops->trap_fini(devlink, trap, trap_item);
10956         free_percpu(trap_item->stats);
10957         kfree(trap_item);
10958 }
10959
10960 static void devlink_trap_disable(struct devlink *devlink,
10961                                  const struct devlink_trap *trap)
10962 {
10963         struct devlink_trap_item *trap_item;
10964
10965         trap_item = devlink_trap_item_lookup(devlink, trap->name);
10966         if (WARN_ON_ONCE(!trap_item))
10967                 return;
10968
10969         devlink->ops->trap_action_set(devlink, trap, DEVLINK_TRAP_ACTION_DROP,
10970                                       NULL);
10971         trap_item->action = DEVLINK_TRAP_ACTION_DROP;
10972 }
10973
10974 /**
10975  * devlink_traps_register - Register packet traps with devlink.
10976  * @devlink: devlink.
10977  * @traps: Packet traps.
10978  * @traps_count: Count of provided packet traps.
10979  * @priv: Driver private information.
10980  *
10981  * Return: Non-zero value on failure.
10982  */
10983 int devlink_traps_register(struct devlink *devlink,
10984                            const struct devlink_trap *traps,
10985                            size_t traps_count, void *priv)
10986 {
10987         int i, err;
10988
10989         if (!devlink->ops->trap_init || !devlink->ops->trap_action_set)
10990                 return -EINVAL;
10991
10992         mutex_lock(&devlink->lock);
10993         for (i = 0; i < traps_count; i++) {
10994                 const struct devlink_trap *trap = &traps[i];
10995
10996                 err = devlink_trap_verify(trap);
10997                 if (err)
10998                         goto err_trap_verify;
10999
11000                 err = devlink_trap_register(devlink, trap, priv);
11001                 if (err)
11002                         goto err_trap_register;
11003         }
11004         mutex_unlock(&devlink->lock);
11005
11006         return 0;
11007
11008 err_trap_register:
11009 err_trap_verify:
11010         for (i--; i >= 0; i--)
11011                 devlink_trap_unregister(devlink, &traps[i]);
11012         mutex_unlock(&devlink->lock);
11013         return err;
11014 }
11015 EXPORT_SYMBOL_GPL(devlink_traps_register);
11016
11017 /**
11018  * devlink_traps_unregister - Unregister packet traps from devlink.
11019  * @devlink: devlink.
11020  * @traps: Packet traps.
11021  * @traps_count: Count of provided packet traps.
11022  */
11023 void devlink_traps_unregister(struct devlink *devlink,
11024                               const struct devlink_trap *traps,
11025                               size_t traps_count)
11026 {
11027         int i;
11028
11029         mutex_lock(&devlink->lock);
11030         /* Make sure we do not have any packets in-flight while unregistering
11031          * traps by disabling all of them and waiting for a grace period.
11032          */
11033         for (i = traps_count - 1; i >= 0; i--)
11034                 devlink_trap_disable(devlink, &traps[i]);
11035         synchronize_rcu();
11036         for (i = traps_count - 1; i >= 0; i--)
11037                 devlink_trap_unregister(devlink, &traps[i]);
11038         mutex_unlock(&devlink->lock);
11039 }
11040 EXPORT_SYMBOL_GPL(devlink_traps_unregister);
11041
11042 static void
11043 devlink_trap_stats_update(struct devlink_stats __percpu *trap_stats,
11044                           size_t skb_len)
11045 {
11046         struct devlink_stats *stats;
11047
11048         stats = this_cpu_ptr(trap_stats);
11049         u64_stats_update_begin(&stats->syncp);
11050         stats->rx_bytes += skb_len;
11051         stats->rx_packets++;
11052         u64_stats_update_end(&stats->syncp);
11053 }
11054
11055 static void
11056 devlink_trap_report_metadata_set(struct devlink_trap_metadata *metadata,
11057                                  const struct devlink_trap_item *trap_item,
11058                                  struct devlink_port *in_devlink_port,
11059                                  const struct flow_action_cookie *fa_cookie)
11060 {
11061         metadata->trap_name = trap_item->trap->name;
11062         metadata->trap_group_name = trap_item->group_item->group->name;
11063         metadata->fa_cookie = fa_cookie;
11064         metadata->trap_type = trap_item->trap->type;
11065
11066         spin_lock(&in_devlink_port->type_lock);
11067         if (in_devlink_port->type == DEVLINK_PORT_TYPE_ETH)
11068                 metadata->input_dev = in_devlink_port->type_dev;
11069         spin_unlock(&in_devlink_port->type_lock);
11070 }
11071
11072 /**
11073  * devlink_trap_report - Report trapped packet to drop monitor.
11074  * @devlink: devlink.
11075  * @skb: Trapped packet.
11076  * @trap_ctx: Trap context.
11077  * @in_devlink_port: Input devlink port.
11078  * @fa_cookie: Flow action cookie. Could be NULL.
11079  */
11080 void devlink_trap_report(struct devlink *devlink, struct sk_buff *skb,
11081                          void *trap_ctx, struct devlink_port *in_devlink_port,
11082                          const struct flow_action_cookie *fa_cookie)
11083
11084 {
11085         struct devlink_trap_item *trap_item = trap_ctx;
11086
11087         devlink_trap_stats_update(trap_item->stats, skb->len);
11088         devlink_trap_stats_update(trap_item->group_item->stats, skb->len);
11089
11090         if (trace_devlink_trap_report_enabled()) {
11091                 struct devlink_trap_metadata metadata = {};
11092
11093                 devlink_trap_report_metadata_set(&metadata, trap_item,
11094                                                  in_devlink_port, fa_cookie);
11095                 trace_devlink_trap_report(devlink, skb, &metadata);
11096         }
11097 }
11098 EXPORT_SYMBOL_GPL(devlink_trap_report);
11099
11100 /**
11101  * devlink_trap_ctx_priv - Trap context to driver private information.
11102  * @trap_ctx: Trap context.
11103  *
11104  * Return: Driver private information passed during registration.
11105  */
11106 void *devlink_trap_ctx_priv(void *trap_ctx)
11107 {
11108         struct devlink_trap_item *trap_item = trap_ctx;
11109
11110         return trap_item->priv;
11111 }
11112 EXPORT_SYMBOL_GPL(devlink_trap_ctx_priv);
11113
11114 static int
11115 devlink_trap_group_item_policer_link(struct devlink *devlink,
11116                                      struct devlink_trap_group_item *group_item)
11117 {
11118         u32 policer_id = group_item->group->init_policer_id;
11119         struct devlink_trap_policer_item *policer_item;
11120
11121         if (policer_id == 0)
11122                 return 0;
11123
11124         policer_item = devlink_trap_policer_item_lookup(devlink, policer_id);
11125         if (WARN_ON_ONCE(!policer_item))
11126                 return -EINVAL;
11127
11128         group_item->policer_item = policer_item;
11129
11130         return 0;
11131 }
11132
11133 static int
11134 devlink_trap_group_register(struct devlink *devlink,
11135                             const struct devlink_trap_group *group)
11136 {
11137         struct devlink_trap_group_item *group_item;
11138         int err;
11139
11140         if (devlink_trap_group_item_lookup(devlink, group->name))
11141                 return -EEXIST;
11142
11143         group_item = kzalloc(sizeof(*group_item), GFP_KERNEL);
11144         if (!group_item)
11145                 return -ENOMEM;
11146
11147         group_item->stats = netdev_alloc_pcpu_stats(struct devlink_stats);
11148         if (!group_item->stats) {
11149                 err = -ENOMEM;
11150                 goto err_stats_alloc;
11151         }
11152
11153         group_item->group = group;
11154
11155         err = devlink_trap_group_item_policer_link(devlink, group_item);
11156         if (err)
11157                 goto err_policer_link;
11158
11159         if (devlink->ops->trap_group_init) {
11160                 err = devlink->ops->trap_group_init(devlink, group);
11161                 if (err)
11162                         goto err_group_init;
11163         }
11164
11165         list_add_tail(&group_item->list, &devlink->trap_group_list);
11166         devlink_trap_group_notify(devlink, group_item,
11167                                   DEVLINK_CMD_TRAP_GROUP_NEW);
11168
11169         return 0;
11170
11171 err_group_init:
11172 err_policer_link:
11173         free_percpu(group_item->stats);
11174 err_stats_alloc:
11175         kfree(group_item);
11176         return err;
11177 }
11178
11179 static void
11180 devlink_trap_group_unregister(struct devlink *devlink,
11181                               const struct devlink_trap_group *group)
11182 {
11183         struct devlink_trap_group_item *group_item;
11184
11185         group_item = devlink_trap_group_item_lookup(devlink, group->name);
11186         if (WARN_ON_ONCE(!group_item))
11187                 return;
11188
11189         devlink_trap_group_notify(devlink, group_item,
11190                                   DEVLINK_CMD_TRAP_GROUP_DEL);
11191         list_del(&group_item->list);
11192         free_percpu(group_item->stats);
11193         kfree(group_item);
11194 }
11195
11196 /**
11197  * devlink_trap_groups_register - Register packet trap groups with devlink.
11198  * @devlink: devlink.
11199  * @groups: Packet trap groups.
11200  * @groups_count: Count of provided packet trap groups.
11201  *
11202  * Return: Non-zero value on failure.
11203  */
11204 int devlink_trap_groups_register(struct devlink *devlink,
11205                                  const struct devlink_trap_group *groups,
11206                                  size_t groups_count)
11207 {
11208         int i, err;
11209
11210         mutex_lock(&devlink->lock);
11211         for (i = 0; i < groups_count; i++) {
11212                 const struct devlink_trap_group *group = &groups[i];
11213
11214                 err = devlink_trap_group_verify(group);
11215                 if (err)
11216                         goto err_trap_group_verify;
11217
11218                 err = devlink_trap_group_register(devlink, group);
11219                 if (err)
11220                         goto err_trap_group_register;
11221         }
11222         mutex_unlock(&devlink->lock);
11223
11224         return 0;
11225
11226 err_trap_group_register:
11227 err_trap_group_verify:
11228         for (i--; i >= 0; i--)
11229                 devlink_trap_group_unregister(devlink, &groups[i]);
11230         mutex_unlock(&devlink->lock);
11231         return err;
11232 }
11233 EXPORT_SYMBOL_GPL(devlink_trap_groups_register);
11234
11235 /**
11236  * devlink_trap_groups_unregister - Unregister packet trap groups from devlink.
11237  * @devlink: devlink.
11238  * @groups: Packet trap groups.
11239  * @groups_count: Count of provided packet trap groups.
11240  */
11241 void devlink_trap_groups_unregister(struct devlink *devlink,
11242                                     const struct devlink_trap_group *groups,
11243                                     size_t groups_count)
11244 {
11245         int i;
11246
11247         mutex_lock(&devlink->lock);
11248         for (i = groups_count - 1; i >= 0; i--)
11249                 devlink_trap_group_unregister(devlink, &groups[i]);
11250         mutex_unlock(&devlink->lock);
11251 }
11252 EXPORT_SYMBOL_GPL(devlink_trap_groups_unregister);
11253
11254 static void
11255 devlink_trap_policer_notify(struct devlink *devlink,
11256                             const struct devlink_trap_policer_item *policer_item,
11257                             enum devlink_command cmd)
11258 {
11259         struct sk_buff *msg;
11260         int err;
11261
11262         WARN_ON_ONCE(cmd != DEVLINK_CMD_TRAP_POLICER_NEW &&
11263                      cmd != DEVLINK_CMD_TRAP_POLICER_DEL);
11264
11265         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
11266         if (!msg)
11267                 return;
11268
11269         err = devlink_nl_trap_policer_fill(msg, devlink, policer_item, cmd, 0,
11270                                            0, 0);
11271         if (err) {
11272                 nlmsg_free(msg);
11273                 return;
11274         }
11275
11276         genlmsg_multicast_netns(&devlink_nl_family, devlink_net(devlink),
11277                                 msg, 0, DEVLINK_MCGRP_CONFIG, GFP_KERNEL);
11278 }
11279
11280 static int
11281 devlink_trap_policer_register(struct devlink *devlink,
11282                               const struct devlink_trap_policer *policer)
11283 {
11284         struct devlink_trap_policer_item *policer_item;
11285         int err;
11286
11287         if (devlink_trap_policer_item_lookup(devlink, policer->id))
11288                 return -EEXIST;
11289
11290         policer_item = kzalloc(sizeof(*policer_item), GFP_KERNEL);
11291         if (!policer_item)
11292                 return -ENOMEM;
11293
11294         policer_item->policer = policer;
11295         policer_item->rate = policer->init_rate;
11296         policer_item->burst = policer->init_burst;
11297
11298         if (devlink->ops->trap_policer_init) {
11299                 err = devlink->ops->trap_policer_init(devlink, policer);
11300                 if (err)
11301                         goto err_policer_init;
11302         }
11303
11304         list_add_tail(&policer_item->list, &devlink->trap_policer_list);
11305         devlink_trap_policer_notify(devlink, policer_item,
11306                                     DEVLINK_CMD_TRAP_POLICER_NEW);
11307
11308         return 0;
11309
11310 err_policer_init:
11311         kfree(policer_item);
11312         return err;
11313 }
11314
11315 static void
11316 devlink_trap_policer_unregister(struct devlink *devlink,
11317                                 const struct devlink_trap_policer *policer)
11318 {
11319         struct devlink_trap_policer_item *policer_item;
11320
11321         policer_item = devlink_trap_policer_item_lookup(devlink, policer->id);
11322         if (WARN_ON_ONCE(!policer_item))
11323                 return;
11324
11325         devlink_trap_policer_notify(devlink, policer_item,
11326                                     DEVLINK_CMD_TRAP_POLICER_DEL);
11327         list_del(&policer_item->list);
11328         if (devlink->ops->trap_policer_fini)
11329                 devlink->ops->trap_policer_fini(devlink, policer);
11330         kfree(policer_item);
11331 }
11332
11333 /**
11334  * devlink_trap_policers_register - Register packet trap policers with devlink.
11335  * @devlink: devlink.
11336  * @policers: Packet trap policers.
11337  * @policers_count: Count of provided packet trap policers.
11338  *
11339  * Return: Non-zero value on failure.
11340  */
11341 int
11342 devlink_trap_policers_register(struct devlink *devlink,
11343                                const struct devlink_trap_policer *policers,
11344                                size_t policers_count)
11345 {
11346         int i, err;
11347
11348         mutex_lock(&devlink->lock);
11349         for (i = 0; i < policers_count; i++) {
11350                 const struct devlink_trap_policer *policer = &policers[i];
11351
11352                 if (WARN_ON(policer->id == 0 ||
11353                             policer->max_rate < policer->min_rate ||
11354                             policer->max_burst < policer->min_burst)) {
11355                         err = -EINVAL;
11356                         goto err_trap_policer_verify;
11357                 }
11358
11359                 err = devlink_trap_policer_register(devlink, policer);
11360                 if (err)
11361                         goto err_trap_policer_register;
11362         }
11363         mutex_unlock(&devlink->lock);
11364
11365         return 0;
11366
11367 err_trap_policer_register:
11368 err_trap_policer_verify:
11369         for (i--; i >= 0; i--)
11370                 devlink_trap_policer_unregister(devlink, &policers[i]);
11371         mutex_unlock(&devlink->lock);
11372         return err;
11373 }
11374 EXPORT_SYMBOL_GPL(devlink_trap_policers_register);
11375
11376 /**
11377  * devlink_trap_policers_unregister - Unregister packet trap policers from devlink.
11378  * @devlink: devlink.
11379  * @policers: Packet trap policers.
11380  * @policers_count: Count of provided packet trap policers.
11381  */
11382 void
11383 devlink_trap_policers_unregister(struct devlink *devlink,
11384                                  const struct devlink_trap_policer *policers,
11385                                  size_t policers_count)
11386 {
11387         int i;
11388
11389         mutex_lock(&devlink->lock);
11390         for (i = policers_count - 1; i >= 0; i--)
11391                 devlink_trap_policer_unregister(devlink, &policers[i]);
11392         mutex_unlock(&devlink->lock);
11393 }
11394 EXPORT_SYMBOL_GPL(devlink_trap_policers_unregister);
11395
11396 static void __devlink_compat_running_version(struct devlink *devlink,
11397                                              char *buf, size_t len)
11398 {
11399         const struct nlattr *nlattr;
11400         struct devlink_info_req req;
11401         struct sk_buff *msg;
11402         int rem, err;
11403
11404         msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
11405         if (!msg)
11406                 return;
11407
11408         req.msg = msg;
11409         err = devlink->ops->info_get(devlink, &req, NULL);
11410         if (err)
11411                 goto free_msg;
11412
11413         nla_for_each_attr(nlattr, (void *)msg->data, msg->len, rem) {
11414                 const struct nlattr *kv;
11415                 int rem_kv;
11416
11417                 if (nla_type(nlattr) != DEVLINK_ATTR_INFO_VERSION_RUNNING)
11418                         continue;
11419
11420                 nla_for_each_nested(kv, nlattr, rem_kv) {
11421                         if (nla_type(kv) != DEVLINK_ATTR_INFO_VERSION_VALUE)
11422                                 continue;
11423
11424                         strlcat(buf, nla_data(kv), len);
11425                         strlcat(buf, " ", len);
11426                 }
11427         }
11428 free_msg:
11429         nlmsg_free(msg);
11430 }
11431
11432 void devlink_compat_running_version(struct net_device *dev,
11433                                     char *buf, size_t len)
11434 {
11435         struct devlink *devlink;
11436
11437         dev_hold(dev);
11438         rtnl_unlock();
11439
11440         devlink = netdev_to_devlink(dev);
11441         if (!devlink || !devlink->ops->info_get)
11442                 goto out;
11443
11444         mutex_lock(&devlink->lock);
11445         __devlink_compat_running_version(devlink, buf, len);
11446         mutex_unlock(&devlink->lock);
11447
11448 out:
11449         rtnl_lock();
11450         dev_put(dev);
11451 }
11452
11453 int devlink_compat_flash_update(struct net_device *dev, const char *file_name)
11454 {
11455         struct devlink_flash_update_params params = {};
11456         struct devlink *devlink;
11457         int ret;
11458
11459         dev_hold(dev);
11460         rtnl_unlock();
11461
11462         devlink = netdev_to_devlink(dev);
11463         if (!devlink || !devlink->ops->flash_update) {
11464                 ret = -EOPNOTSUPP;
11465                 goto out;
11466         }
11467
11468         ret = request_firmware(&params.fw, file_name, devlink->dev);
11469         if (ret)
11470                 goto out;
11471
11472         mutex_lock(&devlink->lock);
11473         devlink_flash_update_begin_notify(devlink);
11474         ret = devlink->ops->flash_update(devlink, &params, NULL);
11475         devlink_flash_update_end_notify(devlink);
11476         mutex_unlock(&devlink->lock);
11477
11478         release_firmware(params.fw);
11479
11480 out:
11481         rtnl_lock();
11482         dev_put(dev);
11483
11484         return ret;
11485 }
11486
11487 int devlink_compat_phys_port_name_get(struct net_device *dev,
11488                                       char *name, size_t len)
11489 {
11490         struct devlink_port *devlink_port;
11491
11492         /* RTNL mutex is held here which ensures that devlink_port
11493          * instance cannot disappear in the middle. No need to take
11494          * any devlink lock as only permanent values are accessed.
11495          */
11496         ASSERT_RTNL();
11497
11498         devlink_port = netdev_to_devlink_port(dev);
11499         if (!devlink_port)
11500                 return -EOPNOTSUPP;
11501
11502         return __devlink_port_phys_port_name_get(devlink_port, name, len);
11503 }
11504
11505 int devlink_compat_switch_id_get(struct net_device *dev,
11506                                  struct netdev_phys_item_id *ppid)
11507 {
11508         struct devlink_port *devlink_port;
11509
11510         /* Caller must hold RTNL mutex or reference to dev, which ensures that
11511          * devlink_port instance cannot disappear in the middle. No need to take
11512          * any devlink lock as only permanent values are accessed.
11513          */
11514         devlink_port = netdev_to_devlink_port(dev);
11515         if (!devlink_port || !devlink_port->switch_port)
11516                 return -EOPNOTSUPP;
11517
11518         memcpy(ppid, &devlink_port->attrs.switch_id, sizeof(*ppid));
11519
11520         return 0;
11521 }
11522
11523 static void __net_exit devlink_pernet_pre_exit(struct net *net)
11524 {
11525         struct devlink *devlink;
11526         u32 actions_performed;
11527         unsigned long index;
11528         int err;
11529
11530         /* In case network namespace is getting destroyed, reload
11531          * all devlink instances from this namespace into init_net.
11532          */
11533         mutex_lock(&devlink_mutex);
11534         xa_for_each_marked(&devlinks, index, devlink, DEVLINK_REGISTERED) {
11535                 if (!devlink_try_get(devlink))
11536                         continue;
11537
11538                 if (!net_eq(devlink_net(devlink), net))
11539                         goto retry;
11540
11541                 WARN_ON(!devlink_reload_supported(devlink->ops));
11542                 err = devlink_reload(devlink, &init_net,
11543                                      DEVLINK_RELOAD_ACTION_DRIVER_REINIT,
11544                                      DEVLINK_RELOAD_LIMIT_UNSPEC,
11545                                      &actions_performed, NULL);
11546                 if (err && err != -EOPNOTSUPP)
11547                         pr_warn("Failed to reload devlink instance into init_net\n");
11548 retry:
11549                 devlink_put(devlink);
11550         }
11551         mutex_unlock(&devlink_mutex);
11552 }
11553
11554 static struct pernet_operations devlink_pernet_ops __net_initdata = {
11555         .pre_exit = devlink_pernet_pre_exit,
11556 };
11557
11558 static int __init devlink_init(void)
11559 {
11560         int err;
11561
11562         err = genl_register_family(&devlink_nl_family);
11563         if (err)
11564                 goto out;
11565         err = register_pernet_subsys(&devlink_pernet_ops);
11566
11567 out:
11568         WARN_ON(err);
11569         return err;
11570 }
11571
11572 subsys_initcall(devlink_init);