mirror of https://github.com/golang/go.git
runtime: use clock_gettime to get ns resolution for time.now & runtime.nanotime
For Linux/{386,arm}, FreeBSD/{386,amd64,arm}, NetBSD/{386,amd64}, OpenBSD/{386,amd64}.
Note: our Darwin implementation already has ns resolution.
Linux/386 (Core i7-2600 @ 3.40GHz, kernel 3.5.2-gentoo)
benchmark old ns/op new ns/op delta
BenchmarkNow 110 118 +7.27%
Linux/ARM (ARM Cortex-A8 @ 800MHz, kernel 2.6.32.28 android)
benchmark old ns/op new ns/op delta
BenchmarkNow 625 542 -13.28%
Linux/ARM (ARM Cortex-A9 @ 1GHz, Pandaboard)
benchmark old ns/op new ns/op delta
BenchmarkNow 992 909 -8.37%
FreeBSD 9-REL-p1/amd64 (Dell R610 Server with Xeon X5650 @ 2.67GHz)
benchmark old ns/op new ns/op delta
BenchmarkNow 699 695 -0.57%
FreeBSD 9-REL-p1/amd64 (Atom D525 @ 1.80GHz)
benchmark old ns/op new ns/op delta
BenchmarkNow 1553 1658 +6.76%
OpenBSD/amd64 (Dell E6410 with i5 CPU M 540 @ 2.53GHz)
benchmark old ns/op new ns/op delta
BenchmarkNow 1262 1236 -2.06%
OpenBSD/i386 (Asus eeePC 701 with Intel Celeron M 900MHz - locked to 631MHz)
benchmark old ns/op new ns/op delta
BenchmarkNow 5089 5043 -0.90%
NetBSD/i386 (VMware VM with Core i5 CPU @ 2.7GHz)
benchmark old ns/op new ns/op delta
BenchmarkNow 277 278 +0.36%
NetBSD/amd64 (VMware VM with Core i5 CPU @ 2.7Ghz)
benchmark old ns/op new ns/op delta
BenchmarkNow 103 105 +1.94%
Thanks Maxim Khitrov, Joel Sing, and Dave Cheney for providing benchmark data.
R=jsing, dave, rsc
CC=golang-dev
https://golang.org/cl/6820120
This commit is contained in:
parent
5b46fc417f
commit
7777bac6e4
|
|
@ -94,10 +94,10 @@ the <code>UnixConn</code>.
|
|||
|
||||
<h3 id="time">time</h3>
|
||||
<p>
|
||||
On Linux, previous versions of the time package returned times with
|
||||
microsecond precision. The Go 1.1 implementation of time on Linux now returns times with
|
||||
nanosecond precision. Code may exist that expects to be able to store
|
||||
such a time in an external format with only microsecond precision,
|
||||
On FreeBSD, Linux, NetBSD, OS X and OpenBSD, previous versions of the time package
|
||||
returned times with microsecond precision. The Go 1.1 implementation of time on these
|
||||
systems now returns times with nanosecond precision. Code may exist that expects to be
|
||||
able to store such a time in an external format with only microsecond precision,
|
||||
read it back, and recover exactly the same time instant.
|
||||
In Go 1.1 the same time will not be recovered, since the external storage
|
||||
will have discarded nanoseconds.
|
||||
|
|
|
|||
|
|
@ -116,40 +116,38 @@ TEXT runtime·setitimer(SB), 7, $-4
|
|||
|
||||
// func now() (sec int64, nsec int32)
|
||||
TEXT time·now(SB), 7, $32
|
||||
MOVL $116, AX
|
||||
MOVL $232, AX
|
||||
LEAL 12(SP), BX
|
||||
MOVL BX, 4(SP)
|
||||
MOVL $0, 8(SP)
|
||||
MOVL $0, 4(SP)
|
||||
MOVL BX, 8(SP)
|
||||
INT $0x80
|
||||
MOVL 12(SP), AX // sec
|
||||
MOVL 16(SP), BX // usec
|
||||
MOVL 16(SP), BX // nsec
|
||||
|
||||
// sec is in AX, usec in BX
|
||||
// sec is in AX, nsec in BX
|
||||
MOVL AX, sec+0(FP)
|
||||
MOVL $0, sec+4(FP)
|
||||
IMULL $1000, BX
|
||||
MOVL BX, nsec+8(FP)
|
||||
RET
|
||||
|
||||
// int64 nanotime(void) so really
|
||||
// void nanotime(int64 *nsec)
|
||||
TEXT runtime·nanotime(SB), 7, $32
|
||||
MOVL $116, AX
|
||||
MOVL $232, AX
|
||||
LEAL 12(SP), BX
|
||||
MOVL BX, 4(SP)
|
||||
MOVL $0, 8(SP)
|
||||
MOVL $0, 4(SP)
|
||||
MOVL BX, 8(SP)
|
||||
INT $0x80
|
||||
MOVL 12(SP), AX // sec
|
||||
MOVL 16(SP), BX // usec
|
||||
MOVL 16(SP), BX // nsec
|
||||
|
||||
// sec is in AX, usec in BX
|
||||
// sec is in AX, nsec in BX
|
||||
// convert to DX:AX nsec
|
||||
MOVL $1000000000, CX
|
||||
MULL CX
|
||||
IMULL $1000, BX
|
||||
ADDL BX, AX
|
||||
ADCL $0, DX
|
||||
|
||||
|
||||
MOVL ret+0(FP), DI
|
||||
MOVL AX, 0(DI)
|
||||
MOVL DX, 4(DI)
|
||||
|
|
|
|||
|
|
@ -94,31 +94,29 @@ TEXT runtime·setitimer(SB), 7, $-8
|
|||
|
||||
// func now() (sec int64, nsec int32)
|
||||
TEXT time·now(SB), 7, $32
|
||||
MOVL $116, AX
|
||||
LEAQ 8(SP), DI
|
||||
MOVQ $0, SI
|
||||
MOVL $232, AX
|
||||
MOVQ $0, DI
|
||||
LEAQ 8(SP), SI
|
||||
SYSCALL
|
||||
MOVQ 8(SP), AX // sec
|
||||
MOVL 16(SP), DX // usec
|
||||
MOVQ 16(SP), DX // nsec
|
||||
|
||||
// sec is in AX, usec in DX
|
||||
// sec is in AX, nsec in DX
|
||||
MOVQ AX, sec+0(FP)
|
||||
IMULQ $1000, DX
|
||||
MOVL DX, nsec+8(FP)
|
||||
RET
|
||||
|
||||
TEXT runtime·nanotime(SB), 7, $32
|
||||
MOVL $116, AX
|
||||
LEAQ 8(SP), DI
|
||||
MOVQ $0, SI
|
||||
MOVL $232, AX
|
||||
MOVQ $0, DI
|
||||
LEAQ 8(SP), SI
|
||||
SYSCALL
|
||||
MOVQ 8(SP), AX // sec
|
||||
MOVL 16(SP), DX // usec
|
||||
MOVQ 16(SP), DX // nsec
|
||||
|
||||
// sec is in AX, usec in DX
|
||||
// sec is in AX, nsec in DX
|
||||
// return nsec in AX
|
||||
IMULQ $1000000000, AX
|
||||
IMULQ $1000, DX
|
||||
ADDQ DX, AX
|
||||
RET
|
||||
|
||||
|
|
|
|||
|
|
@ -86,39 +86,36 @@ TEXT runtime·setitimer(SB), 7, $-8
|
|||
|
||||
// func now() (sec int64, nsec int32)
|
||||
TEXT time·now(SB), 7, $32
|
||||
MOVW $8(R13), R0
|
||||
MOVW $0, R1
|
||||
SWI $116 // gettimeofday
|
||||
MOVW $0, R0 // CLOCK_REALTIME
|
||||
MOVW $8(R13), R1
|
||||
SWI $232 // clock_gettime
|
||||
|
||||
MOVW 8(R13), R0 // sec.low
|
||||
MOVW 16(R13), R2 // usec
|
||||
MOVW 12(R13), R1 // sec.high
|
||||
MOVW 16(R13), R2 // nsec
|
||||
|
||||
MOVW R0, 0(FP)
|
||||
MOVW $0, R1
|
||||
MOVW R1, 4(FP)
|
||||
MOVW $1000, R3
|
||||
MUL R3, R2
|
||||
MOVW R2, 8(FP)
|
||||
RET
|
||||
|
||||
// int64 nanotime(void) so really
|
||||
// void nanotime(int64 *nsec)
|
||||
TEXT runtime·nanotime(SB), 7, $32
|
||||
MOVW $8(R13), R0
|
||||
MOVW $0, R1
|
||||
SWI $116 // gettimeofday
|
||||
MOVW $0, R0 // CLOCK_REALTIME
|
||||
MOVW $8(R13), R1
|
||||
SWI $232 // clock_gettime
|
||||
|
||||
MOVW 8(R13), R0 // sec.low
|
||||
MOVW 16(R13), R2 // usec
|
||||
MOVW 12(R13), R4 // sec.high
|
||||
MOVW 16(R13), R2 // nsec
|
||||
|
||||
MOVW $1000000000, R3
|
||||
MULLU R0, R3, (R1, R0)
|
||||
MOVW $1000, R3
|
||||
MOVW $0, R4
|
||||
MUL R3, R2
|
||||
MUL R3, R4
|
||||
ADD.S R2, R0
|
||||
ADC R4, R1
|
||||
|
||||
|
||||
MOVW 0(FP), R3
|
||||
MOVW R0, 0(R3)
|
||||
MOVW R1, 4(R3)
|
||||
|
|
|
|||
|
|
@ -104,40 +104,38 @@ TEXT runtime·mincore(SB),7,$0-24
|
|||
|
||||
// func now() (sec int64, nsec int32)
|
||||
TEXT time·now(SB), 7, $32
|
||||
MOVL $78, AX // syscall - gettimeofday
|
||||
LEAL 8(SP), BX
|
||||
MOVL $0, CX
|
||||
MOVL $265, AX // syscall - clock_gettime
|
||||
MOVL $0, BX
|
||||
LEAL 8(SP), CX
|
||||
MOVL $0, DX
|
||||
CALL *runtime·_vdso(SB)
|
||||
MOVL 8(SP), AX // sec
|
||||
MOVL 12(SP), BX // usec
|
||||
MOVL 12(SP), BX // nsec
|
||||
|
||||
// sec is in AX, usec in BX
|
||||
// sec is in AX, nsec in BX
|
||||
MOVL AX, sec+0(FP)
|
||||
MOVL $0, sec+4(FP)
|
||||
IMULL $1000, BX
|
||||
MOVL BX, nsec+8(FP)
|
||||
RET
|
||||
|
||||
// int64 nanotime(void) so really
|
||||
// void nanotime(int64 *nsec)
|
||||
TEXT runtime·nanotime(SB), 7, $32
|
||||
MOVL $78, AX // syscall - gettimeofday
|
||||
LEAL 8(SP), BX
|
||||
MOVL $0, CX
|
||||
MOVL $265, AX // syscall - clock_gettime
|
||||
MOVL $0, BX
|
||||
LEAL 8(SP), CX
|
||||
MOVL $0, DX
|
||||
CALL *runtime·_vdso(SB)
|
||||
MOVL 8(SP), AX // sec
|
||||
MOVL 12(SP), BX // usec
|
||||
MOVL 12(SP), BX // nsec
|
||||
|
||||
// sec is in AX, usec in BX
|
||||
// sec is in AX, nsec in BX
|
||||
// convert to DX:AX nsec
|
||||
MOVL $1000000000, CX
|
||||
MULL CX
|
||||
IMULL $1000, BX
|
||||
ADDL BX, AX
|
||||
ADCL $0, DX
|
||||
|
||||
|
||||
MOVL ret+0(FP), DI
|
||||
MOVL AX, 0(DI)
|
||||
MOVL DX, 4(DI)
|
||||
|
|
|
|||
|
|
@ -35,6 +35,7 @@
|
|||
#define SYS_select (SYS_BASE + 142) // newselect
|
||||
#define SYS_ugetrlimit (SYS_BASE + 191)
|
||||
#define SYS_sched_getaffinity (SYS_BASE + 242)
|
||||
#define SYS_clock_gettime (SYS_BASE + 263)
|
||||
|
||||
#define ARM_BASE (SYS_BASE + 0x0f0000)
|
||||
#define SYS_ARM_cacheflush (ARM_BASE + 2)
|
||||
|
|
@ -155,41 +156,37 @@ TEXT runtime·mincore(SB),7,$0
|
|||
RET
|
||||
|
||||
TEXT time·now(SB), 7, $32
|
||||
MOVW $8(R13), R0 // timeval
|
||||
MOVW $0, R1 // zone
|
||||
MOVW $SYS_gettimeofday, R7
|
||||
MOVW $0, R0 // CLOCK_REALTIME
|
||||
MOVW $8(R13), R1 // timespec
|
||||
MOVW $SYS_clock_gettime, R7
|
||||
SWI $0
|
||||
|
||||
MOVW 8(R13), R0 // sec
|
||||
MOVW 12(R13), R2 // usec
|
||||
MOVW 12(R13), R2 // nsec
|
||||
|
||||
MOVW R0, 0(FP)
|
||||
MOVW $0, R1
|
||||
MOVW R1, 4(FP)
|
||||
MOVW $1000, R3
|
||||
MUL R3, R2
|
||||
MOVW R2, 8(FP)
|
||||
RET
|
||||
|
||||
// int64 nanotime(void) so really
|
||||
// void nanotime(int64 *nsec)
|
||||
TEXT runtime·nanotime(SB),7,$32
|
||||
MOVW $8(R13), R0 // timeval
|
||||
MOVW $0, R1 // zone
|
||||
MOVW $SYS_gettimeofday, R7
|
||||
MOVW $0, R0 // CLOCK_REALTIME
|
||||
MOVW $8(R13), R1 // timespec
|
||||
MOVW $SYS_clock_gettime, R7
|
||||
SWI $0
|
||||
|
||||
MOVW 8(R13), R0 // sec
|
||||
MOVW 12(R13), R2 // usec
|
||||
MOVW 12(R13), R2 // nsec
|
||||
|
||||
MOVW $1000000000, R3
|
||||
MULLU R0, R3, (R1, R0)
|
||||
MOVW $1000, R3
|
||||
MOVW $0, R4
|
||||
MUL R3, R2
|
||||
ADD.S R2, R0
|
||||
ADC R4, R1
|
||||
|
||||
|
||||
MOVW 0(FP), R3
|
||||
MOVW R0, 0(R3)
|
||||
MOVW R1, 4(R3)
|
||||
|
|
|
|||
|
|
@ -98,9 +98,9 @@ TEXT runtime·setitimer(SB),7,$-4
|
|||
// func now() (sec int64, nsec int32)
|
||||
TEXT time·now(SB), 7, $32
|
||||
LEAL 12(SP), BX
|
||||
MOVL BX, 4(SP) // arg 1 - tp
|
||||
MOVL $0, 8(SP) // arg 2 - tzp
|
||||
MOVL $418, AX // sys_gettimeofday
|
||||
MOVL $0, 4(SP) // arg 1 - clock_id
|
||||
MOVL BX, 8(SP) // arg 2 - tp
|
||||
MOVL $427, AX // sys_clock_gettime
|
||||
INT $0x80
|
||||
|
||||
MOVL 12(SP), AX // sec - l32
|
||||
|
|
@ -108,8 +108,7 @@ TEXT time·now(SB), 7, $32
|
|||
MOVL 16(SP), AX // sec - h32
|
||||
MOVL AX, sec+4(FP)
|
||||
|
||||
MOVL 20(SP), BX // usec - should not exceed 999999
|
||||
IMULL $1000, BX
|
||||
MOVL 20(SP), BX // nsec
|
||||
MOVL BX, nsec+8(FP)
|
||||
RET
|
||||
|
||||
|
|
@ -117,9 +116,9 @@ TEXT time·now(SB), 7, $32
|
|||
// void nanotime(int64 *nsec)
|
||||
TEXT runtime·nanotime(SB),7,$32
|
||||
LEAL 12(SP), BX
|
||||
MOVL BX, 4(SP) // arg 1 - tp
|
||||
MOVL $0, 8(SP) // arg 2 - tzp
|
||||
MOVL $418, AX // sys_gettimeofday
|
||||
MOVL $0, 4(SP) // arg 1 - clock_id
|
||||
MOVL BX, 8(SP) // arg 2 - tp
|
||||
MOVL $427, AX // sys_clock_gettime
|
||||
INT $0x80
|
||||
|
||||
MOVL 16(SP), CX // sec - h32
|
||||
|
|
@ -129,8 +128,7 @@ TEXT runtime·nanotime(SB),7,$32
|
|||
MOVL $1000000000, BX
|
||||
MULL BX // result in dx:ax
|
||||
|
||||
MOVL 20(SP), BX // usec
|
||||
IMULL $1000, BX
|
||||
MOVL 20(SP), BX // nsec
|
||||
ADDL BX, AX
|
||||
ADCL CX, DX // add high bits with carry
|
||||
|
||||
|
|
|
|||
|
|
@ -122,31 +122,29 @@ TEXT runtime·setitimer(SB),7,$-8
|
|||
|
||||
// func now() (sec int64, nsec int32)
|
||||
TEXT time·now(SB), 7, $32
|
||||
LEAQ 8(SP), DI // arg 1 - tp
|
||||
MOVQ $0, SI // arg 2 - tzp
|
||||
MOVL $418, AX // sys_gettimeofday
|
||||
MOVQ $0, DI // arg 1 - clock_id
|
||||
LEAQ 8(SP), SI // arg 2 - tp
|
||||
MOVL $427, AX // sys_clock_gettime
|
||||
SYSCALL
|
||||
MOVQ 8(SP), AX // sec
|
||||
MOVL 16(SP), DX // usec
|
||||
MOVL 16(SP), DX // nsec
|
||||
|
||||
// sec is in AX, usec in DX
|
||||
// sec is in AX, nsec in DX
|
||||
MOVQ AX, sec+0(FP)
|
||||
IMULQ $1000, DX
|
||||
MOVL DX, nsec+8(FP)
|
||||
RET
|
||||
|
||||
TEXT runtime·nanotime(SB),7,$32
|
||||
LEAQ 8(SP), DI // arg 1 - tp
|
||||
MOVQ $0, SI // arg 2 - tzp
|
||||
MOVL $418, AX // sys_gettimeofday
|
||||
MOVQ $0, DI // arg 1 - clock_id
|
||||
LEAQ 8(SP), SI // arg 2 - tp
|
||||
MOVL $427, AX // sys_clock_gettime
|
||||
SYSCALL
|
||||
MOVQ 8(SP), AX // sec
|
||||
MOVL 16(SP), DX // usec
|
||||
MOVL 16(SP), DX // nsec
|
||||
|
||||
// sec is in AX, usec in DX
|
||||
// sec is in AX, nsec in DX
|
||||
// return nsec in AX
|
||||
IMULQ $1000000000, AX
|
||||
IMULQ $1000, DX
|
||||
ADDQ DX, AX
|
||||
RET
|
||||
|
||||
|
|
|
|||
|
|
@ -98,40 +98,38 @@ TEXT runtime·setitimer(SB),7,$-4
|
|||
|
||||
// func now() (sec int64, nsec int32)
|
||||
TEXT time·now(SB), 7, $32
|
||||
MOVL $116, AX
|
||||
MOVL $232, AX
|
||||
LEAL 12(SP), BX
|
||||
MOVL BX, 4(SP)
|
||||
MOVL $0, 8(SP)
|
||||
MOVL $0, 4(SP)
|
||||
MOVL BX, 8(SP)
|
||||
INT $0x80
|
||||
MOVL 12(SP), AX // sec
|
||||
MOVL 16(SP), BX // usec
|
||||
MOVL 16(SP), BX // nsec
|
||||
|
||||
// sec is in AX, usec in BX
|
||||
// sec is in AX, nsec in BX
|
||||
MOVL AX, sec+0(FP)
|
||||
MOVL $0, sec+4(FP)
|
||||
IMULL $1000, BX
|
||||
MOVL BX, nsec+8(FP)
|
||||
RET
|
||||
|
||||
// int64 nanotime(void) so really
|
||||
// void nanotime(int64 *nsec)
|
||||
TEXT runtime·nanotime(SB),7,$32
|
||||
MOVL $116, AX
|
||||
MOVL $232, AX
|
||||
LEAL 12(SP), BX
|
||||
MOVL BX, 4(SP)
|
||||
MOVL $0, 8(SP)
|
||||
MOVL $0, 4(SP)
|
||||
MOVL BX, 8(SP)
|
||||
INT $0x80
|
||||
MOVL 12(SP), AX // sec
|
||||
MOVL 16(SP), BX // usec
|
||||
MOVL 16(SP), BX // nsec
|
||||
|
||||
// sec is in AX, usec in BX
|
||||
// sec is in AX, nsec in BX
|
||||
// convert to DX:AX nsec
|
||||
MOVL $1000000000, CX
|
||||
MULL CX
|
||||
IMULL $1000, BX
|
||||
ADDL BX, AX
|
||||
ADCL $0, DX
|
||||
|
||||
|
||||
MOVL ret+0(FP), DI
|
||||
MOVL AX, 0(DI)
|
||||
MOVL DX, 4(DI)
|
||||
|
|
|
|||
|
|
@ -130,31 +130,29 @@ TEXT runtime·setitimer(SB),7,$-8
|
|||
|
||||
// func now() (sec int64, nsec int32)
|
||||
TEXT time·now(SB), 7, $32
|
||||
LEAQ 8(SP), DI // arg 1 - tp
|
||||
MOVQ $0, SI // arg 2 - tzp
|
||||
MOVL $116, AX // sys_gettimeofday
|
||||
MOVQ $0, DI // arg 1 - clock_id
|
||||
LEAQ 8(SP), SI // arg 2 - tp
|
||||
MOVL $232, AX // sys_clock_gettime
|
||||
SYSCALL
|
||||
MOVQ 8(SP), AX // sec
|
||||
MOVL 16(SP), DX // usec
|
||||
MOVL 8(SP), AX // sec
|
||||
MOVQ 16(SP), DX // nsec
|
||||
|
||||
// sec is in AX, usec in DX
|
||||
// sec is in AX, nsec in DX
|
||||
MOVQ AX, sec+0(FP)
|
||||
IMULQ $1000, DX
|
||||
MOVL DX, nsec+8(FP)
|
||||
RET
|
||||
|
||||
TEXT runtime·nanotime(SB),7,$32
|
||||
LEAQ 8(SP), DI // arg 1 - tp
|
||||
MOVQ $0, SI // arg 2 - tzp
|
||||
MOVL $116, AX // sys_gettimeofday
|
||||
MOVQ $0, DI // arg 1 - clock_id
|
||||
LEAQ 8(SP), SI // arg 2 - tp
|
||||
MOVL $232, AX // sys_clock_gettime
|
||||
SYSCALL
|
||||
MOVQ 8(SP), AX // sec
|
||||
MOVL 16(SP), DX // usec
|
||||
MOVL 8(SP), AX // sec
|
||||
MOVQ 16(SP), DX // nsec
|
||||
|
||||
// sec is in AX, usec in DX
|
||||
// sec is in AX, nsec in DX
|
||||
// return nsec in AX
|
||||
IMULQ $1000000000, AX
|
||||
IMULQ $1000, DX
|
||||
ADDQ DX, AX
|
||||
RET
|
||||
|
||||
|
|
|
|||
Loading…
Reference in New Issue