Skip to content

Commit

Permalink
Merge pull request #60 from hunshenshi/initState
Browse files Browse the repository at this point in the history
Add HashWithState to increase its scalability
  • Loading branch information
OBrezhniev authored Feb 16, 2024
2 parents 3fb23d7 + 07712e5 commit 36c5a14
Show file tree
Hide file tree
Showing 2 changed files with 53 additions and 3 deletions.
15 changes: 12 additions & 3 deletions poseidon/poseidon.go
Original file line number Diff line number Diff line change
Expand Up @@ -61,8 +61,8 @@ func mix(state []*ff.Element, t int, m [][]*ff.Element) []*ff.Element {
return newState
}

// Hash computes the Poseidon hash for the given inputs
func Hash(inpBI []*big.Int) (*big.Int, error) {
// HashWithState computes the Poseidon hash for the given inputs and initState
func HashWithState(inpBI []*big.Int, initState *big.Int) (*big.Int, error) {
t := len(inpBI) + 1
if len(inpBI) == 0 || len(inpBI) > len(NROUNDSP) {
return nil, fmt.Errorf("invalid inputs length %d, max %d", len(inpBI), len(NROUNDSP))
Expand All @@ -80,7 +80,11 @@ func Hash(inpBI []*big.Int) (*big.Int, error) {
P := c.p[t-2]

state := make([]*ff.Element, t)
state[0] = zero()
if !utils.CheckBigIntInField(initState) {
return nil, errors.New("initState values not inside Finite Field")
}

state[0] = ff.NewElement().SetBigInt(initState)
copy(state[1:], inp)

ark(state, C, 0)
Expand Down Expand Up @@ -127,6 +131,11 @@ func Hash(inpBI []*big.Int) (*big.Int, error) {
return r, nil
}

// Hash computes the Poseidon hash for the given inputs
func Hash(inpBI []*big.Int) (*big.Int, error) {
return HashWithState(inpBI, big.NewInt(0))
}

// HashBytes returns a sponge hash of a msg byte slice split into blocks of 31 bytes
func HashBytes(msg []byte) (*big.Int, error) {
return HashBytesX(msg, spongeInputs)
Expand Down
41 changes: 41 additions & 0 deletions poseidon/poseidon_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -128,6 +128,47 @@ func TestInputsNotInField(t *testing.T) {
require.Error(t, err, "inputs values not inside Finite Field")
}

func TestHashWithState(t *testing.T) {
initState0 := big.NewInt(0)
initState1 := big.NewInt(7)

b1 := big.NewInt(1)
b2 := big.NewInt(2)
b3 := big.NewInt(3)
b4 := big.NewInt(4)
b5 := big.NewInt(5)
b6 := big.NewInt(6)

h, err := HashWithState([]*big.Int{b1, b2, b3, b4, b5, b6}, initState0)
assert.Nil(t, err)
assert.Equal(t,
"20400040500897583745843009878988256314335038853985262692600694741116813247201",
h.String())

h, err = HashWithState([]*big.Int{b1, b2, b3, b4}, initState1)
assert.Nil(t, err)
assert.Equal(t,
"1569211601569591254857354699102545060324851338714426496554851741114291465006",
h.String())
}

func TestInitStateNotInField(t *testing.T) {
var err error

b0 := big.NewInt(0)
b1 := big.NewInt(1)

// Very big number, should just return error and not go into endless loop
initState := utils.NewIntFromString("12242166908188651009877250812424843524687801523336557272219921456462821518061999999999999999999999999999999999999999999999999999999999")
_, err = HashWithState([]*big.Int{b0, b1}, initState)
require.Error(t, err, "initState values not inside Finite Field")

// Finite Field const Q, should return error
initState = utils.NewIntFromString("21888242871839275222246405745257275088548364400416034343698204186575808495617")
_, err = HashWithState([]*big.Int{b0, b1}, initState)
require.Error(t, err, "initState values not inside Finite Field")
}

func TestHashBytes(t *testing.T) {
type testVector struct {
bytes string
Expand Down

0 comments on commit 36c5a14

Please sign in to comment.