diff options
author | Jon Mayo <jmayo@nvidia.com> | 2010-09-09 11:46:18 -0700 |
---|---|---|
committer | Varun Colbert <vcolbert@nvidia.com> | 2010-10-26 15:03:36 -0700 |
commit | 35e97aa59eaa0cc7233c100edc0aa3e7b4e1605e (patch) | |
tree | 743512854b2ce749bd92eb09c6ae52688b8ff1a8 /drivers | |
parent | dc9cea61b3333432d6c1d2003a1bdb9ce055f04a (diff) |
[arm/tegra] support RTC alarm interrupt in odm_kit
New API added to odm_kit to register a callback to use on RTC interrupt.
Supported added for RTC alarms in the max8907b PMU.
Bug 717253
Bug 734529
Change-Id: I34abebd7dd3caf4ef8923fcf651c50f6d245f6b4
Reviewed-on: http://git-master/r/7328
Reviewed-by: Krishna Reddy <vdumpa@nvidia.com>
Reviewed-by: Jonathan Mayo <jmayo@nvidia.com>
Tested-by: Jonathan Mayo <jmayo@nvidia.com>
Reviewed-by: Aleksandr Frid <afrid@nvidia.com>
Reviewed-by: Yu-Huan Hsu <yhsu@nvidia.com>
Reviewed-by: Varun Colbert <vcolbert@nvidia.com>
Tested-by: Varun Colbert <vcolbert@nvidia.com>
Diffstat (limited to 'drivers')
-rw-r--r-- | drivers/rtc/rtc-tegra-odm.c | 57 |
1 files changed, 49 insertions, 8 deletions
diff --git a/drivers/rtc/rtc-tegra-odm.c b/drivers/rtc/rtc-tegra-odm.c index 2a90d60b06b8..8a1c55737bfb 100644 --- a/drivers/rtc/rtc-tegra-odm.c +++ b/drivers/rtc/rtc-tegra-odm.c @@ -21,6 +21,7 @@ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ +#define NV_DEBUG 0 #include <linux/kernel.h> #include <linux/init.h> #include <linux/module.h> @@ -31,10 +32,14 @@ #include <linux/platform_device.h> #include "nvodm_pmu.h" -#define PMU_IOCTL_ENABLE 1 - /* Create a custom rtc structrue and move this to that structure */ static NvOdmPmuDeviceHandle hPmu = NULL; +static struct platform_device *tegra_rtc_pdev = NULL; + +static int tegra_rtc_ioctl(struct device *dev, unsigned int cmd, unsigned long arg) +{ + return -ENOIOCTLCMD; +} static int tegra_rtc_read_time(struct device *dev, struct rtc_time *tm) { @@ -71,7 +76,6 @@ static int tegra_rtc_set_time(struct device *dev, struct rtc_time *tm) return 0; } -#if (PMU_IOCTL_ENABLE) static int tegra_rtc_read_alarm(struct device *dev, struct rtc_wkalrm *wkalrm) { @@ -93,9 +97,14 @@ static int tegra_rtc_set_alarm(struct device *dev, struct rtc_wkalrm *wkalrm) NvU32 alarm_sec; struct rtc_time now_time; + printk("%s(): wkalrm->enabled=%d\n", __func__, wkalrm?wkalrm->enabled:-1); + pr_debug("wkalrm->enabled = %d\n", wkalrm->enabled); - if (wkalrm->enabled == 0) + if (wkalrm->enabled == 0) { + if(!NvOdmPmuWriteAlarm(hPmu, 0)) + return -EINVAL; return 0; + } if (!NvOdmPmuReadRtc(hPmu, &now)) { pr_debug("NvOdmPmuReadRtc failed\n"); @@ -119,20 +128,43 @@ static int tegra_rtc_set_alarm(struct device *dev, struct rtc_wkalrm *wkalrm) pr_debug("alarm_sec = %u\n", alarm_sec); - if(!NvOdmPmuWriteAlarm(hPmu, alarm_sec-now)) + if(!NvOdmPmuWriteAlarm(hPmu, alarm_sec)) return -EINVAL; return 0; } -#endif + +static NvBool tegra_rtc_alarm_interrupt(NvOdmPmuDeviceHandle hPmu) { + unsigned long events = 0; + struct rtc_device *rtc; + + rtc = tegra_rtc_pdev ? platform_get_drvdata(tegra_rtc_pdev) : NULL; + + pr_info("%s():enter.\n", __func__); + + /* Alarm set */ + events |= RTC_IRQF | RTC_AF; + + if (rtc) + rtc_update_irq(rtc, 1, events); + + return NV_TRUE; +} + +static int tegra_rtc_proc(struct device *dev, struct seq_file *seq) +{ + if (!dev || !dev->driver) + return 0; + return seq_printf(seq, "name\t\t: %s\n", dev_name(dev)); +} static struct rtc_class_ops tegra_rtc_ops = { + .ioctl = tegra_rtc_ioctl, .read_time = tegra_rtc_read_time, .set_time = tegra_rtc_set_time, -#if (PMU_IOCTL_ENABLE) .read_alarm = tegra_rtc_read_alarm, .set_alarm = tegra_rtc_set_alarm, -#endif + .proc = tegra_rtc_proc, }; static int __init tegra_rtc_probe(struct platform_device *pdev) @@ -156,6 +188,7 @@ static int __init tegra_rtc_probe(struct platform_device *pdev) return -EINVAL; } + device_init_wakeup(&pdev->dev, 1); rtc = rtc_device_register(pdev->name, &pdev->dev, &tegra_rtc_ops, THIS_MODULE); @@ -168,6 +201,10 @@ static int __init tegra_rtc_probe(struct platform_device *pdev) } platform_set_drvdata(pdev, rtc); + tegra_rtc_pdev = pdev; + + NvOdmPmuAlarmHandlerSet(hPmu, tegra_rtc_alarm_interrupt); + return 0; } @@ -183,11 +220,15 @@ static int __exit tegra_rtc_remove(struct platform_device *pdev) static int tegra_rtc_suspend(struct platform_device *pdev, pm_message_t state) { + NvOdmPmuSuspendRtc(hPmu); + return 0; } static int tegra_rtc_resume(struct platform_device *pdev) { + NvOdmPmuResumeRtc(hPmu); + return 0; } |