From 5b23a8e83112548d4c06e2f4b46aa20bd38d26d5 Mon Sep 17 00:00:00 2001 From: Corinna Vinschen Date: Mon, 21 Jan 2019 22:52:39 +0100 Subject: [PATCH] Cygwin: timerfd: fix gettime - split into to __try/__except blocks to make sure leave_critical_section is always called when required. - Actually fill time_spec in settime so it_interval is returned correctly. - Return all 0 if timer is disarmed. Signed-off-by: Corinna Vinschen --- winsup/cygwin/timerfd.cc | 29 ++++++++++++++++++++++------- 1 file changed, 22 insertions(+), 7 deletions(-) diff --git a/winsup/cygwin/timerfd.cc b/winsup/cygwin/timerfd.cc index a03749a60..295716f46 100644 --- a/winsup/cygwin/timerfd.cc +++ b/winsup/cygwin/timerfd.cc @@ -502,13 +502,26 @@ timerfd_tracker::gettime (struct itimerspec *curr_value) ret = -EBADF; __leave; } - LONG64 next_relative_exp = get_exp_ts () - get_clock_now (); - curr_value->it_value.tv_sec = next_relative_exp / NS100PERSEC; - next_relative_exp -= curr_value->it_value.tv_sec * NS100PERSEC; - curr_value->it_value.tv_nsec = next_relative_exp - * (NSPERSEC / NS100PERSEC); - curr_value->it_interval = time_spec ().it_interval; - leave_critical_section (); + } + __except (NO_ERROR) + { + return -EFAULT; + } + __endtry + + __try + { + if (IsEventSignalled (tfd_shared->disarm_evt ())) + *curr_value = time_spec (); + else + { + LONG64 next_relative_exp = get_exp_ts () - get_clock_now (); + curr_value->it_value.tv_sec = next_relative_exp / NS100PERSEC; + next_relative_exp -= curr_value->it_value.tv_sec * NS100PERSEC; + curr_value->it_value.tv_nsec = next_relative_exp + * (NSPERSEC / NS100PERSEC); + curr_value->it_interval = time_spec ().it_interval; + } ret = 0; } __except (NO_ERROR) @@ -516,6 +529,7 @@ timerfd_tracker::gettime (struct itimerspec *curr_value) ret = -EFAULT; } __endtry + leave_critical_section (); return ret; } @@ -559,6 +573,7 @@ timerfd_shared::arm_timer (int flags, const struct itimerspec *new_value) ts += get_clock_now (); } set_exp_ts (ts); + time_spec () = *new_value; /* TODO: CLOCK_REALTIME_ALARM / CLOCK_BOOTTIME_ALARM Note: Advanced Power Settings -> Sleep -> Allow Wake Timers since W10 1709 */