diff options
Diffstat (limited to 'kernel/time/alarmtimer.c')
-rw-r--r-- | kernel/time/alarmtimer.c | 34 |
1 files changed, 23 insertions, 11 deletions
diff --git a/kernel/time/alarmtimer.c b/kernel/time/alarmtimer.c index 4aec4a457431..a7077d3ae52f 100644 --- a/kernel/time/alarmtimer.c +++ b/kernel/time/alarmtimer.c | |||
@@ -464,18 +464,26 @@ static enum alarmtimer_type clock2alarm(clockid_t clockid) | |||
464 | static enum alarmtimer_restart alarm_handle_timer(struct alarm *alarm, | 464 | static enum alarmtimer_restart alarm_handle_timer(struct alarm *alarm, |
465 | ktime_t now) | 465 | ktime_t now) |
466 | { | 466 | { |
467 | unsigned long flags; | ||
467 | struct k_itimer *ptr = container_of(alarm, struct k_itimer, | 468 | struct k_itimer *ptr = container_of(alarm, struct k_itimer, |
468 | it.alarm.alarmtimer); | 469 | it.alarm.alarmtimer); |
469 | if (posix_timer_event(ptr, 0) != 0) | 470 | enum alarmtimer_restart result = ALARMTIMER_NORESTART; |
470 | ptr->it_overrun++; | 471 | |
472 | spin_lock_irqsave(&ptr->it_lock, flags); | ||
473 | if ((ptr->it_sigev_notify & ~SIGEV_THREAD_ID) != SIGEV_NONE) { | ||
474 | if (posix_timer_event(ptr, 0) != 0) | ||
475 | ptr->it_overrun++; | ||
476 | } | ||
471 | 477 | ||
472 | /* Re-add periodic timers */ | 478 | /* Re-add periodic timers */ |
473 | if (ptr->it.alarm.interval.tv64) { | 479 | if (ptr->it.alarm.interval.tv64) { |
474 | ptr->it_overrun += alarm_forward(alarm, now, | 480 | ptr->it_overrun += alarm_forward(alarm, now, |
475 | ptr->it.alarm.interval); | 481 | ptr->it.alarm.interval); |
476 | return ALARMTIMER_RESTART; | 482 | result = ALARMTIMER_RESTART; |
477 | } | 483 | } |
478 | return ALARMTIMER_NORESTART; | 484 | spin_unlock_irqrestore(&ptr->it_lock, flags); |
485 | |||
486 | return result; | ||
479 | } | 487 | } |
480 | 488 | ||
481 | /** | 489 | /** |
@@ -541,18 +549,22 @@ static int alarm_timer_create(struct k_itimer *new_timer) | |||
541 | * @new_timer: k_itimer pointer | 549 | * @new_timer: k_itimer pointer |
542 | * @cur_setting: itimerspec data to fill | 550 | * @cur_setting: itimerspec data to fill |
543 | * | 551 | * |
544 | * Copies the itimerspec data out from the k_itimer | 552 | * Copies out the current itimerspec data |
545 | */ | 553 | */ |
546 | static void alarm_timer_get(struct k_itimer *timr, | 554 | static void alarm_timer_get(struct k_itimer *timr, |
547 | struct itimerspec *cur_setting) | 555 | struct itimerspec *cur_setting) |
548 | { | 556 | { |
549 | memset(cur_setting, 0, sizeof(struct itimerspec)); | 557 | ktime_t relative_expiry_time = |
558 | alarm_expires_remaining(&(timr->it.alarm.alarmtimer)); | ||
559 | |||
560 | if (ktime_to_ns(relative_expiry_time) > 0) { | ||
561 | cur_setting->it_value = ktime_to_timespec(relative_expiry_time); | ||
562 | } else { | ||
563 | cur_setting->it_value.tv_sec = 0; | ||
564 | cur_setting->it_value.tv_nsec = 0; | ||
565 | } | ||
550 | 566 | ||
551 | cur_setting->it_interval = | 567 | cur_setting->it_interval = ktime_to_timespec(timr->it.alarm.interval); |
552 | ktime_to_timespec(timr->it.alarm.interval); | ||
553 | cur_setting->it_value = | ||
554 | ktime_to_timespec(timr->it.alarm.alarmtimer.node.expires); | ||
555 | return; | ||
556 | } | 568 | } |
557 | 569 | ||
558 | /** | 570 | /** |