golang / go

The Go programming language
https://go.dev
BSD 3-Clause "New" or "Revised" License
123.24k stars 17.57k forks source link

runtime: better support for 64bit div/mod operations on 32bit platforms #19509

Open martisch opened 7 years ago

martisch commented 7 years ago

encountered in https://go-review.googlesource.com/c/38071/:

assuming x and y are uint64:

q = x/y 
r = x%y

only uses a single DIV instruction on amd64 however on 386 this makes a runtime call to uint64div and one to uint64mod.

1) Both could be handled calculated together in a combined uint64divmod runtime call 2) In case y is constant the compiler could optimize the calculation to not require a div and not need a runtime call

martisch commented 7 years ago

If these optimizations sound reasonable i can work on this for 1.9/1.10 after i have my current projects for 1.9 are submitted.

josharian commented 7 years ago

Both could be handled calculated together in a combined uint64divmod runtime call

SGTM. We even already have this, although it's called dodiv at the moment.

In case y is constant the compiler could optimize the calculation to not require a div and not need a runtime call

The compiler should already do this. Worth double-checking, though.

josharian commented 7 years ago

It's probably also work taking a brief look at the code that the compiler generates for vlrt.go. It was tuned for the old backend.

martisch commented 7 years ago

about 2. I checked before and after the issue creation :)

The compiler does not simplify a div with 64bit operands on 32bit:

var x uint64

func main() {
    y := x / 10
    print(y)
}

uses a "CALL runtime.uint64div(SB)"

josharian commented 7 years ago

:) I see.

Both seem worth fixing, then.

Independently, I wonder whether it's worth adding an int32 code path, where we do all the work with int32s instead of int64s, for values that fit in 32 bits (which is probably almost all of them in practice). Might even be cheaper on 64 bit machines. Probably worth a benchmarking experiment.