Lines Matching +full:port +full:- +full:id
1 // SPDX-License-Identifier: GPL-2.0-or-later
11 struct devlink_port *port; member
31 u32 id; member
39 list_for_each_entry(region, &devlink->region_list, list) in devlink_region_get_by_name()
40 if (!strcmp(region->ops->name, region_name)) in devlink_region_get_by_name()
47 devlink_port_region_get_by_name(struct devlink_port *port, in devlink_port_region_get_by_name() argument
52 list_for_each_entry(region, &port->region_list, list) in devlink_port_region_get_by_name()
53 if (!strcmp(region->ops->name, region_name)) in devlink_port_region_get_by_name()
60 devlink_region_snapshot_get_by_id(struct devlink_region *region, u32 id) in devlink_region_snapshot_get_by_id() argument
64 list_for_each_entry(snapshot, ®ion->snapshot_list, list) in devlink_region_snapshot_get_by_id()
65 if (snapshot->id == id) in devlink_region_snapshot_get_by_id()
80 return -EINVAL; in devlink_nl_region_snapshot_id_put()
82 err = nla_put_u32(msg, DEVLINK_ATTR_REGION_SNAPSHOT_ID, snapshot->id); in devlink_nl_region_snapshot_id_put()
105 return -EINVAL; in devlink_nl_region_snapshots_id_put()
107 list_for_each_entry(snapshot, ®ion->snapshot_list, list) { in devlink_nl_region_snapshots_id_put()
131 return -EMSGSIZE; in devlink_nl_region_fill()
137 if (region->port) { in devlink_nl_region_fill()
139 region->port->index); in devlink_nl_region_fill()
144 err = nla_put_string(msg, DEVLINK_ATTR_REGION_NAME, region->ops->name); in devlink_nl_region_fill()
149 region->size, in devlink_nl_region_fill()
155 region->max_snapshots); in devlink_nl_region_fill()
176 struct devlink *devlink = region->devlink; in devlink_nl_region_notify_build()
183 return ERR_PTR(-ENOMEM); in devlink_nl_region_notify_build()
187 err = -EMSGSIZE; in devlink_nl_region_notify_build()
195 if (region->port) { in devlink_nl_region_notify_build()
197 region->port->index); in devlink_nl_region_notify_build()
203 region->ops->name); in devlink_nl_region_notify_build()
209 snapshot->id); in devlink_nl_region_notify_build()
214 region->size, DEVLINK_ATTR_PAD); in devlink_nl_region_notify_build()
233 struct devlink *devlink = region->devlink; in devlink_nl_region_notify()
252 list_for_each_entry(region, &devlink->region_list, list) in devlink_regions_notify_register()
260 list_for_each_entry_reverse(region, &devlink->region_list, list) in devlink_regions_notify_unregister()
265 * __devlink_snapshot_id_increment - Increment number of snapshots using an id
267 * @id: the snapshot id
269 * Track when a new snapshot begins using an id. Load the count for the
270 * given id from the snapshot xarray, increment it, and store it back.
272 * Called when a new snapshot is created with the given id.
274 * The id *must* have been previously allocated by
279 static int __devlink_snapshot_id_increment(struct devlink *devlink, u32 id) in __devlink_snapshot_id_increment() argument
285 xa_lock(&devlink->snapshot_ids); in __devlink_snapshot_id_increment()
286 p = xa_load(&devlink->snapshot_ids, id); in __devlink_snapshot_id_increment()
288 err = -EINVAL; in __devlink_snapshot_id_increment()
293 err = -EINVAL; in __devlink_snapshot_id_increment()
300 err = xa_err(__xa_store(&devlink->snapshot_ids, id, xa_mk_value(count), in __devlink_snapshot_id_increment()
303 xa_unlock(&devlink->snapshot_ids); in __devlink_snapshot_id_increment()
308 * __devlink_snapshot_id_decrement - Decrease number of snapshots using an id
310 * @id: the snapshot id
312 * Track when a snapshot is deleted and stops using an id. Load the count
313 * for the given id from the snapshot xarray, decrement it, and store it
316 * If the count reaches zero, erase this id from the xarray, freeing it
317 * up for future re-use by devlink_region_snapshot_id_get().
319 * Called when a snapshot using the given id is deleted, and when the
320 * initial allocator of the id is finished using it.
322 static void __devlink_snapshot_id_decrement(struct devlink *devlink, u32 id) in __devlink_snapshot_id_decrement() argument
327 xa_lock(&devlink->snapshot_ids); in __devlink_snapshot_id_decrement()
328 p = xa_load(&devlink->snapshot_ids, id); in __devlink_snapshot_id_decrement()
338 count--; in __devlink_snapshot_id_decrement()
339 __xa_store(&devlink->snapshot_ids, id, xa_mk_value(count), in __devlink_snapshot_id_decrement()
342 /* If this was the last user, we can erase this id */ in __devlink_snapshot_id_decrement()
343 __xa_erase(&devlink->snapshot_ids, id); in __devlink_snapshot_id_decrement()
346 xa_unlock(&devlink->snapshot_ids); in __devlink_snapshot_id_decrement()
350 * __devlink_snapshot_id_insert - Insert a specific snapshot ID
352 * @id: the snapshot id
354 * Mark the given snapshot id as used by inserting a zero value into the
359 * It is expected that the id will immediately be used before
362 * Returns zero on success, or an error code if the snapshot id could not
365 static int __devlink_snapshot_id_insert(struct devlink *devlink, u32 id) in __devlink_snapshot_id_insert() argument
369 xa_lock(&devlink->snapshot_ids); in __devlink_snapshot_id_insert()
370 if (xa_load(&devlink->snapshot_ids, id)) { in __devlink_snapshot_id_insert()
371 xa_unlock(&devlink->snapshot_ids); in __devlink_snapshot_id_insert()
372 return -EEXIST; in __devlink_snapshot_id_insert()
374 err = xa_err(__xa_store(&devlink->snapshot_ids, id, xa_mk_value(0), in __devlink_snapshot_id_insert()
376 xa_unlock(&devlink->snapshot_ids); in __devlink_snapshot_id_insert()
381 * __devlink_region_snapshot_id_get - get snapshot ID
383 * @id: storage to return snapshot id
385 * Allocates a new snapshot id. Returns zero on success, or a negative
390 * users of the snapshot id.
396 static int __devlink_region_snapshot_id_get(struct devlink *devlink, u32 *id) in __devlink_region_snapshot_id_get() argument
398 return xa_alloc(&devlink->snapshot_ids, id, xa_mk_value(1), in __devlink_region_snapshot_id_get()
403 * __devlink_region_snapshot_create - create a new snapshot
414 * @snapshot_id: snapshot id to be created
420 struct devlink *devlink = region->devlink; in __devlink_region_snapshot_create()
424 lockdep_assert_held(®ion->snapshot_lock); in __devlink_region_snapshot_create()
427 if (region->cur_snapshots == region->max_snapshots) in __devlink_region_snapshot_create()
428 return -ENOSPC; in __devlink_region_snapshot_create()
431 return -EEXIST; in __devlink_region_snapshot_create()
435 return -ENOMEM; in __devlink_region_snapshot_create()
441 snapshot->id = snapshot_id; in __devlink_region_snapshot_create()
442 snapshot->region = region; in __devlink_region_snapshot_create()
443 snapshot->data = data; in __devlink_region_snapshot_create()
445 list_add_tail(&snapshot->list, ®ion->snapshot_list); in __devlink_region_snapshot_create()
447 region->cur_snapshots++; in __devlink_region_snapshot_create()
460 struct devlink *devlink = region->devlink; in devlink_region_snapshot_del()
462 lockdep_assert_held(®ion->snapshot_lock); in devlink_region_snapshot_del()
465 region->cur_snapshots--; in devlink_region_snapshot_del()
466 list_del(&snapshot->list); in devlink_region_snapshot_del()
467 region->ops->destructor(snapshot->data); in devlink_region_snapshot_del()
468 __devlink_snapshot_id_decrement(devlink, snapshot->id); in devlink_region_snapshot_del()
474 struct devlink *devlink = info->user_ptr[0]; in devlink_nl_region_get_doit()
475 struct devlink_port *port = NULL; in devlink_nl_region_get_doit() local
483 return -EINVAL; in devlink_nl_region_get_doit()
485 if (info->attrs[DEVLINK_ATTR_PORT_INDEX]) { in devlink_nl_region_get_doit()
486 index = nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_INDEX]); in devlink_nl_region_get_doit()
488 port = devlink_port_get_by_index(devlink, index); in devlink_nl_region_get_doit()
489 if (!port) in devlink_nl_region_get_doit()
490 return -ENODEV; in devlink_nl_region_get_doit()
493 region_name = nla_data(info->attrs[DEVLINK_ATTR_REGION_NAME]); in devlink_nl_region_get_doit()
494 if (port) in devlink_nl_region_get_doit()
495 region = devlink_port_region_get_by_name(port, region_name); in devlink_nl_region_get_doit()
500 return -EINVAL; in devlink_nl_region_get_doit()
504 return -ENOMEM; in devlink_nl_region_get_doit()
507 info->snd_portid, info->snd_seq, 0, in devlink_nl_region_get_doit()
519 struct devlink_port *port, in devlink_nl_cmd_region_get_port_dumpit() argument
525 list_for_each_entry(region, &port->region_list, list) { in devlink_nl_cmd_region_get_port_dumpit()
530 err = devlink_nl_region_fill(msg, port->devlink, in devlink_nl_cmd_region_get_port_dumpit()
532 NETLINK_CB(cb->skb).portid, in devlink_nl_cmd_region_get_port_dumpit()
533 cb->nlh->nlmsg_seq, in devlink_nl_cmd_region_get_port_dumpit()
551 struct devlink_port *port; in devlink_nl_region_get_dump_one() local
556 list_for_each_entry(region, &devlink->region_list, list) { in devlink_nl_region_get_dump_one()
557 if (idx < state->idx) { in devlink_nl_region_get_dump_one()
563 NETLINK_CB(cb->skb).portid, in devlink_nl_region_get_dump_one()
564 cb->nlh->nlmsg_seq, flags, in devlink_nl_region_get_dump_one()
567 state->idx = idx; in devlink_nl_region_get_dump_one()
573 xa_for_each(&devlink->ports, port_index, port) { in devlink_nl_region_get_dump_one()
574 err = devlink_nl_cmd_region_get_port_dumpit(msg, cb, port, &idx, in devlink_nl_region_get_dump_one()
575 state->idx, flags); in devlink_nl_region_get_dump_one()
577 state->idx = idx; in devlink_nl_region_get_dump_one()
593 struct devlink *devlink = info->user_ptr[0]; in devlink_nl_region_del_doit()
595 struct devlink_port *port = NULL; in devlink_nl_region_del_doit() local
603 return -EINVAL; in devlink_nl_region_del_doit()
605 region_name = nla_data(info->attrs[DEVLINK_ATTR_REGION_NAME]); in devlink_nl_region_del_doit()
606 snapshot_id = nla_get_u32(info->attrs[DEVLINK_ATTR_REGION_SNAPSHOT_ID]); in devlink_nl_region_del_doit()
608 if (info->attrs[DEVLINK_ATTR_PORT_INDEX]) { in devlink_nl_region_del_doit()
609 index = nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_INDEX]); in devlink_nl_region_del_doit()
611 port = devlink_port_get_by_index(devlink, index); in devlink_nl_region_del_doit()
612 if (!port) in devlink_nl_region_del_doit()
613 return -ENODEV; in devlink_nl_region_del_doit()
616 if (port) in devlink_nl_region_del_doit()
617 region = devlink_port_region_get_by_name(port, region_name); in devlink_nl_region_del_doit()
622 return -EINVAL; in devlink_nl_region_del_doit()
624 mutex_lock(®ion->snapshot_lock); in devlink_nl_region_del_doit()
627 mutex_unlock(®ion->snapshot_lock); in devlink_nl_region_del_doit()
628 return -EINVAL; in devlink_nl_region_del_doit()
632 mutex_unlock(®ion->snapshot_lock); in devlink_nl_region_del_doit()
638 struct devlink *devlink = info->user_ptr[0]; in devlink_nl_region_new_doit()
640 struct devlink_port *port = NULL; in devlink_nl_region_new_doit() local
650 NL_SET_ERR_MSG(info->extack, "No region name provided"); in devlink_nl_region_new_doit()
651 return -EINVAL; in devlink_nl_region_new_doit()
654 region_name = nla_data(info->attrs[DEVLINK_ATTR_REGION_NAME]); in devlink_nl_region_new_doit()
656 if (info->attrs[DEVLINK_ATTR_PORT_INDEX]) { in devlink_nl_region_new_doit()
657 index = nla_get_u32(info->attrs[DEVLINK_ATTR_PORT_INDEX]); in devlink_nl_region_new_doit()
659 port = devlink_port_get_by_index(devlink, index); in devlink_nl_region_new_doit()
660 if (!port) in devlink_nl_region_new_doit()
661 return -ENODEV; in devlink_nl_region_new_doit()
664 if (port) in devlink_nl_region_new_doit()
665 region = devlink_port_region_get_by_name(port, region_name); in devlink_nl_region_new_doit()
670 NL_SET_ERR_MSG(info->extack, "The requested region does not exist"); in devlink_nl_region_new_doit()
671 return -EINVAL; in devlink_nl_region_new_doit()
674 if (!region->ops->snapshot) { in devlink_nl_region_new_doit()
675 …NL_SET_ERR_MSG(info->extack, "The requested region does not support taking an immediate snapshot"); in devlink_nl_region_new_doit()
676 return -EOPNOTSUPP; in devlink_nl_region_new_doit()
679 mutex_lock(®ion->snapshot_lock); in devlink_nl_region_new_doit()
681 if (region->cur_snapshots == region->max_snapshots) { in devlink_nl_region_new_doit()
682 NL_SET_ERR_MSG(info->extack, "The region has reached the maximum number of stored snapshots"); in devlink_nl_region_new_doit()
683 err = -ENOSPC; in devlink_nl_region_new_doit()
687 snapshot_id_attr = info->attrs[DEVLINK_ATTR_REGION_SNAPSHOT_ID]; in devlink_nl_region_new_doit()
692 NL_SET_ERR_MSG(info->extack, "The requested snapshot id is already in use"); in devlink_nl_region_new_doit()
693 err = -EEXIST; in devlink_nl_region_new_doit()
703 NL_SET_ERR_MSG(info->extack, "Failed to allocate a new snapshot id"); in devlink_nl_region_new_doit()
708 if (port) in devlink_nl_region_new_doit()
709 err = region->port_ops->snapshot(port, region->port_ops, in devlink_nl_region_new_doit()
710 info->extack, &data); in devlink_nl_region_new_doit()
712 err = region->ops->snapshot(devlink, region->ops, in devlink_nl_region_new_doit()
713 info->extack, &data); in devlink_nl_region_new_doit()
727 err = -EINVAL; in devlink_nl_region_new_doit()
733 info->snd_portid, in devlink_nl_region_new_doit()
734 info->snd_seq); in devlink_nl_region_new_doit()
744 mutex_unlock(®ion->snapshot_lock); in devlink_nl_region_new_doit()
748 region->ops->destructor(data); in devlink_nl_region_new_doit()
751 mutex_unlock(®ion->snapshot_lock); in devlink_nl_region_new_doit()
757 mutex_unlock(®ion->snapshot_lock); in devlink_nl_region_new_doit()
770 return -EINVAL; in devlink_nl_cmd_region_read_chunk_fill()
804 /* Allocate and re-use a single buffer */ in devlink_nl_region_read_fill()
807 return -ENOMEM; in devlink_nl_region_read_fill()
814 data_size = min_t(u32, end_offset - curr_offset, in devlink_nl_region_read_fill()
841 memcpy(chunk, &snapshot->data[curr_offset], chunk_size); in devlink_region_snapshot_fill()
852 return region->port_ops->read(region->port, region->port_ops, extack, in devlink_region_port_direct_fill()
862 return region->ops->read(region->devlink, region->ops, extack, in devlink_region_direct_fill()
873 struct nlattr **attrs = info->info.attrs; in devlink_nl_region_read_dumpit()
874 struct devlink_port *port = NULL; in devlink_nl_region_read_dumpit() local
884 start_offset = state->start_offset; in devlink_nl_region_read_dumpit()
886 devlink = devlink_get_from_attrs_lock(sock_net(cb->skb->sk), attrs, in devlink_nl_region_read_dumpit()
892 NL_SET_ERR_MSG(cb->extack, "No region name provided"); in devlink_nl_region_read_dumpit()
893 err = -EINVAL; in devlink_nl_region_read_dumpit()
900 port = devlink_port_get_by_index(devlink, index); in devlink_nl_region_read_dumpit()
901 if (!port) { in devlink_nl_region_read_dumpit()
902 err = -ENODEV; in devlink_nl_region_read_dumpit()
910 if (port) in devlink_nl_region_read_dumpit()
911 region = devlink_port_region_get_by_name(port, region_name); in devlink_nl_region_read_dumpit()
916 NL_SET_ERR_MSG_ATTR(cb->extack, region_attr, "Requested region does not exist"); in devlink_nl_region_read_dumpit()
917 err = -EINVAL; in devlink_nl_region_read_dumpit()
924 NL_SET_ERR_MSG(cb->extack, "No snapshot id provided"); in devlink_nl_region_read_dumpit()
925 err = -EINVAL; in devlink_nl_region_read_dumpit()
929 if (!region->ops->read) { in devlink_nl_region_read_dumpit()
930 NL_SET_ERR_MSG(cb->extack, "Requested region does not support direct read"); in devlink_nl_region_read_dumpit()
931 err = -EOPNOTSUPP; in devlink_nl_region_read_dumpit()
935 if (port) in devlink_nl_region_read_dumpit()
945 NL_SET_ERR_MSG_ATTR(cb->extack, snapshot_attr, "Direct region read does not use snapshot"); in devlink_nl_region_read_dumpit()
946 err = -EINVAL; in devlink_nl_region_read_dumpit()
953 NL_SET_ERR_MSG_ATTR(cb->extack, snapshot_attr, "Requested snapshot does not exist"); in devlink_nl_region_read_dumpit()
954 err = -EINVAL; in devlink_nl_region_read_dumpit()
971 if (end_offset > region->size) in devlink_nl_region_read_dumpit()
972 end_offset = region->size; in devlink_nl_region_read_dumpit()
980 hdr = genlmsg_put(skb, NETLINK_CB(cb->skb).portid, cb->nlh->nlmsg_seq, in devlink_nl_region_read_dumpit()
984 err = -EMSGSIZE; in devlink_nl_region_read_dumpit()
992 if (region->port) { in devlink_nl_region_read_dumpit()
994 region->port->index); in devlink_nl_region_read_dumpit()
1005 err = -EMSGSIZE; in devlink_nl_region_read_dumpit()
1011 cb->extack); in devlink_nl_region_read_dumpit()
1013 if (err && err != -EMSGSIZE) in devlink_nl_region_read_dumpit()
1018 err = -EINVAL; in devlink_nl_region_read_dumpit()
1022 state->start_offset = ret_offset; in devlink_nl_region_read_dumpit()
1028 return skb->len; in devlink_nl_region_read_dumpit()
1039 * devl_region_create - create a new address region
1055 if (WARN_ON(!ops) || WARN_ON(!ops->destructor)) in devl_region_create()
1056 return ERR_PTR(-EINVAL); in devl_region_create()
1058 if (devlink_region_get_by_name(devlink, ops->name)) in devl_region_create()
1059 return ERR_PTR(-EEXIST); in devl_region_create()
1063 return ERR_PTR(-ENOMEM); in devl_region_create()
1065 region->devlink = devlink; in devl_region_create()
1066 region->max_snapshots = region_max_snapshots; in devl_region_create()
1067 region->ops = ops; in devl_region_create()
1068 region->size = region_size; in devl_region_create()
1069 INIT_LIST_HEAD(®ion->snapshot_list); in devl_region_create()
1070 mutex_init(®ion->snapshot_lock); in devl_region_create()
1071 list_add_tail(®ion->list, &devlink->region_list); in devl_region_create()
1079 * devlink_region_create - create a new address region
1086 * Context: Takes and release devlink->lock <mutex>.
1104 * devlink_port_region_create - create a new address region for a port
1106 * @port: devlink port
1111 * Context: Takes and release devlink->lock <mutex>.
1114 devlink_port_region_create(struct devlink_port *port, in devlink_port_region_create() argument
1118 struct devlink *devlink = port->devlink; in devlink_port_region_create()
1122 ASSERT_DEVLINK_PORT_INITIALIZED(port); in devlink_port_region_create()
1124 if (WARN_ON(!ops) || WARN_ON(!ops->destructor)) in devlink_port_region_create()
1125 return ERR_PTR(-EINVAL); in devlink_port_region_create()
1129 if (devlink_port_region_get_by_name(port, ops->name)) { in devlink_port_region_create()
1130 err = -EEXIST; in devlink_port_region_create()
1136 err = -ENOMEM; in devlink_port_region_create()
1140 region->devlink = devlink; in devlink_port_region_create()
1141 region->port = port; in devlink_port_region_create()
1142 region->max_snapshots = region_max_snapshots; in devlink_port_region_create()
1143 region->port_ops = ops; in devlink_port_region_create()
1144 region->size = region_size; in devlink_port_region_create()
1145 INIT_LIST_HEAD(®ion->snapshot_list); in devlink_port_region_create()
1146 mutex_init(®ion->snapshot_lock); in devlink_port_region_create()
1147 list_add_tail(®ion->list, &port->region_list); in devlink_port_region_create()
1160 * devl_region_destroy - destroy address region
1166 struct devlink *devlink = region->devlink; in devl_region_destroy()
1172 mutex_lock(®ion->snapshot_lock); in devl_region_destroy()
1173 list_for_each_entry_safe(snapshot, ts, ®ion->snapshot_list, list) in devl_region_destroy()
1175 mutex_unlock(®ion->snapshot_lock); in devl_region_destroy()
1177 list_del(®ion->list); in devl_region_destroy()
1178 mutex_destroy(®ion->snapshot_lock); in devl_region_destroy()
1186 * devlink_region_destroy - destroy address region
1190 * Context: Takes and release devlink->lock <mutex>.
1194 struct devlink *devlink = region->devlink; in devlink_region_destroy()
1203 * devlink_region_snapshot_id_get - get snapshot ID
1206 * Driver should use the same id for multiple snapshots taken
1210 * when finished creating regions using this id.
1215 * @id: storage to return id
1217 int devlink_region_snapshot_id_get(struct devlink *devlink, u32 *id) in devlink_region_snapshot_id_get() argument
1219 return __devlink_region_snapshot_id_get(devlink, id); in devlink_region_snapshot_id_get()
1224 * devlink_region_snapshot_id_put - put snapshot ID reference
1227 * with an id. Doing so ensures that the ID can later be released in the
1231 * @id: id to release reference on
1233 void devlink_region_snapshot_id_put(struct devlink *devlink, u32 id) in devlink_region_snapshot_id_put() argument
1235 __devlink_snapshot_id_decrement(devlink, id); in devlink_region_snapshot_id_put()
1240 * devlink_region_snapshot_create - create a new snapshot
1249 * @snapshot_id: snapshot id to be created
1256 mutex_lock(®ion->snapshot_lock); in devlink_region_snapshot_create()
1258 mutex_unlock(®ion->snapshot_lock); in devlink_region_snapshot_create()