Skip to content

Commit

Permalink
uint256: optimize umul (MulOverflow, MulMod, MulModWithReciprocal, Mu…
Browse files Browse the repository at this point in the history
…lDivOverflow) (#166)
  • Loading branch information
AaronChen0 committed May 13, 2024
1 parent 34f0760 commit 5ecf78c
Showing 1 changed file with 9 additions and 8 deletions.
17 changes: 9 additions & 8 deletions uint256.go
Original file line number Diff line number Diff line change
Expand Up @@ -337,9 +337,8 @@ func umulHop(z, x, y uint64) (hi, lo uint64) {
}

// umul computes full 256 x 256 -> 512 multiplication.
func umul(x, y *Int) [8]uint64 {
func umul(x, y *Int, res *[8]uint64) {
var (
res [8]uint64
carry, carry4, carry5, carry6 uint64
res1, res2, res3, res4, res5 uint64
)
Expand All @@ -363,8 +362,6 @@ func umul(x, y *Int) [8]uint64 {
carry, res[4] = umulStep(res4, x[1], y[3], carry)
carry, res[5] = umulStep(res5, x[2], y[3], carry)
res[7], res[6] = umulStep(carry6, x[3], y[3], carry)

return res
}

// Mul sets z to the product x*y
Expand Down Expand Up @@ -394,7 +391,8 @@ func (z *Int) Mul(x, y *Int) *Int {

// MulOverflow sets z to the product x*y, and returns z and whether overflow occurred
func (z *Int) MulOverflow(x, y *Int) (*Int, bool) {
p := umul(x, y)
var p [8]uint64
umul(x, y, &p)
copy(z[:], p[:4])
return z, (p[4] | p[5] | p[6] | p[7]) != 0
}
Expand Down Expand Up @@ -675,7 +673,8 @@ func (z *Int) MulModWithReciprocal(x, y, m *Int, mu *[5]uint64) *Int {
if x.IsZero() || y.IsZero() || m.IsZero() {
return z.Clear()
}
p := umul(x, y)
var p [8]uint64
umul(x, y, &p)

if m[3] != 0 {
r := reduce4(p, m, *mu)
Expand Down Expand Up @@ -706,7 +705,8 @@ func (z *Int) MulMod(x, y, m *Int) *Int {
if x.IsZero() || y.IsZero() || m.IsZero() {
return z.Clear()
}
p := umul(x, y)
var p [8]uint64
umul(x, y, &p)

if m[3] != 0 {
mu := Reciprocal(m)
Expand Down Expand Up @@ -737,7 +737,8 @@ func (z *Int) MulDivOverflow(x, y, d *Int) (*Int, bool) {
if x.IsZero() || y.IsZero() || d.IsZero() {
return z.Clear(), false
}
p := umul(x, y)
var p [8]uint64
umul(x, y, &p)

var quot [8]uint64
udivrem(quot[:], p[:], d)
Expand Down

0 comments on commit 5ecf78c

Please sign in to comment.