@@ -336,4 +336,8 @@ struct net_device *rdma_read_gid_attr_ndev_rcu(const struct ib_gid_attr *attr);
void rdma_init_coredev(struct ib_core_device *coredev, struct ib_device *dev,
struct net *net);
+
+void ib_free_port_attrs(struct ib_core_device *coredev);
+int ib_setup_port_attrs(struct ib_core_device *coredev,
+ bool alloc_hw_stats);
#endif /* _CORE_PRIV_H */
@@ -715,6 +715,9 @@ static int add_one_compat_dev(struct ib_device *device,
ret = device_add(&cdev->coredev.dev);
if (ret)
goto add_err;
+ ret = ib_setup_port_attrs(&cdev->coredev, false);
+ if (ret)
+ goto port_err;
ret = xa_insert(&device->compat_devs, rnet->id, cdev, GFP_KERNEL);
if (ret)
@@ -724,6 +727,8 @@ static int add_one_compat_dev(struct ib_device *device,
return 0;
insert_err:
+ ib_free_port_attrs(&cdev->coredev);
+port_err:
device_del(&cdev->coredev.dev);
add_err:
put_device(&cdev->coredev.dev);
@@ -740,6 +745,7 @@ static void remove_one_compat_dev(struct ib_device *device, u32 id)
cdev = xa_erase(&device->compat_devs, id);
mutex_unlock(&device->compat_devs_mutex);
if (cdev) {
+ ib_free_port_attrs(&cdev->coredev);
device_del(&cdev->coredev.dev);
put_device(&cdev->coredev.dev);
}
@@ -1015,7 +1015,8 @@ static void setup_hw_stats(struct ib_device *device, struct ib_port *port,
return;
}
-static int add_port(struct ib_core_device *coredev, int port_num)
+static int add_port(struct ib_core_device *coredev,
+ int port_num, bool alloc_stats)
{
struct ib_device *device = rdma_device_to_ibdev(&coredev->dev);
struct ib_port *p;
@@ -1056,7 +1057,7 @@ static int add_port(struct ib_core_device *coredev, int port_num)
goto err_put;
}
- if (device->ops.process_mad) {
+ if (device->ops.process_mad && alloc_stats) {
p->pma_table = get_counter_table(device, port_num);
ret = sysfs_create_group(&p->kobj, p->pma_table);
if (ret)
@@ -1123,7 +1124,7 @@ static int add_port(struct ib_core_device *coredev, int port_num)
* port, so holder should be device. Therefore skip per port conunter
* initialization.
*/
- if (device->ops.alloc_hw_stats && port_num)
+ if (device->ops.alloc_hw_stats && port_num && alloc_stats)
setup_hw_stats(device, p, port_num);
list_add_tail(&p->kobj.entry, &coredev->port_list);
@@ -1280,7 +1281,7 @@ const struct attribute_group ib_dev_attr_group = {
.attrs = ib_dev_attrs,
};
-static void ib_free_port_attrs(struct ib_core_device *coredev)
+void ib_free_port_attrs(struct ib_core_device *coredev)
{
struct kobject *p, *t;
@@ -1307,7 +1308,7 @@ static void ib_free_port_attrs(struct ib_core_device *coredev)
kobject_put(coredev->ports_kobj);
}
-static int ib_setup_port_attrs(struct ib_core_device *coredev)
+int ib_setup_port_attrs(struct ib_core_device *coredev, bool alloc_stats)
{
struct ib_device *device = rdma_device_to_ibdev(&coredev->dev);
int ret;
@@ -1319,12 +1320,12 @@ static int ib_setup_port_attrs(struct ib_core_device *coredev)
return -ENOMEM;
if (rdma_cap_ib_switch(device)) {
- ret = add_port(coredev, 0);
+ ret = add_port(coredev, 0, alloc_stats);
if (ret)
goto err_put;
} else {
for (i = 1; i <= device->phys_port_cnt; ++i) {
- ret = add_port(coredev, i);
+ ret = add_port(coredev, i, alloc_stats);
if (ret)
goto err_put;
}
@@ -1341,7 +1342,7 @@ int ib_device_register_sysfs(struct ib_device *device)
{
int ret;
- ret = ib_setup_port_attrs(&device->coredev);
+ ret = ib_setup_port_attrs(&device->coredev, true);
if (ret)
return ret;