drivers/timers: Simplify the error handling in arch rtc/alarm/timer wrapper

This commit is contained in:
Xiang Xiao 2018-11-08 12:06:44 -06:00 committed by Gregory Nutt
parent 414ace8f46
commit 2e8ffd8cc6
3 changed files with 120 additions and 119 deletions

View File

@ -43,8 +43,6 @@
#include <nuttx/clock.h> #include <nuttx/clock.h>
#include <nuttx/timers/arch_alarm.h> #include <nuttx/timers/arch_alarm.h>
#include <string.h>
/**************************************************************************** /****************************************************************************
* Pre-processor Definitions * Pre-processor Definitions
****************************************************************************/ ****************************************************************************/
@ -248,52 +246,57 @@ void up_alarm_set_lowerhalf(FAR struct oneshot_lowerhalf_s *lower)
#ifdef CONFIG_CLOCK_TIMEKEEPING #ifdef CONFIG_CLOCK_TIMEKEEPING
int up_timer_getcounter(FAR uint64_t *cycles) int up_timer_getcounter(FAR uint64_t *cycles)
{ {
struct timespec now; int ret = -EAGAIN;
if (!g_oneshot_lower) if (g_oneshot_lower != NULL)
{ {
*cycles = 0; struct timespec now;
return 0;
ret = ONESHOT_CURRENT(g_oneshot_lower, &now);
if (ret == 0)
{
*cycles = timespec_to_usec(&now) / USEC_PER_TICK;
}
} }
ONESHOT_CURRENT(g_oneshot_lower, &now); return ret;
*cycles = timespec_to_usec(&now) / USEC_PER_TICK;
return 0;
} }
void up_timer_getmask(FAR uint64_t *mask) void up_timer_getmask(FAR uint64_t *mask)
{ {
struct timespec maxts; *mask = 0;
uint64_t maxticks = 0;
if (g_oneshot_lower) if (g_oneshot_lower != NULL)
{ {
struct timespec maxts;
uint64_t maxticks;
ONESHOT_MAX_DELAY(g_oneshot_lower, &maxts); ONESHOT_MAX_DELAY(g_oneshot_lower, &maxts);
maxticks = timespec_to_usec(&maxts) / USEC_PER_TICK; maxticks = timespec_to_usec(&maxts) / USEC_PER_TICK;
}
*mask = 0; for(; ; )
while (1)
{
uint64_t next = (*mask << 1) | 1;
if (next > maxticks)
{ {
break; uint64_t next = (*mask << 1) | 1;
if (next > maxticks)
{
break;
}
*mask = next;
} }
*mask = next; }
}
} }
#elif defined(CONFIG_SCHED_TICKLESS) #elif defined(CONFIG_SCHED_TICKLESS)
int up_timer_gettime(FAR struct timespec *ts) int up_timer_gettime(FAR struct timespec *ts)
{ {
if (!g_oneshot_lower) int ret = -EAGAIN;
if (g_oneshot_lower != NULL)
{ {
memset(ts, 0, sizeof(*ts)); ret = ONESHOT_CURRENT(g_oneshot_lower, ts);
return 0;
} }
ONESHOT_CURRENT(g_oneshot_lower, ts); return ret;
return 0;
} }
#endif #endif
@ -334,14 +337,15 @@ int up_timer_gettime(FAR struct timespec *ts)
#ifdef CONFIG_SCHED_TICKLESS #ifdef CONFIG_SCHED_TICKLESS
int up_alarm_cancel(FAR struct timespec *ts) int up_alarm_cancel(FAR struct timespec *ts)
{ {
if (!g_oneshot_lower) int ret = -EAGAIN;
if (g_oneshot_lower != NULL)
{ {
return -EAGAIN; ret = ONESHOT_CANCEL(g_oneshot_lower, ts);
ONESHOT_CURRENT(g_oneshot_lower, ts);
} }
ONESHOT_CANCEL(g_oneshot_lower, ts); return ret;
ONESHOT_CURRENT(g_oneshot_lower, ts);
return 0;
} }
#endif #endif
@ -372,18 +376,19 @@ int up_alarm_cancel(FAR struct timespec *ts)
#ifdef CONFIG_SCHED_TICKLESS #ifdef CONFIG_SCHED_TICKLESS
int up_alarm_start(FAR const struct timespec *ts) int up_alarm_start(FAR const struct timespec *ts)
{ {
struct timespec now; int ret = -EAGAIN;
struct timespec delta;
if (!g_oneshot_lower) if (g_oneshot_lower != NULL)
{ {
return -EAGAIN; struct timespec now;
struct timespec delta;
ONESHOT_CURRENT(g_oneshot_lower, &now);
clock_timespec_subtract(ts, &now, &delta);
ret = ONESHOT_START(g_oneshot_lower, oneshot_callback, NULL, &delta);
} }
ONESHOT_CURRENT(g_oneshot_lower, &now); return ret;
clock_timespec_subtract(ts, &now, &delta);
ONESHOT_START(g_oneshot_lower, oneshot_callback, NULL, &delta);
return 0;
} }
#endif #endif
@ -413,11 +418,11 @@ void up_mdelay(unsigned int milliseconds)
void up_udelay(useconds_t microseconds) void up_udelay(useconds_t microseconds)
{ {
if (g_oneshot_lower) if (g_oneshot_lower != NULL)
{ {
udelay_accurate(microseconds); udelay_accurate(microseconds);
} }
else /* oneshot timer doesn't init yet */ else /* Oneshot timer hasn't been initialized yet */
{ {
udelay_coarse(microseconds); udelay_coarse(microseconds);
} }

View File

@ -42,8 +42,6 @@
#include <nuttx/arch.h> #include <nuttx/arch.h>
#include <nuttx/timers/arch_rtc.h> #include <nuttx/timers/arch_rtc.h>
#include <string.h>
/**************************************************************************** /****************************************************************************
* Private Data * Private Data
****************************************************************************/ ****************************************************************************/
@ -94,17 +92,16 @@ void up_rtc_set_lowerhalf(FAR struct rtc_lowerhalf_s *lower)
#ifndef CONFIG_RTC_HIRES #ifndef CONFIG_RTC_HIRES
time_t up_rtc_time(void) time_t up_rtc_time(void)
{ {
struct rtc_time rtctime;
time_t time = 0; time_t time = 0;
if (!g_rtc_lower) if (g_rtc_lower != NULL)
{ {
return 0; struct rtc_time rtctime;
}
if (g_rtc_lower->ops->rdtime(g_rtc_lower, &rtctime) == 0) if (g_rtc_lower->ops->rdtime(g_rtc_lower, &rtctime) == 0)
{ {
time = mktime((FAR struct tm *)&rtctime); time = mktime((FAR struct tm *)&rtctime);
}
} }
return time; return time;
@ -130,20 +127,18 @@ time_t up_rtc_time(void)
#ifdef CONFIG_RTC_HIRES #ifdef CONFIG_RTC_HIRES
int up_rtc_gettime(FAR struct timespec *tp) int up_rtc_gettime(FAR struct timespec *tp)
{ {
struct rtc_time rtctime; int ret = -EAGAIN;
int ret;
if (!g_rtc_lower) if (g_rtc_lower != NULL)
{ {
memset(tp, 0, sizeof(*tp)); struct rtc_time rtctime;
return 0;
}
ret = g_rtc_lower->ops->rdtime(g_rtc_lower, &rtctime); ret = g_rtc_lower->ops->rdtime(g_rtc_lower, &rtctime);
if (ret == 0) if (ret == 0)
{ {
tp->tv_sec = mktime((FAR struct tm *)&rtctime); tp->tv_sec = mktime((FAR struct tm *)&rtctime);
tp->tv_nsec = rtctime.tm_nsec; tp->tv_nsec = rtctime.tm_nsec;
}
} }
return ret; return ret;
@ -176,19 +171,17 @@ int up_rtc_gettime(FAR struct timespec *tp)
#ifdef CONFIG_RTC_DATETIME #ifdef CONFIG_RTC_DATETIME
int up_rtc_getdatetime(FAR struct tm *tp) int up_rtc_getdatetime(FAR struct tm *tp)
{ {
struct rtc_time rtctime; int ret = -EAGAIN;
int ret;
if (!g_rtc_lower) if (g_rtc_lower != NULL)
{ {
memset(tp, 0, sizeof(*tp)); struct rtc_time rtctime;
return 0;
}
ret = g_rtc_lower->ops->rdtime(g_rtc_lower, &rtctime); ret = g_rtc_lower->ops->rdtime(g_rtc_lower, &rtctime);
if (ret == 0) if (ret == 0)
{ {
*tp = *((FAR struct tm *)&rtctime); *tp = *((FAR struct tm *)&rtctime);
}
} }
return ret; return ret;
@ -211,8 +204,8 @@ int up_rtc_getdatetime(FAR struct tm *tp)
* stop system timer. * stop system timer.
* *
* Input Parameters: * Input Parameters:
* tp - The location to return the high resolution time value. * tp - The location to return the high resolution time value.
* nsec - The location to return the subsecond time value. * nsec - The location to return the sub-second time value.
* *
* Returned Value: * Returned Value:
* Zero (OK) on success; a negated errno on failure * Zero (OK) on success; a negated errno on failure
@ -222,21 +215,18 @@ int up_rtc_getdatetime(FAR struct tm *tp)
#if defined(CONFIG_RTC_DATETIME) && defined(CONFIG_ARCH_HAVE_RTC_SUBSECONDS) #if defined(CONFIG_RTC_DATETIME) && defined(CONFIG_ARCH_HAVE_RTC_SUBSECONDS)
int up_rtc_getdatetime_with_subseconds(FAR struct tm *tp, FAR long *nsec) int up_rtc_getdatetime_with_subseconds(FAR struct tm *tp, FAR long *nsec)
{ {
struct rtc_time rtctime; int ret = -EAGAIN;
int ret;
if (!g_rtc_lower) if (g_rtc_lower != NULL)
{ {
memset(tp, 0, sizeof(*tp)); struct rtc_time rtctime;
*nsec = 0;
return 0;
}
ret = g_rtc_lower->ops->rdtime(g_rtc_lower, &rtctime); ret = g_rtc_lower->ops->rdtime(g_rtc_lower, &rtctime);
if (ret == 0) if (ret == 0)
{ {
*tp = *((FAR struct tm *)&rtctime); *tp = *((FAR struct tm *)&rtctime);
*nsec = rtctime.tm_nsec; *nsec = rtctime.tm_nsec;
}
} }
return ret; return ret;
@ -260,17 +250,18 @@ int up_rtc_getdatetime_with_subseconds(FAR struct tm *tp, FAR long *nsec)
int up_rtc_settime(FAR const struct timespec *tp) int up_rtc_settime(FAR const struct timespec *tp)
{ {
struct rtc_time rtctime; int ret = -EAGAIN;
if (!g_rtc_lower) if (g_rtc_lower != NULL)
{ {
return -EAGAIN; struct rtc_time rtctime;
gmtime_r(&tp->tv_sec, (FAR struct tm *)&rtctime);
#if defined(CONFIG_RTC_HIRES) || defined(CONFIG_ARCH_HAVE_RTC_SUBSECONDS)
rtctime.tm_nsec = tp->tv_nsec;
#endif
ret = g_rtc_lower->ops->settime(g_rtc_lower, &rtctime);
} }
gmtime_r(&tp->tv_sec, (FAR struct tm *)&rtctime); return ret;
#if defined(CONFIG_RTC_HIRES) || defined(CONFIG_ARCH_HAVE_RTC_SUBSECONDS)
rtctime.tm_nsec = tp->tv_nsec;
#endif
return g_rtc_lower->ops->settime(g_rtc_lower, &rtctime);
} }

View File

@ -43,8 +43,6 @@
#include <nuttx/clock.h> #include <nuttx/clock.h>
#include <nuttx/timers/arch_timer.h> #include <nuttx/timers/arch_timer.h>
#include <string.h>
/**************************************************************************** /****************************************************************************
* Pre-processor Definitions * Pre-processor Definitions
****************************************************************************/ ****************************************************************************/
@ -217,8 +215,8 @@ static bool timer_callback(FAR uint32_t *next_interval_us, FAR void *arg)
struct timer_status_s status; struct timer_status_s status;
uint32_t next_interval; uint32_t next_interval;
g_timer.timebase += *next_interval_us; g_timer.timebase += *next_interval_us;
next_interval = g_timer.maxtimeout; next_interval = g_timer.maxtimeout;
g_timer.next_interval = &next_interval; g_timer.next_interval = &next_interval;
sched_timer_expiration(); sched_timer_expiration();
g_timer.next_interval = NULL; g_timer.next_interval = NULL;
@ -229,6 +227,7 @@ static bool timer_callback(FAR uint32_t *next_interval_us, FAR void *arg)
g_timer.timebase += status.timeout - status.timeleft; g_timer.timebase += status.timeout - status.timeleft;
*next_interval_us = next_interval; *next_interval_us = next_interval;
} }
#else #else
g_timer.timebase += USEC_PER_TICK; g_timer.timebase += USEC_PER_TICK;
sched_process_timer(); sched_process_timer();
@ -263,7 +262,7 @@ void up_timer_set_lowerhalf(FAR struct timer_lowerhalf_s *lower)
* *
* Description: * Description:
* Return the elapsed time since power-up (or, more correctly, since * Return the elapsed time since power-up (or, more correctly, since
* the archtecture-specific timer was initialized). This function is * the architecture-specific timer was initialized). This function is
* functionally equivalent to: * functionally equivalent to:
* *
* int clock_gettime(clockid_t clockid, FAR struct timespec *ts); * int clock_gettime(clockid_t clockid, FAR struct timespec *ts);
@ -294,14 +293,15 @@ void up_timer_set_lowerhalf(FAR struct timer_lowerhalf_s *lower)
#ifdef CONFIG_CLOCK_TIMEKEEPING #ifdef CONFIG_CLOCK_TIMEKEEPING
int up_timer_getcounter(FAR uint64_t *cycles) int up_timer_getcounter(FAR uint64_t *cycles)
{ {
if (!g_timer.lower) int ret = -EAGAIN;
if (g_timer.lower != NULL)
{ {
*cycles = 0; *cycles = current_usec() / USEC_PER_TICK;
return 0; ret = 0;
} }
*cycles = current_usec() / USEC_PER_TICK; return ret;
return 0;
} }
void up_timer_getmask(FAR uint64_t *mask) void up_timer_getmask(FAR uint64_t *mask)
@ -322,14 +322,15 @@ void up_timer_getmask(FAR uint64_t *mask)
#elif defined(CONFIG_SCHED_TICKLESS) #elif defined(CONFIG_SCHED_TICKLESS)
int up_timer_gettime(FAR struct timespec *ts) int up_timer_gettime(FAR struct timespec *ts)
{ {
if (!g_timer.lower) int ret = -EAGAIN;
if (g_timer.lower != NULL)
{ {
memset(ts, 0, sizeof(*ts)); timespec_from_usec(ts, current_usec());
return 0; ret = 0;
} }
timespec_from_usec(ts, current_usec()); return ret;
return 0;
} }
#endif #endif
@ -372,13 +373,15 @@ int up_timer_gettime(FAR struct timespec *ts)
#ifdef CONFIG_SCHED_TICKLESS #ifdef CONFIG_SCHED_TICKLESS
int up_timer_cancel(FAR struct timespec *ts) int up_timer_cancel(FAR struct timespec *ts)
{ {
if (!g_timer.lower) int ret = -EAGAIN;
if (g_timer.lower != NULL)
{ {
return -EAGAIN; timespec_from_usec(ts, update_timeout(g_timer.maxtimeout));
ret = 0;
} }
timespec_from_usec(ts, update_timeout(g_timer.maxtimeout)); return ret;
return 0;
} }
#endif #endif
@ -410,13 +413,15 @@ int up_timer_cancel(FAR struct timespec *ts)
#ifdef CONFIG_SCHED_TICKLESS #ifdef CONFIG_SCHED_TICKLESS
int up_timer_start(FAR const struct timespec *ts) int up_timer_start(FAR const struct timespec *ts)
{ {
if (!g_timer.lower) int ret = -EAGAIN;
if (g_timer.lower != NULL)
{ {
return -EAGAIN; update_timeout(timespec_to_usec(ts));
ret = 0;
} }
update_timeout(timespec_to_usec(ts)); return ret;
return 0;
} }
#endif #endif
@ -446,11 +451,11 @@ void up_mdelay(unsigned int milliseconds)
void up_udelay(useconds_t microseconds) void up_udelay(useconds_t microseconds)
{ {
if (g_timer.lower) if (g_timer.lower != NULL)
{ {
udelay_accurate(microseconds); udelay_accurate(microseconds);
} }
else /* period timer doesn't init yet */ else /* Period timer hasn't been initialized yet */
{ {
udelay_coarse(microseconds); udelay_coarse(microseconds);
} }