Linux Kernel  3.7.1
 All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros Groups Pages
max8997.c
Go to the documentation of this file.
1 /*
2  * max8997.c - mfd core driver for the Maxim 8966 and 8997
3  *
4  * Copyright (C) 2011 Samsung Electronics
5  * MyungJoo Ham <[email protected]>
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.
11  *
12  * This program is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15  * GNU General Public License for more details.
16  *
17  * You should have received a copy of the GNU General Public License
18  * along with this program; if not, write to the Free Software
19  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
20  *
21  * This driver is based on max8998.c
22  */
23 
24 #include <linux/slab.h>
25 #include <linux/i2c.h>
26 #include <linux/interrupt.h>
27 #include <linux/pm_runtime.h>
28 #include <linux/module.h>
29 #include <linux/mutex.h>
30 #include <linux/mfd/core.h>
31 #include <linux/mfd/max8997.h>
33 
34 #define I2C_ADDR_PMIC (0xCC >> 1)
35 #define I2C_ADDR_MUIC (0x4A >> 1)
36 #define I2C_ADDR_BATTERY (0x6C >> 1)
37 #define I2C_ADDR_RTC (0x0C >> 1)
38 #define I2C_ADDR_HAPTIC (0x90 >> 1)
39 
40 static struct mfd_cell max8997_devs[] = {
41  { .name = "max8997-pmic", },
42  { .name = "max8997-rtc", },
43  { .name = "max8997-battery", },
44  { .name = "max8997-haptic", },
45  { .name = "max8997-muic", },
46  { .name = "max8997-led", .id = 1 },
47  { .name = "max8997-led", .id = 2 },
48 };
49 
50 int max8997_read_reg(struct i2c_client *i2c, u8 reg, u8 *dest)
51 {
52  struct max8997_dev *max8997 = i2c_get_clientdata(i2c);
53  int ret;
54 
55  mutex_lock(&max8997->iolock);
56  ret = i2c_smbus_read_byte_data(i2c, reg);
57  mutex_unlock(&max8997->iolock);
58  if (ret < 0)
59  return ret;
60 
61  ret &= 0xff;
62  *dest = ret;
63  return 0;
64 }
66 
68 {
69  struct max8997_dev *max8997 = i2c_get_clientdata(i2c);
70  int ret;
71 
72  mutex_lock(&max8997->iolock);
73  ret = i2c_smbus_read_i2c_block_data(i2c, reg, count, buf);
74  mutex_unlock(&max8997->iolock);
75  if (ret < 0)
76  return ret;
77 
78  return 0;
79 }
81 
83 {
84  struct max8997_dev *max8997 = i2c_get_clientdata(i2c);
85  int ret;
86 
87  mutex_lock(&max8997->iolock);
88  ret = i2c_smbus_write_byte_data(i2c, reg, value);
89  mutex_unlock(&max8997->iolock);
90  return ret;
91 }
93 
95 {
96  struct max8997_dev *max8997 = i2c_get_clientdata(i2c);
97  int ret;
98 
99  mutex_lock(&max8997->iolock);
100  ret = i2c_smbus_write_i2c_block_data(i2c, reg, count, buf);
101  mutex_unlock(&max8997->iolock);
102  if (ret < 0)
103  return ret;
104 
105  return 0;
106 }
108 
110 {
111  struct max8997_dev *max8997 = i2c_get_clientdata(i2c);
112  int ret;
113 
114  mutex_lock(&max8997->iolock);
115  ret = i2c_smbus_read_byte_data(i2c, reg);
116  if (ret >= 0) {
117  u8 old_val = ret & 0xff;
118  u8 new_val = (val & mask) | (old_val & (~mask));
119  ret = i2c_smbus_write_byte_data(i2c, reg, new_val);
120  }
121  mutex_unlock(&max8997->iolock);
122  return ret;
123 }
125 
126 static int max8997_i2c_probe(struct i2c_client *i2c,
127  const struct i2c_device_id *id)
128 {
129  struct max8997_dev *max8997;
130  struct max8997_platform_data *pdata = i2c->dev.platform_data;
131  int ret = 0;
132 
133  max8997 = kzalloc(sizeof(struct max8997_dev), GFP_KERNEL);
134  if (max8997 == NULL)
135  return -ENOMEM;
136 
137  i2c_set_clientdata(i2c, max8997);
138  max8997->dev = &i2c->dev;
139  max8997->i2c = i2c;
140  max8997->type = id->driver_data;
141  max8997->irq = i2c->irq;
142 
143  if (!pdata)
144  goto err;
145 
146  max8997->ono = pdata->ono;
147 
148  mutex_init(&max8997->iolock);
149 
150  max8997->rtc = i2c_new_dummy(i2c->adapter, I2C_ADDR_RTC);
151  i2c_set_clientdata(max8997->rtc, max8997);
152  max8997->haptic = i2c_new_dummy(i2c->adapter, I2C_ADDR_HAPTIC);
153  i2c_set_clientdata(max8997->haptic, max8997);
154  max8997->muic = i2c_new_dummy(i2c->adapter, I2C_ADDR_MUIC);
155  i2c_set_clientdata(max8997->muic, max8997);
156 
157  pm_runtime_set_active(max8997->dev);
158 
159  max8997_irq_init(max8997);
160 
161  mfd_add_devices(max8997->dev, -1, max8997_devs,
162  ARRAY_SIZE(max8997_devs),
163  NULL, 0, NULL);
164 
165  /*
166  * TODO: enable others (flash, muic, rtc, battery, ...) and
167  * check the return value
168  */
169 
170  if (ret < 0)
171  goto err_mfd;
172 
173  /* MAX8997 has a power button input. */
174  device_init_wakeup(max8997->dev, pdata->wakeup);
175 
176  return ret;
177 
178 err_mfd:
179  mfd_remove_devices(max8997->dev);
180  i2c_unregister_device(max8997->muic);
181  i2c_unregister_device(max8997->haptic);
182  i2c_unregister_device(max8997->rtc);
183 err:
184  kfree(max8997);
185  return ret;
186 }
187 
188 static int max8997_i2c_remove(struct i2c_client *i2c)
189 {
190  struct max8997_dev *max8997 = i2c_get_clientdata(i2c);
191 
192  mfd_remove_devices(max8997->dev);
193  i2c_unregister_device(max8997->muic);
194  i2c_unregister_device(max8997->haptic);
195  i2c_unregister_device(max8997->rtc);
196  kfree(max8997);
197 
198  return 0;
199 }
200 
201 static const struct i2c_device_id max8997_i2c_id[] = {
202  { "max8997", TYPE_MAX8997 },
203  { "max8966", TYPE_MAX8966 },
204  { }
205 };
206 MODULE_DEVICE_TABLE(i2c, max8998_i2c_id);
207 
208 static u8 max8997_dumpaddr_pmic[] = {
281 
293 
306 
326 
331 };
332 
333 static u8 max8997_dumpaddr_muic[] = {
341 };
342 
343 static u8 max8997_dumpaddr_haptic[] = {
359 };
360 
361 static int max8997_freeze(struct device *dev)
362 {
363  struct i2c_client *i2c = container_of(dev, struct i2c_client, dev);
364  struct max8997_dev *max8997 = i2c_get_clientdata(i2c);
365  int i;
366 
367  for (i = 0; i < ARRAY_SIZE(max8997_dumpaddr_pmic); i++)
368  max8997_read_reg(i2c, max8997_dumpaddr_pmic[i],
369  &max8997->reg_dump[i]);
370 
371  for (i = 0; i < ARRAY_SIZE(max8997_dumpaddr_muic); i++)
372  max8997_read_reg(i2c, max8997_dumpaddr_muic[i],
373  &max8997->reg_dump[i + MAX8997_REG_PMIC_END]);
374 
375  for (i = 0; i < ARRAY_SIZE(max8997_dumpaddr_haptic); i++)
376  max8997_read_reg(i2c, max8997_dumpaddr_haptic[i],
377  &max8997->reg_dump[i + MAX8997_REG_PMIC_END +
379 
380  return 0;
381 }
382 
383 static int max8997_restore(struct device *dev)
384 {
385  struct i2c_client *i2c = container_of(dev, struct i2c_client, dev);
386  struct max8997_dev *max8997 = i2c_get_clientdata(i2c);
387  int i;
388 
389  for (i = 0; i < ARRAY_SIZE(max8997_dumpaddr_pmic); i++)
390  max8997_write_reg(i2c, max8997_dumpaddr_pmic[i],
391  max8997->reg_dump[i]);
392 
393  for (i = 0; i < ARRAY_SIZE(max8997_dumpaddr_muic); i++)
394  max8997_write_reg(i2c, max8997_dumpaddr_muic[i],
395  max8997->reg_dump[i + MAX8997_REG_PMIC_END]);
396 
397  for (i = 0; i < ARRAY_SIZE(max8997_dumpaddr_haptic); i++)
398  max8997_write_reg(i2c, max8997_dumpaddr_haptic[i],
399  max8997->reg_dump[i + MAX8997_REG_PMIC_END +
401 
402  return 0;
403 }
404 
405 static int max8997_suspend(struct device *dev)
406 {
407  struct i2c_client *i2c = container_of(dev, struct i2c_client, dev);
408  struct max8997_dev *max8997 = i2c_get_clientdata(i2c);
409 
410  if (device_may_wakeup(dev))
411  irq_set_irq_wake(max8997->irq, 1);
412  return 0;
413 }
414 
415 static int max8997_resume(struct device *dev)
416 {
417  struct i2c_client *i2c = container_of(dev, struct i2c_client, dev);
418  struct max8997_dev *max8997 = i2c_get_clientdata(i2c);
419 
420  if (device_may_wakeup(dev))
421  irq_set_irq_wake(max8997->irq, 0);
422  return max8997_irq_resume(max8997);
423 }
424 
425 static const struct dev_pm_ops max8997_pm = {
426  .suspend = max8997_suspend,
427  .resume = max8997_resume,
428  .freeze = max8997_freeze,
429  .restore = max8997_restore,
430 };
431 
432 static struct i2c_driver max8997_i2c_driver = {
433  .driver = {
434  .name = "max8997",
435  .owner = THIS_MODULE,
436  .pm = &max8997_pm,
437  },
438  .probe = max8997_i2c_probe,
439  .remove = max8997_i2c_remove,
440  .id_table = max8997_i2c_id,
441 };
442 
443 static int __init max8997_i2c_init(void)
444 {
445  return i2c_add_driver(&max8997_i2c_driver);
446 }
447 /* init early so consumer devices can complete system boot */
448 subsys_initcall(max8997_i2c_init);
449 
450 static void __exit max8997_i2c_exit(void)
451 {
452  i2c_del_driver(&max8997_i2c_driver);
453 }
454 module_exit(max8997_i2c_exit);
455 
456 MODULE_DESCRIPTION("MAXIM 8997 multi-function core driver");
457 MODULE_AUTHOR("MyungJoo Ham <[email protected]>");
458 MODULE_LICENSE("GPL");