diff options
author | Shenghou Ma <minux@golang.org> | 2016-08-04 21:34:06 -0400 |
---|---|---|
committer | Minux Ma <minux@golang.org> | 2016-08-05 20:47:34 +0000 |
commit | 9fde86b0124b8c75000eb5d05887eff922a24566 (patch) | |
tree | c59a36760e14ae00e3ffe8181c0aa03263d2d557 | |
parent | 3a03e877cc03c1fd155055e60a3f1f9cb8bda8d0 (diff) | |
download | go-9fde86b0124b8c75000eb5d05887eff922a24566.tar.gz go-9fde86b0124b8c75000eb5d05887eff922a24566.zip |
runtime, syscall: fix kernel gettimeofday ABI change on iOS 10
Fixes #16570 on iOS.
Thanks Daniel Burhans for reporting the bug and testing the fix.
Change-Id: I43ae7b78c8f85a131ed3d93ea59da9f32a02cd8f
Reviewed-on: https://go-review.googlesource.com/25481
Reviewed-by: Ian Lance Taylor <iant@golang.org>
Reviewed-by: Brad Fitzpatrick <bradfitz@golang.org>
-rw-r--r-- | src/runtime/sys_darwin_arm.s | 15 | ||||
-rw-r--r-- | src/runtime/sys_darwin_arm64.s | 14 | ||||
-rw-r--r-- | src/syscall/syscall_darwin_arm.go | 13 | ||||
-rw-r--r-- | src/syscall/syscall_darwin_arm64.go | 13 | ||||
-rw-r--r-- | src/syscall/syscall_darwin_test.go | 2 |
5 files changed, 43 insertions, 14 deletions
diff --git a/src/runtime/sys_darwin_arm.s b/src/runtime/sys_darwin_arm.s index 6b6437dddd..52f6a94d46 100644 --- a/src/runtime/sys_darwin_arm.s +++ b/src/runtime/sys_darwin_arm.s @@ -162,11 +162,15 @@ TEXT runtime·mincore(SB),NOSPLIT,$0 TEXT time·now(SB), 7, $32 MOVW $8(R13), R0 // timeval MOVW $0, R1 // zone + MOVW $0, R2 // see issue 16570 MOVW $SYS_gettimeofday, R12 SWI $0x80 // Note: R0 is tv_sec, R1 is tv_usec - + CMP $0, R0 + BNE inreg + MOVW 8(R13), R0 + MOVW 12(R13), R1 +inreg: MOVW R1, R2 // usec - MOVW R0, sec+0(FP) MOVW $0, R1 MOVW R1, loc+4(FP) @@ -178,9 +182,14 @@ TEXT time·now(SB), 7, $32 TEXT runtime·nanotime(SB),NOSPLIT,$32 MOVW $8(R13), R0 // timeval MOVW $0, R1 // zone + MOVW $0, R2 // see issue 16570 MOVW $SYS_gettimeofday, R12 SWI $0x80 // Note: R0 is tv_sec, R1 is tv_usec - + CMP $0, R0 + BNE inreg + MOVW 8(R13), R0 + MOVW 12(R13), R1 +inreg: MOVW R1, R2 MOVW $1000000000, R3 MULLU R0, R3, (R1, R0) diff --git a/src/runtime/sys_darwin_arm64.s b/src/runtime/sys_darwin_arm64.s index a3b851d2fc..8e6b5b1ebf 100644 --- a/src/runtime/sys_darwin_arm64.s +++ b/src/runtime/sys_darwin_arm64.s @@ -155,9 +155,14 @@ TEXT time·now(SB),NOSPLIT,$40-12 MOVD RSP, R0 // timeval MOVD R0, R9 // this is how dyld calls gettimeofday MOVW $0, R1 // zone + MOVD $0, R2 // see issue 16570 MOVW $SYS_gettimeofday, R16 SVC $0x80 // Note: x0 is tv_sec, w1 is tv_usec - + CMP $0, R0 + BNE inreg + MOVD 0(RSP), R0 + MOVW 8(RSP), R1 +inreg: MOVD R0, sec+0(FP) MOVW $1000, R3 MUL R3, R1 @@ -168,9 +173,14 @@ TEXT runtime·nanotime(SB),NOSPLIT,$40 MOVD RSP, R0 // timeval MOVD R0, R9 // this is how dyld calls gettimeofday MOVW $0, R1 // zone + MOVD $0, R2 // see issue 16570 MOVW $SYS_gettimeofday, R16 SVC $0x80 // Note: x0 is tv_sec, w1 is tv_usec - + CMP $0, R0 + BNE inreg + MOVD 0(RSP), R0 + MOVW 8(RSP), R1 +inreg: MOVW $1000000000, R3 MUL R3, R0 MOVW $1000, R3 diff --git a/src/syscall/syscall_darwin_arm.go b/src/syscall/syscall_darwin_arm.go index c302d83131..fe431039f4 100644 --- a/src/syscall/syscall_darwin_arm.go +++ b/src/syscall/syscall_darwin_arm.go @@ -26,14 +26,19 @@ func NsecToTimeval(nsec int64) (tv Timeval) { } //sysnb gettimeofday(tp *Timeval) (sec int32, usec int32, err error) -func Gettimeofday(tv *Timeval) (err error) { +func Gettimeofday(tv *Timeval) error { // The tv passed to gettimeofday must be non-nil // but is otherwise unused. The answers come back // in the two registers. sec, usec, err := gettimeofday(tv) - tv.Sec = int32(sec) - tv.Usec = int32(usec) - return err + if err != nil { + return err + } + if sec != 0 || usec != 0 { + tv.Sec = int32(sec) + tv.Usec = int32(usec) + } + return nil } func SetKevent(k *Kevent_t, fd, mode, flags int) { diff --git a/src/syscall/syscall_darwin_arm64.go b/src/syscall/syscall_darwin_arm64.go index 29f40d4229..d396e25332 100644 --- a/src/syscall/syscall_darwin_arm64.go +++ b/src/syscall/syscall_darwin_arm64.go @@ -26,14 +26,19 @@ func NsecToTimeval(nsec int64) (tv Timeval) { } //sysnb gettimeofday(tp *Timeval) (sec int64, usec int32, err error) -func Gettimeofday(tv *Timeval) (err error) { +func Gettimeofday(tv *Timeval) error { // The tv passed to gettimeofday must be non-nil // but is otherwise unused. The answers come back // in the two registers. sec, usec, err := gettimeofday(tv) - tv.Sec = sec - tv.Usec = usec - return err + if err != nil { + return err + } + if sec != 0 || usec != 0 { + tv.Sec = sec + tv.Usec = usec + } + return nil } func SetKevent(k *Kevent_t, fd, mode, flags int) { diff --git a/src/syscall/syscall_darwin_test.go b/src/syscall/syscall_darwin_test.go index dd0e32b968..cea5636d07 100644 --- a/src/syscall/syscall_darwin_test.go +++ b/src/syscall/syscall_darwin_test.go @@ -3,7 +3,7 @@ // license that can be found in the LICENSE file. // +build darwin -// +build amd64 386 +// +build amd64 386 arm arm64 package syscall_test |