[Vm-dev] [commit] r2388 - Add straggler

commits at squeakvm.org commits at squeakvm.org
Wed Jun 1 17:56:27 UTC 2011


Author: eliot
Date: 2011-06-01 10:56:27 -0700 (Wed, 01 Jun 2011)
New Revision: 2388

Added:
   branches/Cog/platforms/win32/vm/sqWin32Time.c
Log:
Add straggler


Added: branches/Cog/platforms/win32/vm/sqWin32Time.c
===================================================================
--- branches/Cog/platforms/win32/vm/sqWin32Time.c	                        (rev 0)
+++ branches/Cog/platforms/win32/vm/sqWin32Time.c	2011-06-01 17:56:27 UTC (rev 2388)
@@ -0,0 +1,146 @@
+/****************************************************************************
+*   sqWin32Time.c
+*   Time functions for non-heartbeat (non STACK) VMs, extracted from
+*	trunk sqWin32Window.c
+*****************************************************************************/
+
+#include <windows.h>
+
+#include "sq.h"
+
+#if !STACKVM
+/*
+ * Win32 FILETIMEs are 10th's of microseconds since 1601.  Smalltalk times
+ * are seconds from 1901.  Let's call a 10th of a microsecond a "tock".
+ */
+
+#if _MSC_VER
+# define SecondsFrom1601To1901 9467020800i64 /*See PRINT_TIME_CONSTANTS below*/
+# define MicrosecondsFrom1601To1901 9467020800000000i64
+
+# define MicrosecondsPerSecond 1000000i64
+# define MillisecondsPerSecond 1000i64
+
+# define MicrosecondsPerMillisecond 1000000i64
+
+# define TocksPerSecond      10000000i64
+# define TocksPerMillisecond 10000i64
+# define TocksPerMicrosecond 10i64
+# define LLFMT "I64d"
+#else
+# define SecondsFrom1601To1901 9467020800LL /*See PRINT_TIME_CONSTANTS below*/
+# define MicrosecondsFrom1601To1901 9467020800000000LL
+
+# define MicrosecondsPerSecond 1000000LL
+# define MillisecondsPerSecond 1000LL
+
+# define MicrosecondsPerMillisecond 1000LL
+
+# define TocksPerSecond      10000000LL
+# define TocksPerMillisecond 10000LL
+# define TocksPerMicrosecond 10LL
+# define LLFMT "lld"
+#endif
+
+/* returns the local wall clock time */
+int ioSeconds(void)
+{ SYSTEMTIME sysTime;
+  GetLocalTime(&sysTime);
+  return convertToSqueakTime(sysTime);
+}
+
+int ioMSecs()
+{
+  /* Make sure the value fits into Squeak SmallIntegers */
+#ifndef _WIN32_WCE
+  return timeGetTime() & 0x3FFFFFFF;
+#else
+  return GetTickCount() &0x3FFFFFFF;
+#endif
+}
+
+/* Note: ioMicroMSecs returns *milli*seconds */
+int ioMicroMSecs(void)
+{
+  /* Make sure the value fits into Squeak SmallIntegers */
+  return timeGetTime() &0x3FFFFFFF;
+}
+
+/* Compute the current VM time basis, the number of microseconds from 1901.
+ *
+ * Alas Windows' system time functions GetSystemTime et al have low resolution;
+ * 15 ms.  So we use timeGetTime for higher resolution and use it as an offset to
+ * the system time, resetting when timeGetTime wraps.  Since timeGetTime wraps we
+ * need some basis information which is passed in as pointers to provide us with
+ * both the heartbeat clock and an instantaneous clock for the VM thread.
+ * This is still insufficient since timeGetTime driefts relative to wall time.
+ * We should apply some periodic adjustment but for now just drift aimlessly.
+ */
+
+/* The bases that relate timeGetTime's 32-bit wrapping millisecond clock to the
+ * non-wrapping 64-bit microsecond clocks.
+ */
+static unsigned __int64 utcTickBaseMicroseconds;
+static DWORD lastTick = (DWORD)-1;
+static DWORD baseTick;
+
+static unsigned __int64
+currentUTCMicroseconds(unsigned __int64 *utcTickBaseUsecsp, DWORD *lastTickp, DWORD *baseTickp)
+{
+	FILETIME utcNow;
+	DWORD currentTick = timeGetTime();
+	DWORD prevTick = *lastTickp;
+
+	*lastTickp = currentTick;
+
+	/* If the timeGetTime millisecond clock wraps (as it will every 49.71 days)
+	 * resync to the system time.  
+	 */
+	if (currentTick < prevTick) {
+
+		*baseTickp = currentTick;
+		GetSystemTimeAsFileTime(&utcNow);
+		*utcTickBaseUsecsp = *(unsigned __int64 *)&utcNow
+							/ TocksPerMicrosecond
+							- MicrosecondsFrom1601To1901;
+		return *utcTickBaseUsecsp;
+	}
+	return *utcTickBaseUsecsp
+		  + (currentTick - *baseTickp) * MicrosecondsPerMillisecond;
+}
+
+usqLong
+ioUTCMicroseconds() { return currentUTCMicroseconds(&utcTickBaseMicroseconds, &lastTick, &baseTick); }
+
+/* This is an expensive interface for use by profiling code that wants the time
+ * now rather than as of the last heartbeat.
+ */
+usqLong
+ioUTCMicrosecondsNow() { return currentUTCMicroseconds(&utcTickBaseMicroseconds, &lastTick, &baseTick); }
+
+static DWORD dwTimerPeriod;
+
+void
+ioInitTime()
+{
+# if !defined(_WIN32_WCE)
+	TIMECAPS tCaps;
+
+	dwTimerPeriod = 0;
+	if(timeGetDevCaps(&tCaps,sizeof(tCaps)) != 0)
+		return;
+	dwTimerPeriod = tCaps.wPeriodMin;
+	if (timeBeginPeriod(dwTimerPeriod) != 0)
+		return;
+# endif
+}
+
+void
+ioReleaseTime(void)
+{
+# if !defined(_WIN32_WCE)
+	if (dwTimerPeriod)
+		timeEndPeriod(dwTimerPeriod);
+# endif /* !defined(_WIN32_WCE) */
+}
+#endif /* STACKVM */



More information about the Vm-dev mailing list