aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/rtc
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/rtc')
-rw-r--r--drivers/rtc/Kconfig38
-rw-r--r--drivers/rtc/Makefile5
-rw-r--r--drivers/rtc/class.c6
-rw-r--r--drivers/rtc/rtc-at91.c24
-rw-r--r--drivers/rtc/rtc-dev.c7
-rw-r--r--drivers/rtc/rtc-ds1307.c2
-rw-r--r--drivers/rtc/rtc-ds1553.c10
-rw-r--r--drivers/rtc/rtc-ds1672.c2
-rw-r--r--drivers/rtc/rtc-ds1742.c12
-rw-r--r--drivers/rtc/rtc-ep93xx.c2
-rw-r--r--drivers/rtc/rtc-isl1208.c2
-rw-r--r--drivers/rtc/rtc-lib.c8
-rw-r--r--drivers/rtc/rtc-m48t86.c2
-rw-r--r--drivers/rtc/rtc-max6902.c2
-rw-r--r--drivers/rtc/rtc-pcf8563.c6
-rw-r--r--drivers/rtc/rtc-pcf8583.c2
-rw-r--r--drivers/rtc/rtc-pl031.c2
-rw-r--r--drivers/rtc/rtc-proc.c6
-rw-r--r--drivers/rtc/rtc-rs5c348.c11
-rw-r--r--drivers/rtc/rtc-rs5c372.c2
-rw-r--r--drivers/rtc/rtc-s3c.c2
-rw-r--r--drivers/rtc/rtc-sa1100.c2
-rw-r--r--drivers/rtc/rtc-sh.c467
-rw-r--r--drivers/rtc/rtc-sysfs.c2
-rw-r--r--drivers/rtc/rtc-test.c2
-rw-r--r--drivers/rtc/rtc-v3020.c5
-rw-r--r--drivers/rtc/rtc-vr41xx.c2
-rw-r--r--drivers/rtc/rtc-x1205.c2
28 files changed, 581 insertions, 54 deletions
diff --git a/drivers/rtc/Kconfig b/drivers/rtc/Kconfig
index 7ff1d88094b6..fc766a7a611e 100644
--- a/drivers/rtc/Kconfig
+++ b/drivers/rtc/Kconfig
@@ -27,7 +27,7 @@ config RTC_HCTOSYS
27 help 27 help
28 If you say yes here, the system time will be set using 28 If you say yes here, the system time will be set using
29 the value read from the specified RTC device. This is useful 29 the value read from the specified RTC device. This is useful
30 in order to avoid unnecessary fschk runs. 30 in order to avoid unnecessary fsck runs.
31 31
32config RTC_HCTOSYS_DEVICE 32config RTC_HCTOSYS_DEVICE
33 string "The RTC to read the time from" 33 string "The RTC to read the time from"
@@ -37,6 +37,13 @@ config RTC_HCTOSYS_DEVICE
37 The RTC device that will be used as the source for 37 The RTC device that will be used as the source for
38 the system time, usually rtc0. 38 the system time, usually rtc0.
39 39
40config RTC_DEBUG
41 bool "RTC debug support"
42 depends on RTC_CLASS = y
43 help
44 Say yes here to enable debugging support in the RTC framework
45 and individual RTC drivers.
46
40comment "RTC interfaces" 47comment "RTC interfaces"
41 depends on RTC_CLASS 48 depends on RTC_CLASS
42 49
@@ -45,8 +52,8 @@ config RTC_INTF_SYSFS
45 depends on RTC_CLASS && SYSFS 52 depends on RTC_CLASS && SYSFS
46 default RTC_CLASS 53 default RTC_CLASS
47 help 54 help
48 Say yes here if you want to use your RTC using the sysfs 55 Say yes here if you want to use your RTCs using sysfs interfaces,
49 interface, /sys/class/rtc/rtcX . 56 /sys/class/rtc/rtc0 through /sys/.../rtcN.
50 57
51 This driver can also be built as a module. If so, the module 58 This driver can also be built as a module. If so, the module
52 will be called rtc-sysfs. 59 will be called rtc-sysfs.
@@ -56,8 +63,9 @@ config RTC_INTF_PROC
56 depends on RTC_CLASS && PROC_FS 63 depends on RTC_CLASS && PROC_FS
57 default RTC_CLASS 64 default RTC_CLASS
58 help 65 help
59 Say yes here if you want to use your RTC using the proc 66 Say yes here if you want to use your first RTC through the proc
60 interface, /proc/driver/rtc . 67 interface, /proc/driver/rtc. Other RTCs will not be available
68 through that API.
61 69
62 This driver can also be built as a module. If so, the module 70 This driver can also be built as a module. If so, the module
63 will be called rtc-proc. 71 will be called rtc-proc.
@@ -67,8 +75,11 @@ config RTC_INTF_DEV
67 depends on RTC_CLASS 75 depends on RTC_CLASS
68 default RTC_CLASS 76 default RTC_CLASS
69 help 77 help
70 Say yes here if you want to use your RTC using the dev 78 Say yes here if you want to use your RTCs using the /dev
71 interface, /dev/rtc . 79 interfaces, which "udev" sets up as /dev/rtc0 through
80 /dev/rtcN. You may want to set up a symbolic link so one
81 of these can be accessed as /dev/rtc, which is a name
82 expected by "hwclock" and some other programs.
72 83
73 This driver can also be built as a module. If so, the module 84 This driver can also be built as a module. If so, the module
74 will be called rtc-dev. 85 will be called rtc-dev.
@@ -78,7 +89,8 @@ config RTC_INTF_DEV_UIE_EMUL
78 depends on RTC_INTF_DEV 89 depends on RTC_INTF_DEV
79 help 90 help
80 Provides an emulation for RTC_UIE if the underlaying rtc chip 91 Provides an emulation for RTC_UIE if the underlaying rtc chip
81 driver did not provide RTC_UIE ioctls. 92 driver does not expose RTC_UIE ioctls. Those requests generate
93 once-per-second update interrupts, used for synchronization.
82 94
83comment "RTC drivers" 95comment "RTC drivers"
84 depends on RTC_CLASS 96 depends on RTC_CLASS
@@ -238,6 +250,16 @@ config RTC_DRV_SA1100
238 To compile this driver as a module, choose M here: the 250 To compile this driver as a module, choose M here: the
239 module will be called rtc-sa1100. 251 module will be called rtc-sa1100.
240 252
253config RTC_DRV_SH
254 tristate "SuperH On-Chip RTC"
255 depends on RTC_CLASS && SUPERH
256 help
257 Say Y here to enable support for the on-chip RTC found in
258 most SuperH processors.
259
260 To compile this driver as a module, choose M here: the
261 module will be called rtc-sh.
262
241config RTC_DRV_VR41XX 263config RTC_DRV_VR41XX
242 tristate "NEC VR41XX" 264 tristate "NEC VR41XX"
243 depends on RTC_CLASS && CPU_VR41XX 265 depends on RTC_CLASS && CPU_VR41XX
diff --git a/drivers/rtc/Makefile b/drivers/rtc/Makefile
index bbcfb09d81d9..3ba5ff6e6800 100644
--- a/drivers/rtc/Makefile
+++ b/drivers/rtc/Makefile
@@ -2,6 +2,10 @@
2# Makefile for RTC class/drivers. 2# Makefile for RTC class/drivers.
3# 3#
4 4
5ifeq ($(CONFIG_RTC_DEBUG),y)
6 EXTRA_CFLAGS += -DDEBUG
7endif
8
5obj-$(CONFIG_RTC_LIB) += rtc-lib.o 9obj-$(CONFIG_RTC_LIB) += rtc-lib.o
6obj-$(CONFIG_RTC_HCTOSYS) += hctosys.o 10obj-$(CONFIG_RTC_HCTOSYS) += hctosys.o
7obj-$(CONFIG_RTC_CLASS) += rtc-core.o 11obj-$(CONFIG_RTC_CLASS) += rtc-core.o
@@ -31,3 +35,4 @@ obj-$(CONFIG_RTC_DRV_PL031) += rtc-pl031.o
31obj-$(CONFIG_RTC_DRV_MAX6902) += rtc-max6902.o 35obj-$(CONFIG_RTC_DRV_MAX6902) += rtc-max6902.o
32obj-$(CONFIG_RTC_DRV_V3020) += rtc-v3020.o 36obj-$(CONFIG_RTC_DRV_V3020) += rtc-v3020.o
33obj-$(CONFIG_RTC_DRV_AT91) += rtc-at91.o 37obj-$(CONFIG_RTC_DRV_AT91) += rtc-at91.o
38obj-$(CONFIG_RTC_DRV_SH) += rtc-sh.o
diff --git a/drivers/rtc/class.c b/drivers/rtc/class.c
index 1cb61a761cb2..7a0d8ee2de9c 100644
--- a/drivers/rtc/class.c
+++ b/drivers/rtc/class.c
@@ -39,7 +39,7 @@ static void rtc_device_release(struct class_device *class_dev)
39 * Returns the pointer to the new struct class device. 39 * Returns the pointer to the new struct class device.
40 */ 40 */
41struct rtc_device *rtc_device_register(const char *name, struct device *dev, 41struct rtc_device *rtc_device_register(const char *name, struct device *dev,
42 struct rtc_class_ops *ops, 42 const struct rtc_class_ops *ops,
43 struct module *owner) 43 struct module *owner)
44{ 44{
45 struct rtc_device *rtc; 45 struct rtc_device *rtc;
@@ -142,9 +142,9 @@ static void __exit rtc_exit(void)
142 class_destroy(rtc_class); 142 class_destroy(rtc_class);
143} 143}
144 144
145module_init(rtc_init); 145subsys_initcall(rtc_init);
146module_exit(rtc_exit); 146module_exit(rtc_exit);
147 147
148MODULE_AUTHOR("Alessandro Zummo <a.zummo@towerteh.it>"); 148MODULE_AUTHOR("Alessandro Zummo <a.zummo@towertech.it>");
149MODULE_DESCRIPTION("RTC class support"); 149MODULE_DESCRIPTION("RTC class support");
150MODULE_LICENSE("GPL"); 150MODULE_LICENSE("GPL");
diff --git a/drivers/rtc/rtc-at91.c b/drivers/rtc/rtc-at91.c
index dfd0ce86f6a0..c0714da44920 100644
--- a/drivers/rtc/rtc-at91.c
+++ b/drivers/rtc/rtc-at91.c
@@ -267,7 +267,7 @@ static irqreturn_t at91_rtc_interrupt(int irq, void *dev_id,
267 return IRQ_NONE; /* not handled */ 267 return IRQ_NONE; /* not handled */
268} 268}
269 269
270static struct rtc_class_ops at91_rtc_ops = { 270static const struct rtc_class_ops at91_rtc_ops = {
271 .ioctl = at91_rtc_ioctl, 271 .ioctl = at91_rtc_ioctl,
272 .read_time = at91_rtc_readtime, 272 .read_time = at91_rtc_readtime,
273 .set_time = at91_rtc_settime, 273 .set_time = at91_rtc_settime,
@@ -307,6 +307,7 @@ static int __init at91_rtc_probe(struct platform_device *pdev)
307 return PTR_ERR(rtc); 307 return PTR_ERR(rtc);
308 } 308 }
309 platform_set_drvdata(pdev, rtc); 309 platform_set_drvdata(pdev, rtc);
310 device_init_wakeup(&pdev->dev, 1);
310 311
311 printk(KERN_INFO "AT91 Real Time Clock driver.\n"); 312 printk(KERN_INFO "AT91 Real Time Clock driver.\n");
312 return 0; 313 return 0;
@@ -327,6 +328,7 @@ static int __devexit at91_rtc_remove(struct platform_device *pdev)
327 328
328 rtc_device_unregister(rtc); 329 rtc_device_unregister(rtc);
329 platform_set_drvdata(pdev, NULL); 330 platform_set_drvdata(pdev, NULL);
331 device_init_wakeup(&pdev->dev, 0);
330 332
331 return 0; 333 return 0;
332} 334}
@@ -336,6 +338,7 @@ static int __devexit at91_rtc_remove(struct platform_device *pdev)
336/* AT91RM9200 RTC Power management control */ 338/* AT91RM9200 RTC Power management control */
337 339
338static struct timespec at91_rtc_delta; 340static struct timespec at91_rtc_delta;
341static u32 at91_rtc_imr;
339 342
340static int at91_rtc_suspend(struct platform_device *pdev, pm_message_t state) 343static int at91_rtc_suspend(struct platform_device *pdev, pm_message_t state)
341{ 344{
@@ -349,6 +352,18 @@ static int at91_rtc_suspend(struct platform_device *pdev, pm_message_t state)
349 rtc_tm_to_time(&tm, &time.tv_sec); 352 rtc_tm_to_time(&tm, &time.tv_sec);
350 save_time_delta(&at91_rtc_delta, &time); 353 save_time_delta(&at91_rtc_delta, &time);
351 354
355 /* this IRQ is shared with DBGU and other hardware which isn't
356 * necessarily doing PM like we are...
357 */
358 at91_rtc_imr = at91_sys_read(AT91_RTC_IMR)
359 & (AT91_RTC_ALARM|AT91_RTC_SECEV);
360 if (at91_rtc_imr) {
361 if (device_may_wakeup(&pdev->dev))
362 enable_irq_wake(AT91_ID_SYS);
363 else
364 at91_sys_write(AT91_RTC_IDR, at91_rtc_imr);
365 }
366
352 pr_debug("%s(): %4d-%02d-%02d %02d:%02d:%02d\n", __FUNCTION__, 367 pr_debug("%s(): %4d-%02d-%02d %02d:%02d:%02d\n", __FUNCTION__,
353 1900 + tm.tm_year, tm.tm_mon, tm.tm_mday, 368 1900 + tm.tm_year, tm.tm_mon, tm.tm_mday,
354 tm.tm_hour, tm.tm_min, tm.tm_sec); 369 tm.tm_hour, tm.tm_min, tm.tm_sec);
@@ -367,6 +382,13 @@ static int at91_rtc_resume(struct platform_device *pdev)
367 rtc_tm_to_time(&tm, &time.tv_sec); 382 rtc_tm_to_time(&tm, &time.tv_sec);
368 restore_time_delta(&at91_rtc_delta, &time); 383 restore_time_delta(&at91_rtc_delta, &time);
369 384
385 if (at91_rtc_imr) {
386 if (device_may_wakeup(&pdev->dev))
387 disable_irq_wake(AT91_ID_SYS);
388 else
389 at91_sys_write(AT91_RTC_IER, at91_rtc_imr);
390 }
391
370 pr_debug("%s(): %4d-%02d-%02d %02d:%02d:%02d\n", __FUNCTION__, 392 pr_debug("%s(): %4d-%02d-%02d %02d:%02d:%02d\n", __FUNCTION__,
371 1900 + tm.tm_year, tm.tm_mon, tm.tm_mday, 393 1900 + tm.tm_year, tm.tm_mon, tm.tm_mday,
372 tm.tm_hour, tm.tm_min, tm.tm_sec); 394 tm.tm_hour, tm.tm_min, tm.tm_sec);
diff --git a/drivers/rtc/rtc-dev.c b/drivers/rtc/rtc-dev.c
index 61a58259c93f..583789c66cdb 100644
--- a/drivers/rtc/rtc-dev.c
+++ b/drivers/rtc/rtc-dev.c
@@ -24,7 +24,7 @@ static int rtc_dev_open(struct inode *inode, struct file *file)
24 int err; 24 int err;
25 struct rtc_device *rtc = container_of(inode->i_cdev, 25 struct rtc_device *rtc = container_of(inode->i_cdev,
26 struct rtc_device, char_dev); 26 struct rtc_device, char_dev);
27 struct rtc_class_ops *ops = rtc->ops; 27 const struct rtc_class_ops *ops = rtc->ops;
28 28
29 /* We keep the lock as long as the device is in use 29 /* We keep the lock as long as the device is in use
30 * and return immediately if busy 30 * and return immediately if busy
@@ -209,7 +209,7 @@ static int rtc_dev_ioctl(struct inode *inode, struct file *file,
209 int err = 0; 209 int err = 0;
210 struct class_device *class_dev = file->private_data; 210 struct class_device *class_dev = file->private_data;
211 struct rtc_device *rtc = to_rtc_device(class_dev); 211 struct rtc_device *rtc = to_rtc_device(class_dev);
212 struct rtc_class_ops *ops = rtc->ops; 212 const struct rtc_class_ops *ops = rtc->ops;
213 struct rtc_time tm; 213 struct rtc_time tm;
214 struct rtc_wkalrm alarm; 214 struct rtc_wkalrm alarm;
215 void __user *uarg = (void __user *) arg; 215 void __user *uarg = (void __user *) arg;
@@ -406,7 +406,6 @@ static int rtc_dev_add_device(struct class_device *class_dev,
406 rtc->char_dev.owner = rtc->owner; 406 rtc->char_dev.owner = rtc->owner;
407 407
408 if (cdev_add(&rtc->char_dev, MKDEV(MAJOR(rtc_devt), rtc->id), 1)) { 408 if (cdev_add(&rtc->char_dev, MKDEV(MAJOR(rtc_devt), rtc->id), 1)) {
409 cdev_del(&rtc->char_dev);
410 dev_err(class_dev->dev, 409 dev_err(class_dev->dev,
411 "failed to add char device %d:%d\n", 410 "failed to add char device %d:%d\n",
412 MAJOR(rtc_devt), rtc->id); 411 MAJOR(rtc_devt), rtc->id);
@@ -496,7 +495,7 @@ static void __exit rtc_dev_exit(void)
496 unregister_chrdev_region(rtc_devt, RTC_DEV_MAX); 495 unregister_chrdev_region(rtc_devt, RTC_DEV_MAX);
497} 496}
498 497
499module_init(rtc_dev_init); 498subsys_initcall(rtc_dev_init);
500module_exit(rtc_dev_exit); 499module_exit(rtc_dev_exit);
501 500
502MODULE_AUTHOR("Alessandro Zummo <a.zummo@towertech.it>"); 501MODULE_AUTHOR("Alessandro Zummo <a.zummo@towertech.it>");
diff --git a/drivers/rtc/rtc-ds1307.c b/drivers/rtc/rtc-ds1307.c
index e8afb9384786..cc5032b6f42a 100644
--- a/drivers/rtc/rtc-ds1307.c
+++ b/drivers/rtc/rtc-ds1307.c
@@ -178,7 +178,7 @@ static int ds1307_set_time(struct device *dev, struct rtc_time *t)
178 return 0; 178 return 0;
179} 179}
180 180
181static struct rtc_class_ops ds13xx_rtc_ops = { 181static const struct rtc_class_ops ds13xx_rtc_ops = {
182 .read_time = ds1307_get_time, 182 .read_time = ds1307_get_time,
183 .set_time = ds1307_set_time, 183 .set_time = ds1307_set_time,
184}; 184};
diff --git a/drivers/rtc/rtc-ds1553.c b/drivers/rtc/rtc-ds1553.c
index 209001495474..9647188fee2c 100644
--- a/drivers/rtc/rtc-ds1553.c
+++ b/drivers/rtc/rtc-ds1553.c
@@ -18,7 +18,7 @@
18#include <linux/platform_device.h> 18#include <linux/platform_device.h>
19#include <linux/io.h> 19#include <linux/io.h>
20 20
21#define DRV_VERSION "0.1" 21#define DRV_VERSION "0.2"
22 22
23#define RTC_REG_SIZE 0x2000 23#define RTC_REG_SIZE 0x2000
24#define RTC_OFFSET 0x1ff0 24#define RTC_OFFSET 0x1ff0
@@ -250,7 +250,7 @@ static int ds1553_rtc_ioctl(struct device *dev, unsigned int cmd,
250 return 0; 250 return 0;
251} 251}
252 252
253static struct rtc_class_ops ds1553_rtc_ops = { 253static const struct rtc_class_ops ds1553_rtc_ops = {
254 .read_time = ds1553_rtc_read_time, 254 .read_time = ds1553_rtc_read_time,
255 .set_time = ds1553_rtc_set_time, 255 .set_time = ds1553_rtc_set_time,
256 .read_alarm = ds1553_rtc_read_alarm, 256 .read_alarm = ds1553_rtc_read_alarm,
@@ -357,9 +357,13 @@ static int __init ds1553_rtc_probe(struct platform_device *pdev)
357 pdata->rtc = rtc; 357 pdata->rtc = rtc;
358 pdata->last_jiffies = jiffies; 358 pdata->last_jiffies = jiffies;
359 platform_set_drvdata(pdev, pdata); 359 platform_set_drvdata(pdev, pdata);
360 sysfs_create_bin_file(&pdev->dev.kobj, &ds1553_nvram_attr); 360 ret = sysfs_create_bin_file(&pdev->dev.kobj, &ds1553_nvram_attr);
361 if (ret)
362 goto out;
361 return 0; 363 return 0;
362 out: 364 out:
365 if (pdata->rtc)
366 rtc_device_unregister(pdata->rtc);
363 if (pdata->irq >= 0) 367 if (pdata->irq >= 0)
364 free_irq(pdata->irq, pdev); 368 free_irq(pdata->irq, pdev);
365 if (ioaddr) 369 if (ioaddr)
diff --git a/drivers/rtc/rtc-ds1672.c b/drivers/rtc/rtc-ds1672.c
index 9be81fd4737c..9c68ec99afa5 100644
--- a/drivers/rtc/rtc-ds1672.c
+++ b/drivers/rtc/rtc-ds1672.c
@@ -156,7 +156,7 @@ static ssize_t show_control(struct device *dev, struct device_attribute *attr, c
156} 156}
157static DEVICE_ATTR(control, S_IRUGO, show_control, NULL); 157static DEVICE_ATTR(control, S_IRUGO, show_control, NULL);
158 158
159static struct rtc_class_ops ds1672_rtc_ops = { 159static const struct rtc_class_ops ds1672_rtc_ops = {
160 .read_time = ds1672_rtc_read_time, 160 .read_time = ds1672_rtc_read_time,
161 .set_time = ds1672_rtc_set_time, 161 .set_time = ds1672_rtc_set_time,
162 .set_mmss = ds1672_rtc_set_mmss, 162 .set_mmss = ds1672_rtc_set_mmss,
diff --git a/drivers/rtc/rtc-ds1742.c b/drivers/rtc/rtc-ds1742.c
index 8e47e5a06d2a..6273a3d240a2 100644
--- a/drivers/rtc/rtc-ds1742.c
+++ b/drivers/rtc/rtc-ds1742.c
@@ -17,7 +17,7 @@
17#include <linux/platform_device.h> 17#include <linux/platform_device.h>
18#include <linux/io.h> 18#include <linux/io.h>
19 19
20#define DRV_VERSION "0.1" 20#define DRV_VERSION "0.2"
21 21
22#define RTC_REG_SIZE 0x800 22#define RTC_REG_SIZE 0x800
23#define RTC_OFFSET 0x7f8 23#define RTC_OFFSET 0x7f8
@@ -116,7 +116,7 @@ static int ds1742_rtc_read_time(struct device *dev, struct rtc_time *tm)
116 return 0; 116 return 0;
117} 117}
118 118
119static struct rtc_class_ops ds1742_rtc_ops = { 119static const struct rtc_class_ops ds1742_rtc_ops = {
120 .read_time = ds1742_rtc_read_time, 120 .read_time = ds1742_rtc_read_time,
121 .set_time = ds1742_rtc_set_time, 121 .set_time = ds1742_rtc_set_time,
122}; 122};
@@ -196,7 +196,7 @@ static int __init ds1742_rtc_probe(struct platform_device *pdev)
196 writeb(sec, ioaddr + RTC_SECONDS); 196 writeb(sec, ioaddr + RTC_SECONDS);
197 writeb(cen & RTC_CENTURY_MASK, ioaddr + RTC_CONTROL); 197 writeb(cen & RTC_CENTURY_MASK, ioaddr + RTC_CONTROL);
198 } 198 }
199 if (readb(ioaddr + RTC_DAY) & RTC_BATT_FLAG) 199 if (!(readb(ioaddr + RTC_DAY) & RTC_BATT_FLAG))
200 dev_warn(&pdev->dev, "voltage-low detected.\n"); 200 dev_warn(&pdev->dev, "voltage-low detected.\n");
201 201
202 rtc = rtc_device_register(pdev->name, &pdev->dev, 202 rtc = rtc_device_register(pdev->name, &pdev->dev,
@@ -208,9 +208,13 @@ static int __init ds1742_rtc_probe(struct platform_device *pdev)
208 pdata->rtc = rtc; 208 pdata->rtc = rtc;
209 pdata->last_jiffies = jiffies; 209 pdata->last_jiffies = jiffies;
210 platform_set_drvdata(pdev, pdata); 210 platform_set_drvdata(pdev, pdata);
211 sysfs_create_bin_file(&pdev->dev.kobj, &ds1742_nvram_attr); 211 ret = sysfs_create_bin_file(&pdev->dev.kobj, &ds1742_nvram_attr);
212 if (ret)
213 goto out;
212 return 0; 214 return 0;
213 out: 215 out:
216 if (pdata->rtc)
217 rtc_device_unregister(pdata->rtc);
214 if (ioaddr) 218 if (ioaddr)
215 iounmap(ioaddr); 219 iounmap(ioaddr);
216 if (pdata->baseaddr) 220 if (pdata->baseaddr)
diff --git a/drivers/rtc/rtc-ep93xx.c b/drivers/rtc/rtc-ep93xx.c
index e1a1169e4664..ef4f147f3c0c 100644
--- a/drivers/rtc/rtc-ep93xx.c
+++ b/drivers/rtc/rtc-ep93xx.c
@@ -73,7 +73,7 @@ static int ep93xx_rtc_proc(struct device *dev, struct seq_file *seq)
73 return 0; 73 return 0;
74} 74}
75 75
76static struct rtc_class_ops ep93xx_rtc_ops = { 76static const struct rtc_class_ops ep93xx_rtc_ops = {
77 .read_time = ep93xx_rtc_read_time, 77 .read_time = ep93xx_rtc_read_time,
78 .set_time = ep93xx_rtc_set_time, 78 .set_time = ep93xx_rtc_set_time,
79 .set_mmss = ep93xx_rtc_set_mmss, 79 .set_mmss = ep93xx_rtc_set_mmss,
diff --git a/drivers/rtc/rtc-isl1208.c b/drivers/rtc/rtc-isl1208.c
index f324d0a635d4..1c743641b73b 100644
--- a/drivers/rtc/rtc-isl1208.c
+++ b/drivers/rtc/rtc-isl1208.c
@@ -390,7 +390,7 @@ static int isl1208_rtc_read_alarm(struct device *dev, struct rtc_wkalrm *alarm)
390 return isl1208_i2c_read_alarm(to_i2c_client(dev), alarm); 390 return isl1208_i2c_read_alarm(to_i2c_client(dev), alarm);
391} 391}
392 392
393static struct rtc_class_ops isl1208_rtc_ops = { 393static const struct rtc_class_ops isl1208_rtc_ops = {
394 .proc = isl1208_rtc_proc, 394 .proc = isl1208_rtc_proc,
395 .read_time = isl1208_rtc_read_time, 395 .read_time = isl1208_rtc_read_time,
396 .set_time = isl1208_rtc_set_time, 396 .set_time = isl1208_rtc_set_time,
diff --git a/drivers/rtc/rtc-lib.c b/drivers/rtc/rtc-lib.c
index 9812120f3a7c..ba795a4db1e9 100644
--- a/drivers/rtc/rtc-lib.c
+++ b/drivers/rtc/rtc-lib.c
@@ -94,12 +94,12 @@ EXPORT_SYMBOL(rtc_time_to_tm);
94int rtc_valid_tm(struct rtc_time *tm) 94int rtc_valid_tm(struct rtc_time *tm)
95{ 95{
96 if (tm->tm_year < 70 96 if (tm->tm_year < 70
97 || tm->tm_mon >= 12 97 || ((unsigned)tm->tm_mon) >= 12
98 || tm->tm_mday < 1 98 || tm->tm_mday < 1
99 || tm->tm_mday > rtc_month_days(tm->tm_mon, tm->tm_year + 1900) 99 || tm->tm_mday > rtc_month_days(tm->tm_mon, tm->tm_year + 1900)
100 || tm->tm_hour >= 24 100 || ((unsigned)tm->tm_hour) >= 24
101 || tm->tm_min >= 60 101 || ((unsigned)tm->tm_min) >= 60
102 || tm->tm_sec >= 60) 102 || ((unsigned)tm->tm_sec) >= 60)
103 return -EINVAL; 103 return -EINVAL;
104 104
105 return 0; 105 return 0;
diff --git a/drivers/rtc/rtc-m48t86.c b/drivers/rtc/rtc-m48t86.c
index 8c0d1a6739ad..8ff4a1221f59 100644
--- a/drivers/rtc/rtc-m48t86.c
+++ b/drivers/rtc/rtc-m48t86.c
@@ -138,7 +138,7 @@ static int m48t86_rtc_proc(struct device *dev, struct seq_file *seq)
138 return 0; 138 return 0;
139} 139}
140 140
141static struct rtc_class_ops m48t86_rtc_ops = { 141static const struct rtc_class_ops m48t86_rtc_ops = {
142 .read_time = m48t86_rtc_read_time, 142 .read_time = m48t86_rtc_read_time,
143 .set_time = m48t86_rtc_set_time, 143 .set_time = m48t86_rtc_set_time,
144 .proc = m48t86_rtc_proc, 144 .proc = m48t86_rtc_proc,
diff --git a/drivers/rtc/rtc-max6902.c b/drivers/rtc/rtc-max6902.c
index 2c9739562b5c..9eeef964663a 100644
--- a/drivers/rtc/rtc-max6902.c
+++ b/drivers/rtc/rtc-max6902.c
@@ -207,7 +207,7 @@ static int max6902_set_time(struct device *dev, struct rtc_time *tm)
207 return max6902_set_datetime(dev, tm); 207 return max6902_set_datetime(dev, tm);
208} 208}
209 209
210static struct rtc_class_ops max6902_rtc_ops = { 210static const struct rtc_class_ops max6902_rtc_ops = {
211 .read_time = max6902_read_time, 211 .read_time = max6902_read_time,
212 .set_time = max6902_set_time, 212 .set_time = max6902_set_time,
213}; 213};
diff --git a/drivers/rtc/rtc-pcf8563.c b/drivers/rtc/rtc-pcf8563.c
index ba9a583b7b68..a760cf69af90 100644
--- a/drivers/rtc/rtc-pcf8563.c
+++ b/drivers/rtc/rtc-pcf8563.c
@@ -95,7 +95,7 @@ static int pcf8563_get_datetime(struct i2c_client *client, struct rtc_time *tm)
95 tm->tm_wday = buf[PCF8563_REG_DW] & 0x07; 95 tm->tm_wday = buf[PCF8563_REG_DW] & 0x07;
96 tm->tm_mon = BCD2BIN(buf[PCF8563_REG_MO] & 0x1F) - 1; /* rtc mn 1-12 */ 96 tm->tm_mon = BCD2BIN(buf[PCF8563_REG_MO] & 0x1F) - 1; /* rtc mn 1-12 */
97 tm->tm_year = BCD2BIN(buf[PCF8563_REG_YR]) 97 tm->tm_year = BCD2BIN(buf[PCF8563_REG_YR])
98 + (buf[PCF8563_REG_MO] & PCF8563_MO_C ? 100 : 0); 98 + (buf[PCF8563_REG_MO] & PCF8563_MO_C ? 0 : 100);
99 99
100 dev_dbg(&client->dev, "%s: tm is secs=%d, mins=%d, hours=%d, " 100 dev_dbg(&client->dev, "%s: tm is secs=%d, mins=%d, hours=%d, "
101 "mday=%d, mon=%d, year=%d, wday=%d\n", 101 "mday=%d, mon=%d, year=%d, wday=%d\n",
@@ -135,7 +135,7 @@ static int pcf8563_set_datetime(struct i2c_client *client, struct rtc_time *tm)
135 135
136 /* year and century */ 136 /* year and century */
137 buf[PCF8563_REG_YR] = BIN2BCD(tm->tm_year % 100); 137 buf[PCF8563_REG_YR] = BIN2BCD(tm->tm_year % 100);
138 if (tm->tm_year / 100) 138 if (tm->tm_year < 100)
139 buf[PCF8563_REG_MO] |= PCF8563_MO_C; 139 buf[PCF8563_REG_MO] |= PCF8563_MO_C;
140 140
141 buf[PCF8563_REG_DW] = tm->tm_wday & 0x07; 141 buf[PCF8563_REG_DW] = tm->tm_wday & 0x07;
@@ -227,7 +227,7 @@ static int pcf8563_rtc_set_time(struct device *dev, struct rtc_time *tm)
227 return pcf8563_set_datetime(to_i2c_client(dev), tm); 227 return pcf8563_set_datetime(to_i2c_client(dev), tm);
228} 228}
229 229
230static struct rtc_class_ops pcf8563_rtc_ops = { 230static const struct rtc_class_ops pcf8563_rtc_ops = {
231 .read_time = pcf8563_rtc_read_time, 231 .read_time = pcf8563_rtc_read_time,
232 .set_time = pcf8563_rtc_set_time, 232 .set_time = pcf8563_rtc_set_time,
233}; 233};
diff --git a/drivers/rtc/rtc-pcf8583.c b/drivers/rtc/rtc-pcf8583.c
index b235a30cb661..5875ebb8c79d 100644
--- a/drivers/rtc/rtc-pcf8583.c
+++ b/drivers/rtc/rtc-pcf8583.c
@@ -273,7 +273,7 @@ static int pcf8583_rtc_set_time(struct device *dev, struct rtc_time *tm)
273 return ret; 273 return ret;
274} 274}
275 275
276static struct rtc_class_ops pcf8583_rtc_ops = { 276static const struct rtc_class_ops pcf8583_rtc_ops = {
277 .read_time = pcf8583_rtc_read_time, 277 .read_time = pcf8583_rtc_read_time,
278 .set_time = pcf8583_rtc_set_time, 278 .set_time = pcf8583_rtc_set_time,
279}; 279};
diff --git a/drivers/rtc/rtc-pl031.c b/drivers/rtc/rtc-pl031.c
index d6d1c5726b0e..739d1a6e14eb 100644
--- a/drivers/rtc/rtc-pl031.c
+++ b/drivers/rtc/rtc-pl031.c
@@ -128,7 +128,7 @@ static int pl031_set_alarm(struct device *dev, struct rtc_wkalrm *alarm)
128 return 0; 128 return 0;
129} 129}
130 130
131static struct rtc_class_ops pl031_ops = { 131static const struct rtc_class_ops pl031_ops = {
132 .open = pl031_open, 132 .open = pl031_open,
133 .release = pl031_release, 133 .release = pl031_release,
134 .ioctl = pl031_ioctl, 134 .ioctl = pl031_ioctl,
diff --git a/drivers/rtc/rtc-proc.c b/drivers/rtc/rtc-proc.c
index cef5f5a3bbf9..d51d8f20e634 100644
--- a/drivers/rtc/rtc-proc.c
+++ b/drivers/rtc/rtc-proc.c
@@ -23,7 +23,7 @@ static int rtc_proc_show(struct seq_file *seq, void *offset)
23{ 23{
24 int err; 24 int err;
25 struct class_device *class_dev = seq->private; 25 struct class_device *class_dev = seq->private;
26 struct rtc_class_ops *ops = to_rtc_device(class_dev)->ops; 26 const struct rtc_class_ops *ops = to_rtc_device(class_dev)->ops;
27 struct rtc_wkalrm alrm; 27 struct rtc_wkalrm alrm;
28 struct rtc_time tm; 28 struct rtc_time tm;
29 29
@@ -61,7 +61,7 @@ static int rtc_proc_show(struct seq_file *seq, void *offset)
61 seq_printf(seq, "%02d-", alrm.time.tm_mon + 1); 61 seq_printf(seq, "%02d-", alrm.time.tm_mon + 1);
62 else 62 else
63 seq_printf(seq, "**-"); 63 seq_printf(seq, "**-");
64 if ((unsigned int)alrm.time.tm_mday <= 31) 64 if (alrm.time.tm_mday && (unsigned int)alrm.time.tm_mday <= 31)
65 seq_printf(seq, "%02d\n", alrm.time.tm_mday); 65 seq_printf(seq, "%02d\n", alrm.time.tm_mday);
66 else 66 else
67 seq_printf(seq, "**\n"); 67 seq_printf(seq, "**\n");
@@ -156,7 +156,7 @@ static void __exit rtc_proc_exit(void)
156 class_interface_unregister(&rtc_proc_interface); 156 class_interface_unregister(&rtc_proc_interface);
157} 157}
158 158
159module_init(rtc_proc_init); 159subsys_initcall(rtc_proc_init);
160module_exit(rtc_proc_exit); 160module_exit(rtc_proc_exit);
161 161
162MODULE_AUTHOR("Alessandro Zummo <a.zummo@towertech.it>"); 162MODULE_AUTHOR("Alessandro Zummo <a.zummo@towertech.it>");
diff --git a/drivers/rtc/rtc-rs5c348.c b/drivers/rtc/rtc-rs5c348.c
index 0964d1dba925..f50f3fc353cd 100644
--- a/drivers/rtc/rtc-rs5c348.c
+++ b/drivers/rtc/rtc-rs5c348.c
@@ -23,7 +23,7 @@
23#include <linux/workqueue.h> 23#include <linux/workqueue.h>
24#include <linux/spi/spi.h> 24#include <linux/spi/spi.h>
25 25
26#define DRV_VERSION "0.1" 26#define DRV_VERSION "0.2"
27 27
28#define RS5C348_REG_SECS 0 28#define RS5C348_REG_SECS 0
29#define RS5C348_REG_MINS 1 29#define RS5C348_REG_MINS 1
@@ -140,7 +140,7 @@ rs5c348_rtc_read_time(struct device *dev, struct rtc_time *tm)
140 return 0; 140 return 0;
141} 141}
142 142
143static struct rtc_class_ops rs5c348_rtc_ops = { 143static const struct rtc_class_ops rs5c348_rtc_ops = {
144 .read_time = rs5c348_rtc_read_time, 144 .read_time = rs5c348_rtc_read_time,
145 .set_time = rs5c348_rtc_set_time, 145 .set_time = rs5c348_rtc_set_time,
146}; 146};
@@ -175,8 +175,15 @@ static int __devinit rs5c348_probe(struct spi_device *spi)
175 goto kfree_exit; 175 goto kfree_exit;
176 if (ret & (RS5C348_BIT_XSTP | RS5C348_BIT_VDET)) { 176 if (ret & (RS5C348_BIT_XSTP | RS5C348_BIT_VDET)) {
177 u8 buf[2]; 177 u8 buf[2];
178 struct rtc_time tm;
178 if (ret & RS5C348_BIT_VDET) 179 if (ret & RS5C348_BIT_VDET)
179 dev_warn(&spi->dev, "voltage-low detected.\n"); 180 dev_warn(&spi->dev, "voltage-low detected.\n");
181 if (ret & RS5C348_BIT_XSTP)
182 dev_warn(&spi->dev, "oscillator-stop detected.\n");
183 rtc_time_to_tm(0, &tm); /* 1970/1/1 */
184 ret = rs5c348_rtc_set_time(&spi->dev, &tm);
185 if (ret < 0)
186 goto kfree_exit;
180 buf[0] = RS5C348_CMD_W(RS5C348_REG_CTL2); 187 buf[0] = RS5C348_CMD_W(RS5C348_REG_CTL2);
181 buf[1] = 0; 188 buf[1] = 0;
182 ret = spi_write_then_read(spi, buf, sizeof(buf), NULL, 0); 189 ret = spi_write_then_read(spi, buf, sizeof(buf), NULL, 0);
diff --git a/drivers/rtc/rtc-rs5c372.c b/drivers/rtc/rtc-rs5c372.c
index 7553d797603f..bbdad099471d 100644
--- a/drivers/rtc/rtc-rs5c372.c
+++ b/drivers/rtc/rtc-rs5c372.c
@@ -160,7 +160,7 @@ static int rs5c372_rtc_proc(struct device *dev, struct seq_file *seq)
160 return 0; 160 return 0;
161} 161}
162 162
163static struct rtc_class_ops rs5c372_rtc_ops = { 163static const struct rtc_class_ops rs5c372_rtc_ops = {
164 .proc = rs5c372_rtc_proc, 164 .proc = rs5c372_rtc_proc,
165 .read_time = rs5c372_rtc_read_time, 165 .read_time = rs5c372_rtc_read_time,
166 .set_time = rs5c372_rtc_set_time, 166 .set_time = rs5c372_rtc_set_time,
diff --git a/drivers/rtc/rtc-s3c.c b/drivers/rtc/rtc-s3c.c
index 2c7de79c83b9..625dad2eeb4f 100644
--- a/drivers/rtc/rtc-s3c.c
+++ b/drivers/rtc/rtc-s3c.c
@@ -386,7 +386,7 @@ static void s3c_rtc_release(struct device *dev)
386 free_irq(s3c_rtc_tickno, rtc_dev); 386 free_irq(s3c_rtc_tickno, rtc_dev);
387} 387}
388 388
389static struct rtc_class_ops s3c_rtcops = { 389static const struct rtc_class_ops s3c_rtcops = {
390 .open = s3c_rtc_open, 390 .open = s3c_rtc_open,
391 .release = s3c_rtc_release, 391 .release = s3c_rtc_release,
392 .ioctl = s3c_rtc_ioctl, 392 .ioctl = s3c_rtc_ioctl,
diff --git a/drivers/rtc/rtc-sa1100.c b/drivers/rtc/rtc-sa1100.c
index ee4b61ee67b0..439c41aea31c 100644
--- a/drivers/rtc/rtc-sa1100.c
+++ b/drivers/rtc/rtc-sa1100.c
@@ -303,7 +303,7 @@ static int sa1100_rtc_proc(struct device *dev, struct seq_file *seq)
303 return 0; 303 return 0;
304} 304}
305 305
306static struct rtc_class_ops sa1100_rtc_ops = { 306static const struct rtc_class_ops sa1100_rtc_ops = {
307 .open = sa1100_rtc_open, 307 .open = sa1100_rtc_open,
308 .read_callback = sa1100_rtc_read_callback, 308 .read_callback = sa1100_rtc_read_callback,
309 .release = sa1100_rtc_release, 309 .release = sa1100_rtc_release,
diff --git a/drivers/rtc/rtc-sh.c b/drivers/rtc/rtc-sh.c
new file mode 100644
index 000000000000..d2ce0c8bb8f3
--- /dev/null
+++ b/drivers/rtc/rtc-sh.c
@@ -0,0 +1,467 @@
1/*
2 * SuperH On-Chip RTC Support
3 *
4 * Copyright (C) 2006 Paul Mundt
5 *
6 * Based on the old arch/sh/kernel/cpu/rtc.c by:
7 *
8 * Copyright (C) 2000 Philipp Rumpf <prumpf@tux.org>
9 * Copyright (C) 1999 Tetsuya Okada & Niibe Yutaka
10 *
11 * This file is subject to the terms and conditions of the GNU General Public
12 * License. See the file "COPYING" in the main directory of this archive
13 * for more details.
14 */
15#include <linux/module.h>
16#include <linux/kernel.h>
17#include <linux/bcd.h>
18#include <linux/rtc.h>
19#include <linux/init.h>
20#include <linux/platform_device.h>
21#include <linux/seq_file.h>
22#include <linux/interrupt.h>
23#include <linux/spinlock.h>
24#include <asm/io.h>
25
26#ifdef CONFIG_CPU_SH3
27#define rtc_reg_size sizeof(u16)
28#define RTC_BIT_INVERTED 0 /* No bug on SH7708, SH7709A */
29#elif defined(CONFIG_CPU_SH4)
30#define rtc_reg_size sizeof(u32)
31#define RTC_BIT_INVERTED 0x40 /* bug on SH7750, SH7750S */
32#endif
33
34#define RTC_REG(r) ((r) * rtc_reg_size)
35
36#define R64CNT RTC_REG(0)
37#define RSECCNT RTC_REG(1)
38#define RMINCNT RTC_REG(2)
39#define RHRCNT RTC_REG(3)
40#define RWKCNT RTC_REG(4)
41#define RDAYCNT RTC_REG(5)
42#define RMONCNT RTC_REG(6)
43#define RYRCNT RTC_REG(7)
44#define RSECAR RTC_REG(8)
45#define RMINAR RTC_REG(9)
46#define RHRAR RTC_REG(10)
47#define RWKAR RTC_REG(11)
48#define RDAYAR RTC_REG(12)
49#define RMONAR RTC_REG(13)
50#define RCR1 RTC_REG(14)
51#define RCR2 RTC_REG(15)
52
53/* RCR1 Bits */
54#define RCR1_CF 0x80 /* Carry Flag */
55#define RCR1_CIE 0x10 /* Carry Interrupt Enable */
56#define RCR1_AIE 0x08 /* Alarm Interrupt Enable */
57#define RCR1_AF 0x01 /* Alarm Flag */
58
59/* RCR2 Bits */
60#define RCR2_PEF 0x80 /* PEriodic interrupt Flag */
61#define RCR2_PESMASK 0x70 /* Periodic interrupt Set */
62#define RCR2_RTCEN 0x08 /* ENable RTC */
63#define RCR2_ADJ 0x04 /* ADJustment (30-second) */
64#define RCR2_RESET 0x02 /* Reset bit */
65#define RCR2_START 0x01 /* Start bit */
66
67struct sh_rtc {
68 void __iomem *regbase;
69 unsigned long regsize;
70 struct resource *res;
71 unsigned int alarm_irq, periodic_irq, carry_irq;
72 struct rtc_device *rtc_dev;
73 spinlock_t lock;
74};
75
76static irqreturn_t sh_rtc_interrupt(int irq, void *id, struct pt_regs *regs)
77{
78 struct platform_device *pdev = id;
79 struct sh_rtc *rtc = platform_get_drvdata(pdev);
80 unsigned int tmp, events = 0;
81
82 spin_lock(&rtc->lock);
83
84 tmp = readb(rtc->regbase + RCR1);
85
86 if (tmp & RCR1_AF)
87 events |= RTC_AF | RTC_IRQF;
88
89 tmp &= ~(RCR1_CF | RCR1_AF);
90
91 writeb(tmp, rtc->regbase + RCR1);
92
93 rtc_update_irq(&rtc->rtc_dev->class_dev, 1, events);
94
95 spin_unlock(&rtc->lock);
96
97 return IRQ_HANDLED;
98}
99
100static irqreturn_t sh_rtc_periodic(int irq, void *id, struct pt_regs *regs)
101{
102 struct sh_rtc *rtc = dev_get_drvdata(id);
103
104 spin_lock(&rtc->lock);
105
106 rtc_update_irq(&rtc->rtc_dev->class_dev, 1, RTC_PF | RTC_IRQF);
107
108 spin_unlock(&rtc->lock);
109
110 return IRQ_HANDLED;
111}
112
113static inline void sh_rtc_setpie(struct device *dev, unsigned int enable)
114{
115 struct sh_rtc *rtc = dev_get_drvdata(dev);
116 unsigned int tmp;
117
118 spin_lock_irq(&rtc->lock);
119
120 tmp = readb(rtc->regbase + RCR2);
121
122 if (enable) {
123 tmp &= ~RCR2_PESMASK;
124 tmp |= RCR2_PEF | (2 << 4);
125 } else
126 tmp &= ~(RCR2_PESMASK | RCR2_PEF);
127
128 writeb(tmp, rtc->regbase + RCR2);
129
130 spin_unlock_irq(&rtc->lock);
131}
132
133static inline void sh_rtc_setaie(struct device *dev, unsigned int enable)
134{
135 struct sh_rtc *rtc = dev_get_drvdata(dev);
136 unsigned int tmp;
137
138 spin_lock_irq(&rtc->lock);
139
140 tmp = readb(rtc->regbase + RCR1);
141
142 if (enable)
143 tmp |= RCR1_AIE;
144 else
145 tmp &= ~RCR1_AIE;
146
147 writeb(tmp, rtc->regbase + RCR1);
148
149 spin_unlock_irq(&rtc->lock);
150}
151
152static int sh_rtc_open(struct device *dev)
153{
154 struct sh_rtc *rtc = dev_get_drvdata(dev);
155 unsigned int tmp;
156 int ret;
157
158 tmp = readb(rtc->regbase + RCR1);
159 tmp &= ~RCR1_CF;
160 tmp |= RCR1_CIE;
161 writeb(tmp, rtc->regbase + RCR1);
162
163 ret = request_irq(rtc->periodic_irq, sh_rtc_periodic, SA_INTERRUPT,
164 "sh-rtc period", dev);
165 if (unlikely(ret)) {
166 dev_err(dev, "request period IRQ failed with %d, IRQ %d\n",
167 ret, rtc->periodic_irq);
168 return ret;
169 }
170
171 ret = request_irq(rtc->carry_irq, sh_rtc_interrupt, SA_INTERRUPT,
172 "sh-rtc carry", dev);
173 if (unlikely(ret)) {
174 dev_err(dev, "request carry IRQ failed with %d, IRQ %d\n",
175 ret, rtc->carry_irq);
176 free_irq(rtc->periodic_irq, dev);
177 goto err_bad_carry;
178 }
179
180 ret = request_irq(rtc->alarm_irq, sh_rtc_interrupt, SA_INTERRUPT,
181 "sh-rtc alarm", dev);
182 if (unlikely(ret)) {
183 dev_err(dev, "request alarm IRQ failed with %d, IRQ %d\n",
184 ret, rtc->alarm_irq);
185 goto err_bad_alarm;
186 }
187
188 return 0;
189
190err_bad_alarm:
191 free_irq(rtc->carry_irq, dev);
192err_bad_carry:
193 free_irq(rtc->periodic_irq, dev);
194
195 return ret;
196}
197
198static void sh_rtc_release(struct device *dev)
199{
200 struct sh_rtc *rtc = dev_get_drvdata(dev);
201
202 sh_rtc_setpie(dev, 0);
203
204 free_irq(rtc->periodic_irq, dev);
205 free_irq(rtc->carry_irq, dev);
206 free_irq(rtc->alarm_irq, dev);
207}
208
209static int sh_rtc_proc(struct device *dev, struct seq_file *seq)
210{
211 struct sh_rtc *rtc = dev_get_drvdata(dev);
212 unsigned int tmp;
213
214 tmp = readb(rtc->regbase + RCR1);
215 seq_printf(seq, "alarm_IRQ\t: %s\n",
216 (tmp & RCR1_AIE) ? "yes" : "no");
217 seq_printf(seq, "carry_IRQ\t: %s\n",
218 (tmp & RCR1_CIE) ? "yes" : "no");
219
220 tmp = readb(rtc->regbase + RCR2);
221 seq_printf(seq, "periodic_IRQ\t: %s\n",
222 (tmp & RCR2_PEF) ? "yes" : "no");
223
224 return 0;
225}
226
227static int sh_rtc_ioctl(struct device *dev, unsigned int cmd, unsigned long arg)
228{
229 unsigned int ret = -ENOIOCTLCMD;
230
231 switch (cmd) {
232 case RTC_PIE_OFF:
233 case RTC_PIE_ON:
234 sh_rtc_setpie(dev, cmd == RTC_PIE_ON);
235 ret = 0;
236 break;
237 case RTC_AIE_OFF:
238 case RTC_AIE_ON:
239 sh_rtc_setaie(dev, cmd == RTC_AIE_ON);
240 ret = 0;
241 break;
242 }
243
244 return ret;
245}
246
247static int sh_rtc_read_time(struct device *dev, struct rtc_time *tm)
248{
249 struct platform_device *pdev = to_platform_device(dev);
250 struct sh_rtc *rtc = platform_get_drvdata(pdev);
251 unsigned int sec128, sec2, yr, yr100, cf_bit;
252
253 do {
254 unsigned int tmp;
255
256 spin_lock_irq(&rtc->lock);
257
258 tmp = readb(rtc->regbase + RCR1);
259 tmp &= ~RCR1_CF; /* Clear CF-bit */
260 tmp |= RCR1_CIE;
261 writeb(tmp, rtc->regbase + RCR1);
262
263 sec128 = readb(rtc->regbase + R64CNT);
264
265 tm->tm_sec = BCD2BIN(readb(rtc->regbase + RSECCNT));
266 tm->tm_min = BCD2BIN(readb(rtc->regbase + RMINCNT));
267 tm->tm_hour = BCD2BIN(readb(rtc->regbase + RHRCNT));
268 tm->tm_wday = BCD2BIN(readb(rtc->regbase + RWKCNT));
269 tm->tm_mday = BCD2BIN(readb(rtc->regbase + RDAYCNT));
270 tm->tm_mon = BCD2BIN(readb(rtc->regbase + RMONCNT));
271
272#if defined(CONFIG_CPU_SH4)
273 yr = readw(rtc->regbase + RYRCNT);
274 yr100 = BCD2BIN(yr >> 8);
275 yr &= 0xff;
276#else
277 yr = readb(rtc->regbase + RYRCNT);
278 yr100 = BCD2BIN((yr == 0x99) ? 0x19 : 0x20);
279#endif
280
281 tm->tm_year = (yr100 * 100 + BCD2BIN(yr)) - 1900;
282
283 sec2 = readb(rtc->regbase + R64CNT);
284 cf_bit = readb(rtc->regbase + RCR1) & RCR1_CF;
285
286 spin_unlock_irq(&rtc->lock);
287 } while (cf_bit != 0 || ((sec128 ^ sec2) & RTC_BIT_INVERTED) != 0);
288
289#if RTC_BIT_INVERTED != 0
290 if ((sec128 & RTC_BIT_INVERTED))
291 tm->tm_sec--;
292#endif
293
294 dev_dbg(&dev, "%s: tm is secs=%d, mins=%d, hours=%d, "
295 "mday=%d, mon=%d, year=%d, wday=%d\n",
296 __FUNCTION__,
297 tm->tm_sec, tm->tm_min, tm->tm_hour,
298 tm->tm_mday, tm->tm_mon, tm->tm_year, tm->tm_wday);
299
300 if (rtc_valid_tm(tm) < 0)
301 dev_err(dev, "invalid date\n");
302
303 return 0;
304}
305
306static int sh_rtc_set_time(struct device *dev, struct rtc_time *tm)
307{
308 struct platform_device *pdev = to_platform_device(dev);
309 struct sh_rtc *rtc = platform_get_drvdata(pdev);
310 unsigned int tmp;
311 int year;
312
313 spin_lock_irq(&rtc->lock);
314
315 /* Reset pre-scaler & stop RTC */
316 tmp = readb(rtc->regbase + RCR2);
317 tmp |= RCR2_RESET;
318 writeb(tmp, rtc->regbase + RCR2);
319
320 writeb(BIN2BCD(tm->tm_sec), rtc->regbase + RSECCNT);
321 writeb(BIN2BCD(tm->tm_min), rtc->regbase + RMINCNT);
322 writeb(BIN2BCD(tm->tm_hour), rtc->regbase + RHRCNT);
323 writeb(BIN2BCD(tm->tm_wday), rtc->regbase + RWKCNT);
324 writeb(BIN2BCD(tm->tm_mday), rtc->regbase + RDAYCNT);
325 writeb(BIN2BCD(tm->tm_mon), rtc->regbase + RMONCNT);
326
327#ifdef CONFIG_CPU_SH3
328 year = tm->tm_year % 100;
329 writeb(BIN2BCD(year), rtc->regbase + RYRCNT);
330#else
331 year = (BIN2BCD((tm->tm_year + 1900) / 100) << 8) |
332 BIN2BCD(tm->tm_year % 100);
333 writew(year, rtc->regbase + RYRCNT);
334#endif
335
336 /* Start RTC */
337 tmp = readb(rtc->regbase + RCR2);
338 tmp &= ~RCR2_RESET;
339 tmp |= RCR2_RTCEN | RCR2_START;
340 writeb(tmp, rtc->regbase + RCR2);
341
342 spin_unlock_irq(&rtc->lock);
343
344 return 0;
345}
346
347static struct rtc_class_ops sh_rtc_ops = {
348 .open = sh_rtc_open,
349 .release = sh_rtc_release,
350 .ioctl = sh_rtc_ioctl,
351 .read_time = sh_rtc_read_time,
352 .set_time = sh_rtc_set_time,
353 .proc = sh_rtc_proc,
354};
355
356static int __devinit sh_rtc_probe(struct platform_device *pdev)
357{
358 struct sh_rtc *rtc;
359 struct resource *res;
360 int ret = -ENOENT;
361
362 rtc = kzalloc(sizeof(struct sh_rtc), GFP_KERNEL);
363 if (unlikely(!rtc))
364 return -ENOMEM;
365
366 spin_lock_init(&rtc->lock);
367
368 rtc->periodic_irq = platform_get_irq(pdev, 0);
369 if (unlikely(rtc->periodic_irq < 0)) {
370 dev_err(&pdev->dev, "No IRQ for period\n");
371 goto err_badres;
372 }
373
374 rtc->carry_irq = platform_get_irq(pdev, 1);
375 if (unlikely(rtc->carry_irq < 0)) {
376 dev_err(&pdev->dev, "No IRQ for carry\n");
377 goto err_badres;
378 }
379
380 rtc->alarm_irq = platform_get_irq(pdev, 2);
381 if (unlikely(rtc->alarm_irq < 0)) {
382 dev_err(&pdev->dev, "No IRQ for alarm\n");
383 goto err_badres;
384 }
385
386 res = platform_get_resource(pdev, IORESOURCE_IO, 0);
387 if (unlikely(res == NULL)) {
388 dev_err(&pdev->dev, "No IO resource\n");
389 goto err_badres;
390 }
391
392 rtc->regsize = res->end - res->start + 1;
393
394 rtc->res = request_mem_region(res->start, rtc->regsize, pdev->name);
395 if (unlikely(!rtc->res)) {
396 ret = -EBUSY;
397 goto err_badres;
398 }
399
400 rtc->regbase = (void __iomem *)rtc->res->start;
401 if (unlikely(!rtc->regbase)) {
402 ret = -EINVAL;
403 goto err_badmap;
404 }
405
406 rtc->rtc_dev = rtc_device_register("sh", &pdev->dev,
407 &sh_rtc_ops, THIS_MODULE);
408 if (IS_ERR(rtc)) {
409 ret = PTR_ERR(rtc->rtc_dev);
410 goto err_badmap;
411 }
412
413 platform_set_drvdata(pdev, rtc);
414
415 return 0;
416
417err_badmap:
418 release_resource(rtc->res);
419err_badres:
420 kfree(rtc);
421
422 return ret;
423}
424
425static int __devexit sh_rtc_remove(struct platform_device *pdev)
426{
427 struct sh_rtc *rtc = platform_get_drvdata(pdev);
428
429 if (likely(rtc->rtc_dev))
430 rtc_device_unregister(rtc->rtc_dev);
431
432 sh_rtc_setpie(&pdev->dev, 0);
433 sh_rtc_setaie(&pdev->dev, 0);
434
435 release_resource(rtc->res);
436
437 platform_set_drvdata(pdev, NULL);
438
439 kfree(rtc);
440
441 return 0;
442}
443static struct platform_driver sh_rtc_platform_driver = {
444 .driver = {
445 .name = "sh-rtc",
446 .owner = THIS_MODULE,
447 },
448 .probe = sh_rtc_probe,
449 .remove = __devexit_p(sh_rtc_remove),
450};
451
452static int __init sh_rtc_init(void)
453{
454 return platform_driver_register(&sh_rtc_platform_driver);
455}
456
457static void __exit sh_rtc_exit(void)
458{
459 platform_driver_unregister(&sh_rtc_platform_driver);
460}
461
462module_init(sh_rtc_init);
463module_exit(sh_rtc_exit);
464
465MODULE_DESCRIPTION("SuperH on-chip RTC driver");
466MODULE_AUTHOR("Paul Mundt <lethal@linux-sh.org>");
467MODULE_LICENSE("GPL");
diff --git a/drivers/rtc/rtc-sysfs.c b/drivers/rtc/rtc-sysfs.c
index 7c1f3d2e53c4..625637b84d33 100644
--- a/drivers/rtc/rtc-sysfs.c
+++ b/drivers/rtc/rtc-sysfs.c
@@ -116,7 +116,7 @@ static void __exit rtc_sysfs_exit(void)
116 class_interface_unregister(&rtc_sysfs_interface); 116 class_interface_unregister(&rtc_sysfs_interface);
117} 117}
118 118
119module_init(rtc_sysfs_init); 119subsys_initcall(rtc_sysfs_init);
120module_exit(rtc_sysfs_exit); 120module_exit(rtc_sysfs_exit);
121 121
122MODULE_AUTHOR("Alessandro Zummo <a.zummo@towertech.it>"); 122MODULE_AUTHOR("Alessandro Zummo <a.zummo@towertech.it>");
diff --git a/drivers/rtc/rtc-test.c b/drivers/rtc/rtc-test.c
index e1fa5fe7901f..bc4bd24508a2 100644
--- a/drivers/rtc/rtc-test.c
+++ b/drivers/rtc/rtc-test.c
@@ -75,7 +75,7 @@ static int test_rtc_ioctl(struct device *dev, unsigned int cmd,
75 } 75 }
76} 76}
77 77
78static struct rtc_class_ops test_rtc_ops = { 78static const struct rtc_class_ops test_rtc_ops = {
79 .proc = test_rtc_proc, 79 .proc = test_rtc_proc,
80 .read_time = test_rtc_read_time, 80 .read_time = test_rtc_read_time,
81 .set_time = test_rtc_set_time, 81 .set_time = test_rtc_set_time,
diff --git a/drivers/rtc/rtc-v3020.c b/drivers/rtc/rtc-v3020.c
index a40f400acff6..09b714f1cdc3 100644
--- a/drivers/rtc/rtc-v3020.c
+++ b/drivers/rtc/rtc-v3020.c
@@ -149,7 +149,7 @@ static int v3020_set_time(struct device *dev, struct rtc_time *dt)
149 return 0; 149 return 0;
150} 150}
151 151
152static struct rtc_class_ops v3020_rtc_ops = { 152static const struct rtc_class_ops v3020_rtc_ops = {
153 .read_time = v3020_read_time, 153 .read_time = v3020_read_time,
154 .set_time = v3020_set_time, 154 .set_time = v3020_set_time,
155}; 155};
@@ -169,9 +169,6 @@ static int rtc_probe(struct platform_device *pdev)
169 if (pdev->resource[0].flags != IORESOURCE_MEM) 169 if (pdev->resource[0].flags != IORESOURCE_MEM)
170 return -EBUSY; 170 return -EBUSY;
171 171
172 if (pdev == NULL)
173 return -EBUSY;
174
175 chip = kzalloc(sizeof *chip, GFP_KERNEL); 172 chip = kzalloc(sizeof *chip, GFP_KERNEL);
176 if (!chip) 173 if (!chip)
177 return -ENOMEM; 174 return -ENOMEM;
diff --git a/drivers/rtc/rtc-vr41xx.c b/drivers/rtc/rtc-vr41xx.c
index 596764fd29f5..58e5ed0aa127 100644
--- a/drivers/rtc/rtc-vr41xx.c
+++ b/drivers/rtc/rtc-vr41xx.c
@@ -296,7 +296,7 @@ static irqreturn_t rtclong1_interrupt(int irq, void *dev_id, struct pt_regs *reg
296 return IRQ_HANDLED; 296 return IRQ_HANDLED;
297} 297}
298 298
299static struct rtc_class_ops vr41xx_rtc_ops = { 299static const struct rtc_class_ops vr41xx_rtc_ops = {
300 .release = vr41xx_rtc_release, 300 .release = vr41xx_rtc_release,
301 .ioctl = vr41xx_rtc_ioctl, 301 .ioctl = vr41xx_rtc_ioctl,
302 .read_time = vr41xx_rtc_read_time, 302 .read_time = vr41xx_rtc_read_time,
diff --git a/drivers/rtc/rtc-x1205.c b/drivers/rtc/rtc-x1205.c
index 788b6d1f8f2f..522c69753bbf 100644
--- a/drivers/rtc/rtc-x1205.c
+++ b/drivers/rtc/rtc-x1205.c
@@ -460,7 +460,7 @@ static int x1205_rtc_proc(struct device *dev, struct seq_file *seq)
460 return 0; 460 return 0;
461} 461}
462 462
463static struct rtc_class_ops x1205_rtc_ops = { 463static const struct rtc_class_ops x1205_rtc_ops = {
464 .proc = x1205_rtc_proc, 464 .proc = x1205_rtc_proc,
465 .read_time = x1205_rtc_read_time, 465 .read_time = x1205_rtc_read_time,
466 .set_time = x1205_rtc_set_time, 466 .set_time = x1205_rtc_set_time,