Merge branches 'x86-fixes-for-linus', 'sched-fixes-for-linus', 'timers-fixes-for...
[pandora-kernel.git] / drivers / mfd / pcf50633-core.c
1 /* NXP PCF50633 Power Management Unit (PMU) driver
2  *
3  * (C) 2006-2008 by Openmoko, Inc.
4  * Author: Harald Welte <laforge@openmoko.org>
5  *         Balaji Rao <balajirrao@openmoko.org>
6  * All rights reserved.
7  *
8  *  This program is free software; you can redistribute  it and/or modify it
9  *  under  the terms of  the GNU General  Public License as published by the
10  *  Free Software Foundation;  either version 2 of the  License, or (at your
11  *  option) any later version.
12  *
13  */
14
15 #include <linux/kernel.h>
16 #include <linux/device.h>
17 #include <linux/sysfs.h>
18 #include <linux/module.h>
19 #include <linux/types.h>
20 #include <linux/interrupt.h>
21 #include <linux/workqueue.h>
22 #include <linux/platform_device.h>
23 #include <linux/i2c.h>
24 #include <linux/pm.h>
25 #include <linux/slab.h>
26
27 #include <linux/mfd/pcf50633/core.h>
28
29 static int __pcf50633_read(struct pcf50633 *pcf, u8 reg, int num, u8 *data)
30 {
31         int ret;
32
33         ret = i2c_smbus_read_i2c_block_data(pcf->i2c_client, reg,
34                                 num, data);
35         if (ret < 0)
36                 dev_err(pcf->dev, "Error reading %d regs at %d\n", num, reg);
37
38         return ret;
39 }
40
41 static int __pcf50633_write(struct pcf50633 *pcf, u8 reg, int num, u8 *data)
42 {
43         int ret;
44
45         ret = i2c_smbus_write_i2c_block_data(pcf->i2c_client, reg,
46                                 num, data);
47         if (ret < 0)
48                 dev_err(pcf->dev, "Error writing %d regs at %d\n", num, reg);
49
50         return ret;
51
52 }
53
54 /* Read a block of up to 32 regs  */
55 int pcf50633_read_block(struct pcf50633 *pcf, u8 reg,
56                                         int nr_regs, u8 *data)
57 {
58         int ret;
59
60         mutex_lock(&pcf->lock);
61         ret = __pcf50633_read(pcf, reg, nr_regs, data);
62         mutex_unlock(&pcf->lock);
63
64         return ret;
65 }
66 EXPORT_SYMBOL_GPL(pcf50633_read_block);
67
68 /* Write a block of up to 32 regs  */
69 int pcf50633_write_block(struct pcf50633 *pcf , u8 reg,
70                                         int nr_regs, u8 *data)
71 {
72         int ret;
73
74         mutex_lock(&pcf->lock);
75         ret = __pcf50633_write(pcf, reg, nr_regs, data);
76         mutex_unlock(&pcf->lock);
77
78         return ret;
79 }
80 EXPORT_SYMBOL_GPL(pcf50633_write_block);
81
82 u8 pcf50633_reg_read(struct pcf50633 *pcf, u8 reg)
83 {
84         u8 val;
85
86         mutex_lock(&pcf->lock);
87         __pcf50633_read(pcf, reg, 1, &val);
88         mutex_unlock(&pcf->lock);
89
90         return val;
91 }
92 EXPORT_SYMBOL_GPL(pcf50633_reg_read);
93
94 int pcf50633_reg_write(struct pcf50633 *pcf, u8 reg, u8 val)
95 {
96         int ret;
97
98         mutex_lock(&pcf->lock);
99         ret = __pcf50633_write(pcf, reg, 1, &val);
100         mutex_unlock(&pcf->lock);
101
102         return ret;
103 }
104 EXPORT_SYMBOL_GPL(pcf50633_reg_write);
105
106 int pcf50633_reg_set_bit_mask(struct pcf50633 *pcf, u8 reg, u8 mask, u8 val)
107 {
108         int ret;
109         u8 tmp;
110
111         val &= mask;
112
113         mutex_lock(&pcf->lock);
114         ret = __pcf50633_read(pcf, reg, 1, &tmp);
115         if (ret < 0)
116                 goto out;
117
118         tmp &= ~mask;
119         tmp |= val;
120         ret = __pcf50633_write(pcf, reg, 1, &tmp);
121
122 out:
123         mutex_unlock(&pcf->lock);
124
125         return ret;
126 }
127 EXPORT_SYMBOL_GPL(pcf50633_reg_set_bit_mask);
128
129 int pcf50633_reg_clear_bits(struct pcf50633 *pcf, u8 reg, u8 val)
130 {
131         int ret;
132         u8 tmp;
133
134         mutex_lock(&pcf->lock);
135         ret = __pcf50633_read(pcf, reg, 1, &tmp);
136         if (ret < 0)
137                 goto out;
138
139         tmp &= ~val;
140         ret = __pcf50633_write(pcf, reg, 1, &tmp);
141
142 out:
143         mutex_unlock(&pcf->lock);
144
145         return ret;
146 }
147 EXPORT_SYMBOL_GPL(pcf50633_reg_clear_bits);
148
149 /* sysfs attributes */
150 static ssize_t show_dump_regs(struct device *dev, struct device_attribute *attr,
151                             char *buf)
152 {
153         struct pcf50633 *pcf = dev_get_drvdata(dev);
154         u8 dump[16];
155         int n, n1, idx = 0;
156         char *buf1 = buf;
157         static u8 address_no_read[] = { /* must be ascending */
158                 PCF50633_REG_INT1,
159                 PCF50633_REG_INT2,
160                 PCF50633_REG_INT3,
161                 PCF50633_REG_INT4,
162                 PCF50633_REG_INT5,
163                 0 /* terminator */
164         };
165
166         for (n = 0; n < 256; n += sizeof(dump)) {
167                 for (n1 = 0; n1 < sizeof(dump); n1++)
168                         if (n == address_no_read[idx]) {
169                                 idx++;
170                                 dump[n1] = 0x00;
171                         } else
172                                 dump[n1] = pcf50633_reg_read(pcf, n + n1);
173
174                 hex_dump_to_buffer(dump, sizeof(dump), 16, 1, buf1, 128, 0);
175                 buf1 += strlen(buf1);
176                 *buf1++ = '\n';
177                 *buf1 = '\0';
178         }
179
180         return buf1 - buf;
181 }
182 static DEVICE_ATTR(dump_regs, 0400, show_dump_regs, NULL);
183
184 static ssize_t show_resume_reason(struct device *dev,
185                                 struct device_attribute *attr, char *buf)
186 {
187         struct pcf50633 *pcf = dev_get_drvdata(dev);
188         int n;
189
190         n = sprintf(buf, "%02x%02x%02x%02x%02x\n",
191                                 pcf->resume_reason[0],
192                                 pcf->resume_reason[1],
193                                 pcf->resume_reason[2],
194                                 pcf->resume_reason[3],
195                                 pcf->resume_reason[4]);
196
197         return n;
198 }
199 static DEVICE_ATTR(resume_reason, 0400, show_resume_reason, NULL);
200
201 static struct attribute *pcf_sysfs_entries[] = {
202         &dev_attr_dump_regs.attr,
203         &dev_attr_resume_reason.attr,
204         NULL,
205 };
206
207 static struct attribute_group pcf_attr_group = {
208         .name   = NULL,                 /* put in device directory */
209         .attrs  = pcf_sysfs_entries,
210 };
211
212 static void
213 pcf50633_client_dev_register(struct pcf50633 *pcf, const char *name,
214                                                 struct platform_device **pdev)
215 {
216         int ret;
217
218         *pdev = platform_device_alloc(name, -1);
219         if (!*pdev) {
220                 dev_err(pcf->dev, "Falied to allocate %s\n", name);
221                 return;
222         }
223
224         (*pdev)->dev.parent = pcf->dev;
225
226         ret = platform_device_add(*pdev);
227         if (ret) {
228                 dev_err(pcf->dev, "Failed to register %s: %d\n", name, ret);
229                 platform_device_put(*pdev);
230                 *pdev = NULL;
231         }
232 }
233
234 #ifdef CONFIG_PM_SLEEP
235 static int pcf50633_suspend(struct device *dev)
236 {
237         struct i2c_client *client = to_i2c_client(dev);
238         struct pcf50633 *pcf = i2c_get_clientdata(client);
239
240         return pcf50633_irq_suspend(pcf);
241 }
242
243 static int pcf50633_resume(struct device *dev)
244 {
245         struct i2c_client *client = to_i2c_client(dev);
246         struct pcf50633 *pcf = i2c_get_clientdata(client);
247
248         return pcf50633_irq_resume(pcf);
249 }
250 #endif
251
252 static SIMPLE_DEV_PM_OPS(pcf50633_pm, pcf50633_suspend, pcf50633_resume);
253
254 static int __devinit pcf50633_probe(struct i2c_client *client,
255                                 const struct i2c_device_id *ids)
256 {
257         struct pcf50633 *pcf;
258         struct pcf50633_platform_data *pdata = client->dev.platform_data;
259         int i, ret;
260         int version, variant;
261
262         if (!client->irq) {
263                 dev_err(&client->dev, "Missing IRQ\n");
264                 return -ENOENT;
265         }
266
267         pcf = kzalloc(sizeof(*pcf), GFP_KERNEL);
268         if (!pcf)
269                 return -ENOMEM;
270
271         pcf->pdata = pdata;
272
273         mutex_init(&pcf->lock);
274
275         i2c_set_clientdata(client, pcf);
276         pcf->dev = &client->dev;
277         pcf->i2c_client = client;
278
279         version = pcf50633_reg_read(pcf, 0);
280         variant = pcf50633_reg_read(pcf, 1);
281         if (version < 0 || variant < 0) {
282                 dev_err(pcf->dev, "Unable to probe pcf50633\n");
283                 ret = -ENODEV;
284                 goto err_free;
285         }
286
287         dev_info(pcf->dev, "Probed device version %d variant %d\n",
288                                                         version, variant);
289
290         pcf50633_irq_init(pcf, client->irq);
291
292         /* Create sub devices */
293         pcf50633_client_dev_register(pcf, "pcf50633-input",
294                                                 &pcf->input_pdev);
295         pcf50633_client_dev_register(pcf, "pcf50633-rtc",
296                                                 &pcf->rtc_pdev);
297         pcf50633_client_dev_register(pcf, "pcf50633-mbc",
298                                                 &pcf->mbc_pdev);
299         pcf50633_client_dev_register(pcf, "pcf50633-adc",
300                                                 &pcf->adc_pdev);
301         pcf50633_client_dev_register(pcf, "pcf50633-backlight",
302                                                 &pcf->bl_pdev);
303
304
305         for (i = 0; i < PCF50633_NUM_REGULATORS; i++) {
306                 struct platform_device *pdev;
307
308                 pdev = platform_device_alloc("pcf50633-regltr", i);
309                 if (!pdev) {
310                         dev_err(pcf->dev, "Cannot create regulator %d\n", i);
311                         continue;
312                 }
313
314                 pdev->dev.parent = pcf->dev;
315                 platform_device_add_data(pdev, &pdata->reg_init_data[i],
316                                         sizeof(pdata->reg_init_data[i]));
317                 pcf->regulator_pdev[i] = pdev;
318
319                 platform_device_add(pdev);
320         }
321
322         ret = sysfs_create_group(&client->dev.kobj, &pcf_attr_group);
323         if (ret)
324                 dev_err(pcf->dev, "error creating sysfs entries\n");
325
326         if (pdata->probe_done)
327                 pdata->probe_done(pcf);
328
329         return 0;
330
331 err_free:
332         kfree(pcf);
333
334         return ret;
335 }
336
337 static int __devexit pcf50633_remove(struct i2c_client *client)
338 {
339         struct pcf50633 *pcf = i2c_get_clientdata(client);
340         int i;
341
342         sysfs_remove_group(&client->dev.kobj, &pcf_attr_group);
343         pcf50633_irq_free(pcf);
344
345         platform_device_unregister(pcf->input_pdev);
346         platform_device_unregister(pcf->rtc_pdev);
347         platform_device_unregister(pcf->mbc_pdev);
348         platform_device_unregister(pcf->adc_pdev);
349         platform_device_unregister(pcf->bl_pdev);
350
351         for (i = 0; i < PCF50633_NUM_REGULATORS; i++)
352                 platform_device_unregister(pcf->regulator_pdev[i]);
353
354         kfree(pcf);
355
356         return 0;
357 }
358
359 static const struct i2c_device_id pcf50633_id_table[] = {
360         {"pcf50633", 0x73},
361         {/* end of list */}
362 };
363 MODULE_DEVICE_TABLE(i2c, pcf50633_id_table);
364
365 static struct i2c_driver pcf50633_driver = {
366         .driver = {
367                 .name   = "pcf50633",
368                 .pm     = &pcf50633_pm,
369         },
370         .id_table = pcf50633_id_table,
371         .probe = pcf50633_probe,
372         .remove = __devexit_p(pcf50633_remove),
373 };
374
375 static int __init pcf50633_init(void)
376 {
377         return i2c_add_driver(&pcf50633_driver);
378 }
379
380 static void __exit pcf50633_exit(void)
381 {
382         i2c_del_driver(&pcf50633_driver);
383 }
384
385 MODULE_DESCRIPTION("I2C chip driver for NXP PCF50633 PMU");
386 MODULE_AUTHOR("Harald Welte <laforge@openmoko.org>");
387 MODULE_LICENSE("GPL");
388
389 subsys_initcall(pcf50633_init);
390 module_exit(pcf50633_exit);