160 lines
3.4 KiB
C
Raw Normal View History

2018-10-14 19:28:18 +08:00
/*
* Copyright (c) 2006-2018, RT-Thread Development Team
*
* SPDX-License-Identifier: Apache-2.0
*
* Change Logs:
* Date Author Notes
*/
#include <sys/time.h>
2018-05-04 09:06:57 +08:00
#include <rtthread.h>
2018-10-26 11:03:55 +08:00
/* days per month -- nonleap! */
const short __spm[13] =
{
0,
(31),
(31 + 28),
(31 + 28 + 31),
(31 + 28 + 31 + 30),
(31 + 28 + 31 + 30 + 31),
(31 + 28 + 31 + 30 + 31 + 30),
(31 + 28 + 31 + 30 + 31 + 30 + 31),
(31 + 28 + 31 + 30 + 31 + 30 + 31 + 31),
(31 + 28 + 31 + 30 + 31 + 30 + 31 + 31 + 30),
(31 + 28 + 31 + 30 + 31 + 30 + 31 + 31 + 30 + 31),
(31 + 28 + 31 + 30 + 31 + 30 + 31 + 31 + 30 + 31 + 30),
(31 + 28 + 31 + 30 + 31 + 30 + 31 + 31 + 30 + 31 + 30 + 31),
};
/* seconds per day */
#define SPD 24*60*60
#ifdef RT_USING_DEVICE
int gettimeofday(struct timeval *tp, void *ignore)
{
time_t time;
rt_device_t device;
device = rt_device_find("rtc");
if (device != RT_NULL)
{
rt_device_control(device, RT_DEVICE_CTRL_RTC_GET_TIME, &time);
if (tp != RT_NULL)
{
tp->tv_sec = time;
tp->tv_usec = 0;
}
return time;
}
return 0;
}
#endif
/**
* Returns the current time.
*
* @param time_t * t the timestamp pointer, if not used, keep NULL.
*
* @return time_t return timestamp current.
*
*/
/* for IAR 6.2 later Compiler */
#if defined (__IAR_SYSTEMS_ICC__) && (__VER__) >= 6020000
#pragma module_name = "?time"
time_t (__time32)(time_t *t) /* Only supports 32-bit timestamp */
#else
time_t time(time_t *t)
#endif
{
time_t time_now = 0;
#ifdef RT_USING_RTC
static rt_device_t device = RT_NULL;
/* optimization: find rtc device only first. */
if (device == RT_NULL)
{
device = rt_device_find("rtc");
}
/* read timestamp from RTC device. */
if (device != RT_NULL)
{
if (rt_device_open(device, 0) == RT_EOK)
{
rt_device_control(device, RT_DEVICE_CTRL_RTC_GET_TIME, &time_now);
rt_device_close(device);
}
}
#endif /* RT_USING_RTC */
/* if t is not NULL, write timestamp to *t */
if (t != RT_NULL)
{
*t = time_now;
}
return time_now;
}
2018-10-26 11:03:55 +08:00
static int __isleap(int year)
{
/* every fourth year is a leap year except for century years that are
* not divisible by 400. */
/* return (year % 4 == 0 && (year % 100 != 0 || year % 400 == 0)); */
return (!(year % 4) && ((year % 100) || !(year % 400)));
}
/**
* This function will convert Time (Restartable)
*
* @param timep the timestamp
* @param the structure to stores information
*
* @return the structure to stores information
*
*/
struct tm *gmtime_r(const time_t *timep, struct tm *r)
{
time_t i;
register time_t work = *timep % (SPD);
r->tm_sec = work % 60;
work /= 60;
r->tm_min = work % 60;
r->tm_hour = work / 60;
work = *timep / (SPD);
r->tm_wday = (4 + work) % 7;
for (i = 1970;; ++i)
{
register time_t k = __isleap(i) ? 366 : 365;
if (work >= k)
work -= k;
else
break;
}
r->tm_year = i - 1900;
r->tm_yday = work;
r->tm_mday = 1;
if (__isleap(i) && (work > 58))
{
if (work == 59)
r->tm_mday = 2; /* 29.2. */
work -= 1;
}
for (i = 11; i && (__spm[i] > work); --i)
;
r->tm_mon = i;
r->tm_mday += work - __spm[i];
return r;
}
RT_WEAK clock_t clock(void)
{
return rt_tick_get();
}