hc
2023-12-11 d2ccde1c8e90d38cee87a1b0309ad2827f3fd30d
kernel/drivers/regulator/twl6030-regulator.c
....@@ -1,13 +1,9 @@
1
+// SPDX-License-Identifier: GPL-2.0-or-later
12 /*
23 * Split TWL6030 logic from twl-regulator.c:
34 * Copyright (C) 2008 David Brownell
45 *
56 * Copyright (C) 2016 Nicolae Rosia <nicolae.rosia@gmail.com>
6
- *
7
- * This program is free software; you can redistribute it and/or modify
8
- * it under the terms of the GNU General Public License as published by
9
- * the Free Software Foundation; either version 2 of the License, or
10
- * (at your option) any later version.
117 */
128
139 #include <linux/module.h>
....@@ -30,9 +26,6 @@
3026
3127 /* twl resource ID, for resource control state machine */
3228 u8 id;
33
-
34
- /* chip constraints on regulator behavior */
35
- u16 min_mV;
3629
3730 u8 flags;
3831
....@@ -64,6 +57,9 @@
6457 #define VREG_BC_PROC 3
6558 #define VREG_BC_CLK_RST 4
6659
60
+/* TWL6030 LDO register values for VREG_VOLTAGE */
61
+#define TWL6030_VREG_VOLTAGE_WR_S BIT(7)
62
+
6763 /* TWL6030 LDO register values for CFG_STATE */
6864 #define TWL6030_CFG_STATE_OFF 0x00
6965 #define TWL6030_CFG_STATE_ON 0x01
....@@ -71,13 +67,15 @@
7167 #define TWL6030_CFG_STATE_SLEEP 0x03
7268 #define TWL6030_CFG_STATE_GRP_SHIFT 5
7369 #define TWL6030_CFG_STATE_APP_SHIFT 2
70
+#define TWL6030_CFG_STATE_MASK 0x03
7471 #define TWL6030_CFG_STATE_APP_MASK (0x03 << TWL6030_CFG_STATE_APP_SHIFT)
7572 #define TWL6030_CFG_STATE_APP(v) (((v) & TWL6030_CFG_STATE_APP_MASK) >>\
7673 TWL6030_CFG_STATE_APP_SHIFT)
7774
78
-/* Flags for SMPS Voltage reading */
75
+/* Flags for SMPS Voltage reading and LDO reading*/
7976 #define SMPS_OFFSET_EN BIT(0)
8077 #define SMPS_EXTENDED_EN BIT(1)
78
+#define TWL_6030_WARM_RESET BIT(3)
8179
8280 /* twl6032 SMPS EPROM values */
8381 #define TWL6030_SMPS_OFFSET 0xB0
....@@ -131,12 +129,13 @@
131129 if (grp < 0)
132130 return grp;
133131 grp &= P1_GRP_6030;
132
+ val = twlreg_read(info, TWL_MODULE_PM_RECEIVER, VREG_STATE);
133
+ val = TWL6030_CFG_STATE_APP(val);
134134 } else {
135
+ val = twlreg_read(info, TWL_MODULE_PM_RECEIVER, VREG_STATE);
136
+ val &= TWL6030_CFG_STATE_MASK;
135137 grp = 1;
136138 }
137
-
138
- val = twlreg_read(info, TWL_MODULE_PM_RECEIVER, VREG_STATE);
139
- val = TWL6030_CFG_STATE_APP(val);
140139
141140 return grp && (val == TWL6030_CFG_STATE_ON);
142141 }
....@@ -190,7 +189,12 @@
190189
191190 val = twlreg_read(info, TWL_MODULE_PM_RECEIVER, VREG_STATE);
192191
193
- switch (TWL6030_CFG_STATE_APP(val)) {
192
+ if (info->features & TWL6032_SUBCLASS)
193
+ val &= TWL6030_CFG_STATE_MASK;
194
+ else
195
+ val = TWL6030_CFG_STATE_APP(val);
196
+
197
+ switch (val) {
194198 case TWL6030_CFG_STATE_ON:
195199 return REGULATOR_STATUS_NORMAL;
196200
....@@ -247,36 +251,18 @@
247251 return -ENODEV;
248252 }
249253
250
-static struct regulator_ops twl6030coresmps_ops = {
254
+static const struct regulator_ops twl6030coresmps_ops = {
251255 .set_voltage = twl6030coresmps_set_voltage,
252256 .get_voltage = twl6030coresmps_get_voltage,
253257 };
254
-
255
-static int twl6030ldo_list_voltage(struct regulator_dev *rdev, unsigned sel)
256
-{
257
- struct twlreg_info *info = rdev_get_drvdata(rdev);
258
-
259
- switch (sel) {
260
- case 0:
261
- return 0;
262
- case 1 ... 24:
263
- /* Linear mapping from 00000001 to 00011000:
264
- * Absolute voltage value = 1.0 V + 0.1 V × (sel – 00000001)
265
- */
266
- return (info->min_mV + 100 * (sel - 1)) * 1000;
267
- case 25 ... 30:
268
- return -EINVAL;
269
- case 31:
270
- return 2750000;
271
- default:
272
- return -EINVAL;
273
- }
274
-}
275258
276259 static int
277260 twl6030ldo_set_voltage_sel(struct regulator_dev *rdev, unsigned selector)
278261 {
279262 struct twlreg_info *info = rdev_get_drvdata(rdev);
263
+
264
+ if (info->flags & TWL_6030_WARM_RESET)
265
+ selector |= TWL6030_VREG_VOLTAGE_WR_S;
280266
281267 return twlreg_write(info, TWL_MODULE_PM_RECEIVER, VREG_VOLTAGE,
282268 selector);
....@@ -287,11 +273,14 @@
287273 struct twlreg_info *info = rdev_get_drvdata(rdev);
288274 int vsel = twlreg_read(info, TWL_MODULE_PM_RECEIVER, VREG_VOLTAGE);
289275
276
+ if (info->flags & TWL_6030_WARM_RESET)
277
+ vsel &= ~TWL6030_VREG_VOLTAGE_WR_S;
278
+
290279 return vsel;
291280 }
292281
293
-static struct regulator_ops twl6030ldo_ops = {
294
- .list_voltage = twl6030ldo_list_voltage,
282
+static const struct regulator_ops twl6030ldo_ops = {
283
+ .list_voltage = regulator_list_voltage_linear_range,
295284
296285 .set_voltage_sel = twl6030ldo_set_voltage_sel,
297286 .get_voltage_sel = twl6030ldo_get_voltage_sel,
....@@ -305,7 +294,7 @@
305294 .get_status = twl6030reg_get_status,
306295 };
307296
308
-static struct regulator_ops twl6030fixed_ops = {
297
+static const struct regulator_ops twl6030fixed_ops = {
309298 .list_voltage = regulator_list_voltage_linear,
310299
311300 .enable = twl6030reg_enable,
....@@ -330,7 +319,7 @@
330319 switch (info->flags) {
331320 case SMPS_OFFSET_EN:
332321 voltage = 100000;
333
- /* fall through */
322
+ fallthrough;
334323 case 0:
335324 switch (index) {
336325 case 0:
....@@ -496,7 +485,7 @@
496485 return twlreg_read(info, TWL_MODULE_PM_RECEIVER, VREG_VOLTAGE_SMPS);
497486 }
498487
499
-static struct regulator_ops twlsmps_ops = {
488
+static const struct regulator_ops twlsmps_ops = {
500489 .list_voltage = twl6030smps_list_voltage,
501490 .map_voltage = twl6030smps_map_voltage,
502491
....@@ -513,6 +502,11 @@
513502 };
514503
515504 /*----------------------------------------------------------------------*/
505
+static const struct linear_range twl6030ldo_linear_range[] = {
506
+ REGULATOR_LINEAR_RANGE(0, 0, 0, 0),
507
+ REGULATOR_LINEAR_RANGE(1000000, 1, 24, 100000),
508
+ REGULATOR_LINEAR_RANGE(2750000, 31, 31, 0),
509
+};
516510
517511 #define TWL6030_ADJUSTABLE_SMPS(label) \
518512 static const struct twlreg_info TWL6030_INFO_##label = { \
....@@ -525,28 +519,31 @@
525519 }, \
526520 }
527521
528
-#define TWL6030_ADJUSTABLE_LDO(label, offset, min_mVolts) \
522
+#define TWL6030_ADJUSTABLE_LDO(label, offset) \
529523 static const struct twlreg_info TWL6030_INFO_##label = { \
530524 .base = offset, \
531
- .min_mV = min_mVolts, \
532525 .desc = { \
533526 .name = #label, \
534527 .id = TWL6030_REG_##label, \
535528 .n_voltages = 32, \
529
+ .linear_ranges = twl6030ldo_linear_range, \
530
+ .n_linear_ranges = ARRAY_SIZE(twl6030ldo_linear_range), \
536531 .ops = &twl6030ldo_ops, \
537532 .type = REGULATOR_VOLTAGE, \
538533 .owner = THIS_MODULE, \
539534 }, \
540535 }
541536
542
-#define TWL6032_ADJUSTABLE_LDO(label, offset, min_mVolts) \
537
+#define TWL6032_ADJUSTABLE_LDO(label, offset) \
543538 static const struct twlreg_info TWL6032_INFO_##label = { \
544539 .base = offset, \
545
- .min_mV = min_mVolts, \
540
+ .features = TWL6032_SUBCLASS, \
546541 .desc = { \
547542 .name = #label, \
548543 .id = TWL6032_REG_##label, \
549544 .n_voltages = 32, \
545
+ .linear_ranges = twl6030ldo_linear_range, \
546
+ .n_linear_ranges = ARRAY_SIZE(twl6030ldo_linear_range), \
550547 .ops = &twl6030ldo_ops, \
551548 .type = REGULATOR_VOLTAGE, \
552549 .owner = THIS_MODULE, \
....@@ -557,7 +554,6 @@
557554 static const struct twlreg_info TWLFIXED_INFO_##label = { \
558555 .base = offset, \
559556 .id = 0, \
560
- .min_mV = mVolts, \
561557 .desc = { \
562558 .name = #label, \
563559 .id = TWL6030##_REG_##label, \
....@@ -574,7 +570,7 @@
574570 #define TWL6032_ADJUSTABLE_SMPS(label, offset) \
575571 static const struct twlreg_info TWLSMPS_INFO_##label = { \
576572 .base = offset, \
577
- .min_mV = 600, \
573
+ .features = TWL6032_SUBCLASS, \
578574 .desc = { \
579575 .name = #label, \
580576 .id = TWL6032_REG_##label, \
....@@ -592,22 +588,22 @@
592588 TWL6030_ADJUSTABLE_SMPS(VDD1);
593589 TWL6030_ADJUSTABLE_SMPS(VDD2);
594590 TWL6030_ADJUSTABLE_SMPS(VDD3);
595
-TWL6030_ADJUSTABLE_LDO(VAUX1_6030, 0x54, 1000);
596
-TWL6030_ADJUSTABLE_LDO(VAUX2_6030, 0x58, 1000);
597
-TWL6030_ADJUSTABLE_LDO(VAUX3_6030, 0x5c, 1000);
598
-TWL6030_ADJUSTABLE_LDO(VMMC, 0x68, 1000);
599
-TWL6030_ADJUSTABLE_LDO(VPP, 0x6c, 1000);
600
-TWL6030_ADJUSTABLE_LDO(VUSIM, 0x74, 1000);
591
+TWL6030_ADJUSTABLE_LDO(VAUX1_6030, 0x54);
592
+TWL6030_ADJUSTABLE_LDO(VAUX2_6030, 0x58);
593
+TWL6030_ADJUSTABLE_LDO(VAUX3_6030, 0x5c);
594
+TWL6030_ADJUSTABLE_LDO(VMMC, 0x68);
595
+TWL6030_ADJUSTABLE_LDO(VPP, 0x6c);
596
+TWL6030_ADJUSTABLE_LDO(VUSIM, 0x74);
601597 /* 6025 are renamed compared to 6030 versions */
602
-TWL6032_ADJUSTABLE_LDO(LDO2, 0x54, 1000);
603
-TWL6032_ADJUSTABLE_LDO(LDO4, 0x58, 1000);
604
-TWL6032_ADJUSTABLE_LDO(LDO3, 0x5c, 1000);
605
-TWL6032_ADJUSTABLE_LDO(LDO5, 0x68, 1000);
606
-TWL6032_ADJUSTABLE_LDO(LDO1, 0x6c, 1000);
607
-TWL6032_ADJUSTABLE_LDO(LDO7, 0x74, 1000);
608
-TWL6032_ADJUSTABLE_LDO(LDO6, 0x60, 1000);
609
-TWL6032_ADJUSTABLE_LDO(LDOLN, 0x64, 1000);
610
-TWL6032_ADJUSTABLE_LDO(LDOUSB, 0x70, 1000);
598
+TWL6032_ADJUSTABLE_LDO(LDO2, 0x54);
599
+TWL6032_ADJUSTABLE_LDO(LDO4, 0x58);
600
+TWL6032_ADJUSTABLE_LDO(LDO3, 0x5c);
601
+TWL6032_ADJUSTABLE_LDO(LDO5, 0x68);
602
+TWL6032_ADJUSTABLE_LDO(LDO1, 0x6c);
603
+TWL6032_ADJUSTABLE_LDO(LDO7, 0x74);
604
+TWL6032_ADJUSTABLE_LDO(LDO6, 0x60);
605
+TWL6032_ADJUSTABLE_LDO(LDOLN, 0x64);
606
+TWL6032_ADJUSTABLE_LDO(LDOUSB, 0x70);
611607 TWL6030_FIXED_LDO(VANA, 0x50, 2100, 0);
612608 TWL6030_FIXED_LDO(VCXIO, 0x60, 1800, 0);
613609 TWL6030_FIXED_LDO(VDAC, 0x64, 1800, 0);
....@@ -687,20 +683,15 @@
687683 struct regulator_init_data *initdata;
688684 struct regulation_constraints *c;
689685 struct regulator_dev *rdev;
690
- const struct of_device_id *match;
691686 struct regulator_config config = { };
687
+ struct device_node *np = pdev->dev.of_node;
692688
693
- match = of_match_device(twl_of_match, &pdev->dev);
694
- if (!match)
695
- return -ENODEV;
696
-
697
- template = match->data;
689
+ template = of_device_get_match_data(&pdev->dev);
698690 if (!template)
699691 return -ENODEV;
700692
701693 id = template->desc.id;
702
- initdata = of_get_regulator_init_data(&pdev->dev, pdev->dev.of_node,
703
- &template->desc);
694
+ initdata = of_get_regulator_init_data(&pdev->dev, np, &template->desc);
704695 if (!initdata)
705696 return -EINVAL;
706697
....@@ -738,10 +729,13 @@
738729 break;
739730 }
740731
732
+ if (of_get_property(np, "ti,retain-on-reset", NULL))
733
+ info->flags |= TWL_6030_WARM_RESET;
734
+
741735 config.dev = &pdev->dev;
742736 config.init_data = initdata;
743737 config.driver_data = info;
744
- config.of_node = pdev->dev.of_node;
738
+ config.of_node = np;
745739
746740 rdev = devm_regulator_register(&pdev->dev, &info->desc, &config);
747741 if (IS_ERR(rdev)) {