19
19
#include <linux/device.h>
20
20
#include <linux/list.h>
21
21
#include <linux/netdevice.h>
22
+ #include <linux/spinlock.h>
22
23
#include <rdma/ib_verbs.h>
23
24
#include <net/netlink.h>
24
25
#include <net/genetlink.h>
@@ -543,12 +544,14 @@ static int devlink_nl_port_fill(struct sk_buff *msg, struct devlink *devlink,
543
544
goto nla_put_failure ;
544
545
if (nla_put_u32 (msg , DEVLINK_ATTR_PORT_INDEX , devlink_port -> index ))
545
546
goto nla_put_failure ;
547
+
548
+ spin_lock (& devlink_port -> type_lock );
546
549
if (nla_put_u16 (msg , DEVLINK_ATTR_PORT_TYPE , devlink_port -> type ))
547
- goto nla_put_failure ;
550
+ goto nla_put_failure_type_locked ;
548
551
if (devlink_port -> desired_type != DEVLINK_PORT_TYPE_NOTSET &&
549
552
nla_put_u16 (msg , DEVLINK_ATTR_PORT_DESIRED_TYPE ,
550
553
devlink_port -> desired_type ))
551
- goto nla_put_failure ;
554
+ goto nla_put_failure_type_locked ;
552
555
if (devlink_port -> type == DEVLINK_PORT_TYPE_ETH ) {
553
556
struct net_device * netdev = devlink_port -> type_dev ;
554
557
@@ -557,22 +560,25 @@ static int devlink_nl_port_fill(struct sk_buff *msg, struct devlink *devlink,
557
560
netdev -> ifindex ) ||
558
561
nla_put_string (msg , DEVLINK_ATTR_PORT_NETDEV_NAME ,
559
562
netdev -> name )))
560
- goto nla_put_failure ;
563
+ goto nla_put_failure_type_locked ;
561
564
}
562
565
if (devlink_port -> type == DEVLINK_PORT_TYPE_IB ) {
563
566
struct ib_device * ibdev = devlink_port -> type_dev ;
564
567
565
568
if (ibdev &&
566
569
nla_put_string (msg , DEVLINK_ATTR_PORT_IBDEV_NAME ,
567
570
ibdev -> name ))
568
- goto nla_put_failure ;
571
+ goto nla_put_failure_type_locked ;
569
572
}
573
+ spin_unlock (& devlink_port -> type_lock );
570
574
if (devlink_nl_port_attrs_put (msg , devlink_port ))
571
575
goto nla_put_failure ;
572
576
573
577
genlmsg_end (msg , hdr );
574
578
return 0 ;
575
579
580
+ nla_put_failure_type_locked :
581
+ spin_unlock (& devlink_port -> type_lock );
576
582
nla_put_failure :
577
583
genlmsg_cancel (msg , hdr );
578
584
return - EMSGSIZE ;
@@ -5300,6 +5306,7 @@ int devlink_port_register(struct devlink *devlink,
5300
5306
devlink_port -> devlink = devlink ;
5301
5307
devlink_port -> index = port_index ;
5302
5308
devlink_port -> registered = true;
5309
+ spin_lock_init (& devlink_port -> type_lock );
5303
5310
list_add_tail (& devlink_port -> list , & devlink -> port_list );
5304
5311
INIT_LIST_HEAD (& devlink_port -> param_list );
5305
5312
mutex_unlock (& devlink -> lock );
@@ -5330,8 +5337,10 @@ static void __devlink_port_type_set(struct devlink_port *devlink_port,
5330
5337
{
5331
5338
if (WARN_ON (!devlink_port -> registered ))
5332
5339
return ;
5340
+ spin_lock (& devlink_port -> type_lock );
5333
5341
devlink_port -> type = type ;
5334
5342
devlink_port -> type_dev = type_dev ;
5343
+ spin_unlock (& devlink_port -> type_lock );
5335
5344
devlink_port_notify (devlink_port , DEVLINK_CMD_PORT_NEW );
5336
5345
}
5337
5346
0 commit comments