From e546b295b8a3b6f8996a02aeecfbdfedd07c21aa Mon Sep 17 00:00:00 2001 From: Lars Wiegman Date: Tue, 17 Jan 2017 11:38:18 +0100 Subject: [PATCH] runtime: use mach_absolute_time for runtime.nanotime The existing darwin/amd64 implementation of runtime.nanotime returns the wallclock time, which results in timers not functioning properly when system time runs backwards. By implementing the algorithm used by the darwin syscall mach_absolute_time, timers will function as expected. The algorithm is described at https://opensource.apple.com/source/xnu/xnu-3248.60.10/libsyscall/wrappers/mach_absolute_time.s Fixes #17610 Change-Id: I9c8d35240d48249a6837dca1111b1406e2686f67 Reviewed-on: https://go-review.googlesource.com/35292 Reviewed-by: Russ Cox Run-TryBot: Russ Cox TryBot-Result: Gobot Gobot --- src/runtime/sys_darwin_amd64.s | 23 ++++++++++++++++++++++- 1 file changed, 22 insertions(+), 1 deletion(-) diff --git a/src/runtime/sys_darwin_amd64.s b/src/runtime/sys_darwin_amd64.s index 96fa5b9710..e68dafe6a6 100644 --- a/src/runtime/sys_darwin_amd64.s +++ b/src/runtime/sys_darwin_amd64.s @@ -117,6 +117,27 @@ TEXT runtime·madvise(SB), NOSPLIT, $0 #define gtod_ns_base 0x70 #define gtod_sec_base 0x78 +TEXT monotonictime<>(SB), NOSPLIT, $32 + MOVQ $0x7fffffe00000, SI // comm page base + +timeloop: + MOVL nt_generation(SI), R8 + TESTL R8, R8 + JZ timeloop + RDTSC + SHLQ $32, DX + ORQ DX, AX + MOVL nt_shift(SI), CX + SUBQ nt_tsc_base(SI), AX + SHLQ CX, AX + MOVL nt_scale(SI), CX + MULQ CX + SHRQ $32, AX:DX + ADDQ nt_ns_base(SI), AX + CMPL nt_generation(SI), R8 + JNE timeloop + RET + TEXT nanotime<>(SB), NOSPLIT, $32 MOVQ $0x7fffffe00000, BP /* comm page base */ // Loop trying to take a consistent snapshot @@ -173,7 +194,7 @@ inreg: RET TEXT runtime·nanotime(SB),NOSPLIT,$0-8 - CALL nanotime<>(SB) + CALL monotonictime<>(SB) MOVQ AX, ret+0(FP) RET -- 2.50.0