101-mxs-add-mxs_power.patch 4.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166
  1. --- a/drivers/power/Kconfig
  2. +++ b/drivers/power/Kconfig
  3. @@ -43,6 +43,14 @@ config MAX8925_POWER
  4. Say Y here to enable support for the battery charger in the Maxim
  5. MAX8925 PMIC.
  6. +config MXS_POWER
  7. + tristate "Freescale MXS power subsystem support"
  8. + depends on ARCH_MXS || COMPILE_TEST
  9. + help
  10. + Say Y here to enable support for the Freescale i.MX23/i.MX28
  11. + power subsystem. This is a requirement to get access to on-chip
  12. + regulators, battery charger and many more.
  13. +
  14. config WM831X_BACKUP
  15. tristate "WM831X backup battery charger support"
  16. depends on MFD_WM831X
  17. --- a/drivers/power/Makefile
  18. +++ b/drivers/power/Makefile
  19. @@ -10,6 +10,7 @@ obj-$(CONFIG_GENERIC_ADC_BATTERY) += gen
  20. obj-$(CONFIG_PDA_POWER) += pda_power.o
  21. obj-$(CONFIG_APM_POWER) += apm_power.o
  22. obj-$(CONFIG_MAX8925_POWER) += max8925_power.o
  23. +obj-$(CONFIG_MXS_POWER) += mxs_power.o
  24. obj-$(CONFIG_WM831X_BACKUP) += wm831x_backup.o
  25. obj-$(CONFIG_WM831X_POWER) += wm831x_power.o
  26. obj-$(CONFIG_WM8350_POWER) += wm8350_power.o
  27. --- /dev/null
  28. +++ b/drivers/power/mxs_power.c
  29. @@ -0,0 +1,136 @@
  30. +/*
  31. + * Freescale MXS power subsystem
  32. + *
  33. + * Copyright (C) 2014 Stefan Wahren
  34. + *
  35. + * Inspired by imx-bootlets
  36. + */
  37. +
  38. +/*
  39. + * The code contained herein is licensed under the GNU General Public
  40. + * License. You may obtain a copy of the GNU General Public License
  41. + * Version 2 or later at the following locations:
  42. + *
  43. + * http://www.opensource.org/licenses/gpl-license.html
  44. + * http://www.gnu.org/copyleft/gpl.html
  45. + */
  46. +
  47. +#include <linux/device.h>
  48. +#include <linux/err.h>
  49. +#include <linux/io.h>
  50. +#include <linux/kernel.h>
  51. +#include <linux/module.h>
  52. +#include <linux/of.h>
  53. +#include <linux/of_platform.h>
  54. +#include <linux/platform_device.h>
  55. +#include <linux/power_supply.h>
  56. +#include <linux/stmp_device.h>
  57. +#include <linux/types.h>
  58. +
  59. +#define BM_POWER_CTRL_POLARITY_VBUSVALID BIT(5)
  60. +#define BM_POWER_CTRL_VBUSVALID_IRQ BIT(4)
  61. +#define BM_POWER_CTRL_ENIRQ_VBUS_VALID BIT(3)
  62. +
  63. +#define HW_POWER_5VCTRL_OFFSET 0x10
  64. +
  65. +#define BM_POWER_5VCTRL_VBUSVALID_THRESH (7 << 8)
  66. +#define BM_POWER_5VCTRL_PWDN_5VBRNOUT BIT(7)
  67. +#define BM_POWER_5VCTRL_ENABLE_LINREG_ILIMIT BIT(6)
  68. +#define BM_POWER_5VCTRL_VBUSVALID_5VDETECT BIT(4)
  69. +
  70. +#define HW_POWER_5VCTRL_VBUSVALID_THRESH_4_40V (5 << 8)
  71. +
  72. +struct mxs_power_data {
  73. + void __iomem *base_addr;
  74. + struct power_supply *ac;
  75. +};
  76. +
  77. +static enum power_supply_property mxs_power_ac_props[] = {
  78. + POWER_SUPPLY_PROP_ONLINE,
  79. +};
  80. +
  81. +static int mxs_power_ac_get_property(struct power_supply *psy,
  82. + enum power_supply_property psp,
  83. + union power_supply_propval *val)
  84. +{
  85. + int ret = 0;
  86. +
  87. + switch (psp) {
  88. + case POWER_SUPPLY_PROP_ONLINE:
  89. + val->intval = 1;
  90. + break;
  91. + default:
  92. + ret = -EINVAL;
  93. + break;
  94. + }
  95. + return ret;
  96. +}
  97. +
  98. +static const struct of_device_id of_mxs_power_match[] = {
  99. + { .compatible = "fsl,imx23-power" },
  100. + { .compatible = "fsl,imx28-power" },
  101. + { /* end */ }
  102. +};
  103. +MODULE_DEVICE_TABLE(of, of_mxs_power_match);
  104. +
  105. +static const struct power_supply_desc ac_desc = {
  106. + .properties = mxs_power_ac_props,
  107. + .num_properties = ARRAY_SIZE(mxs_power_ac_props),
  108. + .get_property = mxs_power_ac_get_property,
  109. + .name = "ac",
  110. + .type = POWER_SUPPLY_TYPE_MAINS,
  111. +};
  112. +
  113. +static int mxs_power_probe(struct platform_device *pdev)
  114. +{
  115. + struct device *dev = &pdev->dev;
  116. + struct device_node *np = dev->of_node;
  117. + struct resource *res;
  118. + struct mxs_power_data *data;
  119. + struct power_supply_config psy_cfg = {};
  120. + void __iomem *v5ctrl_addr;
  121. +
  122. + if (!np) {
  123. + dev_err(dev, "missing device tree\n");
  124. + return -EINVAL;
  125. + }
  126. +
  127. + data = devm_kzalloc(dev, sizeof(*data), GFP_KERNEL);
  128. + if (!data)
  129. + return -ENOMEM;
  130. +
  131. + res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
  132. + data->base_addr = devm_ioremap_resource(dev, res);
  133. + if (IS_ERR(data->base_addr))
  134. + return PTR_ERR(data->base_addr);
  135. +
  136. + psy_cfg.drv_data = data;
  137. +
  138. + data->ac = devm_power_supply_register(dev, &ac_desc, &psy_cfg);
  139. + if (IS_ERR(data->ac))
  140. + return PTR_ERR(data->ac);
  141. +
  142. + platform_set_drvdata(pdev, data);
  143. +
  144. + v5ctrl_addr = data->base_addr + HW_POWER_5VCTRL_OFFSET;
  145. +
  146. + /* Make sure the current limit of the linregs are disabled. */
  147. + writel(BM_POWER_5VCTRL_ENABLE_LINREG_ILIMIT,
  148. + v5ctrl_addr + STMP_OFFSET_REG_CLR);
  149. +
  150. + return of_platform_populate(np, NULL, NULL, dev);
  151. +}
  152. +
  153. +static struct platform_driver mxs_power_driver = {
  154. + .driver = {
  155. + .name = "mxs_power",
  156. + .of_match_table = of_mxs_power_match,
  157. + },
  158. + .probe = mxs_power_probe,
  159. +};
  160. +
  161. +module_platform_driver(mxs_power_driver);
  162. +
  163. +MODULE_AUTHOR("Stefan Wahren <stefan.wahren@i2se.com>");
  164. +MODULE_DESCRIPTION("Freescale MXS power subsystem");
  165. +MODULE_LICENSE("GPL v2");