aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/rtc/rtc-ds1374.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/rtc/rtc-ds1374.c')
-rw-r--r--drivers/rtc/rtc-ds1374.c58
1 files changed, 24 insertions, 34 deletions
diff --git a/drivers/rtc/rtc-ds1374.c b/drivers/rtc/rtc-ds1374.c
index 1f0007fd4431..e6e71deb188f 100644
--- a/drivers/rtc/rtc-ds1374.c
+++ b/drivers/rtc/rtc-ds1374.c
@@ -25,6 +25,7 @@
25#include <linux/bcd.h> 25#include <linux/bcd.h>
26#include <linux/workqueue.h> 26#include <linux/workqueue.h>
27#include <linux/slab.h> 27#include <linux/slab.h>
28#include <linux/pm.h>
28 29
29#define DS1374_REG_TOD0 0x00 /* Time of Day */ 30#define DS1374_REG_TOD0 0x00 /* Time of Day */
30#define DS1374_REG_TOD1 0x01 31#define DS1374_REG_TOD1 0x01
@@ -307,42 +308,25 @@ unlock:
307 mutex_unlock(&ds1374->mutex); 308 mutex_unlock(&ds1374->mutex);
308} 309}
309 310
310static int ds1374_ioctl(struct device *dev, unsigned int cmd, unsigned long arg) 311static int ds1374_alarm_irq_enable(struct device *dev, unsigned int enabled)
311{ 312{
312 struct i2c_client *client = to_i2c_client(dev); 313 struct i2c_client *client = to_i2c_client(dev);
313 struct ds1374 *ds1374 = i2c_get_clientdata(client); 314 struct ds1374 *ds1374 = i2c_get_clientdata(client);
314 int ret = -ENOIOCTLCMD; 315 int ret;
315 316
316 mutex_lock(&ds1374->mutex); 317 mutex_lock(&ds1374->mutex);
317 318
318 switch (cmd) { 319 ret = i2c_smbus_read_byte_data(client, DS1374_REG_CR);
319 case RTC_AIE_OFF: 320 if (ret < 0)
320 ret = i2c_smbus_read_byte_data(client, DS1374_REG_CR); 321 goto out;
321 if (ret < 0)
322 goto out;
323
324 ret &= ~DS1374_REG_CR_WACE;
325
326 ret = i2c_smbus_write_byte_data(client, DS1374_REG_CR, ret);
327 if (ret < 0)
328 goto out;
329
330 break;
331
332 case RTC_AIE_ON:
333 ret = i2c_smbus_read_byte_data(client, DS1374_REG_CR);
334 if (ret < 0)
335 goto out;
336 322
323 if (enabled) {
337 ret |= DS1374_REG_CR_WACE | DS1374_REG_CR_AIE; 324 ret |= DS1374_REG_CR_WACE | DS1374_REG_CR_AIE;
338 ret &= ~DS1374_REG_CR_WDALM; 325 ret &= ~DS1374_REG_CR_WDALM;
339 326 } else {
340 ret = i2c_smbus_write_byte_data(client, DS1374_REG_CR, ret); 327 ret &= ~DS1374_REG_CR_WACE;
341 if (ret < 0)
342 goto out;
343
344 break;
345 } 328 }
329 ret = i2c_smbus_write_byte_data(client, DS1374_REG_CR, ret);
346 330
347out: 331out:
348 mutex_unlock(&ds1374->mutex); 332 mutex_unlock(&ds1374->mutex);
@@ -354,7 +338,7 @@ static const struct rtc_class_ops ds1374_rtc_ops = {
354 .set_time = ds1374_set_time, 338 .set_time = ds1374_set_time,
355 .read_alarm = ds1374_read_alarm, 339 .read_alarm = ds1374_read_alarm,
356 .set_alarm = ds1374_set_alarm, 340 .set_alarm = ds1374_set_alarm,
357 .ioctl = ds1374_ioctl, 341 .alarm_irq_enable = ds1374_alarm_irq_enable,
358}; 342};
359 343
360static int ds1374_probe(struct i2c_client *client, 344static int ds1374_probe(struct i2c_client *client,
@@ -417,7 +401,7 @@ static int __devexit ds1374_remove(struct i2c_client *client)
417 mutex_unlock(&ds1374->mutex); 401 mutex_unlock(&ds1374->mutex);
418 402
419 free_irq(client->irq, client); 403 free_irq(client->irq, client);
420 flush_scheduled_work(); 404 cancel_work_sync(&ds1374->work);
421 } 405 }
422 406
423 rtc_device_unregister(ds1374->rtc); 407 rtc_device_unregister(ds1374->rtc);
@@ -426,32 +410,38 @@ static int __devexit ds1374_remove(struct i2c_client *client)
426} 410}
427 411
428#ifdef CONFIG_PM 412#ifdef CONFIG_PM
429static int ds1374_suspend(struct i2c_client *client, pm_message_t state) 413static int ds1374_suspend(struct device *dev)
430{ 414{
415 struct i2c_client *client = to_i2c_client(dev);
416
431 if (client->irq >= 0 && device_may_wakeup(&client->dev)) 417 if (client->irq >= 0 && device_may_wakeup(&client->dev))
432 enable_irq_wake(client->irq); 418 enable_irq_wake(client->irq);
433 return 0; 419 return 0;
434} 420}
435 421
436static int ds1374_resume(struct i2c_client *client) 422static int ds1374_resume(struct device *dev)
437{ 423{
424 struct i2c_client *client = to_i2c_client(dev);
425
438 if (client->irq >= 0 && device_may_wakeup(&client->dev)) 426 if (client->irq >= 0 && device_may_wakeup(&client->dev))
439 disable_irq_wake(client->irq); 427 disable_irq_wake(client->irq);
440 return 0; 428 return 0;
441} 429}
430
431static SIMPLE_DEV_PM_OPS(ds1374_pm, ds1374_suspend, ds1374_resume);
432
433#define DS1374_PM (&ds1374_pm)
442#else 434#else
443#define ds1374_suspend NULL 435#define DS1374_PM NULL
444#define ds1374_resume NULL
445#endif 436#endif
446 437
447static struct i2c_driver ds1374_driver = { 438static struct i2c_driver ds1374_driver = {
448 .driver = { 439 .driver = {
449 .name = "rtc-ds1374", 440 .name = "rtc-ds1374",
450 .owner = THIS_MODULE, 441 .owner = THIS_MODULE,
442 .pm = DS1374_PM,
451 }, 443 },
452 .probe = ds1374_probe, 444 .probe = ds1374_probe,
453 .suspend = ds1374_suspend,
454 .resume = ds1374_resume,
455 .remove = __devexit_p(ds1374_remove), 445 .remove = __devexit_p(ds1374_remove),
456 .id_table = ds1374_id, 446 .id_table = ds1374_id,
457}; 447};