2 * Copyright (C) 2014 Linaro Ltd
4 * Author: Ulf Hansson <ulf.hansson@linaro.org>
6 * License terms: GNU General Public License (GPL) version 2
8 * MMC power sequence management
10 #include <linux/kernel.h>
11 #include <linux/err.h>
12 #include <linux/module.h>
15 #include <linux/mmc/host.h>
19 static DEFINE_MUTEX(pwrseq_list_mutex
);
20 static LIST_HEAD(pwrseq_list
);
22 int mmc_pwrseq_alloc(struct mmc_host
*host
)
24 struct device_node
*np
;
27 np
= of_parse_phandle(host
->parent
->of_node
, "mmc-pwrseq", 0);
31 mutex_lock(&pwrseq_list_mutex
);
32 list_for_each_entry(p
, &pwrseq_list
, pwrseq_node
) {
33 if (p
->dev
->of_node
== np
) {
34 if (!try_module_get(p
->owner
))
36 "increasing module refcount failed\n");
45 mutex_unlock(&pwrseq_list_mutex
);
50 dev_info(host
->parent
, "allocated mmc-pwrseq\n");
55 void mmc_pwrseq_pre_power_on(struct mmc_host
*host
)
57 struct mmc_pwrseq
*pwrseq
= host
->pwrseq
;
59 if (pwrseq
&& pwrseq
->ops
->pre_power_on
)
60 pwrseq
->ops
->pre_power_on(host
);
63 void mmc_pwrseq_post_power_on(struct mmc_host
*host
)
65 struct mmc_pwrseq
*pwrseq
= host
->pwrseq
;
67 if (pwrseq
&& pwrseq
->ops
->post_power_on
)
68 pwrseq
->ops
->post_power_on(host
);
71 void mmc_pwrseq_power_off(struct mmc_host
*host
)
73 struct mmc_pwrseq
*pwrseq
= host
->pwrseq
;
75 if (pwrseq
&& pwrseq
->ops
->power_off
)
76 pwrseq
->ops
->power_off(host
);
79 void mmc_pwrseq_free(struct mmc_host
*host
)
81 struct mmc_pwrseq
*pwrseq
= host
->pwrseq
;
84 module_put(pwrseq
->owner
);
89 int mmc_pwrseq_register(struct mmc_pwrseq
*pwrseq
)
91 if (!pwrseq
|| !pwrseq
->ops
|| !pwrseq
->dev
)
94 mutex_lock(&pwrseq_list_mutex
);
95 list_add(&pwrseq
->pwrseq_node
, &pwrseq_list
);
96 mutex_unlock(&pwrseq_list_mutex
);
100 EXPORT_SYMBOL_GPL(mmc_pwrseq_register
);
102 void mmc_pwrseq_unregister(struct mmc_pwrseq
*pwrseq
)
105 mutex_lock(&pwrseq_list_mutex
);
106 list_del(&pwrseq
->pwrseq_node
);
107 mutex_unlock(&pwrseq_list_mutex
);
110 EXPORT_SYMBOL_GPL(mmc_pwrseq_unregister
);