alarm: port from 2818, fix shutdown bug

try to fix this bug:
Unable to handle kernel paging request at virtual address 0fff1004
pgd = ce794000
[0fff1004] *pgd=00000000
Internal error: Oops: 5 [#1] PREEMPT
last sysfs file: /sys/power/wake_lock
Modules linked in:
CPU: 0    Not tainted  (2.6.32.27 #1)
PC is at rb_erase+0xf4/0x344
LR is at __remove_hrtimer+0xa4/0xb0
pc : [<c054d030>]    lr : [<c0463bec>]    psr: 20000193
sp : ccc1dda8  ip : c0876af8  fp : 00000000
r10: 00000000  r9 : ccc1c000  r8 : c04290c4
r7 : 00000001  r6 : 00000000  r5 : c0876b00  r4 : 0fff0ffc
r3 : 00000000  r2 : 00000000  r1 : 00000001  r0 : c124fae8
Flags: nzCv  IRQs off  FIQs on  Mode SVC_32  ISA ARM  Segment user
Control: 10c5387d  Table: 6e794019  DAC: 00000015

[<c054d030>] (rb_erase+0xf4/0x344) from [<c0463bec>] (__remove_hrtimer+0xa4/0xb0)
[<c0463bec>] (__remove_hrtimer+0xa4/0xb0) from [<c0463c5c>] (hrtimer_try_to_cancel+0x64/0xac)
[<c0463c5c>] (hrtimer_try_to_cancel+0x64/0xac) from [<c0463cb4>] (hrtimer_cancel+0x10/0x20)
[<c0463cb4>] (hrtimer_cancel+0x10/0x20) from [<c060e25c>] (alarm_shutdown+0x7c/0x270)
[<c060e25c>] (alarm_shutdown+0x7c/0x270) from [<c0581fe0>] (platform_drv_shutdown+0x18/0x1c)
[<c0581fe0>] (platform_drv_shutdown+0x18/0x1c) from [<c057df90>] (device_shutdown+0x58/0xa0)
[<c057df90>] (device_shutdown+0x58/0xa0) from [<c045b75c>] (kernel_power_off+0xc/0x3c)
[<c045b75c>] (kernel_power_off+0xc/0x3c) from [<c045ba50>] (sys_reboot+0x14c/0x22c)
[<c045ba50>] (sys_reboot+0x14c/0x22c) from [<c0428f40>] (ret_fast_syscall+0x0/0x2c)
This commit is contained in:
黄涛 2011-04-26 20:49:01 +08:00
parent a8c20e9e77
commit f86b8aa7d8

View File

@ -419,6 +419,7 @@ static int alarm_suspend(struct platform_device *pdev, pm_message_t state)
if (rtc_current_time + 1 >= rtc_alarm_time) {
pr_alarm(SUSPEND, "alarm about to go off\n");
memset(&rtc_alarm, 0, sizeof(rtc_alarm));
rtc_time_to_tm(0, &rtc_alarm.time);
rtc_alarm.enabled = 0;
rtc_set_alarm(alarm_rtc_dev, &rtc_alarm);
@ -444,6 +445,7 @@ static int alarm_resume(struct platform_device *pdev)
pr_alarm(SUSPEND, "alarm_resume(%p)\n", pdev);
memset(&alarm, 0, sizeof(alarm));
rtc_time_to_tm(0, &alarm.time);
alarm.enabled = 0;
rtc_set_alarm(alarm_rtc_dev, &alarm);
@ -457,6 +459,18 @@ static int alarm_resume(struct platform_device *pdev)
return 0;
}
static void alarm_shutdown(struct platform_device *pdev)
{
struct rtc_wkalrm alarm;
pr_alarm(FLOW, "alarm_shutdown(%p)\n", pdev);
memset(&alarm, 0, sizeof(alarm));
rtc_time_to_tm(0, &alarm.time);
alarm.enabled = 0;
rtc_set_alarm(alarm_rtc_dev, &alarm);
}
static struct rtc_task alarm_rtc_task = {
.func = alarm_triggered_func
};
@ -516,6 +530,7 @@ static struct class_interface rtc_alarm_interface = {
static struct platform_driver alarm_driver = {
.suspend = alarm_suspend,
.resume = alarm_resume,
.shutdown = alarm_shutdown,
.driver = {
.name = "alarm"
}