Skip to content

math: add ARM64 implementation of frexp #47589

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 1 commit into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
12 changes: 11 additions & 1 deletion src/math/all_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -2541,7 +2541,7 @@ func TestFrexp(t *testing.T) {
}
}
for i := 0; i < len(vffrexpBC); i++ {
if f, j := Frexp(vffrexpBC[i]); !alike(frexpBC[i].f, f) || frexpBC[i].i != j {
if f, j := Frexp(vffrexpBC[i]); !veryclose(frexpBC[i].f, f) || frexpBC[i].i != j {
t.Errorf("Frexp(%g) = %g, %d, want %g, %d", vffrexpBC[i], f, j, frexpBC[i].f, frexpBC[i].i)
}
}
Expand Down Expand Up @@ -3467,6 +3467,16 @@ func BenchmarkFrexp(b *testing.B) {
GlobalI = y
}

func BenchmarkFrexpGO(b *testing.B) {
x := 0.0
y := 0
for i := 0; i < b.N; i++ {
x, y = FrexpGO(8)
}
GlobalF = x
GlobalI = y
}

func BenchmarkGamma(b *testing.B) {
x := 0.0
for i := 0; i < b.N; i++ {
Expand Down
6 changes: 0 additions & 6 deletions src/math/arith_s390x.go
Original file line number Diff line number Diff line change
Expand Up @@ -135,12 +135,6 @@ func archPow(x, y float64) float64
func powTrampolineSetup(x, y float64) float64
func powAsm(x, y float64) float64

const haveArchFrexp = false

func archFrexp(x float64) (float64, int) {
panic("not implemented")
}

const haveArchLdexp = false

func archLdexp(frac float64, exp int) float64 {
Expand Down
1 change: 1 addition & 0 deletions src/math/export_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ package math
var ExpGo = exp
var Exp2Go = exp2
var HypotGo = hypot
var FrexpGo = frexp
var SqrtGo = sqrt
var TrigReduce = trigReduce

Expand Down
57 changes: 57 additions & 0 deletions src/math/frexp_arm64.s
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
// Copyright 2021 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.

#include "textflag.h"

#define PosInf 0x7FF0000000000000
#define Float64SmallestNormal 2.2250738585072014e-308

// func archFrexp(x float64) (frac float64, exp int)
TEXT ·archFrexp(SB),NOSPLIT,$0-24
FMOVD x+0(FP), F0
MOVD ZR, R1 // R1 is the ret exp
FABSD F0, F3 // F3 is the absolute of 'x'
FCMPD $(0.0), F3 // avoid the input floating number is -0.0
BEQ isInfOrNaNOrZero

MOVD $PosInf, R3
FMOVD R3, F30 // F30 is PosInf
FCMPD F30, F3
BGE isInfOrNaNOrZero // isInf
FCMPED F0, F0
BNE isInfOrNaNOrZero // isNaN

FMOVD F3, R0
UBFX $52, R0, $11, R0

FMOVD $Float64SmallestNormal, F29
FCMPD F29, F3
BGE pass

// if abs(x) < SmallestNormal ,then run the following special case
FMOVD $(4503599627370496.0), F2 // 4503599627370496.0 is (1<<52)
FMULD F2, F0, F0
SUB $(52), R1, R1 // set R1 to -52
FMOVD F0, R0
// tmp = int((x>>shift)&mask)
UBFX $52, R0, $11, R0

pass:
// tmp = tmp - bias + 1
SUB $0x3FE, R0, R3
// exp = exp + tmp
ADD R3, R1, R1

FMOVD F0, R0
AND $0x800FFFFFFFFFFFFF, R0, R0
ORR $0x3FE0000000000000, R0, R0
FMOVD R0, F0
FMOVD F0, frac+8(FP)
MOVD R1, exp+16(FP)
RET

isInfOrNaNOrZero:
FMOVD F0, frac+8(FP)
MOVD R1, exp+16(FP)
RET
12 changes: 12 additions & 0 deletions src/math/frexp_asm.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
// Copyright 2021 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 arm64
// +build arm64

package math

const haveArchFrexp = true

func archFrexp(x float64) (frac float64, exp int)
14 changes: 14 additions & 0 deletions src/math/frexp_noasm.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
// Copyright 2021 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 !arm64
// +build !arm64

package math

const haveArchFrexp = false

func archFrexp(x float64) (frac float64, exp int)
panic("not implemented")
}
6 changes: 0 additions & 6 deletions src/math/stubs.go
Original file line number Diff line number Diff line change
Expand Up @@ -88,12 +88,6 @@ func archExpm1(x float64) float64 {
panic("not implemented")
}

const haveArchFrexp = false

func archFrexp(x float64) (float64, int) {
panic("not implemented")
}

const haveArchLdexp = false

func archLdexp(frac float64, exp int) float64 {
Expand Down