mirror of
https://github.com/love2d/love.git
synced 2026-08-14 10:13:46 +02:00
Subtract start time before double conversion
To preserve precision the subtraction of the start time happens with integer values now and the platform specific implementations have been split completely.
This commit is contained in:
+66
-41
@@ -35,15 +35,6 @@
|
||||
#include <sys/time.h>
|
||||
#endif
|
||||
|
||||
#if defined(LOVE_LINUX)
|
||||
static inline double getTimeOfDay()
|
||||
{
|
||||
timeval t;
|
||||
gettimeofday(&t, NULL);
|
||||
return (double) t.tv_sec + (double) t.tv_usec / 1000000.0;
|
||||
}
|
||||
#endif
|
||||
|
||||
namespace love
|
||||
{
|
||||
namespace timer
|
||||
@@ -109,58 +100,92 @@ double Timer::getAverageDelta() const
|
||||
return averageDelta;
|
||||
}
|
||||
|
||||
double Timer::getTimerPeriod()
|
||||
#if defined(LOVE_LINUX)
|
||||
|
||||
static inline timespec getTimeOfDay()
|
||||
{
|
||||
#if defined(LOVE_MACOSX) || defined(LOVE_IOS)
|
||||
mach_timebase_info_data_t info;
|
||||
mach_timebase_info(&info);
|
||||
return (double) info.numer / (double) info.denom / 1000000000.0;
|
||||
#elif defined(LOVE_WINDOWS)
|
||||
LARGE_INTEGER temp;
|
||||
if (QueryPerformanceFrequency(&temp) != 0 && temp.QuadPart != 0)
|
||||
return 1.0 / (double) temp.QuadPart;
|
||||
#endif
|
||||
return 0;
|
||||
timeval t;
|
||||
gettimeofday(&t, NULL);
|
||||
return timespec { t.tv_sec, t.tv_usec * 1000 };
|
||||
}
|
||||
|
||||
double Timer::getTimeAbsolute()
|
||||
static timespec getTimeAbsolute()
|
||||
{
|
||||
// The timer period (reciprocal of the frequency.)
|
||||
static const double timerPeriod = getTimerPeriod();
|
||||
|
||||
#if defined(LOVE_LINUX)
|
||||
(void) timerPeriod; // Unused on linux
|
||||
|
||||
double mt;
|
||||
// Check for POSIX timers and monotonic clocks. If not supported, use the gettimeofday fallback.
|
||||
#if _POSIX_TIMERS > 0 && defined(_POSIX_MONOTONIC_CLOCK) \
|
||||
&& (defined(CLOCK_MONOTONIC_RAW) || defined(CLOCK_MONOTONIC))
|
||||
timespec t;
|
||||
|
||||
#ifdef CLOCK_MONOTONIC_RAW
|
||||
clockid_t clk_id = CLOCK_MONOTONIC_RAW;
|
||||
#else
|
||||
clockid_t clk_id = CLOCK_MONOTONIC;
|
||||
#endif
|
||||
|
||||
timespec t;
|
||||
if (clock_gettime(clk_id, &t) == 0)
|
||||
mt = (double) t.tv_sec + (double) t.tv_nsec / 1000000000.0;
|
||||
return t;
|
||||
else
|
||||
return getTimeOfDay();
|
||||
#endif
|
||||
mt = getTimeOfDay();
|
||||
return mt;
|
||||
#elif defined(LOVE_MACOSX) || defined(LOVE_IOS)
|
||||
return (double) mach_absolute_time() * timerPeriod;
|
||||
#elif defined(LOVE_WINDOWS)
|
||||
LARGE_INTEGER microTime;
|
||||
QueryPerformanceCounter(µTime);
|
||||
return (double) microTime.QuadPart * timerPeriod;
|
||||
#endif
|
||||
return getTimeOfDay();
|
||||
}
|
||||
|
||||
double Timer::getTime()
|
||||
{
|
||||
static const double start = getTimeAbsolute();
|
||||
return getTimeAbsolute() - start;
|
||||
static const timespec start = getTimeAbsolute();
|
||||
const timespec now = getTimeAbsolute();
|
||||
const timespec rel = timespec {
|
||||
now.tv_sec - start.tv_sec,
|
||||
now.tv_nsec - start.tv_nsec
|
||||
};
|
||||
return (double) rel.tv_sec + (double) rel.tv_nsec / 1.0e9;
|
||||
}
|
||||
|
||||
#elif defined(LOVE_MACOSX) || defined(LOVE_IOS)
|
||||
|
||||
static mach_timebase_info_data_t getTimebaseInfo()
|
||||
{
|
||||
mach_timebase_info_data_t info;
|
||||
mach_timebase_info(&info);
|
||||
return info;
|
||||
}
|
||||
|
||||
double Timer::getTime()
|
||||
{
|
||||
static const mach_timebase_info_data_t info = getTimebaseInfo();
|
||||
static const uint64_t start = mach_absolute_time();
|
||||
const uint64_t rel = mach_absolute_time() - start;
|
||||
return ((double) rel * 1.0e-9) * (double) info.number / (double) info.denom;
|
||||
}
|
||||
|
||||
#elif defined(LOVE_WINDOWS)
|
||||
|
||||
static LARGE_INTEGER getTimeAbsolute()
|
||||
{
|
||||
LARGE_INTEGER t;
|
||||
QueryPerformanceCounter(&t);
|
||||
return t;
|
||||
}
|
||||
|
||||
static LARGE_INTEGER getFrequency()
|
||||
{
|
||||
LARGE_INTEGER freq;
|
||||
// "On systems that run Windows XP or later, the function will always succeed and will thus never return zero."
|
||||
QueryPerformanceFrequency(&freq);
|
||||
return freq;
|
||||
}
|
||||
|
||||
double Timer::getTime()
|
||||
{
|
||||
static const LARGE_INTEGER freq = getFrequency();
|
||||
static const LARGE_INTEGER start = getTimeAbsolute();
|
||||
const LARGE_INTEGER now = getTimeAbsolute();
|
||||
LARGE_INTEGER rel;
|
||||
rel.QuadPart = now.QuadPart - start.QuadPart;
|
||||
return rel.QuadPart / freq.QuadPart;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
} // timer
|
||||
} // love
|
||||
|
||||
Reference in New Issue
Block a user