Has anyone else ported Newlib to their OS with support for getting the computer date/time? If so, I have a couple of questions:
Is the only requirement gettimeofday()?
gettimeofday only returns the number of seconds elapsed since 00:00:00 on January 1, 1970?
Thanks,
Ian
Newlib and time()
Newlib and time()
BareMetal OS - http://www.returninfinity.com/
Mono-tasking 64-bit OS for x86-64 based computers, written entirely in Assembly
Mono-tasking 64-bit OS for x86-64 based computers, written entirely in Assembly
Re: Newlib and time()
Anyone? I would like to get this coded this weekend.
BareMetal OS - http://www.returninfinity.com/
Mono-tasking 64-bit OS for x86-64 based computers, written entirely in Assembly
Mono-tasking 64-bit OS for x86-64 based computers, written entirely in Assembly
- Brynet-Inc
- Member
- Posts: 2426
- Joined: Tue Oct 17, 2006 9:29 pm
- Libera.chat IRC: brynet
- Location: Canada
- Contact:
Re: Newlib and time()
It's not entirely clear what you're asking. If you wanted to know the standard definition of gettimeofday, then check SUSv4.
http://pubs.opengroup.org/onlinepubs/96 ... ofday.html
http://pubs.opengroup.org/onlinepubs/96 ... ofday.html
Re: Newlib and time()
No worries. Perhaps I wasn't clear enough but I think I have it working:
This reports the date as Jan 1, 1970 @ 00:00:00
This reports the date as Jun 28, 2013 @ 16:59:59:
So all I need to do now is pull the current data from the RTC to populate that tm struct.
This reports the date as Jan 1, 1970 @ 00:00:00
Code: Select all
int gettimeofday(struct timeval *p, void *z)
{
p->tv_sec = 0;
p->tv_usec = 0;
return 0;
}
Code: Select all
int gettimeofday(struct timeval *p, void *z)
{
struct tm t;
t.tm_year = 2013-1900;
t.tm_mon = 5;
t.tm_mday = 28;
t.tm_hour = 16;
t.tm_min = 59;
t.tm_sec = 59;
t.tm_isdst = -1;
p->tv_sec = (long) mktime(&t);
p->tv_usec = 0;
return 0;
}
BareMetal OS - http://www.returninfinity.com/
Mono-tasking 64-bit OS for x86-64 based computers, written entirely in Assembly
Mono-tasking 64-bit OS for x86-64 based computers, written entirely in Assembly
Re: Newlib and time()
The RTC only provides 1 second resolution, whereas gettimeofday should return seconds and microseconds, and if you want to use the newer clock_gettime functions you should return seconds and nanoseconds. One way to provide this is to store a 64-bit counter of nanoseconds since the epoch within the kernel (this should cover a date range +/- around 292 years) which is initialised at boot time from an external source (e.g. RTC or NTP) and then incremented with each timer tick. Then, when something requests the time, you work it out from here with the appropriate division (alternatively store both seconds and nano/microseconds). This is also generally faster than reading the IO ports from the CMOS, which may be a significant bottleneck if an application requests the current time frequently.
Note this can suffer from drift for several reasons: 1) if the timer device is not providing ticks as accurately as you expect and 2) if you are missing some timer interrupts due to your ISR taking too long, but bear in mind that the RTC suffers drift too. For this reason, you would ideally want to periodically check against a NTP server to ensure you're still reasonably accurate.
Regards,
John.
Note this can suffer from drift for several reasons: 1) if the timer device is not providing ticks as accurately as you expect and 2) if you are missing some timer interrupts due to your ISR taking too long, but bear in mind that the RTC suffers drift too. For this reason, you would ideally want to periodically check against a NTP server to ensure you're still reasonably accurate.
Regards,
John.
Re: Newlib and time()
Reading the RTC is slow and will need global locking. If you are concerned at all about performance (I'm sure you are) you will only read the RTC once at boot.
If a trainstation is where trains stop, what is a workstation ?
Re: Newlib and time()
Note that gettimeofday() is an obsolescent API and that microsecond precision isn't good enough these days, where the POSIX standard and others have embraced the nano-precision struct timespec and clock_gettime instead, which offers a far superior API (support for multiple clocks, for instance).
Re: Newlib and time()
Agreed on all points. For right now my implementation is "good enough"™. For BareMetal Node I'll be using the network to get the time from a central server.
For anyone curious, my Newlib syscalls.c is here: https://github.com/ReturnInfinity/BareM ... syscalls.c
For anyone curious, my Newlib syscalls.c is here: https://github.com/ReturnInfinity/BareM ... syscalls.c
BareMetal OS - http://www.returninfinity.com/
Mono-tasking 64-bit OS for x86-64 based computers, written entirely in Assembly
Mono-tasking 64-bit OS for x86-64 based computers, written entirely in Assembly