1// Copyright 2018 The Go Authors. All rights reserved. 2// Use of this source code is governed by a BSD-style 3// license that can be found in the LICENSE file. 4 5//go:build !faketime 6 7#include "go_asm.h" 8#include "textflag.h" 9#include "time_windows.h" 10 11TEXT time·now(SB),NOSPLIT,$0-20 12 MOVW $_INTERRUPT_TIME, R3 13loop: 14 MOVW time_hi1(R3), R1 15 DMB MB_ISH 16 MOVW time_lo(R3), R0 17 DMB MB_ISH 18 MOVW time_hi2(R3), R2 19 CMP R1, R2 20 BNE loop 21 22 // wintime = R1:R0, multiply by 100 23 MOVW $100, R2 24 MULLU R0, R2, (R4, R3) // R4:R3 = R1:R0 * R2 25 MULA R1, R2, R4, R4 26 27 // wintime*100 = R4:R3 28 MOVW R3, mono+12(FP) 29 MOVW R4, mono+16(FP) 30 31 MOVW $_SYSTEM_TIME, R3 32wall: 33 MOVW time_hi1(R3), R1 34 DMB MB_ISH 35 MOVW time_lo(R3), R0 36 DMB MB_ISH 37 MOVW time_hi2(R3), R2 38 CMP R1, R2 39 BNE wall 40 41 // w = R1:R0 in 100ns untis 42 // convert to Unix epoch (but still 100ns units) 43 #define delta 116444736000000000 44 SUB.S $(delta & 0xFFFFFFFF), R0 45 SBC $(delta >> 32), R1 46 47 // Convert to nSec 48 MOVW $100, R2 49 MULLU R0, R2, (R4, R3) // R4:R3 = R1:R0 * R2 50 MULA R1, R2, R4, R4 51 // w = R2:R1 in nSec 52 MOVW R3, R1 // R4:R3 -> R2:R1 53 MOVW R4, R2 54 55 // multiply nanoseconds by reciprocal of 10**9 (scaled by 2**61) 56 // to get seconds (96 bit scaled result) 57 MOVW $0x89705f41, R3 // 2**61 * 10**-9 58 MULLU R1,R3,(R6,R5) // R7:R6:R5 = R2:R1 * R3 59 MOVW $0,R7 60 MULALU R2,R3,(R7,R6) 61 62 // unscale by discarding low 32 bits, shifting the rest by 29 63 MOVW R6>>29,R6 // R7:R6 = (R7:R6:R5 >> 61) 64 ORR R7<<3,R6 65 MOVW R7>>29,R7 66 67 // subtract (10**9 * sec) from nsec to get nanosecond remainder 68 MOVW $1000000000, R5 // 10**9 69 MULLU R6,R5,(R9,R8) // R9:R8 = R7:R6 * R5 70 MULA R7,R5,R9,R9 71 SUB.S R8,R1 // R2:R1 -= R9:R8 72 SBC R9,R2 73 74 // because reciprocal was a truncated repeating fraction, quotient 75 // may be slightly too small -- adjust to make remainder < 10**9 76 CMP R5,R1 // if remainder > 10**9 77 SUB.HS R5,R1 // remainder -= 10**9 78 ADD.HS $1,R6 // sec += 1 79 80 MOVW R6,sec_lo+0(FP) 81 MOVW R7,sec_hi+4(FP) 82 MOVW R1,nsec+8(FP) 83 RET 84 85