Skip to content

Commit f104e1e

Browse files
storulfrafaeljw
authored andcommitted
PM / Domains: Re-order initialization of generic_pm_domain_data
Move the initialization of the struct generic_pm_domain_data into genpd_alloc_dev_data(), including the assignment of the device's ->pm_domain() callback. Make corresponding changes to genpd_free_dev_data(). These changes will make the related code more readable. It will also decrease the critical regions for where genpd's mutex is being held and for where the device's power related spinlock is being held. Signed-off-by: Ulf Hansson <ulf.hansson@linaro.org> Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
1 parent 3e23568 commit f104e1e

File tree

1 file changed

+35
-32
lines changed

1 file changed

+35
-32
lines changed

drivers/base/power/domain.c

Lines changed: 35 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -1377,7 +1377,9 @@ EXPORT_SYMBOL_GPL(pm_genpd_syscore_poweron);
13771377

13781378
#endif /* CONFIG_PM_SLEEP */
13791379

1380-
static struct generic_pm_domain_data *genpd_alloc_dev_data(struct device *dev)
1380+
static struct generic_pm_domain_data *genpd_alloc_dev_data(struct device *dev,
1381+
struct generic_pm_domain *genpd,
1382+
struct gpd_timing_data *td)
13811383
{
13821384
struct generic_pm_domain_data *gpd_data;
13831385
int ret;
@@ -1392,8 +1394,32 @@ static struct generic_pm_domain_data *genpd_alloc_dev_data(struct device *dev)
13921394
goto err_put;
13931395
}
13941396

1397+
if (td)
1398+
gpd_data->td = *td;
1399+
1400+
gpd_data->base.dev = dev;
1401+
gpd_data->need_restore = -1;
1402+
gpd_data->td.constraint_changed = true;
1403+
gpd_data->td.effective_constraint_ns = -1;
1404+
gpd_data->nb.notifier_call = genpd_dev_pm_qos_notifier;
1405+
1406+
spin_lock_irq(&dev->power.lock);
1407+
1408+
if (dev->power.subsys_data->domain_data) {
1409+
ret = -EINVAL;
1410+
goto err_free;
1411+
}
1412+
1413+
dev->power.subsys_data->domain_data = &gpd_data->base;
1414+
dev->pm_domain = &genpd->domain;
1415+
1416+
spin_unlock_irq(&dev->power.lock);
1417+
13951418
return gpd_data;
13961419

1420+
err_free:
1421+
spin_unlock_irq(&dev->power.lock);
1422+
kfree(gpd_data);
13971423
err_put:
13981424
dev_pm_put_subsys_data(dev);
13991425
return ERR_PTR(ret);
@@ -1402,6 +1428,13 @@ static struct generic_pm_domain_data *genpd_alloc_dev_data(struct device *dev)
14021428
static void genpd_free_dev_data(struct device *dev,
14031429
struct generic_pm_domain_data *gpd_data)
14041430
{
1431+
spin_lock_irq(&dev->power.lock);
1432+
1433+
dev->pm_domain = NULL;
1434+
dev->power.subsys_data->domain_data = NULL;
1435+
1436+
spin_unlock_irq(&dev->power.lock);
1437+
14051438
kfree(gpd_data);
14061439
dev_pm_put_subsys_data(dev);
14071440
}
@@ -1423,7 +1456,7 @@ int __pm_genpd_add_device(struct generic_pm_domain *genpd, struct device *dev,
14231456
if (IS_ERR_OR_NULL(genpd) || IS_ERR_OR_NULL(dev))
14241457
return -EINVAL;
14251458

1426-
gpd_data = genpd_alloc_dev_data(dev);
1459+
gpd_data = genpd_alloc_dev_data(dev, genpd, td);
14271460
if (IS_ERR(gpd_data))
14281461
return PTR_ERR(gpd_data);
14291462

@@ -1434,35 +1467,13 @@ int __pm_genpd_add_device(struct generic_pm_domain *genpd, struct device *dev,
14341467
goto out;
14351468
}
14361469

1437-
spin_lock_irq(&dev->power.lock);
1438-
1439-
if (dev->power.subsys_data->domain_data) {
1440-
spin_unlock_irq(&dev->power.lock);
1441-
ret = -EINVAL;
1442-
goto out;
1443-
}
1444-
1445-
dev->power.subsys_data->domain_data = &gpd_data->base;
1446-
1447-
if (td)
1448-
gpd_data->td = *td;
1449-
1450-
dev->pm_domain = &genpd->domain;
1451-
1452-
spin_unlock_irq(&dev->power.lock);
1453-
14541470
if (genpd->attach_dev)
14551471
genpd->attach_dev(genpd, dev);
14561472

14571473
genpd->device_count++;
14581474
genpd->max_off_time_changed = true;
14591475

1460-
gpd_data->base.dev = dev;
14611476
list_add_tail(&gpd_data->base.list_node, &genpd->dev_list);
1462-
gpd_data->need_restore = -1;
1463-
gpd_data->td.constraint_changed = true;
1464-
gpd_data->td.effective_constraint_ns = -1;
1465-
gpd_data->nb.notifier_call = genpd_dev_pm_qos_notifier;
14661477

14671478
out:
14681479
genpd_release_lock(genpd);
@@ -1524,15 +1535,7 @@ int pm_genpd_remove_device(struct generic_pm_domain *genpd,
15241535
if (genpd->detach_dev)
15251536
genpd->detach_dev(genpd, dev);
15261537

1527-
spin_lock_irq(&dev->power.lock);
1528-
1529-
dev->pm_domain = NULL;
15301538
list_del_init(&pdd->list_node);
1531-
dev->power.subsys_data->domain_data = NULL;
1532-
1533-
spin_unlock_irq(&dev->power.lock);
1534-
1535-
pdd->dev = NULL;
15361539

15371540
genpd_release_lock(genpd);
15381541

0 commit comments

Comments
 (0)