static inline void omap_init_irda(void) {}
#endif
+#if defined(CONFIG_OMAP_RTC) || defined(CONFIG_OMAP_RTC)
+
+#define OMAP_RTC_BASE 0xfffb4800
+
+static struct resource rtc_resources[] = {
+ {
+ .start = OMAP_RTC_BASE,
+ .end = OMAP_RTC_BASE + 0x5f,
+ .flags = IORESOURCE_MEM,
+ },
+ {
+ .start = INT_RTC_TIMER,
+ .flags = IORESOURCE_IRQ,
+ },
+ {
+ .start = INT_RTC_ALARM,
+ .flags = IORESOURCE_IRQ,
+ },
+};
+
+static struct platform_device omap_rtc_device = {
+ .name = "omap_rtc",
+ .id = -1,
+ .dev = {
+ .release = omap_nop_release,
+ },
+ .num_resources = ARRAY_SIZE(rtc_resources),
+ .resource = rtc_resources,
+};
+
+static void omap_init_rtc(void)
+{
+ (void) platform_device_register(&omap_rtc_device);
+}
+#else
+static inline void omap_init_rtc(void) {}
+#endif
+
/*-------------------------------------------------------------------------*/
#if defined(CONFIG_MMC_OMAP) || defined(CONFIG_MMC_OMAP_MODULE)
omap_init_i2c();
omap_init_irda();
omap_init_mmc();
+ omap_init_rtc();
omap_init_wdt();
return 0;
.fops = &rtc_fops,
};
-static int __init rtc_init(void)
+static int __init omap_rtc_probe(struct device *dev)
{
- if (!request_region(OMAP_RTC_VIRT_BASE, OMAP_RTC_SIZE,
- rtc_dev.name)) {
+ struct platform_device *pdev = to_platform_device(dev);
+ struct resource *res, *mem;
+
+ res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
+ if (res)
+ mem = request_mem_region(res->start,
+ res->end - res->start + 1,
+ pdev->name);
+ else
+ mem = NULL;
+ if (!mem) {
pr_debug("%s: RTC registers at %x are not free.\n",
- rtc_dev.name, OMAP_RTC_VIRT_BASE);
+ pdev->name, OMAP_RTC_BASE);
return -EBUSY;
}
+ dev_set_drvdata(dev, mem);
if (CMOS_READ(OMAP_RTC_STATUS_REG) & OMAP_RTC_STATUS_POWER_UP) {
pr_info("%s: RTC power up reset detected.\n",
- rtc_dev.name);
+ pdev->name);
/* Clear OMAP_RTC_STATUS_POWER_UP */
CMOS_WRITE(OMAP_RTC_STATUS_POWER_UP, OMAP_RTC_STATUS_REG);
}
if (CMOS_READ(OMAP_RTC_STATUS_REG) & OMAP_RTC_STATUS_ALARM) {
pr_debug("%s: Clearing RTC ALARM interrupt.\n",
- rtc_dev.name);
+ pdev->name);
/* Clear OMAP_RTC_STATUS_ALARM */
CMOS_WRITE(OMAP_RTC_STATUS_ALARM, OMAP_RTC_STATUS_REG);
}
if (request_irq(INT_RTC_TIMER, rtc_interrupt, SA_INTERRUPT,
- rtc_dev.name, NULL)) {
+ pdev->name, NULL)) {
pr_debug("%s: RTC timer interrupt IRQ%d is not free.\n",
- rtc_dev.name, INT_RTC_TIMER);
+ pdev->name, INT_RTC_TIMER);
goto fail;
}
if (request_irq(INT_RTC_ALARM, rtc_interrupt, SA_INTERRUPT,
- rtc_dev.name, NULL)) {
+ pdev->name, NULL)) {
pr_debug("%s: RTC alarm interrupt IRQ%d is not free.\n",
- rtc_dev.name, INT_RTC_ALARM);
+ pdev->name, INT_RTC_ALARM);
free_irq(INT_RTC_TIMER, NULL);
goto fail;
}
/* On boards with split power, RTC_ON_NOFF resets all but the RTC */
if (!(CMOS_READ(OMAP_RTC_CTRL_REG) & OMAP_RTC_CTRL_STOP)) {
- pr_info("%s: Enabling RTC.\n", rtc_dev.name);
+ pr_info("%s: Enabling RTC.\n", pdev->name);
CMOS_WRITE(OMAP_RTC_CTRL_STOP, OMAP_RTC_CTRL_REG);
} else
- pr_info("%s: RTC already running.\n", rtc_dev.name);
+ pr_info("%s: RTC already running.\n", pdev->name);
spin_lock_init(&rtc_lock);
misc_register(&rtc_dev);
return 0;
fail:
- release_region(OMAP_RTC_VIRT_BASE, OMAP_RTC_SIZE);
+ release_resource(mem);
return -EIO;
}
-static void __exit rtc_exit (void)
+static int __exit omap_rtc_remove(struct device *dev)
{
free_irq (INT_RTC_TIMER, NULL);
free_irq (INT_RTC_ALARM, NULL);
remove_proc_entry ("driver/rtc", NULL);
misc_deregister(&rtc_dev);
- release_region (OMAP_RTC_VIRT_BASE, OMAP_RTC_SIZE);
+ release_resource(dev_get_drvdata(dev));
+ return 0;
}
/*
spin_unlock_irq(&rtc_lock);
}
+static struct device_driver omap_rtc_driver = {
+ .name = "omap_rtc",
+ .bus = &platform_bus_type,
+ .probe = omap_rtc_probe,
+ .remove = __exit_p(omap_rtc_remove),
+};
+
+static int __init rtc_init(void)
+{
+ return driver_register(&omap_rtc_driver);
+}
+
+static void __exit rtc_exit(void)
+{
+ driver_unregister(&omap_rtc_driver);
+}
+
module_init(rtc_init);
module_exit(rtc_exit);