diff options
author | Linus Walleij <linus.walleij@linaro.org> | 2012-02-20 15:42:10 -0500 |
---|---|---|
committer | Samuel Ortiz <sameo@linux.intel.com> | 2012-03-06 12:46:42 -0500 |
commit | 0f620837595145cd42be1c9dc6b619146fbeaf88 (patch) | |
tree | c8baef44fa4b407ef897ccd234b91f8d83ac85e3 /include | |
parent | 6d95b7fdd0bd2e28ef651da6863d75edca4c2aca (diff) |
mfd: Add ab8500 version detection and enforcing
There are currently four different versions of the AB8500
around: AB8500, AB8505, AB9540 and AB8540. Unfortunately:
- Some of the chips (AB8500, AB8505, AB9540) cannot read
the AB8500_REV_REG register but return errors
- Some of them have the same ID value in the hardware
register AB8500_REV_REV, for example the first versions
of AB8505 and AB9540 have 0xFF in this register -
just like the AB8500.
So we need to be able to enforce a certain version from
the platform. We do this by using the id of the platform
device that provides the read/write functions.
Reviewed-by: Mark Brown <broonie@opensource.wolfsonmicro.com>
Signed-off-by: Maxime Coquelin <maxime.coquelin@stericsson.com>
Signed-off-by: Alex Macro <alex.macro@stericsson.com>
Signed-off-by: Michel Jaouen <michel.jaouen@stericsson.com>
Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
Signed-off-by: Samuel Ortiz <sameo@linux.intel.com>
Diffstat (limited to 'include')
-rw-r--r-- | include/linux/mfd/abx500.h | 7 | ||||
-rw-r--r-- | include/linux/mfd/abx500/ab8500.h | 59 |
2 files changed, 58 insertions, 8 deletions
diff --git a/include/linux/mfd/abx500.h b/include/linux/mfd/abx500.h index 9970337ff041..1bfbb113a852 100644 --- a/include/linux/mfd/abx500.h +++ b/include/linux/mfd/abx500.h | |||
@@ -33,13 +33,6 @@ | |||
33 | #define AB5500_1_1 0x21 | 33 | #define AB5500_1_1 0x21 |
34 | #define AB5500_2_0 0x24 | 34 | #define AB5500_2_0 0x24 |
35 | 35 | ||
36 | /* AB8500 CIDs*/ | ||
37 | #define AB8500_CUT1P0 0x10 | ||
38 | #define AB8500_CUT1P1 0x11 | ||
39 | #define AB8500_CUT2P0 0x20 | ||
40 | #define AB8500_CUT3P0 0x30 | ||
41 | #define AB8500_CUT3P3 0x33 | ||
42 | |||
43 | /* | 36 | /* |
44 | * AB3100, EVENTA1, A2 and A3 event register flags | 37 | * AB3100, EVENTA1, A2 and A3 event register flags |
45 | * these are catenated into a single 32-bit flag in the code | 38 | * these are catenated into a single 32-bit flag in the code |
diff --git a/include/linux/mfd/abx500/ab8500.h b/include/linux/mfd/abx500/ab8500.h index 838c6b487cc5..79892585c087 100644 --- a/include/linux/mfd/abx500/ab8500.h +++ b/include/linux/mfd/abx500/ab8500.h | |||
@@ -8,6 +8,28 @@ | |||
8 | #define MFD_AB8500_H | 8 | #define MFD_AB8500_H |
9 | 9 | ||
10 | #include <linux/device.h> | 10 | #include <linux/device.h> |
11 | /* | ||
12 | * AB IC versions | ||
13 | * | ||
14 | * AB8500_VERSION_AB8500 should be 0xFF but will never be read as need a | ||
15 | * non-supported multi-byte I2C access via PRCMU. Set to 0x00 to ease the | ||
16 | * print of version string. | ||
17 | */ | ||
18 | enum ab8500_version { | ||
19 | AB8500_VERSION_AB8500 = 0x0, | ||
20 | AB8500_VERSION_AB8505 = 0x1, | ||
21 | AB8500_VERSION_AB9540 = 0x2, | ||
22 | AB8500_VERSION_AB8540 = 0x3, | ||
23 | AB8500_VERSION_UNDEFINED, | ||
24 | }; | ||
25 | |||
26 | /* AB8500 CIDs*/ | ||
27 | #define AB8500_CUTEARLY 0x00 | ||
28 | #define AB8500_CUT1P0 0x10 | ||
29 | #define AB8500_CUT1P1 0x11 | ||
30 | #define AB8500_CUT2P0 0x20 | ||
31 | #define AB8500_CUT3P0 0x30 | ||
32 | #define AB8500_CUT3P3 0x33 | ||
11 | 33 | ||
12 | /* | 34 | /* |
13 | * AB8500 bank addresses | 35 | * AB8500 bank addresses |
@@ -145,6 +167,7 @@ | |||
145 | * @lock: read/write operations lock | 167 | * @lock: read/write operations lock |
146 | * @irq_lock: genirq bus lock | 168 | * @irq_lock: genirq bus lock |
147 | * @irq: irq line | 169 | * @irq: irq line |
170 | * @version: chip version id (e.g. ab8500 or ab9540) | ||
148 | * @chip_id: chip revision id | 171 | * @chip_id: chip revision id |
149 | * @write: register write | 172 | * @write: register write |
150 | * @read: register read | 173 | * @read: register read |
@@ -160,6 +183,7 @@ struct ab8500 { | |||
160 | 183 | ||
161 | int irq_base; | 184 | int irq_base; |
162 | int irq; | 185 | int irq; |
186 | enum ab8500_version version; | ||
163 | u8 chip_id; | 187 | u8 chip_id; |
164 | 188 | ||
165 | int (*write) (struct ab8500 *a8500, u16 addr, u8 data); | 189 | int (*write) (struct ab8500 *a8500, u16 addr, u8 data); |
@@ -195,7 +219,40 @@ struct ab8500_platform_data { | |||
195 | struct ab8500_gpio_platform_data *gpio; | 219 | struct ab8500_gpio_platform_data *gpio; |
196 | }; | 220 | }; |
197 | 221 | ||
198 | extern int __devinit ab8500_init(struct ab8500 *ab8500); | 222 | extern int __devinit ab8500_init(struct ab8500 *ab8500, |
223 | enum ab8500_version version); | ||
199 | extern int __devexit ab8500_exit(struct ab8500 *ab8500); | 224 | extern int __devexit ab8500_exit(struct ab8500 *ab8500); |
200 | 225 | ||
226 | static inline int is_ab8500(struct ab8500 *ab) | ||
227 | { | ||
228 | return ab->version == AB8500_VERSION_AB8500; | ||
229 | } | ||
230 | |||
231 | static inline int is_ab8505(struct ab8500 *ab) | ||
232 | { | ||
233 | return ab->version == AB8500_VERSION_AB8505; | ||
234 | } | ||
235 | |||
236 | static inline int is_ab9540(struct ab8500 *ab) | ||
237 | { | ||
238 | return ab->version == AB8500_VERSION_AB9540; | ||
239 | } | ||
240 | |||
241 | static inline int is_ab8540(struct ab8500 *ab) | ||
242 | { | ||
243 | return ab->version == AB8500_VERSION_AB8540; | ||
244 | } | ||
245 | |||
246 | /* include also ab8505, ab9540... */ | ||
247 | static inline int is_ab8500_1p1_or_earlier(struct ab8500 *ab) | ||
248 | { | ||
249 | return (is_ab8500(ab) && (ab->chip_id <= AB8500_CUT1P1)); | ||
250 | } | ||
251 | |||
252 | /* include also ab8505, ab9540... */ | ||
253 | static inline int is_ab8500_2p0_or_earlier(struct ab8500 *ab) | ||
254 | { | ||
255 | return (is_ab8500(ab) && (ab->chip_id <= AB8500_CUT2P0)); | ||
256 | } | ||
257 | |||
201 | #endif /* MFD_AB8500_H */ | 258 | #endif /* MFD_AB8500_H */ |