| // Copyright 2018 The Go Authors. All rights reserved. |
| // Use of this source code is governed by a BSD-style |
| // license that can be found in the LICENSE file. |
| |
| //go:build !faketime |
| // +build !faketime |
| |
| #include "go_asm.h" |
| #include "textflag.h" |
| #include "time_windows.h" |
| |
| TEXT time·now(SB),NOSPLIT|NOFRAME,$0-24 |
| MOVB runtime·useQPCTime(SB), R0 |
| CMP $0, R0 |
| BNE useQPC |
| MOVD $_INTERRUPT_TIME, R3 |
| loop: |
| MOVWU time_hi1(R3), R1 |
| MOVWU time_lo(R3), R0 |
| MOVWU time_hi2(R3), R2 |
| CMP R1, R2 |
| BNE loop |
| |
| // wintime = R1:R0, multiply by 100 |
| ORR R1<<32, R0 |
| MOVD $100, R1 |
| MUL R1, R0 |
| MOVD R0, mono+16(FP) |
| |
| MOVD $_SYSTEM_TIME, R3 |
| wall: |
| MOVWU time_hi1(R3), R1 |
| MOVWU time_lo(R3), R0 |
| MOVWU time_hi2(R3), R2 |
| CMP R1, R2 |
| BNE wall |
| |
| // w = R1:R0 in 100ns units |
| // convert to Unix epoch (but still 100ns units) |
| #define delta 116444736000000000 |
| ORR R1<<32, R0 |
| SUB $delta, R0 |
| |
| // Convert to nSec |
| MOVD $100, R1 |
| MUL R1, R0 |
| |
| // Code stolen from compiler output for: |
| // |
| // var x uint64 |
| // func f() (sec uint64, nsec uint32) { return x / 1000000000, uint32(x % 100000000) } |
| // |
| LSR $1, R0, R1 |
| MOVD $-8543223759426509416, R2 |
| UMULH R2, R1, R1 |
| LSR $28, R1, R1 |
| MOVD R1, sec+0(FP) |
| MOVD $-6067343680855748867, R1 |
| UMULH R0, R1, R1 |
| LSR $26, R1, R1 |
| MOVD $100000000, R2 |
| MSUB R1, R0, R2, R0 |
| MOVW R0, nsec+8(FP) |
| RET |
| useQPC: |
| B runtime·nowQPC(SB) // tail call |
| |