Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Fast, cross-platform timer?

I'm looking to improve the D garbage collector by adding some heuristics to avoid garbage collection runs that are unlikely to result in significant freeing. One heuristic I'd like to add is that GC should not be run more than once per X amount of time (maybe once per second or so). To do this I need a timer with the following properties:

  1. It must be able to grab the correct time with minimal overhead. Calling core.stdc.time takes an amount of time roughly equivalent to a small memory allocation, so it's not a good option.

  2. Ideally, should be cross-platform (both OS and CPU), for maintenance simplicity.

  3. Super high resolution isn't terribly important. If the times are accurate to maybe 1/4 of a second, that's good enough.

  4. Must work in a multithreaded/multi-CPU context. The x86 rdtsc instruction won't work.

EDIT: The plain old C function clock() seems fast enough. However, here overflow is a problem. On 32-bit Windows and Linux, clock_t is defined as a 32-bit signed integer. When it overflows, does it become negative, or does the clock() function use extra logic to make it wrap to zero instead? If it wraps to zero, then this will do the trick. If it wraps to negative (which also represents error codes, etc.) then it isn't going to work.

Edit # 2: I tried the heuristic out anyhow, using clock() and ignoring the overflow issue, just as a test. It performs so poorly that it's not worth further investigation.

like image 863
dsimcha Avatar asked Feb 21 '11 23:02

dsimcha


2 Answers

Ideally, should be cross-platform (both OS and CPU), for maintenance simplicity.

I think that brings you down to whatever you can find in the standard C library.

Perhaps clock?

like image 131
Vladimir Panteleev Avatar answered Oct 23 '22 05:10

Vladimir Panteleev


Well, my first suggestion would be to use core.time or std.datetime. It does have a StopWatch. Is it not fast enough? It uses whatever the standard monotonic clock is for the system, and I would hope that that would be fast enough. It's certainly the highest precision that you're going to get (though how the high precision affects speed, I don't know). However, if it isn't fast enough, I'm not at all sure that your other options are any better. It's generally the case that you either get second precision or high precision. There isn't much in between. And with high precision, it's generally at least microsecond precision with the question being how much beyond that it goes. 1/4 second precision isn't exactly normal.

Cybershadow's suggestion of clock may be do the trick - certainly it's your only option which is standard C as far as I know - but it may or may not be fast enough.

Aside from clock... On Linux, if you want a non-monotonic way to get the time with higher precision than one second, I believe that gettimeofday is your only real option, but I don't know how fast it is. On Windows, the best non-monotonic solution that I'm aware of is getSystemTimeAsFiletime, but Windows has several time functions that you could play around with.

You can look at std.datetime's Clock.currStdTime to see how to do either of those (though it uses clock_gettime on Posix if it's available, which is what core.time uses - albeit with a different clock - so you probably want the else portion of that function for Linux if StopWatch is too slow for you). However, it does convert to hnsecs from midnight January 1st, 1 A.D., so depending on what you do with the number, you'll want to skip that portion of the calculation.

like image 42
Jonathan M Davis Avatar answered Oct 23 '22 03:10

Jonathan M Davis